View unanswered posts | View active topics It is currently Thu Nov 23, 2017 1:12 am



Reply to topic  [ 9 posts ] 
PropPower - Crank Angle Based Event Scheduling Etc 
Author Message
LQFP112 - Up with the play

Joined: Thu Apr 10, 2008 5:51 pm
Posts: 205
Hi guys,

I am undertaking a project that may be of some interest with respect to engine position tracking and crank-angle-based event scheduling. This is pretty much a pipe dream so far with respect to implementing anything to actually control an engine.

Hardware and Capabilities

Recently I have been playing around a bit with the Propeller Chip, which in a nutshell is an 8-core (Cogs) 80mHz microprocessor with 32 all-purposed I/O pins, 2 multi-purpose timers per core, hardware input pattern matching, and no traditional interrupts.

Overview and Strategy

I have started into writing a firmware package for decoding engine position from toothed wheels, and driving 24 ignition/injection outputs (mixed any way desired) in a true sequential manner, using crank angle scheduling.

Core Functions and Interaction

I have separated tooth decoding and event scheduling into completely different layers. Although the PropChip lacks interrupts, each core has the ability to wait in a suspended state until a masked set of input pins match a predefined pattern, and resume full operation after only 6 clock cycles. This necessitates any tooth edge detection is contained in a Cog separate from code that needs to run continuously (non-blocked), as the edge-detection Cog must be suspended while it waits for the next tooth (when timestamps are critical).

Cog Architecture

(0) Main Loop - This starts at boot, and manages the state of following Cogs
(1) Event Scheduler - This maintains a simulated crank position and is periodically updated by the tooth decoders
(2) Crank Decoder (modular) - This waits for crank teeth and calculates crank position and speed, used to update the Event Scheduler
(3) Cam Decoder (optional) - This waits for cam teeth and calculates cam phase, engine phase, crank speed and position etc if supported
(4) to (7) Future: comms, math, datalogging, etc

Crank Decoder

I have actually written some code for a generic missing-tooth crank wheel decoder. There are a couple of strategies I am trying, one of which is maintaining an array that stores the clocks-per-revolution for each individual tooth. There is a method to this madness: by storing the time for one tooth to make a revolution, the crank speed can be calculated based on that tooth only, whenever that tooth is captured. This gives the effect of updating rpm at every tooth edge (fast response) and making the time period an entire revolution rather than the time since last tooth (less jitter).

Generic Crank Decoder Algorithm

I will provide some pseudocode that describes how my system decodes the wheel and passes the position to common memory. This assumes that we are triggering on the falling edge. By passing a timestamp between the Cogs it should be trivial to eliminate timing issues stemming from access delays.

In my code I have an array with three entries for each present tooth: tooth position, tooth capture time, and tooth period. The tooth counter is used to directly index the array location.

Code:
Init:
Initialize Variables and Arrays to Zero
Set tooth counter to last tooth (total - missing)
Set Synch = False

Loop:
 Wait for pin to go high
 Wait for pin to go low
 Store time
 Calculate time since previous tooth
 Are we on the last tooth?
  Yes:
   Has expected time elapsed for missing teeth? [ ((missing +0.5)*prev) to ((missing + 1.5)*prev) ]
    Yes:
     Set tooth counter to first tooth (0).
     Update period and time for this tooth in local array and set Synch = True.
    No:
     Go to Init
  No:
   Has expected time elapsed since previous tooth? [ (0.5*prev) to (1.5*prev)]
    Yes:
     Increment tooth counter (+1)
     Update period and time for this tooth in local array.
    No:
     Go to Init
 Calculate speed and position for this tooth
 Write Synch, Position, Speed, and Time to common memory
Go to Loop


What's unconventional?

Well, other than what I have babbled on about above, a key difference between my decoder code and say Megasquirt's decoder is that in my code the first tooth after the gap is Tooth 0, which I find to be less confusing. It also makes indexing the tooth data array much easier.

The above code actually handles wheels without missing teeth as well, although a second trigger is needed to set the zero tooth properly. The way it is is would set the second tooth it sees on resynch or cranking as tooth zero. An exception handler could block it from synching until a second trigger established the initial position.

What's next?

I have to write code for the Event Scheduling cog, which will be a free-running counter that indexes crank position in divisions of 1024/revolution, with a variable loop period corresponding with calculated engine speed. This gives me an angular resolution of about 1/3 of a degree. Even at 19,500 I will have around 240 clock cycles to work with for every loop iteration @ 1024 divisions/rev.

Because all Cogs can access all pins at any time, I am going to use a spare pin as a "synchronized" flag between cogs. When this flag is false, all charging events will be disabled but all discharging events will be enabled until all active outputs have been discharged and the wheel position simulator stops. It will double as a visual indicator of wheel synch by hooking an LED to that pin.

In each loop iteration, the crank angle will be incremented by one division, common memory polled for an update from the wheel decoder, adjustment of the loop period and crank position done if an update is present, corresponding output states changed, and next output changes decided. The only additional information that should need to be passed to this Cog is Ignition Advance (angular) and Injector Pulse Width (Angular), both of which can be calculated by the main loop or pushed via comms from another processor (my plan).

