inp.c, inpcom.c: implement a very basic .if/.else block
This commit is contained in:
parent
91ab0a3c74
commit
05a6ec222e
|
|
@ -50,6 +50,7 @@ static char *upper(register char *string);
|
||||||
static bool doedit(char *filename);
|
static bool doedit(char *filename);
|
||||||
static struct line *com_options = NULL;
|
static struct line *com_options = NULL;
|
||||||
static void cktislinear(CKTcircuit *ckt, struct line *deck);
|
static void cktislinear(CKTcircuit *ckt, struct line *deck);
|
||||||
|
static void dotifeval(struct line *deck);
|
||||||
|
|
||||||
void line_free_x(struct line *deck, bool recurse);
|
void line_free_x(struct line *deck, bool recurse);
|
||||||
void create_circbyline(char *line);
|
void create_circbyline(char *line);
|
||||||
|
|
@ -547,6 +548,9 @@ inp_spsource(FILE *fp, bool comfile, char *filename, bool intfile)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* handle .if ... .elseif ... .else ... .endif statements. */
|
||||||
|
dotifeval(deck);
|
||||||
|
|
||||||
/*merge the two option line structs*/
|
/*merge the two option line structs*/
|
||||||
if (!options && com_options)
|
if (!options && com_options)
|
||||||
options = com_options;
|
options = com_options;
|
||||||
|
|
@ -1202,3 +1206,71 @@ com_circbyline(wordlist *wl)
|
||||||
char *newline = wl_flatten(wl);
|
char *newline = wl_flatten(wl);
|
||||||
create_circbyline(newline);
|
create_circbyline(newline);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* handle .if('expr') ... .elseif('expr') ... .else ... .endif statements.
|
||||||
|
numparam has evaluated .if('boolean expression') to
|
||||||
|
.if ( 1.000000000e+000 ) or .elseif ( 0.000000000e+000 ) */
|
||||||
|
static void
|
||||||
|
dotifeval(struct line *deck)
|
||||||
|
{
|
||||||
|
int iftrue = 0, elseiftrue = 0, elsetrue = 0, iffound = 0, elseiffound = 0, elsefound = 0;
|
||||||
|
struct line *dd;
|
||||||
|
char *dottoken;
|
||||||
|
char *s, *t;
|
||||||
|
|
||||||
|
for (dd = deck; dd; dd = dd->li_next) {
|
||||||
|
|
||||||
|
s = t = dd->li_line;
|
||||||
|
|
||||||
|
if (*s == '*')
|
||||||
|
continue;
|
||||||
|
|
||||||
|
dottoken = gettok(&t);
|
||||||
|
/* find '.if' and read its parameter */
|
||||||
|
if (cieq(dottoken, ".if")) {
|
||||||
|
elsefound = 0;
|
||||||
|
elseiffound = 0;
|
||||||
|
iffound = 1;
|
||||||
|
*s = '*';
|
||||||
|
s = dd->li_line + 3;
|
||||||
|
iftrue = atoi(s);
|
||||||
|
}
|
||||||
|
else if (cieq(dottoken, ".elseif")) {
|
||||||
|
elsefound = 0;
|
||||||
|
elseiffound = 1;
|
||||||
|
iffound = 0;
|
||||||
|
*s = '*';
|
||||||
|
if (!iftrue) {
|
||||||
|
s = dd->li_line + 7;
|
||||||
|
elseiftrue = atoi(s);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (cieq(dottoken, ".else")) {
|
||||||
|
elsefound = 1;
|
||||||
|
elseiffound = 0;
|
||||||
|
iffound = 0;
|
||||||
|
if (!iftrue && !elseiftrue)
|
||||||
|
elsetrue = 1;
|
||||||
|
*s = '*';
|
||||||
|
}
|
||||||
|
else if (cieq(dottoken, ".endif")) {
|
||||||
|
elsefound = elseiffound = iffound = 0;
|
||||||
|
elsetrue = elseiftrue = iftrue = 0;
|
||||||
|
*s = '*';
|
||||||
|
// inp_subcktexpand(dd);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (iffound && !iftrue) {
|
||||||
|
*s = '*';
|
||||||
|
}
|
||||||
|
else if (elseiffound && !elseiftrue) {
|
||||||
|
*s = '*';
|
||||||
|
}
|
||||||
|
else if (elsefound && !elsetrue) {
|
||||||
|
*s = '*';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
tfree(dottoken);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
|
|
@ -96,6 +96,7 @@ static void inp_sort_params(struct line *start_card, struct line *end_card, stru
|
||||||
static char *inp_remove_ws(char *s);
|
static char *inp_remove_ws(char *s);
|
||||||
static void inp_compat(struct line *deck);
|
static void inp_compat(struct line *deck);
|
||||||
static void inp_bsource_compat(struct line *deck);
|
static void inp_bsource_compat(struct line *deck);
|
||||||
|
static void inp_dot_if(struct line *deck);
|
||||||
|
|
||||||
static bool chk_for_line_continuation(char *line);
|
static bool chk_for_line_continuation(char *line);
|
||||||
static void comment_out_unused_subckt_models(struct line *start_card, int no_of_lines);
|
static void comment_out_unused_subckt_models(struct line *start_card, int no_of_lines);
|
||||||
|
|
@ -736,7 +737,7 @@ inp_readall(FILE *fp, int call_depth, char *dir_name, bool comfile, bool intfile
|
||||||
|
|
||||||
inp_fix_macro_param_func_paren_io(working);
|
inp_fix_macro_param_func_paren_io(working);
|
||||||
inp_fix_ternary_operator(working);
|
inp_fix_ternary_operator(working);
|
||||||
//tprint(working);
|
|
||||||
inp_expand_macros_in_deck(NULL, working);
|
inp_expand_macros_in_deck(NULL, working);
|
||||||
inp_fix_param_values(working);
|
inp_fix_param_values(working);
|
||||||
|
|
||||||
|
|
@ -744,8 +745,9 @@ inp_readall(FILE *fp, int call_depth, char *dir_name, bool comfile, bool intfile
|
||||||
be correct at this point */
|
be correct at this point */
|
||||||
for (newcard = working; newcard; newcard = newcard->li_next)
|
for (newcard = working; newcard; newcard = newcard->li_next)
|
||||||
end = newcard;
|
end = newcard;
|
||||||
|
// tprint(cc);
|
||||||
inp_reorder_params(subckt_w_params, working, cc, end);
|
inp_reorder_params(subckt_w_params, working, cc, end);
|
||||||
|
|
||||||
inp_fix_inst_calls_for_numparam(subckt_w_params, working);
|
inp_fix_inst_calls_for_numparam(subckt_w_params, working);
|
||||||
|
|
||||||
delete_names(subckt_w_params);
|
delete_names(subckt_w_params);
|
||||||
|
|
@ -767,6 +769,7 @@ inp_readall(FILE *fp, int call_depth, char *dir_name, bool comfile, bool intfile
|
||||||
working = cc->li_next;
|
working = cc->li_next;
|
||||||
/* B source numparam compatibility transformation */
|
/* B source numparam compatibility transformation */
|
||||||
inp_bsource_compat(working);
|
inp_bsource_compat(working);
|
||||||
|
inp_dot_if(working);
|
||||||
}
|
}
|
||||||
|
|
||||||
inp_add_series_resistor(working);
|
inp_add_series_resistor(working);
|
||||||
|
|
@ -5710,3 +5713,29 @@ tprint(struct line *t)
|
||||||
fprintf(fd, "%d %d %s\n", t->li_linenum_orig, t->li_linenum, t->li_line);
|
fprintf(fd, "%d %d %s\n", t->li_linenum_orig, t->li_linenum, t->li_line);
|
||||||
fclose(fd);
|
fclose(fd);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* prepare .if and .elseif for numparam
|
||||||
|
.if(expression) --> .if{expression} */
|
||||||
|
static void
|
||||||
|
inp_dot_if(struct line *deck)
|
||||||
|
{
|
||||||
|
struct line *card;
|
||||||
|
|
||||||
|
for (card = deck; card; card = card->li_next) {
|
||||||
|
char *curr_line = card->li_line;
|
||||||
|
if (*curr_line == '*')
|
||||||
|
continue;
|
||||||
|
if (ciprefix(".if", curr_line) || ciprefix(".elseif", curr_line)) {
|
||||||
|
char *firstbr = strchr(curr_line, '(');
|
||||||
|
char *lastbr = strrchr(curr_line, ')');
|
||||||
|
if ((!firstbr) || (!lastbr)) {
|
||||||
|
fprintf(cp_err, "Error in netlist line %d\n", card->li_linenum_orig);
|
||||||
|
fprintf(cp_err, " Bad syntax: %s\n\n", curr_line);
|
||||||
|
controlled_exit(EXIT_BAD);
|
||||||
|
}
|
||||||
|
*firstbr = '{';
|
||||||
|
*lastbr = '}';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue