Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

OSError: [WinError 0] The operation completed successfully #1877

Closed
rhazz opened this issue Nov 13, 2020 · 3 comments · Fixed by #1887
Closed

OSError: [WinError 0] The operation completed successfully #1877

rhazz opened this issue Nov 13, 2020 · 3 comments · Fixed by #1887

Comments

@rhazz
Copy link

rhazz commented Nov 13, 2020

Platform

  • { Windows nt 2012 }
  • { psutil version: 5.7.3" }
  • { python 3.8.2}

Bug description
Version 5.7.3 again presented this error corrected in version 3.6.7, I solved my problem by going back to version 3.6.7 ... the error ran on windows server 2012 R2 Datacenter virtualized by VMware

Test results


import psutil
from datetime import datetime, timedelta
processName='chrome'
listOfProcessObjects = []

for proc in psutil.process_iter():
    try:
        pinfo = proc.as_dict(attrs=['pid', 'name', 'create_time'])
        pinfo['started'] = datetime.fromtimestamp(pinfo['create_time'])
          # Check if process name contains the given name string.
        if pinfo['name'] and processName.lower() in pinfo['name'].lower():
            listOfProcessObjects.append(pinfo)
    except (psutil.PermissionError, psutil.NoSuchProcess, psutil.AccessDenied, psutil.ZombieProcess):
        pass

print(listOfProcessObjects)
Traceback (most recent call last):
  File ".\teste.py", line 6, in <module>
    for proc in psutil.process_iter():
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\__init__.py", line 1457, in process_iter
    yield add(pid)
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\__init__.py", line 1432, in add
    proc = Process(pid)
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\__init__.py", line 346, in __init__
    self._init(pid)
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\__init__.py", line 373, in _init
    self.create_time()
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\__init__.py", line 723, in create_time
    self._create_time = self._proc.create_time()
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\_pswindows.py", line 681, in wrapper
    raise convert_oserror(err, pid=self.pid, name=self._name)
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\_pswindows.py", line 671, in convert_oserr
or
    raise exc
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\_pswindows.py", line 679, in wrapper
    return fun(self, *args, **kwargs)
  File "C:\Users\user10\AppData\Roaming\Python\Python38\site-packages\psutil\_pswindows.py", line 933, in create_time
    user, system, created = cext.proc_times(self.pid)
OSError: [WinError 0] The operation completed successfully: '(originated from OpenProcess)'
 }
@alxchk
Copy link
Contributor

alxchk commented Jan 7, 2021

I have same thing with psutil 5.8.0/5.8.1 (from git and from pip).
But my setup is a bit... non-standard. I.e. it works ok if I run this from python 3.8 installed from the system, but failed
when python is embedded. Also such thing is not happened when executed from the Administrator. I.e. it's very likely
failed because of access denied.

Here I'm calling proc_times, but this actually happens with other cext.proc_ things. as well

>>> for p in psutil.pids():
>>>     try:
>>>         print(p, psutil._pswindows.cext.proc_times(p))
>>>     except Exception as e:
>>>         print("Failed", p, e)
>>> 
Failed 0 [Errno 13] assume access denied (originated from automatically set for PID 0)
Failed 4 [WinError 0] The operation completed successfully: '(originated from OpenProcess)'
Failed 248 [WinError 0] The operation completed successfully: '(originated from OpenProcess)'
Failed 316 [WinError 0] The operation completed successfully: '(originated from OpenProcess)'
...

788 (0.671875, 0.84375, 1610045289.4229844)
1416 (0.03125, 0.0625, 1610045355.533336)
1484 (0.0, 0.03125, 1610044217.9698591)
...

From the same context, with OpenProcess imported using ctypes.

>>> OpenProcess(0x1000, False, 316)
>>> get_last_error()
5
>>> psutil._pswindows.cext.proc_exe(316)
'\\Device\\HarddiskVolume2\\Windows\\System32\\csrss.exe'
>>> psutil._pswindows.cext.proc_environ(316)
Traceback (most recent call last):
  File "<console>", line 1, in <module>
OSError: [WinError 0] The operation completed successfully: '(originated from OpenProcess)'

Which is a bit weird, as I'm seeing checks in the source code.

The only idea I have - there is some race with GetLastError. I.e. you are checking GetLastError immediately after OpenProcess,
(It's that, because you call PyErr_SetFromOSErrnoWithSyscall only when there is access denied error accroding to GetLastError) and then again in PyErr_SetFromOSErrnoWithSyscall. Maybe something happens between those two calls that makes SetLastError for the thread?

UPDATE:
It looks like sprintf alters GetLastError with some windows runtimes =
(Well, that's why MSDN asks to check GetLastError immediately after system call)

diff --git a/psutil/_psutil_common.c b/psutil/_psutil_common.c
index fae8d970..eee8f4d3 100644
--- a/psutil/_psutil_common.c
+++ b/psutil/_psutil_common.c
@@ -83,8 +83,7 @@ PyErr_SetFromOSErrnoWithSyscall(const char *syscall) {
     char fullmsg[1024];
 
 #ifdef PSUTIL_WINDOWS
-    sprintf(fullmsg, "(originated from %s)", syscall);
-    PyErr_SetFromWindowsErrWithFilename(GetLastError(), fullmsg);
+    PyErr_SetFromWindowsErrWithFilename(GetLastError(), syscall);
 #else
     PyObject *exc;
     sprintf(fullmsg, "%s (originated from %s)", strerror(errno), syscall);
>>> import psutil
>>> psutil._pswindows.cext.proc_times(316)
Traceback (most recent call last):
  File "<console>", line 1, in <module>
PermissionError: [WinError 5] Access denied: 'OpenProcess'

UPDATE:
I decompiled __stdio_common_vsprintf from ucrtbase.dll and it's really calls GetLastError/SetLastError

@Anton-V-K
Copy link

Anton-V-K commented Oct 24, 2021

The test script may fail with OSError: [WinError 0] The operation completed successfully on Windows 7 SP1 64-bit (Russian) with Python 3.8.10 32-bit and psutil 5.8.0:

Traceback (most recent call last):
  File "test_psutil.py", line 8, in <module>
    for proc in psutil.process_iter():
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\__init__.py", line 1439, in process_iter
    yield add(pid)
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\__init__.py", line 1414, in add
    proc = Process(pid)
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\__init__.py", line 326, in __init__
    self._init(pid)
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\__init__.py", line 354, in _init
    self.create_time()
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\__init__.py", line 710, in create_time
    self._create_time = self._proc.create_time()
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\_pswindows.py", line 681, in wrapper
    raise convert_oserror(err, pid=self.pid, name=self._name)
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\_pswindows.py", line 671, in convert_oserror
    raise exc
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\_pswindows.py", line 679, in wrapper
    return fun(self, *args, **kwargs)
  File "C:\Program Files (x86)\Python38-32\lib\site-packages\psutil\_pswindows.py", line 933, in create_time
    user, system, created = cext.proc_times(self.pid)
OSError: [WinError 0] Операция успешно завершена: '(originated from OpenProcess)'

@giampaolo
Copy link
Owner

This is supposed to be fixed by #1904 (still unreleased).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants