0

I define my exceptions on the command line:

-DEXCEPTION_1=\"first\" -DEXCEPTION_2=\"second\" -DEXCEPTION_3=\"third\"

which I check against a string:

except = 0;
#ifdef EXCEPTION_1
if (! strcmp(EXCEPTION_1, mystring))
{  except = 1;
}
#endif
#ifdef EXCEPTION_2
if (! strcmp(EXCEPTION_2, mystring))
{  except = 1;
}
#endif
#ifdef EXCEPTION_3
if (! strcmp(EXCEPTION_3, mystring))
{  except = 1;
}
#endif
if (except == 1)
{  // do something
}
else
{  // do something else
}

Needless to say, while this works, it is also quite ugly, inflexible and causes redundancy in my code.

Is there a way to append a string to a preprocessor macro variable?

I would like to get something like this (the problem of course is that #append does not exist):

#ifdef EXCEPTION_1 #append EXCEPTIONS if (! strcmp(EXCEPTION_1, mystring)) {  except = 1; }
#ifdef EXCEPTION_2 #append EXCEPTIONS if (! strcmp(EXCEPTION_2, mystring)) {  except = 1; }
#ifdef EXCEPTION_3 #append EXCEPTIONS if (! strcmp(EXCEPTION_3, mystring)) {  except = 1; }

Then I could just use EXCEPTIONS in the code and it would work with all possible permutations of exceptions.

In other words I want to append a string to a macro variable - is it possible?

0

4 Answers 4

1

You can have chains of defines, but it won't look much better:

#ifdef EXCEPTION_1 
#define EXCEPTIONS1 if (! strcmp(EXCEPTION_1, mystring)) {  except = 1; }
#else
#define EXCEPTIONS1
#endif

#ifdef EXCEPTION_2
#define EXCEPTIONS2 EXCEPTIONS1 if (! strcmp(EXCEPTION_2, mystring)) {  except = 1; }
#else
#define EXCEPTIONS2 EXCEPTIONS1 
#endif

// etc

Again, not much better.

And you really shouldn't define macros with open if's. It allows weird interactions like if(cond) EXCEPTIONS1 else cout<<"error"; -- that won't do what you expect because EXCEPTIONS1 is a plain if and will gobble up the else branch.

The typical way of writing macros with code blocks is to wrap the whole thing in a do{...}while(0) (note no ending ;).

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

Comments

1

Checkout the token stringification and concatenation section here It might help some. In general, it would seem easier to use your command line macro to populate a table and have a macro that simply expands to a loop that checks the successive entries of that table to set the except flag.

For instance, save the following as silly.c and compile with cc -DEX1=\"hello\"

#include <stdlib.h>
#include <stdio.h>
#include <string.h>

struct Except {
   const char* key;
   int flag;
};

struct Except table[] = {
#if defined(EX1)
   {EX1,1},
#endif
   {NULL,0}
};

#define CHECKEX(mys,rv)  { rv = 0;for(int i=0;table[i].key!=0;i++)      \
         if (strcmp(table[i].key,(mys))==0) \
            rv = 1; \
   }

int main()
{
   int rv;
   CHECKEX("hello",rv);
   if (rv)
      printf("Got an hello\n");
   else printf("Got nothing\n");
   return 0;
}

Simply add more "blocks" to the table as needed. Just a suggestion of course.

Comments

0

You can convert a macro argument to a string:

#define STR(x)    #x

STR(hello)  -->  "hello"

And you can concatenate string literals by just writing them next to each other:

"123" "abc"  -->  "123abc"

Or create a macro:

#define CONCAT(a, b) a b

CONCAT("hello", " world!")  --> "hello world!"

4 Comments

I do not want to concatenate strings, I want to concatenate the input for the compiler
@RolandSeuhs: "How to concatenate/append substitution string". You should learn how to ask. Your question is far from being clear. And: strings are input to the compiler. Egal!
What is that, you don't even bother to read past the question title and you're mocking the OP? Perhaps you should learn how to read and behave instead. Flagging this for moderator attention.
@Blindy: I did read further: "Is there a way to append a string to a preprocessor macro variable"
-1

You can use ## to concatenate string to macros. Use an index and use the conditions only to set the index. Then at the end you can concatenate the index with your macro EXCEPTION. like,

define a macro like #define append(name) name ## counter

this will in turn give you name as name1 if counter is 1

Now you can define different append macros to come with the result in a single variable name

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.