Forum
 elfmushroom New Member Offline Posts: 1 TW Implement upper and lower current limits in op-amp model Sep 11th, 2018, 7:26pm   Hello,I am trying to model a more accurate op-amp with a current limiting function (different sinking and sourcing currents) and some intuitive parameters for tuning the op-amp characteristics. So I used a transfer function, H(s), to model the ideal op-amp. And then tried to add the current limiting function which is in vain. Could someone give some suggestions? Thanks in advance.p.s. I am aware of the convergence issue about the numerical difficulties. However, I cannot say I am 100% understand the issue. And I found it some what confusing and causing some difficulties to make two limitations.Here's my code... I marked out some lines I tried before. So you might have to tweak the code a little bit. Code:````include "disciplines.vams" `include "constants.vams" `define dB2dec(x) pow(10,x/20) module opamp(vinp,vinm,vdd,vss,voutp); inout vinp,vinm,vdd,vss; inout voutp; electrical vinp,vinm,vdd,vss,voutp; electrical n1,n2; parameter real gain = 90 from (0:inf),          // open loop gain in dB            three_dB_freq  = 100 from (0:inf),   // 3dB frequency            rin  = 10M from (0:inf),             // input resistance            cin  = 1p from [0:inf),             // input capacitance            ioutp_max = 20u from (0:inf),        // max. classAB PMOS output current            ioutn_max = 10u from (0:inf),        // max. classAB NMOS output current            rout = 1k from (0:inf),              // output resistance            cout = 1p from (0:inf),              // output capacitance            vout_offset = 0,            volc = 1; real vin,vout,vout0; real voutmax,voutmin; real iout; real qin = 0; real qout = 0; real cond1, cond2; analog begin    vin = V(vinp,vinm);    vout = V(voutp,vss);    voutmax = V(vdd);    voutmin = V(vss);    qin = cin * vin;    I(vinp,vinm) <+ vin / rin + ddt(qin);    vout0 = laplace_nd(vin*`dB2dec(gain),{1,0},{1,1/(`M_TWO_PI*three_dB_freq)}) + vout_offset;    iout = (vout0 - vout) / rout;     /* try    //cond1 = (vout0-voutmax)/voutmax - (iout-ioutp_max)/ioutp_max;    //cond2 = (vout0-voutmin) - (iout-(-ioutn_max));    //@(cross(cond1,0))    //;    //@(cross(cond2,0))    //;    //if(cond1*cond2<0) begin    //    if(cond1>0)    //        vout0 = voutmax;    //    else    //        vout0 = voutmin;    //end    //else begin    //    if(cond1<0)    //        iout = ioutp_max;    //    else if (cond2>0)    //        iout = -ioutn_max;    //end end of try*/ /* another try    // output current limitation    //case (1)    //  iout >  ioutp_max : iout =  ioutp_max;    //  iout < -ioutn_max : iout = -ioutn_max;    //endcase    // output voltage limitation    //if (vout >= vout_offset)    //    iout = iout*tanh(volc*(voutmax-vout));    //else    //    iout = iout*tanh(volc*abs(voutmin-vout));    //iout = slew(iout,ioutp_max*three_dB_freq,-ioutn_max*three_dB_freq);    //I(voutp,vss) <+ -iout; end of another try*/ // Here just some codes to let this can be run like an ideal model.    I(n1,n2) <+ iout;    V(n2,vss) <+ idt(iout) / cout;    V(voutp,vss) <+ V(n2,vss); end endmodule ```Here's a testbench. (using HSPICE) Code:```.options post=1 \$.options method = gear2only .param VH = 5 .param VL = 1 Vin in 0 pwl(5u VL 5.1u VH 25u VH 25.1u VL) Vdd Vdd 0 6 Vss Vss 0 0 Vfb Vfb VOUT DC=0 Xopamp1 in Vfb Vdd Vss VOUT opamp .param RP=3k .param CP=30p R1 VOUT V1 'RP/3' R2 V1   V2 'RP/3' R3 V2   V3 'RP/3' C1 V1 0 'CP/3' C2 V2 0 'CP/3' C3 V3 0 'CP/3' .tran 1n 30u .probe tran v(*) i(*) .end ``` Back to top IP Logged