I'm an inexperienced Linux programmer and am trying to learn to use readlink()
based on this question and answer.
My call to readlink()
returns -1 and sets errno
to 2 (ENOENT
).
The code:
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include <errno.h>
#include <iostream>
#include <algorithm>
#include <cstdio>
int main(int argc, char* argv[])
{
char szTmp[100];
snprintf(szTmp, 100, "proc/%d/exe", getpid());
std::cout << "szTmp is " << szTmp << std::endl;
char executingFolder[500];
errno = 0;
int bytes = std::min(readlink(szTmp, executingFolder, 500), (ssize_t)499);
if (bytes > 0)
{
executingFolder[bytes] = '\0';
}
std::cout << "bytes is " << bytes << std::endl;
std::cout << "errno is " << errno;
if (ENOENT == errno)
{
std::cout << " ENOENT";
}
std::cout << std::endl;
std::cout << "Executing folder is \"" << executingFolder << "\"" << std::endl;
return 0;
}
The output:
(An example from one iteration since pid changes)
szTmp is proc/22272/exe
bytes is -1
errno is 2 ENOENT
Executing folder is ""
Things I have tried:
- After compilation:
sudo ./a.out
(thinking that directory access was restricted because of lack of permission). Result: unchanged behavior from./a.out
- SIGINT the program during execution, and verified that
/proc/<pid>/exe
exists. Result: it consistently exists for each run of the program. - Verified that the value of the target link is well within 499 chars.
Can someone please help identify the problem? Having read the readlink
man page and online descriptions, and the noted StackOverflow article, I am still unclear what is wrong.
Thank you.
proc/1234/exe
is a relative path.I think you want
/proc/%d/exe
, which is an absolute path, and correctly refers to the/proc
directory.Secondly, because
readlink()
will truncate the result in case the buffer is too small, you should consider the case where the return value is== bufsiz
to be an error, as truncation may have happened. You can't know.Also, "Executing folder" is not what
/proc/<pid>/exe
gives you./proc/<pid>/exe
is a symlink to the currently running executable (file), not a directory.