From 7832cb30b33bd5f056cb26e230d6bdb8f5726932 Mon Sep 17 00:00:00 2001 From: Mike Solar Date: Sun, 19 Jul 2026 22:12:29 +0800 Subject: [PATCH] build: move render worker out of app/ into top-level worker/ - oak-render-worker now builds from worker/ (own CMakeLists.txt) as a peer of app/; RenderWorkerPool resolves the new build-tree location - deduplicated the Linux install() rules for the worker - worker-spawning tests resolve build/worker instead of build/app - cd.yml: Windows staging copies the worker from its new output path --- .github/workflows/cd.yml | 2 +- CMakeLists.txt | 1 + app/CMakeLists.txt | 45 +---------- app/render/renderworkerpool.cpp | 1 + tests/gtest/render_clip_buffer_hint_test.cpp | 4 +- tests/gtest/render_direct_connection_test.cpp | 4 +- tests/gtest/render_worker_footage_test.cpp | 4 +- tests/gtest/viewer_display_repro_test.cpp | 2 +- worker/CMakeLists.txt | 76 +++++++++++++++++++ {app/render/worker => worker}/workermain.cpp | 0 .../worker => worker}/workermain_mac.mm | 0 11 files changed, 89 insertions(+), 50 deletions(-) create mode 100644 worker/CMakeLists.txt rename {app/render/worker => worker}/workermain.cpp (100%) rename {app/render/worker => worker}/workermain_mac.mm (100%) diff --git a/.github/workflows/cd.yml b/.github/workflows/cd.yml index b614dbac3..9e66b425c 100644 --- a/.github/workflows/cd.yml +++ b/.github/workflows/cd.yml @@ -59,7 +59,7 @@ jobs: run: | mkdir -p app/packaging/windows/nsis/oak-editor cp build/app/oak-editor.exe app/packaging/windows/nsis/oak-editor/ - cp build/app/oak-render-worker.exe app/packaging/windows/nsis/oak-editor/ + cp build/worker/oak-render-worker.exe app/packaging/windows/nsis/oak-editor/ cp build/app/oakgl.dll app/packaging/windows/nsis/oak-editor/ if [ -f build/app/oakvulkan.dll ]; then cp build/app/oakvulkan.dll app/packaging/windows/nsis/oak-editor/ diff --git a/CMakeLists.txt b/CMakeLists.txt index 28ae29f3a..a4a779a5a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -309,6 +309,7 @@ add_subdirectory(third_party/KDDockWidgets EXCLUDE_FROM_ALL) add_subdirectory(third_party/openfx/HostSupport) add_subdirectory(app) +add_subdirectory(worker) if (BUILD_TESTS) enable_testing() diff --git a/app/CMakeLists.txt b/app/CMakeLists.txt index 92ab1b038..3ac4f2086 100644 --- a/app/CMakeLists.txt +++ b/app/CMakeLists.txt @@ -247,35 +247,8 @@ if (OAK_ENABLE_DYNAMIC_RENDER_BACKEND) add_dependencies(olive-editor oakvulkan) endif () endif () -# Ensure the render worker is always built together with the editor on every platform. -add_dependencies(olive-editor olive-render-worker) - set_target_properties(olive-editor PROPERTIES OUTPUT_NAME "oak-editor") -# Add render worker process (oak-render-worker). -# Reuses the libolive-editor object library so the worker shares the exact same render/node/codec -# code as the editor. It is a headless app that owns its own offscreen GL context. The link set is -# currently the full OLIVE_LIBRARIES for simplicity; trimming UI-only dependencies is a later-phase -# cleanup (see render-process-isolation plan). -add_executable(olive-render-worker - render/worker/workermain.cpp - $ - $ -) -set_target_properties(olive-render-worker PROPERTIES OUTPUT_NAME "oak-render-worker") -if (APPLE) - target_sources(olive-render-worker PRIVATE render/worker/workermain_mac.mm) - target_link_libraries(olive-render-worker PRIVATE "-framework Cocoa") -endif () -target_include_directories(olive-render-worker PUBLIC pluginSupport) -target_link_libraries(olive-render-worker PUBLIC OfxHost) -if (OAK_ENABLE_DYNAMIC_RENDER_BACKEND) - target_compile_definitions(olive-render-worker PRIVATE OAK_ENABLE_DYNAMIC_RENDER_BACKEND) - add_dependencies(olive-render-worker oakgl) - if (TARGET oakvulkan) - add_dependencies(olive-render-worker oakvulkan) - endif () -endif () # Create docs if doxygen was found if (DOXYGEN_FOUND) set(DOXYGEN_PROJECT_NAME "Oak Video Editor") @@ -331,15 +304,12 @@ elseif (APPLE) endif () elseif (UNIX) # Set Linux-specific properties for application - # The render worker must ship next to oak-editor: RenderWorkerPool spawns - # it from QCoreApplication::applicationDirPath() - install(TARGETS olive-editor olive-render-worker RUNTIME DESTINATION bin) + install(TARGETS olive-editor RUNTIME DESTINATION bin) endif () # Set link libraries target_link_libraries(olive-editor PRIVATE ${OLIVE_LIBRARIES}) target_link_libraries(libolive-editor PRIVATE ${OLIVE_LIBRARIES}) -target_link_libraries(olive-render-worker PRIVATE ${OLIVE_LIBRARIES}) # The ffmpeg_bridge shared library ships next to the binaries: inside the # macOS app bundle (Contents/MacOS, resolved via @loader_path), and in the @@ -348,14 +318,13 @@ if (APPLE) # macOS bundles are distributed via POST_BUILD copies (not install()), so # @loader_path must already be in the build-tree binaries' RPATH. set(OLIVE_FB_RPATH "@loader_path") - set_target_properties(olive-editor olive-render-worker PROPERTIES + set_target_properties(olive-editor PROPERTIES BUILD_RPATH "@loader_path") elseif (UNIX) set(OLIVE_FB_RPATH "$ORIGIN/../lib") endif () if (OLIVE_FB_RPATH) - set_target_properties(olive-editor olive-render-worker PROPERTIES - INSTALL_RPATH "${OLIVE_FB_RPATH}") + set_target_properties(olive-editor PROPERTIES INSTALL_RPATH "${OLIVE_FB_RPATH}") if (TARGET oakgl) set_target_properties(oakgl PROPERTIES INSTALL_RPATH "${OLIVE_FB_RPATH}") endif () @@ -367,22 +336,14 @@ endif () # Set compile options target_compile_options(olive-editor PRIVATE ${OLIVE_COMPILE_OPTIONS}) target_compile_options(libolive-editor PRIVATE ${OLIVE_COMPILE_OPTIONS}) -target_compile_options(olive-render-worker PRIVATE ${OLIVE_COMPILE_OPTIONS}) # Set global definitions target_compile_definitions(olive-editor PRIVATE ${OLIVE_DEFINITIONS}) target_compile_definitions(libolive-editor PRIVATE ${OLIVE_DEFINITIONS}) -target_compile_definitions(olive-render-worker PRIVATE ${OLIVE_DEFINITIONS}) # Set include dirs target_include_directories(olive-editor PRIVATE ${OLIVE_INCLUDE_DIRS}) target_include_directories(libolive-editor PRIVATE ${OLIVE_INCLUDE_DIRS}) -target_include_directories(olive-render-worker PRIVATE ${OLIVE_INCLUDE_DIRS}) - -# Install the render worker alongside the editor on Linux. -if (UNIX AND NOT APPLE) - install(TARGETS olive-render-worker RUNTIME DESTINATION bin) -endif () # Add crash handler if (GoogleCrashpad_FOUND AND Qt${QT_VERSION_MAJOR}Network_FOUND) diff --git a/app/render/renderworkerpool.cpp b/app/render/renderworkerpool.cpp index 43f7dcc03..5c40ce969 100644 --- a/app/render/renderworkerpool.cpp +++ b/app/render/renderworkerpool.cpp @@ -245,6 +245,7 @@ QString worker_program_path() const QStringList candidates = { QDir(app_dir).filePath(file), QDir(app_dir).filePath(QStringLiteral("../app/") + file), + QDir(app_dir).filePath(QStringLiteral("../worker/") + file), }; for (const QString &path : candidates) { diff --git a/tests/gtest/render_clip_buffer_hint_test.cpp b/tests/gtest/render_clip_buffer_hint_test.cpp index b90c6abb9..59ef1c8ab 100644 --- a/tests/gtest/render_clip_buffer_hint_test.cpp +++ b/tests/gtest/render_clip_buffer_hint_test.cpp @@ -69,11 +69,11 @@ QString demo_video_path() QString worker_binary_path() { // The test binary lives in cmake-build-debug/tests/gtest; the worker is in - // cmake-build-debug/app. + // cmake-build-debug/worker. QDir dir(QCoreApplication::applicationDirPath()); dir.cdUp(); // tests/gtest -> tests dir.cdUp(); // tests -> build dir - dir.cd(QStringLiteral("app")); + dir.cd(QStringLiteral("worker")); #if defined(_WIN32) return dir.filePath(QStringLiteral("oak-render-worker.exe")); #else diff --git a/tests/gtest/render_direct_connection_test.cpp b/tests/gtest/render_direct_connection_test.cpp index 7a80760cb..717764b80 100644 --- a/tests/gtest/render_direct_connection_test.cpp +++ b/tests/gtest/render_direct_connection_test.cpp @@ -56,11 +56,11 @@ QString demo_video_path() QString worker_binary_path() { // The test binary lives in cmake-build-debug/tests/gtest; the worker is in - // cmake-build-debug/app. + // cmake-build-debug/worker. QDir dir(QCoreApplication::applicationDirPath()); dir.cdUp(); // tests/gtest -> tests dir.cdUp(); // tests -> build dir - dir.cd(QStringLiteral("app")); + dir.cd(QStringLiteral("worker")); #if defined(_WIN32) return dir.filePath(QStringLiteral("oak-render-worker.exe")); #else diff --git a/tests/gtest/render_worker_footage_test.cpp b/tests/gtest/render_worker_footage_test.cpp index b42f0e311..29bf0cbd8 100644 --- a/tests/gtest/render_worker_footage_test.cpp +++ b/tests/gtest/render_worker_footage_test.cpp @@ -93,11 +93,11 @@ constexpr int k_timeout_ms = 30000; QString worker_binary_path() { // The test binary lives in cmake-build-debug/tests/gtest; the worker is in - // cmake-build-debug/app. + // cmake-build-debug/worker. QDir dir(QCoreApplication::applicationDirPath()); dir.cdUp(); // tests/gtest -> tests dir.cdUp(); // tests -> build dir - dir.cd(QStringLiteral("app")); + dir.cd(QStringLiteral("worker")); #if defined(_WIN32) return dir.filePath(QStringLiteral("oak-render-worker.exe")); #else diff --git a/tests/gtest/viewer_display_repro_test.cpp b/tests/gtest/viewer_display_repro_test.cpp index 9dcab12e5..2204a2d16 100644 --- a/tests/gtest/viewer_display_repro_test.cpp +++ b/tests/gtest/viewer_display_repro_test.cpp @@ -59,7 +59,7 @@ QString worker_binary_path_t() QDir dir(QCoreApplication::applicationDirPath()); dir.cdUp(); dir.cdUp(); - dir.cd(QStringLiteral("app")); + dir.cd(QStringLiteral("worker")); #if defined(_WIN32) return dir.filePath(QStringLiteral("oak-render-worker.exe")); #else diff --git a/worker/CMakeLists.txt b/worker/CMakeLists.txt new file mode 100644 index 000000000..5fe6721ae --- /dev/null +++ b/worker/CMakeLists.txt @@ -0,0 +1,76 @@ +# Oak - Non-Linear Video Editor +# Copyright (C) 2026 Oak Team +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . + +# Render worker process (oak-render-worker). +# +# The worker is a headless render process spawned by the editor through +# RenderWorkerPool. It reuses the libolive-editor object library so it +# shares the exact same render/node/codec code as the editor. The link set +# is currently the full OLIVE_LIBRARIES for simplicity; trimming UI-only +# dependencies is a later-phase cleanup (render-process-isolation plan). +add_executable(olive-render-worker + workermain.cpp + $ + $ +) +set_target_properties(olive-render-worker PROPERTIES OUTPUT_NAME "oak-render-worker") + +if (APPLE) + target_sources(olive-render-worker PRIVATE workermain_mac.mm) + target_link_libraries(olive-render-worker PRIVATE "-framework Cocoa") +endif () + +# CMAKE_INCLUDE_CURRENT_DIR only covers the app/ scope, so add the app +# include roots explicitly now that the worker lives outside it +target_include_directories(olive-render-worker PRIVATE + ${CMAKE_SOURCE_DIR}/app + ${CMAKE_BINARY_DIR}/app + ${CMAKE_SOURCE_DIR}/app/pluginSupport + ${OLIVE_INCLUDE_DIRS}) + +target_link_libraries(olive-render-worker PUBLIC OfxHost) +target_link_libraries(olive-render-worker PRIVATE ${OLIVE_LIBRARIES}) +target_compile_options(olive-render-worker PRIVATE ${OLIVE_COMPILE_OPTIONS}) +target_compile_definitions(olive-render-worker PRIVATE ${OLIVE_DEFINITIONS}) + +if (OAK_ENABLE_DYNAMIC_RENDER_BACKEND) + target_compile_definitions(olive-render-worker PRIVATE OAK_ENABLE_DYNAMIC_RENDER_BACKEND) + add_dependencies(olive-render-worker oakgl) + if (TARGET oakvulkan) + add_dependencies(olive-render-worker oakvulkan) + endif () +endif () + +# The ffmpeg_bridge shared library ships next to the binaries: inside the +# macOS app bundle (Contents/MacOS, resolved via @loader_path), and in the +# standard lib directory on other platforms. +if (APPLE) + set_target_properties(olive-render-worker PROPERTIES + BUILD_RPATH "@loader_path" + INSTALL_RPATH "@loader_path") +elseif (UNIX) + set_target_properties(olive-render-worker PROPERTIES + INSTALL_RPATH "$ORIGIN/../lib") +endif () + +# The editor always needs the worker next to it (macOS bundle POST_BUILD +# copies, Linux install() into the same bin directory) +add_dependencies(olive-editor olive-render-worker) + +# Install the render worker alongside the editor on Linux. +if (UNIX AND NOT APPLE) + install(TARGETS olive-render-worker RUNTIME DESTINATION bin) +endif () diff --git a/app/render/worker/workermain.cpp b/worker/workermain.cpp similarity index 100% rename from app/render/worker/workermain.cpp rename to worker/workermain.cpp diff --git a/app/render/worker/workermain_mac.mm b/worker/workermain_mac.mm similarity index 100% rename from app/render/worker/workermain_mac.mm rename to worker/workermain_mac.mm