Skip to content

Allow CMake 3.x with zlib 1.3.2#80

Open
TheNicker wants to merge 2 commits into
agruzdev:masterfrom
TheNicker:cmake3
Open

Allow CMake 3.x with zlib 1.3.2#80
TheNicker wants to merge 2 commits into
agruzdev:masterfrom
TheNicker:cmake3

Conversation

@TheNicker
Copy link
Copy Markdown

@TheNicker TheNicker commented May 14, 2026

Summary

Fixes #77.

This PR contains two separate zlib-related fixes.

First, the project currently requires CMake 4.2 because that version's FindZLIB module recognizes zlib 1.3.2's Windows static library names, zs.lib and zsd.lib. That lookup detail is local to the bundled zlib dependency, so this PR keeps the CMake minimum in the 3.x line and passes the exact zlib library path to downstream dependency builds that call find_package(ZLIB).

Second, clean Ninja builds need the installed zlib static library to be declared as an ExternalProject byproduct. This issue is independent of CMake 4.2's ability to find zlib: even when the correct zlib library path is known, Ninja still needs a build rule that says the zlib install step produces that file before FreeImage links against it.

Changes

  • Change the top-level CMake requirement to 3.28...4.2.
  • Keep zlib 1.3.2 and its zs / zsd Windows static library naming.
  • Reuse the known zlib library path from dependency.zlib.cmake.
  • Pass ZLIB_LIBRARY to PNG, TIFF, HEIF, and JPEG XL dependency builds.
  • Declare the installed zlib static library as an ExternalProject INSTALL_BYPRODUCTS output so Ninja can order clean builds correctly.

Lior Lahav added 2 commits May 14, 2026 18:43
The zlib external project links FreeImage against the installed static library, but Ninja needs that generated file declared on the install step. Record the platform-specific zlib library name and expose it through INSTALL_BYPRODUCTS while still deriving ZLIB_ROOT from the ExternalProject install directory.
@agruzdev
Copy link
Copy Markdown
Owner

agruzdev commented May 25, 2026

Hello!

As I remember, I spent some time to make sure that PNG, TIFF and others find correct zlib via default FindZLIB. So these changes are workarounds to make the old FindZLIB work with latest zlib. I hope, I understood correctly.

Could you please clatify why cmake 3.28 is necessary? It's quite an old version.

@TheNicker
Copy link
Copy Markdown
Author

TheNicker commented May 25, 2026

This PR solves two separate CMake/zlib problems:

1. Restores the project to a CMake 3.x minimum

The project was raised to:

cmake_minimum_required(VERSION 4.2)

mainly because CMake 4.2’s FindZLIB recognizes zlib 1.3.2’s Windows static library names, zs.lib and zsd.lib.

This PR changes that to:

cmake_minimum_required(VERSION 3.28...4.2)

Lowering the minimum required CMake version makes the project easier to integrate for a wider range of consumers, especially environments pinned to CMake 3.x by their OS image, CI image, package manager, or
corporate toolchain.

This is a balance between universality and available CMake features. The older the minimum version we can honestly support without compromising the project, the better, because it keeps the project usable in
more environments. In this case, the newer FindZLIB behavior is useful, but not important enough to justify losing compatibility with otherwise capable CMake 3.x environments. Since FreeImageRe builds and
controls its bundled zlib dependency, it can pass the known zlib library path directly instead of requiring every consumer to upgrade to CMake 4.2 just for that lookup behavior.

The 3.28 lower bound is the repo’s current effective lower bound because cmake/external_project_common.cmake already requires CMake 3.28 for FetchContent_Declare(... EXCLUDE_FROM_ALL), which is used by cmake/
dependency.raw.cmake. Even so, CMake 3.28 is already a reasonably conservative minimum today because it is around 2.5 years old.

Ideally, we want the supported CMake range to stay as broad as possible: keep the lower bound as low as the project can honestly support, and keep the upper policy range as high as the project has been checked
against. In this PR, 3.28...4.2 is conservative because 3.28 matches the repo’s current effective minimum and 4.2 matches the CMake version the project already targeted.

Longer term, after this PR lands, the upper policy version should ideally be raised to the latest CMake version after validating the project against it. One practical way to do that is to add a CI job that
installs the latest CMake instead of only ~4.2.0. That would continuously verify that the project still works with current CMake behavior and would catch future pull requests that introduce compatibility
issues with newer CMake versions early.

2. Fixes the zlib Ninja build ordering issue

Without declaring the installed zlib library as an ExternalProject byproduct, Ninja can fail because FreeImage.dll depends on dependencies/zlib/install/lib/zs.lib, but Ninja has no rule saying the zlib install
step produces it.

Example failed workflow/job:
https://github.com/agruzdev/FreeImageRe/actions/runs/26415065354/job/77757650810

This PR fixes that by adding INSTALL_BYPRODUCTS for the platform-specific zlib static library. This should allow the new Ninja-based Windows 2025 / VS 2026 workflow to get past the zlib failure; that workflow
should probably be merged as well and should pass successfully once the remaining same-class ExternalProject byproduct issues are addressed.

It also passes the known ZLIB_LIBRARY path into PNG, TIFF, HEIF, and JPEG XL, so those dependency builds do not rely on newer FindZLIB behavior to find the bundled zlib.

@agruzdev
Copy link
Copy Markdown
Owner

TL;DR

@TheNicker
Copy link
Copy Markdown
Author

@agruzdev
Copy link
Copy Markdown
Owner

agruzdev commented May 25, 2026

I'm not sure, why zs.lib is missing. FreeImage depends on the LibZLIB target, that depends on ZLIB ExternalProject. So build order is correct. I would like to debug it locally on my PC and see why it happens.
And why all other dependecies work without INSTALL_BYPRODUCTS then?

@TheNicker
Copy link
Copy Markdown
Author

Changed ubuntu generator to ninja, same failure: https://github.com/agruzdev/FreeImageRe/actions/runs/26418525102/job/77768083518

Seems like MSBuild uses a higher level project-level dependency management: it builds the whole ZLIB project first, so the installed zlib library already exists by the time FreeImage links.

Ninja uses stricter, explicit file-level dependency management: if FreeImage links against the installed zlib library, Ninja needs a rule that says which build step produces that file, hence INSTALL_BYPRODUCTS

I wonder if it'll happen with more generators 🤔

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Revert the CMake minimum back to 3.x.

2 participants