Commit Graph
22 Commits
Author SHA1 Message Date
Nicholas Bishop 5e62791ad2 Improve ClangDeclStore ergonomics (#7311)
Change `Lookup` by InstId to return a ClangDecl pointer. All callers
were immediately calling `Get` anyway, so this makes call sites a little
shorter. The other `Lookup` method, by ClangDeclKey, is sometimes called
without calling `Get`, so left that as-is, but renamed to `LookupId`.

Also add a `decl` method to ClangDecl so that the commonly repeated
`clang_decl->key.decl` can be written `clang_decl->decl()`.
2026-06-05 20:49:34 +00:00
Nicholas Bishop 44b17ff436 Set correct C++ access type for fields and static vars (#7312) 2026-06-05 20:07:27 +00:00
Nicholas BishopandRichard Smith 1aa34d7642 Remove CppGlobalVarStore (#7309)
Replace all uses of CppGlobalVarStore store with ClangDeclStore.

Adding a VarStorage->VarDecl mapping to ClangDeclStore is now done with
the `AddVar` method, which takes an extra `pattern_id` arg. While the
corresponding `ClangDecl` is unchanged from before, the reverse mapping
in `inst_id_to_clang_decl_id_` now uses the `pattern_id` as the key.
This is necessary because in some places the original VarStorage
instructions gets replaced (e.g. by a call to `Convert`). The
`pattern_id` remains stable in those cases.

---------

Co-authored-by: Richard Smith <richard@metafoo.co.uk>
2026-06-05 02:07:46 +00:00
Nicholas Bishop f2d0c4d0ae Export Carbon global variables and static vars to C++ (#7298)
Add `ExportVarToCpp`. This checks the `clang_decls` mapping and returns
an existing decl if found. Otherwise, it creates a new `VarDecl` and
adds it to the `clang_decls` mapping.

When lowering, in `FileContext::BuildGlobalVariableDecl`, the
`clang_decls` mapping is used to lookup an existing
`llvm::GlobalVariable` for the instruction. If found, use that rather
than creating a new one to avoid an unwanted second definition in the
llvm IR.
2026-06-03 20:47:54 +00:00
Richard Smith 2952f61095 Support for mapping array types to/from C++. (#7285)
For now, disable the use of array types as by-var paramters and by-init
return types when exporting Carbon functions to C++, as C++ does not
support raw arrays being passed or returned by value.

Assisted-by: Gemini via Antigravity
2026-06-01 21:55:16 +00:00
Richard Smith be70c092fa Add a text mode for fingerprinting. (#7231)
The intent is to add visibility into how the fingerprint is computed, so
that fingerprinting issues and mangling collisions can be more readily
understood and fixed.

Assisted-by: Gemini via Antigravity
2026-05-19 23:16:51 +00:00
David Blaikie 31db4a0931 Export virtual/abstract/override functions as virtual (#7211)
This provides enough to Clang so it can include these new virtual
functions in the vtable of Carbon types derived from C++ types.
2026-05-18 19:04:33 +00:00
Richard Smith 917856aff7 Export Carbon classes as base / final / abstract. (#7191)
* For Carbon `base class C`, export as a regular C++ class.
* For Carbon `class C`, export with the C++ `final` keyword attribute.
* For Carbon `abstract C`, mark the destructor as pure virtual in cases
where no member function is abstract, or emit an error if the destructor
is not virtual.

To support the final point, mark the destructor of an exported class as
virtual if it overrides a virtual destructor from the base class.

In passing, fix a crash exporting fields if the class has an invalid
base type.
2026-05-13 17:48:55 +00:00
David Blaikie 0f5de499d6 Roundtrip (export/reimport) class declarations (#7182)
Roundtrip (export/reimport) class declarations

The remapping was previously implemented using name_scopes, which aren't
created for class declarations, only definitions - causing the reimport
to import a fresh copy of the type that mismatched with the original (as
seen in the test baseline).

By changing the mapping to use the reverse part of the clang_decls
mapping this should generalize better (& we probably should further
migrate to that mapping). Though it did trip over some issue with
exactly which instruction is used as the key in the clang_decls map -
this change moves towards standardizing on the first decl id of the
class as its map key.
2026-05-11 16:35:47 +00:00
Nicholas Bishop 1bc329af14 Support calling Carbon destructors from C++ (#7143)
A destructor is added to the C++ class definition in
`CarbonExternalASTSource::CompleteType`. The destructor calls a Carbon
function that calls the `Destroy` operator.
2026-05-04 20:28:58 +00:00
Nicholas Bishop 2445ad9703 Prevent ref self methods from being called from C++ with an rvalue (#7130)
If the Carbon method takes a `ref self`, give the C++ thunk an lvalue
ref-qualifier.
2026-04-30 00:50:28 +00:00
Nicholas Bishop f3f039516e Support accessing Carbon class fields from C++ (#7119)
When any field of a Carbon class is access from C++ for the first time,
all fields are exported as `clang::FieldDecl`s (this is necessary
because clang fields have an internal index that is initialized on first
use).

`ClangDeclStore` now provides bidirectional mapping. This allows looking
up a `ClangDeclId` by `InstId`, so when Carbon class fields are exported
they can be looked up that way.
2026-04-29 20:07:10 +00:00
Richard Smith 0124aae041 Import non-const rvalue references as var parameters. (#7125)
When importing a C++ function with an rvalue reference parameter, we
previously produced a Carbon value parameter. This would lead to the
toolchain believing it could pass the address of a non-expiring object
to the function, which would lead to a use-after-move.

Instead, we now map non-const rvalue reference parameters to Carbon
`var` parameters. This forces the object passed into C++ to be unique
and owned by the call. While that's not an exact match for C++ rvalue
reference parameters, given that it provides "always move" not
"conditionally move", it's the closest match we have at the moment.
2026-04-29 00:28:00 +00:00
Nicholas Bishop 3f63cf4b10 Support C++ calling Carbon functions with ref parameters (#7107)
When creating the C++ thunk, make the parameters references if the
corresponding callee parameters are `ref`s.

When creating the Carbon thunk, tag the call arguments as `ref` if the
corresponding callee parameters are `ref`s.
2026-04-23 23:45:26 +00:00
Nicholas Bishop 67648b4d49 Remove "__cpp_thunk" from thunk name for exported functions (#7092)
This makes the behavior consistent between methods and regular
functions, and fixes the behavior with `using` aliases (see new
`using.carbon` test).

As requested in
https://github.com/carbon-language/carbon-lang/pull/7078#discussion_r3121104954.
2026-04-22 18:05:02 +00:00
Nicholas Bishop 33d534ab31 Support calling Carbon methods from C++ (#7078)
The FunctionDecl created for calling the Carbon thunk now takes a `self`
parameter for non-static methods, and the C++ thunk now passes an extra
argument for that `self` parameter when needed.

The CXXMethodDecl thunk created for calling methods now sets the storage
class appropriate depending on whether the method is static or not.

To reduce the number of parameters being passed around to thunk-building
functions, added a `FunctionInfo` struct and pass that around instead.
2026-04-22 15:09:33 +00:00
Richard Smith 46f46a538d Preliminary reverse interop support for base classes. (#7059)
Create a Clang AST representation of the base specifier.
2026-04-16 00:29:40 +00:00
Nicholas Bishop 114cf401c2 Support C++ calling Carbon functions with non-() return type (#7051)
For calling non-`()` functions, the Carbon->Carbon thunk now takes an
extra reference parameter and writes the target function's return value
out to that parameter. (At the SemIR level this is how returns already
work, but adding this extra reference parameter is needed so that the
function is lowered correctly.) The C++ thunk now creates a local
variable to be initialized by the Carbon thunk, and then returns that
value to the original C++ caller.
2026-04-16 00:29:38 +00:00
Richard Smith 43867a678b Reverse interop support for type aliases. (#7043)
Allow any type that has a mapping from Carbon to C++ to be exposed to
C++ via name lookup. This also exposes the logic to export Carbon
classes to C++ to apply during type mapping, which gives very slight
support for passing Carbon types to C++ functions from Carbon, but not
really enough to sensibly test yet.

Depends on #7042.
2026-04-14 00:18:33 +00:00
Richard Smith f31e1685fd Only export each class or namespace to C++ once. (#7042)
Instead of exporting a class or namespace each time a new C++ name
lookup discovers it, track that we have exported the entity on its name
scope, and if a new name lookup finds the same entity, produce the same
clang declaration.
2026-04-13 19:43:44 +00:00
Richard Smith b74e0d1260 Superficial support for exporting complete class types to C++. (#7029)
We don't yet populate the bases or fields, so the class types show up as
empty classes in C++ for now. But we do allow calls to static member
functions.
2026-04-08 19:29:25 +00:00
Nicholas Bishop 0635f4628f Add support for C++ calling Carbon functions with parameters (#7024)
This works by generating two thunks, one in C++ and one in Carbon. For
example, given this input:
```c++
// Carbon:
fn Callme(f: f32) {}

// C++:
void F() {
  // This will call `Callme__cpp_thunk`
  Carbon::Callme(1.0);
}
```

These functions are generated:
```c++
// Carbon:
fn Callme__carbon_thunk(ref f: f32) {
  // Call the target function.
  Callme(f);
}

// C++:

// C++ declaration for the Carbon thunk.
void Callme__carbon_thunk(float& f);

void Callme__cpp_thunk(float f) {
  // Call the Carbon thunk with args passed by reference.
  Callme__carbon_thunk(f);
}
```

For now, all arguments are passed by reference, even if they are simple
types like pointers or i32.

Functions with non-void return types are not supported yet.
2026-04-07 23:25:57 +00:00