rust-lang / rust

Empowering everyone to build reliable and efficient software.
https://www.rust-lang.org
Other
97.35k stars 12.59k forks source link

Support Apple's TvOS Simulator on Apple Silicon #115692

Open bcardarella opened 1 year ago

bcardarella commented 1 year ago

Currently it appears that Rust can only compile for TvOS's Simulator running on x86. Apple Silicon need arm64. Specifically we need compile support for this target: https://github.com/apple/swift/blob/ffbc65c8c48cb38db190fa0618fe2b5937a334b8/utils/build-script-impl#L649-L658

Currently there is only:

➜  ~ rustc --print target-list | grep tvos
aarch64-apple-tvos
x86_64-apple-tvos
Urgau commented 1 year ago

Isn't this aarch64-apple-tvos ? since in Rust we use aarch64 instead of arm64.

bcardarella commented 1 year ago

@Urgau according to this issue: https://github.com/rust-lang/rust/issues/48862#issuecomment-1712393361 Rust implemented support for the TvOS Simulator compile target of x86 but Swift itself is using arm64 as the compile target for the TvOS simulator. The original issue is from 2018 so perhaps Apple updated the Simulator when they released the M1/M2 macs?

bcardarella commented 1 year ago

A bit more on this, Apple added support for both x86 and arm64 tvos simulator in Swift 5.3: https://github.com/apple/swift/commit/795c363eb9f0b0b0d925109370bb9d105ec1c270

Nemo157 commented 1 year ago

There's some annoying lack of precision in the target names, for ios and tvos targets the simulator targets only get the -sim suffix when there's also a native target on the same architecture. If you look at the target definitions aarch64-apple-tvos is a tvos_llvm_target while x86_64-apple-tvos is a tvos_sim_llvm_target. What is needed is a new aarch64-apple-tvos-sim target to go next to the native target.

(EDIT: and as actually got mentioned just yesterday some standardization of the target names would make this less confusing, the newer watchos targets always use -sim on the simulator variants).

bcardarella commented 1 year ago

@Nemo157 agreed, the naming has been in part an issue. Would changing these names to follow a convention be considered a breaking change?

Nemo157 commented 1 year ago

Yes, but they're tier 3 targets where breaking changes are allowed. There's an in-progress rename of another tier 3 target that provides a good example: https://github.com/rust-lang/rust/pull/110596, the first step would probably be to start a discussion on zulip to gauge whether the target maintainers are on board with changing the name, and then submit an MCP like the wasi one.

bcardarella commented 1 year ago

@Nemo157 I've had difficulty with knowing where to post messages on Zulip before and get blasted pretty quickly. I've found that community to be pretty hostile to newcomers that are unaware of where the correct place is to ask questions

thomcc commented 1 year ago

So...

  1. I agree the name x86_64-apple-tvos are bad and need to change to x86_64-apple-tvos-sim, and some of our other -sim targets have the same issue too, which would be good to fix, and I have a plan written up below (that I can just take, probably). But...
  2. I don't think a rename of the x86_64-apple-tvos target needs to happen in order to add support for a aarch64-apple-tvos-sim target.

Moreover, even if we could just do the rename without any scrutiny beyond t-compiler r+ (one could make an argument for this in the case of x86_64-apple-tvos-sim), I would prefer if adding aarch64-apple-tvos-sim support to happened in a entirely separate PR from changing any existing target names.

So, if you wanna add aarch64-apple-tvos-sim, that should not be blocked by anything -- feel free to go for it if the inspiration strikes. CC me on the PR.

The rest of comment is about renaming all of the misnamed simulator targets, of which x86_64-apple-tvos is merely a single example. This is not relevant to the problem of adding aarch64-apple-tvos-sim support, so stop reading now if that's what you're here for.

--

So, renaming. I have Thoughts.

This issue applies to several simulator targets right now, a lot of them have names that fail to reflect that they're simulators (among other issues). They're mostly tier 3, with a single tier 2, we should just do all the renames in with a single batch MCP/FCP/whatever, to ensure everything that is a -sim ends in -sim.

Like, right now, to know if a target is a simulator, you either have to check it, memorize the set, or reason it out based on the history of Apple releases of hardware and software, and possibly also Rust's support for that target. For example, the reasoning you might have to apply for figuring out x86_64-apple-ios (which is not the hardest one to reason through) might be:

