Skip to content

UUID _ifconfig_getnodes() will always return None due to broken logic #98415

Closed
@csanders-git

Description

@csanders-git

Bug report

UUID reads the MAC address from the local system in order to generate UUIDv1/v2 spec requests. On Linux and Darwin and unknown platforms it will attempt to run _ifconfig_getnode() to search through ifconfig in order to get the MAC value by searching ifconfig. On MacOS and Unknown platforms it will do this first. (https://github.com/python/cpython/blob/main/Lib/uuid.py#L627)

_ifconfig_getnode() is designed to take a number of args, likely to support multiple systems. Currently this supports 3 flags, '' '-a' and '-av' (https://github.com/python/cpython/blob/main/Lib/uuid.py#L510). This function can never move passed calling the first argument as it will always return. Worse yet, on MacOS and linux passing '' as the argument will actually run the equivalent of /sbin/ifconfig "" which will always return to stderr (which is discarded). This is very likely due to the developer not understanding how popen generates the command string (see https://github.com/python/cpython/blob/main/Lib/subprocess.py#L615)

Due to an incorrectly tabbed return statement this will always result in the function bailing out before testing other valid options. In all tested cases this also results in the function ALWAYS return None. Making the check useless.

    for args in ('', '-a', '-av'):
        mac = _find_mac_near_keyword('ifconfig', args, keywords, lambda i: i+1)
        if mac:
            return mac
        return None

https://github.com/python/cpython/blob/main/Lib/uuid.py#L506

The smallest example of this problem looks something like this

    import subprocess
    """Get the hardware address on Unix by running ifconfig."""
    # This works on Linux ('' or '-a'), Tru64 ('-av'), but not all Unixes.
    for args in ('', '-a', '-av'):
        proc = subprocess.Popen(("/sbin/ifconfig",) + (args,),
                        stdout=subprocess.PIPE,
                        stderr=subprocess.DEVNULL)
        if not proc:
            return None
        stdout, stderr = proc.communicate()
        mac = stdout # This is fine for this example (normally it'd have parsed out a mac
        if mac:
            return mac
        return None

Your environment

  • Python 3.10.6
  • macOS 13.0 Beta 10

Metadata

Metadata

Assignees

No one assigned

    Labels

    type-bugAn unexpected behavior, bug, or error

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions