Tube Simulation with PSPICE: Tips, Tricks, TechniquesAuthor: Dmitry Nizhegorodov (dmitrynizh@hotmail.com). My other projects and articles
1.2 Starting a brand new project... from scratch? 1.3 Transformers and grounding 1.4 A 1M resistor gotcha 1.5 Small assorted gotchas 3. How to Show Plate Curves, Loadlines and Max Dissipation Curves 4. A Real Transformer 5. X-Y mode tricks 6. Collecting and Plotting Distortion Data
1. Zero Node and Other Assorted Oddities1.1 A Zero NodeAn otherwise healthy circuit will not work unless there is at least one node part named 0. This is true for most versions of SPICE. I believe a zero node is used as a reference point to calculate voltages and currents against.I use a grounding-symbol node for this purpose. To come up with such node, I created a grounding part using the parts menu (an icon will work, too), double-clicked on it to open its property dialog and then set its NAME and NODENAME properties to 0. After that I always do Ctrl-c, Ctrl-v on such node if I need an another one. By the way, "0" need not be displayed on the schematics page; to hide, it double-click on the part - this will show the properties list, single-click on "NODENAME" and the press button "Display". In the popped-up dialog, select "Do not Display" and press "OK" button. Then you can cut and paste this node whenever you need a ground. Note that "NAME" need not be 0; if you want to have several grounds with different names, then you can change NAME from 0 to anything like G1 etc. and have the property value displayed.
1.2 Starting a brand new project... from scratch?I avoid starting projects from scratch. Instead, in the "New Project" dialog box which pops up after a name and directory selection dialog is done, I chose an option "Based On" and find a project which is a best prototype for a new design. In my opinion this saves tons of time.
1.3 Transformers and groundingPSPICE, as well as most variants of SPICE will complain if the sub-circuit that is formed by the output taps of a tube output transformer and the load is disconnected from the main circuit.The easiest solution is to connect one wire to the ground.
1.4 A 1M resistor gotcha1M resistors were pretty popular as values of volume pots or grid resistors in old tube schematics and thus SPICE tube circuit modeling may need these. What is so special about that? 1M entered in PSPICE as a value for a resistor will ruin your day. The circuit will suddenly start working in the most strange way.The gotcha is in the 'M'. PSPICE is not case sensitive and it does not understands that 1M is not a 1m! In other words, your 1M pot or greed shunt or feedback resistor will be actually processed by SPICE as 1 milli-Ohm resistor, something infinitely close to a straight wire in the world of tube circuits. Instead of typing 1M you must type 1Meg or 1meg. My "workaround" for this is in not using Mega-Ohms at all. I limit myself to 'K', and on rare occasions when I do need a 1M resistor I punch in "1000k" instead.
1.5 Small assorted gotchas
2. What is the best setup for tube transient analysis?There is probably no "best" setup, but for quick runs with precision sufficient for audio applications I use the following PSPICE setting for "Edit Simulation Profile", "Analysis Type": "Time Domain (Transient ):
Run to time.................. 10ms Start saving after .......... 2ms Maximum step size............ 10us Output File Options: Center Freq .......... 1 khz Number of Harmonics... 5 Output Variables ..... <whatever>For better precision I use slightly more dense steps - 5 or even 1 us.
3. How to Show Plate Curves, Loadlines and Max Dissipation Curves3.1 Plate CurvesI borrowed the following technique from www.next-power.net/next-tube/. The article that discussed the technique is in currently available only in Russian, hence I point directly to a zip file with a PSPICE project that computes plate curves. The project does a DC sweep over anode voltages, with secondary sweep, where the secondary sweep steps across grid voltage range.To set up a new plate-curves project in PSPICE/ORCAD from scratch:
(2) Navigate the menubar: PSpice -> Edit Simulation Profile -> Analysis Type, and select DC Sweep. In Options, Primary Settings select Sweep Variable tab Global Paramater, and type "V" in Paramater Name. Sweep Type set to Linear and specify Start = 0, End = 400, Increment = 10. Check checkbox Secondary Sweep, then also select Sweep Variable tab Global Paramater, and then type "VG" in Paramater Name. Sweep Type set to Linear and specify Start = 0, End = 14, Increment = 1. (3) Add global parameters V and VG using the menu bar selection: PSpice -> Place Optimizer Parameter; double click on the Optimizer Parameters construct and in the dialog type V in the Name field and press "Add", and then type VG, press, "Add" and then "OK". Now Press Run and if everything is fine, you'll see place curves. Note: you'll likely need to adjust the Y scape. doubel click on it and switch to User Defined, providing suitable range. For 6p14p, 0 to 80-100ma is enough. I have a PC folder which "curves" where I maintain a separate project for each tube I use in my PSPICE modeling often.
3.2 Loadlines in PSPICE![]()
Ystart - Xvar / loadwhere Ystart is the point where the load line will cross the Y grid line, Xvar is the variable used for the X coordinate, and load is load resistance. Example:
6ma - V_V1 / 100kFor loadline that goes across a specifc point Px,Py, use this:
Py + (Px - Xvar) / 100k.Thus, for the above curve to go over a 20V, 5mA point:
5ma + (20V - V_V1) / 100k 3.3 DissipationFinally, a power dissipation curve can be plotted with the following formula:
power/Xvarwhere power is max power dissipation but could be any value for power you're interested, and Xvar is voltage such as V_V1. This works because power = V * I.
3.4 Push-pull plate curvesIf you've seen plots with "composite" loadlines for push-pull tubes, you wonder how to do it in PSPICE. It is not completely trivial, yet not hard. A little trick is needed, for which the step of adding optimizer parameters see above shows its usefulness. Composite curves will show up if one tube runs DC sweep as above, while another is swept with plate DC that steps down from the max. If the max is set to 400 then the DC on the second plate must be set to {400 - V}. Exactly similar setting must be done for the grid. If the sweep is from 0 to 20 (meaning we're interested in -10V idle bias), then the second tube should see {20 - VG}. Make sure the secondary sweep is from 0 to 20, not to 14 as above.
4. A Real TransformerTBD
5. X-Y mode tricksFor an experienced eye, a 2-channel oscilloscope set in X-Y mode can be an indispensable source of information about a circuit. It is possible to guess about overloading characteristics, phase distortion, THD and even about relative weight of harmonics of different orders. PSPICE can help to train your eyes in reading X-Y figures.Here is how to switch to X-Y mode in PSPICE
run transient analysis switch X from Time to input signal's variable. to compensate phase: run FFT, get phase shift of the 1st harmonic add another input source, set its phase as above switch X from Time to the new input signal's variable.Some details: To enter X-Y mode, I click on the X axis on a data plot and press the Axis Variable button, By default, the variable is Time. I then tell PSPICE to use an axis variable related to my input signal. PSPICE will display a straight line or an elliptic curve or a bent line - depending on the distortion the circuit introduces. For my SET amps, I often get a thin elliptic curve slightly bent in one direction:
The "gap" between the sides of the ellipse is proportional to the phase shift between the input and the output. 0 phase gives a straight line, -90 and 90 give a circle. A delay of 45 degrees will give a thick, wide oval. The bending reflects harmonics - any assymetry in the shape of the ellips indicates distortion. Low-order harmonic distortion if evident from gentle, smooth bending, sharper knees mean high-order distortion. Even harmonics are evident from assymetrical, single-ended (yes! pun intended) bends. Odd harmonics are evident from symmetrical, s-like patterns. A distinct knee indicates hard single-ended clipping, more rounded one - soft clipping. Symmetrical knees indicate push-pull style of clipping. When one knee is sharp and the opposite one is soft, it indicates either a series of tubes going into various conditions, or a single tube going into above-zero-grid voltage region on the Up swing and and into dense, over-bias region on a down swing. For example, the figure shown above indicates no clipping, small phase shift and clear presence of 2nd order distortion and a touch of 3rd order. Indeed, the FFT analysis gives this data:
NO (HZ) COMPONENT COMPONENT (DEG) PHASE (DEG) 1 1.000E+03 7.938E+00 1.000E+00 2.862E+00 0.000E+00 2 2.000E+03 4.117E-01 5.187E-02 9.775E+01 9.202E+01 3 3.000E+03 1.069E-01 1.347E-02 8.510E+00 -7.633E-02 TOTAL HARMONIC DISTORTION = 5.365536E+00 PERCENTFive % of 2nd order distortion is clearly visible as downward bend of the upper side of the curve. A 1.3 % of 3rd is harder to spot but is is evident from a slight S-shaping of the curve. Adding a staright line helps in disovering deviations. A line that intersects the curve in any desired point can be easily added with the help from the Cursor Display. For the above curve, -1v alone X corresponds to -8.57V alone Y. I add a new trace (Add Trace button) as V(V2+)* 8.57:
My next X-Y trick is phase shift compensation. Often a phase shift makes it hard to judge deviations of a shape from a straight line. Since A Sin input is what most often used for transient analysis, I add another, identical Sin input with a different phase. The phase I find in the FFT data - 2.862E+00 for the example above. I add such Sin node, (it is OK to leave it unconnected), cut&paste the phase value, and re-run simulation, then use the new signal as X variable:
Finally, to get better reading of "deviation" from a bisecting line, I substitute the phase-corrected source multiplied by the same coefficient as above:
6. Collecting and Plotting Distortion DataVery often I want to pas a signal of several different voltages through an amp, collect distortion data for each run, and then show that data on a plot. I came up with the following method. I run repeated simulation and collect distortion data for several runs in a text file. I extract the data from PSPICE-generated *.out reports. Here is an example:
HARMONIC FREQUENCY FOURIER NORMALIZED PHASE NORMALIZED NO (HZ) COMPONENT COMPONENT (DEG) PHASE (DEG) 1 1.000E+03 8.130E+00 1.000E+00 -2.063E+00 0.000E+00 2 2.000E+03 5.096E-02 6.268E-03 1.001E+02 1.042E+02 3 3.000E+03 5.681E-02 6.987E-03 -1.544E+01 -9.246E+00 4 4.000E+03 2.131E-02 2.621E-03 -1.110E+02 -1.027E+02 5 5.000E+03 9.697E-03 1.193E-03 1.586E+02 1.689E+02 1 1.000E+03 7.603E+00 1.000E+00 -2.062E+00 0.000E+00 2 2.000E+03 3.353E-02 4.411E-03 1.077E+02 1.118E+02 3 3.000E+03 3.950E-02 5.195E-03 -1.620E+01 -1.001E+01 4 4.000E+03 1.267E-02 1.666E-03 -1.135E+02 -1.053E+02 5 5.000E+03 4.928E-03 6.481E-04 1.551E+02 1.654E+02 1 1.000E+03 6.798E+00 1.000E+00 -2.059E+00 0.000E+00 2 2.000E+03 1.974E-02 2.904E-03 1.221E+02 1.262E+02 3 3.000E+03 2.382E-02 3.505E-03 -1.681E+01 -1.063E+01 4 4.000E+03 6.115E-03 8.996E-04 -1.170E+02 -1.088E+02 5 5.000E+03 1.827E-03 2.688E-04 1.493E+02 1.595E+02 1 1.000E+03 5.442E+00 1.000E+00 -2.051E+00 0.000E+00 2 2.000E+03 1.031E-02 1.894E-03 1.466E+02 1.507E+02 3 3.000E+03 1.036E-02 1.903E-03 -1.712E+01 -1.096E+01 4 4.000E+03 1.933E-03 3.551E-04 -1.233E+02 -1.150E+02 5 5.000E+03 3.637E-04 6.683E-05 1.411E+02 1.514E+02 1 1.000E+03 4.082E+00 1.000E+00 -2.043E+00 0.000E+00 2 2.000E+03 5.943E-03 1.456E-03 1.634E+02 1.675E+02 3 3.000E+03 3.961E-03 9.703E-04 -1.731E+01 -1.118E+01 4 4.000E+03 6.096E-04 1.494E-04 -1.342E+02 -1.261E+02 5 5.000E+03 8.273E-05 2.027E-05 1.491E+02 1.593E+02 1 1.000E+03 2.720E+00 1.000E+00 -2.036E+00 0.000E+00 2 2.000E+03 2.946E-03 1.083E-03 1.727E+02 1.768E+02 3 3.000E+03 1.068E-03 3.926E-04 -1.852E+01 -1.241E+01 4 4.000E+03 2.198E-04 8.081E-05 -1.545E+02 -1.464E+02 5 5.000E+03 4.948E-05 1.819E-05 -1.796E+02 -1.694E+02 1 1.000E+03 1.360E+00 1.000E+00 -2.030E+00 0.000E+00 2 2.000E+03 9.146E-04 6.727E-04 1.778E+02 1.818E+02 3 3.000E+03 9.078E-05 6.676E-05 -3.220E+01 -2.611E+01 4 4.000E+03 9.804E-05 7.210E-05 -1.695E+02 -1.613E+02 5 5.000E+03 3.731E-05 2.744E-05 -1.733E+02 -1.631E+02 1 1.000E+03 5.437E-01 1.000E+00 -2.027E+00 0.000E+00 2 2.000E+03 2.212E-04 4.068E-04 -1.795E+02 -1.754E+02 3 3.000E+03 1.955E-05 3.596E-05 -1.616E+02 -1.555E+02 4 4.000E+03 4.200E-05 7.725E-05 -1.721E+02 -1.640E+02 5 5.000E+03 1.816E-05 3.339E-05 -1.731E+02 -1.630E+02 1 1.000E+03 2.718E-01 1.000E+00 -2.026E+00 0.000E+00 2 2.000E+03 8.620E-05 3.171E-04 -1.780E+02 -1.740E+02 3 3.000E+03 1.347E-05 4.954E-05 -1.712E+02 -1.651E+02 4 4.000E+03 2.156E-05 7.931E-05 -1.726E+02 -1.645E+02 5 5.000E+03 9.549E-06 3.513E-05 -1.730E+02 -1.628E+02 1 1.000E+03 1.359E-01 1.000E+00 -2.026E+00 0.000E+00 2 2.000E+03 3.709E-05 2.729E-04 -1.770E+02 -1.729E+02 3 3.000E+03 7.320E-06 5.386E-05 -1.732E+02 -1.671E+02 4 4.000E+03 1.091E-05 8.030E-05 -1.725E+02 -1.644E+02 5 5.000E+03 4.953E-06 3.644E-05 -1.724E+02 -1.623E+02Next I pipe this data through an awk script that converts it into a data file for a plotter: spice2plot.sh out.txt > d.plt I use PTPLOT release 2.0 as my plotter. The script spice2plot.sh has several control options that allow me to show output signal as voltage amplitude or RMS, or wattage into specified load, also as amplitude or RMS. Here is the code for spice2plot.sh:
#! C:/mksnt/sh.exe # # usage: spice2plot.sh <simdata> [lpr] [n] # where l:log p: power r: RMS n: load in ohms # by default: voltage amplitude, percentsh # # usage examples: # spice2plot.sh simres.out # V, amplitude, percents # spice2plot.sh simres.out l # V, amplitude, logarithmic # spice2plot.sh simres.out lrp 16 # W, RMS, logarithmic, into 16 ohm awk ' BEGIN { options = "'$2'"; type = (index(options,"l") > 0 ) ? "log" : "%" ; scale = (type == "log") ? 1 : 100; ampl_t = (index(options,"r") > 0 ) ? "RMS" : "Amplitude"; out_t = (index(options,"p") > 0 ) ? "W" : "V"; load = ("'$3'" != "") ? "'$3'" : 8; signal = ""; count = 0; order = 1; } function rms (v) { return ampl_t == "RMS" ? .707 * v : 1 * v; } function power (v) { return out_t == "W" ? v * v / load : 1 * v; } $1 == "1" { count++; signal = power(rms($3)); signals[count] = signal; } $1 ~ /[2-9]/ { if ($1 > order) order = $1; spectrum[signal ":" $1 ] = $4 * scale; } END { print "TitleText: Distortion, ", type print print "Marks: dots" print "XLabel: Output Signal,", out_t, ampl_t, ((out_t == "W") ? "into " load " ohm" : "") print "YLabel: Distortion, ", type print "NumSets: " order-1 if (type == "log") print "YLog: on" for (j = 2; j <= order; j++) { print print "DataSet: " j " harmonic" for (i = 1; i <= count; i++) { val = spectrum[signals[i] ":" j] if (val != "") printf(" %s, %s\n", signals[i], val); } } } ' $1For example, file d1.plt produced as spice2plot.sh out.txt > d.plt results in
or the same input data can be plotted in logarithmic scale: spice2plot.sh out.txt l > dl.plt which gives
finally, how about Watts RMS into 16 ohm: spice2plot.sh out.txt lrp 16 > d1rp16.plt
Author: Dmitry Nizhegorodov (dmitrynizh@hotmail.com). My other projects and articles
|