Building TPT with Meson

From The Powder Toy
Revision as of 08:09, 28 January 2022 by LBPHacker (talk | contribs) (Some library copy-fu needs to be done in dynamic mode)
Jump to: navigation, search
Language: English  • 한국어 • 中文

This is a guide to get you started on coding for The Powder Toy. If you have any questions, just ask in the Development Assistance section on The Powder Toy forums.

EDITOR NOTE: Please do not edit this guide without consulting with TPT developers first; you risk your changes being mercilessly rolled back without prior notice otherwise.

Compiling for Windows

Tested on Windows 10. The cross-compiling bit at the end was tested on Ubuntu 18.04.

Required environment setup

  • install Git (get it here)
    • options should be left unchanged
  • install Python (get it here)
    • it is recommended to allow the installer to add Python to PATH and to disable the path length limit (the latter is offered near the end of the installation process)
  • open an elevated command prompt (search for "cmd" the Start Menu, right-click the most sensible result, click "Run as administrator") and execute the following commands (you can close the prompt afterwards)
python -m pip install --upgrade pip
pip install --upgrade meson ninja
  • open a non-elevated command prompt (the same as before, but instead of running as administrator, just run it by clicking its shortcut) and execute the following commands (you can close the prompt afterwards)
    • replace [wherever you keep your repositories] with the actual path, taking care to remove the [] characters also; if the path has spaces in it, add "" around it
      • example: if your repositories are in C:\Users\Powder Toy Fan\Development, this path will be "C:\Users\Powder Toy Fan\Development"
cd /d [wherever you keep your repositories]
git clone https://github.com/The-Powder-Toy/The-Powder-Toy

Building for the first time with MSVC

MSVC is Microsoft's C/C++ compiler for Windows, which comes with Visual Studio. Using MSVC is the recommended way to build TPT on Windows if you are new to modding or have any reason whatsoever to prefer MSVC over MinGW (for which a separate guide is provided below).

  • install Visual Studio (get it here)
    • select the Desktop Development workload
    • you really only need "MSVC" and "Windows 10 SDK", so you can uncheck everything else in the list on the right
  • find "x64 Native Tools Command Prompt for VS" (or similar, hereafter referred to as "VS prompt") in the Start Menu and execute the following commands
    • it is recommended to pin the resulting window to your taskbar; you will be using this a lot to build TPT
cd /d [wherever you keep your repositories]
cd The-Powder-Toy
meson build-debug
cd build-debug
ninja
  • you may see a few warnings throughout all of this, but no errors (if you do at any stage, do not try to skip it; ask us about it on the forum instead)
    • if you are not sure, run Ninja again; if it says "no work to do", everything worked fine
  • at this point, running TPT from the VS prompt should be possible
powder.exe

Using the Visual Studio IDE

The method above does not let you use the 'Visual' part of Visual Studio, the IDE. Although Meson has limited support for this use case, if for some reason you wish to use the IDE, you can ask Meson to generate a build site that uses Visual Studio instead of Ninja.

  • open a VS prompt (see above) and execute the following commands
cd /d [wherever you keep your repositories]
cd The-Powder-Toy
meson --backend=vs -Dbackend_startup_project=powder build-debug-vs
  • you will not need the VS prompt beyond this point

This will generate a build site with a Visual Studio solution inside (the-powder-toy.sln). You can use this as any other solution, except for a few key differences:

  • the IDE can only be used for more comfortable editing and debugging and not much else, including changing the project structure; you will have to familiarise yourself with Meson and work with the meson.build files in order to do that
  • once you actually change meson.build files, Meson will automatically regenerate the solution the next time you try to build it; Visual Studio will give you a scary popup about the solution having been changed, which is perfectly normal, just click 'Reload Solution'
  • the configuration you currently see (most likely debug|x64, if you are following this guide exactly) is the only configuration the solution has, and it is not recommended to add other configurations as Meson will just overwrite them the next time it regenerates the solution; instead, you have to generate separate build sites with Meson

Building for the first time with MinGW

MinGW is a package that makes it possible to build TPT with GCC even on Windows. You probably have your reasons for preferring MinGW over MSVC (for which a separate guide is provided above); this guide makes no effort to list possible ones.

