cat
cat

Reputation: 4020

What's os.geteuid() do?

I was trying to debug a Python 2 script running on Raspbian (Raspberry Pi flavoured Debian Linux) which had code like

euid = os.geteuid()
if euid != 0:
    print("you must be root!")
    exit(1)

It seemed like, in the user's environment, euid would sometimes be nonzero even if the script was called with sudo.

To investigate whether this was actually the case, I tried to figure out what os.geteuid() is actually doing.

Since the os module is pretty OS-specific by its nature, the source doesn't actually have a clear definition for os.geteuid().

I also tried hg cloneing the source and compiling it, then using inspect.findsource(os.geteuid), but:

TypeError: <built-in function geteuid> is not a module, class, method, function, traceback, frame, or code object

It's... a builtin? Then "geteuid" in dir(__import__("__builtin__")) should be True, but it isn't.

Is geteuid's definition hidden because it could be spoofed into returning the wrong thing (and that would be bad)? Where can I see these sorts of functions' actual source?

Upvotes: 0

Views: 952

Answers (1)

cat
cat

Reputation: 4020

ASCII stupid question, get a stupid ANSI.


I did try full-text searching the source, but apparently I used the wrong command the first time and gave up.

$ grep -rnw '.' -e "geteuid"
./Misc/setuid-prog.c:129:    uid_t euid = geteuid();
./Lib/site.py:209:    if hasattr(os, "getuid") and hasattr(os, "geteuid"):
./Lib/site.py:211:        if os.geteuid() != os.getuid():
./Lib/test/test_shutil.py:84:    @unittest.skipIf(hasattr(os, 'geteuid') and os.geteuid() == 0,
./Lib/test/test_httpservers.py:339:            if os.name == 'posix' and os.geteuid() != 0:
./Lib/test/test_httpservers.py:395:@unittest.skipIf(hasattr(os, 'geteuid') and os.geteuid() == 0,
./Lib/test/test_spwd.py:8:@unittest.skipUnless(hasattr(os, 'geteuid') and os.geteuid() == 0,
./Lib/test/test_posix.py:44:                             "getegid", "geteuid", "getgid", "getgroups",
./Lib/test/test_argparse.py:1532:@unittest.skipIf(hasattr(os, 'geteuid') and os.geteuid() == 0,
Binary file ./Lib/tarfile.py matches
./Lib/rexec.py:148:                      'getcwd', 'getuid', 'getgid', 'geteuid', 'getegid')
Binary file ./Modules/posixmodule.o matches
./Modules/posixmodule.c:4047:"geteuid() -> euid\n\n\
./Modules/posixmodule.c:4053:    return _PyInt_FromUid(geteuid());
./Modules/posixmodule.c:8944:    {"geteuid",         posix_geteuid, METH_NOARGS, posix_geteuid__doc__},
./Doc/library/rexec.rst:234:   'times', 'uname', 'getpid', 'getppid', 'getcwd', 'getuid', 'getgid', 'geteuid',
./Doc/library/os.rst:136:.. function:: geteuid()
Binary file ./python matches
Binary file ./libpython2.7.a matches

./Modules/posixmodule.c:4053, indeed:

#ifdef HAVE_GETEUID
PyDoc_STRVAR(posix_geteuid__doc__,
"geteuid() -> euid\n\n\
Return the current process's effective user id.");

static PyObject *
posix_geteuid(PyObject *self, PyObject *noargs)
{
    return _PyInt_FromUid(geteuid());
}
#endif

I don't know what I expected, subprocess.check_output(["id"])?

It uses the C standard library, it's never wrong.

Upvotes: 1

Related Questions