Commit Graph

165 Commits

Author SHA1 Message Date
Doug Gregor b393f0bfa8 [Embedded] Eliminate special-case handling of declarations used externally
Declarations that are potentially used externally, including those
exposed to foreign languages (e.g., via `@c`), placed in a specific
section (`@section`), or explicitly marked used (`@used`) are
generally eagerly emitted in IR. Embedded Swift was overriding this in
a partial manner, applying specific linkage rules to them to force
them to have unique definitions (regardless of the code generation
model) and then overriding the behavior later on when it came to lazy
emission.

Remove the special cases for Embedded. These declarations will now
follow the same linkage rules as all other declarations, greatly
simplifying the "is non-unique definition" check, and will be
considered as being emitted non-lazily.
2026-05-20 08:35:18 -07:00
Doug Gregor 14bc0baecf Introduce the notion of an "effective" code generation model
The code generation model for a particular declaration or conformance
can be defined explicitly with `@export(interface)`,
`@export(implementation)`, or `@inlinable` (for declarations),
indicating where the definition will occur.

Embedded Swift also has some limitations on what can be emitted into
IR. For example, a generic function cannot be `@export(interface)`
because Embedded Swift does not support unspecialized generics.

Compute the effective code generation model based on what was
explicitly specified, the limitations of the model, and the default
code generation model for the given module, which defaults to
"inlinable" but can be made "implementation" by the DeferredCodeGen
feature. Use the effective code generation model for IR- and SIL-level
determinations of linkage and where to emit symbols.
[WIP] Start computing and using the "effective" code generation model

FIXUP linkage of the alias symbol
2026-05-20 08:35:11 -07:00
Pavel Yaskevich a0f47099b9 [Concurrency] SILDeclRef: Fix isolation computation for local accessors
Local computed variable accessors should get their isolation from the
context unless otherwise specified. This is a narrow fix to address
some "uknown pattern" failures in region-based isolation. A proper
fix would be to set the isolation correctly during type-checking but
that is a major change due to how closures are currently type-checked.

Resolves: rdar://175548302
2026-05-08 08:27:55 -07:00
Doug Gregor 8713c13bef Centralize computation of the "code generation model" for object code & SIL
For a given function, we might end up emitting it's definition as
object code, serialized SIL, or both. The @export, @inlinable, and
@inline(always) attributes provide control of this behavior at the
declaration level.

Centralize the query function that will look for each of these
attributes and map down to a specific "code generation model", whose 3
options follow the naming from SE-0497: interface, inlinable, and
implementation. Use this one computation to back the queries for
"always emit into client", "never emit into client", and "inlinable"
so we can't get inconsistent results from places that are doing
one-off checks for these attributes.
2026-04-15 13:03:55 -07:00
Michael Gottesman 591a11026d [sil] Use VarDecl's initializer isolation for stored property initializer SILFunctions.
Previously (0a60c93ca5), we fixed an issue where variable initializer
expressions would inherit isolation from their containing type rather than from
their property declaration. For example, in:

    @MainActor struct S {
      @CustomActor var x = NS()
      nonisolated init() {}
    }

the variable initializer SILFunction for `x` would be @MainActor isolated
instead of @CustomActor isolated, causing spurious RBI errors.

That fix made the variable initializer SILFunction adopt the VarDecl's own
actor isolation when explicitly specified. However, this broke cases involving
library evolution with default argument generators:

    @MainActor struct DefaultArgumentInitializerTest<T> {
      var strategy: NonSendableEnum = .case1
    }

Here the default argument generator is nonisolated (matching the initializer),
but it calls the variable initializer expression which was now @MainActor
isolated — producing a legitimate merge error in RBI.

Fix this by using `VarDecl::getInitializerIsolation()` instead of the VarDecl's
own actor isolation. This ensures both the variable initializer expression
SILFunction and any default argument generator match the initializer's isolation.
This is correct because:

1. If the initializer expression is nonisolated from an effects perspective, it
   returns a disconnected value that can be stored into actor-isolated storage.