NOTE: For MinGW, we only provide 64-bit prebuilt libraries. Furthermore, we are not aware of a way MinGW would be able to provide these libraries on its own (e.g. through its own package manager), so using system libraries and targeting 32-bit hosts is not supported by our Meson setup.

  • install MinGW (get it here)
    • this comes in multiple "flavours", you will need "x86_64-posix-seh"
    • this guide has been tested with version 8.1.0
    • you will be asked for a directory to install MinGW to; decide on a directory and make note of it for later
      • even if you do not plan on doing anything with MinGW right now other than building TPT, you may need to install other flavours later, so it is recommended to install the required flavour to a location that will not interfere with others, e.g. include the version number and the flavour in the path
  • find "Git Bash" (or similar, hereafter referred to as "bash prompt") in the Start Menu and execute the following commands
    • it is recommended to pin the resulting window to your taskbar; you will be using this a lot to build TPT
    • replace [your MinGW bin directory] with an actual path, taking care to remove the [] characters also
      • the "bin directory" will most likely be the path to whatever directory you installed MinGW to, with /bin appended to it, all backward slashes replaced with forward slashes (/ instead of \), and using the MinGW root notation (/c/ instead of C:\)
      • you do not need to add "" around the path if it contains spaces
      • example: if you install MinGW to C:\mingw-w64\mingw64-x86_64-8.1.0-release-posix-seh-rt_v6-rev0, the path to the bin directory will be /c/mingw-w64/mingw64-x86_64-8.1.0-release-posix-seh-rt_v6-rev0/bin
    • replace [wherever you keep your repositories] with the actual path, taking care to remove the [] characters also; if the path has spaces in it, add "" around it
      • the same applies to the format of the path of this directory as to that of the bin directory
      • example: if your repositories are in C:\Users\Powder Toy Fan\Development, this path will be "/c/Users/Powder Toy Fan/Development"
export PATH="[your MinGW bin directory]:$PATH"
cd [wherever you keep your repositories]
cd The-Powder-Toy
meson build-debug
cd build-debug
ninja
  • you may see a few warnings throughout all of this, but no errors (if you do at any stage, do not try to skip it; ask us about it on the forum instead)
    • if you are not sure, run Ninja again; if it says "no work to do", everything worked fine
  • at this point, running TPT from the bash prompt should be possible
./powder.exe
  • note that this executable depends on the MinGW runtime, which you will have in PATH due to the first command executed in the prompt
  • a debugging session can be initiated like so (GDB cheat sheet):
gdb ./powder.exe

Cross-compiling with MinGW

Cross-compiling amounts to telling Meson about the host machine via cross files. A very basic example is available here, which you may need to tweak for your toolchain, but it will likely work out of the box. Consult your toolchain's manual for the exact location of the binaries required.

