From 97768dcb0ab6303d065c771e439b361439775473 Mon Sep 17 00:00:00 2001 From: "yu.dongliang" <18588496441@163.com> Date: Fri, 4 Apr 2025 01:54:42 +0800 Subject: [PATCH] 1, support to 'TTL Nand gate' & some simple electronic graph like 'ADD' made by it. 2, delete some unused C files. --- Makefile | 3 +- cpk/Makefile | 35 +- cpk/add_gate.c | 80 -- cpk/and_gate.c | 63 -- cpk/nand.c | 78 -- cpk/nand.cpk | Bin 404 -> 410 bytes cpk/nor.cpk | Bin 394 -> 399 bytes cpk/not.cpk | Bin 262 -> 266 bytes cpk/or_gate.c | 63 -- cpk/ttl_add.c | 100 ++ cpk/ttl_add.cpk | Bin 0 -> 1959 bytes cpk/ttl_add_test.c | 52 + cpk/ttl_and.c | 56 + cpk/ttl_and.cpk | Bin 0 -> 628 bytes cpk/ttl_and_test.c | 47 + cpk/ttl_nand.c | 108 ++ cpk/ttl_nand.cpk | Bin 0 -> 1807 bytes cpk/ttl_nand_delay.c | 100 ++ cpk/ttl_nand_gate.c | 53 + cpk/ttl_nand_gate2.c | 101 ++ cpk/ttl_nand_test.c | 47 + cpk/ttl_nor.c | 57 + cpk/ttl_nor.cpk | Bin 0 -> 593 bytes cpk/ttl_nor_test.c | 47 + cpk/ttl_or.c | 63 ++ cpk/ttl_or.cpk | Bin 0 -> 889 bytes cpk/ttl_or_test.c | 47 + cpk/ttl_xor.c | 90 ++ cpk/ttl_xor.cpk | Bin 0 -> 1698 bytes cpk/ttl_xor_test.c | 47 + examples/add_gate.cpk | Bin 864 -> 0 bytes examples/and.cpk | Bin 747 -> 0 bytes examples/and_gate.cpk | Bin 542 -> 0 bytes examples/astable_multivibrator.cpk | Bin 0 -> 827 bytes examples/colpitts_oscillator.cpk | Bin 976 -> 976 bytes examples/or_gate.cpk | Bin 541 -> 0 bytes examples/pnp_oscillator.cpk | Bin 1046 -> 1046 bytes examples/sin_oscillator.cpk | Bin 1046 -> 1046 bytes main.c | 51 +- pack/scf_pack.c | 11 +- scf_eda_pack.c | 153 +-- scf_eda_pack.h | 97 +- ses_core.h | 180 +--- ses_graph.c | 2 - ses_layout.c | 1568 +-------------------------- ses_layout_function.c | 1588 ++++++++++++++++++++++++++++ ses_node_analysis.c | 383 ++++--- ses_path.c | 164 ++- ses_step_battery.c | 8 +- ses_step_dc_diode.c | 71 +- ses_step_dc_npn.c | 79 +- ses_step_dc_pnp.c | 78 +- ses_step_draw.c | 569 +++++++++- ses_step_jr.c | 22 +- ses_step_open.c | 117 +- ses_step_output.c | 8 +- ses_step_status.c | 124 --- ses_step_topo.c | 1059 +++++++++++++------ ses_step_va.c | 65 +- ses_step_va_diode.c | 383 ------- ses_step_va_nodes.c | 25 +- ses_steps.c | 56 +- ses_utils.c | 51 +- 63 files changed, 4789 insertions(+), 3460 deletions(-) delete mode 100644 cpk/add_gate.c delete mode 100644 cpk/and_gate.c delete mode 100644 cpk/nand.c delete mode 100644 cpk/or_gate.c create mode 100644 cpk/ttl_add.c create mode 100644 cpk/ttl_add.cpk create mode 100644 cpk/ttl_add_test.c create mode 100644 cpk/ttl_and.c create mode 100644 cpk/ttl_and.cpk create mode 100644 cpk/ttl_and_test.c create mode 100644 cpk/ttl_nand.c create mode 100644 cpk/ttl_nand.cpk create mode 100644 cpk/ttl_nand_delay.c create mode 100644 cpk/ttl_nand_gate.c create mode 100644 cpk/ttl_nand_gate2.c create mode 100644 cpk/ttl_nand_test.c create mode 100644 cpk/ttl_nor.c create mode 100644 cpk/ttl_nor.cpk create mode 100644 cpk/ttl_nor_test.c create mode 100644 cpk/ttl_or.c create mode 100644 cpk/ttl_or.cpk create mode 100644 cpk/ttl_or_test.c create mode 100644 cpk/ttl_xor.c create mode 100644 cpk/ttl_xor.cpk create mode 100644 cpk/ttl_xor_test.c delete mode 100644 examples/add_gate.cpk delete mode 100644 examples/and.cpk delete mode 100644 examples/and_gate.cpk create mode 100644 examples/astable_multivibrator.cpk delete mode 100644 examples/or_gate.cpk create mode 100644 ses_layout_function.c delete mode 100644 ses_step_status.c delete mode 100644 ses_step_va_diode.c diff --git a/Makefile b/Makefile index 4a9b09a..4dddb79 100644 --- a/Makefile +++ b/Makefile @@ -4,6 +4,7 @@ CFILES += scf_eda_pack.c CFILES += pack/scf_pack.c CFILES += ses_layout.c +CFILES += ses_layout_function.c CFILES += ses_graph.c CFILES += ses_utils.c @@ -28,7 +29,7 @@ CFILES += ses_step_va_nodes.c CFILES += ses_step_output.c CFILES += ses_step_draw.c -CFLAGS += -g -D_GNU_SOURCE +CFLAGS += -g -D_GNU_SOURCE #-Wunused-variable CFLAGS += -I./ CFLAGS += -I./pack diff --git a/cpk/Makefile b/cpk/Makefile index 446ede5..c91dd6c 100644 --- a/cpk/Makefile +++ b/cpk/Makefile @@ -1,13 +1,34 @@ -#CFILES += nand.c -#CFILES += nor.c -#CFILES += not.c -#CFILES += and_gate.c -#CFILES += or_gate.c -CFILES += add_gate.c +CFILES += ttl_nand.c +#CFILES += ttl_and.c +#CFILES += ttl_or.c +#CFILES += ttl_nor.c +#CFILES += ttl_xor.c +#CFILES += ttl_add.c +#CFILES += ttl_nand_test.c +#CFILES += ttl_and_test.c +#CFILES += ttl_or_test.c +#CFILES += ttl_nor_test.c +#CFILES += ttl_xor_test.c +#CFILES += ttl_add_test.c +#CFILES += add.c +#CFILES += jk_gate.c +#CFILES += jk_gate2.c +#CFILES += ttl_nand_delay.c +#CFILES += ttl_nand_gate.c +#CFILES += ttl_nand_gate2.c +#CFILES += rs_gate.c +#CFILES += add_gate.c +#CFILES += adc_gate.c CFILES += ../scf_eda_pack.c CFILES += ../pack/scf_pack.c -CFLAGS += -g +CFILES += ../ses_layout_function.c +CFILES += ../ses_graph.c +CFILES += ../ses_path.c +CFILES += ../ses_step_topo.c +CFILES += ../ses_step_draw.c + +CFLAGS += -g -D_GNU_SOURCE CFLAGS += -I../ CFLAGS += -I../pack diff --git a/cpk/add_gate.c b/cpk/add_gate.c deleted file mode 100644 index 466051d..0000000 --- a/cpk/add_gate.c +++ /dev/null @@ -1,80 +0,0 @@ -#include -#include -#include -#include"ses_core.h" - -int main(int argc, char* argv[]) -{ - ScfEcomponent* B; - ScfEcomponent* R0; - ScfEcomponent* R1; - - ScfEcomponent* NAND0; - ScfEcomponent* NOR0; - ScfEcomponent* NOR1; - ScfEcomponent* NOT0; - - ScfEfunction* f; - ScfEboard* b; - - b = scf_eboard__alloc(); - f = scf_efunction__alloc("add_gate"); - - EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); - EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); - EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); - - B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; - B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; - - EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); - EDA_INST_ADD_COMPONENT(f, NOT0, SCF_EDA_NOT); - EDA_INST_ADD_COMPONENT(f, NOR0, SCF_EDA_NOR); - EDA_INST_ADD_COMPONENT(f, NOR1, SCF_EDA_NOR); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NAND0, SCF_EDA_NAND_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NAND0, SCF_EDA_NAND_NEG); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOR0, SCF_EDA_NOR_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOR0, SCF_EDA_NOR_NEG); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOR1, SCF_EDA_NOR_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOR1, SCF_EDA_NOR_NEG); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOT0, SCF_EDA_NOT_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOT0, SCF_EDA_NOT_NEG); - - EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NOT0, SCF_EDA_NOT_IN); - - EDA_PIN_ADD_PIN(NOT0, SCF_EDA_NOT_OUT, NOR1, SCF_EDA_NOR_IN0); - EDA_PIN_ADD_PIN(NOR0, SCF_EDA_NOR_OUT, NOR1, SCF_EDA_NOR_IN1); - - EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NOR0, SCF_EDA_NOR_IN0); - EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN1, NOR0, SCF_EDA_NOR_IN1); - - EDA_PIN_ADD_PIN(R0, 0, NAND0, SCF_EDA_NAND_IN0); - EDA_PIN_ADD_PIN(R1, 0, NAND0, SCF_EDA_NAND_IN1); - - R0->pins[1]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; - R1->pins[1]->flags = SCF_EDA_PIN_IN; - - NOR1->pins[SCF_EDA_NOR_OUT]->flags = SCF_EDA_PIN_OUT; - NOT0->pins[SCF_EDA_NOT_OUT]->flags |= SCF_EDA_PIN_CF; - - scf_eboard__add_function(b, f); - - long len = 0; - uint8_t* buf = NULL; - - ScfEboard_pack(b, &buf, &len); - ScfEboard_free(b); - b = NULL; - - FILE* fp = fopen("./add_gate.cpk", "wb"); - if (!fp) - return -EINVAL; - - fwrite(buf, len, 1, fp); - fclose(fp); - return 0; -} diff --git a/cpk/and_gate.c b/cpk/and_gate.c deleted file mode 100644 index 26ddfc9..0000000 --- a/cpk/and_gate.c +++ /dev/null @@ -1,63 +0,0 @@ -#include -#include -#include -#include"ses_core.h" - -int main(int argc, char* argv[]) -{ - ScfEcomponent* B; - - ScfEcomponent* NAND0; - ScfEcomponent* NOT0; - ScfEcomponent* R0; - ScfEcomponent* R1; - - ScfEfunction* f; - ScfEboard* b; - - b = scf_eboard__alloc(); - f = scf_efunction__alloc("and_gate"); - - EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); - EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); - EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); - - B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; - B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; - - EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); - EDA_INST_ADD_COMPONENT(f, NOT0, SCF_EDA_NOT); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NAND0, SCF_EDA_NAND_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NAND0, SCF_EDA_NAND_NEG); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOT0, SCF_EDA_NOT_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOT0, SCF_EDA_NOT_NEG); - - EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NOT0, SCF_EDA_NOT_IN); - - EDA_PIN_ADD_PIN(R0, 0, NAND0, SCF_EDA_NAND_IN0); - EDA_PIN_ADD_PIN(R1, 0, NAND0, SCF_EDA_NAND_IN1); - - R0->pins[1]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; - R1->pins[1]->flags = SCF_EDA_PIN_IN; - - NOT0->pins[SCF_EDA_NOT_OUT]->flags = SCF_EDA_PIN_OUT; - - scf_eboard__add_function(b, f); - - uint8_t* buf = NULL; - long len = 0; - - ScfEboard_pack(b, &buf, &len); - ScfEboard_free(b); - b = NULL; - - FILE* fp = fopen("./and_gate.cpk", "wb"); - if (!fp) - return -EINVAL; - - fwrite(buf, len, 1, fp); - fclose(fp); - return 0; -} diff --git a/cpk/nand.c b/cpk/nand.c deleted file mode 100644 index acbbf0e..0000000 --- a/cpk/nand.c +++ /dev/null @@ -1,78 +0,0 @@ -#include -#include -#include -#include"ses_core.h" - -int main(int argc, char* argv[]) -{ - ScfEcomponent* c; - ScfEline* el; - ScfEpin* p; - - ScfEcomponent* R0; - ScfEcomponent* T0; - ScfEcomponent* T1; - - ScfEfunction* f; - - f = scf_efunction__alloc("nand.cpk"); - - EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); - EDA_INST_ADD_COMPONENT(f, T0, SCF_EDA_NPN); - EDA_INST_ADD_COMPONENT(f, T1, SCF_EDA_NPN); - - EDA_PIN_ADD_PIN(R0, 0, T0, SCF_EDA_NPN_C); - EDA_PIN_ADD_PIN(T0, SCF_EDA_NPN_E, T1, SCF_EDA_NPN_C); - - R0->pins[1]->flags = SCF_EDA_PIN_POS; - T1->pins[SCF_EDA_NPN_E]->flags = SCF_EDA_PIN_NEG; - - T0->pins[SCF_EDA_NPN_B]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; - T1->pins[SCF_EDA_NPN_B]->flags = SCF_EDA_PIN_IN; - R0->pins[0]->flags = SCF_EDA_PIN_OUT; - - R0->pins[1]->ic_lid = SCF_EDA_NAND_POS; - T1->pins[SCF_EDA_NPN_E]->ic_lid = SCF_EDA_NAND_NEG; - - T0->pins[SCF_EDA_NPN_B]->ic_lid = SCF_EDA_NAND_IN0; - T1->pins[SCF_EDA_NPN_B]->ic_lid = SCF_EDA_NAND_IN1; - R0->pins[0]->ic_lid = SCF_EDA_NAND_OUT; - - int ret = scf_pins_same_line(f); - if (ret < 0) - return ret; - - long len = 0; - uint8_t* buf = NULL; - - scf_logi("f->n_components: %ld\n", f->n_components); - - long i; - long j; - long k; - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - for (j = 0; j + 1 < el->n_pins; j += 2) { - - c = f->components[el->pins[j]]; - p = c->pins [el->pins[j + 1]]; - - scf_logi("e%ld->flags: %#lx, c%ldp%ld\n", el->id, el->flags, c->id, p->id); - } - printf("\n"); - } - - ScfEfunction_pack(f, &buf, &len); - ScfEfunction_free(f); - f = NULL; - - FILE* fp = fopen("./nand.cpk", "wb"); - if (!fp) - return -EINVAL; - - fwrite(buf, len, 1, fp); - fclose(fp); - return 0; -} diff --git a/cpk/nand.cpk b/cpk/nand.cpk index edf35d3bca3b1947610f6124f1b8f70f1e765c47..cd0bf01d4a3323b24afa32a9cbbd34e60ae701a2 100644 GIT binary patch literal 410 zcma)2F$w}f42+OsiY262@Jb77A7FJ~Ikgjx`-MJB@JGJD$t_AauP_T?cPE*dWIqn$ z<#3*^QUpBWfWpOP87k_+wEUmnX7^{G5bemPI9ek$n{F9qrD_!bRW_-uT|uF663}bQ zKeNZFZ`f)^sG%rxiRxc5$Zoxp1`t;MmFj3(k;oLBGi{5o#N6K~;9k?#oW<yrP)J*r~*{Y=wNYa=NP1p9N78NIwK7%;- zJm<|hM2S^0a_DAQma1}bK~mP9M5cLc>3wWHisGE)Svr diff --git a/cpk/nor.cpk b/cpk/nor.cpk index 09edb244c27fc00c059061b8d9f442d008a7a0a9..b62b0f29bf84e8fb19230983313f7fcd69b649c9 100644 GIT binary patch delta 136 zcmeBT?q{ALA;loTfDTv~SOgeY7$zEuP4tjvV&Ir~QFLOJG9LpY1H&hApkhA014#}O zH;PU?Ai&5l@q!o^3kL%O2MY@W1LMSxlGxO-O*Uo}n(V?TFgch}kb{ATg9E6ZVR9Cu H0wV(e{7o2L delta 142 zcmeBY?qZ%GAtk_o0azGV1Q=LYCTWVAD=_M z14zLEHf{zE2?ibp4jvW;o{1O5xEWZ0IyhKZ7#JBQew4(fW3myW@MJee{>fpC0+Z8$ IbUC9q0PT<&4FCWD diff --git a/cpk/not.cpk b/cpk/not.cpk index cdaa1010bcf5e4281f4f008a20085147c3b79008..8b934a5fbb4a8e7fd0ffee95d0cb5ace59034bab 100644 GIT binary patch literal 266 zcmZWk!41Md3^S4+enipz;CT};0I$vh&q~locPL{au@Mtsio~6YBb^dEPIC2nn~#@i zgw{YvR3NYg!2&;9eyua_&!JOz@C53V-=Ue)(#!57Q9DCR#jwft9q`(l&wQMRrvGIH XB2^ntd39;Ee}vB|KZHehcuS8rH~0$7 literal 262 zcmZXPyA8uI3`8%$6;}|1I=j>a8NiixNg2R$;T@d4vQZ`oWx$329Sef@2!8Tf_vdSS zLubGw$_#@DCXj=F8t$KO=@4fasKp@x?%UDR))3H3RwUE diff --git a/cpk/or_gate.c b/cpk/or_gate.c deleted file mode 100644 index 36b42e3..0000000 --- a/cpk/or_gate.c +++ /dev/null @@ -1,63 +0,0 @@ -#include -#include -#include -#include"ses_core.h" - -int main(int argc, char* argv[]) -{ - ScfEcomponent* B; - - ScfEcomponent* NOR0; - ScfEcomponent* NOT0; - ScfEcomponent* R0; - ScfEcomponent* R1; - - ScfEfunction* f; - ScfEboard* b; - - b = scf_eboard__alloc(); - f = scf_efunction__alloc("or_gate"); - - EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); - EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); - EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); - - B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; - B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; - - EDA_INST_ADD_COMPONENT(f, NOR0, SCF_EDA_NOR); - EDA_INST_ADD_COMPONENT(f, NOT0, SCF_EDA_NOT); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOR0, SCF_EDA_NOR_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOR0, SCF_EDA_NOR_NEG); - - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOT0, SCF_EDA_NOT_POS); - EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOT0, SCF_EDA_NOT_NEG); - - EDA_PIN_ADD_PIN(NOR0, SCF_EDA_NOR_OUT, NOT0, SCF_EDA_NOT_IN); - - EDA_PIN_ADD_PIN(R0, 0, NOR0, SCF_EDA_NOR_IN0); - EDA_PIN_ADD_PIN(R1, 0, NOR0, SCF_EDA_NOR_IN1); - - R0->pins[1]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; - R1->pins[1]->flags = SCF_EDA_PIN_IN; - - NOT0->pins[SCF_EDA_NOT_OUT]->flags = SCF_EDA_PIN_OUT; - - scf_eboard__add_function(b, f); - - long len = 0; - uint8_t* buf = NULL; - - ScfEboard_pack(b, &buf, &len); - ScfEboard_free(b); - b = NULL; - - FILE* fp = fopen("./or_gate.cpk", "wb"); - if (!fp) - return -EINVAL; - - fwrite(buf, len, 1, fp); - fclose(fp); - return 0; -} diff --git a/cpk/ttl_add.c b/cpk/ttl_add.c new file mode 100644 index 0000000..f4ef572 --- /dev/null +++ b/cpk/ttl_add.c @@ -0,0 +1,100 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* NAND0; + ScfEcomponent* NAND1; + ScfEcomponent* NAND2; + ScfEcomponent* NAND3; + ScfEcomponent* NAND4; + ScfEcomponent* NAND5; + ScfEcomponent* NAND6; + + ScfEfunction* f = scf_efunction__alloc("ttl_add"); +/* +x ADD y = (x | y) & ~(x & y) + = ~(~x & ~y) & (x NAND y) + = ~((~x NAND ~y) NAND (x NAND y)) +*/ + EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND1, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND2, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND3, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND4, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND5, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND6, SCF_EDA_NAND); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND1, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND2, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND3, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND4, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND5, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND6, SCF_EDA_NAND_POS); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND1, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND2, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND3, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND4, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND5, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND6, SCF_EDA_NAND_NEG); + + // a = ~x NAND ~y + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND0, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND1, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN1); + + // b = x NAND y + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND3, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND3, SCF_EDA_NAND_IN1); + + // res = ~(a NAND b) + EDA_PIN_ADD_PIN(NAND2, SCF_EDA_NAND_OUT, NAND4, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND3, SCF_EDA_NAND_OUT, NAND4, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND4, SCF_EDA_NAND_OUT, NAND5, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND4, SCF_EDA_NAND_OUT, NAND5, SCF_EDA_NAND_IN1); + + // cf = ~b = x & y + EDA_PIN_ADD_PIN(NAND3, SCF_EDA_NAND_OUT, NAND6, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND3, SCF_EDA_NAND_OUT, NAND6, SCF_EDA_NAND_IN1); + + NAND0->pins[SCF_EDA_NAND_POS]->flags = SCF_EDA_PIN_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->flags = SCF_EDA_PIN_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN; + NAND5->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + NAND6->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_CF; + + NAND0->pins[SCF_EDA_NAND_POS]->ic_lid = SCF_EDA_ADD_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->ic_lid = SCF_EDA_ADD_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_ADD_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_ADD_IN1; + NAND5->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_ADD_OUT; + NAND6->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_ADD_CF; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_add.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_add.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_add.cpk b/cpk/ttl_add.cpk new file mode 100644 index 0000000000000000000000000000000000000000..e6bbc02d589e7017532b24ae7ba3ee885b059dd6 GIT binary patch literal 1959 zcmZvdzfToG5Xa~4CSi+(O!SH+xsWSf%qu96>PfK>6B}b;Y$R#|2GsZ?f{LNFu(IMG zFfp;RlFG_LX>3Uhm5rq(1(n6q@9gc}yW`zLmUry;&3->Kx3lHm-m{JS+uKx7NjVXf zOH76=37#CDCu5v_+d2AvVPoO1zrjQa5fjT2vti4^IXlKb8vQuCdApJ?&j+<3voa@S zt-+_3Z1cIw{I$ft&4SQk89zq1h@;-yUu;xD18B^kql#O8UYVz4@@=?+=`BQuXT^le z;9w#dXTM(s8@IBC4mgG|wN(cjQB^|)c8h_W)nlB!c^PCgng0`+7*uR*Cs^F_N~01U zg2@g$s<`F*%&(^%DnlM_e*`R}SYVpMI^8^vWqPn0RgHzb8j@~u57#3Uva1fQfm@bd zw_t)>Rf%zAbZVzDh62-K(!;b9v{spr)hVX6*TKk9(v-^fFdc41Rn263UaRs&5bZaw zl~!`9P;tXgNnK8{1v#-BDH7V?6w>L_^GL1-sZrHPuBQgO4k% zD|0A?Wm~Wv;1;O*w2#M1mDXu2i$B^pf^dlVKAb5ZTc8TXpjOB?m$*`VC{H!(hLq&S ziCM#Pf%^svK&|F#8H<8nJV?P(vJBV^v9k{c!B-7OrAbj*sZMZ-$6U>^#UV421=! aQ8ku9V&IcC4eP0z)ZVEwBL9H>A^!*UIRM%K literal 0 HcmV?d00001 diff --git a/cpk/ttl_add_test.c b/cpk/ttl_add_test.c new file mode 100644 index 0000000..318bd0d --- /dev/null +++ b/cpk/ttl_add_test.c @@ -0,0 +1,52 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* ADD; + ScfEcomponent* R0; + ScfEcomponent* R1; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("add_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, ADD, SCF_EDA_ADD); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, ADD, SCF_EDA_ADD_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, ADD, SCF_EDA_ADD_NEG); + EDA_PIN_ADD_PIN(R0, 1, ADD, SCF_EDA_ADD_OUT); + EDA_PIN_ADD_PIN(R1, 1, ADD, SCF_EDA_ADD_CF); + EDA_PIN_ADD_PIN(R0, 0, B, SCF_EDA_Battery_NEG); + EDA_PIN_ADD_PIN(R1, 0, B, SCF_EDA_Battery_NEG); + + ADD->pins[SCF_EDA_ADD_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + ADD->pins[SCF_EDA_ADD_IN1]->flags = SCF_EDA_PIN_IN; + ADD->pins[SCF_EDA_ADD_OUT]->flags = SCF_EDA_PIN_OUT; + ADD->pins[SCF_EDA_ADD_CF]->flags = SCF_EDA_PIN_CF; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./add_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_and.c b/cpk/ttl_and.c new file mode 100644 index 0000000..8915b2c --- /dev/null +++ b/cpk/ttl_and.c @@ -0,0 +1,56 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* NAND0; + ScfEcomponent* NAND1; + + ScfEfunction* f = scf_efunction__alloc("ttl_and"); + + EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND1, SCF_EDA_NAND); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND1, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND1, SCF_EDA_NAND_NEG); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NAND1, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND1, SCF_EDA_NAND_IN1); + + NAND0->pins[SCF_EDA_NAND_POS]->flags = SCF_EDA_PIN_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->flags = SCF_EDA_PIN_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND0->pins[SCF_EDA_NAND_IN1]->flags = SCF_EDA_PIN_IN; + NAND1->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + NAND0->pins[SCF_EDA_NAND_POS]->ic_lid = SCF_EDA_AND_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->ic_lid = SCF_EDA_AND_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_AND_IN0; + NAND0->pins[SCF_EDA_NAND_IN1]->ic_lid = SCF_EDA_AND_IN1; + NAND1->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_AND_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_and.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_and.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_and.cpk b/cpk/ttl_and.cpk new file mode 100644 index 0000000000000000000000000000000000000000..4ddd4b3764229442de5f927d18498a62e3d87a9c GIT binary patch literal 628 zcmZuuyH3O~5F964tb~Ou;o>4t2ozK_T$#cJ5)}<49Xg2;A&R5qAMO*7sOb0rDt?2C zKcJwFn01oN@vx#z;vLVW+A3WZfCB^)RD`cJ zsw-E!J!oEKj6&OOa_R;o92lhjNM9u3DO*(M8WbeYP2JfQiAxOLO%D5EWJBZk}VPUNA5+P zQO|2s;Qblh=m=doFrB%!`en(aZe?vVJ0S>YMY5Jri#&Weyex zlouYETh3qz!T?_3Ep}zGejmUXgCQ7rAPppPNHUqZ7(HC1GEwm}{umFZ1j2Ga +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* AND; + ScfEcomponent* R; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("and_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, AND, SCF_EDA_AND); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, AND, SCF_EDA_AND_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, AND, SCF_EDA_AND_NEG); + EDA_PIN_ADD_PIN(R, 1, AND, SCF_EDA_AND_OUT); + EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + AND->pins[SCF_EDA_AND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + AND->pins[SCF_EDA_AND_IN1]->flags = SCF_EDA_PIN_IN; + AND->pins[SCF_EDA_AND_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./and_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nand.c b/cpk/ttl_nand.c new file mode 100644 index 0000000..a120be0 --- /dev/null +++ b/cpk/ttl_nand.c @@ -0,0 +1,108 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* R0; + ScfEcomponent* R1; + ScfEcomponent* R2; + ScfEcomponent* R3; + + ScfEcomponent* D4; + ScfEcomponent* D5; + ScfEcomponent* D6; + ScfEcomponent* D7; + ScfEcomponent* T8; + ScfEcomponent* T9; + ScfEcomponent* T10; + + ScfEcomponent* C8; + ScfEcomponent* C9; + + ScfEfunction* f = scf_efunction__alloc("ttl_nand.cpk"); + + EDA_INST_ADD_COMPONENT(f, R0, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R2, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R3, SCF_EDA_Resistor); + + EDA_INST_ADD_COMPONENT(f, D4, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D5, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D6, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D7, SCF_EDA_Diode); + + EDA_INST_ADD_COMPONENT(f, T8, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T9, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T10, SCF_EDA_NPN); + + EDA_PIN_ADD_PIN(R0, 1, R1, 1); + EDA_PIN_ADD_PIN(R0, 1, R2, 1); + + EDA_PIN_ADD_PIN(R0, 0, D4, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R0, 0, D5, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R0, 0, D6, SCF_EDA_Diode_POS); + + EDA_PIN_ADD_PIN(D6, SCF_EDA_Diode_NEG, T8, SCF_EDA_NPN_B); + EDA_PIN_ADD_PIN(R1, 0, T8, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(R3, 1, T8, SCF_EDA_NPN_E); + EDA_PIN_ADD_PIN(R3, 0, T10, SCF_EDA_NPN_E); + + EDA_PIN_ADD_PIN(R2, 0, T9, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(T9, SCF_EDA_NPN_E, D7, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(T10, SCF_EDA_NPN_C, D7, SCF_EDA_Diode_NEG); + EDA_PIN_ADD_PIN(T10, SCF_EDA_NPN_B, R3, 1); + EDA_PIN_ADD_PIN(T9, SCF_EDA_NPN_B, R1, 0); +#if 0 + EDA_INST_ADD_COMPONENT(f, C8, SCF_EDA_Capacitor); + EDA_INST_ADD_COMPONENT(f, C9, SCF_EDA_Capacitor); + + EDA_PIN_ADD_PIN(T8, SCF_EDA_NPN_B, C8, 1); + EDA_PIN_ADD_PIN(T8, SCF_EDA_NPN_E, C8, 0); + EDA_PIN_ADD_PIN(T9, SCF_EDA_NPN_B, C9, 1); + EDA_PIN_ADD_PIN(T9, SCF_EDA_NPN_E, C9, 0); + + C8->uf = 1e-6; + C9->uf = 1e-6; +#endif + R0->r = 4000; + R1->r = 1600; + R2->r = 130; + R3->r = 10 * 1000; + + R0->pins[1]->flags = SCF_EDA_PIN_POS; + R3->pins[0]->flags = SCF_EDA_PIN_NEG; + + R0->pins[1]->ic_lid = SCF_EDA_NAND_POS; + R3->pins[0]->ic_lid = SCF_EDA_NAND_NEG; + + D4->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + D5->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN; + D7->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_OUT; + + D4->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_IN0; + D5->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_IN1; + D7->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_nand.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_nand.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nand.cpk b/cpk/ttl_nand.cpk new file mode 100644 index 0000000000000000000000000000000000000000..7d2b4e54e125c67e5226fc124d135f4143471914 GIT binary patch literal 1807 zcmZ`)J#Q015S{Z)v53>Lf|FQFCv?RLU11?5qQS+Hf3*m-k*AypoAHyrh=k zwa}ooB+`#%dYnD_?dQ|+!!3~nKd7kps!nm!qhx?>j}66N@_cqO!>7u0eCH3JD2X(P zuN>G`XsVl}+1Zlz%P8`I0ASsWx=fROB#RRUzcJ~KJgyX1<8nEf?*&=fqZHW4;x@2c zpf0oIv%N@z==Q5Envo`x$~A)%P_j(-ZbZ-8UC5_rS%I9jkzz&71#BKuMl4Kw|BXB} zt$m#GkuN~w-85%XL>#;$0;9Jbd(%#mNabsSHtiu${U*k6vM}_CWmAx*$P^i6D=a_L z++3R^)3~`>tZ@vObqYvpuNy@mMX1D8QqhT(R4&{&?=lH%EQ7P_EU+u?N=cH^JJ&cb z{tC(4Tb9av)Sji$ud+dzU~5cZ=jwnuim1V_7NMVQTdKglM>65R$q?LUQ$bdys|C;% z{WaiFj;LX*iGsAw_;nkkd4BqQhRf|Rl5pwQSn+pAs_(EG zsh3w$kF~#Z4OJc`)o3I5NqJW!b!~Do>YFJFVpUPnUz5~OQZwYfBI(p~H&}vQ2S5y5 z!a88<#xm`MKSe$Y-F}0n4*MhN_qSgrR(foxiFjyIe+;t1WsTRyp?r3=HI9Xl z$jA_#;Ji|vcj1Fb7F0_`y$Axf$1rJoybv4{cylBUHOEdBt<^hbHc8?YtD;3Y4VXE2 zf^>i@9G-%omj&9MZ^L+B3W^x*oQXDtHjS39wcKd%S&B7L#+-&PLZ&=r0=_|pB^I=* zv|@Vm5q5PxLJZ92w3rYS2N+Ldkpg)ZT9sNOq|w>|g>s9BGU8A-oEC=$lN!lF8_dC< zhT*Li;_8oaKMg8due26r%AJ=&+TC^#D5 k3p>$pZzE|uw5ySLEg=eDoz*f)j_4Q4nv(-m-1ATR4|96u +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* R1; + ScfEcomponent* R2; + ScfEcomponent* R3; + ScfEcomponent* R4; + + ScfEcomponent* D10; + ScfEcomponent* D11; + ScfEcomponent* D12; + ScfEcomponent* T2; + ScfEcomponent* D3; + ScfEcomponent* T4; + ScfEcomponent* T5; + ScfEcomponent* C5; + + ScfEfunction* f = scf_efunction__alloc("ttl_nand_delay.cpk"); + + EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R2, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R3, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R4, SCF_EDA_Resistor); + + EDA_INST_ADD_COMPONENT(f, D10, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D11, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D12, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D3, SCF_EDA_Diode); + + EDA_INST_ADD_COMPONENT(f, T2, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T4, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T5, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, C5, SCF_EDA_Capacitor); + + EDA_PIN_ADD_PIN(R1, 1, R2, 1); + EDA_PIN_ADD_PIN(R1, 1, R4, 1); + + EDA_PIN_ADD_PIN(R1, 0, D10, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R1, 0, D11, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R1, 0, D12, SCF_EDA_Diode_POS); + + EDA_PIN_ADD_PIN(D12, SCF_EDA_Diode_NEG, T2, SCF_EDA_NPN_B); + EDA_PIN_ADD_PIN(R2, 0, T2, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(R3, 1, T2, SCF_EDA_NPN_E); + EDA_PIN_ADD_PIN(R3, 0, T5, SCF_EDA_NPN_E); + + EDA_PIN_ADD_PIN(R4, 0, T4, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(T4, SCF_EDA_NPN_E, D3, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_C, D3, SCF_EDA_Diode_NEG); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_B, R3, 1); + EDA_PIN_ADD_PIN(T4, SCF_EDA_NPN_B, R2, 0); + + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_B, C5, 1); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_E, C5, 0); + + R1->r = 4000; + R2->r = 1600; + R3->r = 10 * 1000; + R4->r = 130; + C5->uf = 2e-6; + + R1->pins[1]->flags = SCF_EDA_PIN_POS; + R3->pins[0]->flags = SCF_EDA_PIN_NEG; + + R1->pins[1]->ic_lid = SCF_EDA_NAND_POS; + R3->pins[0]->ic_lid = SCF_EDA_NAND_NEG; + + D10->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + D11->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN; + D3 ->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_OUT; + + D10->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_IN0; + D11->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_IN1; + D3 ->pins[SCF_EDA_Diode_NEG]->ic_lid = SCF_EDA_NAND_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_nand_delay.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_nand_delay.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nand_gate.c b/cpk/ttl_nand_gate.c new file mode 100644 index 0000000..d21b936 --- /dev/null +++ b/cpk/ttl_nand_gate.c @@ -0,0 +1,53 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + + ScfEcomponent* NAND; + ScfEcomponent* R; + ScfEfunction* f; + ScfEboard* b; + + b = scf_eboard__alloc(); + f = scf_efunction__alloc("ttl_nand_gate"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, NAND, SCF_EDA_NAND); + + NAND->model = SCF_EDA_NAND_TTL; + + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NAND, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NAND, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(R, 1, NAND, SCF_EDA_NAND_OUT); + EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + NAND->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND->pins[SCF_EDA_NAND_IN1]->flags = SCF_EDA_PIN_IN; + + NAND->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./ttl_nand_gate.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nand_gate2.c b/cpk/ttl_nand_gate2.c new file mode 100644 index 0000000..8c13a20 --- /dev/null +++ b/cpk/ttl_nand_gate2.c @@ -0,0 +1,101 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* R1; + ScfEcomponent* R2; + ScfEcomponent* R3; + ScfEcomponent* R4; + + ScfEcomponent* D10; + ScfEcomponent* D11; + ScfEcomponent* D12; + ScfEcomponent* T2; + ScfEcomponent* D3; + ScfEcomponent* T4; + ScfEcomponent* T5; + ScfEcomponent* C5; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("ttl_nand.cpk"); + ScfEcomponent* B; + ScfEcomponent* RL; + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, RL, SCF_EDA_Resistor); + + EDA_INST_ADD_COMPONENT(f, R1, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R2, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R3, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, R4, SCF_EDA_Resistor); + + EDA_INST_ADD_COMPONENT(f, D10, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D11, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D12, SCF_EDA_Diode); + EDA_INST_ADD_COMPONENT(f, D3, SCF_EDA_Diode); + + EDA_INST_ADD_COMPONENT(f, T2, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T4, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, T5, SCF_EDA_NPN); + EDA_INST_ADD_COMPONENT(f, C5, SCF_EDA_Capacitor); + + EDA_PIN_ADD_PIN(R1, 1, R2, 1); + EDA_PIN_ADD_PIN(R1, 1, R4, 1); + + EDA_PIN_ADD_PIN(R1, 0, D10, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R1, 0, D11, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(R1, 0, D12, SCF_EDA_Diode_POS); + + EDA_PIN_ADD_PIN(D12, SCF_EDA_Diode_NEG, T2, SCF_EDA_NPN_B); + EDA_PIN_ADD_PIN(R2, 0, T2, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(R3, 1, T2, SCF_EDA_NPN_E); + EDA_PIN_ADD_PIN(R3, 0, T5, SCF_EDA_NPN_E); + + EDA_PIN_ADD_PIN(R4, 0, T4, SCF_EDA_NPN_C); + EDA_PIN_ADD_PIN(T4, SCF_EDA_NPN_E, D3, SCF_EDA_Diode_POS); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_C, D3, SCF_EDA_Diode_NEG); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_B, R3, 1); + EDA_PIN_ADD_PIN(T4, SCF_EDA_NPN_B, R2, 0); + + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_B, C5, 1); + EDA_PIN_ADD_PIN(T5, SCF_EDA_NPN_E, C5, 0); + + R1->r = 4000; + R2->r = 1600; + R3->r = 10 * 1000; + R4->r = 130; + C5->uf = 5e-6; + + EDA_PIN_ADD_PIN(R1, 1, B, SCF_EDA_Battery_POS); + EDA_PIN_ADD_PIN(R3, 0, B, SCF_EDA_Battery_NEG); + + EDA_PIN_ADD_PIN(RL, 1, D3, SCF_EDA_Diode_NEG); + EDA_PIN_ADD_PIN(RL, 0, B, SCF_EDA_Battery_NEG); + + D10->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + D11->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_IN; + D3 ->pins[SCF_EDA_Diode_NEG]->flags = SCF_EDA_PIN_OUT; + + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./ttl_nand_gate2.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nand_test.c b/cpk/ttl_nand_test.c new file mode 100644 index 0000000..a0f1517 --- /dev/null +++ b/cpk/ttl_nand_test.c @@ -0,0 +1,47 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* NAND; + ScfEcomponent* R; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("nor_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); +// EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, NAND, SCF_EDA_NAND); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NAND, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NAND, SCF_EDA_NAND_NEG); +// EDA_PIN_ADD_PIN(R, 1, NAND, SCF_EDA_NAND_OUT); +// EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + NAND->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND->pins[SCF_EDA_NAND_IN1]->flags = SCF_EDA_PIN_IN; + NAND->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./nand_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nor.c b/cpk/ttl_nor.c new file mode 100644 index 0000000..bb97522 --- /dev/null +++ b/cpk/ttl_nor.c @@ -0,0 +1,57 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* NAND0; + ScfEcomponent* NAND1; + + ScfEfunction* f = scf_efunction__alloc("ttl_nor"); + + EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND1, SCF_EDA_NAND); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND1, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND1, SCF_EDA_NAND_NEG); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND0, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND1, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NAND1, SCF_EDA_NAND_OUT); + + NAND0->pins[SCF_EDA_NAND_POS]->flags = SCF_EDA_PIN_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->flags = SCF_EDA_PIN_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN; + NAND0->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + NAND0->pins[SCF_EDA_NAND_POS]->ic_lid = SCF_EDA_NOR_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->ic_lid = SCF_EDA_NOR_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_NOR_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_NOR_IN1; + NAND0->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_NOR_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_nor.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_nor.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_nor.cpk b/cpk/ttl_nor.cpk new file mode 100644 index 0000000000000000000000000000000000000000..111b68e3c91fb0fe485850d9394ef0dee7f996a7 GIT binary patch literal 593 zcmZXRJxT;Y5QVE}Dk!jA3fyFqVGdy8h7&X@7>J^Vn< +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* NOR; + ScfEcomponent* R; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("nor_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, NOR, SCF_EDA_NOR); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, NOR, SCF_EDA_NOR_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, NOR, SCF_EDA_NOR_NEG); + EDA_PIN_ADD_PIN(R, 1, NOR, SCF_EDA_NOR_OUT); + EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + NOR->pins[SCF_EDA_NOR_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NOR->pins[SCF_EDA_NOR_IN1]->flags = SCF_EDA_PIN_IN; + NOR->pins[SCF_EDA_NOR_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./nor_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_or.c b/cpk/ttl_or.c new file mode 100644 index 0000000..9820919 --- /dev/null +++ b/cpk/ttl_or.c @@ -0,0 +1,63 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* NAND0; + ScfEcomponent* NAND1; + ScfEcomponent* NAND2; +// x | y = ~(~x & ~y) = ~x NAND ~y + ScfEfunction* f = scf_efunction__alloc("ttl_or"); + + EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND1, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND2, SCF_EDA_NAND); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND1, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND2, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND1, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND2, SCF_EDA_NAND_NEG); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND0, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND1, SCF_EDA_NAND_IN1); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN1); + + NAND0->pins[SCF_EDA_NAND_POS]->flags = SCF_EDA_PIN_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->flags = SCF_EDA_PIN_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN; + NAND2->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + NAND0->pins[SCF_EDA_NAND_POS]->ic_lid = SCF_EDA_OR_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->ic_lid = SCF_EDA_OR_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_OR_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_OR_IN1; + NAND2->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_OR_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_or.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_or.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_or.cpk b/cpk/ttl_or.cpk new file mode 100644 index 0000000000000000000000000000000000000000..b380fd510e4aaa942d09dc93a98cdf56c9f3f657 GIT binary patch literal 889 zcmZvau}T9$5Qb;(rkG-t1+Tb3IMQojQl?lzu(7hV)520vB;Y$};|mCag{3}#RbC;A zisCa^SfvR5Gq-m!noYP1nQv$Qe`dO)(ec5_8F}haK}5a4BzVuyEZ=*-JX$}jrtvW& zazsoV0<$oFwA?HYlNuXzj1rRJs*uO~7xeX}P~36Dn(~O^BbqmzreIuapg<)MDHotr z?mlifa`W4eR86Zp&Bba73a$Q}fYMJBagnu-U_}Uz-_+(yq8dZ&;n{oisyVa#;lrTk zEPmrIzMf%;#V@2v1#ep_Z~;fYSfEnDtt{?me=J34otQXLQ*iXp)YYpg8N1e$EHTwm zjVW|hC@i-2^vP1KWZGLZC8)_^soZy`a+L}akP4sX%<`1!+->)Pn1MRT6rpr%|8y~4 z%t@%cL6B|H)Ud7_j^h%eLF>z_Iy~qgs`@o30T+E3uHt5ig|w|n`=xOobZFRW;sRNs z%^;?EDG&s*wV?$|2{xM8`l%Jj6@i0zwdFlC@)>5nV?8XxN?1oO#n5?RNXV7$XH1>c LWJK{g-|f>6RC99C literal 0 HcmV?d00001 diff --git a/cpk/ttl_or_test.c b/cpk/ttl_or_test.c new file mode 100644 index 0000000..f806fa7 --- /dev/null +++ b/cpk/ttl_or_test.c @@ -0,0 +1,47 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* OR; + ScfEcomponent* R; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("or_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, OR, SCF_EDA_OR); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, OR, SCF_EDA_OR_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, OR, SCF_EDA_OR_NEG); + EDA_PIN_ADD_PIN(R, 1, OR, SCF_EDA_OR_OUT); + EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + OR->pins[SCF_EDA_OR_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + OR->pins[SCF_EDA_OR_IN1]->flags = SCF_EDA_PIN_IN; + OR->pins[SCF_EDA_OR_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./or_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_xor.c b/cpk/ttl_xor.c new file mode 100644 index 0000000..2a01e98 --- /dev/null +++ b/cpk/ttl_xor.c @@ -0,0 +1,90 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* NAND0; + ScfEcomponent* NAND1; + ScfEcomponent* NAND2; + ScfEcomponent* NAND3; + ScfEcomponent* NAND4; + ScfEcomponent* NAND5; + + ScfEfunction* f = scf_efunction__alloc("ttl_xor"); +/* +x XOR y = (x | y) & ~(x & y) + = ~(~x & ~y) & (x NAND y) + = ~((~x NAND ~y) NAND (x NAND y)) +*/ + EDA_INST_ADD_COMPONENT(f, NAND0, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND1, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND2, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND3, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND4, SCF_EDA_NAND); + EDA_INST_ADD_COMPONENT(f, NAND5, SCF_EDA_NAND); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND1, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND2, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND3, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND4, SCF_EDA_NAND_POS); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_POS, NAND5, SCF_EDA_NAND_POS); + + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND1, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND2, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND3, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND4, SCF_EDA_NAND_NEG); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_NEG, NAND5, SCF_EDA_NAND_NEG); + + // a = ~x NAND ~y + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND0, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND1, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_OUT, NAND2, SCF_EDA_NAND_IN1); + + // b = x NAND y + EDA_PIN_ADD_PIN(NAND0, SCF_EDA_NAND_IN0, NAND3, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND1, SCF_EDA_NAND_IN0, NAND3, SCF_EDA_NAND_IN1); + + // res = ~(a NAND b) + EDA_PIN_ADD_PIN(NAND2, SCF_EDA_NAND_OUT, NAND4, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND3, SCF_EDA_NAND_OUT, NAND4, SCF_EDA_NAND_IN1); + EDA_PIN_ADD_PIN(NAND4, SCF_EDA_NAND_OUT, NAND5, SCF_EDA_NAND_IN0); + EDA_PIN_ADD_PIN(NAND4, SCF_EDA_NAND_OUT, NAND5, SCF_EDA_NAND_IN1); + + NAND0->pins[SCF_EDA_NAND_POS]->flags = SCF_EDA_PIN_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->flags = SCF_EDA_PIN_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->flags = SCF_EDA_PIN_IN; + NAND5->pins[SCF_EDA_NAND_OUT]->flags = SCF_EDA_PIN_OUT; + + NAND0->pins[SCF_EDA_NAND_POS]->ic_lid = SCF_EDA_XOR_POS; + NAND0->pins[SCF_EDA_NAND_NEG]->ic_lid = SCF_EDA_XOR_NEG; + + NAND0->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_XOR_IN0; + NAND1->pins[SCF_EDA_NAND_IN0]->ic_lid = SCF_EDA_XOR_IN1; + NAND5->pins[SCF_EDA_NAND_OUT]->ic_lid = SCF_EDA_XOR_OUT; + + int ret = ses_layout_function(f, 100); + if (ret < 0) + return ret; + + ses_draw(f, "ttl_xor.png", f->x, f->y, f->w, f->h, 0, -1); + + long len = 0; + uint8_t* buf = NULL; + + ScfEfunction_pack(f, &buf, &len); + ScfEfunction_free(f); + f = NULL; + + FILE* fp = fopen("./ttl_xor.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/cpk/ttl_xor.cpk b/cpk/ttl_xor.cpk new file mode 100644 index 0000000000000000000000000000000000000000..9361bf284bf286480bf2a7fde5cc201c8337f106 GIT binary patch literal 1698 zcmZuxJ&P1U5Urjmu!Fv%zzJqyIVRZP0)zE3H|PVwL=2XTOvFIUggfQnj6~%S@dH;x zE)oumjPwT>h`-=KjQj(J7Z@3=zN+b&o4K9drFTBwR=rnM{i^-_d$%9%KA@5+Du}4s zWbzb9><$moTIP$z+Wh#|#^3lmCvrqgESt=p0}B_7+XhR^{L7;nyfrecCqG*k3c=&5 z1Dn24SiI)0U&d1e4S0=@*Xy*J%<*E25}E+xCp}b3`FS=XclK|v0_A_124j^7md4-= zvdq7|HySUpRvYAa!q!EdK1--ZlqnBbpxvxxK7VJh?JOSFg$fK+>_abDN_oFUp@z^D ziXJMZ{F%j@Sx=Rx2)1{S0CH3oG_A;*KQ|^jc`M5g$ZAoIEY#JL^ouKxE!2e^)m4VU zBPGiq+bg-URh0OWyl&kxrcfX9c*&jD1gg7+4XO!MUC~q>8IkX<)f5Ia$;*UlG=+h& zI(=)PgLbU6lPir%2|u}}of5_ng{>#5PPmrEuPcoL*Bxt=s3;i_wfE}0C>apdq8d?x z>UwNlB709P6o{a@`X&hI>efZ2`uuWASKkP@N#P6By^BlH4qW`x?-f&otRIFgR2IBr zrB^4fjZ5cP6$7$bR3i)Vyz=Q1IeBWKa1cO5--IF5^w3ZrTa*-nQP!HLwainb?d&Qn zr*9N`q-sfCrs^ literal 0 HcmV?d00001 diff --git a/cpk/ttl_xor_test.c b/cpk/ttl_xor_test.c new file mode 100644 index 0000000..06e9d6d --- /dev/null +++ b/cpk/ttl_xor_test.c @@ -0,0 +1,47 @@ +#include +#include +#include +#include"ses_core.h" + +int main(int argc, char* argv[]) +{ + ScfEcomponent* B; + ScfEcomponent* XOR; + ScfEcomponent* R; + + ScfEboard* b = scf_eboard__alloc(); + ScfEfunction* f = scf_efunction__alloc("xor_test"); + + EDA_INST_ADD_COMPONENT(f, B, SCF_EDA_Battery); + EDA_INST_ADD_COMPONENT(f, R, SCF_EDA_Resistor); + EDA_INST_ADD_COMPONENT(f, XOR, SCF_EDA_XOR); + + B->pins[SCF_EDA_Battery_POS]->flags = SCF_EDA_PIN_POS; + B->pins[SCF_EDA_Battery_NEG]->flags = SCF_EDA_PIN_NEG; + + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_POS, XOR, SCF_EDA_XOR_POS); + EDA_PIN_ADD_PIN(B, SCF_EDA_Battery_NEG, XOR, SCF_EDA_XOR_NEG); + EDA_PIN_ADD_PIN(R, 1, XOR, SCF_EDA_XOR_OUT); + EDA_PIN_ADD_PIN(R, 0, B, SCF_EDA_Battery_NEG); + + XOR->pins[SCF_EDA_XOR_IN0]->flags = SCF_EDA_PIN_IN | SCF_EDA_PIN_IN0; + XOR->pins[SCF_EDA_XOR_IN1]->flags = SCF_EDA_PIN_IN; + XOR->pins[SCF_EDA_XOR_OUT]->flags = SCF_EDA_PIN_OUT; + + scf_eboard__add_function(b, f); + + long len = 0; + uint8_t* buf = NULL; + + ScfEboard_pack(b, &buf, &len); + ScfEboard_free(b); + b = NULL; + + FILE* fp = fopen("./xor_test.cpk", "wb"); + if (!fp) + return -EINVAL; + + fwrite(buf, len, 1, fp); + fclose(fp); + return 0; +} diff --git a/examples/add_gate.cpk b/examples/add_gate.cpk deleted file mode 100644 index 89fae783d1643701930a7787f8c69a9f73678b3d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 864 zcma)(F>1s>3`G?XL9oJ6V2UYHxG+nq93Vy5oFo`*_5wM?USLnOwcDH_$JnoF9LzVw zm1o}Q>q}pUahkr)fecP&~qls(AzkJq2$@8RwFqkEc{ z<#Ux#Lkmcl8>>~7_l~wriLSfcPOFw!iovnDQ?b^GjKH+K$IK2bKvJR&(RmFhieV^H z2WNm7mcdBTpo{o3W&4d+#DPHe>@~#gCGueXaeK1*ul{AgddhzPhIs!(JZ*1?W*3Pn gMcdWXv{v`6HN>qYLI^CkM1^iGYNkMHw#M4|4x#T8T>t<8 diff --git a/examples/and.cpk b/examples/and.cpk deleted file mode 100644 index f856f4a6b6b63d2e6ddc587964e3056cdfa596fa..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 747 zcmb7CF$w}f42%#Y;Ic+o@QN$0vh)EKay~`SR{e#3z!zCx>l>_nfiohAM+Ds}>}+Nx zlT}~uHqwZSiAdw7MP-1pcT~hZsfQrn4$s%wZ8V=O^LX2Jt9QFrl0Yw335jz)9NRbg ztdy`>q-%uIv-3X1)vW_@U5d1leisrFqE-m20Pgvv-;qd(= UYLa1zTuDS$^HT*t#Kk*#03l!;KmY&$ diff --git a/examples/and_gate.cpk b/examples/and_gate.cpk deleted file mode 100644 index ee72fe1c59f47b01a76c3d57dd36cc37e0d5e6ab..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 542 zcmZ`$I|>3p41Ge7fMJZ_0k#m?$^%%4oPK#x$F6B-liRz+teZYf+j-O7&&`DqV~sH>L`h=I0RC@7FeDKx zPJ)`i^x^Br==0?AZ0t`b>-F`XAQpHcqOA~B@DR5deTfwB^D5IRX34|AA=w(Cei0fT z!*irL@G40<58|KmE#ET=cNWMC;MEclQ|5zs1g~<)#^o%|q|qp0LPg?4-hEy1(f_fU zJX{WU)QW@>COp8~ybQL?0>c+;To0S>ioAb#&U=|255aB<(?$$ZHrt#d#rwB5<3D7H Z?GkupXRRG&*7t936WW!<|J9Bd^9??cCqV!J literal 0 HcmV?d00001 diff --git a/examples/colpitts_oscillator.cpk b/examples/colpitts_oscillator.cpk index 231558b163fac080237efd351126926f11a0f54f..54f244d5b436274bd824d7785534741f44fc413e 100644 GIT binary patch delta 313 zcmcb>et~_0=EP>)aC$Fu;KV570OT28N0C;*;MpfxG}Tm_r6rp$bT$3dq2TjiPKUAeI8e85}TUC+9PZ Y1Kr5MqJgki0%R}HlL|c!a67>a0F&%RjQ{`u delta 314 zcmcb>et~_0=456j;fXd}6Bmh1jM12E#w5hWz{0}7Ai%@I!7_27_~cWJf)h{hfK;)w za4;}%uz*Eb85KDh85sEZ3fdhQChIebO^rDMP*AKwvR^L{TM{hhDj^lb*}_u};itn|=7wwF VBK}3Ikd9WMNafF09c=7g?_WM(4<`Ts diff --git a/examples/pnp_oscillator.cpk b/examples/pnp_oscillator.cpk index 0e831f2aa2134b3dc23f53b921e0aef8a3c7ae31..6fac79752c2b23e312c6cd15df452366b38c7f92 100644 GIT binary patch literal 1046 zcma)*u}T9$5QZl(=z_<(!hu&@u|<$84)Fm*&nk~0iC6@J5o6^GXlEh5hR+bNPHS&x zDR~0_pD3rv?BO2AE&Maz{xfr{$FuR(`E+(Mo=k?f(;GPw6(=Gw)>2529Qz*Lze`0z zP_6LY6dAhp{C4oMbGUcncP|%2D@Jx4-nb}HF)R`hV-Zzg;3lx`u2+Pbc+~7b+ zN!s$MCw$wLm6G9+P-uTe^#1z3X#==Z1SAfmpHOSLI&!&>Xz%Bv2H(^|GaQO$6=n&P zN>gHj_YbcPH{UBK4RcG;C`H8nF8U{TlU9&cq-l^s#eV&hS8`k^CPWS9R1~7iU_Rk5 z`#jwqyx-+7gW|2aRsaTtqk(R}2kU~YjRz3W01!K3noZE%PghGS4D+V(uP*Fv_fWPcS;F&WKBbB S(rTvIEmG>SvvZr4j{XAi&NUGL diff --git a/examples/sin_oscillator.cpk b/examples/sin_oscillator.cpk index 47a70ef677ffd13b7582edc447a605f83b2c2656..68a1061aee49ed491d2f6ffa0153555ee392e992 100644 GIT binary patch literal 1046 zcma)*u}T9$5QZl(=z+_+!hu^{vBe=*9O46ro>d-060rybBgV=X(9S}94WA)koz~vY zQt|};f1;c*yN7%1?ZQ9v?d(5ydORInolmA0qw#ofJGqe~QOQIk1Qjn%a_oDU>qAAH ztF*?tDKd2H`R(9i=Wy@D?q1I4XKl7-z%!kP#Ilv5(JYC!ws~xp$*WgpKm?5$k!o-t zq$F+e)DzBj7%v8oIIrc3XzlfV(*|&-2uM&_kE^9v9l6*?w6(KggEci^Mh35Wi|7?7 z6;X)^);_#8+0_FPtzc|ihli*SFl~Uj0@_bT~UacLGg+D z%;)KL|NSn1=?`XY*@4&qY^ix13$e?@IJP7fp8=X0D~Ml6mzQy9MN2DW`go<3_>UwE W_|xv1w3;PGJyS|uwDrGf>F5_H$}?{O literal 1046 zcma)*&q~BF5XNU=(10OED40W$9E$W%#0L7-^JsC=e_z2 zf*08*aK2jTx=hMWDgEU1eLk69j>hBR-Q<=IiOCRAj7)(%Wkdt{TnQ%f zzT}EE5o0&rKKH-24t9>+_SJlT+NHA*Jkl|Vmdy|?nws`~VFOvY$OkSOqH{M-%M)TK%K#&#E+@7K)Z;748*#BKf1R6M)UB#M#0(=|V-*^a zA?2zBoO90~HD21tK$E_uXprLCv;bO2(?s$m{8FqyL95l}XqPO;NA{|JETXX{$+JHv zn-AY-?|YB;GfeOo5!fi$f-@Z}VxNgRwg6VPfizVs2s@a = a; curve->hfe = d; - scf_logi("curve v: %lg, a: %lg, hfe: %lg, R: %lg\n", v, a, d, v / a); + scf_logd("curve v: %lg, a: %lg, hfe: %lg, R: %lg\n", v, a, d, v / a); d = 0.0; dot = 0; @@ -158,6 +158,7 @@ int ses_va_curve(ScfEcomponent* c, const char* txt) int ses_init_component(ScfEcomponent* c) { ScfEcomponent* c2; + ScfEline* el; ScfEdata* ed; ed = scf_ecomponent__find_data(c->type, c->model); @@ -165,6 +166,10 @@ int ses_init_component(ScfEcomponent* c) return -EINVAL; c->ops = ed->ops; + long i; + for (i = 0; i < c->n_pins; i++) + c->pins[i]->c = c; + if (ed->va_curve) { int ret = ses_va_curve(c, ed->va_curve); if (ret < 0) @@ -192,21 +197,22 @@ int ses_init_component(ScfEcomponent* c) return ret; } - scf_logi("c->f->n_components: %ld, c->f->n_elines: %ld\n", c->f->n_components, c->f->n_elines); + c->f->IC = c; - long i; - long j; - for (i = 0; i < c->f->n_components; i++) { - c2 = c->f->components[i]; + scf_logd("c->f->n_components: %ld, c->f->n_elines: %ld\n", c->f->n_components, c->f->n_elines); - for (j = 0; j < c2->n_pins; j++) - c2->pins[j]->IC = c; + for (i = 0; i < c->f->n_elines; i++) { + el = c->f->elines[i]; + el->pf = c->f; + } + + for (i = 0; i < c->f->n_components; i++) { + c2 = c->f->components[i]; + c2->pf = c->f; ret = ses_init_component(c2); if (ret < 0) return ret; - - c2->pf = c->f; } return 0; @@ -214,14 +220,6 @@ int ses_init_component(ScfEcomponent* c) int ses_draw_IC(ScfEcomponent* c) { - ses_lines_same_components(c->f); - - int ret = ses_layout_function(c->f, 100); - if (ret < 0) { - scf_loge("\n"); - return ret; - } - char file[128]; snprintf(file, sizeof(file) - 1, "./IC%ld.png", c->id); @@ -232,7 +230,7 @@ int ses_draw_IC(ScfEcomponent* c) int main(int argc, char* argv[]) { if (argc < 2) { - printf("usage: ./a.out src.cpk [fname cid]\n\n"); + printf("usage: ./ses src.cpk [fname cid]\n\n"); printf("fname: optional, function name in board\n"); printf("cid : optional, component id in function, only for IC\n\n"); printf("if set fname & cid, only show the internal graph of this IC\n"); @@ -240,10 +238,9 @@ int main(int argc, char* argv[]) } ScfEcomponent* c; - ScfEcomponent* c2; ScfEfunction* f; ScfEboard* b = NULL; - ScfEdata* ed = NULL; + ScfEline* el; uint8_t* buf = NULL; @@ -270,6 +267,11 @@ int main(int argc, char* argv[]) for (i = 0; i < b->n_functions; i++) { f = b->functions[i]; + for (j = 0; j < f->n_elines; j++) { + el = f->elines[j]; + el->pf = f; + } + for (j = 0; j < f->n_components; j++) { c = f->components[j]; @@ -281,6 +283,8 @@ int main(int argc, char* argv[]) return ret; } + c->pf = f; + if (4 == argc && c->f && !strcmp(argv[2], f->name) && atol(argv[3]) == c->id) { ret = ses_draw_IC(c); @@ -290,8 +294,6 @@ int main(int argc, char* argv[]) ScfEboard_free(b); return 0; } - - c->pf = f; } } // print_board(b); @@ -302,8 +304,7 @@ int main(int argc, char* argv[]) f = b->functions[i]; printf("f: %s\n", f->name); - - ses_steps_analyse(f, 10 * 1000, 3); + ses_steps_analyse(f, 100LL, 5); } ScfEboard_free(b); diff --git a/pack/scf_pack.c b/pack/scf_pack.c index abe3e83..1e93428 100644 --- a/pack/scf_pack.c +++ b/pack/scf_pack.c @@ -19,7 +19,6 @@ long __scf_pack_one_index(uint8_t* pack, uint64_t u, long shift) max = i; else max -= i; - scf_logd("max: %d, i: %d, j: %d, k: %d, shift: %d\n", max, i, j, k, shift); pack[j] |= max << k; @@ -48,15 +47,13 @@ long __scf_pack_one_index(uint8_t* pack, uint64_t u, long shift) return -EINVAL; } - scf_logd("max: %d, i: %d, j: %d, k: %d, shift: %d\n\n", max, i, j, k, shift); + scf_logd("max: %ld, i: %ld, j: %ld, k: %ld, shift: %ld\n\n", max, i, j, k, shift); max = i; } - if (8 - k < shift && 0 != max) { + if (8 - k < shift && 0 != max) pack[++j] = 0; - scf_logd("max: %d, i: %d, j: %d, k: %d, shift: %d\n\n", max, i, j, k, shift); - } return j + 1; } @@ -201,7 +198,9 @@ long __scf_unpack2(void* p, long shift, const uint8_t* buf, long len) return -EINVAL; } - scf_logd("max: %d, i: %d, j: %d, k: %d, shift: %d\n\n", max, i, j, k, shift); + scf_logd("max: %ld, i: %ld, j: %ld, k: %ld, shift: %ld\n\n", max, i, j, k, shift); + if (0 == max) + break; } j++; diff --git a/scf_eda_pack.c b/scf_eda_pack.c index dc1f052..f236b48 100644 --- a/scf_eda_pack.c +++ b/scf_eda_pack.c @@ -16,16 +16,21 @@ static int component_pins[SCF_EDA_Components_NB] = SCF_EDA_NAND_NB, SCF_EDA_NOR_NB, SCF_EDA_NOT_NB, + + SCF_EDA_AND_NB, + SCF_EDA_OR_NB, + SCF_EDA_XOR_NB, + SCF_EDA_ADD_NB, }; -static int __diode_path_off(ScfEpin* p0, ScfEpin* p1) +static int __diode_path_off(ScfEpin* p0, ScfEpin* p1, int flags) { if (SCF_EDA_Diode_NEG == p0->id) return 1; return 0; } -static int __npn_path_off(ScfEpin* p0, ScfEpin* p1) +static int __npn_path_off(ScfEpin* p0, ScfEpin* p1, int flags) { if (SCF_EDA_NPN_E == p0->id) return 1; @@ -35,14 +40,14 @@ static int __npn_path_off(ScfEpin* p0, ScfEpin* p1) return 1; } -static int __npn_shared(ScfEpin* p) +static int __npn_shared(ScfEpin* p, int flags) { if (SCF_EDA_NPN_E == p->id) return 1; return 0; } -static int __pnp_path_off(ScfEpin* p0, ScfEpin* p1) +static int __pnp_path_off(ScfEpin* p0, ScfEpin* p1, int flags) { if (SCF_EDA_PNP_E != p0->id) return 1; @@ -52,74 +57,80 @@ static int __pnp_path_off(ScfEpin* p0, ScfEpin* p1) return 1; } -static int __pnp_shared(ScfEpin* p) +static int __pnp_shared(ScfEpin* p, int flags) { if (SCF_EDA_PNP_E == p->id) return 1; return 0; } -static int __nand_path_off(ScfEpin* p0, ScfEpin* p1) +static int __ttl_nand_path_off(ScfEpin* p0, ScfEpin* p1, int flags) { if (SCF_EDA_NAND_NEG == p0->id) return 1; + if (flags && (SCF_EDA_NAND_IN0 == p0->id || SCF_EDA_NAND_IN1 == p0->id)) + return 1; if (SCF_EDA_NAND_POS == p0->id) { if (p1 && (SCF_EDA_NAND_IN0 == p1->id || SCF_EDA_NAND_IN1 == p1->id)) return 1; - - } else if (p1 && SCF_EDA_NAND_NEG != p1->id) - return 1; - return 0; -} - -static int __nand_shared(ScfEpin* p) -{ - if (SCF_EDA_NAND_NEG == p->id || SCF_EDA_NAND_POS == p->id) - return 1; + } else { + if (p1) { + if (!flags && (SCF_EDA_NAND_IN0 == p0->id || SCF_EDA_NAND_IN1 == p0->id) + && SCF_EDA_NAND_OUT == p1->id) + return 0; + + if (SCF_EDA_NAND_NEG != p1->id) + return 1; + } + } return 0; } -static int __nor_path_off(ScfEpin* p0, ScfEpin* p1) +static int __ttl_nand_shared(ScfEpin* p, int flags) { - if (SCF_EDA_NOR_NEG == p0->id) - return 1; - - if (SCF_EDA_NOR_POS == p0->id) { - if (p1 && (SCF_EDA_NOR_IN0 == p1->id || SCF_EDA_NOR_IN1 == p1->id)) + if (!flags) { + if (SCF_EDA_NAND_OUT != p->id) return 1; - - } else if (p1 && SCF_EDA_NOR_NEG != p1->id) - return 1; - return 0; + return 0; + } + return 1; } -static int __nor_shared(ScfEpin* p) +static int __ttl_add_path_off(ScfEpin* p0, ScfEpin* p1, int flags) { - if (SCF_EDA_NOR_NEG == p->id || SCF_EDA_NOR_POS == p->id) + if (SCF_EDA_ADD_NEG == p0->id) return 1; - return 0; -} - -static int __not_path_off(ScfEpin* p0, ScfEpin* p1) -{ - if (SCF_EDA_NOT_NEG == p0->id) + if (flags && (SCF_EDA_ADD_IN0 == p0->id || SCF_EDA_ADD_IN1 == p0->id)) return 1; - if (SCF_EDA_NOT_POS == p0->id) { - if (p1 && SCF_EDA_NOT_IN == p1->id) + if (SCF_EDA_ADD_POS == p0->id) { + if (p1 && (SCF_EDA_ADD_IN0 == p1->id || SCF_EDA_ADD_IN1 == p1->id)) return 1; - - } else if (p1 && SCF_EDA_NOT_NEG != p1->id) - return 1; + } else { + if (p1) { + if (!flags + && (SCF_EDA_ADD_IN0 == p0->id || SCF_EDA_ADD_IN1 == p0->id) + && (SCF_EDA_ADD_OUT == p1->id || SCF_EDA_ADD_CF == p1->id)) + return 0; + + if (SCF_EDA_ADD_NEG != p1->id) + return 1; + } + } return 0; } -static int __not_shared(ScfEpin* p) +static int __ttl_add_shared(ScfEpin* p, int flags) { - if (SCF_EDA_NOT_NEG == p->id || SCF_EDA_NOT_POS == p->id) - return 1; - return 0; +// if (SCF_EDA_ADD_NEG == p->id || SCF_EDA_ADD_POS == p->id) +// return 1; + if (!flags) { + if (SCF_EDA_ADD_OUT != p->id && SCF_EDA_ADD_CF != p->id) + return 1; + return 0; + } + return 1; } static ScfEops __diode_ops = @@ -140,40 +151,43 @@ static ScfEops __pnp_ops = __pnp_shared, }; -static ScfEops __nand_ops = +static ScfEops __ttl_nand_ops = { - __nand_path_off, - __nand_shared, + __ttl_nand_path_off, + __ttl_nand_shared, }; -static ScfEops __nor_ops = +static ScfEops __ttl_gate_ops = { - __nor_path_off, - __nor_shared, + __ttl_nand_path_off, + __ttl_nand_shared, }; -static ScfEops __not_ops = +static ScfEops __ttl_add_ops = { - __not_path_off, - __not_shared, + __ttl_add_path_off, + __ttl_add_shared, }; static ScfEdata component_datas[] = { {SCF_EDA_None, 0, 0, 0, 0, 0, 0, 0, 0, NULL, NULL, NULL}, - {SCF_EDA_Battery, 0, SCF_EDA_Battery_POS, 0, 0, 1e-9, 1e9, 0, 0, NULL, NULL, NULL}, + {SCF_EDA_Battery, 0, 0, 0, 0, 1e-9, 1e9, 0, 0, NULL, NULL, NULL}, {SCF_EDA_Resistor, 0, 0, 0, 0, 1e4, 0, 0, 0, NULL, NULL, NULL}, {SCF_EDA_Capacitor, 0, 0, 0, 0, 10, 0.1, 0, 0, NULL, NULL, NULL}, {SCF_EDA_Inductor, 0, 0, 0, 0, 10, 0, 1e3, 0, NULL, NULL, NULL}, - {SCF_EDA_Diode, 0, 0, 0, 0, 0, 0, 0, 0, &__diode_ops, NULL, NULL}, + {SCF_EDA_Diode, 0, 0, 0, 0, 0, 0, 0, 0, &__diode_ops, NULL, "./cpk/9013.txt"}, {SCF_EDA_NPN, 0, 0, 0, 0, 0, 0, 0, 0, &__npn_ops, NULL, "./cpk/9013.txt"}, {SCF_EDA_PNP, 0, 0, 0, 0, 0, 0, 0, 0, &__pnp_ops, NULL, "./cpk/9012.txt"}, - {SCF_EDA_NAND, 0, 0, 0, 0, 0, 0, 0, 0, &__nand_ops, "./cpk/nand.cpk", NULL}, - {SCF_EDA_NOR, 0, 0, 0, 0, 0, 0, 0, 0, &__nor_ops, "./cpk/nor.cpk", NULL}, - {SCF_EDA_NOT, 0, 0, 0, 0, 0, 0, 0, 0, &__not_ops, "./cpk/not.cpk", NULL}, + {SCF_EDA_NAND, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_nand_ops, "./cpk/ttl_nand.cpk", NULL}, + {SCF_EDA_AND, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_gate_ops, "./cpk/ttl_and.cpk", NULL}, + {SCF_EDA_OR, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_gate_ops, "./cpk/ttl_or.cpk", NULL}, + {SCF_EDA_NOR, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_gate_ops, "./cpk/ttl_nor.cpk", NULL}, + {SCF_EDA_XOR, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_gate_ops, "./cpk/ttl_xor.cpk", NULL}, + {SCF_EDA_ADD, 0, 0, 0, 0, 0, 0, 0, 0, &__ttl_add_ops, "./cpk/ttl_add.cpk", NULL}, }; static ScfEdata pin_datas[] = @@ -183,10 +197,10 @@ static ScfEdata pin_datas[] = {SCF_EDA_Diode, 0, SCF_EDA_Diode_NEG, 0, 0, 750, 0, 0, 0, NULL, NULL, NULL}, {SCF_EDA_NPN, 0, SCF_EDA_NPN_B, 0, 0, 750, 0, 0, 0, NULL, NULL, NULL}, - {SCF_EDA_NPN, 0, SCF_EDA_NPN_C, 0, 0, 3, 0, 0, 250, NULL, NULL, NULL}, + {SCF_EDA_NPN, 0, SCF_EDA_NPN_C, 0, 0, 3, 0, 0, 150, NULL, NULL, NULL}, {SCF_EDA_PNP, 0, SCF_EDA_PNP_B, 0, 0, 750, 0, 0, 0, NULL, NULL, NULL}, - {SCF_EDA_PNP, 0, SCF_EDA_PNP_C, 0, 0, 3, 0, 0, 250, NULL, NULL, NULL}, + {SCF_EDA_PNP, 0, SCF_EDA_PNP_C, 0, 0, 3, 0, 0, 150, NULL, NULL, NULL}, }; static ScfEdata* _pin_find_data(const uint64_t type, const uint64_t model, const uint64_t pid) @@ -789,13 +803,20 @@ int scf_pins_same_line(ScfEfunction* f) long n; for (i = 0; i < f->n_components; i++) { - c = f->components[i]; + c = f->components[i]; + c->pf = f; for (j = 0; j < c->n_pins; j++) { - p = c->pins[j]; + p = c->pins[j]; + p->c = c; qsort(p->tos, p->n_tos / 2, sizeof(uint64_t) * 2, epin_cmp); + for (k = 0; k < p->n_tos; k += 2) { + if (p->tos[k] == c->id) + scf_logw("c%ldp%ld connect to its own pin %ld\n", c->id, p->id, p->tos[k + 1]); + } + for (k = 0; k < f->n_elines; k++) { el = f->elines[k]; @@ -826,6 +847,9 @@ int scf_pins_same_line(ScfEfunction* f) p ->lid = el->id; p ->c_lid = el->id; el->flags |= p->flags; + + if (p->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_OUT | SCF_EDA_PIN_SHIFT)) + el->io_lid = p->io_lid; goto next; } } @@ -847,6 +871,9 @@ int scf_pins_same_line(ScfEfunction* f) p ->lid = el->id; p ->c_lid = el->id; el->flags |= p->flags; + + if (p->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_OUT | SCF_EDA_PIN_SHIFT)) + el->io_lid = p->io_lid; next: for (n = 0; n + 1 < p->n_tos; n += 2) { @@ -873,6 +900,9 @@ next: p2->lid = el->id; p2->c_lid = el->id; el->flags |= p2->flags; + + if (p2->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_OUT | SCF_EDA_PIN_SHIFT)) + el->io_lid = p2->io_lid; } qsort(el->pins, el->n_pins / 2, sizeof(uint64_t) * 2, epin_cmp); @@ -892,6 +922,7 @@ next: continue; } + el->pf = f; el->c_pins = el->n_pins; i++; } diff --git a/scf_eda_pack.h b/scf_eda_pack.h index f3813b8..6b4ed2f 100644 --- a/scf_eda_pack.h +++ b/scf_eda_pack.h @@ -19,6 +19,12 @@ enum { SCF_EDA_NOR, SCF_EDA_NOT, + SCF_EDA_AND, + SCF_EDA_OR, + SCF_EDA_XOR, + + SCF_EDA_ADD, + SCF_EDA_Components_NB, }; @@ -29,8 +35,9 @@ enum { #define SCF_EDA_PIN_NEG 8 #define SCF_EDA_PIN_CF 16 #define SCF_EDA_PIN_BORDER 32 -#define SCF_EDA_PIN_CONST 64 +#define SCF_EDA_PIN_SHIFT 64 #define SCF_EDA_PIN_IN0 128 +#define SCF_EDA_PIN_DIV0 256 #define SCF_EDA_V_INIT -10001001.0 #define SCF_EDA_V_MIN -10000000.0 @@ -78,6 +85,16 @@ enum { SCF_EDA_PNP_NB = SCF_EDA_NPN_NB, }; +enum { + SCF_EDA_NOT_NEG, + SCF_EDA_NOT_POS, + + SCF_EDA_NOT_IN, + SCF_EDA_NOT_OUT, + + SCF_EDA_NOT_NB, +}; + enum { SCF_EDA_NAND_NEG, SCF_EDA_NAND_POS, @@ -90,24 +107,59 @@ enum { }; enum { - SCF_EDA_NOR_NEG, - SCF_EDA_NOR_POS, + SCF_EDA_NOR_NEG = SCF_EDA_NAND_NEG, + SCF_EDA_NOR_POS = SCF_EDA_NAND_POS, - SCF_EDA_NOR_IN0, - SCF_EDA_NOR_IN1, - SCF_EDA_NOR_OUT, + SCF_EDA_NOR_IN0 = SCF_EDA_NAND_IN0, + SCF_EDA_NOR_IN1 = SCF_EDA_NAND_IN1, + SCF_EDA_NOR_OUT = SCF_EDA_NAND_OUT, SCF_EDA_NOR_NB, }; enum { - SCF_EDA_NOT_NEG, - SCF_EDA_NOT_POS, + SCF_EDA_AND_NEG = SCF_EDA_NAND_NEG, + SCF_EDA_AND_POS = SCF_EDA_NAND_POS, - SCF_EDA_NOT_IN, - SCF_EDA_NOT_OUT, + SCF_EDA_AND_IN0 = SCF_EDA_NAND_IN0, + SCF_EDA_AND_IN1 = SCF_EDA_NAND_IN1, + SCF_EDA_AND_OUT = SCF_EDA_NAND_OUT, - SCF_EDA_NOT_NB, + SCF_EDA_AND_NB, +}; + +enum { + SCF_EDA_OR_NEG = SCF_EDA_NAND_NEG, + SCF_EDA_OR_POS = SCF_EDA_NAND_POS, + + SCF_EDA_OR_IN0 = SCF_EDA_NAND_IN0, + SCF_EDA_OR_IN1 = SCF_EDA_NAND_IN1, + SCF_EDA_OR_OUT = SCF_EDA_NAND_OUT, + + SCF_EDA_OR_NB, +}; + +enum { + SCF_EDA_XOR_NEG = SCF_EDA_NAND_NEG, + SCF_EDA_XOR_POS = SCF_EDA_NAND_POS, + + SCF_EDA_XOR_IN0 = SCF_EDA_NAND_IN0, + SCF_EDA_XOR_IN1 = SCF_EDA_NAND_IN1, + SCF_EDA_XOR_OUT = SCF_EDA_NAND_OUT, + + SCF_EDA_XOR_NB, +}; + +enum { + SCF_EDA_ADD_NEG = SCF_EDA_NAND_NEG, + SCF_EDA_ADD_POS = SCF_EDA_NAND_POS, + + SCF_EDA_ADD_IN0 = SCF_EDA_NAND_IN0, + SCF_EDA_ADD_IN1 = SCF_EDA_NAND_IN1, + SCF_EDA_ADD_OUT = SCF_EDA_NAND_OUT, + SCF_EDA_ADD_CF, + + SCF_EDA_ADD_NB, }; typedef struct { @@ -162,8 +214,9 @@ typedef struct scf_eboard_s ScfEboard; struct scf_eops_s { - int (*off )(ScfEpin* p0, ScfEpin* p1); - int (*shared)(ScfEpin* p); + int (*off )(ScfEpin* p0, ScfEpin* p1, int flags); + + int (*shared)(ScfEpin* p, int flags); }; struct scf_epin_s @@ -175,8 +228,10 @@ struct scf_epin_s SCF_PACK_DEF_VARS(uint64_t, tos); SCF_PACK_DEF_VAR(uint64_t, c_lid); + SCF_PACK_DEF_VAR(int64_t, io_lid); + SCF_PACK_DEF_VAR(int64_t, ic_lid); - SCF_PACK_DEF_OBJ(ScfEcomponent, IC); + SCF_PACK_DEF_OBJ(ScfEcomponent, c); SCF_PACK_DEF_VAR(double, v); SCF_PACK_DEF_VAR(double, a); @@ -197,7 +252,6 @@ struct scf_epin_s SCF_PACK_DEF_VAR(int, y); SCF_PACK_DEF_VAR(int, n_diodes); - SCF_PACK_DEF_VAR(int, l_pos); SCF_PACK_DEF_VAR(uint8_t, vflag); SCF_PACK_DEF_VAR(uint8_t, pflag); @@ -213,6 +267,7 @@ SCF_PACK_INFO_VAR(ScfEpin, flags), SCF_PACK_INFO_VARS(ScfEpin, tos, uint64_t), SCF_PACK_INFO_VAR(ScfEpin, c_lid), +SCF_PACK_INFO_VAR(ScfEpin, io_lid), SCF_PACK_INFO_VAR(ScfEpin, ic_lid), SCF_PACK_INFO_VAR(ScfEpin, v), @@ -231,7 +286,6 @@ SCF_PACK_INFO_VAR(ScfEpin, path), SCF_PACK_INFO_VAR(ScfEpin, x), SCF_PACK_INFO_VAR(ScfEpin, y), SCF_PACK_INFO_VAR(ScfEpin, n_diodes), -SCF_PACK_INFO_VAR(ScfEpin, l_pos), SCF_PACK_INFO_VAR(ScfEpin, vflag), SCF_PACK_INFO_VAR(ScfEpin, pflag), @@ -255,6 +309,9 @@ typedef struct { SCF_PACK_DEF_VAR(uint64_t, c_pins); SCF_PACK_DEF_VAR(uint64_t, flags); SCF_PACK_DEF_VAR(int64_t, color); + SCF_PACK_DEF_VAR(int64_t, io_lid); + + SCF_PACK_DEF_OBJ(ScfEfunction, pf); SCF_PACK_DEF_OBJS(ScfEconn, conns); SCF_PACK_DEF_OBJS(ScfLine, lines); @@ -265,7 +322,7 @@ typedef struct { SCF_PACK_DEF_VAR(uint8_t, vconst); SCF_PACK_DEF_VAR(uint8_t, aconst); SCF_PACK_DEF_VAR(uint8_t, vflag); - SCF_PACK_DEF_VAR(uint8_t, vinit); + SCF_PACK_DEF_VAR(uint8_t, open_flag); } ScfEline; SCF_PACK_TYPE(ScfEline) @@ -274,6 +331,7 @@ SCF_PACK_INFO_VARS(ScfEline, pins, uint64_t), SCF_PACK_INFO_VAR(ScfEline, c_pins), SCF_PACK_INFO_VAR(ScfEline, flags), SCF_PACK_INFO_VAR(ScfEline, color), +SCF_PACK_INFO_VAR(ScfEline, io_lid), SCF_PACK_INFO_OBJS(ScfEline, conns, ScfEconn), SCF_PACK_INFO_OBJS(ScfEline, lines, ScfLine), @@ -352,6 +410,9 @@ struct scf_efunction_s SCF_PACK_DEF_VARS(uint8_t, name); SCF_PACK_DEF_OBJS(ScfEcomponent, components); SCF_PACK_DEF_OBJS(ScfEline, elines); + + SCF_PACK_DEF_OBJ(ScfEcomponent, IC); + SCF_PACK_DEF_VAR(int, x); SCF_PACK_DEF_VAR(int, y); SCF_PACK_DEF_VAR(int, w); @@ -429,7 +490,7 @@ int scf_pins_same_line(ScfEfunction* f); return ret; \ } \ \ - for (size_t i = 0; i < (_c)->n_pins; i++) \ + for (long i = 0; i < (_c)->n_pins; i++) \ (_c)->pins[i]->cid = (_c)->id; \ } while (0) diff --git a/ses_core.h b/ses_core.h index 839eda2..5d6bcbe 100644 --- a/ses_core.h +++ b/ses_core.h @@ -109,15 +109,19 @@ struct ses_step_s { const char* name; - int (*handler)(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx); + int (*handler)(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx); void* priv; }; +void ses_eline_print(ScfEline* el); +void ses_pin_print(ScfEpin* p); +void ses_IC_print(ScfEcomponent* c); + ses_path_t* ses_path_alloc(); void ses_path_free (ses_path_t* path); -void ses_path_print(ses_path_t* path, ScfEfunction* f); +void ses_path_print(ses_path_t* path); ses_path_t* ses_path_ref (ses_path_t* src); int ses_path_xchg (ses_path_t* path0, int k0, ses_path_t* path1, int k1); @@ -138,7 +142,7 @@ void ses_node_print(ses_node_t* node); void ses_nodes_free (scf_vector_t* nodes); void ses_nodes_print(scf_vector_t* nodes); -void ses_paths_print(scf_vector_t* paths, ScfEfunction* f); +void ses_paths_print(scf_vector_t* paths); ses_ctx_t* ses_ctx_alloc(); void ses_ctx_free (ses_ctx_t* ctx); @@ -154,51 +158,72 @@ int ses_lines_same_components(ScfEfunction* f); int ses_layout_board(ScfEboard* b, int d); int ses_layout_paths(ScfEfunction* f, scf_vector_t* paths); -int ses_steps_analyse(ScfEfunction* f, int64_t ns, int64_t count); +int ses_steps_analyse(ScfEfunction* f, int64_t ps, int64_t count); -int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32_t bw, uint32_t bh, int64_t ns, int64_t count); +int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32_t bw, uint32_t bh, int64_t ps, int64_t count); -int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ns, int64_t count); +int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ps, int64_t count); int __ses_nodes_path (ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, scf_vector_t** pnodes, scf_vector_t** pedges); -int __ses_nodes_path_solve(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, int* changed, int64_t ns, int64_t count); +int __ses_nodes_path_solve(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, int* changed, int64_t ps, int64_t count); int __ses_path_jr(ScfEfunction* f, ses_path_t* path); void __ses_path_pr(ScfEfunction* f, ses_path_t* path, int i, int j, ses_path_t* child, double* r); void __ses_path_sr(ScfEfunction* f, ses_path_t* path, int i, int j, double* r); void __ses_path_lc(ScfEfunction* f, ses_path_t* path, int m, int n, double* cv, double* lv, double* uf, double* uh, double* la); -int __ses_path_va3(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ns, int64_t count); -int __ses_path_va2(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ns, int64_t count); -int __ses_path_va (ScfEfunction* f, ses_path_t* path, int *changed, int64_t ns, int64_t count); - int __ses_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN); int __ses_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN); -static inline ScfEcomponent* ses_component(ScfEfunction* f, ScfEpin* p) +static inline ScfEline* ses_top_line(ScfEline* el) { - if (!p->IC) - return f->components[p->cid]; + ScfEcomponent* c = el->pf->IC; + ScfEpin* p; + + while (c && el->id < c->n_pins) { + p = c->pins[el->id]; - return p->IC->f->components[p->cid]; + if (p->lid >= c->pf->n_elines) + break; + + el = c ->pf->elines[p->lid]; + c = el->pf->IC; + } + return el; } -static inline ScfEline* ses_line(ScfEfunction* f, ScfEpin* p) -{ - if (!p->IC) - return f->elines[p->lid]; +void ses_line_set_v(ScfEline* el, double v); - if (p->lid >= p->IC->n_pins) - return p->IC->f->elines[p->lid]; +static inline ScfEline* ses_top_pline(ScfEpin* p) +{ + return ses_top_line(p->c->pf->elines[p->lid]); +} - p = p->IC->pins[p->lid]; - return f->elines[p->lid]; +static inline int ses_same_line(ScfEpin* p0, ScfEpin* p1) +{ + return ses_top_pline(p0) == ses_top_pline(p1); } -static inline int ses_same_line(ScfEfunction* f, ScfEpin* p0, ScfEpin* p1) +#define SES_LINE_POS(p) (ses_top_pline(p)->flags & SCF_EDA_PIN_POS) +#define SES_LINE_NEG(p) (ses_top_pline(p)->flags & SCF_EDA_PIN_NEG) + +static inline int ses_same_line_in_path(ScfEpin* p, ses_path_t* path) { - return ses_line(f, p0) == ses_line(f, p1); + ScfEline* el = ses_top_pline(p); + ScfEline* el2; + ScfEpin* p2; + + int i; + for (i = 0; i < path->pins->size; i++) { + p2 = path->pins->data[i]; + + el2 = ses_top_pline(p2); + scf_logd("el%ld, el%ld, c%ldp%ld, c%ldp%ld\n", el->id, el2->id, p->cid,p->id, p2->cid,p2->id); + if (ses_top_pline(p2) == el) + return 1; + } + return 0; } static inline void vertical(int* px, int* py, int dx, int dy, int d) @@ -307,109 +332,4 @@ static inline void ses_merge_r(double* tr, double* jtr, double r0, double jr0, d *jtr = jr0 / -R; } -static inline void ses_va_PNN(double U0, double U1, double U2, - double R0, double R1, double R2, - double* pi0, double* pi1, double* pi2, double* pVb0) -{ - double i1 = (R0 * (U2 - U1) + R2 * (U0 - U1)) / (R0 * R1 + R1 * R2 + R0 * R2); - double i0 = (U0 - U1 - i1 * R1) / R0; - double i2 = i0 - i1; - - double V0 = i0 * R0; - double V1 = i1 * R1; - double V2 = i2 * R2; - - scf_logi("U0: %lg, U1: %lg, U2: %lg, R0: %lg, R1: %lg, R2: %lg, i0: %lg, i1: %lg, i2: %lg, V0: %lg, V1: %lg, V2: %lg\n", - U0, U1, U2, R0, R1, R2, i0, i1, i2, V0, V1, V2); - - if (pi0) - *pi0 = i0; - - if (pi1) - *pi1 = i1; - - if (pi2) - *pi2 = i2; - - if (*pVb0) - *pVb0 = U0 - V0; -} - -static inline void ses_va_PPN(double U0, double U1, double U2, - double R0, double R1, double R2, - double* pi0, double* pi1, double* pi2, double* pVb1) -{ - double i1 = (R0 * (U2 - U1) + R2 * (U0 - U1)) / (R0 * R1 + R1 * R2 + R0 * R2); - double i0 = (U0 - U1 - i1 * R1) / R0; - double i2 = i1 - i0; - - double V0 = i0 * R0; - double V1 = i1 * R1; - double V2 = i2 * R2; - - scf_logi("U0: %lg, U1: %lg, U2: %lg, R0: %lg, R1: %lg, R2: %lg, i0: %lg, i1: %lg, i2: %lg, V0: %lg, V1: %lg, V2: %lg\n", - U0, U1, U2, R0, R1, R2, i0, i1, i2, V0, V1, V2); - - if (pi0) - *pi0 = i0; - - if (pi1) - *pi1 = i1; - - if (pi2) - *pi2 = i2; - - if (*pVb1) - *pVb1 = U1 + V1; -} - -static inline void ses_va_bridge( - double U0, double U1, double U2, double U3, double Vbc, - double R0, double R1, double R2, double R3, double Rb, - double* pi0, double* pi1, double* pi2, double* pi3, double* pib, - double* pVb0, double* pVb1) -{ - scf_logw("R0: %lg, R1: %lg, R2: %lg, R3: %lg, Vbc: %lg, U0: %lg, U1: %lg, U2: %lg, U3: %lg\n", R0, R1, R2, R3, Vbc, U0, U1, U2, U3); - - double i1 = (R0 * R3 * (U2 - U1 + Vbc) - R0 * R2 * (U1 - U3 - Vbc) + (R2 * R3 + R3 * Rb + R2 * Rb) * (U0 - U1)) - / ((R2 + R3) * (R0 * R1 + Rb * (R0 + R1)) + R2 * R3 * (R0 + R1)); - - double ib = (U0 - U1 - i1 * (R0 + R1)) / R0; - double i0 = i1 + ib; - double i3 = (R0 * (U1 - U3 - Vbc) - Rb * (U0 - U1) + i1 * (R0 * R1 + Rb * (R0 + R1))) / R0 / R3; - double i2 = i3 - ib; - - double V0 = i0 * R0; - double V1 = i1 * R1; - double V2 = i2 * R2; - double V3 = i3 * R3; - double Vb = ib * Rb; - - scf_logi("i0: %lg, i1: %lg, i2: %lg, i3: %lg, ib: %lg\n", i0, i1, i2, i3, ib); - - double Vb0 = U1 + V1; - double Vb1 = U3 + V3; - - if (pi0) - *pi0 = i0; - - if (pi1) - *pi1 = i1; - - if (pi2) - *pi2 = i2; - - if (pi3) - *pi3 = i3; - - if (pib) - *pib = ib; - - if (pVb0) - *pVb0 = Vb0; - - if (pVb1) - *pVb1 = Vb1; -} - #endif diff --git a/ses_graph.c b/ses_graph.c index f13b074..a074b17 100644 --- a/ses_graph.c +++ b/ses_graph.c @@ -314,8 +314,6 @@ static int __graph_kcolor(scf_vector_t* graph, int k, scf_vector_t* colors) goto overflow; v1->color = v0->color; - ScfEcomponent* c0 = v0->data; - ScfEcomponent* c1 = v1->data; scf_logd("graph->size: %d, k: %d, c%ld, c%ld, color: %ld\n", graph->size, k, c0->id, c1->id, v0->color); __color_del(__colors, v0->color); diff --git a/ses_layout.c b/ses_layout.c index b89f96d..8767c98 100644 --- a/ses_layout.c +++ b/ses_layout.c @@ -1,1531 +1,12 @@ #include #include"ses_core.h" -#include"ses_graph.h" void __ses_function_draw(ScfEfunction* f, cairo_t* cr); -int epin_cmp_color(const void* v0, const void* v1, void* arg) -{ - const uint64_t* t0 = v0; - const uint64_t* t1 = v1; - - ScfEfunction* f = arg; - ScfEcomponent* c0 = f->components[t0[0]]; - ScfEcomponent* c1 = f->components[t1[0]]; - - if (c0->color < c1->color) - return -1; - - if (c0->color > c1->color) - return 1; - return 0; -} - -int epin_cmp_cx(const void* v0, const void* v1, void* arg) -{ - const uint64_t* t0 = v0; - const uint64_t* t1 = v1; - - ScfEfunction* f = arg; - ScfEcomponent* c0 = f->components[t0[0]]; - ScfEcomponent* c1 = f->components[t1[0]]; - - if (c0->x < c1->x) - return -1; - - if (c0->x > c1->x) - return 1; - return 0; -} - -int econn_cmp(const void* v0, const void* v1) -{ - const ScfEconn* ec0 = *(const ScfEconn**)v0; - const ScfEconn* ec1 = *(const ScfEconn**)v1; - - if (ec0->n_cids < ec1->n_cids) - return 1; - - if (ec0->n_cids > ec1->n_cids) - return -1; - return 0; -} - -int eline_cmp(const void* v0, const void* v1) -{ - const ScfEline* el0 = *(const ScfEline**)v0; - const ScfEline* el1 = *(const ScfEline**)v1; - - if (el0->n_conns < el1->n_conns) - return 1; - - if (el0->n_conns > el1->n_conns) - return -1; - - if (el0->n_pins < el1->n_pins) - return 1; - - if (el0->n_pins > el1->n_pins) - return -1; - return 0; -} - -int eline_cmp_id(const void* v0, const void* v1) -{ - const ScfEline* el0 = *(const ScfEline**)v0; - const ScfEline* el1 = *(const ScfEline**)v1; - - if (el0->id < el1->id) - return -1; - - if (el0->id > el1->id) - return 1; - return 0; -} - -int ecomponent_cmp_id(const void* v0, const void* v1) -{ - const ScfEcomponent* c0 = *(const ScfEcomponent**)v0; - const ScfEcomponent* c1 = *(const ScfEcomponent**)v1; - - if (c0->id < c1->id) - return -1; - - if (c0->id > c1->id) - return 1; - return 0; -} - -int ecomponent_cmp_cx(const void* v0, const void* v1) -{ - const ScfEcomponent* c0 = *(const ScfEcomponent**)v0; - const ScfEcomponent* c1 = *(const ScfEcomponent**)v1; - - if (c0->x < c1->x) - return -1; - - if (c0->x > c1->x) - return 1; - return 0; -} - -static inline int __ses_find_eline_index(ScfEfunction* f, uint64_t lid) -{ - ScfEline* el; - size_t j; - - for (j = 0; j < f->n_elines; j++) { - el = f->elines[j]; - - if (el->id == lid) - break; - } - assert(j < f->n_elines); - - return j; -} - -int ses_lines_same_components(ScfEfunction* f) -{ - ScfEline* tmp; - ScfEline* el0; - ScfEline* el1; - ScfEconn* ec; - - size_t i; - size_t j; - size_t k0; - size_t k1; - - ec = NULL; - - for (i = 0; i < f->n_elines; i++) { - el0 = f->elines[i]; - - for (j = 0; j < f->n_elines; j++) { - el1 = f->elines[j]; - - if (el0 == el1) - continue; - - k0 = 0; - k1 = 0; - - if (!ec) { - ec = scf_econn__alloc(); - if (!ec) - return -ENOMEM; - } - - assert(0 == ec->n_cids); - - while (k0 + 1 < el0->n_pins && k1 + 1 < el1->n_pins) { - - uint64_t c0 = el0->pins[k0]; - uint64_t c1 = el1->pins[k1]; - - if (c0 < c1) - k0 += 2; - else if (c0 > c1) - k1 += 2; - else { - k0 += 2; - k1 += 2; - - if (scf_econn__add_cid(ec, c0) < 0) { - ScfEconn_free(ec); - return -ENOMEM; - } - } - } - - if (0 == ec->n_cids) - continue; - - ec->lid = el1->id; - - if (scf_eline__add_conn(el0, ec) < 0) { - ScfEconn_free(ec); - return -ENOMEM; - } - - ec = NULL; - } - - qsort(el0->conns, el0->n_conns, sizeof(ScfEconn*), econn_cmp); - } - - if (ec) { - ScfEconn_free(ec); - ec = NULL; - } - - return 0; -} - -int epath_cmp_pins(const void* v0, const void* v1) -{ - const ses_path_t* p0 = *(const ses_path_t**)v0; - const ses_path_t* p1 = *(const ses_path_t**)v1; - - if (p0->pins->size > p1->pins->size) - return -1; - - if (p0->pins->size < p1->pins->size) - return 1; - return 0; -} - -static inline void eline_mov_before(ScfEfunction* f, intptr_t dst, intptr_t src) -{ - if (dst == src) - return; - - ScfEline* el = f->elines[src]; - intptr_t i; - - for (i = src + 1; i < f->n_elines; i++) - f->elines[i - 1] = f->elines[i]; - - for (i = f->n_elines - 1; i > dst; i--) - f->elines[i] = f->elines[i - 1]; - - f->elines[dst] = el; - - scf_logd("f->elines[%ld]->id: %ld, f->elines[%ld]->id: %ld\n", src, f->elines[src]->id, dst, f->elines[dst]->id); -} - -static inline void eline_mov_after(ScfEfunction* f, intptr_t dst, intptr_t src) -{ - if (dst == src) - return; - - ScfEline* el = f->elines[src]; - intptr_t i; - - for (i = src + 1; i < f->n_elines; i++) - f->elines[i - 1] = f->elines[i]; - - for (i = f->n_elines - 1; i > dst + 1; i--) - f->elines[i] = f->elines[i - 1]; - - f->elines[dst + 1] = el; - - scf_logd("f->elines[%ld]->id: %ld, f->elines[%ld]->id: %ld\n", src, f->elines[src]->id, dst, f->elines[dst]->id); -} - -int _topo_print(scf_vector_t* paths); - -static void __ses_layout_path2(ScfEfunction* f, ses_path_t* path, ses_path_t* base) -{ - ScfEcomponent* c; - ScfEline* el; - ScfEpin* bp; - ScfEpin* p; - ScfEpin* pb; - ScfEpin* pe; - - intptr_t j; - intptr_t k; - intptr_t n; - intptr_t __n; - - bp = base->pins->data[base->pins->size - 1]; - __n = __ses_find_eline_index(f, bp->lid); - - scf_logd("path: %d, __n: %ld, l%ld\n", path->index, __n, f->elines[__n]->id); - - for (j = path->pins->size - 1; j >= 0; j--) { - p = path->pins->data[j]; - - scf_logd("path: %d, c%ldp%ld, __n: %ld, l%ld\n", path->index, p->cid, p->id, __n, f->elines[__n]->id); - - for (k = base->pins->size - 1; k >= 0; k--) { - bp = base->pins->data[k]; - - if (p->lid == bp->lid) { - __n = __ses_find_eline_index(f, bp->lid); - - scf_logd("__n: %ld, l%ld\n\n", __n, f->elines[__n]->id); - break; - } - } - - n = __ses_find_eline_index(f, p->lid); - - if (!f->elines[n]->vflag) { - f->elines[n]->vflag = 1; - - eline_mov_before(f, __n, n); - } - } -} - -static void __ses_layout_path(ScfEfunction* f, ses_path_t* path, ses_path_t* base) -{ - intptr_t i; - - __ses_layout_path2(f, path, base); - - scf_logd("path: %d, base: %d, ------------------------\n", path->index, base->index); - - base = path; - - if (base->childs) { - for (i = 0; i < base->childs->size; i++) { - path = base->childs->data[i]; - - __ses_layout_path(f, path, base); - } - } - - if (base->bridges) { - for (i = 0; i < base->bridges->size; i++) { - path = base->bridges->data[i]; - - __ses_layout_path(f, path, base); - } - } -} - -static int __ses_layout_lines4(ScfEfunction* f) -{ - scf_vector_t* paths; - ses_path_t* base; - ses_path_t* path; - - ScfEline* el; - ScfEpin* p; - - long i; - long j; - long n; - long __n; - - paths = scf_vector_alloc(); - if (!paths) - return -ENOMEM; - - int ret = ses_layout_paths(f, paths); - if (ret < 0) - goto end; - - scf_vector_qsort(paths, epath_cmp_pins); - - ses_paths_print(paths, f); - - for (i = 0; i < paths->size; i++) { - base = paths->data[i]; - - p = base->pins->data[0]; - - if (SCF_EDA_PIN_POS & f->elines[p->lid]->flags) - break; - } - - if (i >= paths->size) - goto end; - - for (j = 0; j < base->pins->size; j += 2) { - p = base->pins->data[j]; - - n = __ses_find_eline_index(f, p->lid); - - SCF_XCHG(f->elines[n], f->elines[j / 2]); - } - - p = base->pins->data[j - 1]; - n = __ses_find_eline_index(f, p->lid); - SCF_XCHG(f->elines[n], f->elines[j / 2]); - - for (i = 0; i < f->n_elines; i++) - f->elines[i]->vflag = 0; - - __ses_layout_path(f, base, base); - - for (i = 0; i < paths->size; i++) { - path = paths->data[i]; - - if (path == base) - continue; - - __ses_layout_path(f, path, base); - } - - ret = 0; -end: - scf_vector_clear(paths, ( void (*)(void*) )ses_path_free); - scf_vector_free(paths); - return ret; -} - -static int __ses_layout_lines2(ScfEfunction* f) -{ - ScfEline* tmp; - ScfEline* el0; - ScfEline* el1; - ScfEconn* ec; - - size_t i; - size_t j; - size_t m; - - if (f->n_elines <= 2) - return 0; - - __ses_layout_lines4(f); - -#if 1 - for (i = 0; i < f->n_elines; i++) { - el0 = f->elines[i]; - - if (el0->n_conns > 1) - continue; - assert(1 == el0->n_conns); - - for (j = i + 1; j < f->n_elines; j++) - f->elines[j - 1] = f->elines[j]; - - j = __ses_find_eline_index(f, el0->conns[0]->lid); - - el1 = f->elines[j]; - - for (m = f->n_elines - 1; m > j; m--) - f->elines[m] = f->elines[m - 1]; - - f->elines[j] = el0; - - if (j == i) - continue; - - scf_loge("mov el%ld [%ld] --> [%ld] el%ld\n", el0->id, i, j, el1->id); - } -#endif - - for (i = 0; i < f->n_elines; i++) { - el0 = f->elines[i]; - - el0->n_lines = 0; - - if (0 == i || i + 1 == f->n_elines) - el0->flags |= SCF_EDA_PIN_BORDER; - } - -#if 0 - for (i = 0; i < f->n_elines; i++) { - el0 = f->elines[i]; - - scf_logd("el0: %ld, n_conns: %ld, n_pins: %ld, flags: %#lx\n", el0->id, el0->n_conns, el0->n_pins, el0->flags); - - for (j = 0; j < el0->n_conns; j++) { - ec = el0->conns[j]; - - scf_logd("j: %ld, lid: %ld, n_cids: %ld, cid[0]: %ld\n", j, ec->lid, ec->n_cids, ec->cids[0]); - } - printf("\n"); - } -#endif - - return 0; -} - -static int __ses_layout_lines(ScfEfunction* f, int d) -{ - ScfEline* el; - ScfLine* l; - - long i; - - int ret = __ses_layout_lines2(f); - if (ret < 0) - return ret; - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - l = malloc(sizeof(ScfLine)); - if (!l) - return -ENOMEM; - - l->x0 = d; - l->x1 = d + l->x0; - l->y0 = d + i * d; - l->y1 = l->y0; - - if (scf_eline__add_line(el, l) < 0) { - free(l); - return -ENOMEM; - } - - if (f->h < l->y0) - f->h = l->y0; - } - - return 0; -} - -static void __ses_layout_components(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEline* el0; - ScfEline* el1; - ScfEpin* p0; - ScfEpin* p1; - - long i; - long j; - long m; - long n; - - for (i = 0; i < f->n_elines - 1; i++) { - el0 = f->elines[i]; - el1 = f->elines[i + 1]; - - m = 0; - n = 0; - j = 0; - while (m + 1 < el0->n_pins && n + 1 < el1->n_pins) { - - uint64_t cid0 = el0->pins[m]; - uint64_t cid1 = el1->pins[n]; - - if (el0->pins[m] < el1->pins[n]) - m += 2; - else if (el0->pins[m] > el1->pins[n]) - n += 2; - - else { - c = f->components[el0->pins[m]]; - - p0 = c->pins[el0->pins[m + 1]]; - p1 = c->pins[el1->pins[n + 1]]; - - p0->x = el0->lines[0]->x1 + j * d + rand() % 10; - p1->x = el1->lines[0]->x1 + j * d + rand() % 10; - p0->y = el0->lines[0]->y0; - p1->y = el1->lines[0]->y0; - - el0->lines[0]->x1 = p0->x; - el1->lines[0]->x1 = p1->x; - - if (f->w < el0->lines[0]->x1 - f->x) - f->w = el0->lines[0]->x1 - f->x; - - if (f->w < el1->lines[0]->x1 - f->x) - f->w = el1->lines[0]->x1 - f->x; - - m += 2; - n += 2; - j++; - } - } - } - - for (i = 0; i < f->n_elines; i++) { - el0 = f->elines[i]; - - for (m = 0; m + 1 < el0->n_pins; m += 2) { - - c = f->components[el0->pins[m]]; - p0 = c->pins [el0->pins[m + 1]]; - - if (0 == p0->x) { - - p0->x = el0->lines[0]->x1 + d + rand() % 10; - p0->y = el0->lines[0]->y1; - - el0->lines[0]->x1 = p0->x; - - if (f->w < el0->lines[0]->x1 - f->x) - f->w = el0->lines[0]->x1 - f->x; - } - } - } -} - -static void __ses_xchg_components(ScfEfunction* f, int d) -{ - ScfEcomponent* c0; - ScfEcomponent* c1; - ScfEline* el; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* p2; - ScfEpin* p3; - - long i; - long j; - long k; - long m; - long n; - long q; - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - for (m = 0; m + 3 < el->n_pins; m += 2) { - - c0 = f->components[el->pins[m]]; - p0 = c0->pins [el->pins[m + 1]]; - - for (j = 0; j < c0->n_pins; j++) { - p1 = c0->pins[j]; - - if (p1 == p0) - continue; - - for (n = 2; n + 1 < el->n_pins; n += 2) { - - c1 = f->components[el->pins[n]]; - p2 = c1->pins [el->pins[n + 1]]; - - for (k = 0; k < c1->n_pins; k++) { - p3 = c1->pins[k]; - - if (p3 == p2) - continue; - - if (p1->y < p0->y && p3->y > p0->y) - continue; - if (p1->y > p0->y && p3->y < p0->y) - continue; - - if (p1->y == p3->y) { - - if (p1->x < p3->x) { - if (p0->x > p2->x) - SCF_XCHG(p0->x, p2->x); - - } else if (p0->x < p2->x) - SCF_XCHG(p0->x, p2->x); - continue; - } - - if (p1->y < p0->y) { - - if (p1->y < p3->y) { - if (p0->x < p2->x) - SCF_XCHG(p0->x, p2->x); - - } else if (p0->x > p2->x) - SCF_XCHG(p0->x, p2->x); - - } else if (p1->y > p0->y) { - - if (p1->y > p3->y) { - if (p0->x < p2->x) - SCF_XCHG(p0->x, p2->x); - - } else if (p0->x > p2->x) { - SCF_XCHG(p0->x, p2->x); - scf_logd("c%ldp%ld-c%ldp%ld->x: %d, c%ldp%ld-c%ldp%ld->x: %d\n\n", - p0->cid, p0->id, p1->cid, p1->id, p0->x, - p2->cid, p2->id, p3->cid, p3->id, p2->x); - } - } - } - } - } - } - } -} - -static int __ses_get_crosses(ScfEfunction* f, int d, scf_vector_t* crosses) -{ - ses_vertex_t* edge0; - ses_vertex_t* edge1; - - ScfEcomponent* c0; - ScfEcomponent* c1; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* p2; - ScfEpin* p3; - - long i; - long j; - long k; - long m; - long n; - long q; - - for (i = 0; i < f->n_components - 1; i++) { - c0 = f->components[i]; - - for (j = 0; j < c0->n_pins - 1; j++) { - p0 = c0->pins[j]; - - for (k = j + 1; k < c0->n_pins; k++) { - p1 = c0->pins[k]; - - if (p0->y - p1->y <= d && p0->y - p1->y >= -d) - continue; - - int y0 = p0->y < p1->y ? p0->y : p1->y; - int y1 = p0->y < p1->y ? p1->y : p0->y; - - for (m = i + 1; m < f->n_components; m++) { - c1 = f->components[m]; - - for (n = 0; n < c1->n_pins - 1; n++) { - p2 = c1->pins[n]; - - if ((p0->x > 0 && p2->x < 0) || (p0->x < 0 && p2->x > 0)) - break; - - for (q = n + 1; q < c1->n_pins; q++) { - p3 = c1->pins[q]; - - if (p2->y - p3->y <= d && p2->y - p3->y >= -d) - continue; - - int y2 = p2->y < p3->y ? p2->y : p3->y; - int y3 = p2->y < p3->y ? p3->y : p2->y; - - if ((y0 < y2 && y2 < y1 && y1 < y3) || (y2 < y0 && y0 < y3 && y3 < y1)) { - - edge0 = ses_vertex_add(crosses, c0); - if (!edge0) - return -ENOMEM; - - edge1 = ses_vertex_add(crosses, c1); - if (!edge1) - return -ENOMEM; - - if (ses_vertex_connect(edge0, edge1) < 0) - return -ENOMEM; - goto next; - } - } - } -next: - c1 = NULL; - } - } - } - } - - scf_vector_qsort(crosses, ses_vertex_cmp_edges); - -#if 0 - for (i = 0; i < crosses->size; i++) { - edge0 = crosses->data[i]; - c0 = edge0->data; - - scf_logw("c%ld\n", c0->id); - - for (j = 0; j < edge0->edges->size; j++) { - edge1 = edge0->edges->data[j]; - c1 = edge1->data; - - scf_logi("j: %ld, c%ld\n", j, c1->id); - } - printf("\n"); - } - - scf_loge("crosses->size: %d\n\n", crosses->size); -#endif - - return 0; -} - -static int __ses_de_cross(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEline* el; - ScfEpin* p; - ScfLine* l0; - ScfLine* l; - - ses_vertex_t* v; - scf_vector_t* graph; - scf_vector_t* colors; - - graph = scf_vector_alloc(); - if (!graph) - return -ENOMEM; - - colors = scf_vector_alloc(); - if (!colors) { - scf_vector_free(graph); - return -ENOMEM; - } - - intptr_t N = 2; - intptr_t i; - intptr_t j; - intptr_t k; - - int ret = __ses_get_crosses(f, d, graph); - if (ret < 0) - return ret; - - if (0 < graph->size) { - v = graph->data[0]; - - N = v->edges->size + 1; - } - - for (j = 1; j <= N; j++) - scf_vector_add(colors, (void*)j); - - for (j = N; j >= 2; j--) { - - int ret = ses_graph_kcolor(graph, j, colors); - if (ret < 0) { - scf_loge("**********\n"); - } - - int n = 0; - for (i = 0; i < graph->size; i++) { - v = graph->data[i]; - - if (v->color < 0) { - c = v->data; - n++; - scf_loge("j: %ld, c%ld->color: %ld\n", j, c->id, v->color); - } - } - - if (n > 0) - break; - - for (i = 0; i < graph->size; i++) { - v = graph->data[i]; - - c = v->data; - c->color = v->color; - v->color = 0; - } - - scf_vector_del(colors, (void*)j); - } - - scf_vector_clear(graph, ( void (*)(void*) )ses_vertex_free); - scf_vector_free(graph); - graph = NULL; - - N = j + 1; - scf_vector_add(colors, (void*)N); - scf_vector_add(colors, (void*)0); - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - for (j = 0; j < colors->size; j++) - colors->data[j] = NULL; - - for (j = 0; j + 1 < el->n_pins; j += 2) { - c = f->components[el->pins[j]]; - - ++colors->data[c->color]; - } - - intptr_t _j = 0; - intptr_t _n = (intptr_t)colors->data[_j]; - - if (_n > 1) - continue; - - for (j = 1; j < colors->size; j++) { - - if (_n < (intptr_t)colors->data[j]) { - _n = (intptr_t)colors->data[j]; - _j = j; - } - } - - if (0 == _j) - continue; - - for (j = 0; j + 1 < el->n_pins; j += 2) { - c = f->components[el->pins[j]]; - - if (0 == c->color) { - scf_loge("c%ld->color: %ld --> %ld\n", c->id, c->color, _j); - c->color = _j; - } - } - } - - scf_vector_free(colors); - colors = NULL; - - int x1 = 0; - - for (j = 1; j <= N; j++) { - - intptr_t j0 = (j - 1) / 2; - intptr_t j1 = (j - 1) % 2; - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - if (0 == j0) - el->lines[0]->x1 = el->lines[0]->x0; - - else if (el->n_lines <= j0) { - - l0 = el->lines[0]; - - l = malloc(sizeof(ScfLine)); - if (!l) - return -ENOMEM; - - l->x0 = x1 + d; - l->x1 = l->x0; - l->y0 = l0->y0; - l->y1 = l0->y1; - - if (scf_eline__add_line(el, l) < 0) { - free(l); - return -ENOMEM; - } - } - - for (k = 0; k + 1 < el->n_pins; k += 2) { - - c = f->components[el->pins[k]]; - p = c->pins [el->pins[k + 1]]; - - if ((c->color - 1) / 2 != j0) - continue; - - l = el->lines[j0]; - p->x = l->x1 + d; - l->x1 = p->x; - - if (x1 < l->x1) - x1 = l->x1; - } - } - } - - for (i = 0; i < f->n_components; i++) { - c = f->components[i]; - scf_logi("N: %ld, i: %ld, c%ld->color: %ld\n", N, i, c->id, c->color); - } - - return 0; -} - -static void __ses_set_xy(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* p2; - - long i; - long j; - - for (i = 0; i < f->n_components; i++) { - c = f->components[i]; - - p0 = c->pins[0]; - p1 = c->pins[1]; - - c->x = (p0->x + p1->x) / 2; - c->y = (p0->y + p1->y) / 2; - - p0->x = c->x; - - if (2 == c->n_pins) { - p1->x = c->x; - continue; - } - - int n = 0; - if (c->color > 0) - n = (c->color - 1) % 2; - - switch (c->type) { - case SCF_EDA_NPN: - case SCF_EDA_PNP: - p0 = c->pins[SCF_EDA_NPN_C]; - p1 = c->pins[SCF_EDA_NPN_E]; - - p0->x = c->x + d / 2; - p1->x = c->x - d / 2; - break; - - case SCF_EDA_NAND: - case SCF_EDA_NOR: - p1->x = c->x; - - p0 = c->pins[SCF_EDA_NAND_IN0]; - p1 = c->pins[SCF_EDA_NAND_IN1]; - p2 = c->pins[SCF_EDA_NAND_OUT]; - - if (p0->y > p1->y) - SCF_XCHG(p0, p1); - - if (0 == n) { - if (c->y < p1->y) { - p0->x = c->x + d * 7 / 8; - p1->x = c->x + d / 8; - } else { - p0->x = c->x + d / 8; - p1->x = c->x + d * 7 / 8; - } - - p2->x = c->x - d * 7 / 8; - } else { - if (c->y < p1->y) { - p0->x = c->x - d * 7 / 8; - p1->x = c->x - d / 8; - } else { - p0->x = c->x - d / 8; - p1->x = c->x - d * 7 / 8; - } - - p2->x = c->x + d * 7 / 8; - } - break; - - case SCF_EDA_NOT: - p1->x = c->x; - - p0 = c->pins[SCF_EDA_NOT_IN]; - p1 = c->pins[SCF_EDA_NOT_OUT]; - - if (c->x < p1->x) { - p0->x = c->x - d * 7 / 8; - p1->x = c->x + d * 7 / 8; - } else { - p0->x = c->x + d * 7 / 8; - p1->x = c->x - d * 7 / 8; - } - break; - default: - break; - }; - } -} - -static inline void __ses_xchg_cx2(ScfEcomponent* c0, ScfEcomponent* c1) -{ - ScfEpin* p; - size_t i; - - int cx0 = c0->x; - int cx1 = c1->x; - - SCF_XCHG(c0->x, c1->x); - - scf_logd("c%ld <--> c%ld, color: %ld, %ld, cx: %d, %d\n", c0->id, c1->id, c0->color, c1->color, c0->x, c1->x); - - for (i = 0; i < c0->n_pins; i++) { - p = c0->pins[i]; - p->x += c0->x - cx0; - } - - for (i = 0; i < c1->n_pins; i++) { - p = c1->pins[i]; - p->x += c1->x - cx1; - } -} - -static void __ses_xchg_cx(ScfEfunction* f, int d) -{ - ScfEcomponent* c0; - ScfEcomponent* c1; - ScfEpin* p; - - size_t i; - size_t j; - size_t k; - size_t n; - - for (i = 0; i < f->n_components - 1; i++) { - c0 = f->components[i]; - - int m0 = 0; - int n0 = 0; - - if (c0->color > 0) { - m0 = (c0->color - 1) / 2; - n0 = (c0->color - 1) % 2; - } - - for (j = i + 1; j < f->n_components; j++) { - c1 = f->components[j]; - - int y2 = INT_MAX; - int y3 = INT_MIN; - int m1 = 0; - int n1 = 0; - - if (c1->color > 0) { - m1 = (c1->color - 1) / 2; - n1 = (c1->color - 1) % 2; - } - - if (m0 != m1) - continue; - - if ((n0 < n1 && c0->x > c1->x) || (n0 > n1 && c0->x < c1->x)) - __ses_xchg_cx2(c0, c1); - } - } - - do { - n = 0; - - for (i = 0; i < f->n_components - 1; i++) { - c0 = f->components[i]; - - int y0 = INT_MAX; - int y1 = INT_MIN; - int m0 = 0; - int n0 = 0; - - if (c0->color > 0) { - m0 = (c0->color - 1) / 2; - n0 = (c0->color - 1) % 2; - } - - for (k = 0; k < c0->n_pins; k++) { - p = c0->pins[k]; - - if (y0 > p->y) - y0 = p->y; - - if (y1 < p->y) - y1 = p->y; - } - - for (j = i + 1; j < f->n_components; j++) { - c1 = f->components[j]; - - int y2 = INT_MAX; - int y3 = INT_MIN; - int m1 = 0; - int n1 = 0; - - if (c1->color > 0) { - m1 = (c1->color - 1) / 2; - n1 = (c1->color - 1) % 2; - } - - if (m0 != m1 || n0 != n1) - continue; - - for (k = 0; k < c1->n_pins; k++) { - p = c1->pins[k]; - - if (y2 > p->y) - y2 = p->y; - - if (y3 < p->y) - y3 = p->y; - } - - if ((y0 <= y2 && y3 < y1) || (y0 < y2 && y3 <= y1)) { - - if ((0 == n0 && c0->x > c1->x) || (1 == n0 && c0->x < c1->x)) { - __ses_xchg_cx2(c0, c1); - n++; - } - - } else if ((y2 <= y0 && y1 < y3) || (y2 < y0 && y1 <= y3)) { - - if ((0 == n0 && c0->x < c1->x) || (1 == n0 && c0->x > c1->x)) { - __ses_xchg_cx2(c0, c1); - n++; - } - } - } - } - } while (n > 0); -} - -static void __ses_set_cx(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEcomponent* c2; - ScfEline* el; - ScfEpin* p; - ScfEpin* p2; - - long i; - long j; - long k; - - qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); - for (i = 1; i < f->n_components; i++) { - c = f->components[i]; - c2 = f->components[i - 1]; - - int tmp = c->x; - - if (SCF_EDA_NPN == c->type - || SCF_EDA_NPN == c2->type - || SCF_EDA_PNP == c->type || SCF_EDA_PNP == c2->type - || SCF_EDA_NAND == c->type || SCF_EDA_NAND == c2->type - || SCF_EDA_NOR == c->type || SCF_EDA_NOR == c2->type - || SCF_EDA_NOT == c->type || SCF_EDA_NOT == c2->type) - c->x = c2->x + d * 2; - else - c->x = c2->x + d; - - for (k = 0; k < c->n_pins; k++) { - p = c->pins[k]; - p->x += c->x - tmp; - } - } - - for (i = 0; i < f->n_components; i++) { - c = f->components[i]; - - for (j = 0; j < f->n_elines; j++) { - el = f->elines[j]; - - if (c->y - d / 4 < el->lines[0]->y0 && el->lines[0]->y0 < c->y + d / 4) - c->y -= d / 3; - } - } - - qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_id); -} - -static void __ses_min_cx(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEcomponent* c2; - ScfEpin* p; - ScfEpin* p2; - - long i; - long j; - long k; - long m; - - qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); - - for (i = 1; i < f->n_components; i++) { - c = f->components[i]; - - int tmp = c->x; - int max = 0; - int mt = 0; - int m0 = 0; - - if (c->color > 0) - m0 = (c->color - 1) / 2; - - int y0 = INT_MAX; - int y1 = 0; - - for (k = 0; k < c->n_pins; k++) { - p = c->pins[k]; - - if (y0 > p->y) - y0 = p->y; - - if (y1 < p->y) - y1 = p->y; - } - - for (j = i - 1; j >= 0; j--) { - c2 = f->components[j]; - - int m1 = 0; - - if (c2->color > 0) - m1 = (c2->color - 1) / 2; - - if (m0 != m1) - continue; - - for (k = 0; k < c->n_pins; k++) { - p = c->pins[k]; - - for (m = 0; m < c2->n_pins; m++) { - p2 = c2->pins[m]; - - if (p->y == p2->y) { - if ((c->y >= p->y && c2->y >= p->y) || (c->y <= p->y && c2->y <= p->y)) - goto _max; - - scf_logd("c%ld->x: %d, c%ld->x: %d\n", c->id, c->x, c2->id, c2->x); - goto _next; - } - } - } - - int y2 = INT_MAX; - int y3 = 0; - - for (m = 0; m < c2->n_pins; m++) { - p2 = c2->pins[m]; - - if (y2 > p2->y) - y2 = p2->y; - - if (y3 < p2->y) - y3 = p2->y; - } - - if (!(y1 <= y2 || y0 >= y3)) - goto _max; -_next: - continue; -_max: - if (max < c2->x) { - max = c2->x; - mt = c2->type; - } - } - - if (0 == max) - continue; - - if (SCF_EDA_NPN == c->type - || SCF_EDA_NPN == mt - || SCF_EDA_PNP == c->type || SCF_EDA_PNP == mt - || SCF_EDA_NAND == c->type || SCF_EDA_NAND == mt - || SCF_EDA_NOR == c->type || SCF_EDA_NOR == mt - || SCF_EDA_NOT == c->type || SCF_EDA_NOT == mt) - c->x = max + d * 2; - else - c->x = max + d; - - for (k = 0; k < c->n_pins; k++) { - p = c->pins[k]; - p->x += c->x - tmp; - } - } - - qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); - - for (i = 1; i < f->n_components; i++) { - c = f->components[i]; - c2 = f->components[i - 1]; - - int tmp = c->x; - if (tmp - c2->x > d) { - - for (j = i; j < f->n_components; j++) { - c = f->components[j]; - - if (c->x > tmp) - break; - - if (SCF_EDA_NPN == c->type - || SCF_EDA_NPN == c2->type - || SCF_EDA_PNP == c->type || SCF_EDA_PNP == c2->type - || SCF_EDA_NAND == c->type || SCF_EDA_NAND == c2->type - || SCF_EDA_NOR == c->type || SCF_EDA_NOR == c2->type - || SCF_EDA_NOT == c->type || SCF_EDA_NOT == c2->type) - c->x = c2->x + d * 2; - else - c->x = c2->x + d; - - for (k = 0; k < c->n_pins; k++) { - p = c->pins[k]; - p->x += c->x - tmp; - } - } - } - } - - qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_id); -} - -static void __ses_xchg_ce(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEpin* pb; - ScfEpin* pe; - ScfEpin* pc; - - int64_t i; - int64_t j; - - assert(SCF_EDA_NPN_B == SCF_EDA_PNP_B); - assert(SCF_EDA_NPN_C == SCF_EDA_PNP_C); - assert(SCF_EDA_NPN_E == SCF_EDA_PNP_E); - - for (i = 0; i < f->n_components; i++) { - c = f->components[i]; - - if (SCF_EDA_NPN != c->type && SCF_EDA_PNP != c->type) - continue; - - j = 0; - - if (c->color > 0) - j = (c->color - 1) % 2; - - pb = c->pins[SCF_EDA_NPN_B]; - pc = c->pins[SCF_EDA_NPN_C]; - pe = c->pins[SCF_EDA_NPN_E]; - - if (pc->y > pe->y) - SCF_XCHG(pc, pe); - - if (pc->y > pb->y) { - - if ((0 == j && pc->x < pe->x) || (1 == j && pc->x > pe->x)) - SCF_XCHG(pc->x, pe->x); - - } else if (pe->y < pb->y) { - - if ((0 == j && pc->x > pe->x) || (1 == j && pc->x < pe->x)) - SCF_XCHG(pc->x, pe->x); - - } else if (pc->y < pb->y) { - - pc = c->pins[SCF_EDA_NPN_C]; - pe = c->pins[SCF_EDA_NPN_E]; - - if ((0 == j && pc->x > pb->x) || (1 == j && pc->x < pb->x)) - SCF_XCHG(pc->x, pe->x); - } - - pc = c->pins[SCF_EDA_NPN_C]; - pe = c->pins[SCF_EDA_NPN_E]; - - if (pc->x < c->x) { - pc->x = c->x - d * 7 / 8; - pe->x = c->x + d * 7 / 8; - } else { - pc->x = c->x + d * 7 / 8; - pe->x = c->x - d * 7 / 8; - } - } -} - -int ses_layout_function(ScfEfunction* f, int d) -{ - ScfEcomponent* c; - ScfEcomponent* c2; - ScfEline* el; - ScfEline* el2; - ScfEpin* p0; - ScfEpin* p1; - - size_t i; - size_t j; - size_t k; - - f->x = 0; - f->y = 0; - f->w = 0; - f->h = 0; - - int ret = __ses_layout_lines(f, d); - if (ret < 0) - return ret; - - __ses_layout_components(f, d); - __ses_xchg_components(f, d); - - qsort(f->elines, f->n_elines, sizeof(ScfEline*), eline_cmp_id); - - ret = __ses_de_cross(f, d); - if (ret < 0) - return ret; - - __ses_set_xy(f, d); - __ses_set_cx(f, d); - __ses_xchg_cx(f, d); - __ses_min_cx(f, d); - __ses_xchg_ce(f, d); - - int tx0 = INT_MAX; - int tx1 = 0; - - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - - for (j = 0; j < el->n_lines; j++) { - el->lines[j]->x0 = INT_MAX; - el->lines[j]->x1 = 0; - } - - for (j = 0; j < el->n_pins; j += 2) { - - c = f->components[el->pins[j]]; - p0 = c->pins [el->pins[j + 1]]; - - if (tx0 > p0->x) - tx0 = p0->x; - - if (tx1 < p0->x) - tx1 = p0->x; - - intptr_t k = (c->color - 1) / 2; - - if (el->lines[k]->x0 > p0->x) - el->lines[k]->x0 = p0->x; - - if (el->lines[k]->x1 < p0->x) - el->lines[k]->x1 = p0->x; - } - - for (j = 0; j < el->n_lines; j++) - scf_logd("l%ld->lines[%ld]: x0: %d, x1: %d\n", el->id, j, el->lines[j]->x0, el->lines[j]->x1); -// printf("\n"); - } - - f->w = tx1 + d * 2; - f->h += d; - - scf_logi("f->x: %d, y: %d, w: %d, h: %d, tx0: %d, tx1: %d\n", f->x, f->y, f->w, f->h, tx0, tx1); - return 0; -} - int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_t bh) { - ScfEcomponent* c; ScfEfunction* f; ScfEline* el; - ScfEpin* p; - ScfEpin* pb; - ScfEpin* pc; - ScfEpin* pe; ScfLine* l; cairo_surface_t* surface; @@ -1562,14 +43,17 @@ int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_ SHOW_COLOR(cr, 0.8, 0, 0); else if (SCF_EDA_PIN_IN & el->flags) - SHOW_COLOR(cr, 0, 0, 0.8); + SHOW_COLOR(cr, 1.0, 0.6, 0.07); - else if (SCF_EDA_PIN_CONST & el->flags) - SHOW_COLOR(cr, 0, 0.6, 0); + else if (SCF_EDA_PIN_DIV0 & el->flags) + SHOW_COLOR(cr, 0, 1, 0); else if (SCF_EDA_PIN_OUT & el->flags) SHOW_COLOR(cr, 1, 0, 1); + else if (SCF_EDA_PIN_SHIFT & el->flags) + SHOW_COLOR(cr, 0.5, 0, 0.5); + else if (SCF_EDA_PIN_CF & el->flags) SHOW_COLOR(cr, 0.8, 0, 0.8); else @@ -1578,7 +62,7 @@ int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_ uint8_t text[64]; cairo_select_font_face(cr, "Calibri", CAIRO_FONT_SLANT_NORMAL, CAIRO_FONT_WEIGHT_BOLD); - cairo_set_font_size (cr, 28); + cairo_set_font_size (cr, 26); ScfLine* prev = NULL; @@ -1593,6 +77,23 @@ int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_ cairo_move_to (cr, l->x0 - 10 - n * 14, l->y0 + 10); cairo_show_text(cr, text); + cairo_stroke(cr); + + if (el->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_OUT | SCF_EDA_PIN_DIV0 | SCF_EDA_PIN_SHIFT)) { + cairo_set_font_size(cr, 22); + + if (el->flags & SCF_EDA_PIN_DIV0) + n = snprintf(text, sizeof(text) - 1, "DIV0"); + + else if (el->flags & SCF_EDA_PIN_SHIFT) + n = snprintf(text, sizeof(text) - 1, "T%ld", el->io_lid); + else + n = snprintf(text, sizeof(text) - 1, "B%ld", el->io_lid); + + cairo_move_to (cr, l->x0 - 8 - n * 13, l->y0 + 36); + cairo_show_text(cr, text); + cairo_stroke(cr); + } } cairo_set_line_width(cr, 3); @@ -1602,7 +103,7 @@ int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_ if (prev) { if (!(el->flags & SCF_EDA_PIN_BORDER)) - cairo_set_line_width(cr, 1); + cairo_set_line_width(cr, 1.5); cairo_move_to(cr, prev->x0, prev->y0); cairo_line_to(cr, l->x0, l->y0); @@ -1633,26 +134,18 @@ int ses_layout_draw(ScfEboard* b, uint32_t bx, uint32_t by, uint32_t bw, uint32_ int ses_layout_board(ScfEboard* b, int d) { ScfEfunction* f; - scf_vector_t* loops; - size_t i; - size_t j; - size_t k; - - int x = 0; - int y = 0; - int w = 0; - int h = 0; + long i; + int x = 0; + int y = 0; + int w = 0; + int h = 0; for (i = 0; i < b->n_functions; i++) { f = b->functions[i]; printf("f: %s\n", f->name); - scf_pins_same_line(f); - - ses_lines_same_components(f); - int ret = ses_layout_function(f, d); if (ret < 0) { scf_loge("\n"); @@ -1666,6 +159,5 @@ int ses_layout_board(ScfEboard* b, int d) } ses_layout_draw(b, x, y, w, h); - return 0; } diff --git a/ses_layout_function.c b/ses_layout_function.c new file mode 100644 index 0000000..95c8334 --- /dev/null +++ b/ses_layout_function.c @@ -0,0 +1,1588 @@ +#include"ses_core.h" +#include"ses_graph.h" + +static inline int LAYOUT_P0(ScfEcomponent* c) +{ + int k = 0; + switch (c->type) { + case SCF_EDA_NAND: + case SCF_EDA_NOT: + case SCF_EDA_NOR: + case SCF_EDA_XOR: + case SCF_EDA_OR: + case SCF_EDA_AND: + case SCF_EDA_ADD: + k = 2; + break; + default: + k = 0; + break; + }; + return k; +} + +int epin_cmp_color(const void* v0, const void* v1, void* arg) +{ + const uint64_t* t0 = v0; + const uint64_t* t1 = v1; + + ScfEfunction* f = arg; + ScfEcomponent* c0 = f->components[t0[0]]; + ScfEcomponent* c1 = f->components[t1[0]]; + + if (c0->color < c1->color) + return -1; + + if (c0->color > c1->color) + return 1; + return 0; +} + +int epin_cmp_cx(const void* v0, const void* v1, void* arg) +{ + const uint64_t* t0 = v0; + const uint64_t* t1 = v1; + + ScfEfunction* f = arg; + ScfEcomponent* c0 = f->components[t0[0]]; + ScfEcomponent* c1 = f->components[t1[0]]; + + if (c0->x < c1->x) + return -1; + + if (c0->x > c1->x) + return 1; + return 0; +} + +int econn_cmp(const void* v0, const void* v1) +{ + const ScfEconn* ec0 = *(const ScfEconn**)v0; + const ScfEconn* ec1 = *(const ScfEconn**)v1; + + if (ec0->n_cids < ec1->n_cids) + return 1; + + if (ec0->n_cids > ec1->n_cids) + return -1; + return 0; +} + +int eline_cmp(const void* v0, const void* v1) +{ + const ScfEline* el0 = *(const ScfEline**)v0; + const ScfEline* el1 = *(const ScfEline**)v1; + + if (el0->n_conns < el1->n_conns) + return 1; + + if (el0->n_conns > el1->n_conns) + return -1; + + if (el0->n_pins < el1->n_pins) + return 1; + + if (el0->n_pins > el1->n_pins) + return -1; + return 0; +} + +int eline_cmp_id(const void* v0, const void* v1) +{ + const ScfEline* el0 = *(const ScfEline**)v0; + const ScfEline* el1 = *(const ScfEline**)v1; + + if (el0->id < el1->id) + return -1; + + if (el0->id > el1->id) + return 1; + return 0; +} + +int ecomponent_cmp_id(const void* v0, const void* v1) +{ + const ScfEcomponent* c0 = *(const ScfEcomponent**)v0; + const ScfEcomponent* c1 = *(const ScfEcomponent**)v1; + + if (c0->id < c1->id) + return -1; + + if (c0->id > c1->id) + return 1; + return 0; +} + +int ecomponent_cmp_cx(const void* v0, const void* v1) +{ + const ScfEcomponent* c0 = *(const ScfEcomponent**)v0; + const ScfEcomponent* c1 = *(const ScfEcomponent**)v1; + + if (c0->x < c1->x) + return -1; + + if (c0->x > c1->x) + return 1; + return 0; +} + +static inline int __ses_find_eline_index(ScfEfunction* f, uint64_t lid) +{ + ScfEline* el; + size_t j; + + for (j = 0; j < f->n_elines; j++) { + el = f->elines[j]; + + if (el->id == lid) + break; + } + assert(j < f->n_elines); + + return j; +} + +int ses_lines_same_components(ScfEfunction* f) +{ + ScfEline* el0; + ScfEline* el1; + ScfEconn* ec; + + long i; + long j; + long k0; + long k1; + + ec = NULL; + + for (i = 0; i < f->n_elines; i++) { + el0 = f->elines[i]; + + for (j = 0; j < f->n_elines; j++) { + el1 = f->elines[j]; + + if (el0 == el1) + continue; + + k0 = 0; + k1 = 0; + + if (!ec) { + ec = scf_econn__alloc(); + if (!ec) + return -ENOMEM; + } + + assert(0 == ec->n_cids); + + while (k0 + 1 < el0->n_pins && k1 + 1 < el1->n_pins) { + + ScfEcomponent* c0 = f->components[el0->pins[k0]]; + ScfEcomponent* c1 = f->components[el1->pins[k1]]; + uint64_t p0 = el0->pins[k0 + 1]; + uint64_t p1 = el1->pins[k1 + 1]; + + if (p0 < LAYOUT_P0(c0)) { + k0 += 2; + continue; + } + + if (p1 < LAYOUT_P0(c1)) { + k1 += 2; + continue; + } + + if (c0->id < c1->id) + k0 += 2; + else if (c0->id > c1->id) + k1 += 2; + else { + k0 += 2; + k1 += 2; + + if (scf_econn__add_cid(ec, c0->id) < 0) { + ScfEconn_free(ec); + return -ENOMEM; + } + } + } + + if (0 == ec->n_cids) + continue; + + ec->lid = el1->id; + + if (scf_eline__add_conn(el0, ec) < 0) { + ScfEconn_free(ec); + return -ENOMEM; + } + + ec = NULL; + } + + qsort(el0->conns, el0->n_conns, sizeof(ScfEconn*), econn_cmp); + } + + if (ec) { + ScfEconn_free(ec); + ec = NULL; + } + + return 0; +} + +int epath_cmp_pins(const void* v0, const void* v1) +{ + const ses_path_t* p0 = *(const ses_path_t**)v0; + const ses_path_t* p1 = *(const ses_path_t**)v1; + + if (p0->pins->size > p1->pins->size) + return -1; + + if (p0->pins->size < p1->pins->size) + return 1; + return 0; +} + +static inline void eline_mov_before(ScfEfunction* f, intptr_t dst, intptr_t src) +{ + if (dst == src) + return; + + ScfEline* el = f->elines[src]; + intptr_t i; + + for (i = src + 1; i < f->n_elines; i++) + f->elines[i - 1] = f->elines[i]; + + for (i = f->n_elines - 1; i > dst; i--) + f->elines[i] = f->elines[i - 1]; + + f->elines[dst] = el; + + scf_logd("f->elines[%ld]->id: %ld, f->elines[%ld]->id: %ld\n", src, f->elines[src]->id, dst, f->elines[dst]->id); +} + +static inline void eline_mov_after(ScfEfunction* f, intptr_t dst, intptr_t src) +{ + if (dst == src) + return; + + ScfEline* el = f->elines[src]; + intptr_t i; + + for (i = src + 1; i < f->n_elines; i++) + f->elines[i - 1] = f->elines[i]; + + for (i = f->n_elines - 1; i > dst + 1; i--) + f->elines[i] = f->elines[i - 1]; + + f->elines[dst + 1] = el; + + scf_logd("f->elines[%ld]->id: %ld, f->elines[%ld]->id: %ld\n", src, f->elines[src]->id, dst, f->elines[dst]->id); +} + +int _topo_print(scf_vector_t* paths); + +static void __ses_layout_path2(ScfEfunction* f, ses_path_t* path, ses_path_t* base) +{ + ScfEpin* bp; + ScfEpin* p; + + intptr_t j; + intptr_t k; + intptr_t n; + intptr_t __n; + + bp = base->pins->data[base->pins->size - 1]; + __n = __ses_find_eline_index(f, bp->lid); + + scf_logd("path: %d, __n: %ld, l%ld\n", path->index, __n, f->elines[__n]->id); + + for (j = path->pins->size - 1; j >= 0; j--) { + p = path->pins->data[j]; + + scf_logd("path: %d, c%ldp%ld, __n: %ld, l%ld\n", path->index, p->cid, p->id, __n, f->elines[__n]->id); + + for (k = base->pins->size - 1; k >= 0; k--) { + bp = base->pins->data[k]; + + if (p->lid == bp->lid) { + __n = __ses_find_eline_index(f, bp->lid); + + scf_logd("__n: %ld, l%ld\n\n", __n, f->elines[__n]->id); + break; + } + } + + n = __ses_find_eline_index(f, p->lid); + + if (!f->elines[n]->vflag) { + f->elines[n]->vflag = 1; + + eline_mov_before(f, __n, n); + } + } +} + +static void __ses_layout_path(ScfEfunction* f, ses_path_t* path, ses_path_t* base) +{ + intptr_t i; + + __ses_layout_path2(f, path, base); + + scf_logd("path: %d, base: %d, ------------------------\n", path->index, base->index); + + base = path; + + if (base->childs) { + for (i = 0; i < base->childs->size; i++) { + path = base->childs->data[i]; + + __ses_layout_path(f, path, base); + } + } + + if (base->bridges) { + for (i = 0; i < base->bridges->size; i++) { + path = base->bridges->data[i]; + + __ses_layout_path(f, path, base); + } + } +} + +static int __ses_layout_lines4(ScfEfunction* f) +{ + scf_vector_t* paths; + ses_path_t* base; + ses_path_t* path; + ScfEpin* p; + + long i; + long j; + long n; + + paths = scf_vector_alloc(); + if (!paths) + return -ENOMEM; + + int ret = ses_layout_paths(f, paths); + if (ret < 0) + goto end; + + scf_vector_qsort(paths, epath_cmp_pins); + + ses_paths_print(paths); + + for (i = 0; i < paths->size; i++) { + base = paths->data[i]; + + p = base->pins->data[0]; + + if (SCF_EDA_PIN_POS & f->elines[p->lid]->flags) + break; + } + + if (i >= paths->size) + goto end; + + for (j = 0; j < base->pins->size; j += 2) { + p = base->pins->data[j]; + + n = __ses_find_eline_index(f, p->lid); + + SCF_XCHG(f->elines[n], f->elines[j / 2]); + } + + p = base->pins->data[j - 1]; + n = __ses_find_eline_index(f, p->lid); + SCF_XCHG(f->elines[n], f->elines[j / 2]); + + for (i = 0; i < f->n_elines; i++) + f->elines[i]->vflag = 0; + + __ses_layout_path(f, base, base); + + for (i = 0; i < paths->size; i++) { + path = paths->data[i]; + + if (path == base) + continue; + + __ses_layout_path(f, path, base); + } + + ret = 0; +end: + scf_vector_clear(paths, ( void (*)(void*) )ses_path_free); + scf_vector_free(paths); + return ret; +} + +static int __ses_layout_lines2(ScfEfunction* f) +{ + ScfEline* el0; + ScfEline* el1; + + size_t i; + size_t j; + size_t m; + + if (f->n_elines <= 2) + return 0; + + __ses_layout_lines4(f); + +#if 1 + for (i = 0; i < f->n_elines; i++) { + el0 = f->elines[i]; + + if (el0->flags & (SCF_EDA_PIN_POS | SCF_EDA_PIN_NEG)) + continue; + + uint64_t lid; + + if (el0->n_conns > 1) { + if (el0->n_pins > 2) + continue; + + int max = 0; + + for (j = 0; j < el0->n_conns; j++) { + + int k = __ses_find_eline_index(f, el0->conns[j]->lid); + if (max < k) { + max = k; + lid = el0->conns[j]->lid; + } + } + } else { + assert(el0->n_conns > 0); + lid = el0->conns[0]->lid; + } + + for (j = i + 1; j < f->n_elines; j++) + f->elines[j - 1] = f->elines[j]; + + j = __ses_find_eline_index(f, lid); + + el1 = f->elines[j]; + + for (m = f->n_elines - 1; m > j; m--) + f->elines[m] = f->elines[m - 1]; + + f->elines[j] = el0; + + if (j == i) + continue; + + scf_logw("mov el%ld [%ld] --> [%ld] el%ld\n", el0->id, i, j, el1->id); + } +#endif + + for (i = 0; i < f->n_elines; i++) { + el0 = f->elines[i]; + + el0->n_lines = 0; + + if (0 == i || i + 1 == f->n_elines) + el0->flags |= SCF_EDA_PIN_BORDER; + } + +#if 0 + for (i = 0; i < f->n_elines; i++) { + el0 = f->elines[i]; + + scf_logd("el0: %ld, n_conns: %ld, n_pins: %ld, flags: %#lx\n", el0->id, el0->n_conns, el0->n_pins, el0->flags); + + for (j = 0; j < el0->n_conns; j++) { + ec = el0->conns[j]; + + scf_logd("j: %ld, lid: %ld, n_cids: %ld, cid[0]: %ld\n", j, ec->lid, ec->n_cids, ec->cids[0]); + } + printf("\n"); + } +#endif + + return 0; +} + +static int __ses_layout_lines(ScfEfunction* f, int d) +{ + ScfEline* el; + ScfLine* l; + + long i; + + int ret = __ses_layout_lines2(f); + if (ret < 0) + return ret; + + for (i = 0; i < f->n_elines; i++) { + el = f->elines[i]; + + l = malloc(sizeof(ScfLine)); + if (!l) + return -ENOMEM; + + l->x0 = d; + l->x1 = d + l->x0; + l->y0 = d + i * d; + l->y1 = l->y0; + + if (scf_eline__add_line(el, l) < 0) { + free(l); + return -ENOMEM; + } + + if (f->h < l->y0) + f->h = l->y0; + } + + return 0; +} + +static void __ses_layout_components(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEline* el0; + ScfEline* el1; + ScfEpin* p0; + ScfEpin* p1; + + long i; + long j; + long m; + long n; + + for (i = 0; i < f->n_elines - 1; i++) { + el0 = f->elines[i]; + el1 = f->elines[i + 1]; + + m = 0; + n = 0; + j = 0; + while (m + 1 < el0->n_pins && n + 1 < el1->n_pins) { + + if (el0->pins[m] < el1->pins[n]) + m += 2; + else if (el0->pins[m] > el1->pins[n]) + n += 2; + + else { + c = f->components[el0->pins[m]]; + + p0 = c->pins[el0->pins[m + 1]]; + p1 = c->pins[el1->pins[n + 1]]; + + p0->x = el0->lines[0]->x1 + j * d + rand() % 10; + p1->x = el1->lines[0]->x1 + j * d + rand() % 10; + p0->y = el0->lines[0]->y0; + p1->y = el1->lines[0]->y0; + + el0->lines[0]->x1 = p0->x; + el1->lines[0]->x1 = p1->x; + + if (f->w < el0->lines[0]->x1 - f->x) + f->w = el0->lines[0]->x1 - f->x; + + if (f->w < el1->lines[0]->x1 - f->x) + f->w = el1->lines[0]->x1 - f->x; + + m += 2; + n += 2; + j++; + } + } + } + + for (i = 0; i < f->n_elines; i++) { + el0 = f->elines[i]; + + for (m = 0; m + 1 < el0->n_pins; m += 2) { + + c = f->components[el0->pins[m]]; + p0 = c->pins [el0->pins[m + 1]]; + + if (0 == p0->x) { + + p0->x = el0->lines[0]->x1 + d + rand() % 10; + p0->y = el0->lines[0]->y1; + + el0->lines[0]->x1 = p0->x; + + if (f->w < el0->lines[0]->x1 - f->x) + f->w = el0->lines[0]->x1 - f->x; + } + } + } +} + +static void __ses_xchg_components(ScfEfunction* f, int d) +{ + ScfEcomponent* c0; + ScfEcomponent* c1; + ScfEline* el; + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + + long i; + long j; + long k; + long m; + long n; + + for (i = 0; i < f->n_elines; i++) { + el = f->elines[i]; + + for (m = 0; m + 3 < el->n_pins; m += 2) { + + c0 = f->components[el->pins[m]]; + p0 = c0->pins [el->pins[m + 1]]; + + for (j = 0; j < c0->n_pins; j++) { + p1 = c0->pins[j]; + + if (p1 == p0) + continue; + + for (n = 2; n + 1 < el->n_pins; n += 2) { + + c1 = f->components[el->pins[n]]; + p2 = c1->pins [el->pins[n + 1]]; + + for (k = 0; k < c1->n_pins; k++) { + p3 = c1->pins[k]; + + if (p3 == p2) + continue; + + if (p1->y < p0->y && p3->y > p0->y) + continue; + if (p1->y > p0->y && p3->y < p0->y) + continue; + + if (p1->y == p3->y) { + + if (p1->x < p3->x) { + if (p0->x > p2->x) + SCF_XCHG(p0->x, p2->x); + + } else if (p0->x < p2->x) + SCF_XCHG(p0->x, p2->x); + continue; + } + + if (p1->y < p0->y) { + + if (p1->y < p3->y) { + if (p0->x < p2->x) + SCF_XCHG(p0->x, p2->x); + + } else if (p0->x > p2->x) + SCF_XCHG(p0->x, p2->x); + + } else if (p1->y > p0->y) { + + if (p1->y > p3->y) { + if (p0->x < p2->x) + SCF_XCHG(p0->x, p2->x); + + } else if (p0->x > p2->x) { + SCF_XCHG(p0->x, p2->x); + scf_logd("c%ldp%ld-c%ldp%ld->x: %d, c%ldp%ld-c%ldp%ld->x: %d\n\n", + p0->cid, p0->id, p1->cid, p1->id, p0->x, + p2->cid, p2->id, p3->cid, p3->id, p2->x); + } + } + } + } + } + } + } +} + +static int __ses_get_crosses(ScfEfunction* f, int d, scf_vector_t* crosses) +{ + ses_vertex_t* edge0; + ses_vertex_t* edge1; + + ScfEcomponent* c0; + ScfEcomponent* c1; + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + + long i; + long j; + long k; + long m; + long n; + long q; + + for (i = 0; i < f->n_components - 1; i++) { + c0 = f->components[i]; + + for (j = LAYOUT_P0(c0); j < c0->n_pins - 1; j++) { + p0 = c0->pins[j]; + + for (k = j + 1; k < c0->n_pins; k++) { + p1 = c0->pins[k]; + + if (p0->y - p1->y <= d && p0->y - p1->y >= -d) + continue; + + int y0 = p0->y < p1->y ? p0->y : p1->y; + int y1 = p0->y < p1->y ? p1->y : p0->y; + + for (m = i + 1; m < f->n_components; m++) { + c1 = f->components[m]; + + for (n = LAYOUT_P0(c1); n < c1->n_pins - 1; n++) { + p2 = c1->pins[n]; + + if ((p0->x > 0 && p2->x < 0) || (p0->x < 0 && p2->x > 0)) + break; + + for (q = n + 1; q < c1->n_pins; q++) { + p3 = c1->pins[q]; + + if (p2->y - p3->y <= d && p2->y - p3->y >= -d) + continue; + + int y2 = p2->y < p3->y ? p2->y : p3->y; + int y3 = p2->y < p3->y ? p3->y : p2->y; + + if ((y0 < y2 && y2 < y1 && y1 < y3) || (y2 < y0 && y0 < y3 && y3 < y1)) { + + edge0 = ses_vertex_add(crosses, c0); + if (!edge0) + return -ENOMEM; + + edge1 = ses_vertex_add(crosses, c1); + if (!edge1) + return -ENOMEM; + + if (ses_vertex_connect(edge0, edge1) < 0) + return -ENOMEM; + goto next; + } + } + } +next: + c1 = NULL; + } + } + } + } + + scf_vector_qsort(crosses, ses_vertex_cmp_edges); + +#if 0 + for (i = 0; i < crosses->size; i++) { + edge0 = crosses->data[i]; + c0 = edge0->data; + + scf_logw("c%ld\n", c0->id); + + for (j = 0; j < edge0->edges->size; j++) { + edge1 = edge0->edges->data[j]; + c1 = edge1->data; + + scf_logi("j: %ld, c%ld\n", j, c1->id); + } + printf("\n"); + } + + scf_loge("crosses->size: %d\n\n", crosses->size); +#endif + + return 0; +} + +static int __ses_de_cross(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEline* el; + ScfEpin* p; + ScfLine* l0; + ScfLine* l; + + ses_vertex_t* v; + scf_vector_t* graph; + scf_vector_t* colors; + + graph = scf_vector_alloc(); + if (!graph) + return -ENOMEM; + + colors = scf_vector_alloc(); + if (!colors) { + scf_vector_free(graph); + return -ENOMEM; + } + + intptr_t N = 2; + intptr_t i; + intptr_t j; + intptr_t k; + + int ret = __ses_get_crosses(f, d, graph); + if (ret < 0) + return ret; + + if (0 < graph->size) { + v = graph->data[0]; + + N = v->edges->size + 1; + } + + for (j = 1; j <= N; j++) + scf_vector_add(colors, (void*)j); + + for (j = N; j >= 2; j--) { + + int ret = ses_graph_kcolor(graph, j, colors); + if (ret < 0) { + scf_loge("**********\n"); + } + + int n = 0; + for (i = 0; i < graph->size; i++) { + v = graph->data[i]; + + if (v->color < 0) { + c = v->data; + n++; + scf_logd("j: %ld, c%ld->color: %ld\n", j, c->id, v->color); + } + } + + if (n > 0) + break; + + for (i = 0; i < graph->size; i++) { + v = graph->data[i]; + + c = v->data; + c->color = v->color; + v->color = 0; + } + + scf_vector_del(colors, (void*)j); + } + + scf_vector_clear(graph, ( void (*)(void*) )ses_vertex_free); + scf_vector_free(graph); + graph = NULL; + + N = j + 1; + + for (j = 0; j < f->n_components; j++) { + c = f->components[j]; + + if (0 == c->color) + c->color = 1; + } + + scf_vector_free(colors); + colors = NULL; + + int x1 = 0; + + for (j = 1; j <= N; j++) { + + intptr_t j0 = (j - 1) / 2; +// intptr_t j1 = (j - 1) % 2; + + for (i = 0; i < f->n_elines; i++) { + el = f->elines[i]; + + if (0 == j0) + el->lines[0]->x1 = el->lines[0]->x0; + + else if (el->n_lines <= j0) { + + l0 = el->lines[0]; + + l = malloc(sizeof(ScfLine)); + if (!l) + return -ENOMEM; + + l->x0 = x1 + d; + l->x1 = l->x0; + l->y0 = l0->y0; + l->y1 = l0->y1; + + if (scf_eline__add_line(el, l) < 0) { + free(l); + return -ENOMEM; + } + } + + for (k = 0; k + 1 < el->n_pins; k += 2) { + + c = f->components[el->pins[k]]; + p = c->pins [el->pins[k + 1]]; + + if ((c->color - 1) / 2 != j0) + continue; + + l = el->lines[j0]; + p->x = l->x1 + d; + l->x1 = p->x; + + if (x1 < l->x1) + x1 = l->x1; + } + } + } + + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + scf_logi("N: %ld, i: %ld, c%ld->color: %ld\n", N, i, c->id, c->color); + } + + return 0; +} + +static void __set_xy_by_pins(ScfEcomponent* c, int pid0, int pid1) +{ + ScfEpin* p0 = c->pins[pid0]; + ScfEpin* p1 = c->pins[pid1]; + + c->x = (p0->x + p1->x) / 2; + c->y = (p0->y + p1->y) / 2; + + p0->x = c->x; + p1->x = c->x; +} + +static void __ses_set_xy(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + + long i; + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + + int n = 0; + if (c->color > 0) + n = (c->color - 1) % 2; + + switch (c->type) { + case SCF_EDA_NPN: + case SCF_EDA_PNP: + __set_xy_by_pins(c, SCF_EDA_NPN_B, SCF_EDA_NPN_E); + + p0 = c->pins[SCF_EDA_NPN_C]; + p1 = c->pins[SCF_EDA_NPN_E]; + p0->x = c->x + d / 2; + p1->x = c->x - d / 2; + break; + + case SCF_EDA_NOT: + __set_xy_by_pins(c, SCF_EDA_NOT_IN, SCF_EDA_NOT_OUT); + + c->pins[SCF_EDA_NOT_POS]->x = c->x; + c->pins[SCF_EDA_NOT_NEG]->x = c->x; + break; + + case SCF_EDA_NAND: + case SCF_EDA_AND: + case SCF_EDA_OR: + case SCF_EDA_NOR: + case SCF_EDA_XOR: + __set_xy_by_pins(c, SCF_EDA_NAND_IN0, SCF_EDA_NAND_IN1); + + c->pins[SCF_EDA_NAND_POS]->x = c->x; + c->pins[SCF_EDA_NAND_NEG]->x = c->x; + + p0 = c->pins[SCF_EDA_NAND_IN0]; + p1 = c->pins[SCF_EDA_NAND_IN1]; + p2 = c->pins[SCF_EDA_NAND_OUT]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); + + if (0 == n) { + if (c->y <= p1->y) { + p0->x = c->x + d * 3 / 4; + p1->x = c->x + d / 4; + } else { + p0->x = c->x + d / 4; + p1->x = c->x + d * 3 / 4; + } + + p2->x = c->x - d * 3 / 4; + } else { + if (c->y <= p1->y) { + p0->x = c->x - d * 3 / 4; + p1->x = c->x - d / 4; + } else { + p0->x = c->x - d / 4; + p1->x = c->x - d * 3 / 4; + } + + p2->x = c->x + d * 3 / 4; + } + break; + + case SCF_EDA_ADD: + __set_xy_by_pins(c, SCF_EDA_ADD_IN0, SCF_EDA_ADD_IN1); + + c->pins[SCF_EDA_ADD_POS]->x = c->x; + c->pins[SCF_EDA_ADD_NEG]->x = c->x; + + p0 = c->pins[SCF_EDA_ADD_IN0]; + p1 = c->pins[SCF_EDA_ADD_IN1]; + p2 = c->pins[SCF_EDA_ADD_OUT]; + p3 = c->pins[SCF_EDA_ADD_CF]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); + + if (p2->y > p3->y) + SCF_XCHG(p2, p3); + + if (0 == n) { + if (c->y <= p1->y) { + p0->x = c->x + d * 3 / 4; + p1->x = c->x + d / 4; + } else { + p0->x = c->x + d / 4; + p1->x = c->x + d * 3 / 4; + } + + if (c->y <= p3->y) { + p2->x = c->x - d / 4; + p3->x = c->x - d * 3 / 4; + } else { + p2->x = c->x - d * 3 / 4; + p3->x = c->x - d / 4; + } + } else { + if (c->y <= p1->y) { + p0->x = c->x - d * 3 / 4; + p1->x = c->x - d / 4; + } else { + p0->x = c->x - d / 4; + p1->x = c->x - d * 3 / 4; + } + + if (c->y <= p3->y) { + p2->x = c->x + d / 4; + p3->x = c->x + d * 3 / 4; + } else { + p2->x = c->x + d * 3 / 4; + p3->x = c->x + d / 4; + } + } + break; + default: + __set_xy_by_pins(c, 0, 1); + break; + }; + } +} + +static inline void __ses_xchg_cx2(ScfEcomponent* c0, ScfEcomponent* c1) +{ + ScfEpin* p; + size_t i; + + int cx0 = c0->x; + int cx1 = c1->x; + + SCF_XCHG(c0->x, c1->x); + + scf_logd("c%ld <--> c%ld, color: %ld, %ld, cx: %d, %d\n", c0->id, c1->id, c0->color, c1->color, c0->x, c1->x); + + for (i = 0; i < c0->n_pins; i++) { + p = c0->pins[i]; + p->x += c0->x - cx0; + } + + for (i = 0; i < c1->n_pins; i++) { + p = c1->pins[i]; + p->x += c1->x - cx1; + } +} + +static void __ses_xchg_cx(ScfEfunction* f, int d) +{ + ScfEcomponent* c0; + ScfEcomponent* c1; + ScfEpin* p; + + size_t i; + size_t j; + size_t k; + size_t n; + + for (i = 0; i < f->n_components - 1; i++) { + c0 = f->components[i]; + + int m0 = 0; + int n0 = 0; + + if (c0->color > 0) { + m0 = (c0->color - 1) / 2; + n0 = (c0->color - 1) % 2; + } + + for (j = i + 1; j < f->n_components; j++) { + c1 = f->components[j]; + + int m1 = 0; + int n1 = 0; + + if (c1->color > 0) { + m1 = (c1->color - 1) / 2; + n1 = (c1->color - 1) % 2; + } + + if (m0 != m1) + continue; + + if ((n0 < n1 && c0->x > c1->x) || (n0 > n1 && c0->x < c1->x)) + __ses_xchg_cx2(c0, c1); + } + } + + do { + n = 0; + + for (i = 0; i < f->n_components - 1; i++) { + c0 = f->components[i]; + + int y0 = INT_MAX; + int y1 = INT_MIN; + int m0 = 0; + int n0 = 0; + + if (c0->color > 0) { + m0 = (c0->color - 1) / 2; + n0 = (c0->color - 1) % 2; + } + + for (k = LAYOUT_P0(c0); k < c0->n_pins; k++) { + p = c0->pins[k]; + + if (y0 > p->y) + y0 = p->y; + + if (y1 < p->y) + y1 = p->y; + } + + for (j = i + 1; j < f->n_components; j++) { + c1 = f->components[j]; + + int y2 = INT_MAX; + int y3 = INT_MIN; + int m1 = 0; + int n1 = 0; + + if (c1->color > 0) { + m1 = (c1->color - 1) / 2; + n1 = (c1->color - 1) % 2; + } + + if (m0 != m1 || n0 != n1) + continue; + + for (k = LAYOUT_P0(c1); k < c1->n_pins; k++) { + p = c1->pins[k]; + + if (y2 > p->y) + y2 = p->y; + + if (y3 < p->y) + y3 = p->y; + } + + if ((y0 <= y2 && y3 < y1) || (y0 < y2 && y3 <= y1)) { + + if ((0 == n0 && c0->x > c1->x) || (1 == n0 && c0->x < c1->x)) { + __ses_xchg_cx2(c0, c1); + n++; + } + + } else if ((y2 <= y0 && y1 < y3) || (y2 < y0 && y1 <= y3)) { + + if ((0 == n0 && c0->x < c1->x) || (1 == n0 && c0->x > c1->x)) { + __ses_xchg_cx2(c0, c1); + n++; + } + + } else if (y0 == y2 && y1 == y3) { + + if (c0->n_pins - LAYOUT_P0(c0) > 2) { + + if ((0 == n0 && c0->x < c1->x) || (1 == n0 && c0->x > c1->x)) { + __ses_xchg_cx2(c0, c1); + n++; + } + } else if (c1->n_pins - LAYOUT_P0(c1) > 2) { + + if ((0 == n0 && c0->x > c1->x) || (1 == n0 && c0->x < c1->x)) { + __ses_xchg_cx2(c0, c1); + n++; + } + } + } + } + } + } while (n > 0); +} + +static void __ses_set_cx(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEcomponent* c2; + ScfEline* el; + ScfEpin* p; + + long i; + long j; + long k; + + qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); + for (i = 1; i < f->n_components; i++) { + c = f->components[i]; + c2 = f->components[i - 1]; + + int tmp = c->x; + + if (SCF_EDA_NPN == c->type + || SCF_EDA_NPN == c2->type + || SCF_EDA_PNP == c->type || SCF_EDA_PNP == c2->type + || SCF_EDA_NAND == c->type || SCF_EDA_NAND == c2->type + || SCF_EDA_AND == c->type || SCF_EDA_AND == c2->type + || SCF_EDA_ADD == c->type || SCF_EDA_ADD == c2->type + || SCF_EDA_OR == c->type || SCF_EDA_OR == c2->type + || SCF_EDA_XOR == c->type || SCF_EDA_XOR == c2->type + || SCF_EDA_NOR == c->type || SCF_EDA_NOR == c2->type) + c->x = c2->x + d * 2; + else + c->x = c2->x + d; + + for (k = 0; k < c->n_pins; k++) { + p = c->pins[k]; + p->x += c->x - tmp; + } + } + + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + + for (j = 0; j < f->n_elines; j++) { + el = f->elines[j]; + + if (c->y - d / 4 < el->lines[0]->y0 && el->lines[0]->y0 < c->y + d / 4) + c->y -= d / 3; + } + } + + qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_id); +} + +static void __ses_min_cx(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEcomponent* c2; + ScfEcomponent* c3; + ScfEpin* p; + ScfEpin* p2; + + long i; + long j; + long k; + long m; + + qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); + + for (i = 1; i < f->n_components; i++) { + c = f->components[i]; + + int tmp = c->x; + int max = 0; + int mt = 0; + int m0 = 0; + + if (c->color > 0) + m0 = (c->color - 1) / 2; + + int y0 = INT_MAX; + int y1 = 0; + for (k = LAYOUT_P0(c); k < c->n_pins; k++) { + p = c->pins[k]; + + if (y0 > p->y) + y0 = p->y; + + if (y1 < p->y) + y1 = p->y; + } + + scf_logd("c%ld->x: %d, color: %ld, max: %d\n", c->id, c->x, c->color, max); + + for (j = i - 1; j >= 0; j--) { + c2 = f->components[j]; + + int m1 = 0; + if (c2->color > 0) + m1 = (c2->color - 1) / 2; + + if (m0 < m1) + continue; + + int y2 = INT_MAX; + int y3 = 0; + for (m = LAYOUT_P0(c2); m < c2->n_pins; m++) { + p2 = c2->pins[m]; + + if (y2 > p2->y) + y2 = p2->y; + + if (y3 < p2->y) + y3 = p2->y; + } + + if (!(y1 <= y2 || y0 >= y3)) { + if (max < c2->x) { + max = c2->x; + mt = c2->type; + } + } + } + + if (0 == max) + c->x = f->components[0]->x; + else { + if (SCF_EDA_NPN == c->type + || SCF_EDA_NPN == mt + || SCF_EDA_PNP == c->type || SCF_EDA_PNP == mt + || SCF_EDA_NAND == c->type || SCF_EDA_NAND == mt + || SCF_EDA_AND == c->type || SCF_EDA_AND == mt + || SCF_EDA_ADD == c->type || SCF_EDA_ADD == mt + || SCF_EDA_OR == c->type || SCF_EDA_OR == mt + || SCF_EDA_XOR == c->type || SCF_EDA_XOR == mt + || SCF_EDA_NOR == c->type || SCF_EDA_NOR == mt) + c->x = max + d * 2; + else + c->x = max + d; + } + + for (k = 0; k < c->n_pins; k++) { + p = c->pins[k]; + p->x += c->x - tmp; + } + } + + qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_cx); + + for (i = 1; i < f->n_components; i++) { + c = f->components[i]; + c2 = f->components[i - 1]; + + int d2 = d; + for (j = i - 1; j >= 0; j--) { + c3 = f->components[j]; + + if (c3->x < c2->x) + break; + if (SCF_EDA_NPN == c3->type + || SCF_EDA_PNP == c3->type + || SCF_EDA_NAND == c3->type || SCF_EDA_AND == c3->type + || SCF_EDA_ADD == c3->type || SCF_EDA_OR == c3->type + || SCF_EDA_XOR == c3->type || SCF_EDA_NOR == c3->type) { + c2 = c3; + d2 = d * 2; + } + } + + int tmp = c->x; + if (tmp - c2->x > d) { + for (j = i; j < f->n_components; j++) { + c = f->components[j]; + + if (c->x > tmp) + break; + + if (SCF_EDA_NPN == c->type + || SCF_EDA_PNP == c->type + || SCF_EDA_NAND == c->type || SCF_EDA_AND == c->type + || SCF_EDA_ADD == c->type || SCF_EDA_OR == c->type + || SCF_EDA_XOR == c->type || SCF_EDA_NOR == c->type) + c->x = c2->x + d * 2; + else + c->x = c2->x + d2; + + for (k = 0; k < c->n_pins; k++) { + p = c->pins[k]; + p->x += c->x - tmp; + } + } + } + } + + qsort(f->components, f->n_components, sizeof(ScfEcomponent*), ecomponent_cmp_id); +} + +static void __ses_xchg_ce(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEpin* pb; + ScfEpin* pe; + ScfEpin* pc; + + int64_t i; + int64_t j; + + assert(SCF_EDA_NPN_B == SCF_EDA_PNP_B); + assert(SCF_EDA_NPN_C == SCF_EDA_PNP_C); + assert(SCF_EDA_NPN_E == SCF_EDA_PNP_E); + + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + + if (SCF_EDA_NPN != c->type && SCF_EDA_PNP != c->type) + continue; + + j = 0; + + if (c->color > 0) + j = (c->color - 1) % 2; + + pb = c->pins[SCF_EDA_NPN_B]; + pc = c->pins[SCF_EDA_NPN_C]; + pe = c->pins[SCF_EDA_NPN_E]; + + if (pc->y > pe->y) + SCF_XCHG(pc, pe); + + if (pc->y > pb->y) { + + if ((0 == j && pc->x < pe->x) || (1 == j && pc->x > pe->x)) + SCF_XCHG(pc->x, pe->x); + + } else if (pe->y < pb->y) { + + if ((0 == j && pc->x > pe->x) || (1 == j && pc->x < pe->x)) + SCF_XCHG(pc->x, pe->x); + + } else if (pc->y < pb->y) { + + pc = c->pins[SCF_EDA_NPN_C]; + pe = c->pins[SCF_EDA_NPN_E]; + + if ((0 == j && pc->x > pb->x) || (1 == j && pc->x < pb->x)) + SCF_XCHG(pc->x, pe->x); + } + + pc = c->pins[SCF_EDA_NPN_C]; + pe = c->pins[SCF_EDA_NPN_E]; + + if (pc->x < c->x) { + pc->x = c->x - d * 7 / 8; + pe->x = c->x + d * 7 / 8; + } else { + pc->x = c->x + d * 7 / 8; + pe->x = c->x - d * 7 / 8; + } + } +} + +int ses_layout_function(ScfEfunction* f, int d) +{ + ScfEcomponent* c; + ScfEline* el; + ScfEpin* p; + + long i; + long j; + + int ret = scf_pins_same_line(f); + if (ret < 0) + return ret; + + ret = ses_lines_same_components(f); + if (ret < 0) + return ret; + + f->x = 0; + f->y = 0; + f->w = 0; + f->h = 0; + + ret = __ses_layout_lines(f, d); + if (ret < 0) + return ret; + + __ses_layout_components(f, d); + __ses_xchg_components(f, d); + + qsort(f->elines, f->n_elines, sizeof(ScfEline*), eline_cmp_id); + + ret = __ses_de_cross(f, d); + if (ret < 0) + return ret; + + __ses_set_xy(f, d); + __ses_set_cx(f, d); + __ses_xchg_cx(f, d); + __ses_min_cx(f, d); + __ses_xchg_ce(f, d); + + int tx0 = INT_MAX; + int tx1 = 0; + + for (i = 0; i < f->n_elines; i++) { + el = f->elines[i]; + + for (j = 0; j < el->n_lines; j++) { + el->lines[j]->x0 = INT_MAX; + el->lines[j]->x1 = 0; + } + + for (j = 0; j < el->n_pins; j += 2) { + + c = f->components[el->pins[j]]; + p = c->pins [el->pins[j + 1]]; + + if (tx0 > p->x) + tx0 = p->x; + + if (tx1 < p->x) + tx1 = p->x; + + intptr_t k = (c->color - 1) / 2; + + if (el->lines[k]->x0 > p->x) + el->lines[k]->x0 = p->x; + + if (el->lines[k]->x1 < p->x) + el->lines[k]->x1 = p->x; + } + + for (j = 0; j < el->n_lines; j++) + scf_logd("l%ld->lines[%ld]: x0: %d, x1: %d\n", el->id, j, el->lines[j]->x0, el->lines[j]->x1); +// printf("\n"); + } + + f->w = tx1 + d * 2; + f->h += d; + + scf_logi("f->x: %d, y: %d, w: %d, h: %d, tx0: %d, tx1: %d\n", f->x, f->y, f->w, f->h, tx0, tx1); + return 0; +} diff --git a/ses_node_analysis.c b/ses_node_analysis.c index 5119803..d9191eb 100644 --- a/ses_node_analysis.c +++ b/ses_node_analysis.c @@ -49,7 +49,9 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s ses_node_t* node = NULL; ScfEcomponent* c; + ScfEcomponent* c2; ScfEpin* p; + ScfEpin* p2; int ret = -1; @@ -105,7 +107,7 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s for (i = vip_n - 1; i >= vip_m; i -= 2) { p = path->pins->data[i]; - c = ses_component(f, p); + c = p->c; switch (c->type) { @@ -120,6 +122,10 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s } else if (SCF_EDA_NPN_C == p->id) edge2 = ses_edges_find_edge_by_pin(edges, c->pins[SCF_EDA_NPN_B]); + case SCF_EDA_Diode: + if (SCF_EDA_Diode == c->type) + bflag = 1; + case SCF_EDA_Capacitor: case SCF_EDA_Inductor: if (!node) { @@ -129,6 +135,16 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s } break; default: + if (i - 1 >= vip_m) { + p2 = path->pins->data[i - 1]; + c2 = p2->c; + + if (SCF_EDA_Diode == c2->type && !node) { + node = ses_node_alloc(); + if (!node) + return -ENOMEM; + } + } break; }; @@ -151,6 +167,7 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s return ret; \ } \ } else { \ + scf_loge("\n"); \ ses_node_free(node); \ return -EINVAL; \ } @@ -222,7 +239,7 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s node->vip_i = i; node->path = path; - node->el = ses_line(f, p); + node->el = ses_top_pline(p); edge = ses_edge_alloc(path, i, j); if (!edge) @@ -271,6 +288,38 @@ int __ses_nodes_path2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, s return 0; } +static void __ses_path_clear_vflag(ses_path_t* path) +{ + ses_path_t* child; + int k; + + path->vflag = 0; + + if (path->connections) { + for (k = 0; k < path->connections->size; k++) { + child = path->connections->data[k]; + + __ses_path_clear_vflag(child); + } + } + + if (path->childs) { + for (k = 0; k < path->childs->size; k++) { + child = path->childs->data[k]; + + __ses_path_clear_vflag(child); + } + } + + if (path->bridges) { + for (k = 0; k < path->bridges->size; k++) { + child = path->bridges->data[k]; + + __ses_path_clear_vflag(child); + } + } +} + int __ses_nodes_path(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, scf_vector_t** pnodes, scf_vector_t** pedges) { scf_vector_t* nodes; @@ -291,30 +340,41 @@ int __ses_nodes_path(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, sc return -ENOMEM; } + __ses_path_clear_vflag(path); + int ret = __ses_nodes_path2(f, path, vip_m, vip_n, nodes, edges); - if (ret < 0) { - scf_vector_clear(nodes, (void (*)(void*) )ses_node_free); - scf_vector_clear(edges, (void (*)(void*) )ses_edge_free); - scf_vector_free(nodes); - scf_vector_free(edges); - return ret; - } + if (ret < 0) + goto error; + + ScfEcomponent* B = f->components[0]; + ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; + ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); + ScfEline* el; + ScfEpin* p; for (i = 0; i < nodes->size; ) { node = nodes->data[i]; - if (nodes->size > 1 && node->edges->size <= 1) { + for (j = node->edges->size - 1; j >= 0; j--) { + edge = node->edges->data[j]; - assert(0 == scf_vector_del(nodes, node)); - - for (j = 0; j < node->edges->size; j++) { - edge = node->edges->data[j]; + if (node->el == LP) { + assert(0 == scf_vector_del(node->edges, edge)); if (edge->node0 == node) edge->node0 = NULL; if (edge->node1 == node) edge->node1 = NULL; + } else { + if (edge->node0 != node && edge->node1 != node) + assert(0 == scf_vector_del(node->edges, edge)); } + } + + if (node->edges->size <= 0) { + assert(0 == scf_vector_del(nodes, node)); ses_node_free(node); node = NULL; @@ -324,16 +384,71 @@ int __ses_nodes_path(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, sc } } + for (j = 0; j < edges->size; j++) { + edge = edges->data[j]; + + p = edge->path->pins->data[edge->vip_n]; + el = ses_top_pline(p); + + if (edge->node0 || el == LN) + continue; + + for (i = 0; i < nodes->size; i++) { + node = nodes->data[i]; + + if (el == node->el) { + edge->node0 = node; + + ret = scf_vector_add(node->edges, edge); + if (ret < 0) + goto error; + break; + } + } + + if (i >= nodes->size) { + node = ses_node_alloc(); + if (!node) { + ret = -ENOMEM; + goto error; + } + node->index = nodes->size; + + ret = scf_vector_add(nodes, node); + if (ret < 0) { + ses_node_free(node); + goto error; + } + + node->vip_i = edge->vip_n; + node->path = edge->path; + node->el = el; + + edge->node0 = node; + + ret = scf_vector_add(node->edges, edge); + if (ret < 0) + goto error; + } + } + *pnodes = nodes; *pedges = edges; return 0; + +error: + scf_vector_clear(nodes, (void (*)(void*) )ses_node_free); + scf_vector_clear(edges, (void (*)(void*) )ses_edge_free); + scf_vector_free(nodes); + scf_vector_free(edges); + return ret; } static void ses_AbX_print(double* A, double* b, double* X, int N) { int i; int j; -#if 0 + printf("A:\n"); for (i = 0; i < N; i++) { for (j = 0; j < N; j++) @@ -344,7 +459,7 @@ static void ses_AbX_print(double* A, double* b, double* X, int N) printf("\nb:\n"); for (j = 0; j < N; j++) printf("%lg\n", b[j]); -#endif + printf("\nX:\n"); for (j = 0; j < N; j++) printf("%lg\n", X[j]); @@ -370,7 +485,7 @@ static void ses_AbX_print(double* A, double* b, double* X, int N) v[m - 1][0] - v[m - 1][1] - a[m - 1] * R[m - 1] = C[m - 1] */ -static void __ses_nodes_set_Ab(ScfEfunction* f, scf_vector_t* nodes, scf_vector_t* edges, int64_t ns, double* A, double* b, int N) +static void __ses_nodes_set_Ab(ScfEfunction* f, scf_vector_t* nodes, scf_vector_t* edges, int64_t ps, double* A, double* b, int N) { ses_node_t* node; ses_edge_t* edge; @@ -451,19 +566,19 @@ static void __ses_nodes_set_Ab(ScfEfunction* f, scf_vector_t* nodes, scf_vector_ v0 - v1 - i * (r + dt/C + L/dt) = cv - Li0/dt */ - b[n + edge->index] = cv - uh * 1000.0 * la / ns; + b[n + edge->index] = cv - uh * 1000000.0 * la / ps; // 1ns = 1000ps if (uf > 0.0) - A[(n + edge->index) * N + n + edge->index] = -r - uh * 1000.0 / ns - ns / 1000.0 / uf; + A[(n + edge->index) * N + n + edge->index] = -r - uh * 1000000.0 / ps - ps / 1000000.0 / uf; else - A[(n + edge->index) * N + n + edge->index] = -r - uh * 1000.0 / ns; + A[(n + edge->index) * N + n + edge->index] = -r - uh * 1000000.0 / ps; - if (edge->node0 && edge->node0->el != ses_line(f, Bn)) + if (edge->node0 && edge->node0->el != ses_top_pline(Bn)) A[(n + edge->index) * N + edge->node0->index] = -1; else b[n + edge->index] += Bn->v; - if (edge->node1 && edge->node1->el != ses_line(f, Bp)) + if (edge->node1 && edge->node1->el != ses_top_pline(Bp)) A[(n + edge->index) * N + edge->node1->index] = 1; else b[n + edge->index] -= Bp->v; @@ -506,7 +621,7 @@ static void __ses_Vb_by_curve(ScfEcomponent* c, double Ib, double* V) *V = V0 + R * (Ib - A0); } - scf_logi("i: %d, n_curves: %ld, Ib: %lg, R: %lg, V: %lg\n", i, c->n_curves, Ib, R, *V); + scf_logd("i: %d, n_curves: %ld, Ib: %lg, R: %lg, V: %lg\n", i, c->n_curves, Ib, R, *V); } static int __ses_edges_update_Ab(ScfEfunction* f, scf_vector_t* edges, double* A, double* b, double* X, int N, int* n_offs) @@ -530,22 +645,21 @@ static int __ses_edges_update_Ab(ScfEfunction* f, scf_vector_t* edges, double* A p0 = edge->path->pins->data[edge->vip_m]; p1 = edge->path->pins->data[edge->vip_n]; - c = ses_component(f, p0); + c = p0->c; - if (edge->bflag) { - double Vb; - double Ve; - - if (edge->node1 && edge->node1->el != ses_line(f, Bp)) - Vb = X[edge->node1->index]; - else - Vb = Bp->v; + double Vb; + double Ve; + if (edge->node1 && edge->node1->el != ses_top_pline(Bp)) + Vb = X[edge->node1->index]; + else + Vb = Bp->v; - if (edge->node0 && edge->node0->el != ses_line(f, Bn)) - Ve = X[edge->node0->index]; - else - Ve = Bn->v; + if (edge->node0 && edge->node0->el != ses_top_pline(Bn)) + Ve = X[edge->node0->index]; + else + Ve = Bn->v; + if (edge->bflag) { double dV = Vb - Ve; double Ib = X[n + edge->index]; double Rb = SCF_EDA_V_NPN_ON / Ib; @@ -559,56 +673,45 @@ static int __ses_edges_update_Ab(ScfEfunction* f, scf_vector_t* edges, double* A #endif if (-1e8 < Rb && Rb < 1e8) { if (dV < V * 0.99 || dV > V * 1.01) { - - if (p0->IC) - scf_logd("edge: [%d] IC%ld_c%ldp%ld-c%ldp%ld, Vb: %lg, Ve: %lg, dV: %lg, V: %lg, Ib: %lg, Rb: %lg\n", - edge->index, p0->IC->id, p0->cid, p0->id, p1->cid, p1->id, Vb, Ve, dV, V, Ib, Rb); - else - scf_logd("edge: [%d] c%ldp%ld-c%ldp%ld, Vb: %lg, Ve: %lg, dV: %lg, V: %lg, Ib: %lg, Rb: %lg\n", - edge->index, p0->cid, p0->id, p1->cid, p1->id, Vb, Ve, dV, V, Ib, Rb); - +#if 0 + scf_logi("edge: [%d], ", edge->index); + ses_pin_print(p0); + printf("status: %d, dV: %lg, Vb: %lg, Ve: %lg, V: %lg, Ib: %lg, Rb: %lg\n", c->status, dV, Vb, Ve, V, Ib, Rb); +#endif A[(n + edge->index) * N + n + edge->index] = -Rb; b[ n + edge->index] += 0; k++; } else { - if (p0->IC) - scf_logi("edge: [%d] IC%ld_c%ldp%ld-c%ldp%ld, Vb: %lg, Ve: %lg, dV: %lg, V: %lg, Ib: %lg, Rb: %lg\n", - edge->index, p0->IC->id, p0->cid, p0->id, p1->cid, p1->id, Vb, Ve, dV, V, Ib, Rb); - else - scf_logi("edge: [%d] c%ldp%ld-c%ldp%ld, Vb: %lg, Ve: %lg, dV: %lg, V: %lg, Ib: %lg, Rb: %lg\n", - edge->index, p0->cid, p0->id, p1->cid, p1->id, Vb, Ve, dV, V, Ib, Rb); +#if 0 + scf_logi("edge: [%d], ", edge->index); + ses_pin_print(p0); + printf("status: %d, dV: %lg, Vb: %lg, Ve: %lg, V: %lg, Ib: %lg, Rb: %lg\n", c->status, dV, Vb, Ve, V, Ib, Rb); +#endif } } else { - c->status = SCF_EDA_Status_OFF; - c->lock = 1; - (*n_offs)++; - - if (p0->IC) - scf_logi("\033[34mIC%ld_c%ld, status: %d, dV: %lg, Ib: %lg, Rb: %lg, edge->index: %d\033[0m\n", p0->IC->id, c->id, c->status, dV, Ib, Rb, edge->index); - else - scf_logi("\033[34mc%ld, status: %d, dV: %lg, Ib: %lg, Rb: %lg, edge->index: %d\033[0m\n", c->id, c->status, dV, Ib, Rb, edge->index); + if (dV < SCF_EDA_V_NPN_OFF && Ve < Bp->v - SCF_EDA_V_NPN_OFF) { + c->status = SCF_EDA_Status_OFF; + c->lock = 1; + (*n_offs)++; + } +#if 1 + scf_logi("\033[34medge: [%d], ", edge->index); + ses_pin_print(p0); + printf("status: %d, dV: %lg, Vb: %lg, Ve: %lg, V: %lg, Ib: %lg, Rb: %lg\033[0m\n", c->status, dV, Vb, Ve, V, Ib, Rb); +#endif } } else if (edge->edge_b) { double Ic = X[n + edge->index]; double Ib = X[n + edge->edge_b->index]; + double Vc = Vb; - double dI = Ib * edge->hfe - Ic; - - double Vb; - double Ve; - - if (edge->edge_b->node1 && edge->edge_b->node1->el != ses_line(f, Bp)) + if (edge->edge_b->node1 && edge->edge_b->node1->el != ses_top_pline(Bp)) Vb = X[edge->edge_b->node1->index]; else Vb = Bp->v; - if (edge->edge_b->node0 && edge->edge_b->node0->el != ses_line(f, Bn)) - Ve = X[edge->edge_b->node0->index]; - else - Ve = Bn->v; - - double dV = Vb - Ve; + double dI = Ib * edge->hfe - Ic; double V = SCF_EDA_V_NPN_ON; double Rb = V / Ib; #if 1 @@ -620,24 +723,20 @@ static int __ses_edges_update_Ab(ScfEfunction* f, scf_vector_t* edges, double* A #endif if (dI < -1e-10 && -1e8 < Rb && Rb < 1e8) { - if (!edge->amplify_flag) { edge->amplify_flag = 1; - - if (p0->IC) - scf_logd("edge: [%d] IC%ld_c%ldp%ld-c%ldp%ld [b%d], Ic: %lg, Ib: %lg, dI: %lg, dVbe: %lg, Rb: %lg\n", - edge->index, p0->IC->id, p0->cid, p0->id, p1->cid, p1->id, edge->edge_b->index, Ic, Ib, dI, dV, Rb); - else - scf_logd("edge: [%d] c%ldp%ld-c%ldp%ld [b%d], Ic: %lg, Ib: %lg, dI: %lg, dVbe: %lg, Rb: %lg\n", - edge->index, p0->cid, p0->id, p1->cid, p1->id, edge->edge_b->index, Ic, Ib, dI, dV, Rb); - +#if 0 + scf_logi("edge: [%d], ", edge->index); + ses_pin_print(p0); + ses_pin_print(p1); + printf("[b%d], Ic: %lg, Ib: %lg, dI: %lg, Vbe: %lg, Rb: %lg\n", edge->edge_b->index, Ic, Ib, dI, Vb - Ve, Rb); +#endif for (i = 0; i < N; i++) A[(n + edge->index) * N + i] = 0; A[(n + edge->index) * N + n + edge->index] = -1; A[(n + edge->index) * N + n + edge->edge_b->index] = edge->hfe; b[ n + edge->index] = 0; - k++; } } @@ -647,7 +746,7 @@ static int __ses_edges_update_Ab(ScfEfunction* f, scf_vector_t* edges, double* A return k; } -static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, scf_vector_t* nodes, scf_vector_t* edges, int* changed, int64_t ns, int64_t count) +static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, scf_vector_t* nodes, scf_vector_t* edges, int* changed, int64_t ps, int64_t count) { ses_node_t* node; ses_edge_t* edge; @@ -656,7 +755,6 @@ static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, ScfEcomponent* B = f->components[0]; ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEpin* pm = path->pins->data[vip_m]; ScfEpin* pn = path->pins->data[vip_n]; ScfEpin* p0; @@ -669,14 +767,10 @@ static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, int m = edges->size; int n = nodes->size; - - if (ses_same_line(f, pm, Bp)) - n = nodes->size - 1; - int N = n + m; - pm->v = ses_line(f, pm)->v; - pn->v = ses_line(f, pn)->v; + pm->v = ses_top_pline(pm)->v; + pn->v = ses_top_pline(pn)->v; scf_logi("c%ldp%ld->v: %lg, c%ldp%ld->v: %lg, n: %d, m: %d, N: %d\n", pm->cid, pm->id, pm->v, pn->cid, pn->id, pn->v, n, m, N); @@ -693,7 +787,7 @@ static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, __ses_path_jr(f, path); - __ses_nodes_set_Ab(f, nodes, edges, ns, A, b, N); + __ses_nodes_set_Ab(f, nodes, edges, ps, A, b, N); gsl_matrix_view _A = gsl_matrix_view_array(U, N, N); gsl_vector_view _b = gsl_vector_view_array(b, N); @@ -715,13 +809,21 @@ static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, gsl_linalg_SV_decomp(&_A.matrix, &_V.matrix, &_S.vector, &_W.vector); gsl_linalg_SV_solve (&_A.matrix, &_V.matrix, &_S.vector, &_b.vector, &_X.vector); -// ses_AbX_print(A, b, X, N); - ret = __ses_edges_update_Ab(f, edges, A, b, X, N, &n_offs); try++; - scf_logi("ret: %d, try: %d\n\n", ret, try); + scf_logd("ret: %d, try: %d\n\n", ret, try); + for (i = 0; i < n; i++) { + node = nodes->data[i]; + el = node->el; + el->v = X[i]; + } + + if (n_offs > 0) { + *changed += n_offs; + break; + } } while (ret > 0 && try < MAX_TRYS); if (try >= MAX_TRYS) { @@ -729,62 +831,91 @@ static int __ses_nodes_path_solve2(ScfEfunction* f, ses_path_t* path, int vip_m, return -1; } - for (i = 0; i < n; i++) { - node = nodes->data[i]; - - el = node->el; - el->v = X[i]; - } +// ses_AbX_print(A, b, X, N); - if (n_offs > 0) { - *changed += n_offs; - free(A); - return 0; - } + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); for (j = 0; j < edges->size; j++) { edge = edges->data[j]; p0 = edge->path->pins->data[edge->vip_m]; p1 = edge->path->pins->data[edge->vip_n]; + c = p0->c; - c = ses_component(f, p0); + el = ses_top_pline(p0); + p0->v = el->v; + if (el != LP && el != LN) + ses_line_set_v(c->pf->elines[p0->lid], p0->v); - p0->v = ses_line(f, p0)->v; - p1->v = ses_line(f, p1)->v; - - scf_logd("c%ldp%ld->v: %lg, c%ldp%ld->v: %lg, a: %lg, edge->index: %d\n", p0->cid, p0->id, p0->v, p1->cid, p1->id, p1->v, edge->a, edge->index); + el = ses_top_pline(p1); + p1->v = el->v; + if (el != LP && el != LN) + ses_line_set_v(c->pf->elines[p1->lid], p1->v); edge->a = X[n + edge->index]; - +#if 1 + if (edge->a < -1e-4) + printf("\033[36m"); + ses_pin_print(p0); + ses_pin_print(p1); + if (edge->a < -1e-4) + printf(", v: %lg, %lg, a: %lg, edge->index: %d\033[0m\n", p0->v, p1->v, edge->a, edge->index); + else + printf(", v: %lg, %lg, a: %lg, edge->index: %d\n", p0->v, p1->v, edge->a, edge->index); +#endif if (SCF_EDA_NPN == c->type) { - ses_ui_r(&edge->r, 0, p0->v - p1->v, 0, edge->a, 0); + if (SCF_EDA_NPN_B == p0->id && edge->a < -1e-4) { + c->status = SCF_EDA_Status_OFF; + c->lock = 1; + (*changed)++; + } - p0->dr = edge->r - p0->r; - p0->a = edge->a; - p1->a = c->pins[SCF_EDA_NPN_B]->a + c->pins[SCF_EDA_NPN_C]->a; + p0->a = edge->a; + p1->a = c->pins[SCF_EDA_NPN_B]->a + c->pins[SCF_EDA_NPN_C]->a; continue; } else if (SCF_EDA_PNP == c->type) { - ses_ui_r(&edge->r, 0, p0->v - p1->v, 0, edge->a, 0); + if (SCF_EDA_PNP_B == p1->id && edge->a < -1e-4) { + c->status = SCF_EDA_Status_OFF; + c->lock = 1; + (*changed)++; + } + + p1->a = edge->a; + p0->a = c->pins[SCF_EDA_PNP_B]->a + c->pins[SCF_EDA_PNP_C]->a; + continue; - p1->dr = edge->r - p1->r; - p1->a = edge->a; - p0->a = c->pins[SCF_EDA_PNP_B]->a + c->pins[SCF_EDA_PNP_C]->a; + } else if (SCF_EDA_Diode == c->type) { + if (edge->a < -1e-4) { + c->status = SCF_EDA_Status_OFF; + c->lock = 1; + (*changed)++; + } + + c->a = edge->a; continue; } else if (SCF_EDA_Inductor == c->type) { int sign = p0->id - !p0->id; - c->v = (edge->a * sign - c->a) * c->uh * 1000.0 / ns; + c->v = (edge->a * sign - c->a) * c->uh * 1000000.0 / ps; + c->a = edge->a * sign; + p0->a = edge->a; + p1->a = edge->a; + continue; } else if (SCF_EDA_Capacitor == c->type) { int sign = p0->id - !p0->id; - c->v += edge->a * sign * ns / 1000.0 / c->uf; + c->v += edge->a * sign * ps / 1000000.0 / c->uf; + c->a = edge->a * sign; + p0->a = edge->a; + p1->a = edge->a; + continue; } - ret = __ses_path_va_branch(f, edge->path, edge->vip_m, edge->vip_n, edge->r, changed, ns, count); + ret = __ses_path_va_branch(f, edge->path, edge->vip_m, edge->vip_n, edge->r, changed, ps, count); if (ret < 0) goto error; } @@ -794,29 +925,21 @@ error: return ret; } -int __ses_nodes_path_solve(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, int* changed, int64_t ns, int64_t count) +int __ses_nodes_path_solve(ScfEfunction* f, ses_path_t* path, int vip_m, int vip_n, int* changed, int64_t ps, int64_t count) { scf_vector_t* nodes = NULL; scf_vector_t* edges = NULL; - ScfEline* el; - ScfEpin* pm = path->pins->data[vip_m]; - ScfEpin* pn = path->pins->data[vip_n]; - ScfEpin* p0; - ScfEpin* p1; - int ret = __ses_nodes_path(f, path, vip_m, vip_n, &nodes, &edges); if (ret < 0) return ret; - ses_nodes_print(nodes); - ret = __ses_nodes_path_solve2(f, path, vip_m, vip_n, nodes, edges, changed, ns, count); + ret = __ses_nodes_path_solve2(f, path, vip_m, vip_n, nodes, edges, changed, ps, count); scf_vector_clear(nodes, (void (*)(void*) )ses_node_free); scf_vector_clear(edges, (void (*)(void*) )ses_edge_free); scf_vector_free(nodes); scf_vector_free(edges); - return ret; } diff --git a/ses_path.c b/ses_path.c index 30cd17d..da24a7a 100644 --- a/ses_path.c +++ b/ses_path.c @@ -46,61 +46,97 @@ void ses_path_free(ses_path_t* path) } } -void ses_path_print(ses_path_t* path, ScfEfunction* f) +void ses_IC_print(ScfEcomponent* IC) { - if (!path) + if (!IC) return; - ses_path_t* child; - ScfEcomponent* c; - ScfEpin* p; + if (IC->pf->IC) + ses_IC_print(IC->pf->IC); + + switch (IC->type) { + case SCF_EDA_NAND: + printf("Nand%ld_", IC->id); + break; + case SCF_EDA_NOR: + printf("Nor%ld_", IC->id); + break; + + case SCF_EDA_NOT: + printf("Not%ld_", IC->id); + break; + case SCF_EDA_AND: + printf("And%ld_", IC->id); + break; + case SCF_EDA_OR: + printf("Or%ld_", IC->id); + break; + + case SCF_EDA_XOR: + printf("Xor%ld_", IC->id); + break; + case SCF_EDA_ADD: + printf("Add%ld_", IC->id); + break; + default: + printf("IC%ld_", IC->id); + break; + }; +} + +void ses_pin_print(ScfEpin* p) +{ + ses_IC_print(p->c->pf->IC); + + switch (p->c->type) { + case SCF_EDA_Resistor: + printf("R%ldp%ld ", p->cid, p->id); + break; + + case SCF_EDA_Capacitor: + printf("C%ldp%ld ", p->cid, p->id); + break; + + case SCF_EDA_Inductor: + printf("L%ldp%ld ", p->cid, p->id); + break; + + case SCF_EDA_Diode: + printf("D%ldp%ld ", p->cid, p->id); + break; + + case SCF_EDA_NPN: + case SCF_EDA_PNP: + if (SCF_EDA_NPN_B == p->id) + printf("T%ldb ", p->cid); + else if (SCF_EDA_NPN_C == p->id) + printf("T%ldc ", p->cid); + else + printf("T%lde ", p->cid); + break; + default: + printf("c%ldp%ld ", p->cid, p->id); + break; + }; +} +void ses_path_print(ses_path_t* path) +{ + if (!path) + return; + + ses_path_t* child; + ScfEpin* p; int i; if (!path->parent) - printf("\033[31mpath : %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, \033[0m", + printf("\033[31mpath : %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, \033[0m\n", path->index, path->n_diodes, path->n_NPNs, path->n_PNPs, path->n_capacitors, path->n_transistors); for (i = 0; i < path->pins->size; i++) { p = path->pins->data[i]; - if (p->IC) { - c = p->IC->f->components[p->cid]; - - printf("IC%ld_", p->IC->id); - } else - c = f->components[p->cid]; - - switch (c->type) { - case SCF_EDA_Resistor: - printf("R%ldp%ld ", p->cid, p->id); - break; - - case SCF_EDA_Capacitor: - printf("C%ldp%ld ", p->cid, p->id); - break; - - case SCF_EDA_Inductor: - printf("L%ldp%ld ", p->cid, p->id); - break; - - case SCF_EDA_Diode: - printf("D%ldp%ld ", p->cid, p->id); - break; - - case SCF_EDA_NPN: - case SCF_EDA_PNP: - if (SCF_EDA_NPN_B == p->id) - printf("T%ldb ", p->cid); - else if (SCF_EDA_NPN_C == p->id) - printf("T%ldc ", p->cid); - else - printf("T%lde ", p->cid); - break; - default: - printf("c%ldp%ld ", p->cid, p->id); - break; - }; + ses_pin_print(p); } printf("\n"); @@ -109,10 +145,11 @@ void ses_path_print(ses_path_t* path, ScfEfunction* f) child = path->connections->data[i]; if (child->parent == path) { - printf("\033[34mconnection: %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m", + printf("\n"); + printf("\033[34mconnection: %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m\n", child->index, child->n_diodes, child->n_NPNs, child->n_PNPs, child->n_capacitors, child->n_transistors, path->index); - ses_path_print(child, f); + ses_path_print(child); } else printf("\033[34mconnection: %d\033[0m\n", child->index); } @@ -122,10 +159,11 @@ void ses_path_print(ses_path_t* path, ScfEfunction* f) for (i = 0; i < path->childs->size; i++) { child = path->childs->data[i]; - printf("\033[32mchild : %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m", + printf("\n"); + printf("\033[32mchild : %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m\n", child->index, child->n_diodes, child->n_NPNs, child->n_PNPs, child->n_capacitors, child->n_transistors, path->index); - ses_path_print(child, f); + ses_path_print(child); } } @@ -133,15 +171,16 @@ void ses_path_print(ses_path_t* path, ScfEfunction* f) for (i = 0; i < path->bridges->size; i++) { child = path->bridges->data[i]; - printf("\033[33mbridge: %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m", + printf("\n"); + printf("\033[33mbridge: %d, n_diodes: %d, n_NPNs: %d, n_PNPs: %d, n_capacitors: %d, n_transistors: %d, parent: %d, \033[0m\n", child->index, child->n_diodes, child->n_NPNs, child->n_PNPs, child->n_capacitors, child->n_transistors, path->index); - ses_path_print(child, f); + ses_path_print(child); } } } -void ses_paths_print(scf_vector_t* paths, ScfEfunction* f) +void ses_paths_print(scf_vector_t* paths) { ses_path_t* path; @@ -149,8 +188,8 @@ void ses_paths_print(scf_vector_t* paths, ScfEfunction* f) for (i = 0; i < paths->size; i++) { path = paths->data[i]; - ses_path_print(path, f); - printf("\n"); + ses_path_print(path); + printf("------------------------\n"); } } @@ -166,12 +205,12 @@ int ses_path_is_child(ScfEfunction* f, ses_path_t* parent, ses_path_t* child) for (i = 0; i < parent->pins->size; i++) { p = parent->pins->data[i]; - if (ses_same_line(f, p, cp0)) { + if (ses_same_line(p, cp0)) { j = i; continue; } - if (ses_same_line(f, p, cp1)) { + if (ses_same_line(p, cp1)) { if (j >= 0) return 1; return 0; @@ -367,19 +406,32 @@ int ses_path_add(ScfEfunction* f, ses_path_t* parent, ses_path_t* child) child->parent_p1 = -1; int j; + int k; for (j = 0; j < parent->pins->size; j++) { p0 = parent->pins->data[j]; - if (ses_same_line(f, p0, cp0)) + if (ses_same_line(p0, cp0)) child->parent_p0 = (j + 1) & ~0x1; - else if (ses_same_line(f, p0, cp1)) + else if (ses_same_line(p0, cp1)) child->parent_p1 = j; if (child->parent_p0 >= 0 && child->parent_p1 >= 0) break; } + if (child->parent_p0 > child->parent_p1) { + j = 0; + k = child->pins->size - 1; + while (j < k) { + SCF_XCHG(child->pins->data[j], child->pins->data[k]); + j++; + k--; + } + + SCF_XCHG(child->parent_p0, child->parent_p1); + } + p0 = parent->pins->data[0]; p1 = parent->pins->data[parent->pins->size - 1]; diff --git a/ses_step_battery.c b/ses_step_battery.c index eef62c7..dd9790e 100644 --- a/ses_step_battery.c +++ b/ses_step_battery.c @@ -1,18 +1,18 @@ #include"ses_core.h" -static int _battery_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _battery_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { ScfEcomponent* c; ScfEline* el; ScfEpin* p; c = f->components[0]; - c->v = 6; + c->v = 5; p = c->pins[SCF_EDA_Battery_POS]; - p->v = 6; + p->v = 5; el = f->elines[p->lid]; - el->v = 6; + el->v = 5; el->vconst = 1; p = c->pins[SCF_EDA_Battery_NEG]; diff --git a/ses_step_dc_diode.c b/ses_step_dc_diode.c index b4eaa99..8887ca9 100644 --- a/ses_step_dc_diode.c +++ b/ses_step_dc_diode.c @@ -60,24 +60,41 @@ static int __dc_diode_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, S pb = c->pins[SCF_EDA_Diode_POS]; pe = c->pins[SCF_EDA_Diode_NEG]; - lb = ses_line(root, pb); - le = ses_line(root, pe); + lb = c->pf->elines[pb->lid]; + le = c->pf->elines[pe->lid]; if (lb == LP && le == LN) { - if (pb->IC) - scf_loge("Diode IC%ld_c%ld, short connected\n", pb->IC->id, c->id); - else - scf_loge("Diode c%ld, short connected\n", c->id); + scf_loge("short connected, "); + ses_pin_print(pb); + printf("\n"); return -EINVAL; } - if (__ses_path_neg(root, lb, LP, LN) && !__ses_path_pos(root, lb, LP, LN)) { + int neg = __ses_path_neg(root, lb, LP, LN); + int pos = __ses_path_pos(root, lb, LP, LN); + + if (neg && !pos) { c->status = SCF_EDA_Status_OFF; - if (pb->IC) - scf_loge("\033[34mDiode IC%ld_c%ld, status: %d\033[0m\n", pb->IC->id, c->id, c->status); - else - scf_loge("\033[34mDiode c%ld, status: %d\033[0m\n", c->id, c->status); + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("\n"); + continue; + } + + if (!neg && pos && SCF_EDA_Status_ON == c->status) { + // c->status = SCF_EDA_Status_OFF; + + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("\n"); + continue; + } + + if (c->lock) { + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_Diode_OFF); continue; } @@ -87,10 +104,6 @@ static int __dc_diode_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, S pe->v = le->v; pb->v = le->v + SCF_EDA_V_Diode_ON; - lb->v = pb->v; - - if (le->v == Bn->v) - lb->vconst = 1; if (pb->v > Bp->v) c->status = SCF_EDA_Status_OFF; @@ -101,53 +114,45 @@ static int __dc_diode_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, S pb->v = lb->v; pe->v = lb->v - SCF_EDA_V_Diode_ON; - le->v = pe->v; if (lb->v == Bp->v) le->vconst = 1; - if (pe->v < Bn->v) + if (pe->v < Bn->v - 0.01) c->status = SCF_EDA_Status_OFF; else c->status = SCF_EDA_Status_ON; } else if (lb->v >= le->v + SCF_EDA_V_Diode_OFF) { - if (le->v == Bn->v) - lb->vconst = 1; - else if (lb->v == Bp->v) - le->vconst = 1; - - lb->v = le->v + SCF_EDA_V_Diode_ON; - pb->v = lb->v; + pb->v = le->v + SCF_EDA_V_Diode_ON; pe->v = le->v; - if (pb->v > Bp->v) + if (pb->v > Bp->v + 0.01) c->status = SCF_EDA_Status_OFF; else c->status = SCF_EDA_Status_ON; } else { pb->v = lb->v; pe->v = le->v; - c->status = SCF_EDA_Status_OFF; +// c->status = SCF_EDA_Status_OFF; } - if (pb->IC) - scf_loge("\033[34mDiode IC%ld_c%ld, status: %d, pb: %lg, pe: %lg, diff: %lg\033[0m\n", pb->IC->id, c->id, c->status, pb->v, pe->v, pb->v - pe->v); - else - scf_loge("\033[34mDiode c%ld, status: %d, pb: %lg, pe: %lg, diff: %lg\033[0m\n", c->id, c->status, pb->v, pe->v, pb->v - pe->v); + scf_logi("\033[34m status: %d, lock: %d, ", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_Diode_OFF); } return 0; } -static int _dc_diode_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _dc_diode_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { ScfEcomponent* B = f->components[0]; ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEline* LP = ses_line(f, Bp); - ScfEline* LN = ses_line(f, Bn); + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); __dc_dfs_init(f, NULL); diff --git a/ses_step_dc_npn.c b/ses_step_dc_npn.c index 2fa2115..00af987 100644 --- a/ses_step_dc_npn.c +++ b/ses_step_dc_npn.c @@ -28,34 +28,41 @@ static int __dc_npn_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, Scf pc = c->pins[SCF_EDA_NPN_C]; pe = c->pins[SCF_EDA_NPN_E]; - lb = ses_line(root, pb); - le = ses_line(root, pe); + lb = ses_top_pline(pb); + le = ses_top_pline(pe); if (lb == LP && le == LN) { - if (pb->IC) - scf_loge("NPN IC%ld_T%ld, short connected\n", pb->IC->id, c->id); - else - scf_loge("NPN T%ld, short connected\n", c->id); + scf_loge("short connected, "); + ses_pin_print(pb); + printf("\n"); return -EINVAL; } - if (__ses_path_neg(root, lb, LP, LN) && !__ses_path_pos(root, lb, LP, LN)) { + int neg = __ses_path_neg(root, lb, LP, LN); + int pos = __ses_path_pos(root, lb, LP, LN); +#if 0 + if (neg && !pos) { c->status = SCF_EDA_Status_OFF; - if (pb->IC) - scf_logi("NPN IC%ld_T%ld, status: %d\n", pb->IC->id, c->id, c->status); - else - scf_logi("NPN T%ld, status: %d\n", c->id, c->status); + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); continue; } + if (!neg && pos && SCF_EDA_Status_ON == c->status) { + c->status = SCF_EDA_Status_OFF; + + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); + continue; + } +#endif if (c->lock) { - if (pb->IC) - scf_logi("\033[34mIC%ld_T%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - pb->IC->id, c->id, c->status, c->lock, pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); - else - scf_logi("\033[34mT%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - c->id, c->status, c->lock, pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); continue; } @@ -65,10 +72,6 @@ static int __dc_npn_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, Scf pe->v = le->v; pb->v = le->v + SCF_EDA_V_NPN_ON; - lb->v = pb->v; - - if (le->v == Bn->v) - lb->vconst = 1; if (pb->v > Bp->v) c->status = SCF_EDA_Status_OFF; @@ -79,56 +82,42 @@ static int __dc_npn_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, Scf pb->v = lb->v; pe->v = lb->v - SCF_EDA_V_NPN_ON; - le->v = pe->v; - if (lb->v == Bp->v) - le->vconst = 1; - - if (pe->v < Bn->v) + if (pe->v < Bn->v - 0.01) c->status = SCF_EDA_Status_OFF; else c->status = SCF_EDA_Status_ON; } else if (lb->v >= le->v + SCF_EDA_V_NPN_OFF) { - if (le->v == Bn->v) - lb->vconst = 1; - else if (lb->v == Bp->v) - le->vconst = 1; - - lb->v = le->v + SCF_EDA_V_NPN_ON; + pb->v = le->v + SCF_EDA_V_NPN_ON; pb->v = lb->v; - pe->v = le->v; - if (pb->v > Bp->v) + if (pb->v > Bp->v + 0.01) c->status = SCF_EDA_Status_OFF; else c->status = SCF_EDA_Status_ON; } else { pb->v = lb->v; pe->v = le->v; - - c->status = SCF_EDA_Status_OFF; +// c->status = SCF_EDA_Status_OFF; } - if (pb->IC) - scf_logi("\033[34mIC%ld_T%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - pb->IC->id, c->id, c->status, c->lock, pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); - else - scf_logi("\033[34mT%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - c->id, c->status, c->lock, pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); + scf_logi("\033[34m status: %d, lock: %d, ", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", pb->v, pe->v, pb->v - pe->v, SCF_EDA_V_NPN_OFF); } return 0; } -static int _dc_npn_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _dc_npn_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { ScfEcomponent* B = f->components[0]; ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEline* LP = ses_line(f, Bp); - ScfEline* LN = ses_line(f, Bn); + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); return __dc_npn_status(f, f, Bp, Bn, LP, LN); } diff --git a/ses_step_dc_pnp.c b/ses_step_dc_pnp.c index b93920b..a2c8b41 100644 --- a/ses_step_dc_pnp.c +++ b/ses_step_dc_pnp.c @@ -28,24 +28,23 @@ static int __dc_pnp_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, Scf pc = c->pins[SCF_EDA_PNP_C]; pe = c->pins[SCF_EDA_PNP_E]; - lb = ses_line(root, pb); - le = ses_line(root, pe); + lb = ses_top_pline(pb); + le = ses_top_pline(pe); if (le == LP && lb == LN) { - if (pb->IC) - scf_loge("PNP IC%ld_c%ld, short connected\n", pb->IC->id, c->id); - else - scf_loge("PNP c%ld, short connected\n", c->id); + scf_loge("short connected, "); + ses_pin_print(pb); + printf("\n"); return -EINVAL; } - if (__ses_path_pos(root, lb, LP, LN) && !__ses_path_neg(root, lb, LP, LN)) { - c->status = SCF_EDA_Status_OFF; + int neg = __ses_path_neg(root, lb, LP, LN); + int pos = __ses_path_pos(root, lb, LP, LN); - if (pb->IC) - scf_loge("PNP IC%ld_c%ld, status: %d\n", pb->IC->id, c->id, c->status); - else - scf_loge("PNP c%ld, status: %d\n", c->id, c->status); + if (c->lock) { + scf_logi("\033[34m status: %d, lock: %d, \033[0m", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\n", pb->v, pe->v, pe->v - pb->v, SCF_EDA_V_PNP_OFF); continue; } @@ -55,73 +54,52 @@ static int __dc_pnp_status(ScfEfunction* root, ScfEfunction* f, ScfEpin* Bp, Scf pe->v = le->v; pb->v = le->v - SCF_EDA_V_PNP_ON; - lb->v = pb->v; - if (le->v == Bp->v) - lb->vconst = 1; - - if (pb->v < Bn->v) { - if (!c->lock) - c->status = SCF_EDA_Status_OFF; - } else + if (pb->v < Bn->v) + c->status = SCF_EDA_Status_OFF; + else c->status = SCF_EDA_Status_ON; } else if (le->v < SCF_EDA_V_MIN) { pb->v = lb->v; pe->v = lb->v + SCF_EDA_V_PNP_ON; - le->v = pe->v; - - if (lb->v == Bn->v) - le->vconst = 1; - if (pe->v > Bp->v) { - if (!c->lock) - c->status = SCF_EDA_Status_OFF; - } else + if (pe->v > Bp->v + 0.01) + c->status = SCF_EDA_Status_OFF; + else c->status = SCF_EDA_Status_ON; } else if (lb->v <= le->v - SCF_EDA_V_PNP_OFF) { - if (le->v == Bp->v) - lb->vconst = 1; - else if (lb->v == Bn->v) - le->vconst = 1; - - lb->v = le->v - SCF_EDA_V_PNP_ON; - pb->v = lb->v; + pb->v = le->v - SCF_EDA_V_PNP_ON; pe->v = le->v; - if (pb->v < Bn->v) { - if (!c->lock) - c->status = SCF_EDA_Status_OFF; - } else + if (pb->v < Bn->v - 0.01) + c->status = SCF_EDA_Status_OFF; + else c->status = SCF_EDA_Status_ON; } else { pb->v = lb->v; pe->v = le->v; - if (!c->lock) - c->status = SCF_EDA_Status_OFF; + // c->status = SCF_EDA_Status_OFF; } - if (pb->IC) - scf_loge("\033[34mIC%ld_c%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - pb->IC->id, c->id, c->status, c->lock, pb->v, pe->v, pe->v - pb->v, SCF_EDA_V_PNP_OFF); - else - scf_loge("\033[34mc%ld, status: %d, lock: %d, pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", - c->id, c->status, c->lock, pb->v, pe->v, pe->v - pb->v, SCF_EDA_V_PNP_OFF); + scf_logi("\033[34m status: %d, lock: %d, ", c->status, c->lock); + ses_pin_print(pb); + printf("pb->v: %lg, pe->v: %lg, diff: %lg, off: %lg\033[0m\n", pb->v, pe->v, pe->v - pb->v, SCF_EDA_V_PNP_OFF); } return 0; } -static int _dc_pnp_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _dc_pnp_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { ScfEcomponent* B = f->components[0]; ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEline* LP = ses_line(f, Bp); - ScfEline* LN = ses_line(f, Bn); + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); return __dc_pnp_status(f, f, Bp, Bn, LP, LN); } diff --git a/ses_step_draw.c b/ses_step_draw.c index a2bc48b..c89a7e7 100644 --- a/ses_step_draw.c +++ b/ses_step_draw.c @@ -108,7 +108,7 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) case SCF_EDA_Diode: n = snprintf(text, sizeof(text) - 1, "D%ld", c->id); - cairo_move_to(cr, c->x + 15, c->y + 10); + cairo_move_to(cr, c->x + 10, c->y + 8); break; case SCF_EDA_NPN: @@ -121,15 +121,23 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) cairo_move_to(cr, c->x - 20 - n * 10, c->y + 12); break; + case SCF_EDA_NOT: + n = snprintf(text, sizeof(text) - 1, "%ld", c->id); + cairo_move_to(cr, c->x + 10, c->y + 8); + break; + case SCF_EDA_NAND: case SCF_EDA_NOR: - case SCF_EDA_NOT: + case SCF_EDA_AND: + case SCF_EDA_OR: + case SCF_EDA_XOR: + case SCF_EDA_ADD: n = snprintf(text, sizeof(text) - 1, "%ld", c->id); if (c->pins[2]->x < c->x) - cairo_move_to(cr, c->x + 10, c->y - 12); + cairo_move_to(cr, c->x + 10, c->y - 20); else - cairo_move_to(cr, c->x - 10 - n * 10, c->y - 12); + cairo_move_to(cr, c->x - 10 - n * 10, c->y - 20); break; default: n = snprintf(text, sizeof(text) - 1, "%ld", c->id); @@ -140,6 +148,13 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) cairo_show_text(cr, text); cairo_stroke(cr); + cairo_set_font_size(cr, 16); +#if 0 + snprintf(text, sizeof(text) - 1, "%ld", c->color); + cairo_move_to(cr, c->x + 4, c->y - 24); + cairo_show_text(cr, text); + cairo_stroke(cr); +#endif if ((SCF_EDA_Diode == c->type || SCF_EDA_NPN == c->type) && SCF_EDA_Status_OFF == c->status) SHOW_COLOR(cr, 0.0, 0.6, 0.6); else @@ -158,8 +173,6 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) int dx1; int dy1; - int dx2; - int dy2; int dx3; int dy3; @@ -252,9 +265,9 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) SHOW_COLOR(cr, 0.0, 0.0, 0.0); - if (c->uf < 1e-6) + if (c->uf < 1e-5) snprintf(text, sizeof(text) - 1, "%lgpF", c->uf * 1e6); - else if (c->uf < 1e-3) + else if (c->uf < 1e-2) snprintf(text, sizeof(text) - 1, "%lgnF", c->uf * 1000.0); else snprintf(text, sizeof(text) - 1, "%lguF", c->uf); @@ -364,8 +377,8 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) case SCF_EDA_Diode: p = c->pins[SCF_EDA_Diode_POS]; - vertical(&dx0, &dy0, c->x - p->x, c->y - p->y, 6); - forward (&dx1, &dy1, c->x - p->x, c->y - p->y, 6); + vertical(&dx0, &dy0, c->x - p->x, c->y - p->y, 8); + forward (&dx1, &dy1, c->x - p->x, c->y - p->y, 8); cairo_move_to(cr, p->x, p->y); cairo_line_to(cr, c->x - dx1, c->y - dy1); @@ -381,6 +394,7 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) cairo_line_to (cr, c->x + dx1, c->y + dy1); cairo_rel_move_to(cr, dx0, dy0); cairo_rel_line_to(cr, -dx0 * 2, -dy0 * 2); + cairo_stroke(cr); ses_text_a(cr, c->x + 10, c->y + 25, c->a); cairo_stroke(cr); @@ -581,11 +595,21 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) cairo_line_to(cr, c->x - 6, c->y + 10); cairo_line_to(cr, c->x - 6, c->y - 10); cairo_line_to(cr, c->x + 6, c->y - 10); + cairo_stroke(cr); + if (p0 == c->pins[SCF_EDA_NAND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); cairo_move_to(cr, c->x - 6, c->y - 5); cairo_line_to(cr, p0->x, c->y - 5); cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + if (p1 == c->pins[SCF_EDA_NAND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); cairo_move_to(cr, c->x - 6, c->y + 5); cairo_line_to(cr, p1->x, c->y + 5); cairo_line_to(cr, p1->x, p1->y); @@ -605,17 +629,27 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) cairo_line_to(cr, c->x + 6, c->y + 10); cairo_line_to(cr, c->x + 6, c->y - 10); cairo_line_to(cr, c->x - 6, c->y - 10); + cairo_stroke(cr); + if (p0 == c->pins[SCF_EDA_NAND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); cairo_move_to(cr, c->x + 6, c->y - 5); cairo_line_to(cr, p0->x, c->y - 5); cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + if (p1 == c->pins[SCF_EDA_NAND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); cairo_move_to(cr, c->x + 6, c->y + 5); cairo_line_to(cr, p1->x, c->y + 5); cairo_line_to(cr, p1->x, p1->y); } cairo_stroke(cr); - +#if 0 p = c->pins[SCF_EDA_NAND_POS]; if (p->y < c->y) { cairo_move_to(cr, c->x, c->y - 10); @@ -634,6 +668,196 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) } cairo_stroke(cr); +#endif + break; + + case SCF_EDA_AND: + p = c->pins[SCF_EDA_AND_OUT]; + p0 = c->pins[SCF_EDA_AND_IN0]; + p1 = c->pins[SCF_EDA_AND_IN1]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); + + if (c->x < p->x) { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y); + cairo_line_to(cr, c->x + 16, c->y); + cairo_stroke(cr); + + cairo_arc(cr, c->x + 6, c->y, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_stroke(cr); + + cairo_move_to(cr, c->x + 6, c->y + 10); + cairo_line_to(cr, c->x - 6, c->y + 10); + cairo_line_to(cr, c->x - 6, c->y - 10); + cairo_line_to(cr, c->x + 6, c->y - 10); + cairo_stroke(cr); + + if (p0 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x - 6, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + + if (p1 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x - 6, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); + } else { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y); + cairo_line_to(cr, c->x - 16, c->y); + cairo_stroke(cr); + + cairo_arc(cr, c->x - 6, c->y, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_stroke(cr); + + cairo_move_to(cr, c->x - 6, c->y + 10); + cairo_line_to(cr, c->x + 6, c->y + 10); + cairo_line_to(cr, c->x + 6, c->y - 10); + cairo_line_to(cr, c->x - 6, c->y - 10); + cairo_stroke(cr); + + if (p0 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x + 6, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + + if (p1 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x + 6, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); + } + cairo_stroke(cr); + break; + + case SCF_EDA_ADD: + p = c->pins[SCF_EDA_ADD_OUT]; + pc = c->pins[SCF_EDA_ADD_CF]; + p0 = c->pins[SCF_EDA_ADD_IN0]; + p1 = c->pins[SCF_EDA_ADD_IN1]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); + + if (p->y > pc->y) + SCF_XCHG(p, pc); + + cairo_rectangle(cr, c->x - 18, c->y - 18, 36, 36); + cairo_stroke(cr); + + if (c->x < p->x) { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y - 10); + cairo_line_to(cr, c->x + 18, c->y - 10); + cairo_stroke(cr); + + cairo_move_to(cr, pc->x, pc->y); + cairo_line_to(cr, pc->x, c->y + 10); + cairo_line_to(cr, c->x + 18, c->y + 10); + cairo_stroke(cr); + + if (p->flags & SCF_EDA_PIN_CF) { + cairo_set_font_size(cr, 22); + cairo_move_to(cr, c->x - 4, c->y + 14); + cairo_show_text(cr, "Σ"); + cairo_stroke(cr); + + cairo_set_font_size(cr, 14); + cairo_move_to(cr, c->x - 2, c->y - 4); + cairo_show_text(cr, "C0"); + } else { + cairo_set_font_size(cr, 22); + cairo_move_to(cr, c->x - 4, c->y); + cairo_show_text(cr, "Σ"); + cairo_stroke(cr); + + cairo_set_font_size(cr, 14); + cairo_move_to(cr, c->x - 2, c->y + 14); + cairo_show_text(cr, "C0"); + } + cairo_stroke(cr); + + if (p0 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x - 18, c->y - 10); + cairo_line_to(cr, p0->x, c->y - 10); + cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + + if (p1 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x - 18, c->y + 10); + cairo_line_to(cr, p1->x, c->y + 10); + cairo_line_to(cr, p1->x, p1->y); + } else { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y + 10); + cairo_line_to(cr, c->x - 18, c->y + 10); + cairo_stroke(cr); + + cairo_move_to(cr, pc->x, pc->y); + cairo_line_to(cr, pc->x, c->y - 10); + cairo_line_to(cr, c->x - 18, c->y - 10); + cairo_stroke(cr); + + if (p->flags & SCF_EDA_PIN_CF) { + cairo_set_font_size(cr, 22); + cairo_move_to(cr, c->x - 4, c->y - 4); + cairo_show_text(cr, "Σ"); + cairo_stroke(cr); + + cairo_set_font_size(cr, 14); + cairo_move_to(cr, c->x - 16, c->y + 14); + cairo_show_text(cr, "C0"); + } else { + cairo_set_font_size(cr, 22); + cairo_move_to(cr, c->x - 4, c->y + 14); + cairo_show_text(cr, "Σ"); + cairo_stroke(cr); + + cairo_set_font_size(cr, 14); + cairo_move_to(cr, c->x - 16, c->y - 4); + cairo_show_text(cr, "C0"); + } + cairo_stroke(cr); + + if (p0 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x + 18, c->y - 10); + cairo_line_to(cr, p0->x, c->y - 10); + cairo_line_to(cr, p0->x, p0->y); + cairo_stroke(cr); + + if (p1 == c->pins[SCF_EDA_AND_IN1]) + SHOW_COLOR(cr, 0.0, 0.0, 0.8); + else + SHOW_COLOR(cr, 0.6, 0.6, 0.0); + cairo_move_to(cr, c->x + 18, c->y + 10); + cairo_line_to(cr, p1->x, c->y + 10); + cairo_line_to(cr, p1->x, p1->y); + } + cairo_stroke(cr); break; case SCF_EDA_NOR: @@ -717,6 +941,7 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) } cairo_stroke(cr); +#if 0 p = c->pins[SCF_EDA_NOR_POS]; if (p->y < c->y) { cairo_move_to(cr, c->x, c->y - 10); @@ -735,67 +960,211 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) } cairo_stroke(cr); +#endif break; - case SCF_EDA_NOT: - p = c->pins[SCF_EDA_NOT_OUT]; + case SCF_EDA_OR: + p = c->pins[SCF_EDA_OR_OUT]; + p0 = c->pins[SCF_EDA_OR_IN0]; + p1 = c->pins[SCF_EDA_OR_IN1]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); if (c->x < p->x) { cairo_move_to(cr, p->x, p->y); cairo_line_to(cr, p->x, c->y); - cairo_line_to(cr, c->x + 24, c->y); + cairo_line_to(cr, c->x + 16, c->y); cairo_stroke(cr); - cairo_arc(cr, c->x + 20, c->y, 4, 0, 2 * M_PI); + cairo_save(cr); + cairo_translate(cr, c->x, c->y); + cairo_scale(cr, 1.6, 1.0); + cairo_arc (cr, 0, 0, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_restore(cr); cairo_stroke(cr); - cairo_move_to(cr, c->x + 16, c->y); - cairo_line_to(cr, c->x - 16, c->y + 10); - cairo_line_to(cr, c->x - 16, c->y - 10); - cairo_line_to(cr, c->x + 16, c->y); + cairo_save(cr); + cairo_translate(cr, c->x - 6, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); - p = c->pins[SCF_EDA_NOT_IN]; - cairo_move_to(cr, c->x - 16, c->y); - cairo_line_to(cr, p->x, c->y); - cairo_line_to(cr, p->x, p->y); + cairo_move_to(cr, c->x, c->y + 10); + cairo_line_to(cr, c->x - 6, c->y + 10); + cairo_move_to(cr, c->x - 6, c->y - 10); + cairo_line_to(cr, c->x, c->y - 10); + + cairo_move_to(cr, c->x - 2, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + + cairo_move_to(cr, c->x - 2, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); } else { cairo_move_to(cr, p->x, p->y); cairo_line_to(cr, p->x, c->y); - cairo_line_to(cr, c->x - 24, c->y); + cairo_line_to(cr, c->x - 16, c->y); cairo_stroke(cr); - cairo_arc(cr, c->x - 20, c->y, 4, 0, 2 * M_PI); + cairo_save(cr); + cairo_translate(cr, c->x, c->y); + cairo_scale(cr, 1.6, 1.0); + cairo_arc (cr, 0, 0, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_restore(cr); cairo_stroke(cr); - cairo_move_to(cr, c->x - 16, c->y); - cairo_line_to(cr, c->x + 16, c->y + 10); - cairo_line_to(cr, c->x + 16, c->y - 10); + cairo_save(cr); + cairo_translate(cr, c->x + 6, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_move_to(cr, c->x, c->y + 10); + cairo_line_to(cr, c->x + 6, c->y + 10); + cairo_move_to(cr, c->x + 6, c->y - 10); + cairo_line_to(cr, c->x, c->y - 10); + + cairo_move_to(cr, c->x + 2, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + + cairo_move_to(cr, c->x + 2, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); + } + cairo_stroke(cr); + break; + + case SCF_EDA_XOR: + p = c->pins[SCF_EDA_XOR_OUT]; + p0 = c->pins[SCF_EDA_XOR_IN0]; + p1 = c->pins[SCF_EDA_XOR_IN1]; + + if (p0->y > p1->y) + SCF_XCHG(p0, p1); + + if (c->x < p->x) { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y); + cairo_line_to(cr, c->x + 16, c->y); + cairo_stroke(cr); + + cairo_save(cr); + cairo_translate(cr, c->x, c->y); + cairo_scale(cr, 1.6, 1.0); + cairo_arc (cr, 0, 0, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_save(cr); + cairo_translate(cr, c->x - 6, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_save(cr); + cairo_translate(cr, c->x - 11, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, -0.5 * M_PI, 0.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_move_to(cr, c->x, c->y + 10); + cairo_line_to(cr, c->x - 6, c->y + 10); + cairo_move_to(cr, c->x - 6, c->y - 10); + cairo_line_to(cr, c->x, c->y - 10); + + cairo_move_to(cr, c->x - 2, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + + cairo_move_to(cr, c->x - 2, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); + } else { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, p->x, c->y); cairo_line_to(cr, c->x - 16, c->y); + cairo_stroke(cr); - p = c->pins[SCF_EDA_NOT_IN]; - cairo_move_to(cr, c->x + 16, c->y); - cairo_line_to(cr, p->x, c->y); - cairo_line_to(cr, p->x, p->y); + cairo_save(cr); + cairo_translate(cr, c->x, c->y); + cairo_scale(cr, 1.6, 1.0); + cairo_arc (cr, 0, 0, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_save(cr); + cairo_translate(cr, c->x + 6, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_save(cr); + cairo_translate(cr, c->x + 11, c->y); + cairo_scale(cr, 0.6, 1.0); + cairo_arc (cr, 0, 0, 10, 0.5 * M_PI, 1.5 * M_PI); + cairo_restore(cr); + cairo_stroke(cr); + + cairo_move_to(cr, c->x, c->y + 10); + cairo_line_to(cr, c->x + 6, c->y + 10); + cairo_move_to(cr, c->x + 6, c->y - 10); + cairo_line_to(cr, c->x, c->y - 10); + + cairo_move_to(cr, c->x + 2, c->y - 5); + cairo_line_to(cr, p0->x, c->y - 5); + cairo_line_to(cr, p0->x, p0->y); + + cairo_move_to(cr, c->x + 2, c->y + 5); + cairo_line_to(cr, p1->x, c->y + 5); + cairo_line_to(cr, p1->x, p1->y); } cairo_stroke(cr); + break; - p = c->pins[SCF_EDA_NOT_POS]; - if (p->y < c->y) { - cairo_move_to(cr, c->x, c->y - 5); - cairo_line_to(cr, p->x, p->y); + case SCF_EDA_NOT: + p = c->pins[SCF_EDA_NOT_OUT]; - p = c->pins[SCF_EDA_NOT_NEG]; - cairo_move_to(cr, c->x, c->y + 5); + if (c->y < p->y) { + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, c->x, c->y + 18); + cairo_stroke(cr); + + cairo_arc(cr, c->x, c->y + 14, 4, 0, 2 * M_PI); + cairo_stroke(cr); + + cairo_move_to(cr, c->x, c->y + 10); + cairo_line_to(cr, c->x - 6, c->y - 8); + cairo_line_to(cr, c->x + 6, c->y - 8); + cairo_line_to(cr, c->x, c->y + 10); + + p = c->pins[SCF_EDA_NOT_IN]; + cairo_move_to(cr, c->x, c->y - 8); cairo_line_to(cr, p->x, p->y); } else { - cairo_move_to(cr, c->x, c->y + 5); - cairo_line_to(cr, p->x, p->y); + cairo_move_to(cr, p->x, p->y); + cairo_line_to(cr, c->x, c->y - 18); + cairo_stroke(cr); - p = c->pins[SCF_EDA_NOT_NEG]; - cairo_move_to(cr, c->x, c->y - 5); + cairo_arc(cr, c->x, c->y - 14, 4, 0, 2 * M_PI); + cairo_stroke(cr); + + cairo_move_to(cr, c->x, c->y - 10); + cairo_line_to(cr, c->x - 6, c->y + 8); + cairo_line_to(cr, c->x + 6, c->y + 8); + cairo_line_to(cr, c->x, c->y - 10); + + p = c->pins[SCF_EDA_NOT_IN]; + cairo_move_to(cr, c->x, c->y + 8); cairo_line_to(cr, p->x, p->y); } - cairo_stroke(cr); break; default: @@ -804,10 +1173,9 @@ void __ses_function_draw(ScfEfunction* f, cairo_t* cr) } } -int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32_t bw, uint32_t bh, int64_t ns, int64_t count) +int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32_t bw, uint32_t bh, int64_t ps, int64_t count) { ScfEcomponent* B; - ScfEcomponent* c; ScfEline* el; ScfLine* l; @@ -828,22 +1196,23 @@ int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32 cairo_set_source_rgb(cr, 0, 0, 0); if (count >= 0) { - int64_t t = ns * count; - int64_t s = t / 1000000000; - t %= 1000000000; - int64_t ms = t / 1000000; + int64_t t = ps * count; + int64_t s = t / (1000000LL * 1000000LL); + t %= 1000000LL * 1000000LL; + int64_t ms = t / (1000000LL * 1000LL); + t %= 1000000LL * 1000LL; + int64_t us = t / 1000000; t %= 1000000; - int64_t us = t / 1000; + int64_t ns = t / 1000; t %= 1000; uint8_t time[512]; - snprintf(time, sizeof(time) - 1, "%03ld,%03ld,%03ld,%03ldns", s, ms, us, t); + snprintf(time, sizeof(time) - 1, "%03ld,%03ld,%03ld,%03ld,%03ldps", s, ms, us, ns, t); cairo_move_to (cr, 10, 20); cairo_show_text(cr, time); cairo_stroke(cr); } - long i; long j; long k; @@ -867,10 +1236,13 @@ int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32 SHOW_COLOR(cr, 0.8, 0, 0); else if (SCF_EDA_PIN_IN & el->flags) - SHOW_COLOR(cr, 0, 0, 0.8); + SHOW_COLOR(cr, 1.0, 0.6, 0.07); - else if (SCF_EDA_PIN_CONST & el->flags) - SHOW_COLOR(cr, 0, 0.6, 0); + else if (SCF_EDA_PIN_DIV0 & el->flags) + SHOW_COLOR(cr, 0, 1, 0); + + else if (SCF_EDA_PIN_SHIFT & el->flags) + SHOW_COLOR(cr, 0.5, 0, 0.5); else if (SCF_EDA_PIN_CF & el->flags) SHOW_COLOR(cr, 0.8, 0, 0.8); @@ -895,6 +1267,22 @@ int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32 cairo_move_to (cr, l->x0 - 8 - n * 13, l->y0 + 12); cairo_show_text(cr, text); cairo_stroke(cr); + + if (el->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_OUT | SCF_EDA_PIN_DIV0 | SCF_EDA_PIN_SHIFT)) { + cairo_set_font_size(cr, 22); + + if (el->flags & SCF_EDA_PIN_DIV0) + n = snprintf(text, sizeof(text) - 1, "DIV0"); + + else if (el->flags & SCF_EDA_PIN_SHIFT) + n = snprintf(text, sizeof(text) - 1, "T%ld", el->io_lid); + else + n = snprintf(text, sizeof(text) - 1, "B%ld", el->io_lid); + + cairo_move_to (cr, l->x0 - 8 - n * 13, l->y0 + 36); + cairo_show_text(cr, text); + cairo_stroke(cr); + } } cairo_set_line_width(cr, 3); @@ -956,7 +1344,70 @@ int ses_draw(ScfEfunction* f, const char* file, uint32_t bx, uint32_t by, uint32 return 0; } -static int _draw_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static void get_IC_name(ScfEcomponent* IC, char* buf, long size) +{ + if (!IC) + return; + + if (IC->pf->IC) + get_IC_name(IC->pf->IC, buf, size); + + long len = strlen(buf); + + switch (IC->type) { + case SCF_EDA_NAND: + snprintf(buf + len, size - 1 - len, "Nand%ld_", IC->id); + break; + case SCF_EDA_NOR: + snprintf(buf + len, size - 1 - len, "Nor%ld_", IC->id); + break; + + case SCF_EDA_NOT: + snprintf(buf + len, size - 1 - len, "Not%ld_", IC->id); + break; + case SCF_EDA_AND: + snprintf(buf + len, size - 1 - len, "And%ld_", IC->id); + break; + case SCF_EDA_OR: + snprintf(buf + len, size - 1 - len, "Or%ld_", IC->id); + break; + + case SCF_EDA_XOR: + snprintf(buf + len, size - 1 - len, "Xor%ld_", IC->id); + break; + case SCF_EDA_ADD: + snprintf(buf + len, size - 1 - len, "Add%ld_", IC->id); + break; + default: + snprintf(buf + len, size - 1 - len, "IC%ld_", IC->id); + break; + }; +} + +static void __draw_IC(ScfEfunction* f, int64_t ps, int64_t count, int64_t i) +{ + ScfEcomponent* c; + int j; + + for (j = 0; j < f->n_components; j++) { + c = f->components[j]; + + if (c->f) { + __draw_IC(c->f, ps, count, i); + + char file[4096]; + + file[0] = '\0'; + get_IC_name(c, file, sizeof(file) - 1); + + snprintf(file + strlen(file), sizeof(file) - 1, "_%ld.png", i); + + ses_draw(c->f, file, c->f->x, c->f->y, c->f->w, c->f->h, ps, count); + } + } +} + +static int _draw_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { static int64_t i = 0; @@ -968,7 +1419,7 @@ static int _draw_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* #endif if (1 || count % 10 == 0) { -#if 1 +#if 0 static FILE* fp = NULL; if (!fp) fp = fopen("v.txt", "w"); @@ -976,7 +1427,9 @@ static int _draw_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* if (fp) fprintf(fp, "%ld, %lg\n", i, f->elines[4]->v); #endif - ses_draw(f, file, f->x, f->y, f->w, f->h, ns, count); + ses_draw(f, file, f->x, f->y, f->w, f->h, ps, count); + + __draw_IC(f, ps, count, i); i++; } diff --git a/ses_step_jr.c b/ses_step_jr.c index 3619044..3f44782 100644 --- a/ses_step_jr.c +++ b/ses_step_jr.c @@ -95,12 +95,14 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) for (i = 0; i < path->pins->size; i++) { p = path->pins->data[i]; - c = ses_component(f, p); + c = p->c; r2 = r; r += p->r + p->dr; - if (i & 0x1) + if (i & 0x1) { r += c->r + c->dr; + } + scf_logd("path: %d, i: %d, c%ldp%ld, p->r: %lg, p->dr: %lg, c->r: %lg, r: %lg\n", path->index, i, p->cid, p->id, p->r, p->dr, c->r, r); if (SCF_EDA_NPN == c->type && !(i & 0x1)) { p->sr = r2; @@ -109,13 +111,11 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) p->sr = r; p->pr = r; } - - scf_logd("path: %d, i: %d, c%ldp%ld, sr: %lg\n", path->index, i, p->cid, p->id, p->sr); + scf_logd("path: %d, i: %d, c%ldp%ld, sr: %lg, r: %lg\n", path->index, i, p->cid, p->id, p->sr, r); } if (path->childs) { - - printf("\033[32mchilds:\033[0m\n"); +// printf("\033[32mchilds:\033[0m\n"); for (i = path->childs->size - 1; i >= 0; i--) { child = path->childs->data[i]; @@ -128,7 +128,7 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) for (j = 0; j < path->pins->size; j++) { p = path->pins->data[j]; - if (ses_same_line(f, p, cp0)) { + if (ses_same_line(p, cp0)) { p0 = p; break; } @@ -140,7 +140,7 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) for ( ; j < path->pins->size; j++) { p = path->pins->data[j]; - if (ses_same_line(f, p, cp1)) { + if (ses_same_line(p, cp1)) { p1 = p; break; } @@ -170,7 +170,7 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) scf_logd("j: %d, c%ldp%ld, p->pr: %lg, p->sr: %lg\n", j, p->cid, p->id, p->pr, p->sr); } - scf_logi("child: %d, pr: %lg, dr: %lg\n", child->index, child->pr, dr); + scf_logd("child: %d, pr: %lg, dr: %lg\n", child->index, child->pr, dr); } } @@ -183,7 +183,7 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) for (j = 0; j < path->pins->size; j++) { p = path->pins->data[j]; - if (ses_same_line(f, p, cp1)) { + if (ses_same_line(p, cp1)) { child->parent_pr = p->pr; break; } @@ -195,6 +195,6 @@ int __ses_path_jr(ScfEfunction* f, ses_path_t* path) path->pr = p->pr; path->sr = p->sr; - scf_logi("path: %d, pr: %lg, sr: %lg\n\n", path->index, path->pr, path->sr); + scf_logd("path: %d, pr: %lg, sr: %lg\n\n", path->index, path->pr, path->sr); return 0; } diff --git a/ses_step_open.c b/ses_step_open.c index 1cc28e7..277ee2c 100644 --- a/ses_step_open.c +++ b/ses_step_open.c @@ -1,28 +1,28 @@ #include"ses_core.h" -static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN); -static int __dfs_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN); +static int __dfs_path_pos(ScfEline* el, ScfEline* LP, ScfEline* LN); +static int __dfs_path_neg(ScfEline* el, ScfEline* LP, ScfEline* LN); static int __dfs_path_pos2(ScfEfunction* f, ScfEpin* p2, ScfEline* LP, ScfEline* LN) { ScfEcomponent* c; ScfEpin* p; - if (__dfs_path_pos(f, f->elines[p2->lid], LP, LN)) + if (__dfs_path_pos(f->elines[p2->lid], LP, LN)) return 1; - if (p2->IC && p2->lid < p2->IC->n_pins) { - c = p2->IC; + if (p2->c->pf->IC && p2->lid < p2->c->pf->IC->n_pins) { + c = p2->c->pf->IC; p = c->pins[p2->lid]; p->vflag = 1; - if (__dfs_path_pos(c->pf, c->pf->elines[p->lid], LP, LN)) + if (__dfs_path_pos(c->pf->elines[p->lid], LP, LN)) return 1; } return 0; } -static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN) +static int __dfs_path_pos(ScfEline* el, ScfEline* LP, ScfEline* LN) { ScfEcomponent* c; ScfEpin* p; @@ -30,15 +30,15 @@ static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* long i; - if (LP == el) + if (ses_top_line(el) == LP) return 1; - if (LN == el) + if (ses_top_line(el) == LN) return 0; for (i = 0; i + 1 < el->n_pins; i += 2) { - c = f->components[el->pins[i]]; - p = c->pins [el->pins[i + 1]]; + c = el->pf->components[el->pins[i]]; + p = c->pins[el->pins[i + 1]]; if (p->vflag) continue; @@ -47,7 +47,7 @@ static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* if (c->f) { assert(p->id < c->f->n_elines); - if (__dfs_path_pos(c->f, c->f->elines[p->id], LP, LN)) + if (__dfs_path_pos(c->f->elines[p->id], LP, LN)) return 1; continue; } @@ -67,13 +67,13 @@ static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* p2 = c->pins[SCF_EDA_NPN_B]; p2->vflag = 1; - if (__dfs_path_pos2(f, p2, LP, LN)) + if (__dfs_path_pos2(el->pf, p2, LP, LN)) return 1; p2 = c->pins[SCF_EDA_NPN_C]; p2->vflag = 1; - if (__dfs_path_pos2(f, p2, LP, LN)) + if (__dfs_path_pos2(el->pf, p2, LP, LN)) return 1; continue; } else @@ -83,7 +83,7 @@ static int __dfs_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* continue; p2->vflag = 1; - if (__dfs_path_pos2(f, p2, LP, LN)) + if (__dfs_path_pos2(el->pf, p2, LP, LN)) return 1; } @@ -95,21 +95,21 @@ static int __dfs_path_neg2(ScfEfunction* f, ScfEpin* p2, ScfEline* LP, ScfEline* ScfEcomponent* c; ScfEpin* p; - if (__dfs_path_neg(f, f->elines[p2->lid], LP, LN)) + if (__dfs_path_neg(f->elines[p2->lid], LP, LN)) return 1; - if (p2->IC && p2->lid < p2->IC->n_pins) { - c = p2->IC; + if (p2->c->pf->IC && p2->lid < p2->c->pf->IC->n_pins) { + c = p2->c->pf->IC; p = c->pins[p2->lid]; p->vflag = 1; - if (__dfs_path_neg(c->pf, c->pf->elines[p->lid], LP, LN)) + if (__dfs_path_neg(c->pf->elines[p->lid], LP, LN)) return 1; } return 0; } -static int __dfs_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN) +static int __dfs_path_neg(ScfEline* el, ScfEline* LP, ScfEline* LN) { ScfEcomponent* c; ScfEpin* p; @@ -117,15 +117,15 @@ static int __dfs_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* long i; - if (LN == el) + if (ses_top_line(el) == LN) return 1; - if (LP == el) + if (ses_top_line(el) == LP) return 0; for (i = 0; i + 1 < el->n_pins; i += 2) { - c = f->components[el->pins[i]]; - p = c->pins [el->pins[i + 1]]; + c = el->pf->components[el->pins[i]]; + p = c->pins[el->pins[i + 1]]; if (p->vflag) continue; @@ -134,7 +134,7 @@ static int __dfs_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* if (c->f) { assert(p->id < c->f->n_elines); - if (__dfs_path_pos(c->f, c->f->elines[p->id], LP, LN)) + if (__dfs_path_neg(c->f->elines[p->id], LP, LN)) return 1; continue; } @@ -157,7 +157,7 @@ static int __dfs_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* continue; p2->vflag = 1; - if (__dfs_path_neg2(f, p2, LP, LN)) + if (__dfs_path_neg2(el->pf, p2, LP, LN)) return 1; } @@ -189,45 +189,78 @@ int __ses_path_pos(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN) { __dfs_path_init(f); - return __dfs_path_pos(f, el, LP, LN); + return __dfs_path_pos(el, LP, LN); } int __ses_path_neg(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN) { __dfs_path_init(f); - return __dfs_path_neg(f, el, LP, LN); + return __dfs_path_neg(el, LP, LN); } -static int _open_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static void __open_status_line(ScfEfunction* f, ScfEline* el, ScfEline* LP, ScfEline* LN) { + if (__ses_path_pos(f, el, LP, LN)) { + if (__ses_path_neg(f, el, LP, LN)) + return; + el->v = LP->v; + + } else if (__ses_path_neg(f, el, LP, LN)) + el->v = LN->v; + else + el->v = SCF_EDA_V_NPN_ON / 2; + + scf_logw(""); + ses_eline_print(el); + printf("->v: %lg\n", el->v); +} + +static void __open_status_IC(ScfEfunction* f, ScfEcomponent* IC, ScfEline* LP, ScfEline* LN) +{ + ScfEcomponent* c; + ScfEline* el; + + long i; + for (i = 0; i < IC->f->n_components; i++) { + c = IC->f->components[i]; + + if (c->f) + __open_status_IC(f, c, LP, LN); + } + + for (i = 0; i < IC->f->n_elines; i++) { + el = IC->f->elines[i]; + + __open_status_line(f, el, LP, LN); + } +} + +static int _open_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) +{ + ScfEcomponent* c; ScfEcomponent* B = f->components[0]; ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEline* LP = ses_line(f, Bp); - ScfEline* LN = ses_line(f, Bn); + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); ScfEline* el; long i; - for (i = 0; i < f->n_elines; i++) { el = f->elines[i]; if (el->flags & (SCF_EDA_PIN_IN | SCF_EDA_PIN_POS | SCF_EDA_PIN_NEG)) continue; - if (__ses_path_pos(f, el, LP, LN)) { - - if (!__ses_path_neg(f, el, LP, LN)) { - el->v = Bp->v; + __open_status_line(f, el, LP, LN); + } - scf_logw("e%ld->v: %lg\n", el->id, el->v); - } - } else if (__ses_path_neg(f, el, LP, LN)) { - el->v = Bn->v; + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; - scf_logw("e%ld->v: %lg\n", el->id, el->v); - } + if (c->f) + __open_status_IC(f, c, LP, LN); } printf("\n"); diff --git a/ses_step_output.c b/ses_step_output.c index a47b1fd..2d8f109 100644 --- a/ses_step_output.c +++ b/ses_step_output.c @@ -1,12 +1,8 @@ #include"ses_core.h" -static int _output_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _output_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEline* el; - + ScfEline* el; long i; printf("\n"); diff --git a/ses_step_status.c b/ses_step_status.c deleted file mode 100644 index 213775d..0000000 --- a/ses_step_status.c +++ /dev/null @@ -1,124 +0,0 @@ -#include"ses_core.h" - -int __ses_path_status(ScfEfunction* f, ses_path_t* bridge, int* changed, scf_vector_t* paths, int64_t ns, int64_t count) -{ - ScfEcomponent* B; - ScfEline* el; - ScfEpin* Bp; - ScfEpin* Bn; - ScfEpin* p0; - ScfEpin* p1; - - B = f->components[0]; - Bp = B->pins[SCF_EDA_Battery_POS]; - Bn = B->pins[SCF_EDA_Battery_NEG]; - - p0 = bridge->pins->data[0]; - p1 = bridge->pins->data[bridge->pins->size - 1]; - - if (p0->lid == Bp->lid && p1->lid == Bn->lid) - return 0; - - el = f->elines[p0->lid]; - p0->v = el->v; - - el = f->elines[p1->lid]; - p1->v = el->v; - - if (p0->v < SCF_EDA_V_MIN || p1->v < SCF_EDA_V_MIN) - return 0; - - int __changed = 0; - - __ses_path_jr(f, bridge); - - if (bridge->n_diodes + bridge->n_NPNs + bridge->n_PNPs > 0) { - __ses_path_va_diode(f, bridge); - __ses_path_jr (f, bridge); - } - - int ret = __ses_path_va(f, bridge, &__changed, ns, count); - if (ret < 0) - return ret; - - *changed += __changed; - - scf_loge("bridge: %d, c%ldp%ld--c%ldp%ld, __changed: %d, p0->v: %lg, p1->v: %lg, n_diodes: %d, n_NPNs: %d, p0->a: %lg, p1->a: %lg\n\n", - bridge->index, p0->cid, p0->id, p1->cid, p1->id, __changed, p0->v, p1->v, bridge->n_diodes, bridge->n_NPNs, p0->a, p1->a); - - bridge->vflag = 0; - return 0; -} - -static int ses_path_status(ScfEfunction* f, ses_path_t* path, int* changed, scf_vector_t* paths, int64_t ns, int64_t count) -{ - ses_path_t* child; - - int ret; - int j; - - if (!path) - return -EINVAL; - - if (0 == path->n_capacitors) { - - ret = __ses_path_status(f, path, changed, paths, ns, count); - if (ret < 0) - return ret; - } - - if (path->bridges) { - scf_vector_t* vec = scf_vector_alloc(); - if (!vec) - return -ENOMEM; - - ret = scf_vector_add(vec, path); - if (ret < 0) { - scf_vector_free(vec); - return ret; - } - - for (j = 0; j < path->bridges->size; j++) { - child = path->bridges->data[j]; - - ret = ses_path_status(f, child, changed, vec, ns, count); - if (ret < 0) { - scf_vector_free(vec); - return ret; - } - } - - scf_vector_free(vec); - vec = NULL; - } - - return 0; -} - -static int _status_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) -{ - ses_path_t* path; - - int changed = 0; - int i; - - for (i = 0; i < ctx->paths->size; i++) { - path = ctx->paths->data[i]; - - scf_logi("i: %d, path->index: %d\n", i, path->index); - - int ret = ses_path_status(f, path, &changed, ctx->paths, ns, count); - if (ret < 0) - return ret; - } - - ctx->changed += changed; - return 0; -} - -ses_step_t ses_step_status = -{ - .name = "status", - - .handler = _status_handler, -}; diff --git a/ses_step_topo.c b/ses_step_topo.c index 1ceaa17..952e615 100644 --- a/ses_step_topo.c +++ b/ses_step_topo.c @@ -24,27 +24,44 @@ static int __ses_dfs_add_ppath(scf_vector_t* paths, ses_path_t** ppath) return 0; } -static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags); +static int __ses_dfs_path(ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags); -static int __ses_dfs_line(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* np, scf_vector_t* __paths, ses_path_t** ppath, int flags) +static int __ses_dfs_line(ScfEcomponent* rc, ScfEpin* np, scf_vector_t* __paths, ses_path_t** ppath, int flags) { ScfEcomponent* c; - ScfEline* el = f->elines[np->lid]; + ScfEline* el = rc->pf->elines[np->lid]; ScfEpin* p; int add = 0; int ret = 0; long j; + if (el->n_pins <= 2) { + c = el->pf->IC; + + if (c && el->id < c->n_pins) { + p = c->pins[el->id]; + + return __ses_dfs_line(c, p, __paths, ppath, flags); + } + return __ses_dfs_add_ppath(__paths, ppath); + } + for (j = 0; j + 1 < el->n_pins; j += 2) { - c = f->components[el->pins[j]]; - p = c->pins [el->pins[j + 1]]; + c = rc->pf->components[el->pins[j]]; + p = c->pins [el->pins[j + 1]]; + + if (SCF_EDA_Battery == c->type) + continue; if (p->pflag) { if (p != np) { - scf_logd("branch: c%ld_p%ld, l%ld\n\n", c->id, p->id, el->id); - +#if 0 + scf_logw("branch l%ld, ", el->id); + ses_pin_print(p); + printf("\n"); +#endif ret = __ses_dfs_add_ppath(__paths, ppath); if (ret < 0) return ret; @@ -69,7 +86,7 @@ static int __ses_dfs_line(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* np, scf_v add = 0; } - if (!c->ops || !c->ops->shared || !c->ops->shared(p)) + if (!c->ops || !c->ops->shared || !c->ops->shared(p, flags)) p->vflag = 1; ses_path_t* tmp = NULL; @@ -81,12 +98,14 @@ static int __ses_dfs_line(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* np, scf_v add = 1; } - ret = __ses_dfs_path(f, c, p, __paths, ppath, flags); + ret = __ses_dfs_path(c, p, __paths, ppath, flags); if (ret < 0) return ret; - if (SCF_EDA_Path_OFF == ret) - p->vflag = 0; + if (SCF_EDA_Path_OFF == ret) { + if (!p->pflag) + p->vflag = 0; + } if (tmp) *ppath = tmp; @@ -99,10 +118,15 @@ static int __ses_dfs_line(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* np, scf_v *ppath = NULL; } +#if 0 + scf_logi(""); + ses_pin_print(np); + printf("l%ld, vflag: %d, pflag: %d\n", np->lid, np->vflag, np->pflag); +#endif return ret; } -static int __ses_dfs_IC(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags) +static int __ses_dfs_IC(ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags) { ses_path_t* path; @@ -111,7 +135,11 @@ static int __ses_dfs_IC(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vec ScfEpin* np; ScfEpin* p; - scf_logd("*** rc->f->elines: %p, rc->f->n_elines: %ld, rc: %ld, rp->id: %ld, el: %p\n", rc->f->elines, rc->f->n_elines, rc->id, rp->id, el); +#if 0 + scf_logi("*** rc->f->n_elines: %ld, ", rc->f->n_elines); + ses_pin_print(rp); + printf("l%ld, vflag: %d, pflag: %d\n", rp->lid, rp->vflag, rp->pflag); +#endif int size = __paths->size; @@ -120,14 +148,28 @@ static int __ses_dfs_IC(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vec c = rc->f->components[el->pins[j]]; p = c->pins [el->pins[j + 1]]; +#if 0 + scf_logi("\033[34m--- j:%ld, rc->f: %p, \033[0m", j, rc->f); + ses_pin_print(rp); + printf(", l%ld, vflag: %d, pflag: %d, p: ", p->lid, p->vflag, p->pflag); + ses_pin_print(p); + printf("\n"); +#endif + if (p->pflag) { + assert(p != rp); - if (p->vflag) + int ret = __ses_dfs_add_ppath(__paths, ppath); + if (ret < 0) + return ret; + + *ppath = NULL; continue; + } - scf_logd("--- c%ldp%ld->IC: %p, l%ld, vflag: %d, pflag: %d, f: %p, rc->f: %p, c%ldp%ld\n", - rp->cid, rp->id, rp->IC, rp->lid, rp->vflag, rp->pflag, f, rc->f, c->id, p->id); + if (p->vflag) + continue; - int ret = __ses_dfs_path(rc->f, c, p, __paths, ppath, 0); + int ret = __ses_dfs_path(c, p, __paths, ppath, flags); if (ret < 0) { scf_loge("\n"); return ret; @@ -142,32 +184,29 @@ static int __ses_dfs_IC(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vec for (i = __paths->size - 1; i >= size; i--) { path = __paths->data[i]; - for (k = path->pins->size - 1; k > 0; k -= 2) { + for (k = path->pins->size - 1; k >= 0; k--) { p = path->pins->data[k]; - if (p->IC != rc) + if (p->c->pf->IC != rc) break; + if ((k & 0x1) && k < path->pins->size - 1) + continue; + if (p->lid >= rc->n_pins) continue; np = rc->pins[p->lid]; - el = f->elines[np->lid]; + el = rc->pf->elines[np->lid]; - scf_logd("i: %d, np: c%ldp%ld\n", i, np->cid, np->id); - - if (SCF_EDA_PIN_NEG & el->flags) { + if (SCF_EDA_PIN_NEG & ses_top_pline(np)->flags) { scf_logd("neg l%ld\n\n", el->id); continue; } - if (path->pins->size - 1 == k) { - assert(0 == scf_vector_del(__paths, path)); - *ppath = path; - } else - *ppath = NULL; + *ppath = NULL; - int ret = __ses_dfs_line(f, rc, np, __paths, ppath, flags); + int ret = __ses_dfs_line(rc, np, __paths, ppath, flags); if (ret < 0) { scf_loge("\n"); return ret; @@ -175,30 +214,22 @@ static int __ses_dfs_IC(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vec } } - scf_logd("*** rc->f->elines: %p, rc->f->n_elines: %ld, rc: %ld, rp->id: %ld, size: %d, %d\n\n", - rc->f->elines, rc->f->n_elines, rc->id, rp->id, size, __paths->size); return 0; } -static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags) +static int __ses_dfs_path(ScfEcomponent* rc, ScfEpin* rp, scf_vector_t* __paths, ses_path_t** ppath, int flags) { - ScfEcomponent* c; - ScfEline* el; - ScfEpin* np; - ScfEpin* p; - - long i; - long j; + ScfEline* el; + ScfEpin* np; - if (rc->ops && rc->ops->off && rc->ops->off(rp, NULL)) + if (rc->ops && rc->ops->off && rc->ops->off(rp, NULL, flags)) return SCF_EDA_Path_OFF; if (SCF_EDA_Status_OFF != rc->status) { #if 1 if (flags && rc->f) - return __ses_dfs_IC(f, rc, rp, __paths, ppath, flags); + return __ses_dfs_IC(rc, rp, __paths, ppath, flags); #endif - if (!*ppath) { *ppath = ses_path_alloc(); if (!*ppath) @@ -209,15 +240,16 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v return -ENOMEM; } - if (!rc->ops || !rc->ops->shared || !rc->ops->shared(rp)) + if (!rc->ops || !rc->ops->shared || !rc->ops->shared(rp, flags)) rp->vflag = 1; - if (rp->IC) - scf_logd("IC%ld_c%ldp%ld, l%ld, vflag: %d, pflag: %d\n", rp->IC->id, rp->cid, rp->id, rp->lid, rp->vflag, rp->pflag); - else - scf_logd("c%ldp%ld, l%ld, vflag: %d, pflag: %d\n", rp->cid, rp->id, rp->lid, rp->vflag, rp->pflag); - - int ret = 0; +#if 0 + scf_logi(""); + ses_pin_print(rp); + printf("l%ld, vflag: %d, pflag: %d\n", rp->lid, rp->vflag, rp->pflag); +#endif + int ret = 0; + long i; for (i = 0; i < rc->n_pins; i++) { np = rc->pins[i]; @@ -225,17 +257,16 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v if (np->vflag) continue; - if (rc->ops && rc->ops->off && rc->ops->off(rp, np)) + if (rc->ops && rc->ops->off && rc->ops->off(rp, np, flags)) continue; +#if 0 + scf_logi(""); + ses_pin_print(np); + printf("l%ld, vflag: %d, pflag: %d\n", np->lid, np->vflag, np->pflag); +#endif + el = rc->pf->elines[np->lid]; - if (np->IC) - scf_logd("IC%ld_c%ldp%ld, l%ld, vflag: %d, pflag: %d\n", np->IC->id, np->cid, np->id, np->lid, np->vflag, np->pflag); - else - scf_logd("c%ldp%ld, l%ld, vflag: %d, pflag: %d\n", np->cid, np->id, np->lid, np->vflag, np->pflag); - - el = f->elines[np->lid]; - - if (SCF_EDA_PIN_POS & el->flags) { + if (SCF_EDA_PIN_POS & ses_top_pline(np)->flags) { scf_logd("pos l%ld\n\n", el->id); ret = SCF_EDA_Path_OFF; @@ -249,7 +280,7 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v return -ENOMEM; } - if (rc->ops && rc->ops->shared && rc->ops->shared(rp) && 0 == (*ppath)->pins->size) { + if (rc->ops && rc->ops->shared && rc->ops->shared(rp, flags) && 0 == (*ppath)->pins->size) { if (scf_vector_add((*ppath)->pins, rp) < 0) return -ENOMEM; @@ -259,10 +290,10 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v return -ENOMEM; } - if (!rc->ops || !rc->ops->shared || !rc->ops->shared(np)) + if (!rc->ops || !rc->ops->shared || !rc->ops->shared(np, flags)) np->vflag = 1; - if (SCF_EDA_PIN_NEG & el->flags) { + if (SCF_EDA_PIN_NEG & ses_top_pline(np)->flags) { scf_logd("neg l%ld\n\n", el->id); if (SCF_EDA_Status_OFF == rc->status) @@ -282,7 +313,7 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v *ppath = NULL; } - ret = __ses_dfs_line(f, rc, np, __paths, ppath, flags); + ret = __ses_dfs_line(rc, np, __paths, ppath, flags); if (ret < 0) return ret; @@ -293,8 +324,10 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v if (*ppath) scf_vector_del((*ppath)->pins, np); - if (SCF_EDA_Path_OFF == ret) - np->vflag = 0; + if (SCF_EDA_Path_OFF == ret) { + if (!np->pflag) + np->vflag = 0; + } } } @@ -303,18 +336,25 @@ static int __ses_dfs_path(ScfEfunction* f, ScfEcomponent* rc, ScfEpin* rp, scf_v scf_vector_del((*ppath)->pins, rp); if (SCF_EDA_Path_OFF == ret) { - rp->vflag = 0; - - scf_logd("off: c%ld_p%ld, l%ld\n\n", rp->cid, rp->id, rp->lid); - - } else if (SCF_EDA_Status_OFF == ret) - scf_logd("off: c%ld_p%ld, l%ld\n\n", rp->cid, rp->id, rp->lid); + if (!rp->pflag) + rp->vflag = 0; + + } else if (SCF_EDA_Status_OFF == ret) { +#if 0 + scf_loge("off: "); + ses_pin_print(rp); + printf("l%ld, vflag: %d, pflag: %d\n", rp->lid, rp->vflag, rp->pflag); +#endif + } } + if (*ppath) + ret = __ses_dfs_add_ppath(__paths, ppath); + return ret; } -static int ses_line_to_pin(const ScfEfunction* f, const ScfEpin* vip, const ScfEline* el, int ctype, int pid) +static int ses_line_to_pin(const ScfEpin* vip, const ScfEline* el, int ctype, int pid) { ScfEcomponent* c; ScfEpin* p; @@ -322,8 +362,8 @@ static int ses_line_to_pin(const ScfEfunction* f, const ScfEpin* vip, const ScfE long i; for (i = 0; i < el->n_pins; i += 2) { - c = f->components[el->pins[i]]; - p = c->pins [el->pins[i + 1]]; + c = el->pf->components[el->pins[i]]; + p = c->pins [el->pins[i + 1]]; if (p == vip) continue; @@ -332,7 +372,7 @@ static int ses_line_to_pin(const ScfEfunction* f, const ScfEpin* vip, const ScfE return 1; if (c->f) { - if (ses_line_to_pin(c->f, vip, c->f->elines[p->id], ctype, pid)) + if (ses_line_to_pin(vip, c->f->elines[p->id], ctype, pid)) return 1; } } @@ -340,72 +380,56 @@ static int ses_line_to_pin(const ScfEfunction* f, const ScfEpin* vip, const ScfE return 0; } -static int ses_pin_to_npn(const ScfEfunction* f, const ScfEpin* vip, int pid) +static int ses_pin_to_component(const ScfEpin* vip, int ctype, int pid) { const ScfEcomponent* c; const ScfEline* el; const ScfEpin* p; - if (!vip->IC) { - el = f->elines[vip->lid]; - return ses_line_to_pin(f, vip, el, SCF_EDA_NPN, pid); - } - - el = vip->IC->f->elines[vip->lid]; - if (ses_line_to_pin(vip->IC->f, vip, el, SCF_EDA_NPN, pid)) + el = vip->c->pf->elines[vip->lid]; + if (ses_line_to_pin(vip, el, ctype, pid)) return 1; - if (vip->lid < vip->IC->n_pins) { - p = vip->IC->pins[vip->lid]; + c = el->pf->IC; - el = f->elines[p->lid]; - if (ses_line_to_pin(f, p, el, SCF_EDA_NPN, pid)) + while (c && el->id < c->n_pins) { + p = c->pins[el->id]; + + if (p->lid >= c->pf->n_elines) + break; + + el = c->pf->elines[p->lid]; + if (ses_line_to_pin(p, el, ctype, pid)) return 1; - } + c = el->pf->IC; + } return 0; } -static int ses_pin_to_pnp(const ScfEfunction* f, const ScfEpin* vip, int pid) +static int ses_pin_to_npn(const ScfEpin* vip, int pid) { - const ScfEcomponent* c; - const ScfEline* el; - const ScfEpin* p; - - if (!vip->IC) { - el = f->elines[vip->lid]; - return ses_line_to_pin(f, vip, el, SCF_EDA_PNP, pid); - } - - el = vip->IC->f->elines[vip->lid]; - if (ses_line_to_pin(vip->IC->f, vip, el, SCF_EDA_PNP, pid)) - return 1; - - if (vip->lid < vip->IC->n_pins) { - p = vip->IC->pins[vip->lid]; - - el = f->elines[p->lid]; - if (ses_line_to_pin(f, p, el, SCF_EDA_PNP, pid)) - return 1; - } - - return 0; + return ses_pin_to_component(vip, SCF_EDA_NPN, pid); +} +static int ses_pin_to_pnp(const ScfEpin* vip, int pid) +{ + return ses_pin_to_component(vip, SCF_EDA_PNP, pid); } -static int ses_path_to_npn(const ScfEfunction* f, const ses_path_t* path, int pid) +static int ses_path_to_npn(const ses_path_t* path, int pid) { const ScfEpin* p0 = path->pins->data[0]; const ScfEpin* p1 = path->pins->data[path->pins->size - 1]; - return ses_pin_to_npn(f, p0, pid) || ses_pin_to_npn(f, p1, pid); + return ses_pin_to_npn(p0, pid) || ses_pin_to_npn(p1, pid); } -static int ses_path_to_pnp(const ScfEfunction* f, const ses_path_t* path, int pid) +static int ses_path_to_pnp(const ses_path_t* path, int pid) { const ScfEpin* p0 = path->pins->data[0]; const ScfEpin* p1 = path->pins->data[path->pins->size - 1]; - return ses_pin_to_pnp(f, p0, pid) || ses_pin_to_pnp(f, p1, pid); + return ses_pin_to_pnp(p0, pid) || ses_pin_to_pnp(p1, pid); } static int _ses_child_cmp(const void* v0, const void* v1) @@ -488,8 +512,8 @@ static int __topo_path_bridges(ScfEfunction* f, ses_path_t* path) if (SCF_EDA_PIN_IN & p1->flags) goto bridge_sp0; - c0 = ses_component(f, p0); - c1 = ses_component(f, p1); + c0 = p0->c; + c1 = p1->c; if ((SCF_EDA_NPN == c0->type && SCF_EDA_NPN_C == p0->id) || (SCF_EDA_PNP == c0->type && SCF_EDA_PNP_C == p0->id)) @@ -509,14 +533,14 @@ static int __topo_path_bridges(ScfEfunction* f, ses_path_t* path) || (SCF_EDA_PNP == c1->type && SCF_EDA_PNP_B == p1->id)) goto bridge_sp0; - if (ses_pin_to_npn(f, p0, SCF_EDA_NPN_B) || ses_pin_to_pnp(f, p0, SCF_EDA_PNP_B)) + if (ses_pin_to_npn(p0, SCF_EDA_NPN_B) || ses_pin_to_pnp(p0, SCF_EDA_PNP_B)) goto bridge_sp1; - if (ses_pin_to_npn(f, p1, SCF_EDA_NPN_B) || ses_pin_to_pnp(f, p1, SCF_EDA_PNP_B)) + if (ses_pin_to_npn(p1, SCF_EDA_NPN_B) || ses_pin_to_pnp(p1, SCF_EDA_PNP_B)) goto bridge_sp0; - if (ses_pin_to_npn(f, p0, SCF_EDA_NPN_C) || ses_pin_to_pnp(f, p0, SCF_EDA_PNP_C)) + if (ses_pin_to_npn(p0, SCF_EDA_NPN_C) || ses_pin_to_pnp(p0, SCF_EDA_PNP_C)) goto bridge_sp1; - if (ses_pin_to_npn(f, p1, SCF_EDA_NPN_C) || ses_pin_to_pnp(f, p1, SCF_EDA_PNP_C)) + if (ses_pin_to_npn(p1, SCF_EDA_NPN_C) || ses_pin_to_pnp(p1, SCF_EDA_PNP_C)) goto bridge_sp0; // negative pin of path @@ -529,14 +553,14 @@ static int __topo_path_bridges(ScfEfunction* f, ses_path_t* path) if (SCF_EDA_PIN_IN & p1->flags) goto bridge_sp0; - if (ses_pin_to_npn(f, p0, SCF_EDA_NPN_B) || ses_pin_to_pnp(f, p0, SCF_EDA_PNP_B)) + if (ses_pin_to_npn(p0, SCF_EDA_NPN_B) || ses_pin_to_pnp(p0, SCF_EDA_PNP_B)) goto bridge_sp1; - if (ses_pin_to_npn(f, p1, SCF_EDA_NPN_B) || ses_pin_to_pnp(f, p1, SCF_EDA_PNP_B)) + if (ses_pin_to_npn(p1, SCF_EDA_NPN_B) || ses_pin_to_pnp(p1, SCF_EDA_PNP_B)) goto bridge_sp0; - if (ses_pin_to_npn(f, p0, SCF_EDA_NPN_C) || ses_pin_to_pnp(f, p0, SCF_EDA_PNP_C)) + if (ses_pin_to_npn(p0, SCF_EDA_NPN_C) || ses_pin_to_pnp(p0, SCF_EDA_PNP_C)) goto bridge_sp1; - if (ses_pin_to_npn(f, p1, SCF_EDA_NPN_C) || ses_pin_to_pnp(f, p1, SCF_EDA_PNP_C)) + if (ses_pin_to_npn(p1, SCF_EDA_NPN_C) || ses_pin_to_pnp(p1, SCF_EDA_PNP_C)) goto bridge_sp0; c0 = f->components[p0->cid]; @@ -580,6 +604,61 @@ bridge_sp0: return 0; } +static int __topo_connect(ScfEfunction* f, scf_vector_t* paths, ses_path_t* conn, ScfEpin* vip, ses_path_t** ppath) +{ + ses_path_t* path; + ScfEpin* p0 = conn->pins->data[0]; + ScfEpin* p1 = conn->pins->data[conn->pins->size - 1]; + ScfEpin* p2; + ScfEpin* p3; + ScfEpin* p; + + int j; + int k; + + for (j = 0; j < paths->size; j++) { + path = paths->data[j]; + + if (path == conn) + continue; + + p2 = path->pins->data[0]; + p3 = path->pins->data[path->pins->size - 1]; + + if (ses_same_line(p2, p0) && ses_same_line(p3, p1)) + continue; + if (ses_same_line(p3, p0) && ses_same_line(p2, p1)) + continue; + + for (k = 0; k < path->pins->size; k++) { + p = path->pins->data[k]; + + if (ses_same_line(p, vip)) { + if (vip == p1 && p == p3 + && path->n_diodes + path->n_NPNs + path->n_PNPs + path->n_transistors > 0 + && conn->n_diodes + conn->n_NPNs + conn->n_PNPs + conn->n_transistors > 0) + return -1; + *ppath = path; + return k; + } + } + + if (path->childs) { + k = __topo_connect(f, path->childs, conn, vip, ppath); + if (k >= 0) + return k; + } + + if (path->bridges) { + k = __topo_connect(f, path->bridges, conn, vip, ppath); + if (k >= 0) + return k; + } + } + + return -1; +} + static int _topo_path_bridges(ScfEfunction* f, ses_path_t* path) { if (!path || !path->childs || path->childs->size <= 0) @@ -600,38 +679,36 @@ static int _topo_path_bridges(ScfEfunction* f, ses_path_t* path) return __topo_path_bridges(f, path); } -static int _ses_connect_cmp(const void* v0, const void* v1, void* arg) +static int _ses_connect_cmp(const void* v0, const void* v1) { - const ScfEfunction* f = arg; - - const ses_path_t* p0 = *(const ses_path_t**)v0; - const ses_path_t* p1 = *(const ses_path_t**)v1; + const ses_path_t* p0 = *(const ses_path_t**)v0; + const ses_path_t* p1 = *(const ses_path_t**)v1; if (0 == p0->n_capacitors) { if (0 == p1->n_capacitors) { - if (ses_path_to_npn(f, p0, SCF_EDA_NPN_B) || ses_path_to_pnp(f, p0, SCF_EDA_PNP_B)) + if (ses_path_to_npn(p0, SCF_EDA_NPN_B) || ses_path_to_pnp(p0, SCF_EDA_PNP_B)) return -1; - if (ses_path_to_npn(f, p1, SCF_EDA_NPN_B) || ses_path_to_pnp(f, p1, SCF_EDA_PNP_B)) + if (ses_path_to_npn(p1, SCF_EDA_NPN_B) || ses_path_to_pnp(p1, SCF_EDA_PNP_B)) return 1; - if (ses_path_to_npn(f, p0, SCF_EDA_NPN_C) || ses_path_to_pnp(f, p0, SCF_EDA_PNP_C)) + if (ses_path_to_npn(p0, SCF_EDA_NPN_C) || ses_path_to_pnp(p0, SCF_EDA_PNP_C)) return -1; - if (ses_path_to_npn(f, p1, SCF_EDA_NPN_C) || ses_path_to_pnp(f, p1, SCF_EDA_PNP_C)) + if (ses_path_to_npn(p1, SCF_EDA_NPN_C) || ses_path_to_pnp(p1, SCF_EDA_PNP_C)) return 1; } return -1; } else if (0 == p1->n_capacitors) return 1; - if (ses_path_to_npn(f, p0, SCF_EDA_NPN_C) || ses_path_to_pnp(f, p0, SCF_EDA_PNP_C)) + if (ses_path_to_npn(p0, SCF_EDA_NPN_C) || ses_path_to_pnp(p0, SCF_EDA_PNP_C)) return -1; - if (ses_path_to_npn(f, p1, SCF_EDA_NPN_C) || ses_path_to_pnp(f, p1, SCF_EDA_PNP_C)) + if (ses_path_to_npn(p1, SCF_EDA_NPN_C) || ses_path_to_pnp(p1, SCF_EDA_PNP_C)) return 1; - if (ses_path_to_npn(f, p0, SCF_EDA_NPN_B) || ses_path_to_pnp(f, p0, SCF_EDA_PNP_B)) + if (ses_path_to_npn(p0, SCF_EDA_NPN_B) || ses_path_to_pnp(p0, SCF_EDA_PNP_B)) return 1; - if (ses_path_to_npn(f, p1, SCF_EDA_NPN_B) || ses_path_to_pnp(f, p1, SCF_EDA_PNP_B)) + if (ses_path_to_npn(p1, SCF_EDA_NPN_B) || ses_path_to_pnp(p1, SCF_EDA_PNP_B)) return -1; if (p0->n_capacitors > p1->n_capacitors) @@ -646,20 +723,15 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) if (!f || !paths) return -EINVAL; - scf_vector_t* vec; - ses_path_t* path0; - ses_path_t* path1; - - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEcomponent* c0; - ScfEcomponent* c1; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* p2; - ScfEpin* p3; - ScfEpin* p; + scf_vector_t* vec; + ses_path_t* path0; + ses_path_t* path1; + + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + ScfEpin* p; int i; int j; @@ -671,7 +743,7 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) return -ENOMEM; // qsort in 'vec' and keep the origin order in 'paths' - qsort_r(vec->data, vec->size, sizeof(void*), _ses_connect_cmp, f); + qsort(vec->data, vec->size, sizeof(void*), _ses_connect_cmp); i = 0; while (i < vec->size) { @@ -680,7 +752,7 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) p0 = path0->pins->data[0]; p1 = path0->pins->data[path0->pins->size - 1]; - if (ses_same_line(f, p0, Bp) || ses_same_line(f, p1, Bn)) { + if (SES_LINE_POS(p0) || SES_LINE_NEG(p1)) { i++; continue; } @@ -694,7 +766,15 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) p2 = path1->pins->data[0]; p3 = path1->pins->data[path1->pins->size - 1]; - if (ses_same_line(f, p3, p0)) { + if (ses_same_line(p3, p0)) { + if (SES_LINE_POS(p3) || SES_LINE_NEG(p3)) + continue; + if (ses_same_line_in_path(p1, path1) || ses_same_line_in_path(p2, path0)) + continue; + + if (path0->parent_p1 < 0) + continue; + for (k = 0; k < path0->pins->size; k++) { p = path0->pins->data[k]; @@ -703,9 +783,15 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) } goto connected; - } else if (ses_same_line(f, p3, p1)) { + } else if (ses_same_line(p3, p1)) { + if (path0->n_diodes + path0->n_NPNs + path0->n_PNPs + path0->n_transistors > 0) + continue; + if (SES_LINE_POS(p3) || SES_LINE_NEG(p3)) + continue; + if (ses_same_line_in_path(p0, path1) || ses_same_line_in_path(p2, path0)) + continue; - if (path0->n_diodes + path0->n_NPNs > 0 || path0->n_transistors > 0) + if (path0->parent_p0 < 0) continue; for (k = path0->pins->size - 1; k >= 0; k--) { @@ -716,7 +802,15 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) } goto connected; - } else if (ses_same_line(f, p2, p1)) { + } else if (ses_same_line(p2, p1)) { + if (SES_LINE_POS(p2) || SES_LINE_NEG(p2)) + continue; + if (ses_same_line_in_path(p0, path1) || ses_same_line_in_path(p3, path0)) + continue; + + if (path0->parent_p0 < 0) + continue; + for (k = 0; k < path1->pins->size; k++) { p = path1->pins->data[k]; @@ -727,9 +821,15 @@ static int _topo_path_connect(ScfEfunction* f, scf_vector_t* paths) SCF_XCHG(path0->pins, path1->pins); goto connected; - } else if (ses_same_line(f, p2, p0)) { + } else if (ses_same_line(p2, p0)) { + if (path0->n_diodes + path0->n_NPNs + path0->n_PNPs + path0->n_transistors > 0) + continue; + if (SES_LINE_POS(p2) || SES_LINE_NEG(p2)) + continue; + if (ses_same_line_in_path(p1, path1) || ses_same_line_in_path(p3, path0)) + continue; - if (path0->n_diodes + path0->n_NPNs > 0 || path0->n_transistors > 0) + if (path0->parent_p1 < 0) continue; m = path0->pins->size - 1; @@ -759,6 +859,11 @@ connected: assert(0 == scf_vector_del(vec, path0)); assert(0 == scf_vector_del(paths, path0)); + path1->n_diodes += path0->n_diodes; + path1->n_NPNs += path0->n_NPNs; + path1->n_PNPs += path0->n_PNPs; + path1->n_transistors += path0->n_transistors; + ses_path_free(path0); path0 = NULL; i = 0; @@ -772,7 +877,7 @@ error: return -ENOMEM; } -static int _topo_fix_complete(ScfEfunction* f, scf_vector_t* paths, ses_path_t* parent) +static int __topo_fix_complete(ScfEfunction* f, scf_vector_t* paths, ses_path_t* parent) { ses_path_t* child; @@ -817,28 +922,38 @@ static int _topo_fix_complete(ScfEfunction* f, scf_vector_t* paths, ses_path_t* return 0; } +static int __topo_path_xchg(ScfEfunction* f, scf_vector_t* paths, ses_path_t* path0, int k0, ses_path_t* path1, int k1) +{ + int ret = ses_path_xchg(path0, k0, path1, k1); + if (ret < 0) + return ret; + + ret = __topo_fix_complete(f, paths, path1); + if (ret < 0) + return ret; + + return __topo_fix_complete(f, paths, path0); +} + static int _topo_path_completes(ScfEfunction* f, scf_vector_t* paths) { if (!f || !paths) return -EINVAL; - ses_path_t* path0; - ses_path_t* path1; - - ScfEcomponent* c0; - ScfEcomponent* c1; - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* p2; - ScfEpin* p3; - ScfEpin* p; + ses_path_t* path0; + ses_path_t* path1; + + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + ScfEpin* __p0; + ScfEpin* __p3; int i; int j; int k; + int m; for (i = 0; i < paths->size; ) { path0 = paths->data[i]; @@ -846,12 +961,12 @@ static int _topo_path_completes(ScfEfunction* f, scf_vector_t* paths) p0 = path0->pins->data[0]; p1 = path0->pins->data[path0->pins->size - 1]; - if (!ses_same_line(f, p1, Bn)) { + if (!SES_LINE_NEG(p1)) { i++; continue; } - if (ses_same_line(f, p0, Bp)) { + if (SES_LINE_POS(p0)) { i++; continue; } @@ -865,81 +980,250 @@ static int _topo_path_completes(ScfEfunction* f, scf_vector_t* paths) p2 = path1->pins->data[0]; p3 = path1->pins->data[path1->pins->size - 1]; - if (!ses_same_line(f, p2, Bp)) + if (!SES_LINE_POS(p2)) continue; - if (ses_same_line(f, p3, Bn)) + if (SES_LINE_NEG(p3)) + continue; + + for (k = path1->pins->size - 1; k >= 0; k -= 2) { + __p3 = path1->pins->data[k]; + + for (m = 0; m < path0->pins->size; m += 2) { + __p0 = path0->pins->data[m]; + + if (ses_same_line(__p3, __p0)) + goto xchg; + } + } + } + + i++; + continue; +xchg: +#if 1 + scf_logi("\033[36mconnect path: \033[0m"); + ses_pin_print(p2); + ses_pin_print(__p3); + printf("(%d)--", path1->pins->size); + ses_pin_print(__p0); + ses_pin_print(p1); + printf("(%d)\n", path0->pins->size); +#endif + int ret = __topo_path_xchg(f, paths, path0, m, path1, k + 1); + if (ret < 0) + return ret; + + if (path0->pins->size <= 0) { + if (scf_vector_del(paths, path0) < 0) + return -1; + + ses_path_free(path0); + path0 = NULL; + } + + if (path0) + i++; + } + + return 0; +} + +static int _topo_path_neg(ScfEfunction* f, scf_vector_t* paths) +{ + if (!f || !paths) + return -EINVAL; + + ses_path_t* path0; + ses_path_t* path1; + ses_path_t* conn; + + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + ScfEpin* p; + + int i; + int j; + int k; + + for (i = 0; i < paths->size; ) { + path0 = paths->data[i]; + + p0 = path0->pins->data[0]; + p1 = path0->pins->data[path0->pins->size - 1]; + + if (SES_LINE_POS(p0)) { + i++; + continue; + } + + if (!SES_LINE_NEG(p1)) { + k = __topo_connect(f, paths, path0, p1, &conn); + if (k < 0) { + i++; + continue; + } + + while (conn->parent) + conn = conn->parent; + + p3 = conn->pins->data[conn->pins->size - 1]; + if (!SES_LINE_NEG(p3)) { + i++; + continue; + } + } + + for (j = 0; j < paths->size; j++) { + path1 = paths->data[j]; + + if (path1 == path0) + continue; + + p2 = path1->pins->data[0]; + p3 = path1->pins->data[path1->pins->size - 1]; + + if (SES_LINE_POS(p2) && SES_LINE_NEG(p3)) + continue; + if (ses_same_line_in_path(p2, path0)) continue; for (k = path1->pins->size - 1; k >= 0; k -= 2) { p = path1->pins->data[k]; - if (ses_same_line(f, p, p0)) + if (ses_same_line(p, p0)) break; } if (k > 0) { - scf_loge("merge path: c%ldp%ld-c%ldp%ld (%d)... c%ldp%ld-c%ldp%ld (%d)\n", - p2->cid, p2->id, p->cid, p->id, path1->pins->size, - p0->cid, p0->id, p1->cid, p1->id, path0->pins->size); - - int ret = ses_path_xchg(path0, 0, path1, k + 1); - if (ret < 0) - return ret; - - ret = _topo_fix_complete(f, paths, path1); - if (ret < 0) - return ret; - - ret = _topo_fix_complete(f, paths, path0); +#if 1 + scf_logi("\033[36mconnect path: \033[0m"); + ses_pin_print(p2); + ses_pin_print(p); + printf("(%d)--", path1->pins->size); + ses_pin_print(p0); + ses_pin_print(p1); + printf("\n"); +#endif + int ret = __topo_path_xchg(f, paths, path0, 0, path1, k + 1); if (ret < 0) return ret; if (path0->pins->size <= 0) { - if (scf_vector_del(paths, path0) < 0) - return -1; + assert(0 == scf_vector_del(paths, path0)); ses_path_free(path0); path0 = NULL; } break; } + } - for (k = 0; k < path0->pins->size; k += 2) { - p = path0->pins->data[k]; + if (path0) + i++; + } - if (ses_same_line(f, p, p3)) - break; + return 0; +} + +static int _topo_path_pos(ScfEfunction* f, scf_vector_t* paths) +{ + if (!f || !paths) + return -EINVAL; + + ses_path_t* path0; + ses_path_t* path1; + ses_path_t* conn; + + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; + ScfEpin* __p0; + ScfEpin* __p3; + + int i; + int j; + int k; + int m; + + for (i = 0; i < paths->size; ) { + path0 = paths->data[i]; + + p0 = path0->pins->data[0]; + p1 = path0->pins->data[path0->pins->size - 1]; + + if (SES_LINE_POS(p0)) { + i++; + continue; + } + + if (!SES_LINE_NEG(p1)) { + k = __topo_connect(f, paths, path0, p1, &conn); + if (k < 0) { + i++; + continue; } - if (k < path0->pins->size) { - scf_loge("merge path: c%ldp%ld-c%ldp%ld (%d) ... c%ldp%ld-c%ldp%ld (%d)\n", - p2->cid, p2->id, p3->cid, p3->id, path1->pins->size, - p ->cid, p ->id, p1->cid, p1->id, path0->pins->size); + while (conn->parent) + conn = conn->parent; - int ret = ses_path_xchg(path0, k, path1, path1->pins->size); - if (ret < 0) - return ret; + p3 = conn->pins->data[conn->pins->size - 1]; + if (!SES_LINE_NEG(p3)) { + i++; + continue; + } + } - ret = _topo_fix_complete(f, paths, path1); - if (ret < 0) - return ret; + for (j = 0; j < paths->size; j++) { + path1 = paths->data[j]; - ret = _topo_fix_complete(f, paths, path0); - if (ret < 0) - return ret; + if (path1 == path0) + continue; - if (path0->pins->size <= 0) { - if (scf_vector_del(paths, path0) < 0) - return -1; + p2 = path1->pins->data[0]; + p3 = path1->pins->data[path1->pins->size - 1]; - ses_path_free(path0); - path0 = NULL; + if (!SES_LINE_POS(p2) || SES_LINE_NEG(p3)) + continue; + + for (k = path1->pins->size - 1; k >= 0; k -= 2) { + __p3 = path1->pins->data[k]; + + for (m = 0; m < path0->pins->size; m += 2) { + __p0 = path0->pins->data[m]; + + if (ses_same_line(__p3, __p0)) + goto xchg; } - break; } } + i++; + continue; +xchg: +#if 1 + scf_logi("\033[36mconnect path: \033[0m"); + ses_pin_print(p2); + ses_pin_print(__p3); + printf("(%d)--", path1->pins->size); + ses_pin_print(__p0); + ses_pin_print(p1); + printf("(%d)\n", path0->pins->size); +#endif + int ret = __topo_path_xchg(f, paths, path0, m, path1, k + 1); + if (ret < 0) + return ret; + + if (path0->pins->size <= 0) { + assert(0 == scf_vector_del(paths, path0)); + + ses_path_free(path0); + path0 = NULL; + } + if (path0) i++; } @@ -976,7 +1260,7 @@ static int _topo_layers(ScfEfunction* f, scf_vector_t* paths) p0 = child->pins->data[0]; p1 = child->pins->data[child->pins->size - 1]; - if (ses_same_line(f, p0, Bp) && ses_same_line(f, p1, Bn)) + if (SES_LINE_POS(p0) && SES_LINE_NEG(p1)) continue; for (j = paths->size - 1; j >= 0; j--) { @@ -988,24 +1272,29 @@ static int _topo_layers(ScfEfunction* f, scf_vector_t* paths) p2 = parent->pins->data[0]; p3 = parent->pins->data[parent->pins->size - 1]; - if (ses_same_line(f, p2, p0) && ses_same_line(f, p3, p1)) + if (ses_same_line(p2, p0) && ses_same_line(p3, p1)) continue; - if (ses_same_line(f, p3, p0) && ses_same_line(f, p2, p1)) + if (ses_same_line(p3, p0) && ses_same_line(p2, p1)) continue; - int n = 0; - + int k0 = -1; + int k1 = -1; for (k = 0; k < parent->pins->size; k++) { p = parent->pins->data[k]; - if (ses_same_line(f, p, p0)) - n |= 0x1; - - if (ses_same_line(f, p, p1)) - n |= 0x2; + if (ses_same_line(p, p0)) { + k0 = k; + child->parent_p0 = k; + } else if (ses_same_line(p, p1)) { + k1 = k; + child->parent_p1 = k; + } - if (0x3 == n) + if (k0 >= 0 && k1 >= 0) { + if (k0 > k1 && child->n_diodes + child->n_NPNs + child->n_PNPs + child->n_transistors > 0) + break; goto branch; + } } } @@ -1063,7 +1352,7 @@ static int topo_epin_cmp(const void* v0, const void* v1, void* arg) return 0; } -static void _topo_key_components(ScfEfunction* f, ses_path_t* path) +static void __topo_key_components(ses_path_t* path) { ScfEcomponent* c; ScfEpin* p; @@ -1079,11 +1368,7 @@ static void _topo_key_components(ScfEfunction* f, ses_path_t* path) for (i = 0; i < path->pins->size; i++) { p = path->pins->data[i]; - if (p->IC) - c = p->IC->f->components[p->cid]; - else - c = f->components[p->cid]; - + c = p->c; if (SCF_EDA_Diode == c->type) { if (SCF_EDA_Diode_NEG == p->id) @@ -1113,6 +1398,13 @@ static void _topo_key_components(ScfEfunction* f, ses_path_t* path) } } +static void _topo_key_components(scf_vector_t* paths) +{ + int i; + for (i = 0; i < paths->size; i++) + __topo_key_components(paths->data[i]); +} + static void _topo_clear(ScfEfunction* f) { if (!f) @@ -1130,6 +1422,7 @@ static void _topo_clear(ScfEfunction* f) el->ain = 0; el->aout = 0; el->vflag = 0; + el->open_flag = 0; qsort_r(el->pins, el->n_pins / 2, sizeof(uint64_t) * 2, topo_epin_cmp, f); } @@ -1138,7 +1431,9 @@ static void _topo_clear(ScfEfunction* f) c = f->components[i]; c->vflag = 0; c->lock = 0; -// c->a = 0; + + if (SCF_EDA_Inductor != c->type) + c->a = 0; for (j = 0; j < c->n_pins; j++) { p = c->pins[j]; @@ -1153,9 +1448,9 @@ static void _topo_clear(ScfEfunction* f) } } -static int _topo_paths(ScfEfunction* f, ScfEline* el, scf_vector_t* paths, int flags) +static int _topo_paths(ScfEline* el, scf_vector_t* paths, int flags) { - if (!f || !el || !paths) + if (!el || !paths) return -EINVAL; ses_path_t* path; @@ -1168,13 +1463,16 @@ static int _topo_paths(ScfEfunction* f, ScfEline* el, scf_vector_t* paths, int f for (i = 0; i + 1 < el->n_pins; i += 2) { - c = f->components[el->pins[i]]; - p = c->pins [el->pins[i + 1]]; + c = el->pf->components[el->pins[i]]; + p = c->pins [el->pins[i + 1]]; if (SCF_EDA_Battery == c->type) continue; - int ret = __ses_dfs_path(f, c, p, paths, &path, flags); + if (p->vflag) + continue; + + int ret = __ses_dfs_path(c, p, paths, &path, flags); if (ret < 0) return ret; @@ -1187,9 +1485,7 @@ static int _topo_paths(ScfEfunction* f, ScfEline* el, scf_vector_t* paths, int f continue; } - scf_logi("path: %p\n\n", path); - - if (scf_vector_add(paths, path) < 0) { + if (__ses_dfs_add_ppath(paths, &path) < 0) { ses_path_free(path); return -ENOMEM; } @@ -1211,69 +1507,14 @@ static int _topo_paths(ScfEfunction* f, ScfEline* el, scf_vector_t* paths, int f return 0; } -static int __topo_connect(ScfEfunction* f, scf_vector_t* paths, ses_path_t* conn, ScfEpin* vip, ses_path_t** ppath) -{ - ses_path_t* path; - ScfEpin* p0 = conn->pins->data[0]; - ScfEpin* p1 = conn->pins->data[conn->pins->size - 1]; - ScfEpin* p2; - ScfEpin* p3; - - int j; - int k; - - for (j = 0; j < paths->size; j++) { - path = paths->data[j]; - - if (path == conn) - continue; - - p2 = path->pins->data[0]; - p3 = path->pins->data[path->pins->size - 1]; - - if (ses_same_line(f, p2, p0) && ses_same_line(f, p3, p1)) - continue; - if (ses_same_line(f, p3, p0) && ses_same_line(f, p2, p1)) - continue; - - for (k = 0; k < path->pins->size; k++) { - p2 = path->pins->data[k]; - - if (ses_same_line(f, p2, vip)) { - *ppath = path; - return k; - } - } - - if (path->childs) { - k = __topo_connect(f, path->childs, conn, vip, ppath); - if (k >= 0) - return k; - } - - if (path->bridges) { - k = __topo_connect(f, path->bridges, conn, vip, ppath); - if (k >= 0) - return k; - } - } - - return -1; -} - static int _topo_bridge_piers(ScfEfunction* f, scf_vector_t* paths) { - ses_path_t* pier; - ses_path_t* bridge; - - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEpin* p0; - ScfEpin* p1; + ses_path_t* pier; + ses_path_t* bridge; + ScfEpin* p0; + ScfEpin* p1; int i; - int j; int k; for (i = paths->size - 1; i >= 0; i--) { @@ -1284,8 +1525,8 @@ static int _topo_bridge_piers(ScfEfunction* f, scf_vector_t* paths) bridge = NULL; - if (ses_same_line(f, p0, Bp)) { - if (ses_same_line(f, p1, Bn)) + if (SES_LINE_POS(p0)) { + if (SES_LINE_NEG(p1)) continue; k = __topo_connect(f, paths, pier, p1, &bridge); @@ -1295,7 +1536,7 @@ static int _topo_bridge_piers(ScfEfunction* f, scf_vector_t* paths) pier->parent_p0 = -2; pier->parent_p1 = k; - } else if (ses_same_line(f, p1, Bn)) { + } else if (SES_LINE_NEG(p1)) { k = __topo_connect(f, paths, pier, p0, &bridge); if (k < 0) @@ -1324,6 +1565,61 @@ static int _topo_bridge_piers(ScfEfunction* f, scf_vector_t* paths) return 0; } +static int _topo_path_leaf(ScfEfunction* f, scf_vector_t* paths) +{ + ses_path_t* leaf; + ses_path_t* path; + ScfEpin* p0; + ScfEpin* p1; + + int i; + int k; + + for (i = paths->size - 1; i >= 0; i--) { + leaf = paths->data[i]; + + p0 = leaf->pins->data[0]; + p1 = leaf->pins->data[leaf->pins->size - 1]; + + if (SES_LINE_POS(p0) && SES_LINE_NEG(p1)) + continue; + + if (leaf->childs || leaf->bridges || leaf->connections) + continue; + + path = NULL; + + k = __topo_connect(f, paths, leaf, p1, &path); + if (k < 0) { + k = __topo_connect(f, paths, leaf, p0, &path); + if (k < 0) + continue; + + leaf->parent_p0 = (k + 1) & ~0x1; + leaf->parent_p1 = -2; + } else { + leaf->parent_p0 = -2; + leaf->parent_p1 = k; + } + + if (!path->bridges) { + path->bridges = scf_vector_alloc(); + if (!path->bridges) + return -ENOMEM; + } + + int ret = scf_vector_add(path->bridges, leaf); + if (ret < 0) + return ret; + + assert(0 == scf_vector_del(paths, leaf)); + + leaf->parent = path; + } + + return 0; +} + static int _topo_add_connection(ses_path_t* path, ses_path_t* conn) { if (!conn->connections) { @@ -1335,34 +1631,41 @@ static int _topo_add_connection(ses_path_t* path, ses_path_t* conn) return scf_vector_add_unique(conn->connections, path); } -static int _topo_bridge_connections(ScfEfunction* f, scf_vector_t* paths) +static int __topo_bridge_connections(ScfEfunction* f, scf_vector_t* paths, int flag) { - ses_path_t* path; - ses_path_t* conn0; - ses_path_t* conn1; - - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEpin* p0; - ScfEpin* p1; + ses_path_t* path; + ses_path_t* conn; + ScfEpin* p0; + ScfEpin* p1; + ScfEpin* p2; + ScfEpin* p3; int i; - int j; - for (i = paths->size - 1; i >= 0; i--) { path = paths->data[i]; p0 = path->pins->data[0]; p1 = path->pins->data[path->pins->size - 1]; - if (ses_same_line(f, p0, Bp) && ses_same_line(f, p1, Bn)) + if (SES_LINE_POS(p0) && SES_LINE_NEG(p1)) continue; int k0 = __topo_connect(f, paths, path, p0, &path->conn0); if (k0 < 0) continue; + if (flag) { + for (conn = path->conn0; conn->parent; conn = conn->parent); + + p2 = conn->pins->data[0]; + p3 = conn->pins->data[conn->pins->size - 1]; + + if (!SES_LINE_POS(p2) || !SES_LINE_NEG(p3)) { + path->conn0 = NULL; + continue; + } + } + int k1 = __topo_connect(f, paths, path, p1, &path->conn1); if (k1 < 0) continue; @@ -1381,10 +1684,14 @@ static int _topo_bridge_connections(ScfEfunction* f, scf_vector_t* paths) assert(0 == scf_vector_del(paths, path)); } - return 0; } +static int _topo_bridge_connections(ScfEfunction* f, scf_vector_t* paths) +{ + return __topo_bridge_connections(f, paths, 0); +} + static int _topo_paths_mov_top(ScfEfunction* f, scf_vector_t* paths, ses_path_t* parent, ses_path_t* child) { ses_path_t* path; @@ -1397,7 +1704,7 @@ static int _topo_paths_mov_top(ScfEfunction* f, scf_vector_t* paths, ses_path_t* path = paths->data[k]; p = path->pins->data[0]; - if (!ses_same_line(f, p, p0)) + if (!ses_same_line(p, p0)) continue; path->parent_p0 = 0; @@ -1430,7 +1737,6 @@ static int _topo_path_parallel(ScfEfunction* f, scf_vector_t* paths) int i; int j; - int k; for (i = 0; i < paths->size - 1; i++) { parent = paths->data[i]; @@ -1444,7 +1750,7 @@ static int _topo_path_parallel(ScfEfunction* f, scf_vector_t* paths) p2 = child->pins->data[0]; p3 = child->pins->data[child->pins->size - 1]; - if (ses_same_line(f, p0, p2) && ses_same_line(f, p1, p3)) { + if (ses_same_line(p0, p2) && ses_same_line(p1, p3)) { int ret = ses_path_add(f, parent, child); if (ret < 0) @@ -1474,33 +1780,55 @@ int __ses_topo_layers(ScfEfunction* f, scf_vector_t* paths) { ses_path_t* path; + int ret; int size; int i; + for (i = 0; i < paths->size; i++) { + path = paths->data[i]; + + path->parent_p0 = -1; + path->parent_p1 = -1; + } + do { do { - size = paths->size; + do { + size = paths->size; - for (i = 0; i < paths->size; i++) { - path = paths->data[i]; + _topo_key_components(paths); - _topo_key_components(f, path); - } + ret = _topo_layers(f, paths); + if (ret < 0) + return ret; - int ret = _topo_layers(f, paths); - if (ret < 0) - return ret; + ret = _topo_path_completes(f, paths); + if (ret < 0) + return ret; + } while (size > paths->size); - ret = _topo_path_completes(f, paths); + _topo_key_components(paths); + + ret = _topo_path_neg(f, paths); if (ret < 0) return ret; } while (size > paths->size); - int ret = _topo_path_connect(f, paths); + _topo_key_components(paths); + + ret = _topo_path_pos(f, paths); + if (ret < 0) + return ret; + + _topo_key_components(paths); + + ret = _topo_path_connect(f, paths); if (ret < 0) return ret; } while (size > paths->size); + _topo_key_components(paths); + return _topo_bridge_piers(f, paths); } @@ -1509,13 +1837,11 @@ int ses_layout_paths(ScfEfunction* f, scf_vector_t* paths) if (!f || !paths) return -EINVAL; - ses_path_t* path; - ScfEcomponent* B; - ScfEline* el; + ScfEline* el; + long i; scf_vector_clear(paths, ( void (*)(void*) )ses_path_free); - long i; for (i = 0; i < f->n_elines; i++) { el = f->elines[i]; @@ -1523,7 +1849,7 @@ int ses_layout_paths(ScfEfunction* f, scf_vector_t* paths) if (el->flags & SCF_EDA_PIN_POS) { - int ret = _topo_paths(f, el, paths, 0); + int ret = _topo_paths(el, paths, 0); if (ret < 0) return ret; break; @@ -1535,18 +1861,51 @@ int ses_layout_paths(ScfEfunction* f, scf_vector_t* paths) if (el->flags & SCF_EDA_PIN_IN) { - int ret = _topo_paths(f, el, paths, 0); + int ret = _topo_paths(el, paths, 0); if (ret < 0) return ret; } } -// ses_paths_print(paths); +// ses_paths_print(paths, f); return __ses_topo_layers(f, paths); } -static int _topo_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _topo_paths_lc(ScfEfunction* root, ScfEfunction* f, scf_vector_t* paths) +{ + ScfEcomponent* c; + ScfEline* el; + ScfEpin* p; + + int i; + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + + if (c->f) { + int ret = _topo_paths_lc(root, c->f, paths); + if (ret < 0) + return ret; + continue; + } + + if (SCF_EDA_Capacitor == c->type || SCF_EDA_Inductor == c->type) { + if (c->v >= 0) + p = c->pins[1]; + else + p = c->pins[0]; + el = ses_top_pline(p); + + int ret = _topo_paths(el, paths, 1); + if (ret < 0) + return ret; + } + } + + return 0; +} + +static int _topo_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { ses_path_t* path; ScfEcomponent* B; @@ -1559,13 +1918,16 @@ static int _topo_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* B = f->components[0]; el = f->elines[B->pins[SCF_EDA_Battery_POS]->lid]; - int ret = _topo_paths(f, el, ctx->paths, 1); + int ret = _topo_paths(el, ctx->paths, 1); if (ret < 0) return ret; - scf_logi("\n"); - ses_paths_print(ctx->paths, f); - scf_logi("\n\n"); + ret = _topo_paths_lc(f, f, ctx->paths); + if (ret < 0) + return ret; +// scf_logi("\n"); +// ses_paths_print(ctx->paths); +// scf_logi("\n\n"); ret = __ses_topo_layers(f, ctx->paths); if (ret < 0) @@ -1579,14 +1941,11 @@ static int _topo_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* if (ret < 0) return ret; - int i; - for (i = 0; i < ctx->paths->size; i++) { - path = ctx->paths->data[i]; - - _topo_key_components(f, path); - } + ret = _topo_path_leaf(f, ctx->paths); + if (ret < 0) + return ret; - ses_paths_print(ctx->paths, f); + ses_paths_print(ctx->paths); return 0; } diff --git a/ses_step_va.c b/ses_step_va.c index f151464..8d463ef 100644 --- a/ses_step_va.c +++ b/ses_step_va.c @@ -4,7 +4,7 @@ static void __ses_path_split_v(ScfEfunction* f, ses_path_t* path, int i0, int i, { ScfEpin* p0 = path->pins->data[i0]; ScfEpin* p = path->pins->data[i]; - ScfEcomponent* c = ses_component(f, p); + ScfEcomponent* c = p->c; double v; double r; @@ -48,8 +48,7 @@ void __ses_path_lc(ScfEfunction* f, ses_path_t* path, int m, int n, double* cv, for (i = m; i <= n; i++) { p = path->pins->data[i]; - - c = ses_component(f, p); + c = p->c; if (i & 0x1) { int sign = !p->id - p->id; @@ -75,25 +74,28 @@ void __ses_path_lc(ScfEfunction* f, ses_path_t* path, int m, int n, double* cv, } } -int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ns, int64_t count) +int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double pr, int* changed, int64_t ps, int64_t count) { if (!path) return -EINVAL; - - if (path->pins->size < 2) { - scf_loge("\n"); + if (path->pins->size < 2) return -EINVAL; - } if (n - m < 1) return 0; ScfEcomponent* c; + ScfEcomponent* B = f->components[0]; + ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; + ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; + ScfEline* LP = ses_top_pline(Bp); + ScfEline* LN = ses_top_pline(Bn); + + ScfEpin* p0 = path->pins->data[m]; + ScfEpin* p1 = path->pins->data[n]; ScfEline* el; ScfEpin* p; ScfEpin* p2; - ScfEpin* p0 = path->pins->data[m]; - ScfEpin* p1 = path->pins->data[n]; double _sr0 = p0->sr; double _pr0 = p0->pr; @@ -126,26 +128,27 @@ int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double scf_logw("path: %d, c%ldp%ld-c%ldp%ld, p0->v: %lg, p1->v: %lg, v: %lg, cv: %lg, lv: %lg, pr: %lg, path->pr: %lg, a: %lg\n\n", path->index, p0->cid, p0->id, p1->cid, p1->id, p0->v, p1->v, v, cv, lv, pr, path->pr, a); - double r = 0; - double dv = 0; - double dvc = 0; + double r = 0; + double dv = 0; int i0 = m; int i; for (i = m; i <= n; i++) { p = path->pins->data[i]; - - c = ses_component(f, p); - el = ses_line(f, p); + c = p->c; + el = ses_top_pline(p); 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); - p->a = a; - p->v -= dvc; - el->v = p->v; + p->a = a; + + if (el != LP && el != LN) { + el->v = p->v; + ses_line_set_v(c->pf->elines[p->lid], p->v); + } r += p->r + p->dr; @@ -157,29 +160,7 @@ int __ses_path_va_branch(ScfEfunction* f, ses_path_t* path, int m, int n, double int sign = !p->id - p->id; p2->a = a; - - if (SCF_EDA_Capacitor == c->type) { - cv = c->v * sign; - dv -= cv; - - c->a = a * sign; - dvc += cv; - - scf_logi("c%ld->v: %lg, p->v: %lg, p2->v: %lg, dv: %lg, ja: %lg, ja0: %lg, ns: %ld, uF: %lg\n", - c->id, c->v, p->v, p2->v, dv, p->a, c->a, ns, c->uf); - - } else if (SCF_EDA_Inductor == c->type) { - lv = c->v * sign; - dv -= lv; - - c->a = a * sign; - dvc += lv; - - scf_logi("c%ld->v: %lg, p->v: %lg, p2->v: %lg, dv: %lg, ja: %lg, ja0: %lg, ns: %ld, uH: %lg\n", - c->id, c->v, p->v, p2->v, dv, p->a, c->a, ns, c->uh); - } else - c->a = a * sign; - + c->a = a * sign; c->count = count; scf_logi("path: %d, i: %d, c%ldp%ld, p->v: %lg, dv: %lg, r: %lg, p->a: %lg, a: %lg, p->pr: %lg, e%ld->v: %lg\n\n", diff --git a/ses_step_va_diode.c b/ses_step_va_diode.c deleted file mode 100644 index 985a139..0000000 --- a/ses_step_va_diode.c +++ /dev/null @@ -1,383 +0,0 @@ -#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; - - } else if (SCF_EDA_PNP == c->type && SCF_EDA_PNP_B == p->id) { - - ses_ui_r(&p->dr, NULL, SCF_EDA_V_PNP_ON, 0, a, 0); - - p->dr -= p->r; - - p1 = c->pins[SCF_EDA_PNP_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_PNP_ON, p->r, a, p->dr, p1->cid, p1->id, p1->a); - - p1 = c->pins[SCF_EDA_PNP_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; - ses_path_t* child; - ScfEpin* cp0; - ScfEpin* cp1; - ScfEpin* p; - ScfEpin* p0 = path->pins->data[i]; - ScfEpin* p1 = path->pins->data[j]; - - double v = p0->v - p1->v; - double r; - - __ses_path_pr(f, path, i, j, NULL, &r); - - scf_loge("c%ldp%ld--c%ldp%ld, r: %lg\n", p0->cid, p0->id, p1->cid, p1->id, r); - - int k; - for (k = 0; k < path->childs->size; k++) { - child = path->childs->data[k]; - - cp0 = child->pins->data[0]; - cp1 = child->pins->data[child->pins->size - 1]; - - if (cp0->lid != p0->lid || cp1->lid != p1->lid) - continue; - - double cv = 0; - double lv = 0; - - if (child->n_capacitors > 0) { - __ses_path_lc(f, child, 0, child->pins->size - 1, &cv, &lv, NULL, NULL, NULL); - v -= cv + lv; - ses_ur_i(&child->a, NULL, v, 0, child->pr, 0); - } else { - ses_ur_i(&child->a, NULL, v, 0, child->pr, 0); - - if (child->a >= la) - ses_split_i(&child->a, NULL, la, 0, child->pr, 0, r, 0); - } - - *a -= child->a; - - double _sr = cp1->sr; - double _pr = cp1->pr; - - cp1->sr = child->sr; - cp1->pr = child->pr; - - if (child->n_diodes + child->n_NPNs + child->n_PNPs > 0) { - - 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("k: %d, c%ldp%ld--c%ldp%ld, v: %lg, cv: %lg, lv: %lg, child->pr: %lg, r: %lg, child->a: %lg, el->a: %lg\n", - k, cp0->cid, cp0->id, cp1->cid, cp1->id, v, cv, lv, child->pr, r, child->a, la); - - cp1->v = p1->v; - cp0->v = p0->v; - - double ca = child->a; - - if (child->childs) - __ses_path_split_i(f, child, 0, child->pins->size - 1, child->a, &ca); - - cp0->a = ca; - - if (child->n_diodes + child->n_NPNs + child->n_PNPs > 0) - __ses_path_dr_forward(f, child, 0, child->pins->size - 1, ca); - -ok: - cp1->sr = _sr; - cp1->pr = _pr; - - 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); - } -} - -static void __ses_path_a_diode(ScfEfunction* f, ses_path_t* path, int i, int k, double cv, double* a) -{ - ses_info_t* info; - ses_path_t* child; - - ScfEpin* p0 = path->pins->data[i]; - ScfEpin* p1 = path->pins->data[path->pins->size - 1]; - ScfEpin* pi; - ScfEpin* pj; - - double v = p0->v - p1->v - cv; - double r = 0; - - double _r; - - int j; - - for (j = k; j < path->infos->size; j++) { - info = path->infos->data[j]; - pi = path->pins->data[i]; - pj = path->pins->data[info->i]; - - v -= info->n_diodes * SCF_EDA_V_Diode_ON; - v -= info->n_NPNs * SCF_EDA_V_NPN_ON; - v -= info->n_PNPs * SCF_EDA_V_PNP_ON; - - __ses_path_pr(f, path, i, info->i, NULL, &_r); - - r += _r; - - scf_logd("c%ldp%ld--c%ldp%ld, r: %lg, v: %lg, _r: %lg\n", pi->cid, pi->id, pj->cid, pj->id, r, v, _r); - - i = info->j; - } - - j = path->pins->size - 1; - - if (i < j) { - pi = path->pins->data[i]; - pj = path->pins->data[j]; - - __ses_path_pr(f, path, i, j, NULL, &_r); - - r += _r; - scf_logd("c%ldp%ld--c%ldp%ld, r: %lg, v: %lg, _r: %lg\n", pi->cid, pi->id, pj->cid, pj->id, r, v, _r); - } - - ses_ur_i(a, NULL, v, 0, r, 0); - - scf_loge("c%ldp%ld--c%ldp%ld, r: %lg, v: %lg, a: %lg\n\n", p0->cid, p0->id, p1->cid, p1->id, r, v, *a); -} - -int __ses_path_va_diode(ScfEfunction* f, ses_path_t* path) -{ - ses_path_t* child; - ses_info_t* info; - - ScfEcomponent* c; - ScfEline* el; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* pi; - ScfEpin* pj; - - if ((path->n_diodes + path->n_NPNs + path->n_PNPs) * 2 >= path->pins->size) { - scf_loge("all components are diodes\n\n"); - return -1; - } - - if (path->n_diodes + path->n_NPNs + path->n_PNPs <= 0) - return 0; - - p0 = path->pins->data[0]; - p1 = path->pins->data[path->pins->size - 1]; - - el = f->elines[p0->lid]; - p0->v = el->v; - - el = f->elines[p1->lid]; - p1->v = el->v; - - double v; - double r; - double a; - double cv = 0; - double lv = 0; - - int i = 0; - int j; - - for (j = 0; j < path->infos->size; j++) { - info = path->infos->data[j]; - pi = path->pins->data[info->i]; - pj = path->pins->data[info->j]; - - c = f->components[pi->cid]; - el = f->elines[pi->lid]; - pi->v = el->v; - - assert((SCF_EDA_Diode == c->type && SCF_EDA_Diode_POS == pi->id) - || (SCF_EDA_NPN == c->type && SCF_EDA_NPN_B == pi->id) - || (SCF_EDA_PNP == c->type && SCF_EDA_PNP_E == pi->id)); - - __ses_path_lc(f, path, i, path->pins->size - 1, &cv, &lv, NULL, NULL, NULL); - - __ses_path_a_diode(f, path, i, j, cv + lv, &a); - - if (a < 0) - break; - - if (0 == j) - path->a = a; - - pi->a = a; - - __ses_path_pr(f, path, i, info->i, NULL, &r); - - ses_ir_u(&v, NULL, a, 0, r, 0); - - double cv2 = 0; - double lv2 = 0; - __ses_path_lc(f, path, i, info->i, &cv2, &lv2, NULL, NULL, NULL); - - pi->v = p0->v - v - cv2 - lv2; - pj->v = pi->v - info->n_diodes * SCF_EDA_V_Diode_ON - - info->n_NPNs * SCF_EDA_V_NPN_ON - - info->n_PNPs * SCF_EDA_V_PNP_ON; - - scf_logi("c%ldp%ld->v: %lg, c%ldp%ld->v: %lg, c%ldp%ld->v: %lg, cv2: %lg, lv2: %lg, r: %lg, v: %lg, a: %lg\n", - p0->cid, p0->id, p0->v, pi->cid, pi->id, pi->v, pj->cid, pj->id, pj->v, cv2, lv2, r, v, a); - - el = f->elines[pi->lid]; - el->v = pi->v; -// el->vconst = 1; - - el = f->elines[pj->lid]; - el->v = pj->v; -// el->vconst = 1; - - if (path->childs) { - __ses_path_split_i(f, path, info->i, path->pins->size - 1, a, &pi->a); - - if (info->j < path->pins->size - 1) - __ses_path_split_i(f, path, info->i, info->j, a, &pi->a); - } - 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); - i = info->j + 1; - } - - return 0; -} - -static int ses_path_va_diode(ScfEfunction* f, ses_path_t* path) -{ - ScfEcomponent* B; - ScfEpin* p0; - ScfEpin* p1; - ScfEpin* Bp; - ScfEpin* Bn; - - size_t i; - size_t j; - size_t k; - - if (!path) - return -EINVAL; - - if (path->pins->size < 2) { - scf_loge("\n"); - return -EINVAL; - } - - B = f->components[0]; - Bp = B->pins[SCF_EDA_Battery_POS]; - Bn = B->pins[SCF_EDA_Battery_NEG]; - - p0 = path->pins->data[0]; - p1 = path->pins->data[path->pins->size - 1]; - - if (p0->lid != Bp->lid || p1->lid != Bn->lid) - return 0; - - __ses_path_jr(f, path); - - int ret = __ses_path_va_diode(f, path); - if (ret < 0) - return ret; - - if (path->childs) { - for (j = 0; j < path->childs->size; j++) { - - ret = ses_path_va_diode(f, path->childs->data[j]); - if (ret < 0) - return ret; - } - } - - return 0; -} - -static int _va_diode_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) -{ - ses_path_t* path; - - size_t i; - - for (i = 0; i < ctx->paths->size; i++) { - path = ctx->paths->data[i]; - - scf_logi("i: %ld, path->index: %d\n", i, path->index); - - int ret = ses_path_va_diode(f, path); - if (ret < 0) - return ret; - - printf("\n"); - } - - return 0; -} - -ses_step_t ses_step_va_diode = -{ - .name = "va_diode", - - .handler = _va_diode_handler, -}; diff --git a/ses_step_va_nodes.c b/ses_step_va_nodes.c index 609c340..0b26bb7 100644 --- a/ses_step_va_nodes.c +++ b/ses_step_va_nodes.c @@ -1,6 +1,6 @@ #include"ses_core.h" -int __ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vector_t* paths, int64_t ns, int64_t count) +int __ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vector_t* paths, int64_t ps, int64_t count) { if (!path) return -EINVAL; @@ -25,7 +25,7 @@ int __ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vec scf_logi("---------------\n"); - int ret = __ses_nodes_path_solve(f, path, 0, path->pins->size - 1, changed, ns, count); + int ret = __ses_nodes_path_solve(f, path, 0, path->pins->size - 1, changed, ps, count); if (ret < 0) { scf_loge("\n"); return ret; @@ -39,19 +39,14 @@ int __ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vec return 0; } -static int ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vector_t* paths, int64_t ns, int64_t count) +static int ses_path_va_nodes(ScfEfunction* f, ses_path_t* path, int* changed, scf_vector_t* paths, int64_t ps, int64_t count) { - return __ses_path_va_nodes(f, path, changed, paths, ns, count); + return __ses_path_va_nodes(f, path, changed, paths, ps, count); } -static int _va_nodes_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx_t* ctx) +static int _va_nodes_handler(ScfEfunction* f, int64_t ps, int64_t count, ses_ctx_t* ctx) { - ses_path_t* path; - ScfEcomponent* B = f->components[0]; - ScfEpin* Bp = B->pins[SCF_EDA_Battery_POS]; - ScfEpin* Bn = B->pins[SCF_EDA_Battery_NEG]; - ScfEpin* p0; - ScfEpin* p1; + ses_path_t* path; int changed = 0; int i; @@ -59,15 +54,9 @@ static int _va_nodes_handler(ScfEfunction* f, int64_t ns, int64_t count, ses_ctx for (i = 0; i < ctx->paths->size; i++) { path = ctx->paths->data[i]; - p0 = path->pins->data[0]; - p1 = path->pins->data[path->pins->size - 1]; - -// if (p0->lid != Bp->lid || p1->lid != Bn->lid) -// continue; - scf_logi("i: %d, path->index: %d\n", i, path->index); - int ret = ses_path_va_nodes(f, path, &changed, ctx->paths, ns, count); + int ret = ses_path_va_nodes(f, path, &changed, ctx->paths, ps, count); if (ret < 0) return ret; } diff --git a/ses_steps.c b/ses_steps.c index 822c235..1bb8e8d 100644 --- a/ses_steps.c +++ b/ses_steps.c @@ -10,9 +10,6 @@ extern ses_step_t ses_step_dc_pnp; extern ses_step_t ses_step_topo; -extern ses_step_t ses_step_jr; -extern ses_step_t ses_step_va; - extern ses_step_t ses_step_open; extern ses_step_t ses_step_va_nodes; @@ -45,7 +42,7 @@ static ses_step_t* ses_steps_2[] = &ses_step_draw, }; -static int __ses_analyse_input(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t* ctx) +static int __ses_analyse_input(ScfEfunction* f, int64_t ps, int64_t i, ses_ctx_t* ctx) { ses_step_t* s; @@ -57,7 +54,7 @@ static int __ses_analyse_input(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t if (!s || !s->handler) continue; - int ret = s->handler(f, ns, i, ctx); + int ret = s->handler(f, ps, i, ctx); if (ret < 0) { scf_loge("analysis step '%s' ret: %d\n", s->name, ret); return ret; @@ -67,7 +64,7 @@ static int __ses_analyse_input(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t return 0; } -static int __ses_analyse_time(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t* ctx) +static int __ses_analyse_time(ScfEfunction* f, int64_t ps, int64_t i, ses_ctx_t* ctx) { ses_step_t* s; @@ -79,17 +76,17 @@ static int __ses_analyse_time(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t* if (!s || !s->handler) continue; - int ret = s->handler(f, ns, i, ctx); + int ret = s->handler(f, ps, i, ctx); if (ret < 0) { scf_loge("analysis step '%s' ret: %d\n", s->name, ret); - return ret; +// return ret; } } return 0; } -static int __ses_analyse_current(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx_t* ctx) +static int __ses_analyse_current(ScfEfunction* f, int64_t ps, int64_t i, ses_ctx_t* ctx) { ses_step_t* s; @@ -103,38 +100,53 @@ static int __ses_analyse_current(ScfEfunction* f, int64_t ns, int64_t i, ses_ctx if (!s || !s->handler) continue; - int ret = s->handler(f, ns, i, ctx); + int ret = s->handler(f, ps, i, ctx); if (ret < 0) { scf_loge("analysis step '%s' ret: %d\n", s->name, ret); return ret; } } - scf_loge("--------------- ctx->changed: %d\n", ctx->changed); + scf_logi("--------------- ctx->changed: %d\n", ctx->changed); return ctx->changed > 0 ? -EAGAIN : 0; } -int ses_steps_analyse(ScfEfunction* f, int64_t ns, int64_t count) +static void __ses_init_v(ScfEfunction* f) { - if (!f || ns <= 0 || count < 0) + ScfEcomponent* c; + ScfEline* el; + + long i; + for (i = 0; i < f->n_elines; i++) { + el = f->elines[i]; + el->v = SCF_EDA_V_INIT; + } + + for (i = 0; i < f->n_components; i++) { + c = f->components[i]; + + if (c->f) + __ses_init_v(c->f); + } +} + +int ses_steps_analyse(ScfEfunction* f, int64_t ps, int64_t count) +{ + if (!f || ps <= 0 || count < 0) return -EINVAL; ses_ctx_t* ctx = ses_ctx_alloc(); if (!ctx) return -ENOMEM; - ScfEline* el; - int64_t i; + int64_t i; - for (i = 0; i < f->n_elines; i++) { - el = f->elines[i]; - el->v = SCF_EDA_V_INIT; - } + __ses_init_v(f); for (i = 0; i < count; i++) { printf("\n\033[36m%s(), %d(), count: %ld\033[0m\n", __func__, __LINE__, i); - int ret = __ses_analyse_input(f, ns, i, ctx); + int ret = __ses_analyse_input(f, ps, i, ctx); if (ret < 0) return ret; @@ -142,7 +154,7 @@ int ses_steps_analyse(ScfEfunction* f, int64_t ns, int64_t count) for (j = 0; j < 1; j++) { printf("\n\033[33m%s(), %d(), j: %d\033[0m\n", __func__, __LINE__, j); - ret = __ses_analyse_current(f, ns, i, ctx); + ret = __ses_analyse_current(f, ps, i, ctx); if (-EAGAIN == ret) continue; @@ -154,7 +166,7 @@ int ses_steps_analyse(ScfEfunction* f, int64_t ns, int64_t count) break; } - ret = __ses_analyse_time(f, ns, i, ctx); + ret = __ses_analyse_time(f, ps, i, ctx); if (ret < 0) return ret; } diff --git a/ses_utils.c b/ses_utils.c index fd2a280..47811e5 100644 --- a/ses_utils.c +++ b/ses_utils.c @@ -62,20 +62,14 @@ void ses_edge_print(ses_edge_t* edge) for (j = edge->vip_m; j <= edge->vip_n; j++) { p = edge->path->pins->data[j]; - if (j < edge->vip_n) - printf("c%ldp%ld, ", p->cid, p->id); - else - printf("c%ldp%ld ", p->cid, p->id); + ses_pin_print(p); } } else { for (j = edge->vip_m; j >= edge->vip_n; j--) { p = edge->path->pins->data[j]; - if (j > edge->vip_n) - printf("c%ldp%ld, ", p->cid, p->id); - else - printf("c%ldp%ld ", p->cid, p->id); + ses_pin_print(p); } } @@ -135,17 +129,17 @@ void ses_node_print(ses_node_t* node) return; ses_edge_t* edge; - int i; - printf("node %d: ", node->index); + printf("node %d: \n", node->index); for (i = 0; i < node->edges->size; i++) { edge = node->edges->data[i]; ses_edge_print(edge); + printf("\n"); } - printf("\n\n"); + printf("\n"); } void ses_nodes_print(scf_vector_t* nodes) @@ -188,16 +182,23 @@ void __ses_npn_dr(ScfEcomponent* c, ScfEpin* pb, ScfEpin* pe) pb->dr = pb->r * (SCF_EDA_V_NPN_ON - SCF_EDA_V_NPN_OFF) / (v - SCF_EDA_V_NPN_OFF + 0.001); } +void ses_eline_print(ScfEline* el) +{ + if (el->pf->IC) + ses_IC_print(el->pf->IC); + + printf("el%ld", el->id); +} + void ses_elines_print(ScfEfunction* f) { ScfEline* el; - int i; - for (i = 0; i < f->n_elines; i++) { el = f->elines[i]; - printf("### e%ld->v: %lg\n", el->id, el->v); + ses_eline_print(el); + printf("->v: %lg\n", el->v); } } @@ -219,3 +220,25 @@ void ses_components_print(ScfEfunction* f) } } } + +static void __dfs_set_v(ScfEline* el, double v) +{ + ScfEcomponent* c; + ScfEpin* p; + int i; + + el->v = v; + + for (i = 0; i < el->n_pins; i += 2) { + c = el->pf->components[el->pins[i]]; + p = c->pins [el->pins[i + 1]]; + + if (c->f && p->id < c->f->n_elines) + __dfs_set_v(c->f->elines[p->id], v); + } +} + +void ses_line_set_v(ScfEline* el, double v) +{ + __dfs_set_v(ses_top_line(el), v); +} -- 2.25.1