Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 10 additions & 0 deletions cmake/defaults/CY2023.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2023")
ENDIF()
ENDIF()

# Cryptography https://cryptography.io/en/latest/changelog/
SET(RV_DEPS_CRYPTOGRAPHY_VERSION
"42.0.5"
)

# Imath Can find the build version in OpenRV/_build/RV_DEPS_IMATH/install/lib/
SET(RV_DEPS_IMATH_VERSION
"3.1.12"
Expand Down Expand Up @@ -108,6 +113,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2023")
"1_1"
)

# Pydantic https://docs.pydantic.dev/latest/changelog/
SET(RV_DEPS_PYDANTIC_VERSION
"2.7.1"
)

# PySide
SET(RV_DEPS_PYSIDE_TARGET
"RV_DEPS_PYSIDE2"
Expand Down
10 changes: 10 additions & 0 deletions cmake/defaults/CY2024.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2024")
"f7050f554a65f6a42ece221eaeec1660"
)

# Cryptography https://cryptography.io/en/latest/changelog/
SET(RV_DEPS_CRYPTOGRAPHY_VERSION
"42.0.5"
)

# Imath Can find the build version in OpenRV/_build/RV_DEPS_IMATH/install/lib/
SET(RV_DEPS_IMATH_VERSION
"3.1.12"
Expand Down Expand Up @@ -82,6 +87,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2024")
"3"
)

# Pydantic https://docs.pydantic.dev/latest/changelog/
SET(RV_DEPS_PYDANTIC_VERSION
"2.7.1"
)

# PySide
SET(RV_DEPS_PYSIDE_VERSION
"6.5.3"
Expand Down
10 changes: 10 additions & 0 deletions cmake/defaults/CY2025.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2025")
"53aeccc3167909ee770e34469f8dd592"
)

# Cryptography https://cryptography.io/en/latest/changelog/
SET(RV_DEPS_CRYPTOGRAPHY_VERSION
"42.0.5"
)

# Imath Can find the build version in OpenRV/_build/RV_DEPS_IMATH/install/lib/
SET(RV_DEPS_IMATH_VERSION
"3.1.12"
Expand Down Expand Up @@ -82,6 +87,11 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2025")
"3"
)

# Pydantic https://docs.pydantic.dev/latest/changelog/
SET(RV_DEPS_PYDANTIC_VERSION
"2.7.1"
)

# PySide
SET(RV_DEPS_PYSIDE_VERSION
"6.5.3"
Expand Down
20 changes: 20 additions & 0 deletions cmake/defaults/CY2026.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,19 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2026")
"6cd58b3cc890e4fbbc036c7629129e18"
)

# Cryptography https://cryptography.io/en/latest/changelog/ Newer than the CY2024/CY2025 pin because Python 3.13 needs it: 42.x vendors pyo3-ffi 0.20, whose
# build aborts with "the configured Python interpreter version (3.13) is newer than PyO3's maximum supported version (3.12)".
SET(RV_DEPS_CRYPTOGRAPHY_VERSION
"45.0.7"
)

# Cython https://github.com/cython/cython/releases Pinned because numpy 2.3.0 declares an unbounded "Cython>=3.0.6" build requirement, so pip's build
# isolation would otherwise resolve the newest Cython. Cython 3.3.0 breaks Meson's cython sanity check ("Compiler cython cannot compile programs") when
# building numpy from source. CY2023-CY2025 do not need this: their numpy versions cap Cython themselves (<3.0 / <3.1).
SET(RV_DEPS_CYTHON_VERSION
"3.2.9"
)

# Imath Can find the build version in OpenRV/_build/RV_DEPS_IMATH/install/lib/
SET(RV_DEPS_IMATH_VERSION
"3.2.2"
Expand Down Expand Up @@ -82,6 +95,13 @@ IF(RV_VFX_PLATFORM STREQUAL "CY2026")
"3"
)

# Pydantic https://docs.pydantic.dev/latest/changelog/ Newer than the CY2024/CY2025 pin because Python 3.13 needs it: pydantic 2.7 pulls in pydantic-core
# 2.18, whose build-time generate_self_schema.py calls ForwardRef._evaluate() with the pre-3.13 signature and fails with "missing 1 required keyword-only
# argument: 'recursive_guard'".
SET(RV_DEPS_PYDANTIC_VERSION
"2.11.10"
)

