implement "case"

This commit is contained in:
rlar 2017-07-14 19:07:03 +02:00 committed by Holger Vogt
parent b272e153c6
commit aa5009fbe4
4 changed files with 148 additions and 47 deletions

View File

@ -2633,6 +2633,37 @@ inline double _d1_pow(double x,double y) { return (x==0.0)?0.0:((log(x)/exp(0.
<admst:text select="if[dynamic='yes']" format="#endif /* if(...) */\n"/>
</admst:template>
<!-- analog//case -->
<admst:template match="case">
<admst:text format="/* -- CASE BEGIN -- */;\n"/>
<admst:variable name="casecondition" path="case"/>
<admst:variable name="havedefault" string="no"/>
<!-- check for default -->
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:variable name="havedefault" string="yes"/>
</admst:for-each>
<admst:for-each select="caseitem/[defaultcase='no']">
<admst:text format="/* CASE ITEM */\n"/>
<admst:text format="if\n("/>
<admst:join select="condition" separator="||">
<admst:text format="((%(e($casecondition/tree)))==(%(.)))"/>
</admst:join>
<admst:text format=")\n"/>
<admst:text test="code/[datatypename!='block']" format="{\n"/>
<admst:apply-templates select="code" match="%(datatypename)" required="yes"/>
<admst:text test="code/[datatypename!='block']" format="}\n"/>
<admst:text format="else\n"/>
</admst:for-each>
<admst:text select="[$havedefault='no']" format="{ /* no default */ }\n"/>
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:text format="/* CASE DEFAULT */\n"/>
<admst:text test="code/[datatypename!='block']" format="{\n"/>
<admst:apply-templates select="code" match="%(datatypename)" required="yes"/>
<admst:text test="code/[datatypename!='block']" format="}\n"/>
</admst:for-each>
<admst:text format="/* -- CASE END -- */;\n"/>
</admst:template>
<!-- analog//nilled -->
<admst:template match="nilled">
</admst:template>
@ -2738,8 +2769,13 @@ inline double _d1_pow(double x,double y) { return (x==0.0)?0.0:((log(x)/exp(0.
<admst:when test="adms[datatypename='callfunction']"/>
<admst:when test="adms[datatypename='nilled']"/>
<admst:when test="adms[datatypename='blockvariable']"/>
<admst:when test="adms[datatypename='case']">
<admst:for-each select="caseitem">
<admst:apply-templates select="code" match="block:local:declaration"/>
</admst:for-each>
</admst:when>
<admst:otherwise>
<admst:fatal format="'datatypename=%(adms/datatypename)': should not be reached %s\n"/>
<admst:fatal format="'datatypename=%(adms/datatypename)': should not be reached !\n"/>
</admst:otherwise>
</admst:choose>
</admst:template>

View File

@ -138,6 +138,36 @@
</admst:choose>
</admst:if>
</admst:when>
<admst:when test="[datatypename='case']">
<admst:text format="/* -- CASE BEGIN -- */;\n"/>
<admst:variable name="casecondition" path="case"/>
<admst:variable name="havedefault" string="no"/>
<!-- check for default -->
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:variable name="havedefault" string="yes"/>
</admst:for-each>
<admst:for-each select="caseitem/[defaultcase='no']">
<admst:text format="/* CASE ITEM */\n"/>
<admst:text format="if\n("/>
<admst:join select="condition" separator="||">
<admst:apply-templates select="$(casecondition)" match="expression:stringify:noprobe"/>
<admst:text format="((%s)==(%(.)))"/>
</admst:join>
<admst:text format=")\n"/>
<admst:text format="{\n"/>
<admst:apply-templates select="code" match="evaluatetopology"/>
<admst:text format="}\n"/>
<admst:text format="else\n"/>
</admst:for-each>
<admst:text select="[$havedefault='no']" format="{ /* no default */ }\n"/>
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:text format="/* CASE DEFAULT */\n"/>
<admst:text format="{\n"/>
<admst:apply-templates select="code" match="evaluatetopology"/>
<admst:text format="}\n"/>
</admst:for-each>
<admst:text format="/* -- CASE END -- */;\n"/>
</admst:when>
<admst:when test="[datatypename='contribution']">
<admst:if test="lhs[discipline/potential=nature]">
<admst:choose>

View File

@ -1599,8 +1599,35 @@
<!-- analog//case -->
<admst:template match="case">
<admst:error format="case statement: please implement me! (inside block)\n"/>
<admst:text format="/*CASE*/;\n"/>
<admst:text format="/* -- CASE BEGIN -- */;\n"/>
<admst:variable name="casecondition" path="case"/>
<admst:variable name="havedefault" string="no"/>
<!-- check for default -->
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:variable name="havedefault" string="yes"/>
</admst:for-each>
<admst:for-each select="caseitem/[defaultcase='no']">
<admst:text format="/* CASE ITEM */\n"/>
<admst:text format="if\n("/>
<admst:join select="condition" separator="||">
<admst:apply-templates select="$casecondition" match="expression:stringify:noprobe"/>
<admst:text format="((%s)==(%(.)))"/>
</admst:join>
<admst:text format=")\n"/>
<admst:text test="code/[datatypename!='block']" format="{\n"/>
<admst:apply-templates select="code" match="%(datatypename)" required="yes"/>
<admst:text test="code/[datatypename!='block']" format="}\n"/>
<admst:text format="else\n"/>
</admst:for-each>
<admst:text select="[$havedefault='no']" format="{ /* no default */ }\n"/>
<admst:for-each select="caseitem/[defaultcase='yes']">
<admst:text format="/* CASE DEFAULT */\n"/>
<admst:text test="code/[datatypename!='block']" format="{\n"/>
<admst:apply-templates select="code" match="%(datatypename)" required="yes"/>
<admst:text test="code/[datatypename!='block']" format="}\n"/>
</admst:for-each>
<admst:text format="/* -- CASE END -- */;\n"/>
</admst:template>
<!-- analog//nilled -->

View File

@ -165,14 +165,14 @@
`define BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEnd, rgeo, TYPE, Rend) \
if (TYPE == 1) begin \
if(rgeo == 1 || rgeo == 2 || rgeo == 5) \
begin \
case(rgeo) \
1, 2, 5: begin \
if (nuEnd == 0.0) \
Rend = 0.0; \
else \
Rend = Rsh * DMCG / (Weffcj * nuEnd); \
end \
else if(rgeo == 3 || rgeo == 4 || rgeo == 6) begin \
3, 4, 6: begin \
if ((DMCG + DMCI) == 0.0) \
`STROBE("(DMCG + DMCI) can not be equal to zero"); \
if (nuEnd == 0.0) \
@ -180,21 +180,22 @@
else \
Rend = Rsh * Weffcj / (3.0 * nuEnd * (DMCG + DMCI)); \
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified RGEO = %d not matched (BSIM6RdsEndIso), \
Rend is set to zero.", rgeo); \
Rend = 0.0; \
end \
endcase \
end \
else begin \
if(rgeo == 1 || rgeo == 3 || rgeo == 7) \
begin \
case(rgeo) \
1, 3, 7: begin \
if (nuEnd == 0.0) \
Rend = 0.0; \
else \
Rend = Rsh * DMCG / (Weffcj * nuEnd); \
end \
else if(rgeo == 2 || rgeo == 4 || rgeo == 8) begin \
2, 4, 8: begin \
if ((DMCG + DMCI) == 0.0) \
`STROBE("(DMCG + DMCI) can not be equal to zero"); \
if (nuEnd == 0.0) \
@ -202,25 +203,26 @@
else \
Rend = Rsh * Weffcj / (3.0 * nuEnd * (DMCG + DMCI)); \
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified RGEO=%d not matched (BSIM6RdsEndIso \
type 2), Rend is set to zero.", rgeo); \
Rend = 0.0; \
end \
endcase \
end
`define BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEnd, rgeo, TYPE, Rend) \
begin \
if (TYPE == 1) begin \
if(rgeo == 1 || rgeo == 2 || rgeo == 5) \
begin \
case(rgeo) \
1, 2, 5: begin \
if (nuEnd == 0.0) \
Rend = 0.0; \
else \
Rend = Rsh * DMCG / (Weffcj * nuEnd); \
end \
else if (rgeo == 3 || rgeo == 4 || rgeo == 6) begin \
3, 4, 6: begin \
if (DMCG == 0.0) \
`STROBE("DMCG can not be equal to zero"); \
if (nuEnd == 0.0) \
@ -228,21 +230,22 @@
else \
Rend = Rsh * Weffcj / (6.0 * nuEnd * DMCG); \
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified RGEO = %d not matched (BSIM6RdsEndSha), \
Rend is set to zero.", rgeo); \
Rend = 0.0; \
end \
endcase \
end \
else begin \
if(rgeo == 1 || rgeo == 3 || rgeo == 7) \
begin \
case(rgeo) \
1, 3, 7: begin \
if (nuEnd == 0.0) \
Rend = 0.0; \
else \
Rend = Rsh * DMCG / (Weffcj * nuEnd); \
end \
else if (rgeo == 2 || rgeo == 4 || rgeo == 8) begin \
2, 4, 8: begin \
if (DMCG == 0.0) \
`STROBE("DMCG can not be equal to zero"); \
if (nuEnd == 0.0) \
@ -250,11 +253,12 @@
else \
Rend = Rsh * Weffcj / (6.0 * nuEnd * DMCG); \
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified RGEO=%d not matched (BSIM6RdsEndSha \
type 2), Rend is set to zero.", rgeo); \
Rend = 0.0; \
end \
endcase \
end \
end
@ -275,8 +279,8 @@
Rint = Rsh * DMCG / ( Weffcj * nuIntD); \
end \
end \
if (geo == 0) \
begin \
case(geo) \
0: begin \
if (TYPE == 1) \
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
@ -284,7 +288,7 @@
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 1) begin \
1: begin \
if (TYPE == 1) \
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
@ -292,7 +296,7 @@
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 2) begin \
2: begin \
if (TYPE == 1) \
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
@ -300,7 +304,7 @@
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 3) begin \
3: begin \
if (TYPE == 1) \
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
@ -308,14 +312,14 @@
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 4) begin \
4: begin \
if (TYPE == 1) \
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
else \
Rend = Rsh * DMDG / Weffcj; \
end \
else if (geo == 5) begin \
5: begin \
if (TYPE == 1) \
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndS, \
rgeo, 1, Rend) \
@ -326,14 +330,14 @@
Rend = Rsh * DMDG / (Weffcj * nuEndD); \
end\
end \
else if (geo == 6) begin \
6: begin \
if (TYPE == 1) \
Rend = Rsh * DMDG / Weffcj; \
else \
`BSIM6RdsEndIso(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 7) begin \
7:begin \
if (TYPE == 1) begin \
if (nuEndS==0) \
Rend = 0; \
@ -343,10 +347,10 @@
`BSIM6RdsEndSha(Weffcj, Rsh, DMCG, DMCI, DMDG, nuEndD, \
rgeo, 0, Rend) \
end \
else if (geo == 8) begin \
8: begin \
Rend = Rsh * DMDG / Weffcj; \
end \
else if (geo == 9) begin /* all wide contacts assumed for geo = 9 and 10 */\
9: begin /* all wide contacts assumed for geo = 9 and 10 */\
if (TYPE == 1) begin \
Rend = 0.5 * Rsh * DMCG / Weffcj; \
if (nf == 2.0) \
@ -359,7 +363,7 @@
Rint = Rsh * DMCG / (Weffcj * nf); \
end \
end \
else if (geo == 10) begin \
10: begin \
if (TYPE == 1) begin \
Rend = 0.0; \
Rint = Rsh * DMCG / (Weffcj * nf); \
@ -372,11 +376,12 @@
Rint = Rsh * DMCG / (Weffcj * (nf - 2.0)); \
end \
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified RGEO=%d not matched (BSIM6RdseffGeo \
), Rint is set to zero.", rgeo); \
Rint = 0.0; \
end \
endcase \
if (Rint <= 0.0) \
Rtot = Rend; \
else if (Rend <= 0.0) \
@ -407,74 +412,74 @@
ADsha = DMCG * Weffcj;\
ASmer = DMDG * Weffcj; \
ADmer = DMDG * Weffcj; \
if(geo == 0) \
begin \
case(geo) \
0: begin \
Ps = nuEndS * PSiso + nuIntS * PSsha;\
Pd = nuEndD * PDiso + nuIntD * PDsha;\
As = nuEndS * ASiso + nuIntS * ASsha;\
Ad = nuEndD * ADiso + nuIntD * ADsha;\
end \
else if(geo == 1) begin \
1: begin \
Ps = nuEndS * PSiso + nuIntS * PSsha;\
Pd = (nuEndD + nuIntD) * PDsha;\
As = nuEndS * ASiso + nuIntS * ASsha;\
Ad = (nuEndD + nuIntD) * ADsha;\
end \
else if(geo == 2) begin \
2: begin \
Ps = (nuEndS + nuIntS) * PSsha;\
Pd = nuEndD * PDiso + nuIntD * PDsha;\
As = (nuEndS + nuIntS) * ASsha;\
Ad = nuEndD * ADiso + nuIntD * ADsha;\
end \
else if(geo == 3) begin \
3: begin \
Ps = (nuEndS + nuIntS) * PSsha;\
Pd = (nuEndD + nuIntD) * PDsha;\
As = (nuEndS + nuIntS) * ASsha;\
Ad = (nuEndD + nuIntD) * ADsha;\
end \
else if(geo == 4) begin \
4: begin \
Ps = nuEndS * PSiso + nuIntS * PSsha;\
Pd = nuEndD * PDmer + nuIntD * PDsha;\
As = nuEndS * ASiso + nuIntS * ASsha;\
Ad = nuEndD * ADmer + nuIntD * ADsha;\
end \
else if(geo == 5) begin \
5: begin \
Ps = (nuEndS + nuIntS) * PSsha;\
Pd = nuEndD * PDmer + nuIntD * PDsha;\
As = (nuEndS + nuIntS) * ASsha;\
Ad = nuEndD * ADmer + nuIntD * ADsha;\
end \
else if(geo == 6) begin \
6: begin \
Ps = nuEndS * PSmer + nuIntS * PSsha;\
Pd = nuEndD * PDiso + nuIntD * PDsha;\
As = nuEndS * ASmer + nuIntS * ASsha;\
Ad = nuEndD * ADiso + nuIntD * ADsha;\
end \
else if(geo == 7) begin \
7: begin \
Ps = nuEndS * PSmer + nuIntS * PSsha;\
Pd = (nuEndD + nuIntD) * PDsha;\
As = nuEndS * ASmer + nuIntS * ASsha;\
Ad = (nuEndD + nuIntD) * ADsha;\
end \
else if(geo == 8) begin \
8: begin \
Ps = nuEndS * PSmer + nuIntS * PSsha;\
Pd = nuEndD * PDmer + nuIntD * PDsha;\
As = nuEndS * ASmer + nuIntS * ASsha;\
Ad = nuEndD * ADmer + nuIntD * ADsha;\
end \
else if(geo == 9) begin \
9: begin \
Ps = PSiso + (nf - 1.0) * PSsha;\
Pd = nf * PDsha;\
As = ASiso + (nf - 1.0) * ASsha;\
Ad = nf * ADsha;\
end \
else if(geo == 10) begin \
10: begin \
Ps = nf * PSsha;\
Pd = PDiso + (nf - 1.0) * PDsha;\
As = nf * ASsha;\
Ad = ADiso + (nf - 1.0) * ADsha;\
end \
else begin \
default: begin \
`STROBE2("Warning: (instance BSIM6) Specified GEO=%d not matched (BSIM6RdseffGeo \
), PS,PD,AS,AD set to zero.", geo); \
Ps = 0;\
@ -482,6 +487,7 @@
As = 0;\
Ad = 0;\
end \
endcase \
end \
//******************************************************
@ -3956,7 +3962,8 @@ DevTemp = $temperature + DTEMP;
thetanoisq = T4 * T4;
cm_igid=0; //Initialization
if(TNOIMOD == 0) begin
case(TNOIMOD)
0: begin
`endif
QSi = - NF * Weff * Leff * Cox *Vt * Qs;
QDi = - NF * Weff * Leff * Cox *Vt * Qd;
@ -3967,7 +3974,7 @@ DevTemp = $temperature + DTEMP;
I(`IntrinsicDrain, `IntrinsicSource) <+ white_noise(sidn, "id");
`ifdef __TNOISW__
end
else if(TNOIMOD == 1) begin
1: begin
Vtn = 2.0 * nq * nVt;
T0 = ueff * Dptwg * Moc * Cox * Vtn;
T1 = 0.5 * (qs + qdeff);
@ -4006,6 +4013,7 @@ DevTemp = $temperature + DTEMP;
I(`IntrinsicGate,`IntrinsicSource) <+ ddt(0.5 * ((1.0 + sigvds) * mig * Cox * Weff * NF * Leff * V(NC)));
I(`IntrinsicGate,`IntrinsicDrain) <+ ddt(0.5 * ((1.0 - sigvds) * mig * Cox * Weff * NF * Leff * V(NC)));
end
endcase
I(N2) <+ V(N2);
I(NR) <+ V(NR);