mirror of
https://github.com/hyugogirubato/KeyDive.git
synced 2026-07-16 02:44:22 +02:00
release v3.0.0
This commit is contained in:
@@ -0,0 +1,114 @@
|
||||
import re
|
||||
|
||||
from typing import List, Optional, Tuple
|
||||
|
||||
|
||||
class Vendor:
|
||||
"""
|
||||
Represents a vendor-specific configuration including process name, minimum SDK version,
|
||||
OEM versioning information, and the name of a related native library.
|
||||
|
||||
This class is used to identify vendor-specific behaviors on Android devices and provides
|
||||
regex-based helpers for pattern matching against processes and libraries.
|
||||
"""
|
||||
|
||||
def __init__(
|
||||
self,
|
||||
process: str,
|
||||
min_sdk: int,
|
||||
min_oem: Tuple[int, str],
|
||||
library: str
|
||||
):
|
||||
"""
|
||||
Initializes a Vendor instance with identifying details.
|
||||
|
||||
Args:
|
||||
process (str): The name of the process to identify for the vendor (can be pattern-based).
|
||||
min_sdk (int): The minimum required Android SDK version for compatibility.
|
||||
min_oem (Tuple[int, str]): Tuple defining the minimum OEM version, e.g., (version_code, version_name).
|
||||
library (str): The shared library name or pattern used by the vendor.
|
||||
|
||||
"""
|
||||
self.process = process
|
||||
self.min_sdk = min_sdk
|
||||
self.min_oem = min_oem
|
||||
self.library = library
|
||||
|
||||
def __repr__(self) -> str:
|
||||
"""
|
||||
Generates a string representation of the current instance for debugging purposes.
|
||||
|
||||
This method is primarily used to help developers understand the state of the object
|
||||
during logging or interactive debugging by displaying all attribute names and values
|
||||
in a clean, readable format.
|
||||
|
||||
Returns:
|
||||
str: A string showing the class name and its instance variables with their values.
|
||||
"""
|
||||
# Construct a formatted string with the class name and a list of key=value pairs from the instance's attributes
|
||||
return '{name}({items})'.format(
|
||||
name=self.__class__.__name__,
|
||||
items=', '.join([f'{k}={repr(v)}' for k, v in self.__dict__.items()])
|
||||
)
|
||||
|
||||
@staticmethod
|
||||
def __pattern(value: str) -> str:
|
||||
"""
|
||||
Converts a given string into a regex-compatible pattern that allows for matching
|
||||
flexible naming conventions found in Android service or library identifiers.
|
||||
|
||||
This is particularly useful when dealing with variant suffixes (e.g., `-lazy`, version tags),
|
||||
or optional annotations (e.g., `@<version>` in `.so` or `.widevine` modules).
|
||||
|
||||
Args:
|
||||
value (str): The base string (e.g., filename or service name) to convert into a regex pattern.
|
||||
|
||||
Returns:
|
||||
str: A regex pattern that can be used to match common variants of the input string.
|
||||
"""
|
||||
return (value
|
||||
.replace('-service', r'-service(?:-lazy)?')
|
||||
.replace('.widevine', r'.widevine(?:@\S+)?')
|
||||
.replace('.so', r'(?:@\S+)?.so')
|
||||
.replace('.', r'\.'))
|
||||
|
||||
def is_process(self, value: str) -> bool:
|
||||
"""
|
||||
Determines whether the provided process name matches the expected vendor-specific process pattern.
|
||||
|
||||
This is useful when trying to detect or hook into a known target process,
|
||||
especially when its name can include runtime-specific suffixes (e.g., versioned .so files or services).
|
||||
|
||||
Args:
|
||||
value (str): The name of the process to evaluate.
|
||||
|
||||
Returns:
|
||||
bool: True if the process name matches the generated pattern; otherwise, False.
|
||||
"""
|
||||
# Generate a regex pattern from the expected process name
|
||||
pattern = self.__pattern(self.process)
|
||||
|
||||
# Check if the input value matches the regex pattern
|
||||
return bool(re.match(pattern, value))
|
||||
|
||||
def get_library(self, values: List[dict]) -> Optional[dict]:
|
||||
"""
|
||||
Retrieves the first matching library dictionary from a provided list based on a dynamically generated regex pattern.
|
||||
|
||||
This method is useful when trying to identify a target library in a list of shared objects (e.g., `.so` files),
|
||||
especially when the exact name may include version tags or runtime decorations (e.g., `libxyz@1.2.so`).
|
||||
|
||||
Args:
|
||||
values (List[dict]): A list of dictionaries, each expected to contain a 'name' key with the library's filename.
|
||||
|
||||
Returns:
|
||||
Optional[dict]: The first dictionary whose 'name' matches the expected regex pattern; returns None if no match is found.
|
||||
"""
|
||||
# Create a regex pattern based on the expected library name, allowing flexibility for suffixes or variants
|
||||
pattern = self.__pattern(self.library)
|
||||
|
||||
# Iterate through the list and return the first dictionary with a matching 'name'
|
||||
return next((v for v in values if re.match(pattern, v['name'])), None)
|
||||
|
||||
|
||||
__all__ = ('Vendor',)
|
||||
Reference in New Issue
Block a user