[Z88dk-users] String in ASM

Bridge to the z88dk-users mailing list
Post Reply
thricenightly
Member
Posts: 28
Joined: Thu Jun 01, 2017 5:46 pm

[Z88dk-users] String in ASM

Post by thricenightly »

This is a basic one, but I can't see why I've got it wrong. My C:

Code: Select all

#include <stdio.h>

extern unsigned char* message;

int main()
{
printf("Message is: \"%s\"\n", message);

return 0;
}
which is linked with:

Code: Select all

SECTION rodata_user

PUBLIC _message

_message:

defb 0x41, 0x00
When run I'd expect "Message is "A"" but I get "Message is "<splat!>".

where <splat!> is what appears to be random chars as far as the first \0 it happens to find. It compiles and links correctly, but clearly the defb isn't providing a stringz in the format the printf is expecting.

Why would that be?

Also, what's the best source of information for this sort of thing? Where, for example, can I find a description of what the "rodata_user" thing is about?



------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
thricenightly
Member
Posts: 28
Joined: Thu Jun 01, 2017 5:46 pm

Post by thricenightly »

This is a basic one, but I can't see why I've got it wrong. My C:

Code: Select all

<snip>
Replying to myself, I've had a look at the ASM the compiler puts out for the main() code. There's a level of indirection in there, so this works:

Code: Select all

#include <stdio.h>

extern unsigned char* message;

int main()
{
unsigned char** ptr = &message;
printf("Message is: \"%s\"\n", ptr);

return 0;
}
But I've no idea why! What should I be reading?



------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
alvin
Well known member
Posts: 1872
Joined: Mon Jul 16, 2007 7:39 pm

Post by alvin »

This:

Code: Select all

#include <stdio.h>

extern unsigned char* message;

int main()
{
printf("Message is: \"%s\"\n", message);

return 0;
}
should be this:

Code: Select all

#include <stdio.h>

extern unsigned char message[];

int main()
{
printf("Message is: \"%s\"\n", message);

return 0;
}
It's the difference between a pointer and an array here.
But I've no idea why! What should I be reading?
When you declare this:

extern unsigned char message[];

the label/address "_message" holds a character array. So beginning at address "_message" there will be characters.

This on the other hand:

extern unsigned char *message;

says the label/address "_message" holds a pointer to a character. So at address "_message" there are two bytes that make up a pointer value. In your example, the value of "_message" will be 0x0041 from your asm file.



------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
thricenightly
Member
Posts: 28
Joined: Thu Jun 01, 2017 5:46 pm

Post by thricenightly »

This:

Code: Select all

#include <stdio.h>

extern unsigned char* message;
should be this:

Code: Select all

#include <stdio.h>

extern unsigned char message[];
Oh Lordy, a salutary lesson in C arrays vs pointers. Thanks for that.



------------------------------------------------------------------------------
Check out the vibrant tech community on one of the world's most
engaging tech sites, Slashdot.org! http://sdm.link/slashdot
Post Reply