fix: NPN's dynamic resistance
authoryu.dongliang <18588496441@163.com>
Thu, 18 Apr 2024 05:55:51 +0000 (13:55 +0800)
committeryu.dongliang <18588496441@163.com>
Thu, 18 Apr 2024 05:55:51 +0000 (13:55 +0800)
ses_step_jr.c
ses_step_va.c
ses_step_va_diode.c
ses_step_va_transistor.c

index 4bf0c1367196ab5cce753cb9613e52a7a1a87559..36eed9bef3ded9b24623602b3c6c05f99e3526fd 100644 (file)
@@ -16,7 +16,7 @@ void __ses_path_sr(ScfEfunction* f, ses_path_t* path, int i, int j, double* r)
 
        *r = p1->sr - p0->pr;
 
-       scf_logi("c%ldp%ld-c%ldp%ld, r: %lg, p0->sr: %lg, p0->pr: %lg, p1->sr: %lg, p1->pr: %lg\n",
+       scf_logd("c%ldp%ld-c%ldp%ld, r: %lg, p0->sr: %lg, p0->pr: %lg, p1->sr: %lg, p1->pr: %lg\n",
                        p0->cid, p0->id, p1->cid, p1->id, *r, p0->sr, p0->pr, p1->sr, p1->pr);
 }
 
