Skip to content

Commit

Permalink
Merge #2839: [Build] Minor fixups and simplifications for macdeploy
Browse files Browse the repository at this point in the history
fea9b7f macdeploy: cleanup .temp.dmg if present (fanquake)
04680fd macdeploy: remove qt4 related code (fanquake)
8d2581c macdeploy: select the plugins we need, rather than excluding those we don't (fanquake)
619fb44 macdeploy: fix framework printing when passing -verbose (fanquake)
e0aa109 macdeploy: remove unused plistlib import (fanquake)

Pull request description:

  Modified backport of bitcoin#22199.

  Github Action's latest macOS 11 runner image has introduced a Qt plugin dylib issue that results in build failures for non-depends based builds (ref: https://github.com/PIVX-Project/PIVX/actions/runs/4610757401/jobs/8206287998). The particular dylib (`libwebp.dylib`) is one that PIVX doesn't use, but the `macdeploy` script was originally written in a way that newer plugins that weren't explicitly excluded were linked, even if not necessarily needed.

  This PR changes the logic/process to instead only link explicitly defined needed plugins that PIVX Core directly uses. Depends based builds are unaffected by this change, as depends builds Qt as static libraries, which don't use Qt plugins.

ACKs for top commit:
  Liquid369:
    tACK fea9b7f

Tree-SHA512: cb42c6ed4947744f55d6e4a13947c5f625d7b5940b3c7083b016e9ff434fc7008d473275e06e1cfeb41483d2d605ac55d9fa23ac228c98c0169a4e4d4594990f
  • Loading branch information
Fuzzbawls committed Apr 8, 2023
2 parents a33988b + fea9b7f commit aadf4bb
Showing 1 changed file with 10 additions and 112 deletions.
122 changes: 10 additions & 112 deletions contrib/macdeploy/macdeployqtplus
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#

import plistlib
import sys, re, os, shutil, stat, os.path
from argparse import ArgumentParser
from ds_store import DSStore
Expand Down Expand Up @@ -53,7 +52,7 @@ class FrameworkInfo(object):
return False

def __str__(self):
return f""" Framework name: {frameworkName}
return f""" Framework name: {self.frameworkName}
Framework directory: {self.frameworkDirectory}
Framework path: {self.frameworkPath}
Binary name: {self.binaryName}
Expand Down Expand Up @@ -85,8 +84,8 @@ class FrameworkInfo(object):
if line == "":
return None

# Don't deploy system libraries (exception for libQtuitools and libQtlucene).
if line.startswith("/System/Library/") or line.startswith("@executable_path") or (line.startswith("/usr/lib/") and "libQt" not in line):
# Don't deploy system libraries
if line.startswith("/System/Library/") or line.startswith("@executable_path") or line.startswith("/usr/lib/"):
return None

m = cls.reOLine.match(line)
Expand Down Expand Up @@ -287,14 +286,6 @@ def copyFramework(framework: FrameworkInfo, path: str, verbose: int) -> Optional
if verbose:
print("Copied Contents:", fromContentsDir)
print(" to:", toContentsDir)
elif framework.frameworkName.startswith("libQtGui"): # Copy qt_menu.nib (applies to non-framework layout)
qtMenuNibSourcePath = os.path.join(framework.frameworkDirectory, "Resources", "qt_menu.nib")
qtMenuNibDestinationPath = os.path.join(path, "Contents", "Resources", "qt_menu.nib")
if os.path.exists(qtMenuNibSourcePath) and not os.path.exists(qtMenuNibDestinationPath):
shutil.copytree(qtMenuNibSourcePath, qtMenuNibDestinationPath, symlinks=True)
if verbose:
print("Copied for libQtGui:", qtMenuNibSourcePath)
print(" to:", qtMenuNibDestinationPath)

return toPath

