The Cranky Sysadmin A world of technology, fun, and ignorant rants.

March 25, 2012

filters with ngspice

Filed under: Electronics — Cranky Sysadmin @ 2:18 pm

I’m learning about RF filters, which is a lot of fun, but it’s math intensive (at least for me it is). I’m trying to work with the gEDA tools like gschem and gattrib along with ngspice so I can simulate circuits before I put them together.

I’m a complete noob to this stuff, so I’m just fumbling my way through as best I can. My first stab at a working filter was a hopeless failure in ngspice, so I won’t trouble you with that. My first sort of working example is a Butterworth third order low pass filter for 2 mhz. Below is the schematic with 50 ohm terminations:

Butterworth Low Pass 2mhz

I used a tutorial to transform the schematic to a net list with gnetlist. The schematic includes all of the values needed to properly import into a net list. The command I used on the finished and saved schematic was:

gnetlist -g spice -o filter.net filter.sch

Then I called ngspice, “ngspice filter.net”

and from the ngspice command line, I setup a frequency sweep from 0.1 hz to 4 mhz (I can’t figure out the magic to do mhz in ngspice, so I used 4000 khz):

> ac lin 1000 0.1 4000khz
> plot n1

The result of the (voltage) plot is:

voltage plot of low pass filter

I then attempted a plot of power, which I am probably getting wrong. I’m using the formula v(at n1) / 50 (the termination resistance) * v (at n1 again). Below is the plot:

power plot of butterworth. Clearly wrong.

I’m doing something(s) wrong, but it’s a fun learning experience. Once I sort out my mistakes, I’ll add a post with some guidance on simulating a filter from a gschem schematic through the ngspice machinations.

4 Comments »

  1. Hi,

    the outputs of an ac simulation are vectors of complex numbers (we have real and imag, transformable into magnitude and phase). So v(n1)*v(n1) will not yield the right result because you need multiplying with the invers.

    Use mag(v(n1)) instead.

    Holger

    Comment by Holger — April 16, 2012 @ 5:35 am

  2. The correct terminology is:

    Multiply v(8) with the conjugated complex number of v(8) (which is done by the function mag() ).

    Holger

    Comment by Holger — April 16, 2012 @ 8:40 am

  3. another comment:

    mag(v(n1)) = sqrt(v(n1)*v~(n1))

    real(v(n1) = real(v~(n1))
    imag(v(n1) = -imag(v~(n1))

    Holger

    Comment by Holger — April 16, 2012 @ 9:40 am

  4. That worked great. Thanks for the help. I ignored math for too long, so I’m a little fuzzy on why it works, but I get a graph that I expect. I am looking for the -3db roll off, which I seem to get in the right place if I divide by 50 (the termination resistance). I don’t know if this is a coincidence. so plot mag(v(n1))/50 shows the -3db roll off at 2mhz. It’s time for me to experiment a little I think.

    Comment by Cranky Sysadmin — April 17, 2012 @ 5:09 am

RSS feed for comments on this post. TrackBack URL

Leave a comment

Powered by WordPress