# PySide
SET(RV_DEPS_PYSIDE_VERSION
"6.8.3"
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
--- a/build_scripts/platforms/macos.py
+++ b/build_scripts/platforms/macos.py
@@ -18,6 +18,9 @@
upper_name = name.capitalize()
bundle = f"{{st_build_dir}}/{{st_package_name}}/{upper_name}.app".format(**_vars)
binary = f"{bundle}/Contents/MacOS/{upper_name}"
+ if not Path(binary).exists():
+ log.info(f"**Skipping rpath patching of {binary}. Tool was not bundled.")
+ return
rpath = "@loader_path/../../../Qt/lib"
macos_add_rpath(rpath, binary)

@@ -174,6 +177,7 @@
plugins_target / "designer",
_filter=filters,
recursive=False,
+ force=False,
_vars=_vars)

if copy_qml:
--- a/build_scripts/platforms/linux.py
+++ b/build_scripts/platforms/linux.py
@@ -79,6 +79,9 @@

for tool in PYSIDE_UNIX_BUNDLED_TOOLS:
tool_path = destination_dir / tool
+ if not tool_path.exists():
+ log.info(f"**Skipping rpath patching of {tool_path}. Tool was not bundled.")
+ continue
linux_patch_executable(pyside_build._patchelf_path, tool_path)

if pyside_build.is_webengine_built(built_modules):
@@ -101,6 +104,7 @@
plugins_target / "designer",
_filter=["*.so"],
recursive=False,
+ force=False,
_vars=_vars)

copied_plugins = pyside_build.get_shared_libraries_in_path_recursively(
--- a/build_scripts/platforms/windows_desktop.py
+++ b/build_scripts/platforms/windows_desktop.py
@@ -393,6 +393,7 @@
f"{plugins_target}/designer",
_filter=["*.dll"],
recursive=False,
+ force=False,
_vars=_vars)

if copy_translations:
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
--- a/sources/pyside-tools/CMakeLists.txt
+++ b/sources/pyside-tools/CMakeLists.txt
@@ -79,13 +79,17 @@
endforeach()

foreach(directory ${directories})
- install(DIRECTORY "${directory}"
- DESTINATION bin
- FILE_PERMISSIONS
- OWNER_EXECUTE OWNER_WRITE OWNER_READ
- GROUP_EXECUTE GROUP_READ
- WORLD_EXECUTE WORLD_READ
- PATTERN "android_utilities.py" EXCLUDE) # excluding the symlink
+ if(EXISTS ${directory})
+ install(DIRECTORY "${directory}"
+ DESTINATION bin
+ FILE_PERMISSIONS
+ OWNER_EXECUTE OWNER_WRITE OWNER_READ
+ GROUP_EXECUTE GROUP_READ
+ WORLD_EXECUTE WORLD_READ
+ PATTERN "android_utilities.py" EXCLUDE) # excluding the symlink
+ else()
+ message(WARNING "${directory} does not exist. Hence, the matching pyside6 tool will not work")
+ endif()
endforeach()

# dealing with android_utilities.py
56 changes: 51 additions & 5 deletions cmake/dependencies/python3.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,25 @@ SET(_numpy_version
"${RV_DEPS_NUMPY_VERSION}"
)

SET(_cryptography_version
"${RV_DEPS_CRYPTOGRAPHY_VERSION}"
)

SET(_pydantic_version
"${RV_DEPS_PYDANTIC_VERSION}"
)

# Cython is only constrained on the VFX platforms whose numpy leaves its own Cython build requirement unbounded. See src/build/pip-build-constraints.txt.in.
IF(RV_DEPS_CYTHON_VERSION)
SET(_cython_constraint
"Cython==${RV_DEPS_CYTHON_VERSION}"
)
ELSE()
SET(_cython_constraint
"# Cython intentionally unconstrained: this platform's numpy pins its own Cython upper bound."
)
ENDIF()

SET(_python3_download_url
"https://github.com/python/cpython/archive/refs/tags/v${_python3_version}.zip"
)
Expand All @@ -68,11 +87,27 @@ SET(_build_dir
${RV_DEPS_BASE_DIR}/${_python3_target}/build
)

# PySide6's pyside-tools and standalone packaging assume Qt Designer/Assistant/Linguist were bundled. macOS .app installs, Linux patchelf rpath patching, and
# Windows/Linux designer-plugin copies all fail when the Qt build does not ship those tools. CY2026's Qt 6.8 build omits Designer; the patch makes each step
# skip-with-warning like the individual tool file install loop.
SET(_pyside_patch_command
${CMAKE_COMMAND} -E true
)
IF(RV_VFX_PLATFORM STREQUAL CY2026)
SET(_pyside_patch_script
"${PROJECT_SOURCE_DIR}/src/build/apply_pyside6_tools_patch.py"
)
SET(_pyside_patch_command
python3 "${_pyside_patch_script}" "<SOURCE_DIR>" "${CMAKE_CURRENT_LIST_DIR}/patch"
)
ENDIF()

