Skip to content

Commit f5749ba

Browse files
committed
Fix heading levels
We use h2 as the top heading level in RFCs; also some headers jumped a level in the document.
1 parent 816d4e7 commit f5749ba

1 file changed

Lines changed: 32 additions & 32 deletions

File tree

text/3458-unsafe-fields.md

Lines changed: 32 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
- RFC PR: [rust-lang/rfcs#3458](https://github.com/rust-lang/rfcs/pull/3458)
44
- Rust Issue: [rust-lang/rust#132922](https://github.com/rust-lang/rust/issues/132922)
55

6-
# Summary
6+
## Summary
77

88
This RFC proposes extending Rust's tooling support for safety hygiene to named fields that carry
99
library safety invariants. Consequently, Rust programmers will be able to use the `unsafe` keyword
@@ -25,7 +25,7 @@ accompanying safety documentation.
2525

2626
[`missing_safety_doc`]: https://rust-lang.github.io/rust-clippy/master/index.html#missing_safety_doc
2727

28-
# Motivation
28+
## Motivation
2929

3030
Safety hygiene is the practice of denoting and documenting where memory safety obligations arise
3131
and where they are discharged. Rust provides some tooling support for this practice. For example,
@@ -142,7 +142,7 @@ consider distant safe code. (See [*The Scope of Unsafe*].)
142142
For crates that practice good safety hygiene, reviewers will mostly be able to limit their review
143143
of distant routines to only `unsafe` code.
144144

145-
# Guide-level explanation
145+
## Guide-level explanation
146146

147147
A safety invariant is any boolean statement about the computer at a time *t*, which should remain
148148
true or else undefined behavior may arise. Language safety invariants are imposed by Rust
@@ -344,9 +344,9 @@ field in `ManuallyDrop`; e.g.:
344344
}
345345
```
346346

347-
## When *Not* To Use Unsafe Fields
347+
### When *Not* To Use Unsafe Fields
348348

349-
### Relaxing a Language Invariant
349+
#### Relaxing a Language Invariant
350350

351351
The `unsafe` modifier is appropriate only for denoting *library* safety invariants. It has no impact
352352
on *language* safety invariants, which must *never* be violated. This, for example, is an unsound
@@ -367,7 +367,7 @@ impl<T> Zeroed<T> {
367367

368368
...because `Zeroed::<NonZeroU8>::zeroed()` induces undefined behavior.
369369

370-
### Denoting a Correctness Invariant
370+
#### Denoting a Correctness Invariant
371371

372372
A library *correctness* invariant is an invariant imposed by an API whose violation must not result
373373
in undefined behavior. In the below example, unsafe code may rely on `alignment_pow`s invariant,
@@ -398,7 +398,7 @@ We might also imagine a variant of the above example where `alignment_pow`, like
398398
carry a safety invariant. Ultimately, whether or not it makes sense for a field to be `unsafe` is a
399399
function of programmer preference and API requirements.
400400

401-
## Complete Example
401+
### Complete Example
402402

403403
The below example demonstrates how field safety support can be applied to build a practical
404404
abstraction with small safety boundaries
@@ -518,9 +518,9 @@ impl<T> DerefMut for UniqueArc<T> {
518518
}
519519
```
520520

521-
# Reference-level explanation
521+
## Reference-level explanation
522522

523-
## Syntax
523+
### Syntax
524524

525525
The [`StructField` syntax][struct syntax], used for the named fields of structs, enums, and unions,
526526
shall be updated to accommodate an optional `unsafe` keyword just before the field `IDENTIFIER`:
@@ -538,13 +538,13 @@ StructField :
538538
The use of unsafe fields on unions shall remain forbidden while the [impact of this feature on
539539
unions](#safe-unions) is decided.
540540

541-
## Semantics
541+
### Semantics
542542

543543
Projections of fields marked `unsafe` must occur within the context of `unsafe`.
544544

545545
Clippy's [`missing_safety_doc`] lint ensures such fields have accompanying safety documentation.
546546

547-
# Rationale and Alternatives
547+
## Rationale and Alternatives
548548

549549
The design of this proposal is primarily guided by three tenets:
550550

@@ -562,7 +562,7 @@ This RFC prioritizes the first two tenets before the third. We believe that the
562562
broader utility, more consistent tooling, and a simplified safety hygiene story — outweigh its
563563
cost, [alarm fatigue](#alarm-fatigue). The third tenet implores us to weigh this cost.
564564

565-
## Tenet: Unsafe Fields Denote Safety Invariants
565+
### Tenet: Unsafe Fields Denote Safety Invariants
566566

567567
> A field *should* be marked `unsafe` if it carries library safety invariants.
568568
@@ -573,7 +573,7 @@ conditional on upholding safety invariants; for example:
573573
- An `unsafe` trait denotes that it carries safety invariants that must be upheld by implementors.
574574
- An `unsafe` function denotes that it carries safety invariants that must be upheld by callers.
575575

576-
## Tenet: Unsafe Usage is Always Unsafe
576+
### Tenet: Unsafe Usage is Always Unsafe
577577

578578
> Uses of `unsafe` fields that could violate their invariants *must* occur in the scope of an
579579
> `unsafe` block.
@@ -584,7 +584,7 @@ imposes when applied to other declarations; for example:
584584
- An `unsafe` trait may only be implemented with an `unsafe impl`.
585585
- An `unsafe` function is only callable in the scope of an `unsafe` block.
586586

587-
## Tenet: Safe Usage is Usually Safe
587+
### Tenet: Safe Usage is Usually Safe
588588

589589
> Uses of `unsafe` fields that cannot violate their invariants *should not* require an unsafe block.
590590
@@ -593,12 +593,12 @@ experience of practicing it. We adopt this tenet as a forcing function between d
593593
our first two tenets. All else being equal, we give priority to designs that minimize the needless
594594
use of `unsafe`.
595595

596-
## Alternatives
596+
### Alternatives
597597

598598
These tenets effectively constrain the design space of tooling for field safety hygiene; the
599599
alternatives we have considered conflict with one or more of these tenets.
600600

601-
### Unsafe Variants
601+
#### Unsafe Variants
602602

603603
We propose that the `unsafe` keyword be applicable on a per-field basis. Alternatively, we can
604604
imagine it being applied on a per-constructor basis; e.g.:
@@ -629,7 +629,7 @@ variants are conceptually unsafe, requiring the programmer to use `unsafe` even
629629
of 'safe' fields. This violates [*Tenet: Safe Usage is Usually
630630
Safe*](#tenet-safe-usage-is-usually-safe).
631631

632-
### Field Moving is Safe
632+
#### Field Moving is Safe
633633

634634
We propose that all uses of `unsafe` fields require `unsafe`, including reading. Alternatively, we
635635
might consider making reads safe. However, a field may carry an invariant that would be violated by
@@ -654,7 +654,7 @@ documents its safety conditions as they relate to `KeepAlive`), rather than in d
654654
interactions with `UnsafeCell<T>` (whose methods necessarily provide only general guidance).
655655
Consequently, we require that moving unsafe fields out of their enclosing type requires `unsafe`.
656656

657-
### Field Copying is Safe
657+
#### Field Copying is Safe
658658

659659
We propose that all uses of unsafe fields require `unsafe`, including copying. Alternatively, we
660660
might consider making field copies safe. However, a field may carry an invariant that could be
@@ -663,7 +663,7 @@ imposes an invariant on the value of `T`. In this alternative proposal, such a f
663663
copiable out of its enclosing type, then safely mutated via the API of `RefCell`. Consequently, we
664664
require that copying unsafe fields out of their enclosing type requires `unsafe`.
665665

666-
### Copy Is Safe To Implement
666+
#### Copy Is Safe To Implement
667667

668668
We propose that `Copy` is conditionally unsafe to implement; i.e., that the `unsafe` modifier is
669669
required to implement `Copy` for types that have unsafe fields. Alternatively, we can imagine
@@ -692,7 +692,7 @@ However, the `ptr` field introduces a declaration-site safety obligation that is
692692
with `unsafe` at any use site; this violates [**Tenet: Unsafe Usage is Always
693693
Unsafe**](#tenet-unsafe-usage-is-always-unsafe).
694694

695-
### Nontrivial Destructors are Prohibited
695+
#### Nontrivial Destructors are Prohibited
696696

697697
If a programmer applies the `unsafe` modifier to a field with a nontrivial destructor and relaxes
698698
its invariant beyond that required by the field's destructor, Rust cannot prevent the
@@ -758,7 +758,7 @@ Unsafe Fields Denote Safety Invariants**](#tenet-unsafe-fields-denote-safety-inv
758758
requiring trivially `unsafe` drop glue), a violation of [**Tenet: Safe Usage is Usually
759759
Safe**](#tenet-safe-usage-is-usually-safe).
760760

761-
### Unsafe Wrapper Type
761+
#### Unsafe Wrapper Type
762762

763763
This RFC proposes extending the Rust language with first-class support for field (un)safety.
764764
Alternatively, we could attempt to achieve the same effects by leveraging Rust's existing visibility
@@ -840,7 +840,7 @@ exchanging the `len`s of two instances of the aforementioned `Vec`).
840840

841841
These challenges motivate first-class support for field safety tooling.
842842

843-
### More Syntactic Granularity
843+
#### More Syntactic Granularity
844844

845845
This RFC proposes the rule that *a field marked `unsafe` is unsafe to use*. This rule is flexible
846846
enough to handle arbitrary field invariants, but — in some scenarios — requires that the user write
@@ -900,7 +900,7 @@ marked `unsafe` is unsafe to use* is both pedagogically simple and failsafe; i.e
900900
field is marked `unsafe`, it cannot be misused in such a way that its invariant is violated in safe
901901
code.
902902

903-
### Mixing Syntactic Knobs with a Wrapper Type
903+
#### Mixing Syntactic Knobs with a Wrapper Type
904904

905905
One alternative proposed in this RFC's discussion recommends a combination of syntactic knobs and a
906906
wrapper type. In brief, a simple [`Unsafe` wrapper type](#unsafe-wrapper-type) would be provided,
@@ -930,9 +930,9 @@ field so that field's safety documentation may be examined.
930930
Comparatively, we believe that this RFC's proposal is both pedagogically simpler and less prone to
931931
misuse, and that these benefits outweigh its [drawbacks](#drawbacks).
932932

933-
# Drawbacks
933+
## Drawbacks
934934

935-
## Trivial Safety Proofs
935+
### Trivial Safety Proofs
936936

937937
The primary drawback of this proposal is that it — in some scenarios — necessitates writing
938938
'trivial' safety proofs. For example, merely reading `Vec`'s `len` field obviously cannot invalidate
@@ -956,19 +956,19 @@ but **not** *must* — denote field safety invariants with the `unsafe` keyword.
956956
soundness nor security issue to continue to adhere to the current convention of using visibility to
957957
enforce field safety invariants.
958958

959-
# Prior art
959+
## Prior art
960960

961961
Some items in the Rust standard library have `#[rustc_layout_scalar_valid_range_start]`,
962962
`#[rustc_layout_scalar_valid_range_end]`, or both. These items have identical behavior to that of
963963
unsafe fields described here. It is likely (though not required by this RFC) that these items will
964964
be required to use unsafe fields, which would reduce special-casing of the standard library.
965965

966-
# Unresolved questions
966+
## Unresolved questions
967967

968968
- If the syntax for restrictions does not change, what is the ordering of keywords on a field that
969969
is both unsafe and mut-restricted?
970970

971-
## Terminology
971+
### Terminology
972972

973973
This RFC defines three terms of art: *safety invariant*, *library safety invariant*, and *language
974974
safety invariant*. The meanings of these terms are not original to this RFC, and the question of
@@ -977,9 +977,9 @@ debated](https://github.com/rust-lang/unsafe-code-guidelines/issues/539). This R
977977
prescribe its terminology. Documentation of the unsafe fields tooling should reflect broader
978978
consensus, once that consensus is reached.
979979

980-
# Future possibilities
980+
## Future possibilities
981981

982-
## Partial Borrows
982+
### Partial Borrows
983983

984984
The primary drawback of this proposal is that it — in some scenarios — necessitates writing
985985
'trivial' safety proofs. For example, merely reading `Vec`'s `len` field obviously cannot invalidate
@@ -990,7 +990,7 @@ maintainer can define a *safe* accessor (i.e.,
990990
proof. However, in cases where multiple, partial field borrows are required, such an accessor cannot
991991
be invoked. Future language extensions that permit partial borrows will resolve this drawback.
992992

993-
## Syntactic Knobs and Wrapper Types
993+
### Syntactic Knobs and Wrapper Types
994994

995995
While we are confident that this RFC has the best tradeoffs among the alternatives in the design
996996
space, it is not a one-way door. Changes to the default semantics of `unsafe` could be realized over
@@ -1000,7 +1000,7 @@ knobs](#more-syntactic-granularity) and [wrapper types](#unsafe-wrapper-type). F
10001000
addition to this RFC's `unsafe` modifier, additional variants in the form `unsafe(<modifiers>)`
10011001
(e.g., `unsafe(mut)`) could be added to denote that some subset of uses is always safe.
10021002

1003-
## Safe Unions
1003+
### Safe Unions
10041004

10051005
Today, unions provide language support for fields with subtractive *language* invariants. Unions may
10061006
be safely defined, constructed and mutated — but require unsafe to read. Consequently, it is

0 commit comments

Comments
 (0)