Skip to content

Commit 872c071

Browse files
gh-71052: Change Android's sys.platform from "linux" to "android"
Co-authored-by: Erlend E. Aasland <[email protected]>
1 parent 9f983e0 commit 872c071

24 files changed

+94
-78
lines changed

Doc/library/sys.rst

Lines changed: 20 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1367,47 +1367,42 @@ always available.
13671367

13681368
.. data:: platform
13691369

1370-
This string contains a platform identifier that can be used to append
1371-
platform-specific components to :data:`sys.path`, for instance.
1372-
1373-
For Unix systems, except on Linux and AIX, this is the lowercased OS name as
1374-
returned by ``uname -s`` with the first part of the version as returned by
1375-
``uname -r`` appended, e.g. ``'sunos5'`` or ``'freebsd8'``, *at the time
1376-
when Python was built*. Unless you want to test for a specific system
1377-
version, it is therefore recommended to use the following idiom::
1378-
1379-
if sys.platform.startswith('freebsd'):
1380-
# FreeBSD-specific code here...
1381-
elif sys.platform.startswith('linux'):
1382-
# Linux-specific code here...
1383-
elif sys.platform.startswith('aix'):
1384-
# AIX-specific code here...
1385-
1386-
For other systems, the values are:
1370+
A string containing a platform identifier. Known values are:
13871371

13881372
================ ===========================
13891373
System ``platform`` value
13901374
================ ===========================
13911375
AIX ``'aix'``
1376+
Android ``'android'``
13921377
Emscripten ``'emscripten'``
1378+
iOS ``'ios'``
13931379
Linux ``'linux'``
1394-
WASI ``'wasi'``
1380+
macOS ``'darwin'``
13951381
Windows ``'win32'``
13961382
Windows/Cygwin ``'cygwin'``
1397-
macOS ``'darwin'``
1383+
WASI ``'wasi'``
13981384
================ ===========================
13991385

1386+
On Unix systems not listed in the table, the value is the lowercased OS name
1387+
as returned by ``uname -s``, with the first part of the version as returned by
1388+
``uname -r`` appended, e.g. ``'sunos5'`` or ``'freebsd8'``, *at the time
1389+
when Python was built*. Unless you want to test for a specific system
1390+
version, it is therefore recommended to use the following idiom::
1391+
1392+
if sys.platform.startswith('freebsd'):
1393+
# FreeBSD-specific code here...
1394+
14001395
.. versionchanged:: 3.3
14011396
On Linux, :data:`sys.platform` doesn't contain the major version anymore.
1402-
It is always ``'linux'``, instead of ``'linux2'`` or ``'linux3'``. Since
1403-
older Python versions include the version number, it is recommended to
1404-
always use the ``startswith`` idiom presented above.
1397+
It is always ``'linux'``, instead of ``'linux2'`` or ``'linux3'``.
14051398

14061399
.. versionchanged:: 3.8
14071400
On AIX, :data:`sys.platform` doesn't contain the major version anymore.
1408-
It is always ``'aix'``, instead of ``'aix5'`` or ``'aix7'``. Since
1409-
older Python versions include the version number, it is recommended to
1410-
always use the ``startswith`` idiom presented above.
1401+
It is always ``'aix'``, instead of ``'aix5'`` or ``'aix7'``.
1402+
1403+
.. versionchanged:: 3.13
1404+
On Android, :data:`sys.platform` now returns ``'android'`` rather than
1405+
``'linux'``.
14111406

14121407
.. seealso::
14131408

Lib/ctypes/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -468,7 +468,7 @@ def LoadLibrary(self, name):
468468

469469
if _os.name == "nt":
470470
pythonapi = PyDLL("python dll", None, _sys.dllhandle)
471-
elif hasattr(_sys, "getandroidapilevel"):
471+
elif _sys.platform == "android":
472472
pythonapi = PyDLL("libpython%d.%d.so" % _sys.version_info[:2])
473473
elif _sys.platform == "cygwin":
474474
pythonapi = PyDLL("libpython%d.%d.dll" % _sys.version_info[:2])

Lib/multiprocessing/util.py

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -102,11 +102,7 @@ def log_to_stderr(level=None):
102102
# Abstract socket support
103103

104104
def _platform_supports_abstract_sockets():
105-
if sys.platform == "linux":
106-
return True
107-
if hasattr(sys, 'getandroidapilevel'):
108-
return True
109-
return False
105+
return sys.platform in ("linux", "android")
110106

111107

112108
def is_abstract_socket_namespace(address):

Lib/shutil.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,8 @@
4747
COPY_BUFSIZE = 1024 * 1024 if _WINDOWS else 64 * 1024
4848
# This should never be removed, see rationale in:
4949
# https://bugs.python.org/issue43743#msg393429
50-
_USE_CP_SENDFILE = hasattr(os, "sendfile") and sys.platform.startswith("linux")
50+
_USE_CP_SENDFILE = (hasattr(os, "sendfile")
51+
and sys.platform.startswith(("linux", "android")))
5152
_HAS_FCOPYFILE = posix and hasattr(posix, "_fcopyfile") # macOS
5253

