correct alter of mos geometries for binned models
This commit is contained in:
parent
96dd397251
commit
99b167b272
|
|
@ -27,6 +27,7 @@ static wordlist *devexpand(char *name);
|
|||
static void all_show(wordlist *wl, int mode);
|
||||
static void all_show_old(wordlist *wl, int mode);
|
||||
static void com_alter_mod(wordlist *wl);
|
||||
static void if_set_binned_model(CKTcircuit *, char *, char *, struct dvec *);
|
||||
|
||||
/*
|
||||
* devhelp: lists available devices and information on parameters
|
||||
|
|
@ -1079,6 +1080,40 @@ com_altermod(wordlist *wl)
|
|||
com_alter_common(wl, 1);
|
||||
}
|
||||
|
||||
static void
|
||||
if_set_binned_model(CKTcircuit *ckt, char *devname, char *param, struct dvec *val)
|
||||
{
|
||||
char *width_length;
|
||||
double w=0.0, l=0.0;
|
||||
struct variable *v;
|
||||
|
||||
v = if_getparam(ckt, &devname, "w", 0, 0);
|
||||
if (!v) {
|
||||
fprintf(cp_err, "Error: Can't access width instance parameter.\n");
|
||||
return;
|
||||
}
|
||||
w = v->va_V.vV_real;
|
||||
|
||||
v = if_getparam(ckt, &devname, "l", 0, 0);
|
||||
if (!v) {
|
||||
fprintf(cp_err, "Error: Can't access length instance parameter.\n");
|
||||
return;
|
||||
}
|
||||
l = v->va_V.vV_real;
|
||||
|
||||
if (param[0] == 'w') {
|
||||
w = *val->v_realdata; /* overwrite the width with the alter param */
|
||||
} else {
|
||||
l = *val->v_realdata; /* overwrite the length with the alter param */
|
||||
}
|
||||
width_length = TMALLOC(char, 36);
|
||||
(void) sprintf(width_length,"w=%15.7e l=%15.7e", w, l);
|
||||
|
||||
if_setparam_model(ft_curckt->ci_ckt, &devname, width_length);
|
||||
FREE(width_length);
|
||||
|
||||
}
|
||||
|
||||
static void
|
||||
com_alter_common(wordlist *wl, int do_model)
|
||||
{
|
||||
|
|
@ -1328,6 +1363,12 @@ com_alter_common(wordlist *wl, int do_model)
|
|||
return;
|
||||
}
|
||||
|
||||
/* If we want alter the geometry of a MOS device
|
||||
we have to ensure that we are in the valid model bin. */
|
||||
if ( (dev[0] == 'm') && ((param[0] == 'w') || (param[0] == 'l')) ) {
|
||||
if_set_binned_model(ft_curckt->ci_ckt, dev, param, dv);
|
||||
}
|
||||
|
||||
if_setparam(ft_curckt->ci_ckt, &dev, param, dv, do_model);
|
||||
|
||||
/* va: garbage collection for dv, if pnode names is no simple value */
|
||||
|
|
|
|||
|
|
@ -160,7 +160,9 @@ if_inpdeck(struct line *deck, INPtables **tab)
|
|||
|
||||
INPpas1( ckt, (card *) deck->li_next, *tab);
|
||||
INPpas2( ckt, (card *) deck->li_next, *tab, ft_curckt->ci_defTask);
|
||||
INPkillMods();
|
||||
/* INPkillMods(); FIXME: modtab should removed later -
|
||||
because needed for alter geometry of binned MOS models,
|
||||
see below if_setparam_model */
|
||||
|
||||
/* INPpas2 has been modified to ignore .NODESET and .IC
|
||||
* cards. These are left till INPpas3 so that we can check for
|
||||
|
|
@ -820,7 +822,7 @@ spif_getparam(CKTcircuit *ckt, char **name, char *param, int ind, int do_model)
|
|||
|
||||
/* 9/26/03 PJB : function to allow setting model of device */
|
||||
void
|
||||
if_setparam_model(CKTcircuit *ckt, char **name, char *val )
|
||||
if_setparam_model(CKTcircuit *ckt, char **name, char *val)
|
||||
{
|
||||
GENinstance *dev = NULL;
|
||||
GENinstance *prevDev = NULL;
|
||||
|
|
@ -830,21 +832,29 @@ if_setparam_model(CKTcircuit *ckt, char **name, char *val )
|
|||
GENinstance *iter;
|
||||
GENmodel *mods, *prevMod;
|
||||
int typecode;
|
||||
char *modname;
|
||||
|
||||
/* retrieve device name from symbol table */
|
||||
INPretrieve(name, ft_curckt->ci_symtab);
|
||||
/* find the specified device */
|
||||
typecode = finddev(ckt, *name, &dev, &curMod);
|
||||
if (typecode == -1) {
|
||||
fprintf(cp_err, "Error: no such device or model name %s\n", *name);
|
||||
fprintf(cp_err, "Error: no such device name %s\n", *name);
|
||||
return;
|
||||
}
|
||||
curMod = dev->GENmodPtr;
|
||||
modname = copy(dev->GENmodPtr->GENmodName);
|
||||
modname = strtok(modname, "."); /* want only have the parent model name */
|
||||
/*
|
||||
retrieve the model from the global model table; also add the model to 'ckt'
|
||||
and indicate model is being used
|
||||
*/
|
||||
INPgetMod( ckt, val, &inpmod, ft_curckt->ci_symtab );
|
||||
INPgetMod( ckt, modname, &inpmod, ft_curckt->ci_symtab );
|
||||
/* check if using model binning -- pass in line since need 'l' and 'w' */
|
||||
if ( inpmod == NULL ) {
|
||||
INPgetModBin( ckt, modname, &inpmod, ft_curckt->ci_symtab, val );
|
||||
}
|
||||
tfree(modname);
|
||||
if ( inpmod == NULL ) {
|
||||
fprintf(cp_err, "Error: no such model %s.\n", val);
|
||||
return;
|
||||
|
|
@ -852,9 +862,8 @@ if_setparam_model(CKTcircuit *ckt, char **name, char *val )
|
|||
newMod = inpmod->INPmodfast;
|
||||
|
||||
/* see if new model name same as current model name */
|
||||
if ( newMod->GENmodName == curMod->GENmodName ) {
|
||||
fprintf(cp_err, "Warning: new model same as current model; nothing changed.\n");
|
||||
return;
|
||||
if ( newMod->GENmodName != curMod->GENmodName ) {
|
||||
printf("Notice: model has changed from %s to %s.\n", curMod->GENmodName, newMod->GENmodName);
|
||||
}
|
||||
if ( newMod->GENmodType != curMod->GENmodType ) {
|
||||
fprintf(cp_err, "Error: new model %s must be same type as current model.\n", val);
|
||||
|
|
|
|||
Loading…
Reference in New Issue