提问人:KaramJaber 提问时间:3/30/2022 最后编辑:KaramJaber 更新时间:3/30/2022 访问量:528
检查目录是否存在时,在 C 中S_ISDIR未解析的外部符号
Unresolved external symbol S_ISDIR in C upon checking if directory exist
问:
我在网上搜索了如何检查提供的路径是文件还是目录,并遇到了系统调用。stat
我尝试实现如下:
#include <sys/types.h>
#include <sys/stat.h>
int isDirectoryExists(const char *path)
{
struct stat stats;
stat(path, &stats);
// Check for file existence
if (S_ISDIR(stats.st_mode))
return 1;
return 0;
}
但是当我尝试在 Windows 上使用 Visual Studio 进行编译时,出现以下错误:
unresolved external symbol S_ISDIR referenced in function
我阅读了 stat 的文档,它确实提供了这个宏,但出于某种原因,我的环境正在识别它......有什么建议吗?
另一种解决方案是实现S_ISDIR正在做的事情:
stat(pathname, &sb);
if ((sb.st_mode & S_IFMT) == S_IFDIR) {
/* Handle directory */
}
答:
2赞
Jonathan Leffler
3/30/2022
#1
我遇到了 Microsoft 没有提供符合 POSIX 标准的 版本的问题。我有自己的标题,用于处理该问题(最早的日期为 1995 年,最后修改时间为 2013 年):<sys/stat.h>
sysstat.h
#ifndef SYSSTAT_H
#define SYSSTAT_H
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif /* HAVE_CONFIG_H */
#include "posixver.h" /* Not always quick enough */
#include <sys/types.h>
#include <sys/stat.h>
#ifdef _MSC_VER /* MS <sys/stat.h> uses this trigger */
typedef unsigned short mode_t; /* POSIX defines mode_t in <sys/types.h> */
#endif /* _MSCVER */
#ifndef S_IRWXU
/* POSIX-compliant defines omitted from sys/stat.h. */
/* Assume UNIX Version 7 header, more or less */
#ifndef S_IREAD
#define S_IREAD 0400
#endif /* S_IREAD */
#ifndef S_IWRITE
#define S_IWRITE 0200
#endif /* S_IWRITE */
#ifndef S_IEXEC
#define S_IEXEC 0100
#endif /* S_IEXEC */
#define S_IRUSR (S_IREAD)
#define S_IWUSR (S_IWRITE)
#define S_IXUSR (S_IEXEC)
#define S_IRGRP (S_IRUSR >> 3)
#define S_IWGRP (S_IWUSR >> 3)
#define S_IXGRP (S_IXUSR >> 3)
#define S_IROTH (S_IRUSR >> 6)
#define S_IWOTH (S_IWUSR >> 6)
#define S_IXOTH (S_IXUSR >> 6)
#define S_IRWXU (S_IRUSR|S_IWUSR|S_IXUSR)
#define S_IRWXG (S_IRGRP|S_IWGRP|S_IXGRP)
#define S_IRWXO (S_IROTH|S_IWOTH|S_IXOTH)
#ifdef _MSC_VER /* MS <sys/stat.h> uses this trigger */
/* MS Windows does not support SUID, SGID or sticky bit */
#ifndef S_ISUID
#define S_ISUID 0
#endif
#ifndef S_ISGID
#define S_ISGID 0
#endif
#ifndef S_ISVTX
#define S_ISVTX 0
#endif
#else
#ifndef S_ISUID
#define S_ISUID 04000
#endif
#ifndef S_ISGID
#define S_ISGID 02000
#endif
#ifndef S_ISVTX
#define S_ISVTX 01000
#endif
#endif /* _MSCVER */
#endif /* S_IRWXU */
/*
** Assume the S_IFMT, S_IFDIR, S_IFCHR, S_IFREG are defined, which is OK
** for Windows under MS Visual Studio 2008 Express. Conditional testing
** not perfect: it assumes pragmatically that S_ISFIFO() is undefined if
** S_IFIFO() is undefined, for example.
*/
/* POSIX file type test macros */
#ifndef S_ISDIR
#define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR)
#endif /* S_ISDIR */
#ifndef S_ISCHR
#define S_ISCHR(m) (((m) & S_IFMT) == S_IFCHR)
#endif /* S_ISCHR */
#ifndef S_ISREG
#define S_ISREG(m) (((m) & S_IFMT) == S_IFREG)
#endif /* S_ISREG */
/* Not in MS Visual Studio 2008 Express */
#ifdef S_IFBLK
#ifndef S_ISBLK
#define S_ISBLK(m) (((m) & S_IFMT) == S_IFBLK)
#endif /* S_ISBLK */
#else
#define S_ISBLK(m) (0)
#endif /* S_IFBLK */
/* Not in Version 7 Unix, but we'll define it anyway */
#ifdef S_IFIFO
#ifndef S_ISFIFO
#define S_ISFIFO(m) (((m) & S_IFMT) == S_IFIFO)
#endif /* S_ISFIFO */
#else
#define S_ISFIFO(m) (0)
#endif /* S_IFIFO */
/* Not in POSIX 1003.1-1990, but we'll define it anyway */
#ifdef S_IFLNK
#ifndef S_ISLNK
#define S_ISLNK(m) (((m) & S_IFMT) == S_IFLNK)
#endif /* S_ISLNK */
#else
#define S_ISLNK(m) (0)
#endif /* S_IFLNK */
/* Not in POSIX 1003.1-1990, but we'll define it anyway */
#ifdef S_IFSOCK
#ifndef S_ISSOCK
#define S_ISSOCK(m) (((m) & S_IFMT) == S_IFSOCK)
#endif /* S_ISSOCK */
#else
#define S_ISSOCK(m) (0)
#endif /* S_IFSOCK */
#endif /* SYSSTAT_H */
标头包含:posixver.h
#ifndef JLSS_ID_POSIXVER_H
#define JLSS_ID_POSIXVER_H
/*
** Include this file before including system headers. By default, with
** C99 support from the compiler, it requests POSIX 2008 support. With
** C89 support only, it requests POSIX 1997 support. Override the
** default behaviour by setting either _XOPEN_SOURCE or _POSIX_C_SOURCE.
*/
/* _XOPEN_SOURCE 700 is loosely equivalent to _POSIX_C_SOURCE 200809L */
/* _XOPEN_SOURCE 600 is loosely equivalent to _POSIX_C_SOURCE 200112L */
/* _XOPEN_SOURCE 500 is loosely equivalent to _POSIX_C_SOURCE 199506L */
#if !defined(_XOPEN_SOURCE) && !defined(_POSIX_C_SOURCE)
#if defined(__cplusplus)
#define _XOPEN_SOURCE 700 /* SUS v4, POSIX 1003.1 2008/13 (POSIX 2008/13) */
#elif __STDC_VERSION__ >= 199901L
#define _XOPEN_SOURCE 700 /* SUS v4, POSIX 1003.1 2008/13 (POSIX 2008/13) */
#else
#define _XOPEN_SOURCE 500 /* SUS v2, POSIX 1003.1 1997 */
#endif /* __STDC_VERSION__ */
#endif /* !_XOPEN_SOURCE && !_POSIX_C_SOURCE */
#endif /* JLSS_ID_POSIXVER_H */
明确地说:你可以随心所欲地使用这段代码,我不需要署名。
评论
S_ISDIR
<sys/stat.h>
#ifndef S_ISDIR
#define S_ISDIR(s) ((s).st_mode & S_IFDIR)
#endif
stat
stat
stats.st_mode