Skip to content
qbittorrent-nox-static

Patching

The script supports automatic patching of all modules during build with a sophisticated three-method priority system. The patching system works hierarchically to ensure maximum flexibility:

Method 1: Source Directory (Highest Priority)

  • Complete source file replacement via patches/{module}/{version}/source/ directory
  • Files are directly copied to the build directory, overwriting existing files
  • Most flexible method for extensive modifications

Method 2: Patch Files (Local)

  • Traditional unified diff patches applied via git apply or patch command
  • Multiple patch sources supported with intelligent merging:
    • patch file (primary patch)
    • url file (downloads and merges remote patches)
    • *.patch and *.diff files (merged in alphabetical order)
  • Auto-detects git repositories and uses appropriate patching method

Method 3: Remote Patches (Fallback)

  • Downloads patches from remote GitHub repositories when local patches are empty/missing
  • Uses GitHub API for comprehensive directory structure downloads
  • Supports both individual files and complete directory trees
  • Validates branch names for security

Here is an example local directory structure that the script will use to apply patches to libtorrent v1.2.19 and qBittorrent release-5.0.3

  • qbt-nox-static.bash
  • Directoryqbt-build/
    • Directorypatches/
      • Directorylibtorrent/
        • Directoryv1.2.19/
          • patch # Primary patch file
          • url # URL to download remote patch
          • 01.patch # Additional patch file
          • 02.diff # Additional diff file
          • Directorysource/ # Source directory (highest priority)
            • Directoryinclude/
            • Directorysrc/
      • Directoryqbittorrent/
        • Directory5.0.3/
          • patch # Primary patch file
          • url # URL to download remote patch
          • custom.patch # Additional patch file
          • Directorysource/ # Source directory (highest priority)
            • Directorysrc/
              • Directorywebui/
                • webui.cpp # Modified source file

