Esempio n. 1
0
def executePostProcessing(result_filename):

    if isWin32Windows():
        # Copy the Windows manifest from the CPython binary to the created
        # executable, so it finds "MSCRT.DLL". This is needed for Python2
        # only, for Python3 newer MSVC doesn't hide the C runtime.
        if python_version < 300 and not Options.shallMakeModule():
            copyResourcesFromFileToFile(
                sys.executable,
                target_filename=result_filename,
                resource_kind=RT_MANIFEST,
            )

        assert os.path.exists(result_filename)

        # Attach the binary blob as a Windows resource.
        addResourceToFile(
            target_filename=result_filename,
            data=ConstantCodes.stream_data.getBytes(),
            resource_kind=RT_RCDATA,
            res_name=3,
            lang_id=0,
        )

    # Modules should not be executable, but Scons creates them like it, fix
    # it up here.
    if not isWin32Windows() and Options.shallMakeModule():
        old_stat = os.stat(result_filename)

        mode = old_stat.st_mode
        mode &= ~(stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH)

        if mode != old_stat.st_mode:
            os.chmod(result_filename, mode)
Esempio n. 2
0
def packDistFolderToOnefileWindows(dist_dir):
    general.warning("Onefile mode is experimental on '%s'." % getOS())

    postprocessing_logger.info(
        "Creating single file from dist folder, this may take a while.")

    onefile_output_filename = getResultFullpath(onefile=True)

    # First need to create the bootstrap binary for unpacking.
    _runOnefileScons(quiet=not Options.isShowScons())

    # Make sure to copy the resources from the created binary to the bootstrap binary, these
    # are icons and version information.
    copyResourcesFromFileToFile(
        source_filename=getResultFullpath(onefile=False),
        target_filename=onefile_output_filename,
        resource_kinds=(RT_ICON, RT_GROUP_ICON, RT_VERSION),
    )

    # Now need to append to payload it, potentially compressing it.
    compression_indicator, compressor = _pickCompressor()

    with open(onefile_output_filename, "ab") as output_file:
        # Seeking to end of file seems necessary on Python2 at least, maybe it's
        # just that tell reports wrong value initially.
        output_file.seek(0, 2)

        start_pos = output_file.tell()

        output_file.write(b"KA" + compression_indicator)

        # Move the binary to start immediately to the start position
        start_binary = getResultFullpath(onefile=False)
        file_list = getFileList(dist_dir)
        file_list.remove(start_binary)
        file_list.insert(0, start_binary)

        for filename_full in file_list:
            filename_relative = os.path.relpath(filename_full, dist_dir)
            filename_encoded = filename_relative.encode("utf-16le") + b"\0\0"

            output_file.write(filename_encoded)

            with open(filename_full, "rb") as input_file:
                compressed = compressor(input_file.read())

                output_file.write(struct.pack("Q", len(compressed)))
                output_file.write(compressed)

        # Using empty filename as a terminator.
        output_file.write(b"\0\0")

        output_file.write(struct.pack("Q", start_pos))
Esempio n. 3
0
def executePostProcessing(result_filename):

    # Copy the Windows manifest from the CPython binary to the created
    # executable, so it finds "MSCRT.DLL". This is needed for Python2
    # only, for Python3 newer MSVC doesn't hide the C runtime.
    if python_version < 300:
        if isWin32Windows() and not Options.shallMakeModule():
            copyResourcesFromFileToFile(sys.executable, result_filename, RT_MANIFEST)

    # Modules should not be executable, but Scons creates them like it, fix
    # it up here.
    if not isWin32Windows() and Options.shallMakeModule():
        old_stat = os.stat(result_filename)

        mode = old_stat.st_mode
        mode &= ~(stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH)

        if mode != old_stat.st_mode:
            os.chmod(result_filename, mode)
