Fuel logic documentation

Talk and Tech about turbocharged 924/944/968 cars
User avatar
whalenlg
Posts: 441
Joined: Mon Jul 05, 2021 8:58 am
Has thanked: 8 times
Been thanked: 119 times
johnb wrote: Fri Aug 28, 2026 11:27 am
I can add something like that. Lately I have taken to adding the raw tables in an appendix at the end of individual articles, along with their raw locations (e.g. I did this in the acceleration guide I just posted last night).

The table numbers I use come directly from reverse engineering the code. This is how the maps actually referred to. The thing is, it's not possible to understand what the numbers in the maps mean without looking at the code where they're used, and the code invariably refers to them exactly the way I do (except I usually use decimal, while disassemblers usually show them as hex). For that reason, the full 2-byte location is never really relevant to me - it's always handled by the standard map lookup routine. But it's no problem to add this info if it's helpful.

I use various python scripts so when I want to know what "map 23" looks like, my script pulls it from the raw hex file and renders it as a markdown table or a graph, with unit translated as much as possible. It shows me the real address of the map too so it's easy to include that.

BTW, I did try adding a table of variables to that post where I tagged you, but I wasn't 100% sure if that was what you had asked for - let me know if that's useful and if so, I'll keep doing it.

I'm also working slowly on a master map of all variables and flags. I find the flags really hard to keep track of so this might be handy. It'll take a while because I'll only add to it as I go along but it will eventually be 100% complete.
Thanks - yes that recent one with the table of inputs and outputs is very helpful!

Having a full list of tables in 1 place helps when looking through the code and seeing a DPTR load. Eventually, I would like to build up a full symbol table to enable debugging with ASCII names instead of addresses of tables, variables and constants. Sounds like you are working to map that out and will be helpful to have a consistent dictionary.

See screenshots for my attempt to name things so far....this came from opendme and your pages, but still a work in progress...
Add Pictures/Files
Screenshot 2026-08-28 at 11.10.45 PM.png
Screenshot 2026-08-28 at 11.10.45 PM.png (216.95 KiB) Viewed 199 times
Screenshot 2026-08-28 at 11.11.25 PM.png
Screenshot 2026-08-28 at 11.11.25 PM.png (234.88 KiB) Viewed 199 times
Screenshot 2026-08-28 at 11.10.28 PM.png
Screenshot 2026-08-28 at 11.10.28 PM.png (173.77 KiB) Viewed 199 times
Screenshot 2026-08-28 at 11.09.22 PM.png
Screenshot 2026-08-28 at 11.09.22 PM.png (262.89 KiB) Viewed 199 times
1986 951 - Silicon Valley

#31

User avatar
johnb
Posts: 363
Joined: Thu Jul 08, 2021 5:57 am
Has thanked: 121 times
Been thanked: 93 times
I just noticed something new (to me). Previously I've written that the injectors always fire once per revolution, just after the second ignition event. That's mostly true but today when I was documenting the real time part of the fuel injection logic I noticed that there are 2 cases where the injectors fire twice per rev, after every ignition event:

1. while cranking
2. when there's low-rpm acceleration enrichment (the 4Ch value I explained in the acceleration enrichments doc a few days ago.)

The 4C value is still only used once, so this is about getting the enrichment in as soon as possible after the airflow is detected, rather than about increasing the enrichment beyond what was calculated.

I'll have to update that documentation with this info but I wanted to drop a quick update here in case you guys see this in simulations and wonder what's going on.

#32

User avatar
whalenlg
Posts: 441
Joined: Mon Jul 05, 2021 8:58 am
Has thanked: 8 times
Been thanked: 119 times
johnb wrote: Sun Aug 30, 2026 2:05 pm I just noticed something new (to me). Previously I've written that the injectors always fire once per revolution, just after the second ignition event. That's mostly true but today when I was documenting the real time part of the fuel injection logic I noticed that there are 2 cases where the injectors fire twice per rev, after every ignition event:

1. while cranking
2. when there's low-rpm acceleration enrichment (the 4Ch value I explained in the acceleration enrichments doc a few days ago.)

The 4C value is still only used once, so this is about getting the enrichment in as soon as possible after the airflow is detected, rather than about increasing the enrichment beyond what was calculated.