FETCHCONTENT_DECLARE(
${_pyside_target}
URL ${_pyside_archive_url}
URL_HASH MD5=${_pyside_download_hash}
SOURCE_SUBDIR "sources" # Avoids the top level CMakeLists.txt
PATCH_COMMAND ${_pyside_patch_command}
)

FETCHCONTENT_MAKEAVAILABLE(${_pyside_target})
Expand Down Expand Up @@ -250,12 +285,22 @@ SET(_requirements_output_file

CONFIGURE_FILE(${_requirements_input_file} ${_requirements_output_file} @ONLY)

# Constraints for pip's build-isolation environments. PIP_CONSTRAINT must be an absolute path: pip resolves it relative to each build-environment subprocess
# working directory. PIP_BUILD_CONSTRAINT is required on pip >= 26.2 to constrain build-isolation envs; set both since RV_PYTHON_BUILD_DEPS installs an unpinned
# pip.
# Generate pip-build-constraints.txt from template. Unlike requirements.txt this one is exported as PIP_CONSTRAINT/PIP_BUILD_CONSTRAINT so that pip's PEP 517
# build-isolation environments inherit our pins: format control propagates into those environments but version pins do not.
SET(_pip_build_constraints_input_file
"${PROJECT_SOURCE_DIR}/src/build/pip-build-constraints.txt.in"
)
SET(_pip_constraint_file
"${PROJECT_SOURCE_DIR}/src/build/pip-build-constraints.txt"
"${CMAKE_BINARY_DIR}/pip-build-constraints.txt"
)

CONFIGURE_FILE(${_pip_build_constraints_input_file} ${_pip_constraint_file} @ONLY)

# Both env vars point at the same file and must be absolute paths: pip's build-environment subprocesses run with their working directory inside the unpacked
# source distribution. The python -s -E -I flags below do not strip either, -E only ignores PYTHON* variables. PIP_CONSTRAINT pins the outer/main resolve
# (requirements.txt itself, and build-isolation envs on pip < 26.2). PIP_BUILD_CONSTRAINT pins build-isolation envs on pip >= 26.2, where PIP_CONSTRAINT was
# deprecated for that purpose (pip issue: build constraints must be requested explicitly via --build-constraint / PIP_BUILD_CONSTRAINT). RV_PYTHON_BUILD_DEPS
# installs an unpinned "pip", so the newest pip is always in play and both variables are needed for the fix to hold across pip versions.
SET(_pip_constraint_env
"PIP_CONSTRAINT=${_pip_constraint_file}" "PIP_BUILD_CONSTRAINT=${_pip_constraint_file}"
)
Expand Down Expand Up @@ -497,7 +542,7 @@ ADD_CUSTOM_COMMAND(
OUTPUT ${${_python3_target}-build-deps-flag}
COMMAND ${_build_deps_install_command}
COMMAND cmake -E touch ${${_python3_target}-build-deps-flag}
DEPENDS ${_python3_target} ${_pip_constraint_file}
DEPENDS ${_python3_target} ${_pip_constraint_file} ${_pip_build_constraints_input_file}
)

# Phase 2 flag: Main requirements (depends on build deps being installed first)
Expand All @@ -511,6 +556,7 @@ ADD_CUSTOM_COMMAND(
COMMAND ${_requirements_install_command}
COMMAND cmake -E touch ${${_python3_target}-requirements-flag}
DEPENDS ${_python3_target} ${${_python3_target}-build-deps-flag} ${_requirements_output_file} ${_requirements_input_file} ${_pip_constraint_file}
${_pip_build_constraints_input_file}
)

# Test Python package imports after requirements are installed. This validates that all pip-installed packages (numpy, opentimelineio, OpenGL, cryptography,
Expand Down
47 changes: 47 additions & 0 deletions cmake/dependencies/qt6.cmake
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,53 @@ IF(RV_TARGET_DARWIN)
)
ENDIF()
ENDFOREACH()