Multi-Patch Merging:

  • When multiple patches exist, they are intelligently merged into a single unified patch
  • Merge order: patch file → url download → *.patch/*.diff files (alphabetical)
  • Each merged patch is labeled with its source for debugging
  • Temporary atomic operations prevent corruption during merging

Smart Patch Application:

  • Auto-detects if source directory contains a git repository
  • Uses git apply for git repositories (with validation via --check)
  • Falls back to traditional patch -p1 for non-git sources
  • Comprehensive error handling and status reporting

Remote Patch Security:

  • Branch name validation using regex ^[a-zA-Z0-9._-]+$
  • GitHub API integration with proper error handling
  • Recursive directory download with JSON parsing validation
  • Automatic cleanup of zero-byte failed downloads

By default the script installs to a build directory that is a sub directory relative to the script location. This means that if you clone the git repo and run the script it won’t find the local patches. There are few ways to handle this.

  • Option 1: Default, the script assumes you will prepare the environment before building by using the bootstrapping feature. This will create the required directory structure, then you copy the patch files to the correct location as needed.

  • Option 2: Clone the repo and copy the patches to the correct location

    git clone --depth 1 https://github.com/userdocs/qbittorrent-nox-static.git
    cd qbittorrent-nox-static
    mkdir -p qbt-build
    cp -r patches qbt-build/
  • Option 3: You can set the build dir to the root of the github repo and the script will find the patches

    export qbt_build_dir="."
  • Option 4: Upload the patches to a remote github repo with the patches dir in the repo root and use the pr switch or qbt_patches_url env to specify the repo URL. The script will download the patches from the remote location and apply them.

  • Option 5: Do nothing and the script will use the default remote patch repo userdocs/qbittorrent-nox-static to apply patches

When bootstrapping the script will create the required directory structure using the current defaults and it will look like this:

qbt-build/patches/zlib/1.3.1.1
qbt-build/patches/iconv/1.18
qbt-build/patches/icu/77-1
qbt-build/patches/openssl/3.5.2
qbt-build/patches/boost/1.89.0
qbt-build/patches/libtorrent/2.0.11
qbt-build/patches/double_conversion/3.3.1
qbt-build/patches/qtbase/6.9.2
qbt-build/patches/qttools/6.9.2
qbt-build/patches/qbittorrent/5.1.2
Section titled “Method 1: Source Directory Method (Recommended)”

This is the most flexible method for extensive modifications. Instead of creating patches, you directly modify source files:

Step 1: Bootstrap the patches directory

./qbt.bash -bs-p

Step 2: Clone the target repository with the specific version

git clone --branch release-5.0.3 --depth 1 https://github.com/qbittorrent/qBittorrent.git

Step 3: Copy the entire source tree to your patch directory

cp -r qBittorrent/* qbt-build/patches/qbittorrent/5.0.3/source/

Step 4: Edit files directly in the source directory

# Edit the file you need to modify
nano qbt-build/patches/qbittorrent/5.0.3/source/src/webui/webui.cpp

Step 5: Build with your modifications

./qbt.bash all

The script will automatically detect the source directory and copy all files to the build location, overwriting the original source.

For smaller, targeted changes, traditional patch files are more efficient:

Step 1: Bootstrap and prepare source

./qbt.bash -bs-p
git clone --branch release-5.0.3 --depth 1 https://github.com/qbittorrent/qBittorrent.git

Step 2: Make a backup and edit the file

cp qBittorrent/src/webui/webui.cpp webui.cpp.orig
cp qBittorrent/src/webui/webui.cpp webui.cpp
# Edit webui.cpp with your changes
nano webui.cpp

Step 3: Create the patch file

diff -Naru webui.cpp.orig webui.cpp > qbt-build/patches/qbittorrent/5.0.3/patch

Step 4: Build with the patch

./qbt.bash all

The script supports merging multiple patch files automatically:

# Place multiple patches in the patch directory
echo "patch content 1" > qbt-build/patches/qbittorrent/5.0.3/01-feature-a.patch
echo "patch content 2" > qbt-build/patches/qbittorrent/5.0.3/02-feature-b.patch
echo "patch content 3" > qbt-build/patches/qbittorrent/5.0.3/99-final-fixes.diff

The script will merge all *.patch and *.diff files in alphabetical order into a single unified patch.

Download and apply patches from remote URLs:

# Create a URL file pointing to a remote patch
echo "https://github.com/qbittorrent/qBittorrent/pull/18271.patch" > qbt-build/patches/qbittorrent/5.0.3/url

The script will download and apply the patch automatically during build.

Some modules like libtorrent and qbittorrent have multiple tags that can be used and they can be passed to the script as variables or switches. The script will use the default tags if none are provided.

Using the -qt and -lt switches here:

~/qbt.bash -qt master -lt RC_2_0 -bs

or

export qbt_qbittorrent_tag=master
export qbt_libtorrent_tag=RC_2_0

The bootstrapped directory structure would look like this instead:

qbt-build/patches/qbittorrent/master
qbt-build/patches/libtorrent/RC_2_0
qbt.bash -qt master -lt RC_2_0 all

The script can automatically download patches from GitHub repositories using the -pr switch or qbt_patches_url environment variable.

Your patches need to be hosted in a GitHub repository with this structure:

patches/qbittorrent/master/patch
patches/qbittorrent/master/url
patches/qbittorrent/master/01-custom.patch
patches/qbittorrent/master/source/src/webui/webui.cpp
patches/qbittorrent/4.5.0/patch
patches/qbittorrent/4.5.0/source/

Method 1: Command line switch

./qbt.bash all -pr username/repository

Method 2: Environment variable

export qbt_patches_url="username/repository"
./qbt.bash all

Recursive Directory Downloads: The script uses GitHub API to recursively download entire directory structures, including nested source/ directories and multiple patch files.

Comprehensive File Support: Downloads all patch-related files:

  • patch files (primary patches)
  • url files (for chained remote patches)
  • *.patch and *.diff files
  • Complete source/ directory trees

Fallback System: If GitHub API fails, the script falls back to downloading common patch filenames directly.

Using qbittorrent as an example we will edit the src/base/bittorrent/session.cpp to apply some session defaults.

Download the relevant git repo:

git clone --no-tags --single-branch --branch release-4.5.0 --shallow-submodules --recurse-submodules --depth 1 https://github.com/qbittorrent/qBittorrent.git

Copy the file that we need to edit to our home directory.

cp qBittorrent/src/base/bittorrent/session.cpp ~/session.cpp

Now edit the ~/session.cpp. Once you have finished making your changes you can create a patch file using this command

diff -Naru qBittorrent/src/base/bittorrent/session.cpp ~/session.cpp > ~/patch

Then you place that patch file in the matching tag directory.

patches/qbittorrent/4.3.4.1/patch

First, it’s sensible to make sure the patch that we want to use is from a pull request on the same branch that we are building against. So when using release-4.5.0 we should use https://github.com/qbittorrent/qBittorrent/tree/v4_5_x

You can see the branches for qBittorrent here - https://github.com/qbittorrent/qBittorrent/branches

When you are on a commit or pull request you simply add .patch to the end of the url.

So here we take the pull request or commit URL

https://github.com/qbittorrent/qBittorrent/pull/18271

https://github.com/qbittorrent/qBittorrent/commit/c924904308e806db6e1b321da18c1f91c4e8f8bf

and add .patch to it so it becomes this

https://github.com/qbittorrent/qBittorrent/pull/18271.patch

https://github.com/qbittorrent/qBittorrent/commit/c924904308e806db6e1b321da18c1f91c4e8f8bf.patch

You can download these using curl or wget and use these as patches in custom builds.

The script provides detailed output during patch application:

  • Method Selection: Shows which patching method is being used
  • File Merging: Labels each merged patch with its source
  • Application Status: Reports success/failure of patch operations
  • Git Detection: Indicates whether git apply or traditional patch is used

Patch Organization:

  • Use descriptive filenames for multiple patches (e.g., 01-security-fix.patch, 02-performance.patch)
  • Keep patches atomic - one logical change per patch file
  • Test patches individually before combining

Source Directory Method:

  • Only include modified files to minimize disk usage
  • Maintain directory structure matching the original source
  • Consider using git to track your modifications in the source directory

Remote Patch Security:

  • Always review remote patches before applying
  • Use trusted repositories for remote patches
  • Consider forking and hosting your own patch repositories

Version Management:

  • Keep patches aligned with specific module versions
  • Test patches when updating module versions
  • Document patch purposes and compatibility

Patch Application Failures:

  • Check patch format (unified diff with -Naru options)
  • Verify patch applies to correct source version
  • Ensure proper line endings (Unix LF, not Windows CRLF)

Remote Download Issues:

  • Verify GitHub repository structure matches expected format
  • Check network connectivity and GitHub API limits
  • Use local patches as fallback for critical builds

The cache folder system serves as an offline dependency system for storing and modifying source files:

Advantages:

  • Persistent modifications across builds
  • Version-specific source storage via git checkout
  • More flexible than patch directory method
  • Allows comprehensive source tree modifications

Usage:

  1. Enable cache folder system in script configuration
  2. Modify source files directly in cached directories
  3. Files are automatically copied to build directory during compilation

This method complements the patch system and provides another layer of source customization flexibility.