index 08a9ea2def1aebadacce0c464cbbe2fd0faca384..afa56fa40bdae327e7cc4c656a940219a9793d0e 100644 (file)
@@ -153,7 +153,7 @@ int __ses_path_va(ScfEfunction* f, ses_path_t* path, int* changed)
        for (i = 0; i < path->pins->size; i++) {
                p  =        path->pins->data[i];
 
-               scf_logw("c%ldp%ld, p->r: %lg, dr: %lg, sr: %lg, pr: %lg\n", p->cid, p->id, p->r, p->dr, p->sr, p->pr);
+               scf_logd("c%ldp%ld, p->r: %lg, dr: %lg, sr: %lg, pr: %lg\n", p->cid, p->id, p->r, p->dr, p->sr, p->pr);
 
                __ses_path_split_v(f, path, i0, i, a, 0);
 
index 0c1d4b699403c333229dc8045557f103544d0c3e..fd1ed3cdb9609ac26926605440d458aefa00f86f 100644 (file)
@@ -1,5 +1,54 @@
 #include"ses_core.h"
 
+void __ses_path_dr_forward(ScfEfunction* f, ses_path_t* path, int i, int j, double a)
+{
+       ScfEpin* p  = path->pins->data[i];
+       ScfEpin* p1 = path->pins->data[j];
+
+       double   r;
+       double   jr;
+
+       int k;
+       for (k = i; k <= j; k++) {
+
+               ScfEcomponent* c;
+
+               p  = path->pins->data[k];
+               c  = f->components[p->cid];
+
+               if (SCF_EDA_Diode == c->type && SCF_EDA_Diode_NEG == p->id) {
+
+                       ses_ui_r(&p->dr, NULL, SCF_EDA_V_Diode_ON, 0, a, 0);
+
+                       p->dr -= p->r;
+
+                       scf_logw("c%ldp%ld, v: %lg, r: %lg, a: %lg, dr: %lg\n", p->cid, p->id, SCF_EDA_V_Diode_ON, p->r, a, p->dr);
+
+                       p1    = c->pins[SCF_EDA_Diode_POS];
+                       p1->a = a;
+
+               } else if (SCF_EDA_NPN == c->type && SCF_EDA_NPN_B == p->id) {
+
+                       ses_ui_r(&p->dr, NULL, SCF_EDA_V_NPN_ON, 0, a, 0);
+
+                       p->dr -= p->r;
+
+                       p1    = c->pins[SCF_EDA_NPN_C];
+                       p1->a = p1->hfe * a;
+                       p1->aconst = 1;
+
+                       scf_logw("c%ldp%ld, v: %lg, r: %lg, a: %lg, dr: %lg, c%ldp%ld->a: %lg\n",
+                                       p->cid, p->id, SCF_EDA_V_NPN_ON, p->r, a, p->dr, p1->cid, p1->id, p1->a);
+
+                       p1    = c->pins[SCF_EDA_NPN_E];
+                       p1->a = (1 + p1->hfe) * a;
+                       p1->aconst = 1;
+
+                       a = p1->a;
+               }
+       }
+}
+
 void __ses_path_split_i(ScfEfunction* f, ses_path_t* path, int i, int j, double la, double* a)
 {
        ScfEcomponent* c;
@@ -45,10 +94,12 @@ void __ses_path_split_i(ScfEfunction* f, ses_path_t* path, int i, int j, double
                        int ret = __ses_path_va_diode(f, child);
                        if (ret < 0)
                                ses_split_i(&child->a, NULL, la, 0, child->pr, 0, r, 0);
+                       else
+                               goto ok;
                }
 
-               scf_logi("j: %d, c%ldp%ld--c%ldp%ld, v: %lg, child->pr: %lg, r: %lg, child->a: %lg, el->a: %lg\n",
-                               j, cp0->cid, cp0->id, cp1->cid, cp1->id, v, child->pr, r, child->a, la);
+               scf_logi("k: %d, c%ldp%ld--c%ldp%ld, v: %lg, child->pr: %lg, r: %lg, child->a: %lg, el->a: %lg\n",
+                               k, cp0->cid, cp0->id, cp1->cid, cp1->id, v, child->pr, r, child->a, la);
 
                cp1->v = p1->v;
                cp0->v = p0->v;
@@ -60,76 +111,19 @@ void __ses_path_split_i(ScfEfunction* f, ses_path_t* path, int i, int j, double
 
                cp0->a = ca;
 
-               c = f->components[cp1->cid];
-
-               if (SCF_EDA_NPN == c->type && SCF_EDA_NPN_E == cp1->id)
-                       p = child->pins->data[child->pins->size - 2];
-               else
-                       p = cp1;
-
-               ses_ui_r(&p->dr, NULL, v, 0, ca, 0);
-
-               p->dr -= cp1->sr;
-               p->a   = ca;
+               if (child->n_diodes > 0)
+                       __ses_path_dr_forward(f, child, 0, child->pins->size - 1, ca);
 
+ok:
                cp1->sr = _sr;
                cp1->pr = _pr;
 
-               scf_logi("j: %d, c%ldp%ld--c%ldp%ld, v: %lg, child->pr: %lg, r: %lg, cp1->a: %lg, el->a: %lg, c%ldp%ld->dr: %lg\n\n",
-                               j, cp0->cid, cp0->id, cp1->cid, cp1->id, v, child->pr, r, p->a, la, p->cid, p->id, p->dr);
-       }
-}
-
-void __ses_path_dr_forward(ScfEfunction* f, ses_path_t* path, int i, int j, double a, double ja)
-{
-       ScfEpin* p  = path->pins->data[i];
-       ScfEpin* p1 = path->pins->data[j];
-
-       double   r;
-       double   jr;
-
-       int k;
-       for (k = i; k <= j; k++) {
-
-               ScfEcomponent* c;
-
-               p  = path->pins->data[k];
-               c  = f->components[p->cid];
-
-               if (SCF_EDA_Diode == c->type && SCF_EDA_Diode_NEG == p->id) {
-
-                       ses_ui_r(&p->dr, NULL, SCF_EDA_V_Diode_ON, 0, a, 0);
-
-                       p->dr -= p->r;
-
-                       scf_logw("c%ldp%ld, v: %lg, r: %lg, a: %lg, dr: %lg\n", p->cid, p->id, SCF_EDA_V_Diode_ON, p->r, a, p->dr);
-
-                       p1    = c->pins[SCF_EDA_Diode_POS];
-                       p1->a = a;
-
-               } else if (SCF_EDA_NPN == c->type && SCF_EDA_NPN_B == p->id) {
-
-                       ses_ui_r(&p->dr, NULL, SCF_EDA_V_NPN_ON, 0, a, 0);
-
-                       p->dr -= p->r;
-
-                       p1    = c->pins[SCF_EDA_NPN_C];
-                       p1->a = p1->hfe * a;
-                       p1->aconst = 1;
-
-                       scf_logw("c%ldp%ld, v: %lg, r: %lg, a: %lg, dr: %lg, c%ldp%ld->a: %lg\n",
-                                       p->cid, p->id, SCF_EDA_V_NPN_ON, p->r, a, p->dr, p1->cid, p1->id, p1->a);
-
-                       p1    = c->pins[SCF_EDA_NPN_E];
-                       p1->a = (1 + p1->hfe) * a;
-                       p1->aconst = 1;
-
-                       a = p1->a;
-               }
+               scf_logi("k: %d, c%ldp%ld--c%ldp%ld, v: %lg, child->pr: %lg, r: %lg, child->a: %lg, cp1->a: %lg, el->a: %lg\n\n",
+                               k, cp0->cid, cp0->id, cp1->cid, cp1->id, v, child->pr, r, child->a, cp1->a, la);
        }
 }
 
-void __ses_path_dr_reverse(ScfEfunction* f, ses_path_t* path, int i, int j, double a, double ja)
+void __ses_path_dr_reverse(ScfEfunction* f, ses_path_t* path, int i, int j, double a)
 {
        ScfEpin* p  = path->pins->data[i];
        ScfEpin* p1 = path->pins->data[j];
@@ -307,7 +301,7 @@ int __ses_path_va_diode(ScfEfunction* f, ses_path_t* path)
                scf_loge("info->i: %d, info->j: %d, c%ldp%ld--c%ldp%ld, pi->v: %lg, pj->v: %lg, pi->a: %lg\n\n",
                                info->i, info->j, pi->cid, pi->id, pj->cid, pj->id, pi->v, pj->v, pi->a);
 
-               __ses_path_dr_forward(f, path, info->i, info->j, pi->a, 0);
+               __ses_path_dr_forward(f, path, info->i, info->j, pi->a);
        }
 
        return 0;
index eb33d4c367302c29c82875e82d7553219e301df4..6d230fa039b349a4a893cb3e647672f4c8496e3e 100644 (file)
@@ -121,11 +121,11 @@ static int __ses_path_va_transistor(ScfEfunction* f, ses_path_t* path)
        p0 = path->pins->data[0];
        pj = path->pins->data[j];
 
-       el     = f->elines[p0->lid];
-       p0->v  = el->v;
+       el    = f->elines[p0->lid];
+       p0->v = el->v;
 
-       el     = f->elines[pj->lid];
-       pj->v  = el->v;
+       el    = f->elines[pj->lid];
+       pj->v = el->v;
 
        for (i = path->pins->size - 1; i >= 0; i--) {
                pc = path->pins->data[i];
@@ -238,13 +238,11 @@ static int ses_path_va_transistor(ScfEfunction* f, ses_path_t* path)
        size_t j;
        size_t k;
 
-       if (!path)
+       if (!path || path->pins->size < 2)
                return -EINVAL;
 
-       if (path->pins->size < 2) {
-               scf_loge("\n");
-               return -EINVAL;
-       }
+       if (2 == path->pins->size)
+               return 0;
 
        B  = f->components[0];
        Bp = B->pins[SCF_EDA_Battery_POS];