基于蒂博d的答案一个完整的功能:
char *do_get_symlink(char *path, struct stat attr) {
/*
* a much more elegant solution would be to use realpath(),
* but it is 35% slower and produces different results on /proc
*/
if (S_ISLNK(attr.st_mode)) {
/*
* st_size appears to be an unreliable source of the link length
* PATH_MAX is artificial and not used by the GNU C Library
*/
ssize_t length;
size_t buffer = 128;
char *symlink = malloc(sizeof(char) * buffer);
if (!symlink) {
fprintf(stderr, "%s: malloc(): %s\n", program, strerror(errno));
return strdup("");
}
/*
* if readlink() fills the buffer, double it and run again
* even if it equals, because we need a character for the termination
*/
while ((length = readlink(path, symlink, buffer)) > 0 && (size_t)length >= buffer) {
buffer *= 2;
symlink = realloc(symlink, buffer);
if (!symlink) {
fprintf(stderr, "%s: realloc(): %s\n", program, strerror(errno));
return strdup("");
}
}
if (length < 0) {
fprintf(stderr, "%s: readlink(%s): %s\n", program, path, strerror(errno));
free(symlink);
return strdup("");
}
symlink[length] = '\0';
return symlink;
}
/*
* the entry is not a symlink
* strdup is needed to keep the output free-able
*/
return strdup("");
}
来源
2016-03-07 22:14:11
amq
我经常'path'缓冲区'readlink'用'memset'之前,而不是明确的。所以即使在'readlink'失败时,'path'也有一个明显的NUL终止的字符串。失败时,你的'pathlength'是-1,'buff [pathlength]'赋值是*未定义行为*(如果不幸的话,[太阳系可能会崩溃](http://stackoverflow.com/a/25636788/841108) – 2014-09-12 21:48:18