# QtWebEngine runs its Chromium renderer in a separate QtWebEngineProcess child. If that helper carries the hardened runtime WITHOUT the entitlements Chromium
# needs (allow-jit, allow-unsigned-executable-memory, disable-library-validation), macOS kills the renderer with SIGTRAP as soon as V8 starts. QtWebEngine
# reports "ProcessGone: 3 (5)" and every QWebEngineView (Live Review, the Flow Production Tracking browser, the Mu doc browser) renders blank. Re-signing
# without --options runtime drops the hardened runtime and fixes it.
#
# The signing identity is irrelevant: re-signing ad-hoc but keeping --options runtime reproduces the crash exactly. Only the hardened-runtime flag matters,
# which is why the check below keys on "runtime" and not on whether the signature is ad-hoc. Note that flags=0x10002(adhoc,runtime) is both ad-hoc and broken.
#
# Qt's own macOS binaries (qt.io installer, aqtinstall) are ad-hoc/linker-signed with no hardened runtime, so this skips them entirely. It triggers for
# redistributions that re-sign Qt with --options runtime; Autodesk's LGPL Qt package does exactly that, with no entitlements, for every framework it ships.
#
# Sign inside-out: the nested helper .app first, then the framework. Using --deep on the framework instead leaves it reporting "embedded framework contains
# modified or invalid version".
#
# Release builds are unaffected either way: they re-sign the bundle with --options runtime AND build/entitlements.plist, which grants all three relaxations.
# Note that stripping the signature outright is NOT an option, because arm64 binaries must carry at least an ad-hoc signature.
SET(_qt_webengine_framework
${RV_STAGE_FRAMEWORKS_DIR}/QtWebEngineCore.framework
)
IF(EXISTS ${_qt_webengine_framework})
# codesign -dv reports on stderr. Match the hardened-runtime bit inside the decoded flags, e.g. flags=0x10000(runtime) or flags=0x10002(adhoc,runtime).
# Anchoring on the flags list avoids matching the unrelated "Runtime Version=" line.
EXECUTE_PROCESS(
COMMAND codesign -dv ${_qt_webengine_framework}
OUTPUT_QUIET
ERROR_VARIABLE _qt_webengine_signature_info
)
IF(_qt_webengine_signature_info MATCHES "flags=[^(]*\\([^)]*runtime")
MESSAGE(STATUS "QtWebEngineCore carries the hardened runtime; re-signing it without, so Chromium's renderer can start")
FILE(GLOB _qt_webengine_helpers ${_qt_webengine_framework}/Versions/A/Helpers/*.app)
FOREACH(
_qt_webengine_signable
${_qt_webengine_helpers} ${_qt_webengine_framework}
)
EXECUTE_PROCESS(
COMMAND codesign --force --sign - ${_qt_webengine_signable}
RESULT_VARIABLE _qt_webengine_codesign_result
OUTPUT_QUIET
ERROR_VARIABLE _qt_webengine_codesign_error
)
IF(NOT _qt_webengine_codesign_result EQUAL 0)
MESSAGE(WARNING "Could not ad-hoc sign ${_qt_webengine_signable}: ${_qt_webengine_codesign_error}")
ENDIF()
ENDFOREACH()
ENDIF()
ENDIF()
ENDIF()

# Linux
Expand Down
2 changes: 1 addition & 1 deletion ruff.toml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ exclude = [
"src/plugins/rv-packages/custom_lut_menu_mode/custom_lut_menu_mode.py" = ["F821"]
"src/plugins/python/gtoContainer/gtoContainer.py" = ["F403", "F405"]
"src/lib/mu/MuQt6/qt6_to_mu.py" = ["E731", "F821", "F841"]
"src/lib/mu/MuQt6/qt2mu.py" = ["E731", "F821", "F841"]
"src/lib/mu/MuQt6/qt68_to_mu.py" = ["E731", "F821", "F841"]
"src/lib/mu/MuQt5/qt515_to_mu.py" = ["E731", "F821", "F841"]
"src/lib/mu/MuQt5/qt512_to_mu.py" = ["E731", "F821", "F841"]
"src/lib/mu/MuQt5/qt2mu.py" = ["E731", "F821", "F841"]
Expand Down
2 changes: 1 addition & 1 deletion src/bin/apps/rvprof/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ TARGET_LINK_LIBRARIES(
${_target}
PRIVATE TwkMath
TwkGLText
OpenGL::GLU
OpenGL::GL
Qt::Gui
Qt::OpenGL
Qt::Widgets
Expand Down
7 changes: 1 addition & 6 deletions src/bin/apps/rvprof/VisMainWindow.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,11 +7,6 @@
#include <iostream>
#include <TwkGLText/TwkGLText.h>
#include <sstream>
#ifdef PLATFORM_DARWIN
#include <OpenGL/glu.h>
#else
#include <GL/glu.h>
#endif

using namespace TwkGLText;

Expand Down Expand Up @@ -1025,7 +1020,7 @@ void GLView::paintGL()
glMatrixMode(GL_PROJECTION);
glLoadIdentity();
double l = (m_endTime - m_startTime) / double(width());
gluOrtho2D(0, m_endTime - m_startTime, 0, l * double(height()));
glOrtho(0, m_endTime - m_startTime, 0, l * double(height()), -1, 1);
glEnable(GL_POLYGON_SMOOTH);

glMatrixMode(GL_MODELVIEW);
Expand Down
Loading
Loading