_________________
Keith MacDonald
Control Engineering (Systems) Technologist


Tue Dec 16, 2008 6:18 am
Profile
Moderator
User avatar

Joined: Tue Jan 15, 2008 2:31 pm
Posts: 14871
Location: Home sweet home!
thebigmacd wrote:
There is a method to this madness: by storing the time for one tooth to make a revolution, the crank speed can be calculated based on that tooth only, whenever that tooth is captured. This gives the effect of updating rpm at every tooth edge (fast response) and making the time period an entire revolution rather than the time since last tooth (less jitter).

That isn't actually a fast response, it is 360 out of phase with reality. An admirable plan though regardless :-)

Quote:
What's unconventional?
Well, other than what I have babbled on about above, a key difference between my decoder code and say Megasquirt's decoder is that in my code the first tooth after the gap is Tooth 0, which I find to be less confusing. It also makes indexing the tooth data array much easier.

Would you really call it unconventional just because ms doesn't do it? I wouldn't. Makes perfect sense to me and mines the same.

Cool project :-)

Fred.

_________________
DIYEFI.org - where Open Source means Open Source, and Free means Freedom
FreeEMS.org - the open source engine management system
FreeEMS dev diary and its comments thread and my turbo truck!
n00bs, do NOT PM or email tech questions! Use the forum!
The ever growing list of FreeEMS success stories!


Tue Dec 16, 2008 7:19 am
Profile WWW
LQFP144 - On Top Of The Game
User avatar

Joined: Sat Feb 23, 2008 8:58 pm
Posts: 387
That's interesting and I actually wanted to do something along the same lines. However, reading the propeller doc I saw that it takes well over 1 second to boot up which seems excessive and might make starting the engine awkward. It also seems to be slow to perform some computations and is designed to use an interpreted language (even though you can use assembly). And I don't think it comes in an automotive rated temperature.

These are all impressions I got from reading the specs and not based on any real experience with the chip. I'd be interested to hear if I'm way off base with this because it completely stopped me from investigating this more. It's an interesting chip but it is definitely targeted at a very different set of applications.

Jean


Tue Dec 16, 2008 8:30 am
Profile WWW
LQFP112 - Up with the play

Joined: Thu Apr 10, 2008 5:51 pm
Posts: 205
There are ways to get around the boot time:
(a) the chip can be left powered on
(b) the cores can be shut down and restarted with minimal delay

As far as ratings:
Quote:
As for industry-standard tests, we recently hired a company called Nano Measurements to perform their own environmental and ESD testing on the Propeller. Specifically, the following tests were conducted:

PPOT - Pressure pot, autoclave: 121ºC, 100% RH, 15 PSIG, 336 hours
TMCL - Tempurature cycle, air, standard ramp: -65ºC to 150ºC, 500 cycles
PREC - Preconditioning (simulates soldering process): 30ºC, 60% RH, 192 hours
HTSL - High tempurature storage life: 150ºC, 1000 hours
ESD HBM - ESD human body model: All pins tested up to +/-8kV

Here are the results:

PPOT - 3 lots of 77 devices (PDIP, LQFP, QFN): 0 failures (a lot of 77 ensures 3-sigma-quality with one failure)
TMCL - 2 lots of 77 devices and 1 lot of 76: 0 failures
PREC - 3 lots of 77 devices: 0 failures
HTSL - 1 lot of 230 devices (near-even mix of PDIP, LQFP, QFN): 0 failures
ESD HBM - 3 devices each of PDIP, LQFP, QFN: all I/O pins survived +/-8kV (limit of tester) with VSS and VDD grounded, VSS-to-VDD zap failed at +/-3kV or greater

So essentially it is a -65 to +150 rated chip.

I got this chip to use to drive a video gauge cluster, as it does video very well. But now that I see what it can do, I am impressed with its power. A lot of its "inherent limitations" are only limitations to people that don't want to innovate/think.

It is fairly low on memory, yes (32k). Since the chip costs all of $12.50, if I take this far enough to actually run an engine it will be split into two chips, with the second chip doing all of the low-speed I/O, mapping, and passing advance and pulsewidth values through comms. I need to do this if I want to retain the pinout capability of combined 12 cyl COP and sequential injection.

_________________
Keith MacDonald
Control Engineering (Systems) Technologist


Tue Dec 16, 2008 1:14 pm
Profile
LQFP144 - On Top Of The Game
User avatar

Joined: Sat Feb 23, 2008 8:58 pm
Posts: 387
Are those environmental or operational conditions? And have constant power is a solution but is a bit inconvenient for what I had in mind. However, it might be worth doing. One thing should be added is that it seems the chip will happily run at 100MHz instead of the rated 80MHz which is a significant increase.

And you should have enough pins to do the 12 cylinder COP/sequential injection. There are 28 general I/Os plus 4 shared I/Os. If you use 24 for ignition and injection, 2 for crank and cam position sensors, that leaves you 2 GPIOs and 4 shared I/Os. I was thinking that a soft SPI connection would be a good choice to communicate with an external CPU so you need 3 or 4 pins. You can use the 2 remaining GPIOs and reuse the 2 SCI pins which become GPIOs after boot up. Of course that requires fitting everything in 32K but this is only a limitation for those who don't want to innovate/think :)

