Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Most standard way to select a function name depending on platform?

I am currently using the popen function in code that is compiled by two compilers: MS Visual Studio and gcc (on linux). I might want to add gcc (on MinGW) later.

The function is called popen for gcc, but _popen for MSVS, so i added the following to my source code:

#ifdef _MSC_VER
#define popen _popen
#define pclose _pclose
#endif

This works, but i would like to understand whether there exists a standard solution for such problems (i recall a similar case with stricmp/strcasecmp). Specifically, i would like to understand the following:

  1. Is _MSC_VER the right flag to depend on? I chose it because i have the impression that linux environment is "more standard".
  2. If i put these #define's in some header file, is it important whether i #include it before or after stdio.h (for the case of popen)?
  3. If _popen is defined as a macro itself, is there a chance my #define will fail? Should i use a "new" token like my_popen instead, for that reason or another?
  4. Did someone already do this job for me and made a good "portability header" file that i can use?
  5. Anything else i should be aware of?
like image 239
anatolyg Avatar asked Jan 30 '11 16:01

anatolyg


2 Answers

  1. Better to check for a windows-specific define (_WIN32 perhaps) because mingw won't have it either. popen() is standardised (it's a part of the Single UNIX® Specification v2)
  2. No; so long as the macro is defined before its first use it does not matter if _popen() is not defined until later.
  3. No; what you have is fine even if _popen is a macro.
  4. It's been done many times but I don't know of a freely-licensed version you can use.
like image 136
Phil Willoughby Avatar answered Nov 18 '22 01:11

Phil Willoughby


The way you are doing it is fine (with the #ifdef etc) but the macro that you test isn't. popen is something that depends on your operating system and not your compiler.

I'd go for something like

#if defined(_POSIX_C_SOURCE) && (_POSIX_C_SOURCE >= 2)
/* system has popen as expected */
#elif defined(YOUR_MACRO_TO DETECT_YOUR_OS)
# define popen _popen
# define pclose _pclose
#elif defined(YOUR_MACRO_TO DETECT_ANOTHER_ONE)
# define popen _pOpenOrSo
# define pclose _pclos
#else
# error "no popen, we don't know what to do"
#endif
like image 1
Jens Gustedt Avatar answered Nov 18 '22 00:11

Jens Gustedt