Search code examples
cliteralsvoid-pointers

How to get a Memory Address (Pointer) from a Number Literal?


Background:

I have decided to work with neutral void pointers (void*) in my programme because it is uniform, efficient and I can cast them to whatever is needed in the context.

When calling a comparison function, all arguments/parametres have to be handed over as void pointer, for example:

compare_integer_equal((void*) &r, p12, (void*) NUMBER_1_INTEGER_STATE_CYBOI_MODEL);

The integer constant is defined globally as:

static int NUMBER_1_INTEGER_STATE_CYBOI_MODEL_ARRAY[] = { 1 };
static int* NUMBER_1_INTEGER_STATE_CYBOI_MODEL = NUMBER_1_INTEGER_STATE_CYBOI_MODEL_ARRAY;

Problem:

Such constants do exist for all frequently used numbers and sum up to a file size of more than 2 MB, which I would like to eliminate. Of course I could always use a local variable like:

int i = 1;
compare_integer_equal((void*) &r, p12, (void*) &i);

But I would like to avoid this extra effort/memory/time when having to do hundreds of comparisons. When trying to get a reference from a literal as shown in the following example, the compiler produces the error: "lvalue required as unary ‘&’ operand":

compare_integer_equal((void*) &r, p12, (void*) &1);

Is there a way to get a memory address (pointer) from a Literal? Are there other ideas to handle literals as (void*)?


Solution

  • The best approach is to declare a static const object of the proper type having the proper value, and pass its address. While C99 added a convenient syntax for compound literals, it will generate less efficient machine code than the approach using static const, and will also yield the address of an object whose lifetime will be limited to the immediate enclosing block, meaning that any persisted pointers to the object will be left dangling. By contrast, any pointer to a static const object will remain valid throughout the lifetime of the program.