Continuing my own thread, after taking the time to experiment a little.

First, I've refactored the build system so we turn the rules.mk into
declarative files (instead of Makefile fragments) and get rid of the
module.mk files.
This allowed me to write a Python script to parse modules.cfg and the
various rules.mk to generate a Makefile based on the configuration
expressed there.
The script is called meta-build.py, and could be easily extended to
generate something else if needed, but I haven't gone further than that.
However, this let me explore with the exact details on how we configure our
build, and the various options to build the library (the generated Makefile
allows you to build three variants of the library: a static library and a
shared library both compiled with -fPIC, and a static library compiled
without it).

Second, I wrote support files for the Meson build for the library. It is
similar to the CMakeLists.txt version, except for the installation /
packaging part. It was a good way to get used to the tool and to compare
its system/header/library probing features.
In the end, and this is personal opinion, I find Meson cleaner than CMake,
sometimes much cleaner, though it has its own little warts that were a bit
surprising, as a new comer. Both systems are so much better than auto-tools
however.

I believe that the ability for any developer to just download a release
archive and run "./configure && make" to get a *default build* of the
library (and "make install" to install) is really important. I insist on
the "default" here, because we have a sophisticated customization system,
which was designed in a different time.
In other words, before considering switching the build to something else, I
propose the following:

- Whatever we do, ensuring that "./configure && make && make install"
continues to work on Posix systems without extra dependencies. This would
only be guaranteed to work on a default build of the library (i.e. without
module customization). Configure options would still be provided as usual
to handle external dependencies like zlib, libz2, etc.

- I would like to drop the dynamic module instantiation / lookup code from
the library, to simplify certain code paths. The ability to inject at
runtime a new FT_Module was designed at a time where it was expected that
people would write custom modules for proprietary/custom font formats, and
tools like git which make it easy to rebase changes on top of an upstream
project were not available or still very unfamiliar. These days, anyone can
create its own fork of an open-source library to add custom features for
its own little embedded project. This means no more modules.cfg, and
ftmodule.h auto-generation, which are fortunately implementation details.
For ABI stability, we will have to keep functions like FT_Add_Module(), but
just change them to return an FT_Err_Unimplemented_Feature error code.

- I would like to ensure src/base/ftsystem.c does the right thing for all
systems. These days, we can avoid probing for <unistd.h> and <fcntl.h> and
assume a Posix system provides a valid mmap() / munmap() implementation.
This will remove one more reason to use auto-tools.
- Similarly, there are several versions of ftdebug.c which are essentially
similar except for two things: How messages are sent to "the log" (stderr
by default), and how to parse the FT2_DEBUG environment variable (when such
thing exists). These two things can be encapsulated in a separate file.
- Also, we don't need to support 8.3 Filepathnames (DOS and Windows 9x
development are long dead), so we can finally use longer filenames (e.g.
ftdebug_posix.cc, ftdebug_windows.cc, etc..) to better differentiate the
files under src/base/ instead of sprinkling them under builds/<system>/
- It also means we can probably drop some of the ugly macros for header
files we're using (still provide them for the API, but change all users
otherwise). Yeah!
- Regarding ftdebug.c and logging, we probably want the customizable
"message" function to take several parameters, e.g.: void
FT_Log_Message(int trace_component, int trace_level, const char* fmt,
va_list args). It's possible to consider trace events (i.e. "start/stop")
to generate flame graph that are easier to read.
- There are different versions of ftconfig.h, with a ton of stuff shared
between them, we should probably move these to common header files whenever
possible.
- Similarly ftoption.h contains both user-selectable options, and things
that are more tweaks for the implementation that a typical developer will
never have to care for. I suggest we move the latter to an internal header
instead.
- There are many things I'd like to get rid of, but apparently

- Finally, the largest issue I've seen is the dependency on Harfbuzz. The
situation where both libraries depend on each other is a little bit
ridiculous. I wonder how much of Harfbuzz we need, and if it's worth
re-implementing in FreeType2 itself. But something tells me implementing
hb_shape() can be really subtle. Any informed opinions on this?

I'm adding two git bundles related to the experiments I've described there
(nothing to consider for submission, imho, for now).
I'll prepare some patches to simplify our existing build files and
customization process as explained above, unless someone has better
suggestions.

Regards,

- Digit









Le jeu. 30 avr. 2020 à 01:39, David Turner <[email protected]> a écrit :

> Starting a thread here to discuss potential build system improvements for
> FreeType.
>
> The current FreeType 2 build system has many flaws. To its credit, it was
> designed in a very different time, when things like CMake / Meson / Ninja/
> Maven / GN / Bazel didn't even exist, when Autotools was considered the
> best system to configure your build (ah!), and GNU Make 3.81 was considered
> new and bleeding edge, and didn't necessarily exist for all platforms. I'm
> not even sure pkg-config was available on all Linux distros until quite a
> long time. As I said ... very different times.
>
> Despite that, it was also designed to make FreeType buildable on a maximum
> amount of systems, and I attribute part of its success to that specific
> feature, especially in the embedded world. While we probably no longer care
> about developers using DOS and OS/2 systems to build the library, I would
> really appreciate if any replacement could continue in this direction.
>
> I think it would also be acceptable if the build system used to develop
> FreeType itself, might be different than the one used by other developers
> that simply want to use it in their own projects. For example something
> that can build and run tests easily with sanitizers, fuzzing, remote bots
> and other goodies, or can integrate well with a continuous integration
> system. While at the same time, being able to generate simple Makefiles /
> CMakefiles / BUILD / BUILD.gn / whatever corresponding to a specific
> configuration of the library (which is what 95% of developers using the
> library need).
>
> I have experience with CMake (I find it a vast improvement over auto-tools
> for package / feature detection, but a hot mess for about anything else),
> GN/Ninja (very powerful, but essentially requires too much dependencies to
> get the most out of it) and Bazel (can be hard to get into, very powerful,
> but requirements are a bit crazy at the moment). I'm curious about Meson.
>
> I don't have something specific to propose, but that's my current point of
> view. I may be wrong or misguided, so please share your feedback in this
> thread.
>
> Let the flame^W war^W games begin :-)
>
> - David
>
>

Attachment: freetype2-meta-build.bundle
Description: Binary data

Attachment: freetype2-meson-build.bundle
Description: Binary data

Reply via email to