|
|
|
@ -1,6 +1,10 @@ |
|
|
|
/********** |
|
|
|
Copyright 1990 Regents of the University of California. All rights reserved. |
|
|
|
Author: 1988 Thomas L. Quarles |
|
|
|
Modified: Paolo Nenzi 2000 |
|
|
|
Remarks: This code is based on a version written by Serban Popescu which |
|
|
|
accepted an optional parameter ac. I have adapted his code |
|
|
|
to conform to INP standard. (PN) |
|
|
|
**********/ |
|
|
|
|
|
|
|
#include "ngspice.h" |
|
|
|
@ -15,12 +19,12 @@ void |
|
|
|
INP2R(void *ckt, INPtables *tab, card *current) |
|
|
|
{ |
|
|
|
/* parse a resistor card */ |
|
|
|
/* serban */ |
|
|
|
/* Rname <node> <node> [<val>][<mname>][w=<val>][l=<val>][ac=<val>] */ |
|
|
|
|
|
|
|
int mytype; /* the type we determine resistors are */ |
|
|
|
int type; /* the type the model says it is */ |
|
|
|
char *line; /* the part of the current line left to parse */ |
|
|
|
char *saveline; /* ... just in case we need to go back... */ |
|
|
|
char *name; /* the resistor's name */ |
|
|
|
char *model; /* the name of the resistor's model */ |
|
|
|
char *nname1; /* the first node's name */ |
|
|
|
@ -28,12 +32,10 @@ char *nname2; /* the second node's name */ |
|
|
|
void *node1; /* the first node's node pointer */ |
|
|
|
void *node2; /* the second node's node pointer */ |
|
|
|
double val; /* temp to held resistance */ |
|
|
|
double acval; /* temp to held resistance */ |
|
|
|
int error; /* error code temporary */ |
|
|
|
int error1; /* secondary error code temporary */ |
|
|
|
int error2; /* third error code temporary */ |
|
|
|
INPmodel *thismodel; /* pointer to model structure describing our model */ |
|
|
|
void *mdfast; /* pointer to the actual model */ |
|
|
|
void *mdfast=NULL; /* pointer to the actual model */ |
|
|
|
void *fast; /* pointer to the actual instance */ |
|
|
|
IFvalue ptemp; /* a value structure to package resistance into */ |
|
|
|
int waslead; /* flag to indicate that funny unlabeled number was found */ |
|
|
|
@ -53,40 +55,40 @@ IFuid uid; /* uid for default model */ |
|
|
|
INPgetTok(&line,&nname2,1); |
|
|
|
INPtermInsert(ckt,&nname2,tab,&node2); |
|
|
|
val = INPevaluate(&line,&error1,1); |
|
|
|
acval = val; /* PN: This is a safe choice */ |
|
|
|
/* either not a number -> model, or |
|
|
|
* follows a number, so must be a model name |
|
|
|
* -> MUST be a model name (or null) |
|
|
|
*/ |
|
|
|
again: |
|
|
|
|
|
|
|
saveline = line; /* save then old pointer */ |
|
|
|
|
|
|
|
INPgetTok(&line,&model,1); |
|
|
|
if(*model) { /* token isn't null */ |
|
|
|
if(!strcmp(model, "ac")) { |
|
|
|
acval = INPevaluate(&line,&error2,1); |
|
|
|
goto again; |
|
|
|
} else { |
|
|
|
INPinsert(&model,tab); |
|
|
|
thismodel = (INPmodel *)NULL; |
|
|
|
current->error = INPgetMod(ckt,model,&thismodel,tab); |
|
|
|
if(thismodel != NULL) { |
|
|
|
if(mytype != thismodel->INPmodType) { |
|
|
|
LITERR("incorrect model type") |
|
|
|
return; |
|
|
|
} |
|
|
|
mdfast = thismodel->INPmodfast; |
|
|
|
type = thismodel->INPmodType; |
|
|
|
} else { |
|
|
|
type = mytype; |
|
|
|
if(!tab->defRmod) { |
|
|
|
/* create default R model */ |
|
|
|
IFnewUid(ckt,&uid,(IFuid)NULL,"R",UID_MODEL,(void **)NULL); |
|
|
|
IFC(newModel, (ckt,type,&(tab->defRmod),uid)) |
|
|
|
|
|
|
|
if(*model) { /* token isn't null */ |
|
|
|
if( INPlookMod(model) ) { /* If this is a valid model connect it */ |
|
|
|
INPinsert(&model,tab); |
|
|
|
thismodel = (INPmodel *)NULL; |
|
|
|
current->error = INPgetMod(ckt,model,&thismodel,tab); |
|
|
|
if(thismodel != NULL) { |
|
|
|
if(mytype != thismodel->INPmodType) { |
|
|
|
LITERR("incorrect model type") |
|
|
|
return; |
|
|
|
} |
|
|
|
mdfast = thismodel->INPmodfast; |
|
|
|
type = thismodel->INPmodType; |
|
|
|
} |
|
|
|
|
|
|
|
} else { /* It is not a model */ |
|
|
|
line = saveline; /* go back */ |
|
|
|
type = mytype; |
|
|
|
if(!tab->defRmod) { /* create default R model */ |
|
|
|
IFnewUid(ckt,&uid,(IFuid)NULL,"R",UID_MODEL,(void **)NULL); |
|
|
|
IFC(newModel, (ckt,type,&(tab->defRmod),uid)) |
|
|
|
} |
|
|
|
mdfast = tab->defRmod; |
|
|
|
} |
|
|
|
IFC(newInstance,(ckt,mdfast,&fast,name)) |
|
|
|
} |
|
|
|
} else { |
|
|
|
} |
|
|
|
IFC(newInstance,(ckt,mdfast,&fast,name)) |
|
|
|
} else { /* The token is null and a default model will be created */ |
|
|
|
type = mytype; |
|
|
|
if(!tab->defRmod) { |
|
|
|
/* create default R model */ |
|
|
|
@ -95,15 +97,11 @@ again: |
|
|
|
} |
|
|
|
IFC(newInstance,(ckt,tab->defRmod,&fast,name)) |
|
|
|
} |
|
|
|
|
|
|
|
if(error1 == 0) { /* got a resistance above */ |
|
|
|
ptemp.rValue = val; |
|
|
|
GCA(INPpName,("resistance",&ptemp,ckt,type,fast)) |
|
|
|
} |
|
|
|
if(error2 == 0) { /* got an AC resistance above */ |
|
|
|
ptemp.rValue = acval; |
|
|
|
GCA(INPpName,("ac",&ptemp,ckt,type,fast)) |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
IFC(bindNode,(ckt,fast,1,node1)) |
|
|
|
IFC(bindNode,(ckt,fast,2,node2)) |
|
|
|
|