Also, you probably want to have injection duration and spark dwell information given in time units together with the angular timing. This will give a much tighter precision on the injection and in the case of injection, duration precision is more important than timing. And it will allow more precision during fast engine speed transients and would even allow the chip to continue to do it's job if the communication with the CPU is briefly interrupted or slowed down for whatever reason.

Jean


Tue Dec 16, 2008 5:42 pm
Profile WWW
LQFP112 - Up with the play

Joined: Thu Apr 10, 2008 5:51 pm
Posts: 205
I'm not sure if the certification testing was done with the chips loaded, but I know their in-house testing was done with all outputs switching at 160 MHz (the internal timers can run faster than the main clock).

I am planning on using the 2 GPIO pins as Tach Out and Synch Flag. The standard serial pins (which by the way can pretty much be used for anything if there is an EEPROM hooked up as standard) will switch from standard serial signaling to some sort of standard chip-chip protocol (maybe even CAN) as soon as boot is finished.

My intent with the injection and ignition channels is to have one transition fixed to crank angle, and the other transition based as a time. In other words, dwell would begin at a calculated time, and the ignition event would happen at a precise crank angle. Injection would begin at a specific crank angle (immediately after intake valve closes) and end after a very precise amount of time.

Another option I just thought of is changing the resolution of the crank angle divisions as rpm goes up, so at low rpm there are say 4096 divisions per revolution and as speed goes up we keep dividing the number of divisions by two so by the time we hit 10,000 there are 2048 divisions, and 1024 divisions at 20,000 rpm. This will keep the loop time in a smaller range, while providing better granularity at low rpm and enough time for calculation between divisions at higher rpm.

Trying to do it with hardware timers to get it down to a few clocks cycles is a bit futile when trying to schedule overlapping rise- and fall-events for 24 pins.

In the end, it's going to be a proof of concept to test the timing accuracy of passing data between Cogs and doing everything in angle-space rather than time-space. My wife has ordered me the Professional Development Board for Christmas so once I get that I will use my existing gauge cluster board I made to generate the 60-2 wheel pattern I am going to test first, and make a nice LED fanout on the PDB.

We'll see how it goes. Perhaps it won't be capable of pulling it off, but hopefully it will. From what I have read it seems like once people understand the Propeller paradigm, it ends up being a very powerful tool for them. Almost as if the 8 cores without interrupts work like 8 traditional interrupt-capable chips in terms of combined ability. There are some nice things like hardware Sine and Log tables that make trig and multiplication/division a lot easier and faster than would first meet the eye as well.

_________________
Keith MacDonald
Control Engineering (Systems) Technologist


Wed Dec 17, 2008 12:41 am
Profile
LQFP112 - Up with the play

Joined: Thu Apr 10, 2008 5:51 pm
Posts: 205
I just realized that I had made this thread a while ago...totally forgot!

Project is now named SpinDrive. The new thread is here: viewtopic.php?f=4&t=832

Using two chips, so supporting 12inj/12ign like Jean suggested is a no-brainer!

_________________
Keith MacDonald
Control Engineering (Systems) Technologist


Sat May 01, 2010 11:25 pm
Profile
TO92 - Vaguely active

Joined: Sun Apr 01, 2012 4:03 pm
Posts: 3
Location: Finland
This is a interesting project. I personally think that the most important thing that ecu does is ignition timing. And I think that most aftermarket ECUs suck at this.
So that leaves only one option: dedicated processor or an FPGA. The only downside of a FPGA is the boot time that is going to be probably around 3-5 seconds minimum (just think how long it takes your flatscreen tv to boot).

As i work in a company that does FPGA stuff I have thought about how to actually implement the decoder, and finally i have it in my head how it should be done... If only i had the time to actually do it! :D
My version would (will?) be based on a 32-64bit timer @ 100-500Mhz with a 16bit tooth to tooth resolution. This would be impossible with a low to medium-end micro but super easy on a FPGA. And no interrupts can f*** the timing as it is calculated in dedicated logic.


Fri Nov 29, 2013 4:34 pm
Profile
Moderator
User avatar

Joined: Tue Jan 15, 2008 2:31 pm
Posts: 14871
Location: Home sweet home!
I agree almost completely with this analysis, however, this is not the only way to kill the cat :-)

_________________
DIYEFI.org - where Open Source means Open Source, and Free means Freedom
FreeEMS.org - the open source engine management system
FreeEMS dev diary and its comments thread and my turbo truck!
n00bs, do NOT PM or email tech questions! Use the forum!
The ever growing list of FreeEMS success stories!


Tue Dec 03, 2013 7:53 pm
Profile WWW
Display posts from previous:  Sort by  
Reply to topic   [ 9 posts ] 

Who is online

Users browsing this forum: Bing [Bot] and 1 guest


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
cron
Powered by phpBB® Forum Software © phpBB Group
Designed by ST Software for PTF. ColorizeIt.