Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Indentation of preprocessor statements in C

I am writing a program in C which should act differently based on the definition or not of symbolic constant(s). For a simple example, my first thought would be to write it like this:

#include <stdio.h>
#define TEST

int main(void) {
   int num;
   #ifdef TEST
      num=1;
      printf("YES\n");
   #else
      num=0;
      printf("NO\n");
   #endif
   printf("%d\n", num);
   return 0;
}

However, upon trying to auto-indent my code (specifically by using gg=G in vim) my indentation was lost:

#include <stdio.h>
#define TEST

int main(void) {
   int num;
   #ifdef TEST
   num=1;
   printf("YES\n");
   #else
   num=0;
   printf("NO\n");
   #endif
   printf("%d\n", num);
   return 0;
}

Of course, if I try to auto-indent something like the following (with actual commands in between) chaos ensues:

#ifdef TEST1
   commands
   #ifdef TEST2
      commands
   #else
      #ifdef TEST3
         commands
      #endif
      commands
   #endif
#endif

So, is there anything I can do to have the indentation above be treated as the default?

like image 580
Ch0sen Avatar asked Sep 25 '22 18:09

Ch0sen


1 Answers

The short answer is: auto-indentation on editors follow established language guidelines, and what you are trying to do is not considered 'good practice' and thus has not been implemented in any editor (that I've seen at least).

Longer answer: The C language does not have any indentation rules, so any indentation done is by established practice. And different people have different opinions on what their ideal of established practice is. Specifically for preprocessor conditionals, I have never seen anyone use any additional depth - and IMO that would be bad practice as it would get terribly confusing when intermixed with the language conditionals (i.e. if (code)) Take a look at these 2 basic examples:

    if (conditional1)
        action1();
#if compileoption1
        else if (conditional2)
            action2();
#else
        action3();
#endif

and

#if compileoption1
    if (conditional1)
#endif
    action1();

It becomes downright impossible to follow the logic through indentation. The pre-processor and the actual compiler are independent steps, and the pre-processor step pays no attention to actual C semantics so conditionals can start and end in places completely orthogonal to the C flow control statements (if, while, for, etc...), making it difficult to try to unify them through something like indentation. Which is in my opinion why it has become standard practice to not use indentation for preprocessor conditionals. For some well established conventions see the kernel coding guidelines: https://www.kernel.org/doc/Documentation/CodingStyle

Chapter 20 deals with conditional compilation.

like image 72
csd Avatar answered Sep 29 '22 07:09

csd