ntmemoryapi 1.6.3__tar.gz → 1.7.1__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.3
2
2
  Name: ntmemoryapi
3
- Version: 1.6.3
3
+ Version: 1.7.1
4
4
  Summary: Simple library for Windows to manipulate process virtual memory with stelthy syscall wraps
5
5
  Author: Xenely
6
6
  Requires-Dist: psutil>=7.1.3
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "ntmemoryapi"
3
- version = "1.6.3"
3
+ version = "1.7.1"
4
4
  description = "Simple library for Windows to manipulate process virtual memory with stelthy syscall wraps"
5
5
  authors = [
6
6
  {name = "Xenely"}
@@ -20,7 +20,6 @@ syscall_wrapper = DirectSyscallWrapper()
20
20
 
21
21
  PROCESS_ID = 1
22
22
  PROCESS_NAME = 2
23
- PROCESS_USERNAME = 4
24
23
 
25
24
 
26
25
  # ==-------------------------------------------------------------------== #
@@ -238,28 +237,21 @@ _nt_protect_virtual_memory = syscall_wrapper.wrap("NtProtectVirtualMemory", resu
238
237
  # ==-------------------------------------------------------------------== #
239
238
  # Functions #
240
239
  # ==-------------------------------------------------------------------== #
241
- def list_processes(include_process_information: int = PROCESS_ID | PROCESS_NAME | PROCESS_USERNAME, current_username_only: bool = True) -> list[dict[str, int | str]]:
240
+ def list_processes(include_process_information: int = PROCESS_ID | PROCESS_NAME) -> list[dict[str, int | str]]:
242
241
  """List all of the currently active system processes."""
243
242
 
244
243
  # If `include_id` and `include_name` disabled both
245
244
  if not include_process_information & PROCESS_ID and not include_process_information & PROCESS_NAME:
246
245
  raise Exception("Unable to disable ID and name including at once")
247
246
 
248
- # Current process username
249
- current_username = psutil.Process().username()
250
-
251
247
  # Result list of processes
252
- processes = list()
248
+ processes = []
253
249
 
254
250
  # Process iteration
255
251
  for process in psutil.process_iter():
256
252
 
257
- # If process started not from current username
258
- if current_username_only and process.username() != current_username:
259
- continue
260
-
261
253
  # Save process to list
262
- process_dict = dict()
254
+ process_dict = {}
263
255
 
264
256
  # If process ID including required
265
257
  if include_process_information & PROCESS_ID:
@@ -269,10 +261,6 @@ def list_processes(include_process_information: int = PROCESS_ID | PROCESS_NAME
269
261
  if include_process_information & PROCESS_NAME:
270
262
  process_dict |= {"name": process.name()}
271
263
 
272
- # If process username including required
273
- if include_process_information & PROCESS_USERNAME:
274
- process_dict |= {"username": process.username()}
275
-
276
264
  # Save process information to list
277
265
  processes.append(process_dict)
278
266
 
@@ -289,17 +277,17 @@ class Process:
289
277
  # Methods #
290
278
  # ==-------------------------------------------------------------------== #
291
279
 
292
- def __init__(self, name_or_pid: int | str, access: int = PROCESS_ALL_ACCESS, current_username_only: bool = True) -> None:
280
+ def __init__(self, name_or_pid: int | str, access: int = PROCESS_ALL_ACCESS) -> None:
293
281
  """Initialize instance to manipulate process."""
294
282
 
295
283
  # Open process by it's ID or it's name
296
284
  match name_or_pid:
297
285
 
298
- case pid if type(name_or_pid) is int:
299
- self.handle, self.name, self.pid = self.__init_with_pid(pid, access, current_username_only)
286
+ case int():
287
+ self.handle, self.pid, self.name = self.__init_with_pid(name_or_pid, access)
300
288
 
301
- case name if type(name_or_pid) is str:
302
- self.handle, self.name, self.pid = self.__init_with_name(name, access, current_username_only)
289
+ case str():
290
+ self.handle, self.pid, self.name = self.__init_with_name(name_or_pid, access)
303
291
 
304
292
  case _:
305
293
  raise Exception("Invalid `pid_or_name` argument value, have to be `int` or `str` type")
@@ -331,7 +319,7 @@ class Process:
331
319
  raise Exception("Unable to create snapshot to iterate process modules")
332
320
 
333
321
  # Result list of process modules
334
- process_modules = list()
322
+ process_modules = []
335
323
 
336
324
  # Process modules enumeration
337
325
  try:
@@ -364,11 +352,11 @@ class Process:
364
352
 
365
353
  return process_modules
366
354
 
367
- def list_memory_regions(self, allowed_states: list[int] = list(), allowed_protects: list[int] = list(), allowed_types: list[int] = list(), memory_regions_filter: typing.Callable[[MEMORY_BASIC_INFORMATION], bool] | None = None) -> list[MEMORY_BASIC_INFORMATION]:
355
+ def list_memory_regions(self, allowed_states: list[int] = [], allowed_protects: list[int] = [], allowed_types: list[int] = [], memory_regions_filter: typing.Callable[[MEMORY_BASIC_INFORMATION], bool] | None = None) -> list[MEMORY_BASIC_INFORMATION]:
368
356
  """List all of the aviable process memory regions."""
369
357
 
370
358
  # Result list of memory regions
371
- memory_regions = list()
359
+ memory_regions = []
372
360
 
373
361
  # Iterate all of the process memory regions
374
362
  current_address = 0
@@ -487,7 +475,7 @@ class Process:
487
475
 
488
476
  return memory_old_protect.value or 0
489
477
 
490
- def pattern_scan(self, pattern: str, allowed_states: list[int] = [MEM_COMMIT], allowed_protects: list[int] = [PAGE_READWRITE], allowed_types: list[int] = list(), start_address: int | None = None, end_address: int | None = None, return_first: int | None = None, memory_regions_filter: typing.Callable[[MEMORY_BASIC_INFORMATION], bool] | None = None) -> list[int]:
478
+ def pattern_scan(self, pattern: str, allowed_states: list[int] = [MEM_COMMIT], allowed_protects: list[int] = [PAGE_READWRITE], allowed_types: list[int] = [], start_address: int | None = None, end_address: int | None = None, return_first: int | None = None, memory_regions_filter: typing.Callable[[MEMORY_BASIC_INFORMATION], bool] | None = None) -> list[int]:
491
479
  """Scan process and return address that validates given pattern hex byte mask, use `??` to wildcard byte, for example - "14 00 00 00 DB FF ?? ?? FF FF 00 00"."""
492
480
 
493
481
  # Validate given pattern
@@ -504,7 +492,7 @@ class Process:
504
492
  raise Exception("Invalid pattern: `%s`" % pattern)
505
493
 
506
494
  # Result list of found addresses
507
- found_addresses = list()
495
+ found_addresses = []
508
496
 
509
497
  # iterate memory regions and finding addresses at them
510
498
  for region in self.list_memory_regions(allowed_states, allowed_protects, allowed_types, memory_regions_filter):
@@ -758,11 +746,11 @@ class Process:
758
746
  # ==-------------------------------------------------------------------== #
759
747
  # Private methods #
760
748
  # ==-------------------------------------------------------------------== #
761
- def __init_with_pid(self, pid: int, access: int, current_username_only: bool, process_name: str | None = None) -> int:
749
+ def __init_with_pid(self, pid: int, access: int, listed_processes: list[dict[str, int | str]] | None = None) -> tuple[int, int, str]:
762
750
  """Open process handle by it's ID with desired access."""
763
751
 
764
- # Iterate all of the processes if name not defined
765
- for process in list_processes(current_username_only=current_username_only):
752
+ # Iterate all of the processes
753
+ for process in listed_processes if listed_processes is not None else list_processes():
766
754
 
767
755
  # If process have a reqired name
768
756
  if process["id"] == pid:
@@ -790,16 +778,16 @@ class Process:
790
778
  else:
791
779
  raise Exception("NtOpenProcess failed with status: 0x%s" % hex(result)[2:].upper())
792
780
 
793
- return handle.value, process_name, pid
781
+ return handle.value, pid, process_name
794
782
 
795
- def __init_with_name(self, name: str, access: int, current_username_only: bool) -> int:
783
+ def __init_with_name(self, name: str, access: int) -> tuple[int, int, str]:
796
784
  """Open process hanle by it's name with desired access."""
797
785
 
798
786
  # Iterate all of the processes using snapshot
799
- for process in list_processes(current_username_only=current_username_only):
787
+ for process in (listed_processes := list_processes()):
800
788
 
801
789
  # If process have a reqired name
802
790
  if process["name"].lower() == name.strip().lower():
803
- return self.__init_with_pid(process["id"], access, current_username_only, process["name"])
791
+ return self.__init_with_pid(process["id"], access, listed_processes)
804
792
 
805
793
  raise Exception("Process with `%s` name not found" % name)
File without changes