|
| 1 | +# Strict Memory Safety Warnings (`StrictMemorySafety`) |
| 2 | + |
| 3 | + |
| 4 | +This diagnostic group includes warnings that identify the use of language constructs and library APIs that can undermine memory safety. They are enabled by the `-strict-memory-safety` compiler flag. Examples of memory-unsafe code in Swift include: |
| 5 | + |
| 6 | +- Use of a function or type annotated with `@unsafe`: |
| 7 | + ```swift |
| 8 | + func getPointee<T>(_ pointer: UnsafeMutablePointer<Int>, as type: T.Type) -> T { |
| 9 | + // reference to unsafe global function 'unsafeBitCast' |
| 10 | + return unsafeBitCast(pointer.pointee, to: type) |
| 11 | + } |
| 12 | + ``` |
| 13 | +- Use of a function involving an `@unsafe` type: |
| 14 | + ```swift |
| 15 | + func evilMalloc(size: Int) -> Int { |
| 16 | + // use of global function 'malloc' involves unsafe type 'UnsafeMutableRawPointer' |
| 17 | + return Int(bitPattern: malloc(size)) |
| 18 | + } |
| 19 | + ``` |
| 20 | + |
| 21 | +- Use of an entity that makes use of an unsafe language feature: |
| 22 | + |
| 23 | + ```swift |
| 24 | + // use of an unowned(unsafe) variable is not memory-safe |
| 25 | + unowned(unsafe) var parentNode: TreeNode<T> |
| 26 | + ``` |
| 27 | + |
| 28 | +- Definition of a type whose storage contains unsafe types: |
| 29 | + ```swift |
| 30 | + // struct MyTemporaryBuffer has storage involving unsafe types |
| 31 | + struct MyTemporaryBuffer<T> { |
| 32 | + private var storage: UnsafeBufferPointer<T> |
| 33 | + } |
| 34 | + ``` |
| 35 | + |
| 36 | +- Using an `@unsafe` operation to satisfy a safe protocol requirement: |
| 37 | + ```swift |
| 38 | + // conformance of 'MyType' to protocol 'CustomStringConvertible' involves unsafe code |
| 39 | + struct MyType: CustomStringConvertible { |
| 40 | + @unsafe var description: String { |
| 41 | + "I am unsafe!" |
| 42 | + } |
| 43 | + } |
| 44 | + ``` |
| 45 | + |
| 46 | +The warnings produced by strict memory safety can be suppressed by acknowledging the unsafe behaior with one of three constructs: |
| 47 | + |
| 48 | +* `unsafe` expressions to acknowledges that there exists memory-unsafe code within the given expression, similar to the way `try` and `await` work for throwing and asynchronous functions: |
| 49 | + |
| 50 | + ```swift |
| 51 | + func evilMalloc(size: Int) -> Int { |
| 52 | + return unsafe Int(bitPattern: malloc(size)) |
| 53 | + } |
| 54 | + ``` |
| 55 | + |
| 56 | +* `@unsafe` attribute, which acknowledges that a type or conformance is also unsafe: |
| 57 | + |
| 58 | + ```swift |
| 59 | + struct MyType: @unsafe CustomStringConvertible { |
| 60 | + @unsafe var description: String { |
| 61 | + "I am unsafe!" |
| 62 | + } |
| 63 | + } |
| 64 | + ``` |
| 65 | + |
| 66 | +* `@safe` attribute to indicate that an entity encapsulates the unsafe behavior to provide a safe interface: |
| 67 | + |
| 68 | + ```swift |
| 69 | + @safe struct MyTemporaryBuffer<T> { |
| 70 | + private var storage: UnsafeBufferPointer<T> |
| 71 | + } |
| 72 | + ``` |
0 commit comments