I have just installed the recent Windows x64 4.2.0-rc1 release and tried updating one of my projects to use '__sdcccall(0)' for existing STM8 assembly code, and was puzzled to find that it had no effect - some functions marked with that attribute were still being called with the new ABI!

After doing some digging, I discovered that functions where the new attribute had no effect were functions that were also declared with '__naked'.

Here is a short test program illustrating the problem:

#include <stdint.h>

static uint8_t test_1(const uint8_t foo) __sdcccall(0) {
    (void)foo;
    return 255;
}

static uint8_t test_2(const uint8_t foo) __naked __sdcccall(0) {
    (void)foo;
    __asm
        ld a, 255
        retf
    __endasm;
}

void main(void) {
    volatile uint8_t foo = test_1(0);
    volatile uint8_t bar = test_2(0);
    while(1);
}

The generated assembly is as follows:

_test_1:
    ld    a, #0xff
    retf

_test_2:
    ld    a, 255
    retf

_main:
    ; ...snip...
    push    #0x00
    callf    _test_1
    addw    sp, #1
    ld    (0x01, sp), a
    clr    a
    callf    _test_2
    ld    (0x02, sp), a
    ; ...snip...

You can see that test_1() has its argument pushed to the stack before being called, as per the old ABI, but test_2() does not - its argument is incorrectly passed in the A register, as per the new ABI.

Is this a bug? I don't believe '__naked' should be changing anything about how a function is *called*, only whether prologue and epilogue code inside that function is generated.

Regards,
Basil Hussain


_______________________________________________
Sdcc-user mailing list
Sdcc-user@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/sdcc-user

Reply via email to