24

Consider the following main():

int main(int argc, char *argv[])
{
    return (0);
}

Upon compilation with cc -Wall -Wextra, warnings saying "unused parameter" get generated.

When I do not need to use a parameter in a function (for instance in a signal handler function that makes no use of its int parameter), I am used to doing the following:

  int main(int argc, char *argv[])
  {
      (void)argc;
      (void)argv;
      return (0);
  }

(For that particular main(), I sometimes see other people do: argv = argv - argc + argc)

But what does (void)var actually do?

I understand that (void) is a cast, so I guess I am casting away the variable? What does the var; line (without the cast) do? Is it an empty assignment, an empty expression?

I would like to understand what is actually going on.

Jonathan Leffler
  • 730,956
  • 141
  • 904
  • 1,278
Diti
  • 1,454
  • 3
  • 23
  • 38
  • 2
    If expr has no lvalue and is not a function call, then `expr;` is a statement with no effect. It does nothing. Writing `(void) expr;` supresses the warning of a statement with no effect. Writing a statement with no effect involving `expr` in it silences warnings involved with not using `expr` in a function where `expr` appears in the parameter list. – Brandin Jan 10 '14 at 16:37

4 Answers4

23

It's just a way of creating a 'harmless' reference to the variable. The compiler doesn't complain about an unused variable, because you did reference the value, and it doesn't complain that you didn't do anything with the value of the expression var because you explicitly cast it to void (nothing), indicating that you didn't care about the value.

I haven't seen this usage on variables before (because the compiler I use doesn't normally complain about unused function arguments,) but I see this used frequently to indicate to the compiler that you don't really care about the return value of a function. printf(), for example, returns a value, but 99% of C programmers don't know (or care) what it returns. To make some fussy compilers or lint tools not complain about an unused return value, you can cast the return value to void, to indicate that you know it's there, and you explicitly don't care about it.

Other than communicating your intent (that you don't care about this value) to the compiler, it doesn't actually do anything - it's just a hint to the compiler.

JVMATL
  • 2,064
  • 15
  • 25
8
  (void)argc;
  (void)argv;

If a function argument is not used, like in your program, then this is the idiomatic way of suppressing the warning of unused function argument issued by some compilers. Any decent compiler will not generate code with these statements.

It evaluates the argument but does nothing with it which has the effect for most compilers to not issue a warning. The (void) cast is used so the compiler would not produce another warning notifying that the value is not used.

Another popular way to suppress the warning is to do:

variable = variable;

Note that I know some compilers that will issue another warning in presence of:

(void) arg;

like "statement with no effect".

ouah
  • 142,963
  • 15
  • 272
  • 331
  • Many thanks! I did not know that other errors ("statement with no effect") could be raised with this technique. My school compiles our projects with `-Werror`, and I want an actual grade, haha! – Diti Jan 10 '14 at 13:42
  • 1
    For what it's worth, my company compiles with -Werror, too: it's painful when you first turn it on for a large project, but not too bad if you start out with it, and in the long run, the more warnings you turn on and leave on, the better your code - not only does the compiler find real problems for you, but programmers are forced to learn more about the language as they work out how to avoid certain warnings, and that helps them be better coders in the long run. – JVMATL Jan 10 '14 at 13:51
  • @JVMATL One of the issues with `-Werror` is in a Makefile it will typically exit the compilation process, while you may be interested to have a big picture with the dump of all the warnings. – ouah Jan 10 '14 at 14:37
  • @ouah if you use 'make -k' (-k == "keep going") you still get all (most of) your warnings. Unless you are using recursive makefiles.. :) (http://aegis.sourceforge.net/auug97.pdf) – JVMATL Jan 10 '14 at 16:17
  • @JVMATL but "keep going" would continue the process also for the other (not compilation) errors which may not be the desired behavior. – ouah Jan 10 '14 at 16:49
2

As other persons correctly noted, It just suppresses a compiler warning about unused variable in your code. Btw, Win32 has defined UNREFERENCED_PARAMETER macro to reach this goal. My suggestion to make something like that in your code:

#ifdef _WIN32
# define UNUSED(x) UNREFERENCED_PARAMETER(x)
#else
# define UNUSED(x) (void) x
#endif
Dmitry
  • 276
  • 2
  • 4
0

This may increase the code efficiency because the call of function dont need to load the registers for arguments.