Merge branch 'master' into ananthchellappa
This commit is contained in:
commit
1d1ff164fb
|
|
@ -63,7 +63,7 @@ symrec *tptr; /* For returning symbol-table pointers */
|
|||
}
|
||||
|
||||
%token STREND 0
|
||||
%token <c> CHAR
|
||||
%token <c> XCHAR
|
||||
%token EXPR /* expr( */
|
||||
%token <val> NUM /* Simple double precision number */
|
||||
%token <tptr> FNCT /* Variable and Function */
|
||||
|
|
@ -81,7 +81,7 @@ input:
|
|||
;
|
||||
|
||||
line:
|
||||
CHAR {get_char($1);}
|
||||
XCHAR {get_char($1);}
|
||||
| EXPR exp ')' {get_expr($2);lex_state = 0;}
|
||||
| EXPR '\'' exp '\'' ')' {get_expr($3);lex_state = 0;}
|
||||
| EXPR exp error
|
||||
|
|
@ -216,8 +216,8 @@ static int kklex()
|
|||
c = *str++;
|
||||
if(c) {
|
||||
kklval.c = c;
|
||||
dbg(dbglev, "lex(): CHAR; %c\n", c);
|
||||
return CHAR;
|
||||
dbg(dbglev, "lex(): XCHAR; %c\n", c);
|
||||
return XCHAR;
|
||||
} else {
|
||||
dbg(dbglev, "lex(): STREND\n");
|
||||
return STREND;
|
||||
|
|
|
|||
95
src/token.c
95
src/token.c
|
|
@ -1174,26 +1174,34 @@ static void print_vhdl_primitive(FILE *fd, int inst) /* netlist primitives, 200
|
|||
|
||||
if(c=='\0')
|
||||
{
|
||||
/* do one level of substitutions to resolve remaining @params and/or tcl expr/code */
|
||||
if(result) {
|
||||
dbg(1, "print_vhdl_primitive(): before translate() result=%s\n", result);
|
||||
if(!strcmp(xctx->sym[xctx->inst[inst].ptr].type, "netlist_commands")) {
|
||||
/* since netlist_commands often have @ characters in spice node save / plot commands, do
|
||||
* not pass through translate, unless a tcleval(...) is present */
|
||||
if(strstr(result, "tcleval(")== result) {
|
||||
my_strdup(_ALLOC_ID_, &result, translate(inst, result));
|
||||
}
|
||||
} else {
|
||||
my_strdup(_ALLOC_ID_, &result, translate(inst, result));
|
||||
}
|
||||
dbg(1, "print_vhdl_primitive(): after translate() result=%s\n", result);
|
||||
}
|
||||
if(result) fprintf(fd, "%s", result);
|
||||
fputc('\n',fd);
|
||||
fprintf(fd, "---- end primitive\n");
|
||||
break ;
|
||||
/* if result is like: 'tcleval(some_string)' pass it thru tcl evaluation so expressions
|
||||
* can be calculated. Before that do also a round of translation to remove remaining @params */
|
||||
if(result) {
|
||||
dbg(1, "print_verilog_primitive(): before translate3() result=%s\n", result);
|
||||
if(strchr(result, '@')) {
|
||||
/* netlist_commands often have @ characters due to ngspice syntax. Do not translate */
|
||||
if(strcmp(xctx->sym[xctx->inst[inst].ptr].type, "netlist_commands")) {
|
||||
my_strdup2(_ALLOC_ID_, &result, translate3(result, 0, xctx->inst[inst].prop_ptr, NULL, NULL, NULL));
|
||||
/* can not put template in above translate3: ------------------------------------^^^^
|
||||
* if instance has VHI=VHI, format string has VHI=@VHI, and symbol template has VHI=3
|
||||
* we do not want token @VHI to resolve to 3, but stop at VHI as specified in instance */
|
||||
if(strchr(result, '@')) {
|
||||
my_strdup2(_ALLOC_ID_, &result, translate3(result, 2, template, NULL, NULL, NULL));
|
||||
}
|
||||
}
|
||||
}
|
||||
my_strdup2(_ALLOC_ID_, &result, tcl_hook2(result)); /* tcl evaluation if tcleval(....) */
|
||||
if(strstr(result, "expr(") ) {
|
||||
result = eval_expr(result);
|
||||
}
|
||||
dbg(1, "print_verilog_primitive(): after translate3() result=%s\n", result);
|
||||
}
|
||||
if(result) fprintf(fd, "%s", result);
|
||||
fputc('\n',fd);
|
||||
fprintf(fd, "---- end primitive\n");
|
||||
break ;
|
||||
}
|
||||
}
|
||||
} /* while(1) */
|
||||
my_free(_ALLOC_ID_, &result);
|
||||
my_free(_ALLOC_ID_, &template);
|
||||
my_free(_ALLOC_ID_, &format);
|
||||
|
|
@ -2398,7 +2406,13 @@ int print_spice_element(FILE *fd, int inst)
|
|||
* model=nfet_01v8
|
||||
*/
|
||||
my_strdup2(_ALLOC_ID_, &val,
|
||||
translate3(token, 2, xctx->inst[inst].prop_ptr, parent_prop_ptr, template, NULL));
|
||||
translate3(token, 0, xctx->inst[inst].prop_ptr, parent_prop_ptr, NULL, NULL));
|
||||
/* can not put template in above translate3: ---------------------------^^^^
|
||||
* if instance has VHI=VHI, format string has VHI=@VHI, and symbol template has VHI=3
|
||||
* we do not want token @VHI to resolve to 3, but stop at VHI as specified in instance */
|
||||
if(strchr(val, '@')) {
|
||||
my_strdup2(_ALLOC_ID_, &val, translate3(val, 0, template, NULL, NULL, NULL));
|
||||
}
|
||||
/* nmos instance format string: @model --> @modeln */
|
||||
dbg(1, "print_spice_element(): 1st round: val: |%s|\n", val);
|
||||
if(strchr(val, '@')) {
|
||||
|
|
@ -2428,12 +2442,10 @@ int print_spice_element(FILE *fd, int inst)
|
|||
}
|
||||
dbg(1, "print_spice_element(): final: val: |%s|\n", val);
|
||||
}
|
||||
value = val;
|
||||
/* xctx->tok_size==0 (set in translate3()) indicates that token(+1) does not exist
|
||||
* in instance attributes so try to get from symbol template */
|
||||
dbg(1, "print_spice_element(): val: %s\n", val);
|
||||
/* still unresolved: set to empty */
|
||||
if(val[0] == '@') value = "";
|
||||
else value = val;
|
||||
token_exists = xctx->tok_size;
|
||||
value = val;
|
||||
tok_val_len = strlen(value);
|
||||
/* @spiceprefix needs a special tag for postprocessing */
|
||||
if(!strcmp(token, "@spiceprefix") && value[0]) {
|
||||
|
|
@ -3109,26 +3121,35 @@ static void print_verilog_primitive(FILE *fd, int inst) /* netlist switch level
|
|||
}
|
||||
if(c=='\0')
|
||||
{
|
||||
/* do one level of substitutions to resolve remaining @params and/or tcl expr/code */
|
||||
/* if result is like: 'tcleval(some_string)' pass it thru tcl evaluation so expressions
|
||||
* can be calculated. Before that do also a round of translation to remove remaining @params */
|
||||
if(result) {
|
||||
dbg(1, "print_verilog_primitive(): before translate() result=%s\n", result);
|
||||
if(!strcmp(xctx->sym[xctx->inst[inst].ptr].type, "netlist_commands")) {
|
||||
/* since netlist_commands often have @ characters in spice node save / plot commands, do
|
||||
* not pass through translate, unless a tcleval(...) is present */
|
||||
if(strstr(result, "tcleval(")== result) {
|
||||
my_strdup(_ALLOC_ID_, &result, translate(inst, result));
|
||||
dbg(1, "print_verilog_primitive(): before translate3() result=%s\n", result);
|
||||
if(strchr(result, '@')) {
|
||||
/* netlist_commands often have @ characters due to ngspice syntax. Do not translate */
|
||||
if(strcmp(xctx->sym[xctx->inst[inst].ptr].type, "netlist_commands")) {
|
||||
my_strdup2(_ALLOC_ID_, &result, translate3(result, 0, xctx->inst[inst].prop_ptr, NULL, NULL, NULL));
|
||||
/* can not put template in above translate3: ------------------------------------^^^^
|
||||
* if instance has VHI=VHI, format string has VHI=@VHI, and symbol template has VHI=3
|
||||
* we do not want token @VHI to resolve to 3, but stop at VHI as specified in instance */
|
||||
if(strchr(result, '@')) {
|
||||
my_strdup2(_ALLOC_ID_, &result, translate3(result, 2, template, NULL, NULL, NULL));
|
||||
}
|
||||
|
||||
}
|
||||
} else {
|
||||
my_strdup(_ALLOC_ID_, &result, translate(inst, result));
|
||||
}
|
||||
dbg(1, "print_verilog_primitive(): after translate() result=%s\n", result);
|
||||
my_strdup2(_ALLOC_ID_, &result, tcl_hook2(result)); /* tcl evaluation if tcleval(....) */
|
||||
if(strstr(result, "expr(") ) {
|
||||
result = eval_expr(result);
|
||||
}
|
||||
dbg(1, "print_verilog_primitive(): after translate3() result=%s\n", result);
|
||||
}
|
||||
if(result) fprintf(fd, "%s", result);
|
||||
fputc('\n',fd);
|
||||
fprintf(fd, "---- end primitive\n");
|
||||
break ;
|
||||
}
|
||||
}
|
||||
} /* while(1) */
|
||||
my_free(_ALLOC_ID_, &result);
|
||||
my_free(_ALLOC_ID_, &template);
|
||||
my_free(_ALLOC_ID_, &format);
|
||||
|
|
@ -3789,7 +3810,7 @@ const char *translate(int inst, const char* s)
|
|||
/* @spice_get_current(...) or @spice_get_modelparam(...) */
|
||||
/* @spice_get_modelvoltage(...) or @spice_get_modelvoltage_param(...) */
|
||||
regcomp(get_sp_cur,
|
||||
"^@spice_get_(current|modelparam|modelvoltage)(_[a-zA-Z][a-zA-Z0-9_]*)*\\(", REG_NOSUB | REG_EXTENDED);
|
||||
"^@spice_get_(current|modelparam|modelvoltage)([_a-zA-Z][a-zA-Z0-9_]*)*\\(", REG_NOSUB | REG_EXTENDED);
|
||||
}
|
||||
|
||||
sp_prefix = tclgetboolvar("spiceprefix");
|
||||
|
|
|
|||
10
src/xinit.c
10
src/xinit.c
|
|
@ -1177,12 +1177,20 @@ static int source_tcl_file(char *s)
|
|||
if(Tcl_EvalFile(interp, s)==TCL_ERROR) {
|
||||
|
||||
fprintf(errfp, "Tcl_AppInit() error: can not execute %s, please fix:\n", s);
|
||||
fprintf(errfp, "Line No: %d\n", Tcl_GetErrorLine(interp));
|
||||
fprintf(errfp, "%s", tclresult());
|
||||
#if TCL_MAJOR_VERSION >= 8 && TCL_MINOR_VERSION >=6
|
||||
fprintf(errfp, "Line No: %d\n", Tcl_GetErrorLine(interp));
|
||||
#endif
|
||||
fprintf(errfp, "\n");
|
||||
#if TCL_MAJOR_VERSION >= 8 && TCL_MINOR_VERSION >=6
|
||||
my_snprintf(tmp, S(tmp), "tk_messageBox -icon error -type ok -message \
|
||||
{Tcl_AppInit() err 1: can not execute %s, please fix:\n%s\nLine No: %d\n}",
|
||||
s, tclresult(), Tcl_GetErrorLine(interp));
|
||||
#else
|
||||
my_snprintf(tmp, S(tmp), "tk_messageBox -icon error -type ok -message \
|
||||
{Tcl_AppInit() err 1: can not execute %s, please fix:\n%s\n}",
|
||||
s, tclresult());
|
||||
#endif
|
||||
if(has_x) {
|
||||
tcleval( "wm withdraw .");
|
||||
tcleval( tmp);
|
||||
|
|
|
|||
|
|
@ -21,21 +21,21 @@ v {xschem version=3.4.6 file_version=1.2
|
|||
}
|
||||
G {}
|
||||
K {type=opamp_va
|
||||
format="@name @@OUT @@IN1 @@IN2 @model"
|
||||
format="@name @@OUT @@IN1 @@IN2 @model gain=@gain amplitude=@amplitude offset=@offset"
|
||||
|
||||
template="name=X1 model=diff_amp_cell"
|
||||
template="name=X1 model=diff_amp_cell gain=40 amplitude=3 offset=1.5"
|
||||
|
||||
device_model="tcleval(
|
||||
.subckt diff_amp_cell OUT IN1 IN2
|
||||
N1 out in1 in2 diff_amp_model
|
||||
.ends diff_amp_cell
|
||||
|
||||
.model diff_amp_model diff_amp
|
||||
|
||||
.control
|
||||
* following line specifies the location for the .osdi file so ngspice can use it.
|
||||
pre_osdi $USER_CONF_DIR/xschem_library/diff_amp.osdi
|
||||
.endc
|
||||
|
||||
.model diff_amp_model diff_amp $ gain=40 amplitude=3 offset=1.5
|
||||
|
||||
.subckt diff_amp_cell OUT IN1 IN2 gain=40 amplitude=3 offset=1.5
|
||||
N1 out in1 in2 diff_amp_model gain=gain amplitude=amplitude offset=offset
|
||||
.ends diff_amp_cell
|
||||
)"
|
||||
}
|
||||
V {}
|
||||
|
|
|
|||
|
|
@ -25,8 +25,8 @@ V {}
|
|||
S {}
|
||||
E {}
|
||||
B 2 840 -580 1640 -170 {flags=graph
|
||||
y1=0
|
||||
y2=6
|
||||
y1=6.3e-14
|
||||
y2=5
|
||||
ypos1=0
|
||||
ypos2=2
|
||||
divy=5
|
||||
|
|
@ -49,7 +49,7 @@ logy=0
|
|||
}
|
||||
B 2 840 -990 1640 -580 {flags=graph
|
||||
y1=0
|
||||
y2=40
|
||||
y2=100
|
||||
ypos1=0
|
||||
ypos2=2
|
||||
divy=5
|
||||
|
|
@ -68,10 +68,9 @@ unitx=1
|
|||
logx=0
|
||||
logy=0
|
||||
}
|
||||
P 4 5 140 -600 140 -880 710 -880 710 -600 140 -600 {}
|
||||
P 4 5 30 -600 30 -880 740 -880 740 -600 30 -600 {}
|
||||
P 4 7 410 -600 410 -560 420 -560 410 -540 400 -560 410 -560 410 -600 {}
|
||||
T {// importing libs
|
||||
|
||||
`include "discipline.h"
|
||||
|
||||
module diff_amp(
|
||||
|
|
@ -79,17 +78,17 @@ module diff_amp(
|
|||
input electrical in1,
|
||||
input electrical in2);
|
||||
|
||||
parameter real gain = 40; // setting gain to 40 of the differential amplifier
|
||||
parameter real vcc = 3; // swing from -vcc/2 to +vcc/2
|
||||
parameter real offset = 3;// added offset
|
||||
(* desc="gain", units="", type="instance" *) parameter real gain = 40 from [-inf: inf];
|
||||
(* desc="amplitude", units="", type="instance" *) parameter real amplitude = 3 from [-inf: inf];
|
||||
(* desc="offset", units="", type="instance" *) parameter real offset = 1.5 from [-inf: inf];
|
||||
|
||||
analog begin
|
||||
|
||||
V(out) <+ offset / 2 + vcc / 2 * tanh( gain / vcc * 2 * V(in1, in2));
|
||||
V(out) <+ offset + amplitude / 2 * tanh( gain / amplitude * 2 * V(in1, in2));
|
||||
|
||||
end
|
||||
endmodule
|
||||
} 150 -870 0 0 0.2 0.2 {font=monospace}
|
||||
} 40 -870 0 0 0.2 0.2 {font=monospace}
|
||||
T {create a diff_amp.va file with following code
|
||||
and compile it into a .osdi file with openvaf.} 190 -940 0 0 0.4 0.4 {}
|
||||
N 180 -450 320 -450 {lab=B}
|
||||
|
|
@ -100,7 +99,6 @@ N 180 -330 180 -290 {lab=0}
|
|||
N 80 -330 80 -290 {lab=0}
|
||||
N 80 -530 80 -390 {lab=A}
|
||||
N 180 -450 180 -390 {lab=B}
|
||||
C {diff_amp.sym} 420 -490 0 0 {name=X1}
|
||||
C {lab_pin.sym} 640 -490 0 1 {name=p1 sig_type=std_logic lab=Z}
|
||||
C {lab_pin.sym} 80 -530 0 0 {name=p2 sig_type=std_logic lab=A}
|
||||
C {lab_pin.sym} 180 -450 0 0 {name=p3 sig_type=std_logic lab=B}
|
||||
|
|
@ -118,7 +116,7 @@ C {code_shown.sym} 240 -320 0 0 {name=COMMANDS only_toplevel=false value="
|
|||
set appendwrite
|
||||
remzerovec
|
||||
write tb_diff_amp.raw
|
||||
quit 0
|
||||
* quit 0
|
||||
.endc
|
||||
"}
|
||||
C {launcher.sym} 670 -120 0 0 {name=h5
|
||||
|
|
@ -130,3 +128,4 @@ C {launcher.sym} 670 -170 0 0 {name=h1
|
|||
descr="OP annotate"
|
||||
tclcommand="xschem annotate_op"
|
||||
}
|
||||
C {diff_amp.sym} 420 -490 0 0 {name=X1 model=diff_amp_cell gain=100 amplitude=5 offset=2.5}
|
||||
|
|
|
|||
Loading…
Reference in New Issue