Retaining the mixed case of Cider quoted string valued parameters. Limit searches for ic.file to D*, M*, and Q* device instantiation lines. Cider model (numos, numd, nbjt) detection is limited to .model lines. Continuation lines which do contain these tokens are not checked, but this should rarely happen. All of the examples/cider circuits meet these assumptions. Memory errors have been removed.

This commit is contained in:
Brian Taylor 2021-09-09 11:54:30 -07:00 committed by Holger Vogt
parent 3599c189b6
commit 81df6ed772
1 changed files with 114 additions and 46 deletions

View File

@ -246,7 +246,7 @@ static char *keep_case_of_cider_param(char *buffer)
static int is_comment_or_blank(char *buffer)
{
/* Assume line buffers have initial whitespace removed */
switch (buffer[0]) {
switch (buffer[0]) {
case '*':
case '$':
case '#':
@ -260,6 +260,9 @@ static int is_comment_or_blank(char *buffer)
static int turn_off_case_retention(char *buffer)
{
if (!buffer) {
return 1;
}
if (buffer[0] == '.') {
if (ciprefix(".model", buffer)) {
return 0;
@ -275,60 +278,126 @@ static int turn_off_case_retention(char *buffer)
}
}
static int line_contains(char *buf, char *str)
static char *make_lower_case_copy(char *inbuf)
{
char *s = buf;
size_t num = strlen(str);
while (*s && (*s != '\n')) {
while (isspace_c(*s)) {
s++;
}
if (*s && (*s != '\n')) {
if (strncasecmp(s, str, num) == 0) {
return 1;
}
} else {
return 0;
}
while (!isspace_c(*s)) {
s++;
}
char *s = NULL;
char *rets = NULL;
size_t lenb = 0;
if (!inbuf) {
return NULL;
}
lenb = strlen(inbuf);
if (lenb < 1) {
return NULL;
}
rets = dup_string(inbuf, lenb);
if (!rets) {
return NULL;
}
for (s = rets; *s; s++) {
*s = tolower_c(*s);
}
return rets;
}
static int ignore_line(char *buf)
{
/* Can the line in buf be ignored for ic.file checking?
Expect to examine only diode, mos, bipolar instance lines.
If the ic.file param is on a continuation line, it will be missed.
This should be rare.
*/
if (!buf) {
return 1;
}
if (buf[0] == '.') {
return 1;
}
if (is_comment_or_blank(buf)) {
return 1;
}
/* Interpreter d.., q.., m.. */
switch (buf[0]) {
case 'D':
case 'd':
if (ciprefix("dc", buf)
|| ciprefix("dowhile", buf) || ciprefix("define", buf)
|| ciprefix("deftype", buf) || ciprefix("delete", buf)
|| ciprefix("destroy", buf) || ciprefix("devhelp", buf)
|| ciprefix("diff", buf) || ciprefix("display", buf)
) {
return 1;
} else {
return 0;
}
break;
case 'M':
case 'm':
if (ciprefix("mc_source", buf) || ciprefix("meas", buf)
|| ciprefix("mdump", buf) || ciprefix("mrdump", buf)
) {
return 1;
} else {
return 0;
}
break;
case 'Q':
case 'q':
if (ciprefix("quit", buf)) {
return 1;
} else {
return 0;
}
break;
default:
break;
}
return 1;
}
static int line_contains_icfile(char *buf)
{
/* Find "ic.file" in a lower cased copy of buf. */
char str[] = "ic.file";
char *s = NULL;
if (ignore_line(buf)) {
return 0;
}
/* make_lower_case_copy checks its input string */
s = make_lower_case_copy(buf);
if (!s) {
return 0;
}
if (strstr(s, str)) {
tfree(s);
return 1;
} else {
tfree(s);
return 0;
}
return 0;
}
static int is_cider_model(char *buf)
{
/* Expect numos, numd, nbjt to be on the same line as the .model.
Otherwise it will be missed if on a continuation line.
This should be rare.
*/
char *s;
if (!ciprefix(".model", buf)) {
return 0;
}
s = buf;
while (!isspace_c(*s)) {
s++;
s = make_lower_case_copy(buf);
if (!s) return 0;
if (strstr(s, "numos") || strstr(s, "numd") || strstr(s, "nbjt")) {
tfree(s);
return 1;
} else {
tfree(s);
return 0;
}
while (*s && (*s != '\n')) {
while (isspace_c(*s)) {
s++;
}
if (*s && (*s != '\n')) {
if (strncasecmp(s, "numos", 4) == 0) {
return 1;
}
if (strncasecmp(s, "numd", 4) == 0) {
return 1;
}
if (strncasecmp(s, "nbjt", 4) == 0) {
return 1;
}
} else {
return 0;
}
while (!isspace_c(*s)) {
s++;
}
}
return 0;
}
#endif
@ -1461,8 +1530,7 @@ struct inp_read_t inp_read( FILE *fp, int call_depth, const char *dir_name,
(ciprefix(".model", buffer) || buffer[0] == '+')) {
s = keep_case_of_cider_param(buffer);
}
else if (!is_comment_or_blank(buffer) &&
line_contains(buffer, "ic.file")) {
else if (line_contains_icfile(buffer)) {
s = keep_case_of_cider_param(buffer);
}
#endif