Esempio n. 4
0
def executePostProcessingResources(manifest, onefile):
    """Adding Windows resources to the binary.

    Used for both onefile and not onefile binary, potentially two times.
    """
    result_filename = OutputDirectories.getResultFullpath(onefile=onefile)

    # TODO: Maybe make these different for onefile and not onefile.
    if (Options.shallAskForWindowsAdminRights()
            or Options.shallAskForWindowsUIAccessRights()):
        if manifest is None:
            manifest = getDefaultWindowsExecutableManifest()

        if Options.shallAskForWindowsAdminRights():
            manifest.addUacAdmin()

        if Options.shallAskForWindowsUIAccessRights():
            manifest.addUacUiAccess()

    if manifest is not None:
        manifest.addResourceToFile(result_filename,
                                   logger=postprocessing_logger)

    if (Options.getWindowsVersionInfoStrings()
            or Options.getWindowsProductVersion()
            or Options.getWindowsFileVersion()):
        version_resources.update(
            addVersionInfoResource(
                string_values=Options.getWindowsVersionInfoStrings(),
                product_version=Options.getWindowsProductVersion(),
                file_version=Options.getWindowsFileVersion(),
                file_date=(0, 0),
                is_exe=not Options.shallMakeModule(),
                result_filename=result_filename,
                logger=postprocessing_logger,
            ))

    # Attach icons from template file if given.
    template_exe = Options.getWindowsIconExecutablePath()
    if template_exe is not None:
        res_copied = copyResourcesFromFileToFile(
            template_exe,
            target_filename=result_filename,
            resource_kinds=(RT_ICON, RT_GROUP_ICON),
        )

        if res_copied == 0:
            postprocessing_logger.warning(
                "The specified icon template executable %r didn't contain anything to copy."
                % template_exe)
        else:
            postprocessing_logger.warning("Copied %d icon resources from %r." %
                                          (res_copied, template_exe))
    else:
        _addWindowsIconFromIcons(onefile=onefile)
Esempio n. 5
0
def executePostProcessing(result_filename):

    # Copy the Windows manifest from the CPython binary to the created
    # executable, so it finds "MSCRT.DLL". This is needed for Python2
    # only, for Python3 newer MSVC doesn't hide the C runtime.
    if python_version < 300:
        if isWin32Windows() and not Options.shallMakeModule():
            copyResourcesFromFileToFile(sys.executable, result_filename,
                                        RT_MANIFEST)

    # Modules should not be executable, but Scons creates them like it, fix
    # it up here.
    if not isWin32Windows() and Options.shallMakeModule():
        old_stat = os.stat(result_filename)

        mode = old_stat.st_mode
        mode &= ~(stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH)

        if mode != old_stat.st_mode:
            os.chmod(result_filename, mode)
Esempio n. 6
0
def executePostProcessing(result_filename):
    if not os.path.exists(result_filename):
        sys.exit("Error, scons failed to create the expected file '%s'. " %
                 result_filename)

    if isWin32Windows():
        # Copy the Windows manifest from the CPython binary to the created
        # executable, so it finds "MSCRT.DLL". This is needed for Python2
        # only, for Python3 newer MSVC doesn't hide the C runtime.
        if python_version < 300 and not Options.shallMakeModule():
            copyResourcesFromFileToFile(
                sys.executable,
                target_filename=result_filename,
                resource_kind=RT_MANIFEST,
            )

        assert os.path.exists(result_filename)

        # Attach the binary blob as a Windows resource.
        addResourceToFile(
            target_filename=result_filename,
            data=ConstantCodes.stream_data.getBytes(),
            resource_kind=RT_RCDATA,
            res_name=3,
            lang_id=0,
        )

    # On macOS, we update the executable path for searching the "libpython"
    # library.
    if (getOS() == "Darwin" and not Options.shallMakeModule()
            and not Options.shallUseStaticLibPython()):
        python_version_str = ".".join(str(s) for s in sys.version_info[0:2])
        python_abi_version = python_version_str + getPythonABI()
        python_dll_filename = "libpython" + python_abi_version + ".dylib"
        python_lib_path = os.path.join(sys.prefix, "lib")

        if os.path.exists(os.path.join(sys.prefix, "conda-meta")):
            callInstallNameToolAddRPath(result_filename, python_lib_path)

        callInstallNameTool(
            filename=result_filename,
            mapping=((
                python_dll_filename,
                os.path.join(python_lib_path, python_dll_filename),
            ), ),
        )

    # Modules should not be executable, but Scons creates them like it, fix
    # it up here.
    if not isWin32Windows() and Options.shallMakeModule():
        old_stat = os.stat(result_filename)

        mode = old_stat.st_mode
        mode &= ~(stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH)

        if mode != old_stat.st_mode:
            os.chmod(result_filename, mode)

    if isWin32Windows() and Options.shallMakeModule():
        candidate = os.path.join(
            os.path.dirname(result_filename),
            "lib" + os.path.basename(result_filename)[:-4] + ".a",
        )

        if os.path.exists(candidate):
            os.unlink(candidate)

    if isWin32Windows() and Options.shallTreatUninstalledPython():
        shutil.copy(getTargetPythonDLLPath(),
                    os.path.dirname(result_filename) or ".")
