Home > Software engineering >  Using snprintf with C90
Using snprintf with C90

Time:10-30

Is there a way instruct the the compiler that:

  • The language is C90
  • The declarations of stdio.h are those of C99 (including snprintf)

With cc -std=c90 -Wall (on a source file using snprintf), an annoying warning is issued (sometimes, depending on the compiler/environment, with a confusing hint that stdio.h should be included, even if it already is), but the linker finds snprintf anyway. I understand what is happening, that is not the question.

Using strict c90 (language) and snprintf (library function) is technically well possible, but I do not know how to instruct the compiler accordingly. In other words, I would like to distinguish between language compliance and library compliance.

Remark: I assume that the language used in the C99 stdio.h header file is actually C90, and that it could thus be included by a C90 source file. Does anything prevent it?

I would prefer a solution with a generic include <stdio.h>, for the sake of portability.

CodePudding user response:

No.

A generic #include <stdio.h> for a C90 compiler needs not declare snprintf.

Before you argue that it's not a C90 compiler, keep in mind that you are requesting that it acts as one usng -std=c90. A compiler acting as a C90 compiler needs not do anything that a C90 compiler wouldn't do.

There is therefore no generic solution.

There may be compiler-specific solutions, including adding the following:

int snprintf( char * buffer, size_t bufsz,  const char * format, ... );

CodePudding user response:

Yes, though it's a bit of a weird thing to do.

You can define _ISOC99_SOURCE to signal that you want C99 functions to be defined.

Example:

#define _ISOC99_SOURCE
#include <features.h>
#include <stdio.h>

int main() {
    char buf[10];
    snprintf(buf, 4, "foo");
    puts(buf);
    return 0;
}

Compile it like so:

$ gcc -std=c90 -Wall test.c  
$ ./a.out 
foo

This will work in gcc 10.3.0 and clang 11.0.0. In terms of library compatibility, it has only been tested with glibc, and not musl or other versions of the standard library.

  • Related