Page 4 of 6
Re: developing a spark cut launch control solution
Posted: Sun Aug 30, 2020 1:01 pm
by NSFW
Nice work, I like where this is going.
If I remember right, TableLookupUnsigned puts the value from the table into the d0 parameter... For the spark-cut limiter, it might be easiest to patch the target address of the JSR that calls TableLookupUnsigned for the dwell table, and have it jump to new code that checks conditions and either sets d0 to zero or just passes through to the table lookup code. This is an approach that I had good luck with in my Subaru. The new code might look something like:
Code: Select all
if ((vehicle speed < 5) && (clutch pressed) && (Throttle > 90%) && (RPM > LaunchControlRpm))
{
d0 = 0
RTS
}
if ((vehicle speed > 10) && (clutch pressed) && (Throttle > 90%) && (RPM > FlatFootShiftRpm))
{
d0 = 0
RTS
}
JSR TableLookupUnsigned
RTS
IIRC that's the logic I used in my Subaru, which has a manual transmission. I never really thought about automatics but I guess you could check for the brake pedal in the first 'if' and maybe just get rid of the second 'if'.
Re: developing a spark cut launch control solution
Posted: Mon Aug 31, 2020 5:20 am
by vwnut8392
NSFW wrote:Nice work, I like where this is going.
If I remember right, TableLookupUnsigned puts the value from the table into the d0 parameter... For the spark-cut limiter, it might be easiest to patch the target address of the JSR that calls TableLookupUnsigned for the dwell table, and have it jump to new code that checks conditions and either sets d0 to zero or just passes through to the table lookup code. This is an approach that I had good luck with in my Subaru. The new code might look something like:
Code: Select all
if ((vehicle speed < 5) && (clutch pressed) && (Throttle > 90%) && (RPM > LaunchControlRpm))
{
d0 = 0
RTS
}
if ((vehicle speed > 10) && (clutch pressed) && (Throttle > 90%) && (RPM > FlatFootShiftRpm))
{
d0 = 0
RTS
}
JSR TableLookupUnsigned
RTS
IIRC that's the logic I used in my Subaru, which has a manual transmission. I never really thought about automatics but I guess you could check for the brake pedal in the first 'if' and maybe just get rid of the second 'if'.
i borrowed the basic logic from the VW/audi ME7 ECU's since it works so similar. yeah you could check brake pedal on as i think these ECU's have an input for that based on the cruise control?i think in auto you could use brake pedal intput, TPS % and wheel speed to activate/deactivate like this, if below 3-4mph, TPS is pressed down above 90% and brake is pressed than launch can activate. once its time to leave the roll out speed and release of the brake pedal will disable it and it cannot reactivate till the vehicle is sitting still. the same principal could be applied to a manual but using clutch switch input instead.
as for the hard limiter you could just add it to the beginning of the routine before everything else thats just a simple if at or above X RPM jump to forcing dwell to 0. this would just keep everything in 1 routine.
what i would want to figure out next is where the final ignition angle is placed into ram and make more code there to add timing retard to it. as long as there is open RAM that when in the launch part of the original routine is entered it sets a flag bit in RAM that the retard code is watching for to get set and that enables the retard to happen. i guess this could even work backwards too with the retard code setting a bit when retard happens and that is part of the routine to enter launch control when the bit is set that way you would get retard first than spark cut.
Re: developing a spark cut launch control solution
Posted: Sat Sep 05, 2020 2:13 pm
by NSFW
There's a TableLookup call to get an ignition timing compensation based on ECT or IAT. If you hook that, you could have it return whatever timing offset you want when launch control is active.
I've heard of nitrous folks grounding an IAT sensor lead to make the PCM think IAT is -40F or so - then they tweak the bottom of the compensation table to get whatever value they need. This would be pretty similar, but done in software instead of hardware.
Re: developing a spark cut launch control solution
Posted: Wed Sep 09, 2020 1:10 am
by turbo_v6
Ok, so I'm working on coding up a quick test to verify I can made something work. Going to try and test with just the brake pedal and engine rpm for the only conditions.
In the end I would really like to have a flag in RAM so that I know if launch control is active or not. That way I can add hysteresis into the logic. I'll see how smooth the LC limiter is without the hysteresis on the above test, but I think it would be nice to have.
Also that would allow for other functions to know when LC is active. My only issue is finding a section of RAM that is not being used. If anyone has tips on finding some unused RAM locations please let me know.
Re: developing a spark cut launch control solution
Posted: Wed Sep 09, 2020 2:38 pm
by turbo_v6
It works!
Here is a screen shot of some log data that I got from PCMLogger with my bench setup (you can tell this from how noisy the engine rpm data is).