2. If the initializer expression is actor-isolated, the storage must match that
   isolation, and only matching-isolation initializers can invoke it.

rdar://173530121
2026-03-28 14:28:01 -07:00
Michael Gottesman 0a60c93ca5 [SILGen] Respect stored property's explicit global actor isolation in its initializer
Previously, when generating SIL for a stored property initializer, we would
use the enclosing context's isolation rather than the property's own explicit
isolation. For example:

    @MainActor
    struct S {
      @CustomActor var x = NS()  // initializer was incorrectly MainActor-isolated
    }

Now the initializer correctly uses the property's explicit @CustomActor isolation
instead of inheriting @MainActor from the struct.

This is implemented by checking for an explicit global actor isolation on the
VarDecl in SILDeclRef::getActorIsolation() before falling back to
getActorIsolationOfContext().
2026-02-17 12:34:16 -08:00
Meghana Gupta 04db3ba069 Update SerializationKind for borrowing accessors
Borrow accessors are synthesized with "direct" access semantics and cannot be serialized
when the storage is resilient.
2026-01-20 11:44:14 -08:00
Doug Gregor b21485dd1f Only foreign thunks need to be serialized, not foreign definitions
This eliminates a SIL verification error with `@c` functions, which
provide definitions for foreign entrypoints. We were serializing @c
definitions when we shouldn't be, which would cause problems down the
line if those @c definitions referenced something internal that they
shouldn't.
2025-11-13 18:39:08 -08:00
Doug Gregor 020b69d4b6 [SE-0497] Implement @export attribute syntax
Implement the @export(implementation) and @export(interface) attributes
to replace @_alwaysEmitIntoClient and @_neverEmitIntoClient. Provide a
warning + Fix-It to start staging out the very-new
@_neverEmitIntoClient. We'll hold off on pushing folks toward
@_alwaysEmitIntoClient for a little longer.
2025-11-07 22:00:40 -08:00
Doug Gregor f267f62f65 [SILGen] Consistently use SIL asmname for foreign function/variable references
Whenever we have a reference to a foreign function/variable in SIL, use
a mangled name at the SIL level with the C name in the asmname
attribute. The expands the use of asmname to three kinds of cases that
it hadn't been used in yet:

* Declarations imported from C headers/modules
* @_cdecl @implementation of C headers/modules
* @_cdecl functions in general

Some code within the SIL pipeline makes assumptions that the C names of
various runtime functions are reflected at the SIL level. For example,
the linking of Embedded Swift runtime functions is done by-name, and
some of those names refer to C functions (like `swift_retain`) and
others refer to Swift functions that use `@_silgen_name` (like
`swift_getDefaultExecutor`). Extend the serialized module format to
include a table that maps from the asmname of functions/variables over
to their mangled names, so we can look up functions by asmname if we
want. These tables could also be used for checking for declarations
that conflict on their asmname in the future. Right now, we leave it
up to LLVM or the linker to do the checking.

`@_silgen_name` is not affected by these changes, nor should it be:
that hidden feature is specifically meant to affect the name at the
SIL level.

The vast majority of test changes are SIL tests where we had expected
to see the C/C++/Objective-C names in the tests for references to
foreign entities, and now we see Swift mangled names (ending in To).
The SIL declarations themselves will have a corresponding asmname.

Notably, the IRGen tests have *not* changed, because we generally the
same IR as before. It's only the modeling at the SIL lever that has
changed.

Another part of rdar://137014448.
2025-10-29 19:35:55 -07:00
Kuba (Brecka) Mracek eb23d3bc0a Merge pull request #85074 from kubamracek/section
SE-0492: Stabilize @_section/@_used into @section/@used
2025-10-24 12:29:48 -07:00
Kuba Mracek adeb40f261 SE-0492: Stabilize @_section/@_used into @section/@used
Removes the underscored prefixes from the @_section and @_used attributes, making them public as @section and @used respectively. The SymbolLinkageMarkers experimental feature has been removed as these attributes are now part of the standard language. Implemented expression syntactic checking rules per SE-0492.

