Landform is a C# terrain mesh processing toolkit that can generate 3DTiles datasets. It is used by the Mars 2020 mission in ground data processing to convert textured terrain meshes into the 3DTiles format, as well as to create contextual meshes that combine up to thousands of in-situ and orbital observations. Landform can be run as a command-line toolset or optionally deployed to AWS as a terrain processing service. It can also be used as a library for building other terrain mesh processing tools.
Landform can read mesh, image, and pointcloud input data in a variety of formats including a limited subset of the OpenInventor binary iv format, GLTF, OBJ, PLY, PNG, JPG, TIFF, GeoTIFF, VICAR, and PDS ODL-wrapped VICAR (IMG). Landform can write mesh and image data in many formats including 3DTiles, GLTF, OBJ, PLY, PNG, JPG, and TIFF.
In addition to serailizers for all the essential data formats used in Mars surface mission terrain processing, Landform also contains implementations of many useful and practical mesh and image processing algorithms including composite image stitching, texture backprojection, texture baking, texture atlassing, mesh decimation, mesh resampling, mesh reconstruction from pointclouds, mesh clipping, convex hull computation, CAHV[ORE] camera models, software rasterization, ray casting, feature-based mesh alignment, and creation of hierarchical 3DTiles datasets from large monolithic textured meshes.
Many Landform workflows currently require access to Mars 2020 or MSL ground data subsystems including the mission Places database server and the mission operational datastore. In principle it should be possible to replace these functions with data from the Mars 2020 Planetary Data System (PDS) Archive, but that will require some development work.
Most of the datasets produced by Landform for the Mars 2020 mission are not currently publicly available. However, our colleague Garrett Johnson has released a few as examples for his JavaScript 3D Tiles renderer:
Landform was originally developed at the Jet Propulsion Laboratory, California Institute of Technology for use in ground data processing for planetary surface missions under a contract with the National Aeronautics and Space Administration.
Individual contributors include Marsette Vona, Bob Crocco, Alexander Menzies, Charles Goddard, Thomas Schibler, Gailin Pease, Nicholas Charchut, Nicholas Anastas, Keavon Chambers, Benjamin Nuernberger, and Andrew Zhang.
Landform is released under the GNU GPL v3 due to the dependency on Emgu.CV. See LICENSE.txt.
If you are using this library for academic research or publications we ask that you please cite this library as:
@misc{nasa-ammos-landform,
author = {Marsette Vona and Bob Crocco and Alexander Menzies and Charles Goddard and Thomas Schibler and Gailin Pease and Nicholas Charchut and Nicholas Anastas and Keavon Chambers and Benjamin Nuernberger and Andrew Zhang},
title = {Landform Terrain Mesh Processing Toolkit},
howpublished = "\url{https://github.com/NASA-AMMOS/Landform}",
}
We have also written a whitepaper on the Landform contextual mesh algorithms:
@misc{vona2025landformcontextual,
author={Marsette Vona},
title={The Landform Contextual Mesh: Automatically Fusing Surface and Orbital Terrain for Mars 2020},
year={2025},
eprint={2509.18330},
archivePrefix={arXiv},
primaryClass={cs.RO},
url={https://arxiv.org/abs/2509.18330},
}
Landform previously required Windows to build and run; the current implementation is multiplatform and builds and runs on Linux x86_64, OS X arm64, and Windows x86_64. Currently two Linux distributions are supported: Ubuntu 24.04 and Amazon Linux 2023; this is mainly due to the EmguCV dependency. Binary packages for EmguCV releases are currently published to NuGet with a native library for Ubuntu 24.04. For Amazon Linux 2023 we have a script that builds a minimal EmguCV native library for Amazon Linux 2023.
set -o igncr because git on Windows may have converted the included .sh scripts to have Windows line endings (though we have a .gitattributes file that is supposed to prevent that), and by default the Cygwin bash interpreter does not like that.dotnet --version should return a version in the 9.0.X series.
apt-get install software-properties-common
add-apt-repository ppa:dotnet/backports
apt-get update
apt-get install dotnet-sdk-9.0
dnf install -y dotnet-sdk-9.0brew install --cask dotnet-sdkexport PATH="$PATH":/c/Program\ Files/dotnet.unzip, zip, curl, cmake, git, and patch. If not, install them as appropriate for your environment. For example:
sudo apt-get install unzip zip curl cmake git patchdnf install -y cmake make unzip zip git patchunzip, zip and curl, and patch should be pre-installed; for cmake run brew install --cask cmake-app or brew install cmake if using the homebrew package manager, or install cmake manually; git will be installed with the Xcode command line tools below.cmake available in the MSYS2 package manager is unfortunately not compatible), and then add it to your PATH: export PATH="$PATH":/c/Program\ Files/CMake/bin; also install git manually.unzip, zip, curl, and patch should be pre-installedcurl and patch should be pre-installed; for unzip and zip run pacman -S unzip zipunzip, zip, and curl if necessary.make and clang++. (On Windows the corresponding tools are nmake and cl, and they are included with Visual Studio.) At least clang++ version 20 is required, run clang++ --version to check.
curl https://apt.llvm.org/llvm-snapshot.gpg.key | apt-key add -
add-apt-repository -y "deb http://apt.llvm.org/noble/ llvm-toolchain-noble-20 main"
apt-get install -y clang-20
update-alternatives --install /usr/bin/clang clang /usr/bin/clang-20 140 --slave /usr/bin/clang++ clang++ /usr/bin/clang++-20
dnf install -y clang20
ln -s /usr/bin/clang-20 /usr/bin/clang
ln -s /usr/bin/clang++-20 /usr/bin/clang++
xcode-select --install.dos2unix src/*.sh src/*/*.sh to ensure that the build scripts have Unix line endings../scripts/build.sh. This will automatically download dependencies and compile both native and C# components../scripts/clean.sh script is also provided to remove compiled artifacts.A Dockerfile is also provided to build an x86_64 Amazon Linux 2023 Docker image suitable for building Landform. Launch Docker and then build the image with cd docker/builder; ./build.sh. A convenience script is also provided to run a bash shell on the image: cd docker/builder; ./up.sh. An alternative Dockerfile is also provided for Ubuntu 24.04; to use it, rename it to Dockerfile.
On an arm64 OS X host you may get build errors within the Docker container unless you enable "Apple Virtualization Framework" and "Use Rosetta for x86_64/amd64 emulation on Apple Silicon" in the Docker Desktop settings. Also, unfortunately, test workflows involving the RayTrace module will still fail in this configuration because RayTrace depends on embree which uses Intel AVX instructions, and those are not supported by Rosetta.
The runtime requirements for Landform are
dnf install -y libpng libtiff libgeotiff libjpeg-turbo mesa-libGL mesa-libGLU freeglut. On OS X and Windows there should be no additional dependencies.A Dockerfile is also provided to build an Amazon Linux 2023 Docker image suitable for running Landform. Launch Docker and then build the image with cd docker/runner; ./build.sh. A convenience script is also provided to run a bash shell on the image: cd docker/runner; ./up.sh. An alternative Dockerfile is also provided for Ubuntu 24.04; to use it, rename it to Dockerfile.
The top-level command-line entrypoint is in Landform.cs; it dispatches to a number of sub-commands such as process-tactical, process-contextual, etc. To see all the available sub-commands run
dir=dist # if you unpacked a pre-built release zip
#dir=src # if you built from source
./$dir/Landform/bin/Release/net9.0/Landform --help
Then run e.g.
./$dir/Landform/bin/Release/net9.0/Landform process-contextual --help
to see the specific command line options for a sub-command.
Additional documentation is provided in the header comments of the corresponding source files in the Landform subproject.
On OS X you will likely need to run ./scripts/osx-unquarantine.sh once for each deployment in order for Landform to invoke third-party dependency executables.
These are managed with the NuGet package manager and will be automatically downloaded as needed:
Landform 3DTiles products are typically viewed by Mars mission ground software such as ASTTRO which downloads the tileset data on demand and integrates with mission-specific interfaces. ASTTRO uses the open-source AMMOS Unity3DTiles component to load and render 3DTiles tilesets. The Unity3DTiles software also includes a simple stand-alone web-based viewer. A similar JavasScript component was also recently developed, AMMOS 3DTilesRendererJS.
Landform can optionally also produce meshes in more traditional textured mesh formats such as PLY or OBJ. This can be done either as a single monolithic mesh with one texture image, or split up into multiple submeshes. The monolithic form can suffer from limited texture resolution, even when using a relatively high resolution (e.g. 8k) image. In that case Landform can optionally allocate a larger central portion of the image to the central detailed portion of the terrain, with the periphery of the image mapped to the remainder of the terrain at a lower resolution.
Landform and its underlying matrix library XNAMath (ported from MonoGame) uses a right handed rotation, row vector convention, e.g. new_row_vector = row_vector * matrix. The portions of code that interface with OpenCV (EMGU) frequently convert to a column vector convention, so be careful.
Images are accessed by pixel using zero based rows and columns with the origin at the top left of the image. Integer pixel coordinats are at the top left corner of the pixel. Some of the camera model code uses pixel center conventions so be aware of half-pixel offsets.
Landform expects that texture coordinates for meshes follow the OpenGL convention of the lower-left of an image being the origin. This means that texture coordinates require a vertical coordinate swap to map between pixels and uvs.