Shop OBEX P1 Docs P2 Docs Learn Events
Has anyone written code to read an automotive tach signal? — Parallax Forums

Has anyone written code to read an automotive tach signal?

turbosupraturbosupra Posts: 1,088
edited 2010-01-03 07:04 in Propeller 1
I believe my tach signal is low side pulses per minute. I'd like to see someones prop code if they don't mind sharing.

Did you have to do anything on the hardware side? I'd theorize that the prop could handle the pulses per minute without additional hardware, maybe sans a pull up resistor?
«1

Comments

  • BradCBradC Posts: 2,601
    edited 2009-12-23 05:56
    I'm doing similar but different at the moment. I'm trying a minimal approach to reading the RPM on some marine diesels. The diesels use inductive sensors. The Cummins use a sensor on the injector pump shaft at 2 pulses per rev, and the Volvos use one on the flywheel at 20 pulses per rev.

    Initially I tried a simple high value series resistor (100K) directly into a port pin. This works ok at idle, but as soon as the revs come up and the voltage starts to creep up (I get 2V p-p at idle and 40v p-p at redline) things go haywire. I've borrowed a portable cro now and I'm going to have a crack at it again on Boxing day to see if I can add some "simple" passive external conditioning to calm it down. If that fails I'll have to built a zero crossing detector and some hysteresis to really clean it up.

    Anyway, the code is probably no good to you, but all I'm doing is timing 8 input cycles by using a waitpeq/waitpne loop in a separate cog. That cog writes the timed period to the hub and some spin code converts it to RPM. It's pretty ugly and untidy.

    I guess my point was you might want to look at some external signal conditioning. I'm thinking a simple low pass filter at the moment using an RC network, but I'll see how the next test pans out. It'd be easier if I could just walk to the car in the driveway and do the tests [noparse];)[/noparse]

    <edit> forgot the code

    the extra delays in there help it settle, but it still bounces and false triggers at high rpm so I need to try something else. This is the code for the Cummins, so it gives me RPM for 2 pulses per cycle.

    PUB GetRPM(pin,Rvar) | X, Y
      Pin := 1<<Pin
      repeat
        waitpeq(0,Pin,0)
        waitcnt(cnt+clkfreq/1000)
        waitpeq(Pin,Pin,0)
        X := Cnt
        ' Positive Edge
        repeat 4
          waitpeq(0,Pin,0)
          waitcnt(cnt+clkfreq/1000)
          waitpeq(Pin,Pin,0)
          Y := Cnt
        X := (Y-X)/10
        long[noparse][[/noparse] Rvar ] := ((800000000/X)/5)*3 <# 9999
    
    

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Life may be "too short", but it's the longest thing we ever do.
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 13:19
    You can't beat a low cost LM1815 for reading VR sensors even in a noisy environment.
  • AquaaddictAquaaddict Posts: 20
    edited 2009-12-23 13:58
    Engines tach signals vary between engines, alot of diesels (esp marine), use a signal from the alternator, others use inductive pickups, others come from the ECU based on data from other engine sensors.

    Ants
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 15:25
    How about using the cam or crank signal?


    2zzcranksignal1.jpg



    Aquaaddict said...
    Engines tach signals vary between engines, alot of diesels (esp marine), use a signal from the alternator, others use inductive pickups, others come from the ECU based on data from other engine sensors.

    Ants
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 15:40
    Use the crank signal, if it's of appropriate level - VRs can easily turn out tens of volts at faster than idle speeds. As previously noted, you'll probably have to condition it in some way. Measure ticks between pulses, calculate next predicted pulse time. Use these numbers to calc rpm. That crank sensor trace looks like a 36-1 pattern. This makes calcs nice and easy, each tooth is 10 degrees apart. To get around the missing tooth problem, if actual pulse comes in more than 10% later than predicted time of next pulse, ignore it and do not update the calculated rpm until the next pulse appears. Rinse, repeat.
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 16:33
    That's exactly what it is, 36-1.

    Do you think a transistor could switch fast enough to keep up with the vr sensor pulses, to deal with my voltage issue? Maybe an optocoupler on a circuit with a 3v source and pull down resistor?

    I'll really have to think about how to code for what you suggested with predicted pulse time, I thought it would be as easy as measuring tickets per second [noparse]:([/noparse]



    pmrobert said...
    Use the crank signal, if it's of appropriate level - VRs can easily turn out tens of volts at faster than idle speeds. As previously noted, you'll probably have to condition it in some way. Measure ticks between pulses, calculate next predicted pulse time. Use these numbers to calc rpm. That crank sensor trace looks like a 36-1 pattern. This makes calcs nice and easy, each tooth is 10 degrees apart. To get around the missing tooth problem, if actual pulse comes in more than 10% later than predicted time of next pulse, ignore it and do not update the calculated rpm until the next pulse appears. Rinse, repeat.
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 17:17
    The LM1815 www.national.com/ds/LM/LM1815.pdf I spoke of earlier is specifically designed to detect VR zero crossings and output a variety of square wave signals/pulses/etc. The only reason I mention using a predicted pulse time window is so you can exclude the 200% longer gap at the missing tooth. Basically, detect the long gap as a statistical outlier and use the rest of the interteeth gaps to calc rpm. It IS as easy as measuring ticks per time period but you gotta detect and throw out the artifactual "bad data" caused by the missing tooth in your calcs. I usually calculate microseconds between teeth and go from there. I'm not being deliberately obtuse, I'm not home at the moment and posting this off a phone. If you need sample working code, let me know.
  • ry.davidry.david Posts: 63
    edited 2009-12-23 17:21
    I am actually working on this exact same problem... 36 teeth/rev for the crank position sensor, but on a little 2.4L, haha

    I was planning on using a cog counter in the Positive (or Negative) Edge mode, so I can do other tasks with the cog at the same time. I am not sure of the hardware to safely interface a either 5v or 12v signal to the prop. I was looking at what they use for Megasquirt, and it was an optoisolator, but I am not sure of the reasoning behind a optoisolator versus a transistor between the signal and prop
  • Cluso99Cluso99 Posts: 18,069
    edited 2009-12-23 17:23
    Wouldn't a 100K series resistor and 3V3 zener to gnd at the prop pins work?

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Links to other interesting threads:

    · Home of the MultiBladeProps: TriBlade,·RamBlade,·SixBlade, website
    · Single Board Computer:·3 Propeller ICs·and a·TriBladeProp board (ZiCog Z80 Emulator)
    · Prop Tools under Development or Completed (Index)
    · Emulators: CPUs Z80 etc; Micros Altair etc;· Terminals·VT100 etc; (Index) ZiCog (Z80) , MoCog (6809)
    · Search the Propeller forums·(uses advanced Google search)
    My cruising website is: ·www.bluemagic.biz·· MultiBladeProp is: www.bluemagic.biz/cluso.htm
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 17:51
    @Cluso, good idea! He doesn't require the precise timing zero crossing provides, just a pulse. Much easier to implement than another IC as well.
    @ry.david, there's a sticky thread or an app note that details interfacing 5/12 to the prop with several methods. I'm pretty sure the MS' opto helps keep the coil flyback voltage/ringing from getting to the processor. Most Kettering coils produce a flyback of 1-300+ volts on the coil -, you really don't want that too near logic level components.
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 18:34
    Hey Robert,

    I'd love to see the sample code, when you have a chance, especially the logic behind it. Did you use an oscope to calculate the microseconds at idle and then go from there to build a reference table?

    pmrobert said...
    The LM1815 www.national.com/ds/LM/LM1815.pdf I spoke of earlier is specifically designed to detect VR zero crossings and output a variety of square wave signals/pulses/etc. The only reason I mention using a predicted pulse time window is so you can exclude the 200% longer gap at the missing tooth. Basically, detect the long gap as a statistical outlier and use the rest of the interteeth gaps to calc rpm. It IS as easy as measuring ticks per time period but you gotta detect and throw out the artifactual "bad data" caused by the missing tooth in your calcs. I usually calculate microseconds between teeth and go from there. I'm not being deliberately obtuse, I'm not home at the moment and posting this off a phone. If you need sample working code, let me know.


    lm1815.jpg
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 20:14
    Meaning like this?


    Revision 2
    propellerchip2.jpg

    Would an optocoupler be a better choice, or is EMI not going to be a concern?

    Cluso99 said...
    Wouldn't a 100K series resistor and 3V3 zener to gnd at the prop pins work?
    Post Edited (turbosupra) : 12/23/2009 8:40:03 PM GMT
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 20:15
    No problem, I'll post code in a couple of days. You can calc rpm by simple math. For a 36 tooth wheel:

    Step1: usec/tooth*36 = usec/rev
    Step 2: ((1000000/(usec/rev))*60) = rpm

    Remember that the Prop has no hardware floating point capability for variables, everything has to be integer. Scale accordingly!
    You could also use one of the floating point objects as well.

    Your diagram needs to have the Zener between signal and ground, the resistor would be between the Zener and prop.

    EMI's always a concern around internal combustion engines. Route wires intelligently, ground appropriately with shielded wire and see how it works.

    Post Edited (pmrobert) : 12/23/2009 8:20:55 PM GMT
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 20:39
    Ok, I updated the partial schematic

    Thanks for the hint about floats, I did not know that


    pmrobert said...
    No problem, I'll post code in a couple of days. You can calc rpm by simple math. For a 36 tooth wheel:

    Step1: usec/tooth*36 = usec/rev
    Step 2: ((1000000/(usec/rev))*60) = rpm

    Remember that the Prop has no hardware floating point capability for variables, everything has to be integer. Scale accordingly!
    You could also use one of the floating point objects as well.

    Your diagram needs to have the Zener between signal and ground, the resistor would be between the Zener and prop.

    EMI's always a concern around internal combustion engines. Route wires intelligently, ground appropriately with shielded wire and see how it works.
  • AJMAJM Posts: 171
    edited 2009-12-23 21:19
    I have been using a LM358, as a unity gain buffer, wired directly to the output pin from the ECU.

    I haven't had any issue thus far.
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 21:29
    AJM, he's tapping the VR crank sensor, not a logic level signal. Apples/oranges.
  • AJMAJM Posts: 171
    edited 2009-12-23 21:40
    I suppose I should read the whole thread before posting.

    In any case, if you have access to the ECU logic levels, the op amp will work.

    Sorry for the confusion blush.gif
  • pmrobertpmrobert Posts: 677
    edited 2009-12-23 21:55
    No problem, I apologize if I came off less than genteel. I do like the idea of the opamp's extra isolation when connecting to the very expensive OEM ECUs!
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-23 22:07
    What type of engine/ecu are you doing this on?

    AJM said...
    I have been using a LM358, as a unity gain buffer, wired directly to the output pin from the ECU.

    I haven't had any issue thus far.
  • Miner_with_a_PICMiner_with_a_PIC Posts: 123
    edited 2009-12-23 23:31
    In the above circuit, where a zener and resistor were employed the resistor might be best placed before rather than after the zener, this way the current taken from the crank sensor is limited. See the attached image, the optional capacitor can be used to suppress short duration spikes and should be selected so that RC (R= 100,000 in this example) is much less that the duration of the pulses.

    Post Edited (Miner_with_a_PIC) : 12/24/2009 4:54:23 AM GMT
    607 x 449 - 19K
  • AJMAJM Posts: 171
    edited 2009-12-23 23:40
    turbosupra,

    I tried this on the ECU for a Toyota 2AZ-FE from my daily driver.
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-24 00:48
    Haha, sweet, scion or xrs?

    Mine is for a 2zz, so I'd imagine whatever you did would work perfect for me, and if you don't mind sharing, I'd rather take the easier road, then the harder

    Can we talk via email?



    AJM said...
    turbosupra,

    I tried this on the ECU for a Toyota 2AZ-FE from my daily driver.
  • matbmatb Posts: 39
    edited 2009-12-24 01:12
    Just building the same thing myself. I was planning on taking the 12V signal from the low side of the coil, or possibly earlier on from one of the ECU outputs, ideally the tacho output.

    Since I expect to pick up on a generic NO ecu output, I had a similar circuit, but with a pull down resistor added. I didn't allow for a cap, but darn good point on that!

    As for software, one way is a with a (semi) dedicated cog to time-stamp the edge. The loop looks like:
    - set the counter in level detect mode to match HIGH level. Set the step to 1, and the phase to CNT.
    - spare time, do speed calcs from last transition
    - wait for pin LOW
    - store the counter value

    - set the counter in level detect mode to match LOW level. Set the step to 1, and the phase to CNT.
    - spare time, do speed calcs from last transition
    - wait for pin HIGH
    - store the counter value

    The trick is pre-loading the counter with CNT, and therafter it keeps counting up in lock step with CNT until the input changes.

    I have code that does that, but has a mess of other stuff in there, such as calibratable odometer and start detection. Can post if wanted.


    BTW if the tacho is not critical, you can monitor it on a round robin basis. I will probably do that as I just want a informational display of tacho and also injector duty cycle. The odo is critical, hence got a dedicated cog.

    Post Edited (matb) : 12/24/2009 1:20:19 AM GMT
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-24 01:31
    Hey Mat,

    I would like to see your code if possible, just to see some example code of what you did, especially the syntax.


    matb said...
    Just building the same thing myself. I was planning on taking the 12V signal from the low side of the coil, or possibly earlier on from one of the ECU outputs, ideally the tacho output.

    Since I expect to pick up on a generic NO ecu output, I had a similar circuit, but with a pull down resistor added. I didn't allow for a cap, but darn good point on that!

    As for software, one way is a with a (semi) dedicated cog to time-stamp the edge. The loop looks like:
    - set the counter in level detect mode to match HIGH level. Set the step to 1, and the phase to CNT.
    - spare time, do speed calcs from last transition
    - wait for pin LOW
    - store the counter value

    - set the counter in level detect mode to match LOW level. Set the step to 1, and the phase to CNT.
    - spare time, do speed calcs from last transition
    - wait for pin HIGH
    - store the counter value

    The trick is pre-loading the counter with CNT, and therafter it keeps counting up in lock step with CNT until the input changes.

    I have code that does that, but has a mess of other stuff in there, such as calibratable odometer and start detection. Can post if wanted.


    BTW if the tacho is not critical, you can monitor it on a round robin basis. I will probably do that as I just want a informational display of tacho and also injector duty cycle. The odo is critical, hence got a dedicated cog.
  • Cluso99Cluso99 Posts: 18,069
    edited 2009-12-24 03:30
    turbosupra: The zener is reverse polarity (swap polarity) and move it to the prop side.

    What it will do is clamp the max voltage to 3v3 and the voltage drop will be throught the 100K resistor which should not interfere with the existing circuit. A capacitor should not be required.

    Why is the polarity of the zener reversed? The way you have it, the zener will always conduct when the input voltage is about 0.6V so you will never see a high. When a zerer is reverse biased, the zener will conduct whenever the voltage is above its voltage reference (3v3 in this case - a 2v7 would also be fine). When it conducts, the current it passes causes a voltage drop on the resistor.

    Why is it on the prop side? In the above I showed the 100K resistor (could probably use a 1M also) is used to drop the voltage. This protects the prop and does not (should not because of the high resistance) interfere with the existing circuit.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    Links to other interesting threads:

    · Home of the MultiBladeProps: TriBlade,·RamBlade,·SixBlade, website
    · Single Board Computer:·3 Propeller ICs·and a·TriBladeProp board (ZiCog Z80 Emulator)
    · Prop Tools under Development or Completed (Index)
    · Emulators: CPUs Z80 etc; Micros Altair etc;· Terminals·VT100 etc; (Index) ZiCog (Z80) , MoCog (6809)
    · Search the Propeller forums·(uses advanced Google search)
    My cruising website is: ·www.bluemagic.biz·· MultiBladeProp is: www.bluemagic.biz/cluso.htm
  • yarisboyyarisboy Posts: 245
    edited 2009-12-28 18:37
    I've gotten help from forum members on this issue. On Toyotas (OBD2 wire) I can use a resistor and a zener to feed the pin on either a BS2 (5 volts) or a Propeller (3.3 volt zener). Just in case some one uses my tachometers on a points distributor antique I have an opto-isolator in the layout now. The one specified by another forum member has hysteresis or schmitt trigger characteristics to clean up the signal going to the pin.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
    MOORE'S LAW: The capabilities of electronics shall double every 18 months.
    cloyd's corollary: Hardware is easy, software is hard.
  • matbmatb Posts: 39
    edited 2009-12-29 09:32
    My odo counter object is attached as example of the counting technique.

    As usual, code needs more cleanup.
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-31 05:06
    @Clusco and yarisboy, I will try that circuit out, thank you!

    @Matb, thanks so much for the code, now to try and institute it, since my car is a 4 stroke coil on plug (no waste spark) I may have to have it read something every 2 revolutions, correct?
  • turbosupraturbosupra Posts: 1,088
    edited 2009-12-31 06:33
    So the consensus is that this is the best setup for my tach input circuit?


    tachsignalprop1.jpg





    And the consensus is that this is the best setup for my voltage follower?


    voltagefollowerprop1.jpg
  • Miner_with_a_PICMiner_with_a_PIC Posts: 123
    edited 2009-12-31 17:19
    Turbosupra, there are a couple of issues with the first circuit that would need to be addressed before it would work successfully...

    1) The tach signal is insufficient to drive the LED in the optocoupler
    2) No current limiter for the LED in the optocoupler
    3) Optocoupler output transistor is inserted in the opposite polarity


    See attached image for suggested fixes...the 100k value probably needs some experimentation. Please note that the signal at the pin is expected to be inverted in the attached schematic (i.e. pin high with no signal and low when signal pulse is applied to tach input). Simple changes to software could correct for this.

    Incidentally does anyone know what to do with the dangling base on the optocoupler output?

    I didn't look too closely at the second circuit as I was unsure what its purpose was.
    842 x 494 - 40K
Sign In or Register to comment.