After sitting on it for some time I figured it can be fixed by just prefixing the label with “L” which makes it private global symbol.
Assembler-local; it makes sure the symbol won't exist at all in the
object file, and that all references to it will have been resolved
before the linker gets involved. There's also a (rarer) "l" prefix for
things that can't be resolved by the compiler but the linker does have
The question here is whether this behaviour is expected. It seems to me any label defined within inline asm must have MCSymbol::IsTemporary set otherwise no way to resolve these fix-ups.
That sounds about right. You've already figured out most of the
details yourself; MachO objects produced by compiler are allowed to be
split up and shuffled by the linker at any global symbol boundary[*].
MachO as a format is pretty deficient and only allows 16 different
kinds of relocation (depending on how you count them). Most of those
are already allocated on ARM so if someone actually wanted to support
labels in asm blocks they'd need to fairly seriously rework either
ARMConstandIslands (to avoid moving constants across such boundaries,
and put them in the correct region in the first place) or CodeGen (to
make constants addressable via relocations that already exist).
I doubt anyone wants to do that without a *very* compelling use-case.
ARMConstantIslands is hard enough to maintain when it only has to
support sane situations.
[*] Theoretically it's controlled by the ".subsections_via_symbols"
directive but that's been emitted unconditionally for years and I
don't think anyone has any appetite for disabling it.