Major parts:
- Renamed @_section to @section and @_used to @used
- Removed the SymbolLinkageMarkers experimental feature
- Added parsing support for the old underscored names with deprecation warnings
- Updated all tests and examples to use the new attribute names
- Added syntactic validation for @section to align with SE-0492 (reusing the legality checker by @artemcm)
- Changed @DebugDescription macro to explicitly use a tuple type instead of type inferring it, to comply with the expression syntax rules
- Added a testcase for the various allowed and disallowed syntactic forms, `test/ConstValues/SectionSyntactic.swift`.
2025-10-22 16:05:39 -07:00
Doug Gregor fad8b24dbb [SIL] Use mangled names + asmname for @c functions
Instead of using the C name for `@c` functions in SIL, retain mangled
names and apply the `asmname` attribute, so we retain more type
information until later in the pipeline and avoid collisions.

Another part of rdar://137014448.
2025-10-22 10:54:42 -07:00
Doug Gregor 4be74c714f [SE-0495, SILGen] Only emit C-compatible entrypoints for @c definitions.
When defining a C-compatible function with `@c`, we were emitting a
Swift function along with a C-compatible thunk. Stop doing that, and
instead only produce the C-compatible function. All uses of the
function will go through that C interface, just like if the function
were declared in C.

This also applies to `@c @implementation` functions, which are
declared in C but implemented in Swift. It does *not* apply to
`@_cdecl`, which will continue to produce both the Swift function and
C thunk to prevent an ABI break.

Fixes rdar://158888024.
2025-10-17 16:34:42 -07:00
Doug Gregor 3445b86ab8 [SILGen] Switch @_extern(c) over to a foreign entrypoint
Rather than treating `@_extern(c)` functions like a Swift function with
a C calling convention, treat them as foreign entrypoints, which
better matches how we handle imported C functions.
2025-10-16 19:06:08 -07:00
Doug Gregor 4b745170c3 [SILGen] Map the @_extern(c) C function name over to the asmname of a SIL function
`@_extern(c)` is meant for referencing C functions defined outside of
this Swift file. Instead of using the C function name as the SIL
function name, which is prone to collisions across different Swift
modules, place make the C function name the "asmname" of the
corresponding SIL function. Show that this prevents deserialization
errors when there are conflicting Swift-level types for the same
`@_extern(c)`-named symbol across modules.

Part of rdar://137014448.
Instead of using the C name as the mangled name of a SIL function
2025-10-15 23:19:12 -07:00
Doug Gregor cc519a09d0 [Embedded] Identify more places to emit symbols even with deferred code generation
Deferred code generation only produces symbols when they are needed.
Expand this out to cover more of the cases where we need them:
* @c/@_cdecl with and without @implementation
* @_expose(Cxx) and @_expose(Wasm)
* @_section and @_used
* (already present) the main entry point

Part of the Embedded Swift linkage model. Also fixes #74328 /
rdar://147207945 along the way.
2025-10-03 16:00:46 -07:00
Arnold Schwaighofer 25a071efc8 Add experimental feature @inline(always)
The intent for `@inline(always)` is to act as an optimization control.
The user can rely on inlining to happen or the compiler will emit an error
message.

Because function values can be dynamic (closures, protocol/class lookup)
this guarantee can only be upheld for direct function references.

In cases where the optimizer can resolve dynamic function values the
attribute shall be respected.

rdar://148608854
2025-09-30 08:36:26 -07:00
Meghana Gupta c764244df0 Merge pull request #84180 from meg-gupta/borrowandmutatepr
Add preliminary support for borrow accessors
2025-09-15 10:01:15 -07:00
Meghana Gupta f1c41960d8 [NFC] Add some utilities in SILDeclRef 2025-09-09 14:45:36 -07:00
John McCall 74496ea86d Fix SILGen's computation of default argument generator isolation 2025-09-09 14:26:57 -04:00
Doug Gregor ba2af97a91 Merge pull request #84095 from DougGregor/embedded-deferred-codegen 2025-09-04 06:05:39 -07:00
Doug Gregor ed93b46fa6 [Embedded] Introduce DeferredCodeGen feature.
Introduce an experimental feature DeferredCodeGen, that defers the
generation of LLVM IR (and therefore object code) for all entities
within an Embedded Swift module unless they have explicitly requested
to not be emitted into the client (e.g., with
`@_neverEmitIntoClient`).

