diff --git a/ChangeLog b/ChangeLog index 6ad758dd8..6f88f3868 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,8 @@ +2010-02-26 Holger Vogt + * vsrc.c, vsrcacct.c, vsrcask.c, vsrcdefs.h, vsrcload.c, vsrcpar.c: + PWL source now has a repeat parameter (r=value) and a delay parameter + (td=value) + 2010-02-25 Holger Vogt * inpcom.c, general.h, mystring.c, numparam.h, spicenum.c, xpressn.c, include/makefile.am, misc/makefile.am, hash.c, hash.h: diff --git a/src/spicelib/devices/vsrc/vsrc.c b/src/spicelib/devices/vsrc/vsrc.c index 9489c6fae..e498a4d84 100644 --- a/src/spicelib/devices/vsrc/vsrc.c +++ b/src/spicelib/devices/vsrc/vsrc.c @@ -34,7 +34,8 @@ OPU ("pos_node",VSRC_POS_NODE, IF_INTEGER,"Positive node of source"), OP ("p", VSRC_POWER, IF_REAL, "Instantaneous power"), IP ("distof1", VSRC_D_F1, IF_REALVEC,"f1 input for distortion"), IP ("distof2", VSRC_D_F2, IF_REALVEC,"f2 input for distortion"), - IP ("r", VSRC_R, IF_REAL, "pwl repeat value") + IP ("r", VSRC_R, IF_REAL, "pwl repeat value"), + IP ("td", VSRC_TD, IF_REAL, "pwl delay value") }; char *VSRCnames[] = { diff --git a/src/spicelib/devices/vsrc/vsrcacct.c b/src/spicelib/devices/vsrc/vsrcacct.c index 61c7b7866..5ca61040e 100644 --- a/src/spicelib/devices/vsrc/vsrcacct.c +++ b/src/spicelib/devices/vsrc/vsrcacct.c @@ -162,7 +162,7 @@ VSRCaccept(CKTcircuit *ckt, GENmodel *inModel) /* no breakpoints (yet) */ } break; - case AM:{ + case AM:{ /* no breakpoints (yet) */ } break; @@ -177,11 +177,11 @@ VSRCaccept(CKTcircuit *ckt, GENmodel *inModel) for(i=0;i<(here->VSRCfunctionOrder/2)-1;i++) { /* if((*(here->VSRCcoeffs+2*i)==ckt->CKTtime)) { if(ckt->CKTbreak) {*/ - if ( ckt->CKTbreak && AlmostEqualUlps(*(here->VSRCcoeffs+2*i), ckt->CKTtime, 3 ) ) { - error = CKTsetBreak(ckt, *(here->VSRCcoeffs+2*i+2)); - if(error) return(error); - goto bkptset; - } + if ( ckt->CKTbreak && AlmostEqualUlps(*(here->VSRCcoeffs+2*i), ckt->CKTtime, 3 ) ) { + error = CKTsetBreak(ckt, *(here->VSRCcoeffs+2*i+2)); + if(error) return(error); + goto bkptset; + } } break; } diff --git a/src/spicelib/devices/vsrc/vsrcask.c b/src/spicelib/devices/vsrc/vsrcask.c index 5b4ce56af..d4ac4ea3c 100644 --- a/src/spicelib/devices/vsrc/vsrcask.c +++ b/src/spicelib/devices/vsrc/vsrcask.c @@ -78,6 +78,9 @@ VSRCask(CKTcircuit *ckt, GENinstance *inst, int which, IFvalue *value, IFvalue * case VSRC_R: value->rValue = here->VSRCr; return (OK); + case VSRC_TD: + value->rValue = here->VSRCrdelay; + return (OK); case VSRC_FCN_ORDER: value->rValue = here->VSRCfunctionOrder; return (OK); diff --git a/src/spicelib/devices/vsrc/vsrcdefs.h b/src/spicelib/devices/vsrc/vsrcdefs.h index 1ecf87680..05faa673c 100644 --- a/src/spicelib/devices/vsrc/vsrcdefs.h +++ b/src/spicelib/devices/vsrc/vsrcdefs.h @@ -50,6 +50,7 @@ typedef struct sVSRCinstance { double VSRCdF2phase; /* distortion f2 phase */ double VSRCr; /* pwl repeat */ + double VSRCrdelay; /* pwl delay period */ double *VSRCposIbrptr; /* pointer to sparse matrix element at * (positive node, branch equation) */ double *VSRCnegIbrptr; /* pointer to sparse matrix element at @@ -119,6 +120,7 @@ typedef struct sVSRCmodel { #define VSRC_AM 22 #define VSRC_R 23 +#define VSRC_TD 24 /* model parameters */ diff --git a/src/spicelib/devices/vsrc/vsrcload.c b/src/spicelib/devices/vsrc/vsrcload.c index b97069ad0..e0f8e18db 100644 --- a/src/spicelib/devices/vsrc/vsrcload.c +++ b/src/spicelib/devices/vsrc/vsrcload.c @@ -289,8 +289,19 @@ VSRCload(GENmodel *inModel, CKTcircuit *ckt) } break; case PWL: { - int i = 0, num_repeat = 0; - double foo, repeat_time = 0, end_time, breakpt_time; + int i = 0, num_repeat = 0, ii = 0; + double foo, repeat_time = 0, end_time, breakpt_time, itime; + + time -= here->VSRCrdelay; +// if(time > PER) { + /* repeating signal - figure out where we are */ + /* in period */ +// basetime = PER * floor(time/PER); +// time -= basetime; +// } + + + if(time < *(here->VSRCcoeffs)) { foo = *(here->VSRCcoeffs + 1) ; value = foo; @@ -298,19 +309,20 @@ VSRCload(GENmodel *inModel, CKTcircuit *ckt) } do { - for( ; i<(here->VSRCfunctionOrder/2)-1; i++ ) { - - if ( fabs( (*(here->VSRCcoeffs+2*i)+repeat_time) - time ) < 1e-20 ) { - foo = *(here->VSRCcoeffs+2*i+1); - value = foo; - goto loadDone; - } else if ( (*(here->VSRCcoeffs+2*i)+repeat_time < time) && (*(here->VSRCcoeffs+2*(i+1))+repeat_time > time) ) { - foo = *(here->VSRCcoeffs+2*i+1) + (((time-(*(here->VSRCcoeffs+2*i)+repeat_time))/ + for(i=ii ; i<(here->VSRCfunctionOrder/2)-1; i++ ) { + itime = *(here->VSRCcoeffs+2*i); + if ( AlmostEqualUlps(itime+repeat_time, time, 3 )) { +// if ( fabs( (*(here->VSRCcoeffs+2*i)+repeat_time) - time ) < 1e-20 ) { + foo = *(here->VSRCcoeffs+2*i+1); + value = foo; + goto loadDone; + } else if ( (*(here->VSRCcoeffs+2*i)+repeat_time < time) && (*(here->VSRCcoeffs+2*(i+1))+repeat_time > time) ) { + foo = *(here->VSRCcoeffs+2*i+1) + (((time-(*(here->VSRCcoeffs+2*i)+repeat_time))/ (*(here->VSRCcoeffs+2*(i+1)) - *(here->VSRCcoeffs+2*i))) * (*(here->VSRCcoeffs+2*i+3) - *(here->VSRCcoeffs+2*i+1))); - value = foo; - goto loadDone; - } + value = foo; + goto loadDone; + } } foo = *(here->VSRCcoeffs+ here->VSRCfunctionOrder-1) ; value = foo; @@ -320,7 +332,7 @@ VSRCload(GENmodel *inModel, CKTcircuit *ckt) end_time = *(here->VSRCcoeffs + here->VSRCfunctionOrder-2); breakpt_time = *(here->VSRCcoeffs + here->VSRCrBreakpt); repeat_time = end_time + (end_time - breakpt_time)*num_repeat++ - breakpt_time; - i = here->VSRCrBreakpt - 1; + ii = here->VSRCrBreakpt/2; } while ( here->VSRCrGiven ); break; } diff --git a/src/spicelib/devices/vsrc/vsrcpar.c b/src/spicelib/devices/vsrc/vsrcpar.c index 6f40f7d0d..304b00836 100644 --- a/src/spicelib/devices/vsrc/vsrcpar.c +++ b/src/spicelib/devices/vsrc/vsrcpar.c @@ -86,7 +86,11 @@ VSRCparam(int param, IFvalue *value, GENinstance *inst, IFvalue *select) } break; - case VSRC_R: + case VSRC_TD: + here->VSRCrdelay = value->rValue; + break; + case VSRC_R: { + double end_time; here->VSRCr = value->rValue; here->VSRCrGiven = TRUE; @@ -94,13 +98,19 @@ VSRCparam(int param, IFvalue *value, GENinstance *inst, IFvalue *select) here->VSRCrBreakpt = i; if ( here->VSRCr == *(here->VSRCcoeffs+i) ) break; } - - if ( here->VSRCr != *(here->VSRCcoeffs+here->VSRCrBreakpt) ) { - fprintf(stderr, "ERROR: repeat value %g for pwl voltage source does not match breakpoint!\n", here->VSRCr ); + + end_time = *(here->VSRCcoeffs + here->VSRCfunctionOrder-2); + if ( here->VSRCr > end_time ) { + fprintf(stderr, "ERROR: repeat start time value %g for pwl voltage source must be smaller than final time point given!\n", here->VSRCr ); return ( E_PARMVAL ); } - break; + if ( here->VSRCr != *(here->VSRCcoeffs+here->VSRCrBreakpt) ) { + fprintf(stderr, "ERROR: repeat start time value %g for pwl voltage source does not match any time point given!\n", here->VSRCr ); + return ( E_PARMVAL ); + } + + break; } case VSRC_SFFM: here->VSRCfunctionType = SFFM; here->VSRCfuncTGiven = TRUE; diff --git a/visualc/vngspice.sln b/visualc/vngspice.sln index 61f6266ed..992f525b0 100644 --- a/visualc/vngspice.sln +++ b/visualc/vngspice.sln @@ -25,8 +25,8 @@ Global {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.console_release|Win32.Build.0 = console_release|Win32 {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.console_release|x64.ActiveCfg = console_release|x64 {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.console_release|x64.Build.0 = console_release|x64 - {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|Win32.ActiveCfg = Debug|Win32 - {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|Win32.Build.0 = Debug|Win32 + {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|Win32.ActiveCfg = Release|Win32 + {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|Win32.Build.0 = Release|Win32 {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|x64.ActiveCfg = Debug|x64 {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Debug|x64.Build.0 = Debug|x64 {83E315C7-EDD3-4F6B-AF28-87A92A4FA49A}.Release|Win32.ActiveCfg = Release|Win32