30

I have many different 3 axis sensors I am writing test code for. In the C files for each of them, I have the same char string defined:

char axis[3][8] = {"X", "Y", "Z"}

which I use when I "for" loop results to print the axis that is failing like this:

DEVICETEST_LOG("%s Failed %s axis for Min range\n",device_name[DUT], axis[i]);

I was thinking to save some space I could define a character string array in a header file to use all over the place.

I have tried a number of things, but I can't seem to get an array of strings defined in my header file that I can iterate through to pass a compile.

5 Answers 5

45

If you must put it in a header file, use extern or static:

// option 1
// .h
extern char axis[3][8];

// .c
char axis[3][8] = { "X", "Y", "Z" };

// option 2
// .h
static char axis[3][8] = { "X", "Y", "Z" };

Extern tells the linker that there is a global variable named axis defined in one of our implementation files (i.e. in one .c file), and I need to reference that here.

static, on the other hand, tells the compiler the opposite: I need to be able to see and use this variable, but don't export it to the linker, so it can't be referenced by extern or cause naming conflicts.

Sign up to request clarification or add additional context in comments.

1 Comment

Note that, when using static and compiling with -Wunused, if you do not use that array in that compilation unit, you''get a warning about it.
28

In order to avoid linker errors, you have to declare your array as extern in a header file, and then define the array once in one of your code modules.

So for instance:

//myheader.h
extern const char* axis[3];

then in another code module somewhere:

//myfile.c
const char* axis[3] = { "X", "Y", "Z" };

5 Comments

ah that makes sense but seems bassackwards... So the header file I include everywhere points all the other C files to the "myfile.c" local definition.
So even though I have included the header file in the other c files I am getting a compile error "undefined refrence". So in myheader.h I have >>extern char* AXIS[3][8]; and in myfile.c I have >>char* AXIS[3][8] = {{"X"}, {"Y"}, {"Z"}}; and I am including the myheader.h in the otherfile.c. I also tried a few other tricks but they are not synching up.
Something else is wrong then because this does work ... what happens if you take the macro out of the equation and simply try to access the array in another code module that includes the header file? Secondly, it should only be const char* AXIS[3] = { "X", "Y", "Z" }; since these are string literals ... where are you getting the 8 from?
I have the 8 there because I get a compile error otherwise. The compiler claims "error: format'%s' expects 'char *' but argument 5 has type 'int'" on the print line basically stateing the assignment of axis[i] to %s is wrong because it is an int even though it is defined as a char.
By the way ...DUHH that is so stupid of me...why have it in a header file. Just make a global in the high level test file that calls all of the low level files that is extern defined in the low level files. I did not have enough coffee yet when I was thinking this through.
8

Add this to your header:

extern char *axis[];

Add this to one source file in your project:

char *axis[] = { "X", "Y", "Z", "Time", "Space", "The Scary Door" };

1 Comment

Well done! I use this when I need to create a menu' with indefinite number of elements. It's perfect because at compile time the compiler sets up the array length exactly, moreover the code seems to be much more readable.
3

Put this in your header file

extern char axis[3][8];

and keep this in a C file:

char axis[3][8] = {"X", "Y", "Z"};

Comments

0

Michael Barr (Netrino) advises against the declaration of storage in a header file. Likewise, the Netrino embedded system coding standard does not condone the use of extern'ed storage in headers.

I generally agree with these principles, and I've found it to be a good idea to extern storage into the C files that need it, and only those.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.