This feature is meant to generalize and subsume
-emit-empty-object-file, relying on lazy emission of entities rather
than abruptly ending the compilation pipeline before emitting any IR.

Part of rdar://158363967.
2025-09-03 15:55:47 -07:00
Janat Baig 798c0f51a4 Merge branch 'main' into temp-branch 2025-08-23 11:11:04 -04:00
Doug Gregor 2f60d729f0 Add @_neverEmitIntoClient to prohibit SIL serialization for a function
Part of the Embedded Swift linkage model, this attribute ensures that
the function it applies to has a strong definition in its owning
module, and that its SIL is never serialized. That way, other modules
will not have access to its definition.

Implements rdar://158364184.
2025-08-17 23:21:57 -07:00
Doug Gregor 9a20ebac5b [Embedded] Emit weak definitions for imported symbols
When Embedded Swift emits a symbol that was imported from another
module, ensure that the symbol is emitted as a weak definition. This
way, importing the same module (and using its symbol) into several
different modules doesn't cause duplicate-symbol errors at link time.
Rather, the linker will merge the different symbol definitions. This
makes Embedded Swift libraries work without resorting to
`-mergeable-symbols` or `-emit-empty-object-file`.
2025-08-17 15:26:08 -07:00
JanBaig ff894c4d01 [Format] Apply clang-format to recent changes 2025-08-09 12:46:18 -04:00
JanBaig c84cc3491e [SIL] Emit CanSILFunctionType for the new SILDeclRef 2025-08-08 18:46:56 -04:00
JanBaig 988a3dcf25 [SIL] Introduce new SILDeclRef 2025-07-29 21:16:11 -04:00
Anthony Latsis fec049e5e4 Address llvm::PointerUnion::{is,get} deprecations
These were deprecated in
https://github.com/llvm/llvm-project/pull/122623.
2025-07-29 18:37:48 +01:00
Allan Shortlidge 7d866bfe69 AST: Skip serializing non-public accessors of @backDeployed properties.
Avoids a crash in SILGen when skipping non-inlinable function bodies.

Resolves rdar://136853454.
2025-07-27 21:25:44 -07:00
Alexis Laferrière dcc7e38ca7 SIL: Fix warning on unused variable 2025-07-01 14:10:46 -07:00
Alexis Laferrière 89f7ebfb18 Sema: @cdecl functions C name defaults to the Swift name 2025-06-11 12:42:38 -07:00
Becca Royal-Gordon aac6f64051 Make inlinability non-ABI for @abi
Inlinability doesn’t affect the mangling except in function specializations, which are applied after the fact and should never mangle in information from an ABI-only decl. That means we can simply ban these from `@abi` instead of inferring them.

Also adds some assertions to help double-check that SIL never tries to directly mangle or retrieve inlinability info from an ABI-only decl.
2025-04-18 14:50:01 -07:00
Nate Chandler 056fbc44c9 [CoroutineAccessors] Control ABI via flag. 2025-04-10 07:41:37 -07:00
Becca Royal-Gordon 5bb6245a5a [NFC] Check that SILGen doesn’t use ABI-only decls
Adds assertions in various places where properties that can vary between ABI-only decls and their counterparts—particularly function and parameter attributes—are handled in SILGen, ensuring that we don’t accidentally end up processing ABI-only decls there.
2025-03-26 10:47:13 -07:00
Nate Chandler 35d06c325d [CoroutineAccessors] Witness and vtable dispatch.
And thunking.
2025-03-07 11:46:50 -08:00
Anthony Latsis a84dfc8387 [Gardening] Fix some set but not used variables 2025-01-30 21:34:38 +00:00
Allan Shortlidge 95cc7319a1 SIL: Revert public linkage for @_silgen_name forward declarations.
It turns out that the stdlib build depends on `internal` functions with
`@_silgen_name` getting hidden linkage in some configurations. Instead of
messing with the linkage computation, just fix the `stdlib/Error.swift` test by
making `setWillThrowHandler` `public` to give it the right linkage.

