Reading PWM of an external source

I'm trying to read the rpm signal of my vehicle through an output wire from the ECU. It's already a 5v pwm signal so I simply plugged it into D5 on my uno.

Here's my unadultered current code with unused functions left out.

int speedoPin = 4;
int RPMInPin = 5;
int slaveSelectPin = 10;
unsigned long HzToRPMConversion = 114; //31665.4<U+202C>;
volatile unsigned long signal = -1;
volatile unsigned long time1 = -1;
volatile unsigned long time2 = -1;

void setup()
{
  len = 8;        //length set at 8 for all messages sent
  extended = 0x0; //set as not extended format for all messages sent
  del = 10;       // delay time between steps 10-15 works well.

  pinMode(RPMInPin, INPUT); // Set D5 as tach input from LS PCM

  CAN_begin(MCP2515_SPEED_500000);
  CAN_setMode(CAN_MODE_NORMAL);

  //   attachInterrupt(0, timing1, RISING);
  //    attachInterrupt(1, timing2, FALLING);

  Serial.begin(115200);
}

void timing1()
{
  time1 = micros();
}

void timing2()
{
  time2 = micros();
  Serial.println(time2 - time1);
}

unsigned long rpm = 0;

void loop()
{
  //CheckRPM();
  // delay(del);
  CheckRPM1();
  return;
  // if (CAN_available())
  // {
  //   CAN_getMessage();
  //   CAN_ProcessMessage();
  // }

  delay(del);
  //Todo: Get vehicle RPM
  send_RPM(500); //DME1
  delay(del);
  send_DME2();
  delay(del);
  send_DME4();
  delay(del);
  send_ASC1();

  send_Speed(90);
}

void CheckRPM()
{
  signed long rpmDurationHigh = pulseIn(RPMInPin, HIGH);
  signed long rpmDurationLow = pulseIn(RPMInPin, LOW);
  unsigned long cycleTime = rpmDurationHigh + rpmDurationLow;
  Serial.print("High => ");
  Serial.print(rpmDurationHigh);
  Serial.print(" Low => ");
  Serial.print(rpmDurationLow);
  Serial.print(" Cycle => ");
  Serial.println(cycleTime);
  rpm = cycleTime * HzToRPMConversion;
  Serial.println(rpm);
}

byte in_was = LOW;
byte in_now;
unsigned long wentup = 0;
unsigned long wentdn = 0;
unsigned long total = 0;

void CheckRPM1()
{
  // Read pin once
  in_now = digitalRead(RPMInPin);

  // Now, were we high or low?
  if (in_was == LOW)
  {
    if (in_now == HIGH)
    {
      // So, has transitioned from low to high
      in_was = HIGH;
      Serial.print("wentup = ");
      Serial.println(micros() - wentup);
      wentup = micros();
    }
  }
  else
  {
    if (in_now == LOW)
    {
      // So, has transitioned from high to low
      in_was = LOW;

      Serial.print("wentdn = ");
      Serial.println(micros() - wentdn);
      wentdn = micros();
    }
  }
  // if( wentup - wentdn != total)
  // {
  //  total = wentup - wentdn;
  ///     Serial.print("total = ");
  //     Serial.println(total);
  // }
}

Attached is this code's output while cranking the engine over (I can't start it just yet). The car does run, it just has no exhaust on it currently.

Anyway, I can't make heads or tails of what the output is giving me. I'm assuming the car's voltage is filtered as to not have fluctuations. Googling says 50hz should equate to 1900rpms. Cranking should be around 200rpms. But also, the rpm output has been messed with by a previous owner so it might be off by a factor of 1/4 (8cyl mode vs 6cyl mode, long story).

Am I even on the right path here?

Read the instructions for posting please.

Also: Knowledgeable people will not open a .zip file from the Internet.

Other than quotes instead of code tags and uploading a zip, is there anything I did wrong? I changed the attachment to an image but that kind of does away with a lot of the data.

You cou

protomor:
Other than quotes instead of code tags and uploading a zip, is there anything I did wrong? I changed the attachment to an image but that kind of does away with a lot of the data.

You could learn how to Embed an uploaded image: How to Embed Uploaded Images
And, I can only address the "reading a PWM signal" part. Converting that data to RPM probably requires more information.

Assuming the Arduino you wish to use [are attempting to use] (something you failed to mention, as far as I can tell), is fast enough to do this at the resolution you are hoping for (another, apparent, missing detail), I would approach this by directly using one of the Timers to capture the pulse width of either the HIGH pulse, or the LOW pulse, or both. To do this, you will, likely need to dig into the MCU's Timer Control registers, such as for the 16-bit Timer/Counter1, on the Atmel328P [MCU for the Arduino UNO].

Have a look at this: http://ww1.microchip.com/downloads/en/AppNotes/Atmel-8014-Using-Timer-Capture-to-Measure-PWM-Duty-Cycle_ApplicationNote_AVR135.pdf

Hi EMF. My second sentence says I'm using an Uno. I'm not sure about resolution. I was hoping to see what I could get and see if it met my needs.

I'll take a look at the pdf and see if it helps.

I modded the first post to have the image in it but it cuts down the size. If zip files aren't allowed, why is it an accepted upload? I would have much preferred to upload my original xlsx.

protomor:
I'm trying to read the rpm signal of my vehicle through an output wire from the ECU. It's already a 5v pwm signal so I simply plugged it into D5 on my uno.

Anyway, I can't make heads or tails of what the output is giving me. I'm assuming the car's voltage is filtered as to not have fluctuations. Googling says 50hz should equate to 1900rpms. Cranking should be around 200rpms. But also, the rpm output has been messed with by a previous owner so it might be off by a factor of 1/4 (8cyl mode vs 6cyl mode, long story).

It's definitely hard to make heads-or-tails from the details too for somebody else without accurate details about the data you're showing (in that spreadsheet).

You mention from an output wire of ECU, but your data shows at least two sets of data --- 'up' and 'down'. So first step is to establish what up and down waveforms represent.

Also --- pwm is supposed to be constant peak amplitude....so some of those spikes that are much larger than the other ones look out of place.

The code that I'm running is from another thread (Read signal (5v wave) get it's frequency, output converted frequency x2 - Project Guidance - Arduino Forum) on the same general topic I'm working on now.

The up and down seems to be the duration of the high and low pulses of the pwm signal. My understanding is that the PWM signal should have a consistent total up and down time and that the difference between the two is the duty cycle. But that's most definitely not what's happening. So I'm really confused.

After reading the PDF posted, I'm thinking of doing an attachinterrupt to try a different way of getting the same type of data.

protomor:
If zip files aren't allowed, why is it an accepted upload? I would have much preferred to upload my original xlsx.

It's not that it's not allowed. It's just that downloading and opening one is digital Russian-Roulette. Same with an xlsx ['cuz of the Macro capability]. I know -- sux to be the OP :wink:

I did not calculate the timing but I suggest you look at the print statements. They are not instantaneous and could be messing you up.

I had done something like this but with a Microchip µP. If my memory serves me right I used one of the capture / compare timers. I set it up :

  1. set the edge to capture to rising;
  2. after the edge was captured I changed it to capture falling
  3. then rising again
    Now I have period and on time.