Flashforge creator 3 pro - patching binary

This page will describe how to patch the binary and some problems there were.

Patching problems

The first version of the patch for preparing arguments for function M106 looked like:

_start:
/* LAB_001318d0  (prepare for M106 command) */
        mov        r0,r5                  @ arg 1       (0x1318d0 28 46)
        mov        r1,r8                  @ arg 2       (0x1318d2 41 46)
        ldr        r2, [sp, #0x20]        @ arg 3       (0x1318d4 08 99)
        bl         #0x330a88              @ handle m106 (0x1318d6 ff f1 d7 f8)
        clz        r0, r0                 @             (0x1318da b0 fa 80 f0)
        b          #0x1318ec              @             (0x1318de 05 e0)
 
@  - or -
@       b.w        #0x1318ec              @             (0x1318de 00 F0 05 B8)
@                                         @ ... continue at lsrs r0, r0, #0x5 and then b #0x1316d6
 
@
@  LAB_001318e0 (prepare for M26 command)
@       mov        r0,r5                  @ arg 1       (0x1318e0 28 46)
@       ldr        r2, [sp, #0x20]        @ arg 3       (0x1318e2 08 99)
@       bl         #0x129c44              @ handle m601 (0x1318e4 f8 f7 ae f9)
@       clz        r0,r0                  @             (0x1318e8 b0 fa 80 f0)
@       lsrs       r0,r0,#0x5             @             (0x1318ec 40 09)
@       b          #0x1316d6              @             (001318ee f2 e6)
@

But during testing, the printer crashed at receiving command M26 with an “illegal instruction” error. A backtrace in gdb showed quickly where the problem was: The branch instruction at address 0x1318de should have been a “b #0x1318e8” (05 e0), but the assembler converted the branch instruction into “b.w #0x1318ec” (00 F0 05 B8) and thus overwriting partly the function for M26.

Why GNU as encoded the branch instruction into a 32 bit instruction I do not yet know. The easiest solution was to accept that the instruction may occupy 32 bit, and branch from one instruction earlier. So instead of “0x1318da clz r0,r0” followed by “0x1318de b #0x1318ec” it would just do “0x1318da b #0x1318e8”:

_start:
        mov        r0,r5                  @ arg 1, (0x1318d0 28 46)
        mov        r1,r8                  @ arg 2, (0x1318d2 41 46)
        ldr        r2, [sp, #0x20]        @ arg 3, (0x1318d4 08 9a)
        bl         #0x330a88              @ handle m106, 0x1318d6 ff f1 d7 b8)
        b          #0x1318e8              @        (0x1318da 05 0e)