Resolves rdar://141590619.
2024-12-17 08:35:01 -08:00
Allan Shortlidge 87d625ecdc SIL: Always give @_silgen_name forward declarations public linkage.
When `@_silgen_name` is applied to a function with no body, it is a forward
declaration. It therefore must be treated as an external (public) declaration
regardless of the access level it was given in source.

Resolves rdar://141436934.
2024-12-13 16:48:18 -08:00
Kuba Mracek 6f4ae28520 [ASTMangler] Pass ASTContext to all instantiations of ASTMangler 2024-12-02 15:01:04 -08:00
Allan Shortlidge a4057551ad SILGen: Avoid attempting to profile any ClangImporter synthesized function.
ClangImporter synthesized declarations inherently do not have user written
code. Unfortunately, despite that they are not always marked implicit as they
should be. This was causing a crash when attempting to generate profile
coverage maps for synthesized constructors for imported structs.

I tried marking the constructors implicit, but that had too many knock-on
effects in tests. This more targeted fix unblocks compatibility suite testing
without trying to grapple with the implications of that more fundamental fix.

Resolves rdar://139486938.
2024-11-11 16:28:02 -08:00
Akira Hatanaka f73c2e51bd Revert "[SILGen] Fix the type of closure thunks that are passed const reference structs (#76903)" (#77309)
This reverts commit 9c44b79189.

The commit caused swift's deserialization code to crash.

rdar://138726860
2024-10-31 15:16:00 -07:00
Akira Hatanaka 9c44b79189 [SILGen] Fix the type of closure thunks that are passed const reference structs (#76903)
The thunk's parameter needs the @in_guaranteed convention if it's a
const reference parameter. However, that convention wasn't being used
because clang importer was removing the const reference from the
type and SILGen was computing the type of the parameter based on the
type without const reference.

This commit fixes the bug by passing the clang function type to
SILDeclRef so that it can be used to compute the correct thunk type.

This fixes a crash when a closure is passed to a C function taking a
pointer to a function that has a const reference struct parameter.

This recommits e074426 with fixes to
serialization/deserialization of function types. The fixes prevent clang
types of functions from being dropped during serialization.

rdar://131321096
2024-10-08 23:44:49 -07:00
Konrad `ktoso` Malawski dea3b59331 Merge pull request #76250 from ktoso/wip-experimental-isolated-deinit 2024-10-03 17:19:10 +09:00
Konrad `ktoso` Malawski 45b97f146b Merge branch 'main' into wip-experimental-isolated-deinit 2024-09-30 13:47:39 +09:00
Slava Pestov 9632979879 Revert "[SILGen] Fix the type of closure thunks that are passed const referen…"
This reverts commit e074426058.
2024-09-29 22:32:04 -04:00
Akira Hatanaka e074426058 [SILGen] Fix the type of closure thunks that are passed const reference structs (#75491)
The thunk's parameter needs the @in_guaranteed convention if it's a
const reference parameter. However, that convention wasn't being used
because clang importer was removing the const reference from the
type and SILGen was computing the type of the parameter based on the
type without const reference.

This commit fixes the bug by passing the clang function type to
SILDeclRef so that it can be used to compute the correct thunk type.

This fixes a crash when a closure is passed to a C function taking a
pointer to a function that has a const reference struct parameter.

rdar://131321096
2024-09-27 07:04:47 -07:00
Kuba Mracek 4c33af9ea2 [embedded] Move default arg logic from postEmitFunction to SILDeclRef::isTransparent 2024-09-25 12:57:47 -07:00
Konrad `ktoso` Malawski 7d1ce789ad Revert "Revert "Isolated synchronous deinit"" 2024-09-17 17:35:38 +09:00