Ssortingngify premier niveau macro expansion C

Est-il possible de ssortingngier cette macro C:

#define GPIO_INT_PIN (GPIO_PORT_D|GPIO_PIN_IRQ_RISING|GPIO_PIN5) 

en utilisant quelque chose comme

  MY_STRINGFY(GPIO_INT_PIN) 

obtenir

"(GPIO_PORT_D|GPIO_PIN_IRQ_RISING|GPIO_PIN5)" ?

Oui c’est possible. Lisez à propos de la hiérarchisation dans la documentation GCC cpp .

  #define STRINGIFY(It) #It #define MY_STRINGIFY(It) STRINGIFY(It) 

J’ai corrigé ma réponse grâce à celle de Wojtek Surowka

puis utilisez MY_STRINGIFY(GPIO_PORT_D|GPIO_PIN_IRQ_RISING|GPIO_PIN5) ce qui fonctionnerait beaucoup mieux si vous MY_STRINGIFY(GPIO_PORT_D|GPIO_PIN_IRQ_RISING|GPIO_PIN5) un enum pour définir les constantes, par exemple

 enum Gpio_stuff_en { GPIO_PORT_D=5, GPIO_PIN_IRQ_RISING=17, GPIO_PIN5=23 }; 

Bien sûr, cela ne fonctionnera pas comme vous le souhaitez si vous avez besoin que GPIO_PORT_D soit une macro, par exemple, car elle se développe en une expression non-littérale constante (comme une variable ou un access à un champ d’une structure globale, etc.). …)

En contre-exemple:

 #define FOO 1 #define BAR 2 #define STRINGIFY(s) #s #define MY_STRINGIFY(s) STRINGIFY(s) MY_STRINGIFY(FOO|BAR) 

est étendu à "1|2" non à "FOO|BAR" , si vous supprimez les deux #define -s pour FOO et pour BAR et les remplacez par

 enum { FOO=1, BAR=2 }; 

vous obtenez vraiment l’extension "FOO|BAR" comme vous le souhaitez. Vérifiez avec gcc -C -E

Également:

 enum {FOO=1, BAR=2}; #define FOOORBAR (FOO|BAR) #define STRINGIFY(s) #s #define MY_STRINGIFY(s) STRINGIFY(s) MY_STRINGIFY(FOOORBAR) 

est élargi comme "(FOO|BAR)" . Mais si vous utilisez #define pour FOO et pour BAR vous obtenez l’extension "(1|2)" .

Peut-être que vous pourriez append dans votre propre en-tête, après avoir inclus l’en-tête externe définissant GPIO_PORT_D etc … en tant que constantes littérales, quelque chose comme:

 enum {en_GPIO_PORT_D= GPIO_PORT_D, en_GPIO_PIN_IRQ_RISING= GPIO_PIN_IRQ_RISING, en_GPIO_PIN5= GPIO_PIN5}; #undef GPIO_PORT_D #undef GPIO_PIN_IRQ_RISING #undef GPIO_PIN5 #define GPIO_PORT_D en_GPIO_PORT_D #define GPIO_PIN_IRQ_RISING en_GPIO_PIN_IRQ_RISING #define GPIO_PIN5 en_GPIO_PIN5 

et alors vous obtiendrez des constantes ssortingngifiées plus lisibles (mais pas exactement ce dont vous rêvez).

Si vous avez ces deux définitions

 #define STRINGIFY(s) #s #define MY_STRINGIFY(s) STRINGIFY(s) 

MY_STRINGIFY fait ce que vous voulez – développe son argument et ajoute des guillemets après.