A .metal file is source text in the Metal Shading Language (MSL). Apple
defines the language in its Metal Shading Language Specification, a PDF of
about 300 pages (version 3.2 is dated June 2024). That PDF is larger than the tools used
for this page could read, so the language’s grammar, types, attributes and standard
library are not reproduced here; this page gives what Apple’s developer documentation and
its metal-cpp headers state, and points to the specification for the
rest.
Language versions
A program chooses the version when it compiles source at run time
(MTLLanguageVersion), and the command-line compiler takes it as
-std=metal4.0 and so on. The API value is the major version in the upper
16 bits and the minor version in the lower 16.
| Version | API value | Version | API value |
|---|---|---|---|
| 1.0 | 65536 (0x10000) | 2.3 | 131075 (0x20003) |
| 1.1 | 65537 (0x10001) | 2.4 | 131076 (0x20004) |
| 1.2 | 65538 (0x10002) | 3.0 | 196608 (0x30000) |
| 2.0 | 131072 (0x20000) | 3.1 | 196609 (0x30001) |
| 2.1 | 131073 (0x20001) | 3.2 | 196610 (0x30002) |
| 2.2 | 131074 (0x20002) | 4.0 | 262144 (0x40000) |
Apple’s documentation also lists version 4.1; its numeric value was not in the header
copy read for this page. The compiler defines __METAL_VERSION__ while it
compiles MSL, which shared C++/MSL headers test to tell the two apart.
What a file contains
MSL is based on C++, so a file is C++-style source: preprocessor directives,
declarations of types and helper functions, and entry-point functions marked with a
function-type keyword such as kernel or fragment. Pointers
and references carry an address-space keyword (see below). How arguments are bound to
the pipeline, with attributes, is defined in the specification and not reproduced
here.
Function types
The type of a top-level function, as the Metal API reports it
(MTLFunctionType):
| Type | API value | Meaning |
|---|---|---|
| vertex | 1 | A vertex function for a render pipeline. |
| fragment | 2 | A fragment function for a render pipeline. |
| kernel | 3 | A kernel for a compute pipeline. |
| visible | 5 | A function for a visible function table. |
| intersection | 6 | A function for an intersection function table. |
| mesh | 7 | A mesh function. |
| object | 8 | An object function. |
Address spaces
Address spaces named in Apple’s documentation: device,
constant, thread, threadgroup,
threadgroup_imageblock, ray_data and
object_data. In MSL 4.0 and earlier every pointer needs one of these
keywords; the implicit this of a member function without one is
thread.
MSL 4.1 adds generic pointers: a pointer without a keyword may point into
thread, threadgroup or device memory (but not
the other spaces, which still need their keyword, and not resource parameters of an
entry point). Related additions:
| Feature | Meaning |
|---|---|
static_cast<space T*>(p) | Converts a generic pointer to a concrete one without a check. |
addrspace_cast<space T*>(p) | Converts with a run-time check; gives nullptr if the pointer is in another space. |
is_thread_addrspace(), is_device_addrspace(), is_threadgroup_addrspace() | Test which space a generic pointer refers to (false for nullptr). |
MSL 4.1 also changes how function names are decorated, so binaries compiled for 4.0 and 4.1 must not be linked together.
From source to library
xcrun -sdk macosx metal -o Shadow.ir -c Shadow.metal source → intermediate file
xcrun -sdk macosx metal-ar -q Lights.metalar A.ir B.ir intermediate files → archive
xcrun -sdk macosx metal -o Lib.metallib Lights.metalar Shadow.ir → Metal library
.metal files in a project.The app loads the library at run time (makeLibrary(URL:)). The layout of
the library file is on the Metal library
page.
Sources
- Metal Shading Language Specification – Apple; the defining document (not read in full for this page)
- MTLLanguageVersion and MTLFunctionType – Apple developer documentation
- Writing reusable GPU functions with generic pointers – Apple: address spaces, generic pointers, casts and the MSL 4.1 ABI change
- Building a shader library by precompiling source files – Apple: the compile steps
- MTLLibrary.hpp – Apple’s metal-cpp header (a copy published with Babylon Native), for the numeric values
Not covered (in the specification only): MSL’s full grammar, scalar, vector, matrix and packed types, the attribute list, textures and samplers, and the standard library.