Моя программа работает в среде Linux, скомпилированной с gcc версии 4.4.7.Почему realpath() возвращает ошибку EEXIST?
Я использую realpath()
для «canonicalize» путей к файлам. Путь каждого каталога и файла, который я кормлю до realpath()
, определенно существует, что, конечно же, необходимо для корректной работы realpath()
.
Однако иногда realpath()
сбой кода ошибки 17, имя EEXIST
, строка описание «Файл существует».
Это меня озадачивает. Конечно, он существует, я кричу на realpath()
. Но realpath()
не тронут моим разглагольствованием.
Документация для realpath()
по адресу http://pubs.opengroup.org/onlinepubs/009695399/functions/realpath.html содержит ошибки, которые приводят к сбою, но EEXIST
не является одним из них.
Почему realpath()
терпят неудачу таким образом?
Примеры каталогов и пути к файлам, которые вызывают EEXIST
ошибку:
- Абсолютный путь к каталогу:
/alpha/bravo/charlie/delta
- Абсолютный путь к файлу:
/alpha/bravo/charlie/foo.txt
- относительный путь к файлу :
../../charlie/foo.txt
- путь к файлу, который имеет дополнительную точку в нем:
/alpha/bravo/Charlie/./foo.txt
Но эти примеры не являются окончательными, поскольку другие файлы с такими же шаблонами и в тех же каталогах будут удовлетворены.
Похоже, что нет никаких рифм или причин тому, что каталог или файл вызовет ошибку EEXIST
. Ошибка обычно возникает только для первого пути к файлу, который я пытаюсь выполнить канонизацию, а затем не для последующих. Однако я не могу обманывать его, просто пытаюсь снова канонизировать этот первый файл; ошибка будет продолжаться только для этого.
Программа сниппет:
#include <string>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <limits.h> // for PATH_MAX
using std;
string PathCanonicalize(string const & path)
{
string result;
char szResult[ PATH_MAX ];
::realpath(path.c_str(), szResult);
if (errno == EEXIST)
{
// Why?
cerr << "realpath: error code " << errno << ", " << ::strerror(errno) << ": '" << path << "'. Of course the file exists!" << endl;
result = path;
}
else if (errno)
{
cerr << "realpath: error code " << errno << ", " << ::strerror(errno) << ": '" << path << "'" << endl;
result = path;
}
else
{
result = szResult;
}
return result;
}
Это багги код, вы должны * только * проверить 'errno', если функция возвращает NULL. –