Expand Down Expand Up @@ -351,116 +342,20 @@ def deployFrameworksForAppBundle(applicationBundle: ApplicationBundleInfo, strip
return deployFrameworks(frameworks, applicationBundle.path, applicationBundle.binaryPath, strip, verbose)

def deployPlugins(appBundleInfo: ApplicationBundleInfo, deploymentInfo: DeploymentInfo, strip: bool, verbose: int):
# Lookup available plugins, exclude unneeded
plugins = []
if deploymentInfo.pluginPath is None:
return
for dirpath, dirnames, filenames in os.walk(deploymentInfo.pluginPath):
pluginDirectory = os.path.relpath(dirpath, deploymentInfo.pluginPath)
if pluginDirectory == "designer":
# Skip designer plugins
continue
elif pluginDirectory == "printsupport":
# Skip printsupport plugins

if pluginDirectory not in ['imageformats', 'iconengines', 'styles', 'platforms']:
continue
elif pluginDirectory == "sqldrivers":
# Deploy the sql plugins only if QtSql is in use
if not deploymentInfo.usesFramework("QtSql"):
continue
elif pluginDirectory == "script":
# Deploy the script plugins only if QtScript is in use
if not deploymentInfo.usesFramework("QtScript"):
continue
elif pluginDirectory == "qmltooling" or pluginDirectory == "qml1tooling":
# Deploy the qml plugins only if QtDeclarative is in use
if not deploymentInfo.usesFramework("QtDeclarative"):
continue
elif pluginDirectory == "bearer":
# Deploy the bearer plugins only if QtNetwork is in use
if not deploymentInfo.usesFramework("QtNetwork"):
continue
elif pluginDirectory == "position":
# Deploy the position plugins only if QtPositioning is in use
if not deploymentInfo.usesFramework("QtPositioning"):
continue
elif pluginDirectory == "sensors" or pluginDirectory == "sensorgestures":
# Deploy the sensor plugins only if QtSensors is in use
if not deploymentInfo.usesFramework("QtSensors"):
continue
elif pluginDirectory == "audio" or pluginDirectory == "playlistformats":
# Deploy the audio plugins only if QtMultimedia is in use
if not deploymentInfo.usesFramework("QtMultimedia"):
continue
elif pluginDirectory == "mediaservice":
# Deploy the mediaservice plugins only if QtMultimediaWidgets is in use
if not deploymentInfo.usesFramework("QtMultimediaWidgets"):
continue
elif pluginDirectory == "canbus":
# Deploy the canbus plugins only if QtSerialBus is in use
if not deploymentInfo.usesFramework("QtSerialBus"):
continue
elif pluginDirectory == "webview":
# Deploy the webview plugins only if QtWebView is in use
if not deploymentInfo.usesFramework("QtWebView"):
continue
elif pluginDirectory == "gamepads":
# Deploy the webview plugins only if QtGamepad is in use
if not deploymentInfo.usesFramework("QtGamepad"):
continue
elif pluginDirectory == "geoservices":
# Deploy the webview plugins only if QtLocation is in use
if not deploymentInfo.usesFramework("QtLocation"):
continue
elif pluginDirectory == "texttospeech":
# Deploy the texttospeech plugins only if QtTextToSpeech is in use
if not deploymentInfo.usesFramework("QtTextToSpeech"):
continue
elif pluginDirectory == "virtualkeyboard":
# Deploy the virtualkeyboard plugins only if QtVirtualKeyboard is in use
if not deploymentInfo.usesFramework("QtVirtualKeyboard"):
continue
elif pluginDirectory == "sceneparsers":
# Deploy the virtualkeyboard plugins only if Qt3DCore is in use
if not deploymentInfo.usesFramework("Qt3DCore"):
continue
elif pluginDirectory == "renderplugins":
# Deploy the renderplugins plugins only if Qt3DCore is in use
if not deploymentInfo.usesFramework("Qt3DCore"):
continue
elif pluginDirectory == "geometryloaders":
# Deploy the geometryloaders plugins only if Qt3DCore is in use
if not deploymentInfo.usesFramework("Qt3DCore"):
continue

for pluginName in filenames:
pluginPath = os.path.join(pluginDirectory, pluginName)
if pluginName.endswith("_debug.dylib"):
# Skip debug plugins

if pluginName.split('.')[0] not in ['libqminimal', 'libqcocoa', 'libqmacstyle', 'libqsvg', 'libqsvgicon']:
continue
elif pluginPath == "imageformats/libqsvg.dylib" or pluginPath == "iconengines/libqsvgicon.dylib":
# Deploy the svg plugins only if QtSvg is in use
if not deploymentInfo.usesFramework("QtSvg"):
print ("qtSVG NOT FOUND")
continue
else:
print ("qtSVG FOUND!")
#a = deploymentInfo.usesFramework("QtSvg")
elif pluginPath == "accessible/libqtaccessiblecompatwidgets.dylib":
# Deploy accessibility for Qt3Support only if the Qt3Support is in use
if not deploymentInfo.usesFramework("Qt3Support"):
continue
elif pluginPath == "graphicssystems/libqglgraphicssystem.dylib":
# Deploy the opengl graphicssystem plugin only if QtOpenGL is in use
if not deploymentInfo.usesFramework("QtOpenGL"):
continue
elif pluginPath == "accessible/libqtaccessiblequick.dylib":
# Deploy the accessible qtquick plugin only if QtQuick is in use
if not deploymentInfo.usesFramework("QtQuick"):
continue
elif pluginPath == "platforminputcontexts/libqtvirtualkeyboardplugin.dylib":
# Deploy the virtualkeyboardplugin plugin only if QtVirtualKeyboard is in use
if not deploymentInfo.usesFramework("QtVirtualKeyboard"):
continue

plugins.append((pluginDirectory, pluginName))

Expand Down Expand Up @@ -528,6 +423,9 @@ if os.path.exists(appname + ".dmg"):
print("+ Removing existing DMG +")
os.unlink(appname + ".dmg")

if os.path.exists(appname + ".temp.dmg"):
os.unlink(appname + ".temp.dmg")

# ------------------------------------------------

target = os.path.join("dist", "PIVX-Qt.app")
Expand Down

0 comments on commit aadf4bb

Please sign in to comment.