- Mon Oct 16, 2017 8:13 pm
#21671
This is what I had in mind. It is a first pass to think about the theory. I did not compile it.
Basically, SecondaryTrig looks for the Cam1 single missing pulse rising edge and declares this a "cam edge".
Then Primary Trig looks for the "cam edge" and the first 2 crank missing teeth and starts counting crank edges.
It counts to 36 and rolls over to 1.
void triggerSetup_Vq35deTooth()
{
triggerToothAngle = 360 / configPage2.triggerTeeth; //The number of degrees that passes from tooth to tooth
if(configPage2.TrigSpeed) { triggerToothAngle = 720 / configPage2.triggerTeeth; } //Account for cam speed missing tooth
triggerActualTeeth = configPage2.triggerTeeth - configPage2.triggerMissingTeeth; //The number of physical teeth on the wheel. Doing this here saves us a calculation each time in the interrupt
triggerFilterTime = (int)(1000000 / (MAX_RPM / 60 * configPage2.triggerTeeth)); //Trigger filter time is the shortest possible time (in uS) that there can be between crank teeth (ie at max RPM). Any pulses that occur faster than this time will be disgarded as noise
secondDerivEnabled = false;
decoderIsSequential = false;
checkSyncToothCount = (configPage2.triggerTeeth) >> 1; //50% of the total teeth.
MAX_STALL_TIME = (3333UL * triggerToothAngle * (configPage2.triggerMissingTeeth + 1)); //Minimum 50rpm. (3333uS is the time per degree at 50rpm)
curStartOfCam1Bank = false;
curStartOfCam1BankLast = false;
}
void triggerPri_Vq35deTooth()
{
curTime = micros(); // get time of falling edge
curGap = curTime - toothLastToothTime; // Time between this falling edge and last falling edge
if ( curGap < triggerFilterTime ) { return; } //Debounce check. Pulses should never be less than triggerFilterTime, so if they are it means a false trigger. (A 36-1 wheel at 8000pm will have triggers approx. every 200uS)
toothCurrentCount++; //Increment the tooth counter
addToothLogEntry(curGap);
//Begin the missing tooth detection
targetGap = ((toothLastToothTime - toothLastMinusOneToothTime)) * 2;
//More than 1 tooth missing, Multiply by 2 (Checks for a gap 2x greater than the last one).
if ( curGap > targetGap ) { toothCurrentCount += 2 }; //Increment the tooth counter for the 2 missing teeth
// curGap > targetGap -> this means we have found the tooth AFTER the missing teeth
// If switching Cam cycle (cyl banks), and found missing tooth or counted entire trig wheel -> then reset the toothCurrentCount
if ( (curStartOfCam1Bank == true && curStartOfCam1BankLast == false) && ((curGap > targetGap) || (toothCurrentCount > triggerActualTeeth)) )
{
if(toothCurrentCount < (triggerActualTeeth) && currentStatus.hasSync) { currentStatus.hasSync = false; return; } //This occurs when we're at tooth #1, but haven't seen all the other teeth. This indicates a signal issue so we flag lost sync so this will attempt to resync on the next revolution.
toothCurrentCount = 1;
revolutionOne = !revolutionOne; //Flip sequential revolution tracker
toothOneMinusOneTime = toothOneTime;
toothOneTime = curTime;
currentStatus.hasSync = true;
currentStatus.startRevolutions++; //Counter
triggerFilterTime = 0; //This is used to prevent a condition where serious intermitent signals (Eg someone furiously plugging the sensor wire in and out) can leave the filter in an unrecoverable state
}
else
{
//Filter can only be recalc'd for the regular teeth, not the missing one.
setFilter(curGap);
}
toothLastMinusOneToothTime = toothLastToothTime;
toothLastToothTime = curTime;
curStartOfCam1BankLast = curStartOfCam1Bank;
}
// Use rising edge in order to set the StartOfCam1Bank signal BEFORE the 2 missing crank teeth of the 12-2 sequence for cyl 1 (falling *MAY* be too late-race condition)
void triggerSec_Vq35deTooth()
{
curTime = micros(); // get time of edge
curGap = curTime - toothLastToothTime; // Time between this edge and last edge
if ( curGap < triggerFilterTime * 2 ) { return; } //Debounce check. Pulses should never be less than triggerFilterTime, so if they are it means a false trigger.
addToothLogEntry(curGap);
//Begin the missing tooth detection (detect only the single missing tooth)
targetGap = (((toothLastToothTime - toothLastMinusOneToothTime)) * 3) >> 1; // 1 tooth missing, mult by 1.5
targetGapMax = (((toothLastToothTime - toothLastMinusOneToothTime)) * 10) >> 2; // 1 tooth missing, mult by 2.5
if ( (curGap > targetGap) && (curGap < targetGapMax) )
{
// found 1 tooth gap -> send out a pulse so the crank function can reset the counter
curStartOfCam1Bank = true;
}
else
{
if ( curGap < targetGap ) {setFilter(curGap);} //Filter can only be recalc'd for the regular teeth, not the missing one.
curStartOfCam1Bank = false;
}
toothLastMinusOneToothTime = toothLastToothTime;
toothLastToothTime = curTime;
}