I'm developing a hardware abstraction library for an embedded product using GCC C. Within the library there is a variable that should be read-only to the application that links the library, but can be modified from within the compilation unit that defines it.
Is there a standard, acceptable way to declare the integer (in the library header file) that will allow the application to read the value in the variable, but tell the compiler to generate an error if any attempt is made to generate code that writes back to it? For example, if I were to declare a function as:
extern void foo(int const bar);
... then the caller is permitted to pass a local variable:
int bar = 0;
foo(bar);
... but if the function declaration attempts to write to bar
:
void foo(int const bar)
{
bar = 99;
}
... then the compiler duely reports an error: assignment of read-only location 'bar'.
The syntax of placing the const
before the name does not appear to apply to variables in the same way that it does to function parameters, and the two lines below seem to be effectively equivalent:
extern const int x;
extern int const y;
... because defining y as int y;
results in an error: conflicting type qualifiers for 'y', as I would expect to have seen had x been defined as int x;
.
I know that I can get around the problem by declaring and defining an accessor function that returns the value (which can only be used as an r-value).
I've read a number of related questions here, but none that I've found provide a definitive answer for C (as opposed to C++ or C#):
C — Accessing a non-const through const declaration
Mixing extern and const
Please can someone point in me the direction of an example of how I might achieve it, or confirm my suspicion that it is not syntactically achievable?
Within the library there is a variable that should be read-only to the application that links the library, but can be modified from within the compilation unit that defines it.
The solution is to use object-oriented design, namely something called private encapsulation.
module.h
int module_get_x (void);
module.c
static int x;
int module_get_x (void)
{
return x;
}
main.c
#include "module.h"
int main(void)
{
int value = module_get_x();
}
If the variable must be read-write inside the module, then this is the only proper way to do this. All other ways are just some flavour of spaghetti programming.
You can use pointer to get past the issue.
module.c
static int readwrite = 0;
int const * const readonly = &readwrite;
module.h
extern int const * const readonly;
If there is no reason to expose address of the variable, you should prefer Lundins getter approach to have proper encapsulation.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With