在 CentOS 上说到 readdir,通常有两种语境:
readdir() / readdir_r()下面分别说明怎么“兼容旧版本”。
readdir() 而不是 readdir_r()readdir_r(线程安全)readdir_r 被标记为 deprecated,官方建议直接用 readdir()✅ 兼容写法(推荐)
#include <dirent.h>
DIR *dir = opendir(path);
struct dirent *entry;
while ((entry = readdir(dir)) != NULL) {
// 兼容所有 CentOS 版本
}
closedir(dir);
如果你必须支持非常老的 CentOS(如 CentOS 5/6)且要求线程安全,可以用宏控制:
#if defined(__GLIBC__) && (__GLIBC__ < 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ < 24))
struct dirent entry;
struct dirent *result;
readdir_r(dir, &entry, &result);
#else
struct dirent *entry = readdir(dir);
#endif
不同 CentOS 版本中 struct dirent 可能不同:
| 字段 | 说明 |
|---|---|
d_name |
一定存在 |
d_type |
CentOS 6+ 才有(ext4/xfs) |
d_ino |
一般有 |
✅ 兼容写法
if (entry->d_type != DT_UNKNOWN) {
// 可用
} else {
// 用 stat() 兜底
}
-D_GNU_SOURCEgcc -D_GNU_SOURCE -o test test.c
避免某些旧 glibc 下函数不可用。
gcc -static test.c -o test
⚠️ 体积大、不支持某些 NSS
| CentOS | glibc |
|---|---|
| 5 | 2.5 |
| 6 | 2.12 |
| 7 | 2.17 |
| 8 | 2.28 |
⚠️ 不要手动升级 glibc,否则系统容易崩
readdirfor f in "$dir"/*; do
echo "$f"
done
或 find,这本身是跨版本兼容的。
✅ 最稳妥的兼容方案:
readdir()readdir_rd_type如果你能说清楚:
我可以给你更精确的代码或解决方案。