Pages: [1]
Author Topic: MED9.1 Communicating with peripherals (e.g. cluster)  (Read 8282 times)
Basano
Full Member
***

Karma: +90/-3
Offline Offline

Posts: 192


« on: June 06, 2014, 08:25:50 AM »

Hi guys,

There’s another neat bit of information contained within the ram.

The ECU transmits a number of CANBUS messages on the bus which are picked up by other modules. The transmitted messages are described in the FR in section CANECU 1.240.0 CAN Sendebotschaften und Signaldefinitionen and section CAN_CONF 1.50.0 CAN-Kanalbelegung in der MED9. You really need the FR as a reference for this Grin

Bosch VAG MED9.1 FDEF

For example, in Message ID 280 (Motor 1) bytes 3 and 4 contain the engine rpm (nmot_c). This information comes straight from the FR. Disassembling and looking at the code that sets bytes 3 and 4 will lead you to the variable that holds nmot_c. This is how devices like the instrument cluster know what rpm to display – they get the message with the rpm over the CANBUS.





By searching on the CANBUS message ID’s in the ram dump, I came across a section of the ram that contains the message ID’s and payload. Ergo, these are the message buffers that contain the data that will be sent out by the ecu. By disassembling in IDA and looking at the cross references that point at this section of ram, you can locate the variables that hold the data to be sent out. This was in the external ram which starts at 0x800000, so all the ram address in this particular ram dump are offset from this (0x0 = 0x800000, 0x1 = 0x800001 etc)

External_RAM_dump.bin



CANBUS Message ID
Payload

« Last Edit: June 06, 2014, 08:27:51 AM by Basano » Logged
Basano
Full Member
***

Karma: +90/-3
Offline Offline

Posts: 192


« Reply #1 on: June 06, 2014, 08:30:21 AM »

What about the other direction? Changing nmot_c to change what’s transmitted out?

I was a bit wary about changing nmot_c directly. Although nmot_c will indeed be passed to the message buffer for transmission, what about other places in the code that may depend on nmot_c? The results could be unpredictable. So instead of changing the variable nmot_c, I decided to change the message buffer instead. Just before nmot_c is written to the message buffer, I insert my own value thus:

Original flow:
nmot_c -> general purpose register -> message buffer

Modified flow:
nmot_c -> general purpose register -> my_own_value -> general purpose register -> message buffer

I limited my changes to the message buffer to when the engine was not running (B_nmin). Remember, although I’m not setting the variable nmot_c within the ecu, I’m still going to be sending out a CANBUS message with a modified value for nmot_c. The cluster should see this and move the rpm needle. Other nodes may also think the engine is running when it’s not… So I played it safe and put in some conditions – engine not running (B_nmin) , brake pedal pressed (B_br), clutch pedal pressed (B_kuppl).

The result is a little routine that flicks the rpm needle from 1000 -> 2000 -> 3000 -> 4000 -> 1000 every time the clutch pedal is pressed and released (plus engine not running and brake pedal also pressed). All I’m doing is overwriting bytes 3 and 4 in that message buffer.

This code is specific to my bin and location therein. I’ve chosen the General Purpose Registers and RAM addresses _very_ carefully to avoid clashes. It took me ages and I bricked my ecu more than once. BDM was my friend to recover here. Use it as a guide by all means, but it’s not intended as a straight copy/paste exercise. If it all goes horribly wrong, you have been warned…

This is my entry point into the code. I replace the original instruction at ROM:004F7B60 with my own instruction which is a jump to a free area ROM:0047C750. The penultimate instruction in the free area will be the displaced original instruction and the final instruction will be another jump back to the original code. General purpose register r30 is what I’m going to ultimately overwrite as explained above.

Code:
This section is the original code

