Electronic – How to measure phase accurately using LTSpice

ltspicephase

I am trying, and failing, to measure phase in LTSpice. I've used the suggestion here

.tran 0.00001 0.5
.meas TRAN time_1 TRIG V(N001)=0 RISE=1 TD=0.4 TARG V(N001)=0 RISE=2 TD=0.4
.meas TRAN time_2 TRIG V(N001)=0 RISE=1 TD=0.4 TARG V(N002)=0 RISE=1 TD=0.4
.meas phase param 360*time_2/time_1

but the result isn't very accurate, even for the simple RC filter in the picture below.

LTSpice RC filter

How should I be doing it?

Note that the actual phase I need to measure is in a slightly more complex circuit, but I've reduced it to a simple circuit that seems to have the same problem.

Best Answer

The measurements should be fine, there is no one way to rule them all. You can use:

.meas t1 when v(1)=0 rise=1 td=0.4
.meas t2 when v(2)=0 rise=1 td=0.4
.meas phase param 360*(t2-t1)*500

just as well and it will give you what you want. It is assumed you are in the steady-state (the reason for adding td).

The problem is that you are using .tran 10u 0.5 probably thinking that you are imposing a timestep, but that's not what it does. It can be misleading, I agree. For an imposed timestep, you have to use:

.tran 0 0.5 0 10u

This, by itself, will help, but not much. By default, LTspice uses a waveform compression algorithm which limits the number of plotted points to 1024. For your case, 0.5/10u = 50k points, which will be reduced, so to disable waveform compression, either alter the option in Control Panel > Compression > Window size(No. of Points) (the setting is not remembered during sessions), or add:

.opt plotwinsize=0

to the schematic. This is the preferred way, since it is remembered for any schematic that uses the option (and can be easily toggled between a SPICE directive, and a comment). The downside is that, with waveform compression off, the .raw file will grow and grow. One cure for that is to use the .save command.

Another thing that you can do to increase the accuracy is to use:

.opt numdgt=7 measdgt=13

Any number greater than 6 for numdgt enables double precision data points, while measdgt sets the number of digits for the .meas.


An .AC analysis is recommended for frequency domain measurements (as mentioned by Bimpelrekkie), if possible (there are times when it's not). If it is possible, using .ac list 500 will work fir this case. One thing to remember is that the number of .AC points is limited to 65536.

For those cases when it's not possible, regarding imposing an even smaller timestep, there is a workaround. If your circuit has a long settling time, imposing a very small timestep will mean possible hours of simulation and many GB of storage. There may be a trick to avoid that: don't set a timestep, instead set up a PULSE() source with a delay >= settling time, and with a period <= the smallest desired timestep. This way, the simulation will fly during the transient, and will crawl during the steady-state.

For example, given the circuit in your picture, the 1% settling time should be after some 46 ms, so set up a source with PULSE 0 1 50m 1u 1u 1u 4u. This will impose a 1 µs timestep since the timepoints for the source are known, which means the solver will have to reduce the timestep to accomodate these.

The advantage is that it can also be turned on or off:

  • If it only has to be turned off, then specifying the number of periods will do, but be careful with this: since the timepoints need to be known, that means there will be a delay before the simulation starts caused by calculating these timepoints. This only happens if the number is large (i.e. many timepoints to calculate). If the number of periods is not specified, the engine knows it only needs a simple repeating pattern of a few timepoints.

  • If it needs to be turned on and off, then use the keyword trigger: PULSE 0 1 50m 1u 1u 1u 4u trigger V(x)>0.3, where V(x) is some controlling voltage. It's pretty self-explanatory, but for the sake of future readers, if V(x) is from another source, e.g. SIN 0 1 10, then the PULSE() source will be turned on everytime `V(x)>0.3, and off otherwise.