In this section, we describe some advanced building scenarios. Basic building instructions are available elsewhere.
Install and run Docker for Windows (tested with version 18.06.1-ce-win73),
enable Windows containers,
increase maximum container disk size
and run docker-compose up. If you change Dockerfile, you'll need to run
docker-compose up --build to rebuild the Docker image. To run some other
commands instead of build.ps1, run
docker-compose run --rm ipasim powershell. To re-build, delete the folder
cmake (rm -r cmake from PowerShell). To build manually, just execute the
script build.ps1 (.\scripts\build.ps1 from PowerShell inside the container).
To run commands in a container repeatedly, first run
docker-compose run --name ipasim ipasim powershell (i.e., without option
--rm) and then (after exiting the container) run docker start -ai ipasim.
When we have our Docker machine up and running, we can start building. First,
run .\scripts\build.ps1 inside C:\ipaSim\src. That script creates build
directory C:\ipaSim\build. Inside that directory, run
ninja config-ipaSim-x86-Debug to prepare building of that configuration (x86
Debug). Then, move to C:\ipaSim\build\ipaSim-x86-Debug and continue using
Ninja from there (e.g., run ninja -t targets to see list of possible build
targets). To enable incremental builds across Docker builds, use scripts
C:\ipaSim\src\scripts\backup.ps1 and C:\ipaSim\src\scripts\restore.ps1. See
issue #3 for more details.
We use a concept of issues. They are contained in folder /docs/issues/ and
can be referenced from code by hashtag and number, e.g., #1.
Before we started using issues, we also used tags, i.e., unique short identifiers that were referenced from code and documented elsewhere. Below are documented those that can still be found in code.
[docker-script]: This script is referenced fromDockerfile. It's not meant to be run manually.
TAPI sources are located in /deps/tapi/.
[must-quote]: Changedbool->QuotingType,false->QuotingType::None,true->QuotingType::Double. LLVM API probably evolved.[no-dynamic]:ObjCPropertydoes not contain methodisDynamicand it seems it never did.[sort]: Inspired by Swift'sTBDGen.[no-cmake]: In the original code, this was built with CMake. But we don't use CMake, so we crafted it manually.
WinObjC sources are located in /deps/WinObjC/.
[objc-class]- We replace_OBJC_CLASS__NSCF...symbol references (those were generated by the GNUstep runtime) withOBJC_CLASS_$__NSCF...symbol references (which are generated by our Apple-like runtime).[class-symbols]- Changed_OBJC_CLASS_*toOBJC_CLASS_$_*and__objc_class_name_*toOBJC_METACLASS_$_*. This reflects the difference between how our runtime and the GNUstep runtime name those symbols. Although symbols__objc_class_name_*andOBJC_METACLASS_$_*probably doesn't mean the same thing, we only replace those symbols in.deffiles so it only causes them to be exported which is exactly what we want. Note that this "tag" is not actually used, because it would be virtually in every.deffile inside/deps/WinObjC/build/. TODO: Write a script that will do this automatically (without the need for manually changing those.deffiles).[ehtype]- So that it is not an error to have multiple occurrences of symbol_OBJC_EHTYPE_$_NSException. TODO: Instead makeclangto not generate those symbols.[no-nsobject]-NSObjectis implemented in our runtime, so we disabled it in WinObjC'sFoundationframework.[uikit-autolayout]- There is a circular dependency between projectsAutoLayoutandUIKit.
See its documentation.
LLVM's sources are located in /deps/llvm/, /deps/clang/, /deps/lld/ and
/deps/lldb/.
[ipasim-objc-runtime]: We are adding a new runtime calledipasimthat derives from theiosruntime and introduces changes that themicrosoftruntime introduced.[dllimport]: See section "Objective-C symbols across DLLs".[mhdr]: We are patching linker (lld-link) to add a section named.mhdrwhich will contain Mach-O header. This Mach-O header will then be used by ourlibobjcto initialize the image.[fixbind]: See[dllimport]- we are fixing some symbols to use__declspec(dllimport)semantics, but that introduces another level of indirection in data pointers. Unfortunately, Windows loader cannot bind symbols directly, so we need to fix those bindings at runtime. In Clang, we create a new section called.fixbindwhich contains addresses to all the bindings that need to be fixed. At runtime, we then fix those addresses in ourdyld.[pretty-print]: We improved pretty printing of functions to match our needs inHeadersAnalyzer.[emit-all-decls]: SeeHeadersAnalyzer.[irt]: We renamed folderInstrumentationRuntimetoIRtbecause the former was too long for Windows. TODO: Obviously, don't do this. Rather move our sources near the root (e.g.,C:\src\). But then also mention that in build instructions.[macho]: We want to read Mach-O object files on Windows, too. Alternative to this would be to emit PE/COFF instead, or just DWARF (-gsplit-dwarf). Then, we wouldn't have to read Mach-O object files.[no-lsystem]: We added option-no_lsystemwhich, when used, tells Clang driver not to pass option-lSystemto linker. We use this option inside ourHeadersAnalyzerto generate.dylibs on Windows (where is nolibSystem.dylibfor linker to use).[emit-bodies]: We don't want to emit bodies in ourHeadersAnalyzersince we are only interested in declarations. So we added and used this option to speed up the compilation by skipping body emission. If ever pushed upstream, this should be changed to emit just declarations, though. Because now it emits invalid almost-empty definitions.
LIEF's sources are located in /deps/LIEF/.
[lief-mt]: We link LIEF statically, because we need only substantial portion of it. But UWP apps need to link to CRT dynamically, so we need to use/MDcompiler option instead of/MT.