- chart.png (31.58 KiB) Viewed 6506 times
Ignition dwell going to zero corresponded perfectly with an LED that I have connected to the coil output.
Re: developing a spark cut launch control solution
Posted: Fri Sep 18, 2020 6:31 am
by turbo_v6
Ok, so I'm looking for some feedback before I go about implementing this into assembly.
I have some mock code to get feedback on the logic. Please be kind as I have almost zero formal programming experience (mostly self taught).
In the location I am hooking into D6 contains the dwell, so that's why my logic clears D6 and not D0.
I added a few features into this:
Spark Cut Rev Limiter
Spark Cut Launch Control
Spark Cut Flat Foot Shift
Timed Spark Retard After Launch (This will need a bit more work as I'll have to figure out how to use the TBLx instruction a little more before I'm confident)
Code: Select all
//Hook from dwell lookup
JSR table_lookup
//Spark Cut Rev Limit
if(engine_speed > engine_speed_max){
CLR d6
RTS
}
//Launch control active logic
if(launch_control_status == 1){
//Test for launch control exit & enable timed launch retard
if(vehicle_speed > launch_max_vehicle_speed or throttle_position < launch_min_tps or brake_pedal != 1 or or clutch_pedal != 1){
launch_control_status = 0
if(vehicle_speed < launch_max_vehicle_speed and throttle_position > launch_min_tps){
timing_retard_status = 1
timing_retard_cycle = cycle_count
}
RTS
}
if(engine_speed > launch_control_engine_speed){
CLR d6
}
RTS
}
//Test to activate launch control
if(vehicle_speed < launch_max_vehicle_speed and throttle_position > launch_min_tps and brake_pedal == 1 and clutch_pedal == 1){
launch_control_status = 1
}
//Test to activate Flat Foot Shift Cut
if(vehicle_speed > ffs_min_vehicle_speed and throttle_position > ffs_min_tps and clutch_pedal == 1 and engine_speed > ffs_engine_speed){
CLR d6
}
RTS
Need to hook into this somewhere to modify the ignition timing based on time.
Code: Select all
//Hook for timing modification TODO
JSR table_lookup
//Launch retard timing
if(timing_retard_status == 1){
//Stop timing retard logic if throttle lifted or timeout
if(throttle_position < launch_min_tps or launch_time > launch_control_timing_retard_max_time){
timing_retard_status = 0
RTS
}
launch_time = cycle_count - timing_retard_cycle
table_lookup_timing_retard_vs_time
}
RTS
Re: developing a spark cut launch control solution
Posted: Tue Sep 22, 2020 9:20 am
by vwnut8392
bubba2533 wrote:Ok, so I'm looking for some feedback before I go about implementing this into assembly.
I have some mock code to get feedback on the logic. Please be kind as I have almost zero formal programming experience (mostly self taught).
In the location I am hooking into D6 contains the dwell, so that's why my logic clears D6 and not D0.
I added a few features into this:
Spark Cut Rev Limiter
Spark Cut Launch Control
Spark Cut Flat Foot Shift
Timed Spark Retard After Launch (This will need a bit more work as I'll have to figure out how to use the TBLx instruction a little more before I'm confident)
Code: Select all
//Hook from dwell lookup
JSR table_lookup
//Spark Cut Rev Limit
if(engine_speed > engine_speed_max){
CLR d6
RTS
}
//Launch control active logic
if(launch_control_status == 1){
//Test for launch control exit & enable timed launch retard
if(vehicle_speed > launch_max_vehicle_speed or throttle_position < launch_min_tps or brake_pedal != 1 or or clutch_pedal != 1){
launch_control_status = 0
if(vehicle_speed < launch_max_vehicle_speed and throttle_position > launch_min_tps){
timing_retard_status = 1
timing_retard_cycle = cycle_count
}
RTS
}
if(engine_speed > launch_control_engine_speed){
CLR d6
}
RTS
}
//Test to activate launch control
if(vehicle_speed < launch_max_vehicle_speed and throttle_position > launch_min_tps and brake_pedal == 1 and clutch_pedal == 1){
launch_control_status = 1
}
//Test to activate Flat Foot Shift Cut
if(vehicle_speed > ffs_min_vehicle_speed and throttle_position > ffs_min_tps and clutch_pedal == 1 and engine_speed > ffs_engine_speed){
CLR d6
}
RTS
Need to hook into this somewhere to modify the ignition timing based on time.
Code: Select all
//Hook for timing modification TODO
JSR table_lookup
//Launch retard timing
if(timing_retard_status == 1){
//Stop timing retard logic if throttle lifted or timeout
if(throttle_position < launch_min_tps or launch_time > launch_control_timing_retard_max_time){
timing_retard_status = 0
RTS
}
launch_time = cycle_count - timing_retard_cycle
table_lookup_timing_retard_vs_time
}
RTS
well my issue here is that i dont know C code like your using to follow you. i've already started to learn the actual assembler code. only way to know if it works is to try it what you made.
Re: developing a spark cut launch control solution
Posted: Tue Sep 22, 2020 9:27 am
by vwnut8392
This is the code that i wrote. unsure if it works though. in assembler it works though.
Code: Select all
ROM:0001FE00 ; =============== S U B R O U T I N E =======================================
ROM:0001FE00
ROM:0001FE00
ROM:0001FE00 [color=#0000BF]Launch_Control: [/color] ; CODE XREF: Coil_Dwell_Routine+2C↓p
ROM:0001FE00 1638 9F34 move.b ($FF9F34).w,d3 ; Load wheel speed from RAM
ROM:0001FE04 3839 0001 EB00 move.w (word_1EB00).l,d4 ; Read wheel speed constant
ROM:0001FE0A B644 cmp.w d4,d3 ; Compare RAM and constant
ROM:0001FE0C 6C12 bge.s loc_1FE20 ; Branch if Greater or Equal
ROM:0001FE0E 1638 A4C4 move.b ($FFA4C4).w,d3 ; Read engine RPM from RAM
ROM:0001FE12 3839 0001 EB02 move.w (word_1EB02).l,d4 ; Read launch control RPM constant
ROM:0001FE18 B644 cmp.w d4,d3 ; Compare RAM and constant
ROM:0001FE1A 6504 bcs.s loc_1FE20 ; Branch if Carry Set
ROM:0001FE1C 4238 AEBA clr.b ($FFAEBA).w ; Force Coil Dwell to 0????
ROM:0001FE20 This is the stock code i had to
ROM:0001FE20 remove to make the jump out for
ROM:0001FE20 this code.
ROM:0001FE20 You must always try and keep
ROM:0001FE20 stock logic when doing this.
ROM:0001FE20
ROM:0001FE20 loc_1FE20: ; CODE XREF: Launch_Control+C↑j
ROM:0001FE20 ; Launch_Control+1A↑j
ROM:0001FE20 3E3C 1A00 move.w #$1A00,d7 ; Move Data from Source to Destination
ROM:0001FE24 BE41 cmp.w d1,d7 ; Compare
ROM:0001FE26 4E75 rts ; Return from Subroutine
ROM:0001FE26 ; End of function Launch_Control
Code: Select all
0001FE00 16 38 9F 34 38 39 00 01 EB 00 B6 44 6C 12 16 38
0001FE10 A4 C4 38 39 00 01 EB 02 B6 44 65 04 42 38 AE BA
0001FE20 3E 3C 1A 00 BE 41 4E 75 FF FF FF FF FF FF FF FF
Re: developing a spark cut launch control solution
Posted: Wed Sep 23, 2020 10:54 am
by turbo_v6
Well I've tried my best to get this timed launch retard to function, but I just can't seem to get it to work.
If someone could go over this ASM logic.
I've attached a PCMLogger CSV Log of me testing it on the bench.
At ~40 secs the LC goes active (FF819E)
At ~57 secs the LC goes inactive and the timed retard goes active (FF819E) and the Timed Retard Cycle (FF81A0) is updated.
The issue is that after this point I expect that the cycle delta (FF81A4) should be giving an output, but it's not. I'm also not able to deactivate the timed retard via the TPS which is in the second function.
Function 1 Jump Patched in at ROM:0003B912
Code: Select all
ROM:0008A900
ROM:0008A900 ; =============== S U B R O U T I N E =======================================
ROM:0008A900
ROM:0008A900
ROM:0008A900 sub_8A900: ; CODE XREF: sub_3B82A+E8p
ROM:0008A900 jsr sub_2696E
ROM:0008A906 tst.b ($FFFFB370).w //DBW Enable
ROM:0008A90A beq.s loc_8A912
ROM:0008A90C move.w ($FFFFA598).w,d4 //DBW TPS
ROM:0008A910 bra.s loc_8A916
ROM:0008A912 ; ---------------------------------------------------------------------------
ROM:0008A912
ROM:0008A912 loc_8A912: ; CODE XREF: sub_8A900+Aj
ROM:0008A912 move.w ($FFFFAB64).w,d4 //NON-DBW TPS
ROM:0008A916
ROM:0008A916 loc_8A916: ; CODE XREF: sub_8A900+10j
ROM:0008A916 move.w ($FFFFA562).w,d3 //Engine Speed
ROM:0008A91A cmp.w (word_8AB00).l,d3 // LC Engine Speed
ROM:0008A920 bcc.w loc_8A9CC
ROM:0008A924 tst.b ($FFFF819E).w // LC Status
ROM:0008A928 beq.s loc_8A97E
ROM:0008A92A tst.b ($FFFFAF3A).w // Brake Pedal
ROM:0008A92E beq.s loc_8A94A
ROM:0008A930 tst.b ($FFFFAF3A).w // Brake Pedal (Need to confirm clutch ram address before changing this)
ROM:0008A934 beq.s loc_8A94A
ROM:0008A936 move.w ($FFFFAEBC).w,d3 // Vehicle Speed Filtered
ROM:0008A93A cmp.w (word_8AB02).l,d3
ROM:0008A940 bhi.s loc_8A94A
ROM:0008A942 cmp.w (word_8AB04).l,d4
ROM:0008A948 bhi.s loc_8A970
ROM:0008A94A
ROM:0008A94A loc_8A94A: ; CODE XREF: sub_8A900+2Ej
ROM:0008A94A ; sub_8A900+34j ...
ROM:0008A94A clr.b ($FFFF819E).w // Disable LC if a parameter is no longer satisfied
ROM:0008A94E move.w ($FFFFAEBC).w,d3 // Vehicle Speed
ROM:0008A952 cmp.w (word_8AB02).l,d3
ROM:0008A958 bhi.s locret_8A9CE
ROM:0008A95A cmp.w (word_8AB04).l,d4
ROM:0008A960 bcs.s locret_8A9CE
ROM:0008A962 move.b #1,($FFFF819F).w // Enable timed spark retard
ROM:0008A968 move.w ($FFFFB544).w,($FFFF81A0).w // Move cycle counter to a local copy when timed retard is enabled
ROM:0008A96E bra.s locret_8A9CE
ROM:0008A970 ; ---------------------------------------------------------------------------
ROM:0008A970
ROM:0008A970 loc_8A970: ; CODE XREF: sub_8A900+48j
ROM:0008A970 move.w ($FFFFA562).w,d3 // Engine speed
ROM:0008A974 cmp.w (word_8AB06).l,d3
ROM:0008A97A bcc.s loc_8A9CC
ROM:0008A97C bra.s locret_8A9CE
ROM:0008A97E ; ---------------------------------------------------------------------------
ROM:0008A97E
ROM:0008A97E loc_8A97E: ; CODE XREF: sub_8A900+28j
ROM:0008A97E tst.b ($FFFFAF3A).w // Brake Pedal
ROM:0008A982 beq.s loc_8A9A6
ROM:0008A984 tst.b ($FFFFAF3A).w // Brake Pedal (Need to confirm clutch ram address before changing this)
ROM:0008A988 beq.s loc_8A9A6
ROM:0008A98A move.w ($FFFFAEBC).w,d3 // Vehicle Speed
ROM:0008A98E cmp.w (word_8AB02).l,d3
ROM:0008A994 bhi.s loc_8A9A6
ROM:0008A996 cmp.w (word_8AB04).l,d4
ROM:0008A99C bcs.s loc_8A9A6
ROM:0008A99E move.b #1,($FFFF819E).w // Enable LC if all parameters are satisifed
ROM:0008A9A4 bra.s locret_8A9CE
ROM:0008A9A6 ; ---------------------------------------------------------------------------
ROM:0008A9A6
ROM:0008A9A6 loc_8A9A6: ; CODE XREF: sub_8A900+82j
ROM:0008A9A6 ; sub_8A900+88j ...
ROM:0008A9A6 tst.b ($FFFFAF3A).w // FFS Brake Pedal (Need to confirm clutch ram address before changing this)
ROM:0008A9AA beq.s locret_8A9CE
ROM:0008A9AC move.w ($FFFFAEBC).w,d3 // Compare vehicle speed for FFS
ROM:0008A9B0 cmp.w (word_8AB08).l,d3
ROM:0008A9B6 bcs.s locret_8A9CE
ROM:0008A9B8 cmp.w (word_8AB04).l,d4 // Compare TPS for FFS
ROM:0008A9BE bcs.s locret_8A9CE
ROM:0008A9C0 move.w ($FFFFA562).w,d3 // Compare engine speed for FFS
ROM:0008A9C4 cmp.w (word_8AB0C).l,d3
ROM:0008A9CA bcs.s locret_8A9CE
ROM:0008A9CC
ROM:0008A9CC loc_8A9CC: ; CODE XREF: sub_8A900+20j
ROM:0008A9CC ; sub_8A900+7Aj
ROM:0008A9CC clr.l d6 // Clear dwell value
ROM:0008A9CE
ROM:0008A9CE locret_8A9CE: ; CODE XREF: sub_8A900+58j
ROM:0008A9CE ; sub_8A900+60j ...
ROM:0008A9CE rts
ROM:0008A9CE ; End of function sub_8A900
ROM:0008A9CE
Function 2 Jump Patched in at ROM:0003A48E
Code: Select all
ROM:0008A9D0
ROM:0008A9D0 ; =============== S U B R O U T I N E =======================================
ROM:0008A9D0
ROM:0008A9D0
ROM:0008A9D0 sub_8A9D0: ; CODE XREF: sub_3A436+58p
ROM:0008A9D0 jsr sub_26994
ROM:0008A9D6 tst.b ($FFFF819F).w // Test if timed retard active
ROM:0008A9DA beq.s locret_8AA22
ROM:0008A9DC tst.b ($FFFFB370).w // DBW Enable
ROM:0008A9E0 beq.s loc_8A9E8
ROM:0008A9E2 move.w ($FFFFA598).w,d3 // DBW TPS
ROM:0008A9E6 bra.s loc_8A9EC
ROM:0008A9E8 ; ---------------------------------------------------------------------------
ROM:0008A9E8
ROM:0008A9E8 loc_8A9E8: ; CODE XREF: sub_8A9D0+10j
ROM:0008A9E8 move.w ($FFFFAB64).w,d3 // Non-DBW TPS
ROM:0008A9EC
ROM:0008A9EC loc_8A9EC: ; CODE XREF: sub_8A9D0+16j
ROM:0008A9EC cmp.w (word_8AB04).l,d3
ROM:0008A9F2 bcs.s loc_8AA1E
ROM:0008A9F4 clr.l d3
ROM:0008A9F6 move.w ($FFFF81A0).w,d1 // Cycle counter when timed retard was activated
ROM:0008A9FA move.w ($FFFFB544).w,d3 // Cycle counter
ROM:0008A9FE sub.w d1,d3
ROM:0008AA00 move.w d3,($FFFF81A4).w // Delta cycles
ROM:0008AA04 mulu.w #$10,d3
ROM:0008AA08 cmpi.w #$2800,d3
ROM:0008AA0C bcc.s loc_8AA1E
ROM:0008AA0E tbls.w (word_8AB0E).l,d3
ROM:0008AA16 add.w d3,d0
ROM:0008AA18 move.w d3,($FFFF81A2).w // Save result from table lookup
ROM:0008AA1C bra.s locret_8AA22
ROM:0008AA1E ; ---------------------------------------------------------------------------
ROM:0008AA1E
ROM:0008AA1E loc_8AA1E: ; CODE XREF: sub_8A9D0+22j
ROM:0008AA1E ; sub_8A9D0+3Cj
ROM:0008AA1E clr.b ($FFFF819F).w // Clear timed retard status
ROM:0008AA22
ROM:0008AA22 locret_8AA22: ; CODE XREF: sub_8A9D0+Aj
ROM:0008AA22 ; sub_8A9D0+4Cj
ROM:0008AA22 rts
ROM:0008AA22 ; End of function sub_8A9D0
ROM:0008AA22
Re: developing a spark cut launch control solution
Posted: Wed Sep 23, 2020 11:11 am
by turbo_v6
Here is a bin with the patches applied and another log.
I have been testing with a V6 bin because that's what I am running, but it should work just the same on a V8.
Will likely need testers for the future (and so I can get the clutch input correct).