I'll have to update that documentation with this info but I wanted to drop a quick update here in case you guys see this in simulations and wonder what's going on.
Confirmed - I see that for the 1st 33.7 sec of my cold engine idle (5C temp at 740 rpm) when it injectors switch from 2x per cycle to 1x. 4c seems to stay at 00h for both cold and warm engine sims, though....
1986 951 - Silicon Valley

#33

User avatar
johnb
Posts: 363
Joined: Thu Jul 08, 2021 5:57 am
Has thanked: 121 times
Been thanked: 93 times
whalenlg wrote: Sun Aug 30, 2026 6:48 pm
johnb wrote: Sun Aug 30, 2026 2:05 pm I just noticed something new (to me). Previously I've written that the injectors always fire once per revolution, just after the second ignition event. That's mostly true but today when I was documenting the real time part of the fuel injection logic I noticed that there are 2 cases where the injectors fire twice per rev, after every ignition event:

1. while cranking
2. when there's low-rpm acceleration enrichment (the 4Ch value I explained in the acceleration enrichments doc a few days ago.)

The 4C value is still only used once, so this is about getting the enrichment in as soon as possible after the airflow is detected, rather than about increasing the enrichment beyond what was calculated.

I'll have to update that documentation with this info but I wanted to drop a quick update here in case you guys see this in simulations and wonder what's going on.
Confirmed - I see that for the 1st 33.7 sec of my cold engine idle (5C temp at 740 rpm) when it injectors switch from 2x per cycle to 1x. 4c seems to stay at 00h for both cold and warm engine sims, though....
The DME thinks the engine is still cranking. The cranking flag 23h.2 is set initially when rpm < 160 is detected, but only cleared once the rpm exceeds the relevant value from Map 3:

**1-Axis Map** (address `1447`, input variable `Engine Temperature (0x13)`)

| Engine Temperature (0x13) | Value |
|---|---|
| -34.61 | 18 |
| 2.24 | 20 |
| 45.66 | 20 |

For 5C that's 20*40 = 800rpm.

Once the cranking flag is clear you should see injection switch to once per rev. There's a lot of other things I'd expect to not be working right in that case though!

When the actual car is started, the idle stabilizer routine adds air to do a kind of brief flare with a target rpm higher than normal idle, depending on temperature:
map_53_startup_flare.png
map_53_startup_flare.png (29.74 KiB) Viewed 170 times
Should be around 960rpm for 5C.

I'm guessing that you're just moving the rpm up smoothly from cranking speed?

For 4C, are you sure you're hitting the criteria for it to have a value? It needs to be below 40C and have a vane delta of at least 16 between 10h and 53h. Also below 2840 rpm.

#34

User avatar
Tom
Site Admin
Posts: 9207
Joined: Fri Jun 25, 2021 2:04 pm
Location: Silicon Valley, CA
Has thanked: 961 times
Been thanked: 4160 times
Contact:
I'll run it on my DME next week, as I'll have my hands full with other things this week. That's a great discovery -- love it. I guess the benefit is to ensure at least one of the pulses is close to intake valve opening -- wonder if one could smooth out the idle by keeping that active at low rpms... May have to try that once I get my car back from the paint shop.

Perhaps others already knew this, but I discovered this weekend that the factory BIN has a UART serial stream with RPM, load, commanded fuel, AFM, coolant, IAT, battery voltage, and other RAM variables -- at 1E53. It requires a handshake to enable (which I disabled for testing) and seems quite hackable to spit out whatever data you might want (including variables, etc). I was able to connect to it this afternoon and pick up the data stream. I assume it was the port for the original Bosch diagnostic equipment, at is also includes an ability to adjust injector pulses and timing. :shifty:

#35

User avatar
johnb
Posts: 363
Joined: Thu Jul 08, 2021 5:57 am
Has thanked: 121 times
Been thanked: 93 times
Tom wrote: Sun Aug 30, 2026 8:10 pm I'll run it on my DME next week, as I'll have my hands full with other things this week. That's a great discovery -- love it. I guess the benefit is to ensure at least one of the pulses is close to intake valve opening -- wonder if one could smooth out the idle by keeping that active at low rpms... May have to try that once I get my car back from the paint shop.

Perhaps others already knew this, but I discovered this weekend that the factory BIN has a UART serial stream with RPM, load, commanded fuel, AFM, coolant, IAT, battery voltage, and other RAM variables -- at 1E53. It requires a handshake to enable (which I disabled for testing) and seems quite hackable to spit out whatever data you might want (including variables, etc). I was able to connect to it this afternoon and pick up the data stream. I assume it was the port for the original Bosch diagnostic equipment, at is also includes an ability to adjust injector pulses and timing. :shifty:
Yeah I think the KLR has something similar too. I've never looked at it but that sounds cool!

#36

User avatar
Tom
Site Admin
Posts: 9207
Joined: Fri Jun 25, 2021 2:04 pm
Location: Silicon Valley, CA
Has thanked: 961 times
Been thanked: 4160 times
Contact:
johnb wrote: Sun Aug 30, 2026 8:42 pm
Tom wrote: Sun Aug 30, 2026 8:10 pm I'll run it on my DME next week, as I'll have my hands full with other things this week. That's a great discovery -- love it. I guess the benefit is to ensure at least one of the pulses is close to intake valve opening -- wonder if one could smooth out the idle by keeping that active at low rpms... May have to try that once I get my car back from the paint shop.

Perhaps others already knew this, but I discovered this weekend that the factory BIN has a UART serial stream with RPM, load, commanded fuel, AFM, coolant, IAT, battery voltage, and other RAM variables -- at 1E53. It requires a handshake to enable (which I disabled for testing) and seems quite hackable to spit out whatever data you might want (including variables, etc). I was able to connect to it this afternoon and pick up the data stream. I assume it was the port for the original Bosch diagnostic equipment, at is also includes an ability to adjust injector pulses and timing. :shifty:
Yeah I think the KLR has something similar too. I've never looked at it but that sounds cool!
You don't say! I haven't built tools to disassemble the KLR yet, but that's intriguing!

#37

User avatar
whalenlg
Posts: 441
Joined: Mon Jul 05, 2021 8:58 am
Has thanked: 8 times
Been thanked: 119 times
johnb wrote: Sun Aug 30, 2026 7:01 pm
whalenlg wrote: Sun Aug 30, 2026 6:48 pm
johnb wrote: Sun Aug 30, 2026 2:05 pm I just noticed something new (to me). Previously I've written that the injectors always fire once per revolution, just after the second ignition event. That's mostly true but today when I was documenting the real time part of the fuel injection logic I noticed that there are 2 cases where the injectors fire twice per rev, after every ignition event:

1. while cranking
2. when there's low-rpm acceleration enrichment (the 4Ch value I explained in the acceleration enrichments doc a few days ago.)

The 4C value is still only used once, so this is about getting the enrichment in as soon as possible after the airflow is detected, rather than about increasing the enrichment beyond what was calculated.

I'll have to update that documentation with this info but I wanted to drop a quick update here in case you guys see this in simulations and wonder what's going on.
Confirmed - I see that for the 1st 33.7 sec of my cold engine idle (5C temp at 740 rpm) when it injectors switch from 2x per cycle to 1x. 4c seems to stay at 00h for both cold and warm engine sims, though....
The DME thinks the engine is still cranking. The cranking flag 23h.2 is set initially when rpm < 160 is detected, but only cleared once the rpm exceeds the relevant value from Map 3:

**1-Axis Map** (address `1447`, input variable `Engine Temperature (0x13)`)

| Engine Temperature (0x13) | Value |
|---|---|
| -34.61 | 18 |
| 2.24 | 20 |
| 45.66 | 20 |

For 5C that's 20*40 = 800rpm.

Once the cranking flag is clear you should see injection switch to once per rev. There's a lot of other things I'd expect to not be working right in that case though!

When the actual car is started, the idle stabilizer routine adds air to do a kind of brief flare with a target rpm higher than normal idle, depending on temperature:

map_53_startup_flare.png

Should be around 960rpm for 5C.

I'm guessing that you're just moving the rpm up smoothly from cranking speed?

