| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,71 @@ | ||
| import sys | ||
| try: | ||
| from ctypes import cdll, c_void_p, c_char_p, util | ||
| except ImportError: | ||
| # ctypes is an optional module. If it's not present, we're limited in what | ||
| # we can tell about the system, but we don't want to prevent the module | ||
| # from working. | ||
| print("ctypes isn't available; iOS system calls will not be available") | ||
| objc = None | ||
| else: | ||
| # ctypes is available. Load the ObjC library, and wrap the objc_getClass, | ||
| # sel_registerName methods | ||
| lib = util.find_library("objc") | ||
| if lib is None: | ||
| # Failed to load the objc library | ||
| raise RuntimeError("ObjC runtime library couldn't be loaded") | ||
|
|
||
| objc = cdll.LoadLibrary(lib) | ||
| objc.objc_getClass.restype = c_void_p | ||
| objc.objc_getClass.argtypes = [c_char_p] | ||
| objc.sel_registerName.restype = c_void_p | ||
| objc.sel_registerName.argtypes = [c_char_p] | ||
|
|
||
|
|
||
| def get_platform_ios(): | ||
| # Determine if this is a simulator using the multiarch value | ||
| is_simulator = sys.implementation._multiarch.endswith("simulator") | ||
|
|
||
| # We can't use ctypes; abort | ||
| if not objc: | ||
| return None | ||
|
|
||
| # Most of the methods return ObjC objects | ||
| objc.objc_msgSend.restype = c_void_p | ||
| # All the methods used have no arguments. | ||
| objc.objc_msgSend.argtypes = [c_void_p, c_void_p] | ||
|
|
||
| # Equivalent of: | ||
| # device = [UIDevice currentDevice] | ||
| UIDevice = objc.objc_getClass(b"UIDevice") | ||
| SEL_currentDevice = objc.sel_registerName(b"currentDevice") | ||
|
Comment thread
Copy link
Copy Markdown
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low Qualitysnake_case for this and the other variables here, or is it more important to mirror the objc names? https://peps.python.org/pep-0008/#function-and-variable-names
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityYes - the intention was to mirror the objc naming, so that it's a little easier to see that the name comes from an "alien space", and might have some additional considerations - a sort of very weak Hungarian notation. In terms of pure functionality, it doesn't have any impact on the operation of the code. Any variable name will do; this naming convention is entirely as an affordance to future readers. For my money, the "hey, that's weird - they're not camel case" reaction is mildly desirable in this case.
Sorry, something went wrong.
ned-deily reacted with thumbs up emoji
All reactions
|
||
| device = objc.objc_msgSend(UIDevice, SEL_currentDevice) | ||
|
|
||
| # Equivalent of: | ||
| # device_systemVersion = [device systemVersion] | ||
| SEL_systemVersion = objc.sel_registerName(b"systemVersion") | ||
| device_systemVersion = objc.objc_msgSend(device, SEL_systemVersion) | ||
|
|
||
| # Equivalent of: | ||
| # device_systemName = [device systemName] | ||
| SEL_systemName = objc.sel_registerName(b"systemName") | ||
| device_systemName = objc.objc_msgSend(device, SEL_systemName) | ||
|
|
||
| # Equivalent of: | ||
| # device_model = [device model] | ||
| SEL_model = objc.sel_registerName(b"model") | ||
| device_model = objc.objc_msgSend(device, SEL_model) | ||
|
|
||
| # UTF8String returns a const char*; | ||
| SEL_UTF8String = objc.sel_registerName(b"UTF8String") | ||
| objc.objc_msgSend.restype = c_char_p | ||
|
|
||
| # Equivalent of: | ||
| # system = [device_systemName UTF8String] | ||
| # release = [device_systemVersion UTF8String] | ||
| # model = [device_model UTF8String] | ||
| system = objc.objc_msgSend(device_systemName, SEL_UTF8String).decode() | ||
| release = objc.objc_msgSend(device_systemVersion, SEL_UTF8String).decode() | ||
| model = objc.objc_msgSend(device_model, SEL_UTF8String).decode() | ||
|
|
||
| return system, release, model, is_simulator | ||
| Original file line number | Diff line number | Diff line change | ||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Expand Up | @@ -496,6 +496,30 @@ def mac_ver(release='', versioninfo=('', '', ''), machine=''): | |||||||||||||
| # If that also doesn't work return the default values | ||||||||||||||
| return release, versioninfo, machine | ||||||||||||||
|
|
||||||||||||||
|
|
||||||||||||||
| # A namedtuple for iOS version information. | ||||||||||||||
| IOSVersionInfo = collections.namedtuple( | ||||||||||||||
| "IOSVersionInfo", | ||||||||||||||
| ["system", "release", "model", "is_simulator"] | ||||||||||||||
| ) | ||||||||||||||
|
|
||||||||||||||
|
|
||||||||||||||
| def ios_ver(system="", release="", model="", is_simulator=False): | ||||||||||||||
| """Get iOS version information, and return it as a namedtuple: | ||||||||||||||
| (system, release, model, is_simulator). | ||||||||||||||
|
|
||||||||||||||
| If values can't be determined, they are set to values provided as | ||||||||||||||
| parameters. | ||||||||||||||
| """ | ||||||||||||||
| if sys.platform == "ios": | ||||||||||||||
| import _ios_support | ||||||||||||||
| result = _ios_support.get_platform_ios() | ||||||||||||||
| if result is not None: | ||||||||||||||
| return IOSVersionInfo(*result) | ||||||||||||||
|
|
||||||||||||||
| return IOSVersionInfo(system, release, model, is_simulator) | ||||||||||||||
|
|
||||||||||||||
|
|
||||||||||||||
| def _java_getprop(name, default): | ||||||||||||||
| """This private helper is deprecated in 3.13 and will be removed in 3.15""" | ||||||||||||||
| from java.lang import System | ||||||||||||||
| Expand Down Expand Up | @@ -654,7 +678,7 @@ def _platform(*args): | |||||||||||||
| if cleaned == platform: | ||||||||||||||
| break | ||||||||||||||
| platform = cleaned | ||||||||||||||
| while platform[-1] == '-': | ||||||||||||||
| while platform and platform[-1] == '-': | ||||||||||||||
| platform = platform[:-1] | ||||||||||||||
|
|
||||||||||||||
| return platform | ||||||||||||||
| Expand Down Expand Up | @@ -695,7 +719,7 @@ def _syscmd_file(target, default=''): | |||||||||||||
| default in case the command should fail. | ||||||||||||||
|
|
||||||||||||||
| """ | ||||||||||||||
| if sys.platform in ('dos', 'win32', 'win16'): | ||||||||||||||
| if sys.platform in {'dos', 'win32', 'win16', 'ios', 'tvos', 'watchos'}: | ||||||||||||||
| # XXX Others too ? | ||||||||||||||
| return default | ||||||||||||||
|
|
||||||||||||||
| Expand Down Expand Up | @@ -859,6 +883,14 @@ def get_OpenVMS(): | |||||||||||||
| csid, cpu_number = vms_lib.getsyi('SYI$_CPU', 0) | ||||||||||||||
| return 'Alpha' if cpu_number >= 128 else 'VAX' | ||||||||||||||
|
|
||||||||||||||
| # On the iOS simulator, os.uname returns the architecture as uname.machine. | ||||||||||||||
| # On device it returns the model name for some reason; but there's only one | ||||||||||||||
| # CPU architecture for iOS devices, so we know the right answer. | ||||||||||||||
| def get_ios(): | ||||||||||||||
| if sys.implementation._multiarch.endswith("simulator"): | ||||||||||||||
| return os.uname().machine | ||||||||||||||
| return 'arm64' | ||||||||||||||
|
Comment thread
Comment on lines
+890
to
+892
Copy link
Copy Markdown
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low Quality
Suggested change
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityBecause of the way the build works for iOS, I think we can assume that _multiarch is always present.
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityConfirming: iOS builds will always have _multiarch set (because of this section of configure.ac); and this block of logic will only be invoked on iOS as it's part of a get_ios() method.
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityThat is true for CPython, but it may change for different implementations that keep our stdlib. It's not a big deal, but generally I avoid adding a hard dependency on implementation details. This is certainly not a blocker, just a possible improvement.
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityAvoiding hard dependencies on implementation details definitely makes sense; However, I'm not sure if using a fallback is entirely safe. Without any additional changes, using a fallback value for _multiarch will result in:
The second point would at least complicate, and possibly prevent any binary module from loading; the first would lead to misleading or incorrect behavior. On that basis, I'd argue it would be safer to fail early, providing a clear indicator that something isn't configured correctly (or, at least, not configured the way that the CPython implementation expects). However, it's also a relatively straightforward change, so I'm happy to be overruled on this.
Sorry, something went wrong.
FFY00 reacted with thumbs up emoji
All reactions
|
||||||||||||||
|
|
||||||||||||||
| def from_subprocess(): | ||||||||||||||
| """ | ||||||||||||||
| Fall back to `uname -p` | ||||||||||||||
| Expand Down Expand Up | @@ -1018,6 +1050,10 @@ def uname(): | |||||||||||||
| system = 'Android' | ||||||||||||||
| release = android_ver().release | ||||||||||||||
|
|
||||||||||||||
| # Normalize responses on iOS | ||||||||||||||
| if sys.platform == 'ios': | ||||||||||||||
| system, release, _, _ = ios_ver() | ||||||||||||||
|
|
||||||||||||||
| vals = system, node, release, version, machine | ||||||||||||||
| # Replace 'unknown' values with the more portable '' | ||||||||||||||
| _uname_cache = uname_result(*map(_unknown_as_blank, vals)) | ||||||||||||||
| Expand Down Expand Up | @@ -1297,11 +1333,14 @@ def platform(aliased=False, terse=False): | |||||||||||||
| system, release, version = system_alias(system, release, version) | ||||||||||||||
|
|
||||||||||||||
| if system == 'Darwin': | ||||||||||||||
| # macOS (darwin kernel) | ||||||||||||||
| macos_release = mac_ver()[0] | ||||||||||||||
| if macos_release: | ||||||||||||||
| system = 'macOS' | ||||||||||||||
| release = macos_release | ||||||||||||||
| # macOS and iOS both report as a "Darwin" kernel | ||||||||||||||
| if sys.platform == "ios": | ||||||||||||||
| system, release, _, _ = ios_ver() | ||||||||||||||
| else: | ||||||||||||||
| macos_release = mac_ver()[0] | ||||||||||||||
| if macos_release: | ||||||||||||||
| system = 'macOS' | ||||||||||||||
| release = macos_release | ||||||||||||||
|
|
||||||||||||||
| if system == 'Windows': | ||||||||||||||
| # MS platforms | ||||||||||||||
| Expand Down | ||||||||||||||
| Original file line number | Diff line number | Diff line change | ||||
|---|---|---|---|---|---|---|
| Expand Up | @@ -21,6 +21,7 @@ | |||||
|
|
||||||
| # Keys for get_config_var() that are never converted to Python integers. | ||||||
| _ALWAYS_STR = { | ||||||
| 'IPHONEOS_DEPLOYMENT_TARGET', | ||||||
| 'MACOSX_DEPLOYMENT_TARGET', | ||||||
| } | ||||||
|
|
||||||
| Expand Down Expand Up | @@ -57,6 +58,7 @@ | |||||
| 'scripts': '{base}/Scripts', | ||||||
| 'data': '{base}', | ||||||
| }, | ||||||
|
|
||||||
| # Downstream distributors can overwrite the default install scheme. | ||||||
| # This is done to support downstream modifications where distributors change | ||||||
| # the installation layout (eg. different site-packages directory). | ||||||
| Expand Down Expand Up | @@ -114,8 +116,8 @@ def _getuserbase(): | |||||
| if env_base: | ||||||
| return env_base | ||||||
|
|
||||||
| # Emscripten, VxWorks, and WASI have no home directories | ||||||
| if sys.platform in {"emscripten", "vxworks", "wasi"}: | ||||||
| # Emscripten, iOS, tvOS, VxWorks, WASI, and watchOS have no home directories | ||||||
| if sys.platform in {"emscripten", "ios", "tvos", "vxworks", "wasi", "watchos"}: | ||||||
| return None | ||||||
|
|
||||||
| def joinuser(*args): | ||||||
| Expand Down Expand Up | @@ -290,6 +292,7 @@ def _get_preferred_schemes(): | |||||
| 'home': 'posix_home', | ||||||
| 'user': 'osx_framework_user', | ||||||
| } | ||||||
|
|
||||||
| return { | ||||||
| 'prefix': 'posix_prefix', | ||||||
| 'home': 'posix_home', | ||||||
| Expand Down Expand Up | @@ -623,10 +626,15 @@ def get_platform(): | |||||
| if m: | ||||||
| release = m.group() | ||||||
| elif osname[:6] == "darwin": | ||||||
| import _osx_support | ||||||
| osname, release, machine = _osx_support.get_platform_osx( | ||||||
| get_config_vars(), | ||||||
| osname, release, machine) | ||||||
| if sys.platform == "ios": | ||||||
| release = get_config_vars().get("IPHONEOS_DEPLOYMENT_TARGET", "12.0") | ||||||
| osname = sys.platform | ||||||
| machine = sys.implementation._multiarch | ||||||
|
Comment thread
Copy link
Copy Markdown
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low Quality
Suggested change
Sorry, something went wrong.
All reactions
Copy link
Copy Markdown
Contributor
Author
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityAgain; this is iOS specific code.
Sorry, something went wrong.
All reactions
|
||||||
| else: | ||||||
| import _osx_support | ||||||
| osname, release, machine = _osx_support.get_platform_osx( | ||||||
| get_config_vars(), | ||||||
| osname, release, machine) | ||||||
|
|
||||||
| return f"{osname}-{release}-{machine}" | ||||||
|
|
||||||
| Expand Down | ||||||
| Back | FazBrowse Home | New Git URL |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualitySorry, something went wrong.
Uh oh!
There was an error while loading. Please reload this page.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Choose a reason Spam Abuse Off Topic Outdated Duplicate Resolved Low QualityAs above: iOS always has _multiarch, and get_platform_ios() is only invoked by platform.ios_ver(), after being gated to be iOS-specific.
Sorry, something went wrong.
Uh oh!
There was an error while loading. Please reload this page.