128
129
ctypes.byref(mem_struct),
129
130
ctypes.sizeof(mem_struct))
131
trace.note('Failed to GetProcessMemoryInfo()')
132
trace.note(gettext('Failed to GetProcessMemoryInfo()'))
133
134
info = {'PageFaultCount': mem_struct.PageFaultCount,
134
135
'PeakWorkingSetSize': mem_struct.PeakWorkingSetSize,
149
150
proc = win32process.GetCurrentProcess()
150
151
info = win32process.GetProcessMemoryInfo(proc)
152
trace.note('Cannot debug memory on win32 without ctypes'
153
trace.note(gettext('Cannot debug memory on win32 without ctypes'
156
157
# using base-2 units (see HACKING.txt).
157
trace.note('WorkingSize %7dKiB'
158
'\tPeakWorking %7dKiB\t%s',
158
trace.note(gettext('WorkingSize {0:>7}KiB'
159
'\tPeakWorking {1:>7}KiB\t{2}').format(
159
160
info['WorkingSetSize'] / 1024,
160
161
info['PeakWorkingSetSize'] / 1024,
164
165
trace.note('%s', message)
165
trace.note('WorkingSize %8d KiB', info['WorkingSetSize'] / 1024)
166
trace.note('PeakWorking %8d KiB', info['PeakWorkingSetSize'] / 1024)
167
trace.note('PagefileUsage %8d KiB', info.get('PagefileUsage', 0) / 1024)
168
trace.note('PeakPagefileUsage %8d KiB',
166
trace.note(gettext('WorkingSize %8d KiB'), info['WorkingSetSize'] / 1024)
167
trace.note(gettext('PeakWorking %8d KiB'), info['PeakWorkingSetSize'] / 1024)
168
trace.note(gettext('PagefileUsage %8d KiB'), info.get('PagefileUsage', 0) / 1024)
169
trace.note(gettext('PeakPagefileUsage %8d KiB'),
169
170
info.get('PeakPagefileUsage', 0) / 1024)
170
trace.note('PrivateUsage %8d KiB', info.get('PrivateUsage', 0) / 1024)
171
trace.note('PageFaultCount %8d', info.get('PageFaultCount', 0))
171
trace.note(gettext('PrivateUsage %8d KiB'), info.get('PrivateUsage', 0) / 1024)
172
trace.note(gettext('PageFaultCount %8d'), info.get('PageFaultCount', 0))
174
175
def get_console_size(defaultx=80, defaulty=25):
470
471
def get_app_path(appname):
471
"""Look up in Windows registry for full path to application executable.
472
r"""Look up in Windows registry for full path to application executable.
472
473
Typically, applications create subkey with their basename
473
474
in HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\
522
523
trace.mutter('Unable to set hidden attribute on %r: %s', path, e)
525
def _command_line_to_argv(command_line, single_quotes_allowed=False):
526
def _command_line_to_argv(command_line, argv, single_quotes_allowed=False):
526
527
"""Convert a Unicode command line into a list of argv arguments.
528
529
It performs wildcard expansion to make wildcards act closer to how they
536
537
:return: A list of unicode strings.
539
# First, spit the command line
538
540
s = cmdline.Splitter(command_line, single_quotes_allowed=single_quotes_allowed)
539
# Now that we've split the content, expand globs if necessary
542
# Bug #587868 Now make sure that the length of s agrees with sys.argv
543
# we do this by simply counting the number of arguments in each. The counts should
544
# agree no matter what encoding sys.argv is in (AFAIK)
545
# len(arguments) < len(sys.argv) should be an impossibility since python gets
546
# args from the very same PEB as does GetCommandLineW
549
# Now shorten the command line we get from GetCommandLineW to match sys.argv
550
if len(arguments) < len(argv):
551
raise AssertionError("Split command line can't be shorter than argv")
552
arguments = arguments[len(arguments) - len(argv):]
554
# Carry on to process globs (metachars) in the command line
555
# expand globs if necessary
540
556
# TODO: Use 'globbing' instead of 'glob.glob', this gives us stuff like
541
557
# '**/' style globs
543
for is_quoted, arg in s:
559
for is_quoted, arg in arguments:
544
560
if is_quoted or not glob.has_magic(arg):
557
573
if command_line is None:
558
574
raise ctypes.WinError()
559
575
# Skip the first argument, since we only care about parameters
560
argv = _command_line_to_argv(command_line)[1:]
561
if getattr(sys, 'frozen', None) is None:
562
# Invoked via 'python.exe' which takes the form:
563
# python.exe [PYTHON_OPTIONS] C:\Path\bzr [BZR_OPTIONS]
564
# we need to get only BZR_OPTIONS part,
565
# We already removed 'python.exe' so we remove everything up to and
566
# including the first non-option ('-') argument.
567
for idx in xrange(len(argv)):
568
if argv[idx][:1] != '-':
576
argv = _command_line_to_argv(command_line, sys.argv)[1:]
573
579
get_unicode_argv = None
583
def _pywin32_is_local_pid_dead(pid):
584
"""True if pid doesn't correspond to live process on this machine"""
586
handle = win32api.OpenProcess(1, False, pid) # PROCESS_TERMINATE
587
except pywintypes.error, e:
588
if e[0] == 5: # ERROR_ACCESS_DENIED
589
# Probably something alive we're not allowed to kill
591
elif e[0] == 87: # ERROR_INVALID_PARAMETER
596
is_local_pid_dead = _pywin32_is_local_pid_dead
597
elif has_ctypes and sys.platform == 'win32':
598
from ctypes.wintypes import BOOL, DWORD, HANDLE
599
_kernel32 = ctypes.windll.kernel32
600
_CloseHandle = ctypes.WINFUNCTYPE(BOOL, HANDLE)(
601
("CloseHandle", _kernel32))
602
_OpenProcess = ctypes.WINFUNCTYPE(HANDLE, DWORD, BOOL, DWORD)(
603
("OpenProcess", _kernel32))
604
def _ctypes_is_local_pid_dead(pid):
605
"""True if pid doesn't correspond to live process on this machine"""
606
handle = _OpenProcess(1, False, pid) # PROCESS_TERMINATE
608
errorcode = ctypes.GetLastError()
609
if errorcode == 5: # ERROR_ACCESS_DENIED
610
# Probably something alive we're not allowed to kill
612
elif errorcode == 87: # ERROR_INVALID_PARAMETER
614
raise ctypes.WinError(errorcode)
617
is_local_pid_dead = _ctypes_is_local_pid_dead