NOTE: For MinGW, we only provide 64-bit prebuilt libraries. Furthermore, we are not aware of a way MinGW would be able to provide these libraries on its own (e.g. through the system's package manager), so using system libraries and targeting 32-bit hosts is not supported by our Meson setup.

The workflow is the same as when you build for Linux, with the exception that the cross file to use is specified at configure time:

meson --cross-file=cross-examples/mingw.ini build-debug

There is currently no supported way to use system libraries discovered via the toolchain's pkg-config or similar; the current setup downloads our prebuilt libraries the same way it does when using MinGW on Windows. Feel free to experiment though.

NOTE: It is possible to not only compile but also run the resulting binary on your host machine, but while our Meson setup copies the DLLs for the prebuilt libraries into the build site, in dynamic mode (e.g. -Dstatic=none, which is the default), there may be additional DLLs that need to be copied or symlinked in for the binary to work, depending on your toolchain and the way you run the binary. Example, which may or may not translate well to your setup:

ln -s /usr/x86_64-w64-mingw32/bin/libwinpthread-1.dll
ln -s /usr/x86_64-w64-mingw32/bin/libstdc++-6.dll
ln -s /usr/x86_64-w64-mingw32/bin/libgcc_s_seh-1.dll

Compiling for MacOS

Tested on MacOS 10.15 and 11.5.

Required environment setup

  • install Homebrew (get it here)
  • in the next step, xcode-select is used; note that you do not need to install Xcode to run that command
  • in a terminal, execute the following commands
xcode-select --install # asks you for confirmation, installs compilers
sudo -H python -m pip install --upgrade pip # if you get "No module named pip", try python3
sudo -H pip install --upgrade meson ninja
brew install pkg-config luajit fftw sdl2
cd [wherever you keep your repositories]
git clone https://github.com/The-Powder-Toy/The-Powder-Toy

Building for the first time

  • cd to the repository root and execute the following commands
meson build-debug
cd build-debug
ninja
  • you may see a few warnings throughout all of this, but no errors (if you do at any stage, do not try to skip it; ask us about it on the forum instead)
    • if you are not sure, run Ninja again; if it says "no work to do", everything worked fine
  • at this point, running TPT from the prompt should be possible
./powder

Compiling for Linux

Tested on Ubuntu 20.04 and Raspbian 10.

Required environment setup

  • make sure your package lists are up to date (e.g. sudo apt update)
  • install a C++ compiler (e.g. sudo apt install g++)
  • install git (e.g. sudo apt install git)
  • install python (e.g. sudo apt install python3)
  • install pip if not present (consult their guide)
  • upgrade pip (e.g. sudo -H python3 -m pip install --upgrade pip)
  • install Meson and Ninja if not present (e.g. sudo -H pip install --upgrade meson ninja)
  • optionally, install ccache (e.g. sudo apt install ccache)
  • install a library utility (e.g. sudo apt install pkg-config)
  • install required libraries (e.g. sudo apt install libluajit-5.1-dev libcurl4-openssl-dev libfftw3-dev zlib1g-dev libsdl2-dev)
    • your package manager may package these under wildly different names
  • download the source code (e.g. git clone https://github.com/The-Powder-Toy/The-Powder-Toy)

Building for the first time

  • cd to the repository root and execute the following commands
meson build-debug
cd build-debug
ninja
  • you may see a few warnings throughout all of this, but no errors (if you do at any stage, do not try to skip it; ask us about it on the forum instead)
    • if you are not sure, run Ninja again; if it says "no work to do", everything worked fine
  • at this point, running TPT from the prompt should be possible
./powder

Next steps (all platforms)

Updating the binary

Now that you have successfully built TPT for the first time, you will probably want to change things in the code. To update the binary, build it again by executing

ninja

in the same prompt you executed it the last time. You will have to do this every time you change something and want the binary to reflect the change.

Release builds

So far, you have been building "debug" binaries. These make debugging significantly easier than "release" builds, but they also offer less performance. You can instead build a "release" binary, which is much more performant, but very difficult to debug. Only use these builds when you are certain that you have no more bugs to take care of. If a bug does appear later on, go back to building debug binaries.

To build a release binary, navigate back to the root of the repository in your prompt and create a new build site with Meson, then build with Ninja again

cd [whatever parameters that take you to your repositories, see above]
cd The-Powder-Toy
meson -Dbuildtype=release build-release
cd build-release
ninja

Note that build-debug and build-release directories are independent "build sites", each of which you can update with Ninja when you set them as your current directory (by using cd, see the lists of commands above).

Static builds

Both the debug and release configurations above produce "dynamic" binaries, which means they depend on certain components of your system (libraries you have installed with apt on linux or with brew on macos) or files other than powder.exe (DLLs in the same directory as powder.exe on windows). If you are a mod author, please make sure you are not shipping such binaries, as your users are used to TPT not depending on anything and thus are unlikely to have experience with installing these libraries on their own.

You can get rid of most of these dependencies by building a "static" binary. This way, the binary will depend on very basic components of your system that are very likely to be present. It will also gain a few megabytes and linking it will take longer, which is why you would only do this when you are about to release it to the public.

To build a static binary, navigate back to the root of the repository in your prompt and create a new build site with Meson (see NOTE below!), then build with Ninja again

meson -Dbuildtype=release -Dstatic=prebuilt build-release-static
cd build-release-static
ninja

NOTE: On Windows, if using MSVC, you will also need to add the -Db_vscrt=static_from_buildtype option to the Meson call above, otherwise the resulting binaries will be dynamically linked against the MSVC runtime (vcruntime.dll and similar).

meson -Dbuildtype=release -Dstatic=prebuilt -Db_vscrt=static_from_buildtype build-release-static
cd build-release-static
ninja

NOTE: On Windows, if using MinGW, -Db_lto=true is known to break static builds; use this setting at your own risk. The Meson configuration will throw an error upon detecting this setting; you will have to fix this on your own.

NOTE: On Windows, if using MinGW, even static builds will not be "fully static", as they will still import functions from msvcrt.dll. This is fine though, as this library is present on every modern install of Windows.

It used to work, but it broke

Each platform has its own set of quirks that need to be worked around (mostly looking at you, microsoft and apple). Fortunately, our build system takes care of most of these. Unfortunately, the workarounds come in the form of upgrades to the build system, which are not installed automatically, and even if they are, affected build sites may need to be reconfigured manually. If you had at some point gotten TPT to build successfully, but since then your build sites somehow broke, you can try one of the following methods to fix them.

The most straightforward way to fix a single build site is to reconfigure it. To check if this worked, try running Ninja.

cd [whatever parameters that take you to your repositories, see above]
cd The-Powder-Toy
meson --reconfigure --wipe build-debug # or whatever you named your build site
cd build-debug
ninja

You will have to do this with every broken build site.

If this does not help, you can upgrade pip, Meson and Ninja. Like when setting them up for the first time, add sudo -H on Linux and MacOS, and run this in an elevated command prompt on Windows.

python -m pip install --upgrade pip # if you get "No module named pip", try python3
pip install --upgrade meson ninja

Once you are done with this, reconfigure your build sites (see above).

If not even this helps, that is your cue to start from scratch, following the guide as if you are building TPT for the first time, except you already have the repository, so you do not need to clone that again. In fact, this is where your changes to TPT are stored, so you should never delete it. Deleting your local clone of the repository never solves any problem, it only results in loss of code. Do not even consider doing it.

As a last resort, you can ask us on the forum.

Build options

Build options are passed to Meson at when you set up a build site (see examples above) or at any later time, when the build site is already in use. In both cases, they are passed as command line arguments of the form -D[name]=[value]. For example, to set up a build site that compiles TPT with Lua 5.1 instead of LuaJIT, you would issue the following command

meson -Dlua=lua5.1 build-debug-lua5.1

But you could also take an existing build site and change the relevant build option to do the same

cd build-debug
meson configure -Dlua=lua5.1

The next time you run Ninja, everything that needs to be rebuilt as a result of this change will be rebuilt. See the Meson quick guide for more on configuring build sites.

Below is a list of build options our Meson setup supports

Name Type Description
static one of 'none', 'system', 'prebuilt' Build statically using libraries present on the system ('system') or using prebuilt libraries official builds use ('prebuilt')
beta boolean Beta build
ignore_updates boolean Don't show notifications about available updates
install_check boolean Do install check on startup
http boolean Enable HTTP via libcurl
gravfft boolean Enable FFT gravity via libfftw3
snapshot boolean Snapshot build
snapshot_id integer Snapshot ID, only relevant if 'snapshot' is true
mod_id integer Mod ID, used on the Starcatcher build server; the build server will compile for all platforms for you and send updates in-game, see jacob1 to get a mod ID
lua one of 'none', 'lua5.1', 'lua5.2', 'luajit' Lua library to use
ssl currently only 'openssl' SSL library to use
x86_sse one of 'none', 'sse', 'sse2', 'sse3', 'auto' Enable SSE (available only on x86)
native boolean Build with optimizations specific to the local machine, may not run on other machines, overrides 'x86_sse'
ogli boolean Enable OpenGL interface rendering (currently defunct)
oglr boolean Enable OpenGL particle rendering (currently defunct)
build_powder boolean Build the game
build_render boolean Build the thumbnail renderer
build_font boolean Build the font editor
server string Simulation server
static_server string Static simulation server
update_server string Update server, only used by snapshots and mods, see 'snapshot_id' and 'mod_id'
workaround_gcc_no_pie boolean Pass -no-pie to gcc manually to work around meson's -Db_pie=false doing nothing