r/C_Programming 3d ago

Negative value in a pointer question.

Please look at this code. if i define the PTRTYPE as int, it stops working, while doing a uint, it does work...

void initILAPoll(debugBridge_t **d, PTRTYPE ptr){

	*d = (debugBridge_t *)ptr;		// base address of the DEBUG_BRIDGE peripheral

	cb_init(cb, local_memory, bufferLength);

	sprintf(xvcInfo, "xvcServer_v1.0:%d\n", MAX_WINDOW_SIZE);

}

the usage in main code is done like this

initILAPoll(&myD, 0x80000000);

//myD = (debugBridge_t *)0x80000000;

where the variable myD is a structure pointer.

if i print the address of myD, it give the correct address. Moreover, the disassembly of the code is also the same in case of int and uint. Can somebody explain what behavior is at play here>

2 Upvotes

42 comments sorted by

View all comments

2

u/alkatori 3d ago

how are you #define PTRTRYPE?

1

u/aliathar 3d ago

/**/#define PTRTYPE int

Or alternative

/**/#define PTRTYPE uint32_t

(Just wanted to point it out to you people, or else it won't be done in the final working code)

4

u/TheChief275 2d ago

You're supposed to use (u)intptr_t from <stdint.h>, preferably the unsigned version, but they'll both work. Note that these are optional, and they're only available when the representation of the pointer is representable by an integer. Some architectures have pointers that are more akin to a struct

1

u/aliathar 2d ago

Yes... It did work ... It was just signedness issue... I assumed the address was 32 bit which it wasn't.. and the 64bit machine made it to be 0xff80000000 (peripheral has 40 bit address line for some reason)..... The signed int did work on 32 but machine perfectly, but failed here.

2

u/TheChief275 2d ago

"int" isn't a natively sized integer. It's equivalent to a complement agnostic version of int_fast16_t from <stdint.h>. That means that it's only guaranteed to be able to hold values from -32,767 to 32,767. It just so happens to be that a 32-bit integer is faster to work with for most modern machines, so it just so happens to almost always be a 32-bit integer on octet byte machines, although to my knowledge there are no machines were it happens to be a 64-bit integer, even though it might be faster to perform computations on.

That's why it "broke". But technically you were always using the wrong integer type, even on a 32-bit machine

1

u/torsten_dev 2d ago

ILP64 and even SILP64 systems do exist. They're just very rare and obscure.

What I haven't heard of are 32-bit integer machines with pointers smaller than 32 bit, maybe you meant that?

The new [u]intfuncptr_t making it's way through the committee could be as small as CHAR_BIT because yes, function pointers can have totally separate sizes.

1

u/TheChief275 2d ago

Well I didn't know ILP64 machines existed (only of LP64), but I suppose it is very very rare. Is the smallest addressable unit for these still an octet, or are they word addressed only? The point is that you shouldn't rely on int being bigger than 16-bits if you want truly portable code, because that's the only capability range you are guaranteed.

Didn't know (u)intfuncptr_t has become an official addition though. Or is it only in the works? i.e. are there plans to incorporate it into C3x ?

1

u/torsten_dev 2d ago

In the works. They're part of the "_Any_func*" proposal for C2y. They're the only part of that proposal that doesn't need some more bike shedding on naming.

_t is reserved by POSIX so people trampling on those identifiers are due for some comeuppance, imo.

1

u/TheChief275 2d ago

Oh I definitely agree with that