inp.c, inp_parse_temper(), rewrite, using search_idenifier and find_assignment
try to make it more robust with regard to '!=' '<=' '==' don't misinterpret as '=' "atemperaticvariable" don't misinterpret as 'temper' multiple temper in one expression
This commit is contained in:
parent
511389ad10
commit
2df8f433f8
|
|
@ -1438,7 +1438,6 @@ static int
|
||||||
inp_parse_temper(struct line *card, struct pt_temper **modtlist_p, struct pt_temper **devtlist_p)
|
inp_parse_temper(struct line *card, struct pt_temper **modtlist_p, struct pt_temper **devtlist_p)
|
||||||
{
|
{
|
||||||
int error = 0;
|
int error = 0;
|
||||||
char *end_tstr, *beg_tstr, *beg_pstr, *str_ptr, *devmodname, *paramname;
|
|
||||||
|
|
||||||
struct pt_temper *modtlist = NULL;
|
struct pt_temper *modtlist = NULL;
|
||||||
struct pt_temper *devtlist = NULL;
|
struct pt_temper *devtlist = NULL;
|
||||||
|
|
@ -1450,115 +1449,73 @@ inp_parse_temper(struct line *card, struct pt_temper **modtlist_p, struct pt_tem
|
||||||
char *curr_line = card->li_line;
|
char *curr_line = card->li_line;
|
||||||
|
|
||||||
/* exclude some elements */
|
/* exclude some elements */
|
||||||
if ((*curr_line == '*') || (*curr_line == 'v') || (*curr_line == 'b') || (*curr_line == 'i') ||
|
if (strchr("*vbiegfh", curr_line[0]))
|
||||||
(*curr_line == 'e') || (*curr_line == 'g') || (*curr_line == 'f') || (*curr_line == 'h'))
|
|
||||||
continue;
|
continue;
|
||||||
/* exclude all dot commands except .model */
|
/* exclude all dot commands except .model */
|
||||||
if ((*curr_line == '.') && (!prefix(".model", curr_line)))
|
if (curr_line[0] == '.' && !prefix(".model", curr_line))
|
||||||
continue;
|
continue;
|
||||||
/* exclude lines not containing 'temper' */
|
/* exclude lines not containing 'temper' */
|
||||||
if (strstr(curr_line, "temper") == NULL)
|
if (!strstr(curr_line, "temper"))
|
||||||
continue;
|
continue;
|
||||||
/* now start processing of the remaining lines containing 'temper' */
|
|
||||||
if (prefix(".model", curr_line)) {
|
bool is_model = prefix(".model", curr_line);
|
||||||
struct pt_temper *modtlistnew = NULL;
|
|
||||||
/* remove '.model' */
|
/* skip ".model" */
|
||||||
|
if (is_model)
|
||||||
curr_line = nexttok(curr_line);
|
curr_line = nexttok(curr_line);
|
||||||
devmodname = gettok(&curr_line);
|
|
||||||
beg_tstr = curr_line;
|
|
||||||
while ((end_tstr = beg_tstr = strstr(beg_tstr, "temper")) != NULL) {
|
|
||||||
modtlistnew = TMALLOC(struct pt_temper, 1);
|
|
||||||
while ((*beg_tstr) != '=')
|
|
||||||
beg_tstr--;
|
|
||||||
beg_pstr = beg_tstr;
|
|
||||||
/* go back over param name */
|
|
||||||
while(isspace_c(*beg_pstr))
|
|
||||||
beg_pstr--;
|
|
||||||
while(!isspace_c(*beg_pstr))
|
|
||||||
beg_pstr--;
|
|
||||||
/* get parameter name */
|
|
||||||
paramname = copy_substring(beg_pstr + 1, beg_tstr);
|
|
||||||
/* find end of expression string */
|
|
||||||
while (((*end_tstr) != '\0') && ((*end_tstr) != '='))
|
|
||||||
end_tstr++;
|
|
||||||
/* go back over next param name */
|
|
||||||
if (*end_tstr == '=') {
|
|
||||||
end_tstr--;
|
|
||||||
while(isspace_c(*end_tstr))
|
|
||||||
end_tstr--;
|
|
||||||
while(!isspace_c(*end_tstr))
|
|
||||||
end_tstr--;
|
|
||||||
}
|
|
||||||
/* copy the expression */
|
|
||||||
modtlistnew->expression = copy_substring(beg_tstr + 1, end_tstr);
|
|
||||||
/* now remove this parameter entry by overwriting with ' '
|
|
||||||
ngspice then will use the default parameter to set up the circuit */
|
|
||||||
for (str_ptr = beg_pstr; str_ptr < end_tstr; str_ptr++)
|
|
||||||
*str_ptr = ' ';
|
|
||||||
|
|
||||||
/* to be filled in by evaluation function */
|
/* now start processing of the remaining lines containing 'temper' */
|
||||||
modtlistnew->wlend = wl_cons(NULL, NULL);
|
char *name = gettok(&curr_line);
|
||||||
/* create wordlist suitable for com_altermod */
|
char *t = curr_line;
|
||||||
modtlistnew->wl =
|
while ((t = search_identifier(t, "temper", curr_line)) != NULL) {
|
||||||
wl_cons(copy(devmodname),
|
struct pt_temper *alter = TMALLOC(struct pt_temper, 1);
|
||||||
wl_cons(paramname,
|
char *eq_ptr = find_back_assignment(t, curr_line);
|
||||||
wl_cons(copy("="),
|
if (!eq_ptr) {
|
||||||
modtlistnew->wlend)));
|
t = t + 1;
|
||||||
|
continue;
|
||||||
/* fill in the linked parse tree list */
|
|
||||||
modtlistnew->next = modtlist;
|
|
||||||
modtlist = modtlistnew;
|
|
||||||
}
|
}
|
||||||
tfree(devmodname);
|
/* go back over param name */
|
||||||
} else { /* instance expression with 'temper' */
|
char *end_param = skip_back_ws(eq_ptr, curr_line);
|
||||||
struct pt_temper *devtlistnew = NULL;
|
char *beg_param = skip_back_non_ws(end_param, curr_line);
|
||||||
/* get device name */
|
/* find end of expression string */
|
||||||
devmodname = gettok(&curr_line);
|
char *beg_expr = skip_ws(eq_ptr + 1);
|
||||||
beg_tstr = curr_line;
|
char *end_expr = find_assignment(beg_expr);
|
||||||
while ((end_tstr = beg_tstr = strstr(beg_tstr, "temper")) != NULL) {
|
if (end_expr) {
|
||||||
devtlistnew = TMALLOC(struct pt_temper, 1);
|
end_expr = skip_back_ws(end_expr, curr_line);
|
||||||
while ((*beg_tstr) != '=')
|
end_expr = skip_back_non_ws(end_expr, curr_line);
|
||||||
beg_tstr--;
|
} else {
|
||||||
beg_pstr = beg_tstr;
|
end_expr = strchr(beg_expr, '\0');
|
||||||
/* go back over param name */
|
|
||||||
while(isspace_c(*beg_pstr))
|
|
||||||
beg_pstr--;
|
|
||||||
while(!isspace_c(*beg_pstr))
|
|
||||||
beg_pstr--;
|
|
||||||
/* get parameter name */
|
|
||||||
paramname = copy_substring(beg_pstr + 1, beg_tstr);
|
|
||||||
/* find end of expression string */
|
|
||||||
while (((*end_tstr) != '\0') && ((*end_tstr) != '='))
|
|
||||||
end_tstr++;
|
|
||||||
/* go back over next param name */
|
|
||||||
if (*end_tstr == '=') {
|
|
||||||
end_tstr--;
|
|
||||||
while(isspace_c(*end_tstr))
|
|
||||||
end_tstr--;
|
|
||||||
while(!isspace_c(*end_tstr))
|
|
||||||
end_tstr--;
|
|
||||||
}
|
|
||||||
/* copy the expression */
|
|
||||||
devtlistnew->expression = copy_substring(beg_tstr + 1, end_tstr);
|
|
||||||
/* now remove this parameter entry by overwriting with ' '
|
|
||||||
ngspice then will use the default parameter to set up the circuit */
|
|
||||||
for (str_ptr = beg_pstr; str_ptr < end_tstr; str_ptr++)
|
|
||||||
*str_ptr = ' ';
|
|
||||||
|
|
||||||
/* to be filled in by evaluation function */
|
|
||||||
devtlistnew->wlend = wl_cons(NULL, NULL);
|
|
||||||
/* create wordlist suitable for com_altermod */
|
|
||||||
devtlistnew->wl =
|
|
||||||
wl_cons(copy(devmodname),
|
|
||||||
wl_cons(paramname,
|
|
||||||
wl_cons(copy("="), devtlistnew->wlend)));
|
|
||||||
|
|
||||||
/* fill in the linked parse tree list */
|
|
||||||
devtlistnew->next = devtlist;
|
|
||||||
devtlist = devtlistnew;
|
|
||||||
}
|
}
|
||||||
tfree(devmodname);
|
end_expr = skip_back_ws(end_expr, curr_line);
|
||||||
|
/* overwrite this parameter assignment with ' '
|
||||||
|
* the backend will use a default
|
||||||
|
* later, after evaluation, "alter" the parameter
|
||||||
|
*/
|
||||||
|
alter->expression = copy_substring(beg_expr, end_expr);
|
||||||
|
|
||||||
|
/* to be filled in by evaluation function */
|
||||||
|
alter->wlend = wl_cons(NULL, NULL);
|
||||||
|
/* create wordlist suitable for com_altermod */
|
||||||
|
alter->wl =
|
||||||
|
wl_cons(copy(name),
|
||||||
|
wl_cons(copy_substring(beg_param, end_param),
|
||||||
|
wl_cons(copy("="),
|
||||||
|
alter->wlend)));
|
||||||
|
|
||||||
|
memset(beg_param, ' ', (size_t) (end_expr - beg_param));
|
||||||
|
|
||||||
|
/* fill in the linked parse tree list */
|
||||||
|
if (is_model) {
|
||||||
|
alter->next = modtlist;
|
||||||
|
modtlist = alter;
|
||||||
|
} else {
|
||||||
|
alter->next = devtlist;
|
||||||
|
devtlist = alter;
|
||||||
|
}
|
||||||
|
|
||||||
|
t = end_expr;
|
||||||
}
|
}
|
||||||
|
tfree(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
*modtlist_p = modtlist;
|
*modtlist_p = modtlist;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue