10

Questions

  • Are the posix macros S_ISREG, S_ISDIR etc linux only? I need to find out because i am trying to compile CURL and it is trying to use them on windows
  • What include file can i use to access them on windows.

This is the offending code

/*we ignore file size for char/block devices, sockets etc*/
if(S_ISREG(fileinfo.st_mode))
   uploadfilesize= fileinfo.st_size;
}

and it causes an error

error LNK2019: unresolved external symbol _S_ISREG referenced in function _operate file tool_operate.obj

They are referenced in the following questions

Apparently S_ISREG() is part of a bunch of posix macros and is apparently supposed to tell us if a file is a "regular file" but all the examples I found had linux specific include files.

Community
  • 1
  • 1
Dr Deo
  • 4,650
  • 11
  • 43
  • 73
  • "Are the posix macros S_ISREG, S_ISDIR etc linux only?" No, you say it yourself in that question: "posix macros". They are on every POSIX-compliant system. – Some programmer dude Jun 28 '12 at 06:36
  • Wouldn't it be easier to get a pre-compiled Windows version? Shouldn't be too hard to find. Otherwise, how do you configure CURL for building? What environment (Visual Studio, Cygwin, MinGW?) – Some programmer dude Jun 28 '12 at 06:38
  • Funnily enough, nobody seems to have noticed that the link error is about the underscore-prefixed _S_ISREG, which is why curl's #define does not fire: most likely S_ISREG is already defined and references _S_ISREG. My guess is that including would enable it to compile. – alvherre Mar 04 '16 at 20:32

4 Answers4

14

Currently curl 7.21.5 defines in setup.h this:

#if !defined(S_ISREG) && defined(S_IFMT) && defined(S_IFREG)
#define S_ISREG(m) (((m) & S_IFMT) == S_IFREG)
#endif
Oliver Zendel
  • 2,695
  • 34
  • 29
5

After having inspected Microsoft's sys/stat.h, I found that the following modification of @OliverZendel's answer worked for me, with Visual Studio 2017, and hopefully on other compilers as well:

// Windows does not define the S_ISREG and S_ISDIR macros in stat.h, so we do.
// We have to define _CRT_INTERNAL_NONSTDC_NAMES 1 before #including sys/stat.h
// in order for Microsoft's stat.h to define names like S_IFMT, S_IFREG, and S_IFDIR,
// rather than just defining  _S_IFMT, _S_IFREG, and _S_IFDIR as it normally does.
#define _CRT_INTERNAL_NONSTDC_NAMES 1
#include <sys/stat.h>
#if !defined(S_ISREG) && defined(S_IFMT) && defined(S_IFREG)
  #define S_ISREG(m) (((m) & S_IFMT) == S_IFREG)
#endif
#if !defined(S_ISDIR) && defined(S_IFMT) && defined(S_IFDIR)
  #define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR)
#endif
Some Guy
  • 405
  • 8
  • 15
3

On windows try adding the underscore (_S_ISREG). In MinGW's lib the S_ISREG macro is also accessible in <sys/stat.h>

Maybe you should just check your configuration macros.

David L.
  • 2,095
  • 23
  • 23
Viktor Latypov
  • 14,289
  • 3
  • 40
  • 55
  • its not my code. Its part of curl code that generates errors during link step in tool_operate.c . – Dr Deo Jun 28 '12 at 06:21
  • What include file is needed or what library should be linked? – Dr Deo Jun 28 '12 at 06:25
  • Where did you find _S_ISREG ? Is this MinGW specific? VS2010 does not have it – Oliver Zendel Mar 14 '14 at 12:24
  • S_ISREG is an emulation of POSIX macro. For Win32 one should use MSVC/MSDN-specified APIs. I've found the underscore using a text-mode search in all of the MinGW's headers. – Viktor Latypov Mar 14 '14 at 15:22
  • I guess the underscore is in MSVC's linker (.C file compiled with cdecl convention will use underscores in symbol names). – Tomasz Gandor Oct 07 '16 at 13:36
  • 1
    After having inspected Microsoft's sys/stat.h for VS2017, it appears to me that neither S_ISREG nor _S_ISREG will be defined by it. However, enough constants like _S_IFMT and _S_IFREG are defined (and also S_IFMT and S_IFREG if _CRT_INTERNAL_NONSTDC_NAMES is #defined to 1) to allow you to define your own S_ISREG. See my answer below. – Some Guy Jun 14 '20 at 11:26
3

No such thing on windows, you can use the FindFirstFile, FindNextFile win32 api, the return structure contains something similar but not the same.

If you use gcc/mingw library they have a stat() simulation. You need to include sys/stat.h for that macro.

pizza
  • 7,296
  • 1
  • 25
  • 22
  • 1
    I have the same S_ISREG undefine problem, but I don't understand the answer. I can see that sys/stat.h is already being included in setup_once.h, which should be included by setup.h already. Exactly what do I need to do to resolve this? – M W Aug 07 '12 at 18:45
  • which compiler you are using? – pizza Aug 07 '12 at 22:34
  • MSVC. I got it to compiled by moving the #include setup_once.h statements right before the S_ISREG definition so it will pick up the S_IFREG defn. Not sure if it's the right way to fix. – M W Aug 08 '12 at 15:08
  • if you use MSVC, you should use the windows API instead of the unix stat(). e.g.http://msdn.microsoft.com/en-us/library/windows/desktop/aa364428%28v=vs.85%29.aspx – pizza Aug 08 '12 at 19:39
  • To be clear, sys/stat.h and the stat function do exist on Windows (at least VS2017). What's missing is the S_ISREG macros (and similar macros like S_ISDIR). However, it is possible to add them yourself. See my answer below. If you can do this in a header file that includes sys/stat.h (e.g. "mystat.h"), then you can use portable code using the stat function in your source files, without having to do an 'ifdef' for operating-system-specific APIs like FindFirstFile each time you need to check file status. (It is puzzling that Microsoft included sys/stat.h but only some of its contents.) – Some Guy Jun 15 '20 at 02:27