diff --git a/ChangeLog b/ChangeLog index 55d5f104a..9ca071cca 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,25 +1,34 @@ +2011-10-16 Robert Larice + * src/spicelib/parser/inpptree-parser.y , + * src/spicelib/parser/inpptree.c : + bug fix, allow special nodenames "/Node" and "Node-4" in `B' expressions + related to + http://sourceforge.net/tracker/?func=detail&aid=3421234&group_id=38962&atid=423915 + the lexer will now identify special function applications + v(node) v(node,node) and i(instance) + 2011-10-02 Holger Vogt * device.c updates to altermod command, allow reading from file with multiple .model sections - + 2011-09-18 Holger Vogt * com_fft.c: fft now uses faster Green's method (may be deselected by unsetting #define GREEN swirch * spiceif.c: code beutify for better readability - * device.c updates to altermod command, allow reading from file + * device.c updates to altermod command, allow reading from file * com_measure2.c: warning real ac removed - + 2011-09-11 Holger Vogt * frontend/plotting/grid.c: Error message, if requested resolution cannot be handled. 2011-08-28 Dietmar Warning - * /admst/ngspice.xml, ngspiceVersion.xml, psp102.va: psp102 module name change + * /admst/ngspice.xml, ngspiceVersion.xml, psp102.va: psp102 module name change according to model developer used naming convention (psp102 is now PSP102VA) 2011-08-24 Dietmar Warning * configure.ac, inp2q.c, inpdomod.c, dev.c, ngspice.xml, bjt504t.va: - change the name of the mextram verilog module according to model developer + change the name of the mextram verilog module according to model developer used naming convention (mextram.va is substituted by bjt504t.va), means including parasitic substrate transistor and selfheating is enabled diff --git a/src/spicelib/parser/inpptree-parser.y b/src/spicelib/parser/inpptree-parser.y index 5fcbbb553..d2b9d4b43 100644 --- a/src/spicelib/parser/inpptree-parser.y +++ b/src/spicelib/parser/inpptree-parser.y @@ -36,6 +36,7 @@ %token TOK_NUM %token TOK_STR +%token TOK_pnode %token TOK_LE TOK_LT TOK_GE TOK_GT TOK_EQ TOK_NE %type exp nonempty_arglist @@ -80,6 +81,8 @@ exp: | TOK_STR '(' nonempty_arglist ')' { $$ = mkfnode($1, $3); } + | TOK_pnode + | exp '?' exp ':' exp { $$ = mkfnode("ternary_fcn", mkbnode(",", mkbnode(",", $1, $3), diff --git a/src/spicelib/parser/inpptree.c b/src/spicelib/parser/inpptree.c index 82ae79905..19f0e07a7 100644 --- a/src/spicelib/parser/inpptree.c +++ b/src/spicelib/parser/inpptree.c @@ -19,6 +19,9 @@ static int PTcheck(INPparseNode * p); static INPparseNode *mkbnode(const char *opstr, INPparseNode * arg1, INPparseNode * arg2); static INPparseNode *mkfnode(const char *fname, INPparseNode * arg); +static INPparseNode *mkvnode(char *name); +static INPparseNode *mkinode(char *name); + static INPparseNode *mknnode(double number); static INPparseNode *mksnode(const char *string, void *ckt); static INPparseNode *PTdifferentiate(INPparseNode * p, int varnum); @@ -813,8 +816,7 @@ static INPparseNode *mkfnode(const char *fname, INPparseNode * arg) { int i; INPparseNode *p; - char buf[128], *name; - CKTnode *temp; + char buf[128]; /* Make sure the case is ok. */ (void) strcpy(buf, fname); @@ -822,71 +824,7 @@ static INPparseNode *mkfnode(const char *fname, INPparseNode * arg) p = TMALLOC(INPparseNode, 1); - if (!strcmp(buf, "v")) { - name = TMALLOC(char, 128); - if (arg->type == PT_PLACEHOLDER) { - strcpy(name, arg->funcname); - } else if (arg->type == PT_CONSTANT) { - (void) sprintf(name, "%d", (int) arg->constant); - } else if (arg->type != PT_COMMA) { - fprintf(stderr, "Error: badly formed node voltage\n"); - return (NULL); - } - - if (arg->type == PT_COMMA) { - /* Change v(a,b) into v(a) - v(b) */ - p = mkb(PT_MINUS, mkfnode(fname, arg->left), - mkfnode(fname, arg->right)); - } else { - INPtermInsert(circuit, &name, tables, &temp); - for (i = 0; i < numvalues; i++) - if ((types[i] == IF_NODE) && (values[i].nValue == temp)) - break; - if (i == numvalues) { - if (numvalues) { - values = TREALLOC(IFvalue, values, numvalues + 1); - types = TREALLOC(int, types, numvalues + 1); - } else { - values = TMALLOC(IFvalue, 1); - types = TMALLOC(int, 1); - } - values[i].nValue = temp; - types[i] = IF_NODE; - numvalues++; - } - p->valueIndex = i; - p->type = PT_VAR; - } - } else if (!strcmp(buf, "i")) { - name = TMALLOC(char, 128); - if (arg->type == PT_PLACEHOLDER) - strcpy(name, arg->funcname); - else if (arg->type == PT_CONSTANT) - (void) sprintf(name, "%d", (int) arg->constant); - else { - fprintf(stderr, "Error: badly formed branch current\n"); - return (NULL); - } - INPinsert(&name, tables); - for (i = 0; i < numvalues; i++) - if ((types[i] == IF_INSTANCE) && (values[i].uValue == name)) - break; - if (i == numvalues) { - if (numvalues) { - values = TREALLOC(IFvalue, values, numvalues + 1); - types = TREALLOC(int, types, numvalues + 1); - } else { - values = TMALLOC(IFvalue, 1); - types = TMALLOC(int, 1); - } - values[i].uValue = (IFuid) name; - types[i] = IF_INSTANCE; - numvalues++; - } - p->valueIndex = i; - p->type = PT_VAR; - - } else if(!strcmp("ternary_fcn", buf)) { + if(!strcmp("ternary_fcn", buf)) { // extern void printTree(INPparseNode *); // @@ -932,6 +870,63 @@ static INPparseNode *mkfnode(const char *fname, INPparseNode * arg) return (p); } +static INPparseNode *mkvnode(char *name) +{ + INPparseNode *p = TMALLOC(INPparseNode, 1); + + int i; + CKTnode *temp; + + INPtermInsert(circuit, &name, tables, &temp); + for (i = 0; i < numvalues; i++) + if ((types[i] == IF_NODE) && (values[i].nValue == temp)) + break; + if (i == numvalues) { + if (numvalues) { + values = TREALLOC(IFvalue, values, numvalues + 1); + types = TREALLOC(int, types, numvalues + 1); + } else { + values = TMALLOC(IFvalue, 1); + types = TMALLOC(int, 1); + } + values[i].nValue = temp; + types[i] = IF_NODE; + numvalues++; + } + p->valueIndex = i; + p->type = PT_VAR; + + return (p); +} + +static INPparseNode *mkinode(char *name) +{ + INPparseNode *p = TMALLOC(INPparseNode, 1); + + int i; + + INPinsert(&name, tables); + for (i = 0; i < numvalues; i++) + if ((types[i] == IF_INSTANCE) && (values[i].uValue == name)) + break; + if (i == numvalues) { + if (numvalues) { + values = TREALLOC(IFvalue, values, numvalues + 1); + types = TREALLOC(int, types, numvalues + 1); + } else { + values = TMALLOC(IFvalue, 1); + types = TMALLOC(int, 1); + } + values[i].uValue = (IFuid) name; + types[i] = IF_INSTANCE; + numvalues++; + } + p->valueIndex = i; + p->type = PT_VAR; + + return (p); +} + /* Number node. */ static INPparseNode *mknnode(double number) @@ -1133,6 +1128,53 @@ int PTlex (YYSTYPE *lvalp, char **line) } default: + { + int n1 = -1; + int n2 = -1; + int n3 = -1; + int n4 = -1; + int n = -1; + + sscanf(sbuf, "%*1[vV] ( %n%*[^ \t,()]%n , %n%*[^ \t,()]%n )%n", + &n1, &n2, &n3, &n4, &n); + if(n != -1) { + token = TOK_pnode; + lvalp->pnode = mkb(PT_MINUS, + mkvnode(copy_substring(sbuf+n1, sbuf+n2)), + mkvnode(copy_substring(sbuf+n3, sbuf+n4))); + sbuf += n; + break; + } + } + + { + int n1 = -1; + int n2 = -1; + int n = -1; + + sscanf(sbuf, "%*1[vV] ( %n%*[^ \t,()]%n )%n", &n1, &n2, &n); + if(n != -1) { + token = TOK_pnode; + lvalp->pnode = mkvnode(copy_substring(sbuf+n1, sbuf+n2)); + sbuf += n; + break; + } + } + + { + int n1 = -1; + int n2 = -1; + int n = -1; + + sscanf(sbuf, "%*1[iI] ( %n%*[^ \t,()]%n )%n", &n1, &n2, &n); + if(n != -1) { + token = TOK_pnode; + lvalp->pnode = mkinode(copy_substring(sbuf+n1, sbuf+n2)); + sbuf += n; + break; + } + } + td = INPevaluate(&sbuf, &err, 1); if (err == OK) { token = TOK_NUM;