Previously, we skipped checking the return type of a function for safety
as we expected to warn at the use of the returned value:
let x = returnsUnsafe()
usesUnsafe(x) // warn here
Unfortunately, this resulted in missing some unsafe constructs that can
introduce memory safety issues when the use of the return value had a
different shape resulting in false negatives for cases like:
return returnsUnsafe()
or
usesUnsafe(returnsUnsafe())
This PR changes the analysis to always take return types of function
calls into account.
rdar://157237301
This applies more annotations in the `INTERNAL_CHECKS_ENABLED` disabled
paths, Windows, 32-bit, and non-ObjC paths. Interestingly enough, there
are a couple of compiler intrinsics which are also uncovered.
- when compiling embedded cross compile target standard libraries, include AVR
- add 16-bit pointer as a conditional compilation condition and get the void pointer size right for gyb sources
- attempt to fix clang importer not importing __swift_intptr_t correctly on 16 bit platforms
- changed the unit test target to avr-none-none-elf to match the cmake build
[AVR] got the standard library compiling in a somewhat restricted form:
General
- updated the Embedded Runtime
- tweaked CTypes.swift to fix clang import on 16 bit platforms
Strings
- as discussed in https://forums.swift.org/t/stringguts-stringobject-internals-how-to-layout-on-16-bit-platforms/73130, I went for just using the same basic layout in 16 bit as 32 bit but with 16 bit pointers/ints... the conversation is ongoing, I think something more efficient is possible but at least this compiles and will probably work (inefficiently)
Unicode
- the huge arrays of unicode stuff in UnicodeStubs would not compile, so I skipped it for AVR for now.
Synchronization
- disabled building the Synchronization library on AVR for now. It's arguable if it adds value on this platform anyway.
Speculatively fixing this to rule out potential miscompiles.
The compiler needs to know if a reference is being materialized out of
thin air. The proper way to do that is with the Unmanaged API.
Under the hood, this forces the reference into an "unowned(unsafe)"
variable which the reference must be reloaded from. That tells the
compiler that it can't optimize some seemingly unrelated object which
the reference may happen to refer to at runtime.
/// Warning: Casting from an integer or a pointer type to a reference type
/// is undefined behavior. It may result in incorrect code in any future
/// compiler release. To convert a bit pattern to a reference type:
/// 1. convert the bit pattern to an UnsafeRawPointer.
/// 2. create an unmanaged reference using Unmanaged.fromOpaque()
/// 3. obtain a managed reference using Unmanaged.takeUnretainedValue()
/// The programmer must ensure that the resulting reference has already been
/// manually retained.
It does not compile in this mode.
```
error: no exact matches in call to instance method 'appendInterpolation'
owner: \(repr._objectIdentifier!), \
```
There is little point to having `isUTF16` properties when they simply
return `!isUTF8`; remove them.
Rename `String.Index._copyEncoding(from:)` to
`_copyingEncoding(from:)`.
This fixes a compatibility issue with potential future UTF-8 encoded
foreign String forms, as well as simplifying the code a bit — we no
longer need to do an availability check on inlinable fast paths.
The isForeignUTF8 bit is never set by any past or current stdlib
version, but it allows us to introduce UTF-8 encoded foreign forms
without breaking inlinable index encoding validation introduced in
Swift 5.7.
Starting with Android 11, AArch64 placed a tag in the top byte of pointers to
allocations, which has been slowly rolling out to more devices and collides
with Swift's tags. Moving these tags to the second byte works around this
problem.
There are three flavors, corresponding to i < endIndex, i <= endIndex, and range containment checks.
Additionally, we have separate variants for index validation in substrings.
Assign some previously reserved bits in String.Index and _StringObject to keep track of their associated storage encoding (either UTF-8 or UTF-16).
None of these bits will be reliably set in processes that load binaries compiled with older stdlib releases, but when they do end up getting set, we can use them opportunistically to more reliably detect cases where an index is applied on a string with a mismatching encoding.
As more and more code gets recompiled with 5.7+, the stdlib will gradually become able to detect such issues with complete accuracy.
Code that misuses indices this way was always considered broken; however, String wasn’t able to reliably detect these runtime errors before. Therefore, I expect there is a large amount of broken code out there that keeps using bridged Cocoa String indices (UTF-16) after a mutation turns them into native UTF-8 strings. Therefore, instead of trapping, this commit silently corrects the issue, transcoding the offsets into the correct encoding.
It would probably be a good idea to also emit a runtime warning in addition to recovering from the error. This would generate some noise that would gently nudge folks to fix their code.
rdar://89369680
Commit the platform definition and build script work necessary to
cross-compile for arm64_32.
arm64_32 is a variant of AARCH64 that supports an ILP32 architecture.
Add a missing fix_lifetime. This miscompiles with OSSA because
`object` is destroyed before `bridgeObject` is retained.
Reinterpreting a reference to a trivial type always requires a
fix_lifetime.
One additional tweak (setting the scalar-aligned bit on foreign indices) had to be made to avoid a performance regression for long non-ASCII foreign strings.
Old Swift and new Swift runtimes and overlays need to coexist in the same process. This means there must not be any classes which have the same ObjC runtime name in old and new, because the ObjC runtime doesn't like name collisions.
When possible without breaking source compatibility, classes were renamed in Swift, which results in a different ObjC name.
Public classes were renamed only on the ObjC side using the @_objcRuntimeName attribute.
This is similar to the work done in pull request #19295. That only renamed @objc classes. This renames all of the others, since even pure Swift classes still get an ObjC name.
rdar://problem/46646438
This commit supersedes 2866b4a which was overwritten by 4ab45df.
Store small string code units in little-endian byte order. This way
the code units are in the same order on all machines and can be
safely treated as an array of bytes.
In anticipation of potential future HW features, e.g. armv8.5 memory
tagging, only use the high 4 bytes as discriminator bits in
_BridgeObject rather than the top 8 bits. Utilize two perf flags to
cover this instead. This requires shifting around a fair amount of
internal complexity.
Remove Discriminator, Flags, etc., abstractions from
StringObject. These cause code divergence between 32-bit and 64-bit
ABI, complicate ABI changes, and otherwise contribute to bloat.
We now have plenty of extra inhabitants in the variant enum, so we can get rid of the 7-bit hack.
It’d also be possible now to increase small string capacity to a spacious 11 bytes; however this needs a full overhaul of the 32-bit representation, so it needs a little bit more time in the oven.
Less inlining for hashing and comparison. Saves code size on very
frequent String comparison in exchange for costing us in some of our
ridiculuous micro-benchmarks.
Also adds in more _effects for better codegen