spice netlisting of schematics with parametrized symbol generators should work
This commit is contained in:
parent
bbb5363da9
commit
3facbf6428
|
|
@ -216,17 +216,23 @@ int set_netlist_dir(int force, char *dir)
|
|||
}
|
||||
return 1;
|
||||
}
|
||||
/* wrapper to TCL function */
|
||||
/* remove parameter section of symbol generator before calculating abs path : xxx(a,b) -> xxx */
|
||||
const char *sanitized_abs_sym_path(const char *s, const char *ext)
|
||||
{
|
||||
char c[PATH_MAX+1000];
|
||||
|
||||
my_snprintf(c, S(c), "abs_sym_path [regsub {\\(.*} {%s} {}] {%s}", s, ext);
|
||||
tcleval(c);
|
||||
return tclresult();
|
||||
}
|
||||
|
||||
/* wrapper to TCL function */
|
||||
const char *abs_sym_path(const char *s, const char *ext)
|
||||
{
|
||||
char c[PATH_MAX+1000];
|
||||
|
||||
if(is_symgen(s)) {
|
||||
my_snprintf(c, S(c), "abs_sym_path [regsub {\\(.*} {%s} {}] {%s}", s, ext);
|
||||
} else {
|
||||
my_snprintf(c, S(c), "abs_sym_path {%s} {%s}", s, ext);
|
||||
}
|
||||
my_snprintf(c, S(c), "abs_sym_path {%s} {%s}", s, ext);
|
||||
tcleval(c);
|
||||
return tclresult();
|
||||
}
|
||||
|
|
@ -1215,6 +1221,7 @@ const char *get_sym_name(int inst, int ext)
|
|||
} else {
|
||||
sym = skip_dir(xctx->inst[inst].name);
|
||||
}
|
||||
dbg(1, "get_sym_name(): returning sym=%s\n", sym);
|
||||
return sym;
|
||||
}
|
||||
|
||||
|
|
@ -1559,6 +1566,7 @@ void go_back(int confirm) /* 20171006 add confirm */
|
|||
int prev_sch_type;
|
||||
|
||||
save_ok=1;
|
||||
dbg(1,"go_back(): sch[xctx->currsch]=%s\n", xctx->sch[xctx->currsch]);
|
||||
prev_sch_type = xctx->netlist_type; /* if CAD_SYMBOL_ATTRS do not hilight_parent_pins */
|
||||
if(xctx->currsch>0)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1094,6 +1094,25 @@ int xschem(ClientData clientdata, Tcl_Interp *interp, int argc, const char * arg
|
|||
} /* switch */
|
||||
}
|
||||
}
|
||||
|
||||
/* get_cell cell n_dirs
|
||||
* return result of get_cell function */
|
||||
else if(!strcmp(argv[1], "get_cell") )
|
||||
{
|
||||
if(argc > 3) {
|
||||
Tcl_SetResult(interp, (char *)get_cell(argv[2], atoi(argv[3])), TCL_VOLATILE);
|
||||
}
|
||||
}
|
||||
|
||||
/* get_cell_w_ext cell n_dirs
|
||||
* return result of get_cell_w_ext function */
|
||||
else if(!strcmp(argv[1], "get_cell_w_ext") )
|
||||
{
|
||||
if(argc > 3) {
|
||||
Tcl_SetResult(interp, (char *)get_cell_w_ext(argv[2], atoi(argv[3])), TCL_VOLATILE);
|
||||
}
|
||||
}
|
||||
|
||||
/************ end xschem get subcommands *************/
|
||||
/* getprop instance|instance_pin|symbol|text ref
|
||||
*
|
||||
|
|
|
|||
|
|
@ -552,13 +552,15 @@ int spice_block_netlist(FILE *fd, int i)
|
|||
fprintf(fd, "\n* expanding symbol: %s # of pins=%d\n",
|
||||
xctx->sym[i].name,xctx->sym[i].rects[PINLAYER] );
|
||||
if(xctx->sym[i].base_name) fprintf(fd, "** sym_path: %s\n", abs_sym_path(xctx->sym[i].base_name, ""));
|
||||
else fprintf(fd, "** sym_path: %s\n", abs_sym_path(xctx->sym[i].name, ""));
|
||||
else fprintf(fd, "** sym_path: %s\n", sanitized_abs_sym_path(xctx->sym[i].name, ""));
|
||||
sym_def = get_tok_value(xctx->sym[i].prop_ptr,"spice_sym_def",0);
|
||||
if(sym_def[0]) {
|
||||
fprintf(fd, "%s\n", sym_def);
|
||||
} else {
|
||||
char *s = sanitize(skip_dir(xctx->sym[i].name));
|
||||
fprintf(fd, "** sch_path: %s\n", filename);
|
||||
fprintf(fd, ".subckt %s ",skip_dir(xctx->sym[i].name));
|
||||
fprintf(fd, ".subckt %s ", s);
|
||||
my_free(_ALLOC_ID_, &s);
|
||||
print_spice_subckt_nodes(fd, i);
|
||||
|
||||
my_strdup(_ALLOC_ID_, &extra, get_tok_value(xctx->sym[i].prop_ptr,"extra",0) );
|
||||
|
|
|
|||
29
src/token.c
29
src/token.c
|
|
@ -187,6 +187,17 @@ int is_symgen(const char *name)
|
|||
#endif
|
||||
}
|
||||
|
||||
/* caller must free returned string
|
||||
* cleanup syntax of symbol generators: xxx(a,b,c) --> xxx_a_b_c */
|
||||
char *sanitize(const char *name)
|
||||
{
|
||||
char *s = NULL;
|
||||
tclvareval("regsub -all { *[(),] *} {", name, "} _", NULL);
|
||||
tclvareval("regsub {_$} {", tclresult(), "} {}", NULL);
|
||||
my_strdup2(_ALLOC_ID_, &s, tclresult());
|
||||
return s;
|
||||
}
|
||||
|
||||
int match_symbol(const char *name) /* never returns -1, if symbol not found load systemlib/missing.sym */
|
||||
{
|
||||
int i,found;
|
||||
|
|
@ -215,25 +226,34 @@ int match_symbol(const char *name) /* never returns -1, if symbol not found loa
|
|||
const char *s;
|
||||
char *spc_idx;
|
||||
struct stat buf;
|
||||
/* char *symgen_name = NULL; */
|
||||
|
||||
dbg(1, "match_symbol(): symgen=%s\n",name);
|
||||
cmd = str_chars_replace(name, " (),", ' ');
|
||||
cmd = str_chars_replace(name, " (),", ' '); /* transform name="xxx(a,b,c)" into ss="xxx a b c" */
|
||||
spc_idx = strchr(cmd, ' ');
|
||||
if(!spc_idx) goto end;
|
||||
*spc_idx = '\0';
|
||||
s = abs_sym_path(cmd, "");
|
||||
if(stat(s, &buf)) {
|
||||
if(stat(s, &buf)) { /* symbol generator not found, load 'name' (will probably lead to missing.sym) */
|
||||
load_sym_def(name, NULL, 0);
|
||||
goto end;
|
||||
}
|
||||
my_strdup(_ALLOC_ID_, &ss, s);
|
||||
*spc_idx = ' ';
|
||||
my_strcat(_ALLOC_ID_, &ss, spc_idx);
|
||||
fp = popen(ss, "r");
|
||||
fp = popen(ss, "r"); /* execute ss="xxx a b c" and pipe in the output */
|
||||
dbg(1, "match_symbol(): fp=%p\n", fp);
|
||||
dbg(1, "match_symbol(): s=%s\n", s);
|
||||
dbg(1, "match_symbol(): ss=%s\n", ss);
|
||||
dbg(1, "match_symbol(): is_symgen=%d\n", is_symgen(name));
|
||||
/*
|
||||
tclvareval("regsub -all { *[(),] *} {", name, "} _", NULL);
|
||||
tclvareval("regsub {_$} {", tclresult(), "} {}", NULL);
|
||||
my_strdup2(_ALLOC_ID_, &symgen_name, tclresult());
|
||||
load_sym_def(symgen_name, fp, 1);
|
||||
dbg(1, "match_symbol(): name=%s, regsub=%s\n", name, symgen_name);
|
||||
my_free(_ALLOC_ID_, &symgen_name);
|
||||
*/
|
||||
load_sym_def(name, fp, 1);
|
||||
dbg(1, "match_symbol(): symbol name%s\n", xctx->sym[xctx->symbols - 1].name);
|
||||
pclose(fp);
|
||||
|
|
@ -1861,11 +1881,12 @@ int print_spice_element(FILE *fd, int inst)
|
|||
}
|
||||
else if (strcmp(token,"@symname")==0) /* of course symname must not be present in attributes */
|
||||
{
|
||||
const char *s = get_sym_name(inst, 0);
|
||||
char *s = sanitize(get_sym_name(inst, 0));
|
||||
tmp = strlen(s) +100 ; /* always make room for some extra chars
|
||||
* so 1-char writes to result do not need reallocs */
|
||||
STR_ALLOC(&result, tmp + result_pos, &size);
|
||||
result_pos += my_snprintf(result + result_pos, tmp, "%s", s);
|
||||
my_free(_ALLOC_ID_, &s);
|
||||
/* fputs(s,fd); */
|
||||
}
|
||||
else if (strcmp(token,"@symname_ext")==0) /* of course symname must not be present in attributes */
|
||||
|
|
|
|||
|
|
@ -1157,6 +1157,8 @@ extern const char *get_cell(const char *str, int no_of_dir);
|
|||
extern const char *get_cell_w_ext(const char *str, int no_of_dir);
|
||||
extern const char *rel_sym_path(const char *s);
|
||||
extern const char *abs_sym_path(const char *s, const char *ext);
|
||||
extern const char *sanitized_abs_sym_path(const char *s, const char *ext);
|
||||
extern char *sanitize(const char *name);
|
||||
extern const char *add_ext(const char *f, const char *ext);
|
||||
extern void make_symbol(void);
|
||||
/* sort based on pinnumber pin attribute if present */
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ C {bsource.sym} 480 -330 0 1 {name=B1 VAR=V FUNC="'VCC/2*(1+tanh((min(V(C1),min(
|
|||
C {lab_pin.sym} 310 -400 0 0 {name=l2 sig_type=std_logic lab=A1}
|
||||
C {lab_pin.sym} 480 -250 0 0 {name=l3 sig_type=std_logic lab=0}
|
||||
C {res.sym} 580 -400 1 0 {name=R1
|
||||
value=ROUT
|
||||
value='ROUT'
|
||||
footprint=1206
|
||||
device=resistor
|
||||
m=1}
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ C {bsource.sym} 480 -330 0 1 {name=B1 VAR=V FUNC="'VCC/2*(1+tanh((min(V(A1),V(B1
|
|||
C {lab_pin.sym} 330 -400 0 0 {name=l2 sig_type=std_logic lab=A1}
|
||||
C {lab_pin.sym} 480 -250 0 0 {name=l3 sig_type=std_logic lab=0}
|
||||
C {res.sym} 580 -400 1 0 {name=R1
|
||||
value=ROUT
|
||||
value='ROUT'
|
||||
footprint=1206
|
||||
device=resistor
|
||||
m=1}
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ C {bsource.sym} 470 -400 0 1 {name=B1 VAR=V FUNC="'VCC/2*(1+tanh((V(A1)-VCC/2)*1
|
|||
C {lab_pin.sym} 320 -470 0 0 {name=l2 sig_type=std_logic lab=A1}
|
||||
C {lab_pin.sym} 470 -320 0 0 {name=l3 sig_type=std_logic lab=0}
|
||||
C {res.sym} 570 -470 1 0 {name=R1
|
||||
value=ROUT
|
||||
value='ROUT'
|
||||
footprint=1206
|
||||
device=resistor
|
||||
m=1}
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ C {bsource.sym} 470 -400 0 1 {name=B1 VAR=V FUNC="'VCC/2*(1-tanh((V(A1)-VCC/2)*1
|
|||
C {lab_pin.sym} 320 -470 0 0 {name=l2 sig_type=std_logic lab=A1}
|
||||
C {lab_pin.sym} 470 -320 0 0 {name=l3 sig_type=std_logic lab=0}
|
||||
C {res.sym} 570 -470 1 0 {name=R1
|
||||
value=ROUT
|
||||
value='ROUT'
|
||||
footprint=1206
|
||||
device=resistor
|
||||
m=1}
|
||||
|
|
|
|||
Loading…
Reference in New Issue