Well, iOS doesn't support x86_64 directly, but it does have simulator support, and catalyst support, and the simulator was added first, so the unsuffixed target name must implicitly be the simulator target.

Maybe this is an exaggeration, but it's pretty bad, got worse with the addition of catalyst. It also stands to continue to get worse in the future.

So, we can remove this by renaming simulator targets to end in -sim even if if there's no non-sim version of that triple, but what all would we need to change? These (including more discussion than they deserve):

  1. x86_64-apple-tvos should be renamed to x86_64-apple-tvos-sim.

    This should be uncontroversial and honestly, for a tier 3 target that exists mostly for development/debugging (shipping code for a simulator is probably impossible) and was no_std only prior to a few months ago... I'd almost say that we could probably just do it with only a compiler-team r+.

  2. i386-apple-ios should be i686-apple-ios-sim. This is a profoundly weird one but only really because the name is just a disaster. The fixed name is clear, this target is a simulator (so it should say so), and it has target features on-par with (or slightly better than) the other targets calling themselves i686-*.

    In practice, I don't think it gets much use, although if targetting 32-bit iOS you're probably using it as the simulator (e.g. it works on 64-bit macOS so that you can simulate against a 32-bit chip, as it took a while for iPhones to move to aarch64). The reason to rename it is that it causes a lot of confusion, from:

    • Folks not realizing that it's a simulator, because it doesn't say so. This is occasionally relevant, but presumably something like this is why we seem to have failed to set cfg(target_abi = "sim"), unlike every other simulator target.
    • Folks thinking it's actually honest-to-god i386, because it's in the name. This is very misleading because Rust doesn't support x86 anywhere that old. It's not that rare to find things that use i386 for "unspecified 32bit x86" and Apple calling this target i386 is just a case of that for the most part.

    This target is barely-supported, but won't go away any time soon (I believe we won't drop the 32-bit apple targets until after the currently in-progress iOS/macOS version bump). This simulator only was removed in late 2022, so it's not that obscure either.

    Which is all to say: it's name is busted enough to cause confusion, but the target probably isn't obscure or busted enough to deserve removal. I think we just rename it, and because we're doing it in a batch, we could probably do a single MCP for all three.

    Also, for whatever reason, this target doesn't have cfg(target_abi = "sim") like all the others, despite definitely being a simulator (by default the LLVM target ends with -simulator, and in clang __is_target_environment(simulator)[^env] reports true). My wild unfounded guess would be that this somehow was caused by the fact that the name doesn't have -sim in it.

  3. x86_64-apple-ios should be renamed to x86_64-apple-ios-sim. It is the normal simulator for x86_64 macs, and is the only one of these that is a tier 2 target (the others are tier 3).

    People use this (mainly for development, but some for CI) so we should do so as gently as possible. For example, at a minimum do whatever we're doing for wasm32-wasi.

If we do that, and then never add an apple simulator target that doesn't end with -sim (perhaps verified by a rustc-target unit test that checks that targets with -simulator in the LLVM triple always have target_abi = "sim" and have a rust triple ending in -sim), it would be really nice.

This is a lot, but writing all this down has been on my TODO for a while.

I'll file an MCP for the 3 target renames later, it's off topic for this but I got pinged and even emailed to ask.

thomcc commented 1 year ago

Also we should not call it arm64. It doesn't matter if Apple uses arm64 to refer to that architecture, we call it aarch64 on Apple and non-Apple targets alike and there's no reason to diverge here.

I am firmly against naming the simulator target which runs on the Apple Silicon Macs anything other than aarch64-apple-tvos-sim -- After all, the target name we use for iOS running on the same machines is aarch64-apple-ios-sim, which IMO has no issues.

bcardarella commented 1 year ago

@thomcc I'm :+1: on the larger more-correct effort. If you need help I'm happy to pull in some resources

bcardarella commented 1 year ago

fwiw, I'm not suggesting renaming to arm64. If Rust has a predefined naming convention that makes sense to stick to. I was just using the naming in Apple's own reference code. aarch64 is :+1:

madsmtm commented 7 months ago

Also, for whatever reason, this target doesn't have cfg(target_abi = "sim") like all the others, despite definitely being a simulator (by default the LLVM target ends with -simulator, and in clang __is_target_environment(simulator)[^env] reports true). My wild unfounded guess would be that this somehow was caused by the fact that the name doesn't have -sim in it.

Also hit this today, filed https://github.com/rust-lang/rust/pull/121210 for that.