INTRO
-- Terminology
-- Limitations
I PRE-REQUISITES
-- Tooling
-- Binary and 3rd party UE dependencies
II BUILDING UE
-- Things Unreal Engine does not care about
-- Building UnrealBuildTool and AutomationTools
-- Building UnrealHeaderTool
-- Building Unreal Game target
-- Building Unreal Editor target
-- Minimal working Editor
III ADVANCED BUILD
-- Other platforms and configurations
-- Available targets
-- Skipping Debug symbols and PDB gen)
-- Skipping plugins
-- Skipping modules
-- BuildConfiguration.xml
V BONUS
-- Marketplace content with Legendary
The purpose of this guide is to give you a quick, high-level overview of how to build Unreal Engine from sources somewhat manually and with some hacks&tricks that can potentially speedup the process and, potentially, save on disk space (no IncrediBuild/XGE and all that enterprise jazz). You may find it useful if you iterate on engine sources a lot or just want some explicit building process for troubleshooting purposes.
$(EngineRoot)
- root directory of the engine sources, the one you fetch from UE's git repo.
$(EngineSource)
- the $(EngineRoot)\Engine\Source\
directory
AT
- AutomationTool(s), Epic's C#/.NET UE pipeline app
UBT
- UnrealBuildTool, Epic's C#/.NET UE pipeline app
UHT
- UnrealHeaderTool, C++ pipeline app
- It is assumed, by default, that you are building UE on Windows for Windows. Linux and MacOS -- both as a host and as a target -- are out of the scope of this how-to, simply because I don't have a separate test machine (VM is non-trivial task due to CPU/RAM/Storage requirements). That being said, everything here should be applicable to both Linux and MacOS.
- This guide is only for building bare-bones Editor/Game targets. Building whole toolset for the purposes of fully-functional, multi-platform project-packaging and testing pipeline from the Editor is outside of the scope as well.
As per UE repo, install the required tools and dependencies, relevant to your UE version (switch the tag/branch for relevant readme.md
) This guide assumes you want to build UE 5.x by default but it attempts to cover building older versions as well, like aforementioned 4.23. Because of this, after installing recommended by Epic pre-requisites, it is strongly advised that you install or ensure that you already have installed:
- DotNet 6 or 7 SDK (SDK comes with Runtime)
- .NET Framework 4.8 SDK and .NET Framework 4.8 Targeting Pack
(for older UE; it brings on-board MSBUILD for 4.x .Net projects) - NuGet Package Manager (for older UE)
DO NOT run Setup.bat
or GenerateProjectFiles.bat
yet.
Do you want to save on some disk space?
[Yes/No]_
If the answer is No
, then run the Setup.bat
and go to part II.
If the answer is Yes
, then you must know that this part is for advanced users, in one way or another it will|might require you to tinker with the setup until desired working state is achieved.
When you run Setup.bat
, under the hood it just runs GitDependencies.exe
, which is basically a homegrown binary cvs tool that fetches appropriate dependency content from Epic's CDN according to your current UE version. By default, this executable binary is in:
UE5: Engine\Binaries\DotNET\GitDependencies\win-x64\GitDependencies.exe
UE4: Engine\Binaries\DotNET\GitDependencies.exe
There are 2 ways to cut down on the downloaded binary content:
- command-line arguments to
GitDependencies.exe
to exclude namespaces - via
.gitdepsignore
Command-line arguments allows you to submit some namespaces that will be excluded from the downloaded dependencies, provided there is a match. I don't know yet how to get list of ALL valid namespaces for given UE version, the code for this in decompiled GitDependencies.exe
is very generic, it just adds the submitted namespaces as a string match to the collection to check against. Here are some examples that should give you a hint:
GitDependencies.exe -exclude=WinRT -exclude=HoloLens -exclude=Lumin -exclude=Linux -exclude=Linux32 -exclude=osx64 -exclude=IOS -exclude=Android -exclude=Mac -exclude=HTML5 -exclude=Win32 -exclude=TVOS
You can submit as many as you want, invalid ones will be a noop.
The second method, via .gitdepsignore is a bit more useful, however, by definition, in order to even understand what do you want to (and can) skip, you need to download ALL the default content (GitDependencies.exe
with no args) beforehand and analyze it against previous state of the repo/engine dir. This repo includes my own version that is aimed at Win64
target platform only and tries to skip as much unnecessary stuff as possible. More info on .gitdepsignore
you can find HERE
It is important to note here, that UE deps are messy. Very messy. You think that it makes perfect sense to skip Win32 and IOS stuff if you target Win64? Why yes, it does, but not for UE. If you completely skip these dependencies when building UE 4.x, a lot of things will fail, like AutomationTools (hard dependencies on some of the IOS stuff), or BuildGraph's default build config (some odd hard-dependencies on some Win32 stuff in copy-files). My recommendation is: do not use -exclude=IOS
and -exclude=Android
and -exclude=HTML5
for UE 4.x, they tend to break stuff. My .gitdepsignore
already skips non-critical content from these.
Oh and yes, you can combine both methods mentioned above.
If you've skipped last step from previous chapter - run Setup.bat
now.
Generated project files a-la MSVS's UE5.sln
. At all.
A lot of people having hard time to grasp it but project gen for "IDE X" simply exist for user's convenience sake (i.e. if you plan to work with sources and want a familiar IDE setup). UE building pipeline does not use nor your .sln
, nor any other built-in project files stuff from any other IDE (well, technically there is an asterisk, but we will skip it). Everything is being built via two C# tools: AutomationsTools
and UnrealBuiltTool
. Think of them like homegrown cmake
alternatives. They are used for Engine source building as well as project packaging, platfrom-specific/agnostic pipeline tools.
This is why we needed dotnet core SDK from earlier - to build C#/.NET tooling. UE5 comes with bundled 6.0 sdk but we will skip it for now.
Open command line, either cmd.exe
or your wrapper over it (Windows Terminal, whatever). Navigate to engine root:
cd $(EngineRoot)`
Build UBT:
UE5.3 --
dotnet build Engine\Source\Programs\UnrealBuildTool\UnrealBuildTool.sln -c Development
(I recommend building the *.sln project because it also builds all dependencies like new UHT for U5.3)
UE5.x --
dotnet build Engine\Source\Programs\UnrealBuildTool\UnrealBuildTool.csproj -c Development
Build AutomationTools, (if needed):
UE5 --
dotnet build Engine\Source\Programs\AutomationTool\AutomationTool.csproj -c Development
UE4 --
dotnet build Engine\Source\Programs\DotNETCommon\DotNETUtilities\DotNETUtilities.csproj
dotnet build Engine\Source\Programs\AutomationTool\AutomationTool.csproj -c Development
Now that you've built UBT you can generate your project files, if you desire:
Foreign:
UnrealBuildTool.exe -projectfiles -project="Path:\to\my.uproject" -currentplatform -game
Native:
UnrealBuildTool.exe -projectfiles -currentplatform
If UBT or AT fails to build, see [Troubleshooting] section.
Once you have UBT
built, it is time to test if our dev environment set up correctly and if we can compile and link UE modules and programs. Do note that UnrealHeaderTool was removed from UE 5.3 and is no longer an engine program but rather a part of EpicGames Shared C++ toolkit and is being built when you compile AutomationTools
/UBT
(as a solution for the latter).
From $(EngineRoot)
directory:
UE5.3+ --
Engine\Binaries\DotNET\UnrealBuildTool\UnrealBuildTool.exe BlankProgram Win64 Development
UE5-5.2 --
Engine\Binaries\DotNET\UnrealBuildTool\UnrealBuildTool.exe UnrealHeaderTool Win64 Development
UE4 --
Engine\Binaries\DotNET\UnrealBuildTool.exe UnrealHeaderTool Win64 Development
If UHT
or BlankProgram
build succeeds, congratulations, your dev environment should be good. If it fails, revise the I. [Tooling] or check [Troubleshooting] sections.
This is what I call "UE player" target, it what loads and processes your content runs your game/it's logic. The Engine
.
UE5 --
UnrealBuildTool.exe UnrealGame Win64 Development
UE4 --
UnrealBuildTool.exe UE4Game Win64 Development
Once it is built, you technically can run your Blueprint-only project as a standalone:
UnrealGame.exe full\path\to\mygame.uproject
The Editor itself.
UE5 --
UnrealBuildTool.exe UnrealEditor Win64 Development
UE4 --
UnrealBuildTool.exe UE4Editor Win64 Development
Although the built Editor is technically fully functional, it depends, at minimum, on ShaderCompilerWorker program to run.
UnrealBuildTool.exe ShaderCompileWorker Win64 Development
Now you can run the Editor.
That is pretty much it for the basic UE build.
An example for UE5.3:
dotnet build Engine\Source\Programs\UnrealBuildTool\UnrealBuildTool.sln
dotnet build Engine\Source\Programs\AutomationTool\AutomationTool.csproj
dotnet build Engine\Source\Programs\AutomationTool\AutomationUtils\AutomationUtils.Automation.csproj
dotnet build Engine\Source\Programs\AutomationTool\IOS\IOS.Automation.csproj
dotnet build Engine\Source\Programs\AutomationTool\Scripts\AutomationScripts.Automation.csproj
UnrealBuildTool.exe UnrealPak Win64 Development
UnrealBuildTool.exe ShaderCompileWorker Win64 Development
UnrealBuildTool.exe UnrealEditor Win64 Development
UnrealBuildTool.exe UnrealGame Win64 Development
(for 5.2 add UnrealBuildTool.exe UnrealHeaderTool Win64 Development
)
This build should run, work and package projects.
As you may have noticed, UBT
usage is fairly straightforward, you give it a target
name, UE-compliant platform
name and a configuration
and if it a valid build object/target it will be build within the context of UE pipeline/source setup:
UnrealBuildTool.exe CrashReportClient Win32 Shipping
If you want to build your project-specific targets (foreign project):
UnrealBuildTool.exe -project=full\path\to\my.uproject Target Platform Configuration [-game or -editor]
UBT
will find all valid targets in $(EngineSource)
and in your project's Source/
directory and will try to build what you have requested. Said targets are described via *.Target.cs
files, which contain raw C# code (UBT
compiles them dynamically at runtime). You can simply search for *.Target.cs
or, alternatively, you can generate project files:
Engine --
UnrealBuildTool.exe -projectfiles -currentplatform
Your project --
UnrealBuildTool.exe -projectfiles -project=path:\to\my\game.uproject -currentplatform
and then just go to \Intermediate\ProjectFiles\
directory and open any *.vcxproj
file to find out what it tries to build and how. For example, inside UE5.vcxproj
we can find:
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<!-- snip -->
<NMakeBuildCommandLine>..\..\Build\BatchFiles\Build.bat UnrealGame Win64 Debug -WaitMutex -FromMsBuild</NMakeBuildCommandLine>
<!-- snip -->
<NMakeOutput>..\..\Binaries\Win64\UnrealGame-Win64-Debug.exe</NMakeOutput>
<AdditionalOptions>/std:c++17</AdditionalOptions>
</PropertyGroup>
which should be self-evident. Note that this applies to project generated for MSVS format, which is the default one for Windows. If you chose a different project format, like VisualStudioCode
or XCode
then your aggregated targets will in .vscode\tasks.json
and so on.
As you may now have fully realized - generated project files is just a convenient way to do batch compilation of what we did manually, using default "UE preset".
By default, UBT
has a hardcoded flag to always generate DebugInfo
as well as PDBs. I assume this was done on purpose by Epic to make their life easier and ensure users always provide some kind of meaningful stack crash trace, sacrificing user choice in the process. Let us fix that.
[UE 5.4+]
Just pass -nodebuginfo
and -nolinkerdebuginfo
to UBT
and that will be enough.
[UE <5.4]
Open file
$(EngineSource)\Programs\UnrealBuildTool\Platform\Windows\UEBuildWindows.cs
Find something that looks like this (code here changes every version):
GlobalLinkEnvironment.bCreateDebugInfo = true;
and replace with
GlobalLinkEnvironment.bCreateDebugInfo = GlobalCompileEnvironment.bCreateDebugInfo;
We've just made UBT
to respect our configuration inside BuildConfiguration.xml
. Let us capitalize on that right away.
Open existing or create file BuildConfiguration.xml
inside:
%APPDATA\Unreal Engine\UnrealBuildTool\
and add a section <BuildConfiguration>
:
<BuildConfiguration>
<bDisableDebugInfo>true</bDisableDebugInfo>
<bDisableDebugInfoForGeneratedCode>true</bDisableDebugInfoForGeneratedCode>
<bOmitPCDebugInfoInDevelopment>true</bOmitPCDebugInfoInDevelopment>
</BuildConfiguration>
For more information about about BuildConfiguration.xml file see the relevant section in this doc
Now all that's left is to rebuild UBT
and you are done. PDB and debug info no longer will be generated during build process. This save both on overall build time and disk space. It is actually one of the biggest time saves.
The best and easiest way to skip building specific plugins is to simply remove/move them somewhere else from $(EngineSource)\Plugins
. There is technically a way to somehow add them to blacklist/do-not-build list but I never found a working method. I think it used to work once but with time that code broke and got abandoned/forgotten.
Each UE version has its own requirements to the minimal set of plugins required to build and successfully run Editor/Game
targets. You will have to experiment, because it constantly changes, but in general, here is minimal set for <=5.3 that works:
Plugins/Compression/OodleNetwork Plugins/Editor/EditorDebugTools
Plugins/Developer/BlankPlugin Plugins/Editor/EditorScriptingUtilities
Plugins/Developer/Concert Plugins/Editor/GameplayTagsEditor
Plugins/Developer/NullSourceCodeAccess Plugins/Editor/PluginBrowser
Plugins/Developer/PluginUtils Plugins/Editor/WorldPartitionHLODUtilities
Plugins/Developer/PropertyAccessNode Plugins/EnhancedInput/Binaries
Plugins/Developer/TextureFormatOodle Plugins/EnhancedInput/Config
Plugins/Developer/VisualStudioSourceCodeAccess Plugins/EnhancedInput/Content
Plugins/Editor/AssetManagerEditor Plugins/EnhancedInput/EnhancedInput.uplugin
Plugins/Editor/AssetReferenceRestrictions Plugins/EnhancedInput/Intermediate
Plugins/Editor/AssetSearch Plugins/EnhancedInput/Resources
Plugins/Editor/BlueprintHeaderView Plugins/EnhancedInput/Source
Plugins/Editor/ConsoleVariablesEditor Plugins/Messaging/TcpMessaging
Plugins/Editor/ContentBrowser Plugins/Runtime/Database
Plugins/Editor/CryptoKeys Plugins/Runtime/PropertyAccess
Plugins/Editor/DataValidation
To add a plugin back, you simply can copy it back into the $(EngineSource)\Plugins
and rebuild the targets, if you are working with source build. If you are using a foreign project and/or installed build
, copy the engine plugin into project's Plugins/
folder and rebuild your project. In 99% cases this will work just fine, but there can be some engine plugins that are hardcoded to only work properly when build inside the Engine space, like ReplicationGraph
plugin, so keep that in mind.
Do note that example projects like Lyra
will require a wider variety of plugins and often indirectly, i.e. when one plugins or module requires another and it is not immediately obvious.
This is an uncharted territory. Although the process and setup is similar to previous section describing plugins, one thing you need to keep in mind is that modules are intertwined way too deep between each other and UE itself (hello modularity) and for the most part you can't remove anything without consequences cascading down. Still, if you desire, you can experiement by removing module folder and files from $(EngineSource)\Developer
or $(EngineSource)\Editor
or $(EngineSource)\Runtime
. Don't forget to remove them from other module's dependencies as well, via respectitive *.Build.cs
descriptor.
You will also most likely need to rebuild UBT
afterwards, before you can build engine targets.
If you don't want to go through the hassle of passing some custom compiler/linker flags, then BuildConfiguration.xml
is just a tool for you - it allows you to configure/control build environment and build process for UE and its projects.
It is impossible to cover everything this config file offers, so we only go through the basics. You can read about the rest at
https://docs.unrealengine.com/5.3/en-US/build-configuration-for-unreal-engine/
Example config:
<?xml version="1.0" encoding="utf-8" ?>
<Configuration xmlns="https://www.unrealengine.com/BuildConfiguration">
<ParallelExecutor>
<MaxProcessorCount>6</MaxProcessorCount>
</ParallelExecutor>
<ProjectFileGenerator>
<bIncludeEnginePrograms>false</bIncludeEnginePrograms>
<bAllDocumentationLanguages>false</bAllDocumentationLanguages>
<bIncludeDotNetPrograms>false</bIncludeDotNetPrograms>
<bIncludeTemplateFiles>false</bIncludeTemplateFiles>
<bIncludeConfigFiles>false</bIncludeConfigFiles>
</ProjectFileGenerator>
<WindowsPlatform>
<WindowsSdkVersion>10.0.19041.0</WindowsSdkVersion>
<CompilerVersion>14.36.32532</CompilerVersion>
<PCHMemoryAllocationFactor>400</PCHMemoryAllocationFactor>
</WindowsPlatform>
<BuildConfiguration>
<bDisableDebugInfo>true</bDisableDebugInfo>
<bDisableDebugInfoForGeneratedCode>true</bDisableDebugInfoForGeneratedCode>
<bOmitPCDebugInfoInDevelopment>true</bOmitPCDebugInfoInDevelopment>
</BuildConfiguration>
</Configuration>
<!--5.3-->
Let us unpack this. This config was created for UE 5.3 as a base. The machine it is used on has 12 logical cores and 6 physical ones, but because UE build pipeline operate at a higher level on physical cores (the compilers/linkers will do their own thing), we specify here physical count (the UBT will output number of processor being used/available during build), hence MaxProcessorCount
set to 6. You can omit [ParallelExecutor]
altogether if unsure.
If you want to split execution to logical cores explicitly, you can also specify multiplier:
<ParallelExecutor>
<MaxProcessorCount>6</MaxProcessorCount>
<ProcessorCountMultiplier>1.9</ProcessorCountMultiplier>
</ParallelExecutor>
Example above will split the work across 11 logical cores: (6*1.9) rounded down.
[ProjectFileGenerator]
section allows us to configure some useful behaviour for project gen, like excluding extra junk from being added to project files. There is no point to recompile C# tools every time, for example.
[WindowsPlatform]
section allows us to specify which Windows SDK we will be building against via WindowsSdkVersion
directive (in case you have multiple installed), as well as which C++ build tools version we gonna use via CompilerVersion
directive. To find out which versions you can use there, go to <Visual_Studio_root_dir\VC\Tools\MSVC\>
- there will be a list of directories by version. You specify THIS exact version in the config, not the binary version of the linker/compiler. Finally, PCHMemoryAllocationFactor
allows us to configure how much memory we allocate per thread (in this case it most likely will be a thread per core) for PCH. If you get a lot of out of heap!
errors during compilation, try tweaking this parameter.
And the last section [BuildConfiguration]
is something we've already covered in Skipping Debug symbols and PDB gen). All of the options are self-explanatory, but if you need specifics, please consult linked UE documentation on the subject.
One thing to note is that I personally recommend using
%APPDATA%\Unreal Engine\UnrealBuildTool\
as a default location for your config. For some reason per-engine file sometimes being ignored and I haven't figured out what causes this bug yet.
TODO
TODO
TODO
So now that you have source engine built and running, you probably are wondering how can you get your purchased marketplace content added to it? A terrible option would be to install a launcher engine of the same version and then download marketplace assets/content for it via Epic Launcher and copy over, but this is a waste of space and time and simply not our way to do things.
Instead, we can use a CLI-tool made to interact with for Epic Store, called Legendary. It allows you to login with your credentials and download subscribed content directly. The usage is fairly simple and it has an extensive --help
output, but here is a quick-start:
-
legendary list --include-ue
will list all the downloadable UE content (along with the rest) -
legendary install AppNameHere --download-only --base-path D:\UEStuff
will download the subscription/app content
One thing to note - if you want to download some of the content from UE5.x apps, you can't do it on a freshly made account. You actually need to install Epic Launcher first, login with this account, initiate any UE5 version download, then cancel it and uninstall. This will "subscribe" you to UE5 feed and now it will be accessible in Legendary
as well.