For 4C, are you sure you're hitting the criteria for it to have a value? It needs to be below 40C and have a vane delta of at least 16 between 10h and 53h. Also below 2840 rpm.
The cranking flag does clear just before 33.7 sec. This is a cold idle test so the 53h-10h delta is pretty much 0. But I am seeing some other inputs that don't look right, so it could be something else that I need to lookinto.
1986 951 - Silicon Valley

#38

User avatar
johnb
Posts: 363
Joined: Thu Jul 08, 2021 5:57 am
Has thanked: 121 times
Been thanked: 93 times
whalenlg wrote: Mon Aug 31, 2026 10:00 am
johnb wrote: Sun Aug 30, 2026 7:01 pm
whalenlg wrote: Sun Aug 30, 2026 6:48 pm
Confirmed - I see that for the 1st 33.7 sec of my cold engine idle (5C temp at 740 rpm) when it injectors switch from 2x per cycle to 1x. 4c seems to stay at 00h for both cold and warm engine sims, though....
The DME thinks the engine is still cranking. The cranking flag 23h.2 is set initially when rpm < 160 is detected, but only cleared once the rpm exceeds the relevant value from Map 3:

**1-Axis Map** (address `1447`, input variable `Engine Temperature (0x13)`)

| Engine Temperature (0x13) | Value |
|---|---|
| -34.61 | 18 |
| 2.24 | 20 |
| 45.66 | 20 |

For 5C that's 20*40 = 800rpm.

Once the cranking flag is clear you should see injection switch to once per rev. There's a lot of other things I'd expect to not be working right in that case though!

When the actual car is started, the idle stabilizer routine adds air to do a kind of brief flare with a target rpm higher than normal idle, depending on temperature:

map_53_startup_flare.png

Should be around 960rpm for 5C.

I'm guessing that you're just moving the rpm up smoothly from cranking speed?

For 4C, are you sure you're hitting the criteria for it to have a value? It needs to be below 40C and have a vane delta of at least 16 between 10h and 53h. Also below 2840 rpm.
The cranking flag does clear just before 33.7 sec. This is a cold idle test so the 53h-10h delta is pretty much 0. But I am seeing some other inputs that don't look right, so it could be something else that I need to lookinto.
That's strange, it shouldn't have anything to do with time. Is anything else changing at the 33 second mark?

#39

User avatar
whalenlg
Posts: 441
Joined: Mon Jul 05, 2021 8:58 am
Has thanked: 8 times
Been thanked: 119 times
Tom wrote: Sun Aug 30, 2026 8:10 pm I'll run it on my DME next week, as I'll have my hands full with other things this week. That's a great discovery -- love it. I guess the benefit is to ensure at least one of the pulses is close to intake valve opening -- wonder if one could smooth out the idle by keeping that active at low rpms... May have to try that once I get my car back from the paint shop.

Perhaps others already knew this, but I discovered this weekend that the factory BIN has a UART serial stream with RPM, load, commanded fuel, AFM, coolant, IAT, battery voltage, and other RAM variables -- at 1E53. It requires a handshake to enable (which I disabled for testing) and seems quite hackable to spit out whatever data you might want (including variables, etc). I was able to connect to it this afternoon and pick up the data stream. I assume it was the port for the original Bosch diagnostic equipment, at is also includes an ability to adjust injector pulses and timing. :shifty:
I found these a few weeks back and put it in my dashboard....
Screenshot 2026-08-31 at 11.25.32 PM.png
Screenshot 2026-08-31 at 11.25.32 PM.png (234.8 KiB) Viewed 113 times
KLR has a failure status byte (33h) - there's an additional 1-1 code that occurs but isn't documented anywhere...I've seen it when there are back to back knocks or when one of the power supplies was below tolerance. There's no UART on the 8048, so these codes must be blipped out to LEDs via firmware.
Screenshot 2026-08-31 at 11.25.32 PM.png
Screenshot 2026-08-31 at 11.25.32 PM.png (234.8 KiB) Viewed 113 times
Add Pictures/Files
Screenshot 2026-08-31 at 11.29.37 PM.png
Screenshot 2026-08-31 at 11.29.37 PM.png (107.2 KiB) Viewed 113 times
1986 951 - Silicon Valley

#40

Post Reply