ROM:004F7B50                 clrlslwi  r11, r11, 24,7
ROM:004F7B54                 or        r12, r12, r11
ROM:004F7B58                 clrlslwi  r10, r10, 24,8
ROM:004F7B5C                 or        r30, r12, r10
ROM:004F7B60
ROM:004F7B60 loc_4F7B60:                             # CODE XREF: sub_4F79BC+F0 j
ROM:004F7B60                 b         loc_47C750
ROM:004F7B64 # ---------------------------------------------------------------------------
ROM:004F7B64
ROM:004F7B64 loc_4F7B64:                             # CODE XREF: sub_4F79BC-7B1A0 j
ROM:004F7B64                 srwi      r10, r30, 24
ROM:004F7B68                 or        r11, r11, r10
ROM:004F7B6C                 rlwinm    r12, r30, 24,16,23
ROM:004F7B70                 lis       r29, unk_8043E4@h

And this is the new code that increments a counter. There's a section in here where I store the count byte in non-volatile ram. Directly after that I calculate a checksum of the ram mirror block where I've stored the byte. This is so the value will be comitted from the ram miror to the eeprom. This post has more details about the ram mirror.

Code:
This is my new code I added in free space

ROM:0047C750 # START OF FUNCTION CHUNK FOR sub_4F79BC
ROM:0047C750
ROM:0047C750 loc_47C750:                             # CODE XREF: sub_4F79BC:loc_4F7B60 j
ROM:0047C750                 lbz       r11, byte_7FEBA7 (B_nmin - engine not running)
ROM:0047C754                 cmpwi     r11, 1
ROM:0047C758                 bne       loc_47C818 (if the engine is running, ignore this whole routine and jump to the end)
ROM:0047C75C                 lbz       r11, byte_7FEDBD (B_kuppl - clutch pedal)
ROM:0047C760                 cmpwi     r11, 1
ROM:0047C764                 bne       loc_47C810
ROM:0047C768                 lbz       r11, byte_7FEDB8 (B_br - brake pedal)
ROM:0047C76C                 cmpwi     r11, 1
ROM:0047C770                 bne       loc_47C810
ROM:0047C774                 lbz       r11, byte_807F10 (temporary byte for latch, set / reset when pedal is pressed / released, stops value racing though 1 -> 2 -> 3 -> 4 -> 1 whilst pedal is kept pressed etc)
ROM:0047C778                 cmpwi     r11, 0
ROM:0047C77C                 bne       loc_47C7C8
ROM:0047C780                 li        r11, 1
ROM:0047C784                 stb       r11, byte_807F10
ROM:0047C788                 lbz       r11, byte_7FABF7 (this is the byte that holds the count, increments when the pedal is pressed)
ROM:0047C78C                 addi      r11, r11, 1
ROM:0047C790                 cmpwi     r11, 3
ROM:0047C794                 ble       loc_47C79C
ROM:0047C798                 li        r11, 0
ROM:0047C79C
ROM:0047C79C loc_47C79C:                             # CODE XREF: sub_4F79BC-7B228 j
ROM:0047C79C                 stb       r11, byte_7FABF7 (this section store my count in non-volatile memory, so it’s persistent over power cycles)
ROM:0047C7A0                 li        r7, 0  
ROM:0047C7A4                 li        r29, 0
ROM:0047C7A8
ROM:0047C7A8 loc_47C7A8:                             # CODE XREF: sub_4F79BC-7B200 j
ROM:0047C7A8                 addi      r11, r13, -0x5414 # unk_7FABDC
ROM:0047C7AC                 lbzx      r11, r11, r7
ROM:0047C7B0                 add       r29, r29, r11
ROM:0047C7B4                 addi      r7, r7, 1
ROM:0047C7B8                 cmpwi     r7, 0x1E
ROM:0047C7BC                 blt       loc_47C7A8
ROM:0047C7C0                 xori      r29, r29, 0xFFFF
ROM:0047C7C4                 sth       r29, word_7FABFA
ROM:0047C7C8
ROM:0047C7C8 loc_47C7C8:                             # CODE XREF: sub_4F79BC-7B240 j
ROM:0047C7C8                 lbz       r11, byte_7FABF7 (this section converts count 0-1-2-3 to rpm 1000-2000-3000-4000)
ROM:0047C7CC                 cmpwi     r11, 0
ROM:0047C7D0                 beq       loc_47C7EC
ROM:0047C7D4                 cmpwi     r11, 1
ROM:0047C7D8                 beq       loc_47C7F4
ROM:0047C7DC                 cmpwi     r11, 2
ROM:0047C7E0                 beq       loc_47C7FC
ROM:0047C7E4                 cmpwi     r11, 3
ROM:0047C7E8                 beq       loc_47C804
ROM:0047C7EC
ROM:0047C7EC loc_47C7EC:                             # CODE XREF: sub_4F79BC-7B1EC j
ROM:0047C7EC                 lis       r11, 0xFA0
ROM:0047C7F0                 b         loc_47C808
ROM:0047C7F4 # ---------------------------------------------------------------------------
ROM:0047C7F4
ROM:0047C7F4 loc_47C7F4:                             # CODE XREF: sub_4F79BC-7B1E4 j
ROM:0047C7F4                 lis       r11, 0x1F40
ROM:0047C7F8                 b         loc_47C808
ROM:0047C7FC # ---------------------------------------------------------------------------
ROM:0047C7FC
ROM:0047C7FC loc_47C7FC:                             # CODE XREF: sub_4F79BC-7B1DC j
ROM:0047C7FC                 lis       r11, 0x2EE0
ROM:0047C800                 b         loc_47C808
ROM:0047C804 # ---------------------------------------------------------------------------
ROM:0047C804
ROM:0047C804 loc_47C804:                             # CODE XREF: sub_4F79BC-7B1D4 j
ROM:0047C804                 lis       r11, 0x3E80
ROM:0047C808
ROM:0047C808 loc_47C808:                             # CODE XREF: sub_4F79BC-7B1CC j
ROM:0047C808                                         # sub_4F79BC-7B1C4 j ...
ROM:0047C808                 or        r30, r30, r11 (copy my count into r30)
ROM:0047C80C                 b         loc_47C818
ROM:0047C810 # ---------------------------------------------------------------------------
ROM:0047C810
ROM:0047C810 loc_47C810:                             # CODE XREF: sub_4F79BC-7B258 j
ROM:0047C810                                         # sub_4F79BC-7B24C j
ROM:0047C810                 li        r11, 0
ROM:0047C814                 stb       r11, byte_807F10 (reset the latch)
ROM:0047C818
ROM:0047C818 loc_47C818:                             # CODE XREF: sub_4F79BC-7B264 j
ROM:0047C818                                         # sub_4F79BC-7B1B0 j
ROM:0047C818                 slwi      r11, r30, 24
ROM:0047C81C                 b         loc_4F7B64 (jump back to the main code)

Little video attached to show you the end result 

MOV_0001.mp4
« Last Edit: June 06, 2014, 08:32:38 AM by Basano » Logged
max974
Newbie
*

Karma: +0/-0
Offline Offline

Posts: 17


« Reply #2 on: October 22, 2019, 02:22:00 AM »

Hi, thanks for all you done for this community.

i'am on this part for a long time, already find my Free RAM for all the multimap etc... But still don't find how or why you choose the ROM:004F7B60 Adress to add your jump to the cluster code ?

My file is the  8P0907115AB one.

Can some body tell me where to put this jump or how to fine the good place for the cluster check? Thanks
« Last Edit: October 22, 2019, 04:40:09 AM by max974 » Logged
Pages: [1]
  Print  
 
Jump to:  

Powered by SMF 1.1.21 | SMF © 2015, Simple Machines Page created in 0.025 seconds with 17 queries. (Pretty URLs adds 0.001s, 0q)