--- title: T-spec meeting 2025-06-26 tags: ["T-spec", "meeting", "minutes"] date: 2025-06-26 discussion: https://rust-lang.zulipchat.com/#narrow/channel/399173-t-spec/topic/Meeting.202025-06-26/ url: https://hackmd.io/4SIoMs-_Qp6S5xYt3jUsOQ --- Attendees: - Eric - Pierre-Emmanuel Patry - Sam Wright - Tomas Sedovic - Sid Askary - tshepang - TC - Jack - Josh Regrets: - Joel Marcey Agenda: - Updates to the agenda? - PR Review ## Updates to the agenda ### Tomas: 2025 H2 Project Goals - Proposals open until 2025-07-18 - Submit proposals as PRs to: https://github.com/rust-lang/rust-project-goals/ - Flagship goals: smaller, more specific, bottom-up - What would you like to see as a flagship goal(s)? - July 21 to Aug 1: Prioritization discussions with teams and team leads; flagship goal selection - More details in Niko's email or here: https://hackmd.io/@nikomatsakis/BkOXVTWNle ## Compiler flags and how they affect the abstract machine https://github.com/rust-lang/rust/pull/142824 -- `-Cmin-function-alignment` Eric: TC and I talked about this on Tuesday. What does it mean for flags and other properties to propagate into the language. This is a good case but there are others -- e.g. the target flags. These change how the language is interpreted. Another example: panic/abort, debug assertions, overflow checks. TC: I asked Ralf about this. He said the only existing thing miri cares about in this way are target features. It uses this so that miri doesn't immediately flag UB when it sees an intrinsic. I asked about panic abort and in his world that affect the translation from Rust to MiniRust, but doesn't affect the Mini Rust AM. In his model there are two sets of target features: static and dynamic. The static set is fixed during compilation. The dynamic set must be a superset of the static set, and the dynamic set must contain the target features for any crate that's part of the program. Miri doesn't model the dynamic set; we effectively assume it's equal to the static set. TC: Any particular feelings about how to address this in the specification of the language? Eric: Do you have a vision of what it would look like? Let's say we decide this min-function-alignment is a property worth defining. What would it look like in the Reference? TC: When we get to the operational semantics we'd say: if you pass this compiler flag, it changes the operational semantics of the language to fulfill the property and you can rely on this when proving the soundness of your programs. I.e., when given this flag, the language **must** ensure that the property holds. Eric: You could make the argument that a safety comment around unsafe could say that this is safe because the flag's been passed. TC: That is why it's an interesting specification issue. TC: One interesting question about this, on the lang side, is if it's not a target feature that consistently applies to the entire program, what guarantees are we making for e.g. monomorphized code. Josh: Also even if you said it applied everywhere, it'd still only apply to everywhere Rust. If you try to count on it on functions you've compiled from C, you can't rely on that. I expect it to be compilation-unit specific. TC: For C code, of course, we're not monomorphizing anything (unless we start instantiating C++ templates). Josh: But LTO inlining would. The way we'd document this is that it's not observable. You could either get it with inline assembly (then all bets ar off) or getting the address of the function -- in which case we'd have to generate an out-of-line copy of that function. TC: Everything Josh mentioned are interesting documentation concerns too. Eric: What is the future path for `-Cmin-function-alignment`? Seems like there's a lot of back-and-forth going on. TC: They'd broken out stabilization of this flag. The one with the attribute is a bit harder because it could be applied to specific places in the code. I asked: is there any world where this is better as a crate-level attribute? So they'll need to think about this. What's the usecase? Is it just for performance? There was a Zulip discussion where they discussed relying on it for correctness. Eric: If the solution is to document that you can't rely on this for safety or other properties that seems to solve the issue. TC: I agree, that'd be the simple answer. We can say it's a hint and the compiler can generate any alignment it wants. We need to understand how people are planning to use it, though. If e.g. Rust for Linux will rely on it for correctness we probably can't just say it's a hint. Eric: Someone suggested they'd have a custom target where they had all the custom features thay needed. Josh: The custom target mechanism is useful but: it's not stable and I don't think it's the answer for everything even if it were stable. The current proposal to change some nature of the target but still it being the same target is useful. For min alignment, some people rely on it for optimizations, some for alignment within compilation units. Eric: Would something like min alignment considered to be something that you can't mix? ## Defining the `breakpoint` function https://github.com/rust-lang/rust/pull/142325 TC: This comes down to how we think about documenting the intrinsic behavior of certain language primitives in the operational semantics of the language. There's this intrinsic called `breakpoint`. The library will emit a certain instruction on various platforms. TC: Do you want to treat it as an unconditional break (but not optimize the code that comes after it)? It raises issues on what can someone rely on when they're making safety/soundness arguments. What Miri would do. There's a question about compiler fencing -- whether you can assume that everything that was written before has happened. Josh: The challenge is that this behaviour has the programmer in the loop for the case of correctness. When you put a breakpoint the programmer's expectation is that you're trying to debug this. But from the point of the Reference is when you enter the breakpoint it's treated as an abort. But then the programmer can change the program and continue and at some point the correctess of the program can't be made. TC: Not that I'd propose this, but I think you could argue coherently for this to be treated as a noreturn function unconditionally. The compiler could be within its rights to throw away the code that comes after it. Then keeping the code after the breakpoint would just be a "quality of implementation" issue. Eric: How does this relate to us? We generally don't document intrinsics etc. from the lang side at all. The compiler/stdlib can do whatever it wants. TC: When you think about what Miri has to do, either it throws up its hands like it does in an FFI call. Or it has to have some way to model this and interpret what the correct range of the behaviors of the program is. That Miri must decide this is an exemplar of why this is a language matter. We have to specify the semantics. TC: There's an interesting case study here. When we look at the `black_box` function definition in core, it has a lot of lang documentation related to its operational semantics. If we wanted to be less formal here, the documentation for that could be shorter. Eric: I think we could say that this is outside of the scope of Miri but then Miri could decide to treat this speficically like it does for certain FFI calls. TC: So you'd say this is an intrinsic and we've got a bunch of other intrinsics like fused additions -- where do you draw the line between intrinsics we define vs. ones we treat as FFI calls? Eric: I don't know. TC: That's the hard question. That's why it's an interesting spec question. How do we talk about the scope of the specification of all these intrinsics. Eric: I assume other languages have the same problem. C/C++ compilers have intrinsics. TC: They rigorously define at least the intrinsics of theirs that I've had reason to look at recently, e.g. related to floating point operations. Eric: I'm always inclined to let the standard library docs to fill that space instead of trying to duplicate them. TC: That's what we've done traditionally. It gets to the interesting quesiton of, for the standard library docs to fill both roles, they must not just be general user documentation but also strictly define what the behavior is that you can rely on if you're arguing the correctness of the program. That is, they have to hold to the standard of formal argumentation. Eric: I don't know how difficult it'd be to uphold that. TC: Other questios, thoughts on this? ## PR Review Overview -- https://hackmd.io/@ehuss/BJehg1sVgg Eric: All the things at the bottom are blocked on various things. I figured we could continue Ralf's work since he's responded on Tuesday. ### allow constants to refer to mutable/external memory, but reject such constants as patterns #1859 https://github.com/rust-lang/reference/pull/1859 -- const eval: mutable/external memory comments from ralf to be applied Eric: Ralf left some comment.s My thinking is if you applied those, I don't see a problem. It's still blocked on the change being made. TC: I think he change being made is being blocked on us. TC: Do you actually want to rename the reference identifier? Eric: No opinion but renaming seems to make sense. TC: The second suggestion is adding "interior mutable static". (Discussion, leading to work, leading to merging the Reference PR and unblocking the stabilization.) ### const-eval.const-expr.borrows: mention indirect places #1865 https://github.com/rust-lang/reference/pull/1865 (Discussion leading to us asking questions of the author on the PR.) ## Jitsi Chat