Esempio n. 7
0
def executePostProcessing():
    # These is a bunch of stuff to consider, pylint: disable=too-many-branches

    result_filename = OutputDirectories.getResultFullpath()

    if not os.path.exists(result_filename):
        postprocessing_logger.sysexit(
            "Error, scons failed to create the expected file %r. " %
            result_filename)

    if isWin32Windows():
        if not Options.shallMakeModule():
            needs_manifest = False
            manifest = None

            if python_version < 0x300:
                # Copy the Windows manifest from the CPython binary to the created
                # executable, so it finds "MSCRT.DLL". This is needed for Python2
                # only, for Python3 newer MSVC doesn't hide the C runtime.
                manifest = getWindowsExecutableManifest(sys.executable)

                if manifest is not None:
                    needs_manifest = True

            if (Options.shallAskForWindowsAdminRights()
                    or Options.shallAskForWindowsUIAccessRights()):
                needs_manifest = True

                if manifest is None:
                    manifest = getDefaultWindowsExecutableManifest()

                if Options.shallAskForWindowsAdminRights():
                    manifest.addUacAdmin()

                if Options.shallAskForWindowsUIAccessRights():
                    manifest.addUacUiAccess()

            if needs_manifest:
                manifest.addResourceToFile(result_filename,
                                           logger=postprocessing_logger)

        if (Options.getWindowsVersionInfoStrings()
                or Options.getWindowsProductVersion()
                or Options.getWindowsFileVersion()):
            version_resources.update(
                addVersionInfoResource(
                    string_values=Options.getWindowsVersionInfoStrings(),
                    product_version=Options.getWindowsProductVersion(),
                    file_version=Options.getWindowsFileVersion(),
                    file_date=(0, 0),
                    is_exe=not Options.shallMakeModule(),
                    result_filename=result_filename,
                    logger=postprocessing_logger,
                ))

        source_dir = OutputDirectories.getSourceDirectoryPath()

        # Attach the binary blob as a Windows resource.
        addResourceToFile(
            target_filename=result_filename,
            data=getFileContents(getConstantBlobFilename(source_dir), "rb"),
            resource_kind=RT_RCDATA,
            res_name=3,
            lang_id=0,
            logger=postprocessing_logger,
        )

        # Attach icons from template file if given.
        template_exe = Options.getWindowsIconExecutablePath()
        if template_exe is not None:
            res_copied = copyResourcesFromFileToFile(
                template_exe,
                target_filename=result_filename,
                resource_kinds=(RT_ICON, RT_GROUP_ICON),
            )

            if res_copied == 0:
                postprocessing_logger.warning(
                    "The specified icon template executable %r didn't contain anything to copy."
                    % template_exe)
            else:
                postprocessing_logger.warning(
                    "Copied %d icon resources from %r." %
                    (res_copied, template_exe))
        else:
            addWindowsIconFromIcons()

    # On macOS, we update the executable path for searching the "libpython"
    # library.
    if (getOS() == "Darwin" and not Options.shallMakeModule()
            and not Options.shallUseStaticLibPython()):
        python_abi_version = python_version_str + getPythonABI()
        python_dll_filename = "libpython" + python_abi_version + ".dylib"
        python_lib_path = os.path.join(sys.prefix, "lib")

        # Note: For CPython and potentially others, the rpath for the Python
        # library needs to be set.

        callInstallNameTool(
            filename=result_filename,
            mapping=(
                (
                    python_dll_filename,
                    os.path.join(python_lib_path, python_dll_filename),
                ),
                (
                    "@rpath/Python3.framework/Versions/%s/Python3" %
                    python_version_str,
                    os.path.join(python_lib_path, python_dll_filename),
                ),
            ),
            rpath=python_lib_path,
        )

    # Modules should not be executable, but Scons creates them like it, fix
    # it up here.
    if not isWin32Windows() and Options.shallMakeModule():
        removeFileExecutablePermission(result_filename)

    if isWin32Windows() and Options.shallMakeModule():
        candidate = os.path.join(
            os.path.dirname(result_filename),
            "lib" + os.path.basename(result_filename)[:-4] + ".a",
        )

        if os.path.exists(candidate):
            os.unlink(candidate)

    if isWin32Windows() and Options.shallTreatUninstalledPython():
        shutil.copy(getTargetPythonDLLPath(),
                    os.path.dirname(result_filename) or ".")