5354
# CMD defaults in Windows 10

Lib/test/support/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -520,7 +520,7 @@ def requires_debug_ranges(reason='requires co_positions / debug_ranges'):
520520
# Is not actually used in tests, but is kept for compatibility.
521521
is_jython = sys.platform.startswith('java')
522522

523-
is_android = hasattr(sys, 'getandroidapilevel')
523+
is_android = sys.platform == "android"
524524

525525
if sys.platform not in {"win32", "vxworks", "ios", "tvos", "watchos"}:
526526
unix_shell = '/system/bin/sh' if is_android else '/bin/sh'

Lib/test/support/os_helper.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -612,7 +612,7 @@ def __fspath__(self):
612612
def fd_count():
613613
"""Count the number of open file descriptors.
614614
"""
615-
if sys.platform.startswith(('linux', 'freebsd', 'emscripten')):
615+
if sys.platform.startswith(('linux', 'android', 'freebsd', 'emscripten')):
616616
fd_path = "/proc/self/fd"
617617
elif sys.platform == "darwin":
618618
fd_path = "/dev/fd"

Lib/test/test_asyncio/test_subprocess.py

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -480,7 +480,8 @@ async def empty_error():
480480
self.assertEqual(output, None)
481481
self.assertEqual(exitcode, 0)
482482

483-
@unittest.skipIf(sys.platform != 'linux', "Don't have /dev/stdin")
483+
@unittest.skipIf(sys.platform not in ('linux', 'android'),
484+
"Don't have /dev/stdin")
484485
def test_devstdin_input(self):
485486

486487
async def devstdin_input(message):

Lib/test/test_c_locale_coercion.py

Lines changed: 10 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -26,17 +26,16 @@
2626
TARGET_LOCALES = ["C.UTF-8", "C.utf8", "UTF-8"]
2727

2828
# Apply some platform dependent overrides
29-
if sys.platform.startswith("linux"):
30-
if support.is_android:
31-
# Android defaults to using UTF-8 for all system interfaces
32-
EXPECTED_C_LOCALE_STREAM_ENCODING = "utf-8"
33-
EXPECTED_C_LOCALE_FS_ENCODING = "utf-8"
34-
else:
35-
# Linux distros typically alias the POSIX locale directly to the C
36-
# locale.
37-
# TODO: Once https://bugs.python.org/issue30672 is addressed, we'll be
38-
# able to check this case unconditionally
39-
EXPECTED_C_LOCALE_EQUIVALENTS.append("POSIX")
29+
if sys.platform == "android":
30+
# Android defaults to using UTF-8 for all system interfaces
31+
EXPECTED_C_LOCALE_STREAM_ENCODING = "utf-8"
32+
EXPECTED_C_LOCALE_FS_ENCODING = "utf-8"
33+
elif sys.platform.startswith("linux"):
34+
# Linux distros typically alias the POSIX locale directly to the C
35+
# locale.
36+
# TODO: Once https://bugs.python.org/issue30672 is addressed, we'll be
37+
# able to check this case unconditionally
38+
EXPECTED_C_LOCALE_EQUIVALENTS.append("POSIX")
4039
elif sys.platform.startswith("aix"):
4140
# AIX uses iso8859-1 in the C locale, other *nix platforms use ASCII
4241
EXPECTED_C_LOCALE_STREAM_ENCODING = "iso8859-1"

Lib/test/test_fcntl.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -129,8 +129,8 @@ def test_fcntl_bad_file_overflow(self):
129129
fcntl.fcntl(BadFile(INT_MIN - 1), fcntl.F_SETFL, os.O_NONBLOCK)
130130

131131
@unittest.skipIf(
132-
any(platform.machine().startswith(name) for name in {"arm", "aarch"})
133-
and platform.system() in {"Linux", "Android"},
132+
platform.machine().startswith(("arm", "aarch"))
133+
and platform.system() in ("Linux", "Android"),
134134
"ARM Linux returns EINVAL for F_NOTIFY DN_MULTISHOT")
135135
def test_fcntl_64_bit(self):
136136
# Issue #1309352: fcntl shouldn't fail when the third arg fits in a

Lib/test/test_logging.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -603,7 +603,7 @@ def test_name(self):
603603
def test_builtin_handlers(self):
604604
# We can't actually *use* too many handlers in the tests,
605605
# but we can try instantiating them with various options
606-
if sys.platform in ('linux', 'darwin'):
606+
if sys.platform in ('linux', 'android', 'darwin'):
607607
for existing in (True, False):
608608
fn = make_temp_file()
609609
if not existing:
@@ -667,7 +667,7 @@ def test_path_objects(self):
667667
(logging.handlers.RotatingFileHandler, (pfn, 'a')),
668668
(logging.handlers.TimedRotatingFileHandler, (pfn, 'h')),
669669
)
670-
if sys.platform in ('linux', 'darwin'):
670+
if sys.platform in ('linux', 'android', 'darwin'):
671671
cases += ((logging.handlers.WatchedFileHandler, (pfn, 'w')),)
672672
for cls, args in cases:
673673
h = cls(*args, encoding="utf-8")

0 commit comments

Comments
 (0)