[clang] [APINotes] Parse function-like Where.Parameters (PR #203227)
via cfe-commits
cfe-commits at lists.llvm.org
Thu Jun 11 04:51:07 PDT 2026
https://github.com/StoeckOverflow updated https://github.com/llvm/llvm-project/pull/203227
>From b154eed5122c80ac434df7d23c86b5bc7590843a Mon Sep 17 00:00:00 2001
From: stoeckoverflow <dominic-st at gmx.de>
Date: Thu, 11 Jun 2026 10:32:28 +0200
Subject: [PATCH] [clang][APINotes] Parse function-like Where.Parameters
---
clang/lib/APINotes/APINotesYAMLCompiler.cpp | 26 +++++++++
.../WhereParametersMapElement.apinotes | 8 +++
...hereParametersMethodWhereSequence.apinotes | 9 +++
.../WhereParametersMissingName.apinotes | 7 +++
.../Headers/WhereParametersParser.apinotes | 50 +++++++++++++++++
.../Headers/WhereParametersScalar.apinotes | 7 +++
.../WhereParametersUnknownWhereKey.apinotes | 7 +++
.../WhereParametersWhereSequence.apinotes | 8 +++
.../test/APINotes/where-parameters-yaml.test | 56 +++++++++++++++++++
9 files changed, 178 insertions(+)
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersMapElement.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersMethodWhereSequence.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersMissingName.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersParser.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersScalar.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersUnknownWhereKey.apinotes
create mode 100644 clang/test/APINotes/Inputs/Headers/WhereParametersWhereSequence.apinotes
create mode 100644 clang/test/APINotes/where-parameters-yaml.test
diff --git a/clang/lib/APINotes/APINotesYAMLCompiler.cpp b/clang/lib/APINotes/APINotesYAMLCompiler.cpp
index 390dd428d55e3..0ff1367e7de28 100644
--- a/clang/lib/APINotes/APINotesYAMLCompiler.cpp
+++ b/clang/lib/APINotes/APINotesYAMLCompiler.cpp
@@ -338,8 +338,15 @@ template <> struct MappingTraits<Class> {
} // namespace llvm
namespace {
+typedef std::vector<StringRef> WhereParamsSeq;
+
+struct FunctionWhere {
+ std::optional<WhereParamsSeq> Parameters;
+};
+
struct Function {
StringRef Name;
+ std::optional<FunctionWhere> Where;
ParamsSeq Params;
NullabilitySeq Nullability;
std::optional<NullabilityKind> NullabilityOfRet;
@@ -361,9 +368,16 @@ LLVM_YAML_IS_SEQUENCE_VECTOR(Function)
namespace llvm {
namespace yaml {
+template <> struct MappingTraits<FunctionWhere> {
+ static void mapping(IO &IO, FunctionWhere &W) {
+ IO.mapOptional("Parameters", W.Parameters);
+ }
+};
+
template <> struct MappingTraits<Function> {
static void mapping(IO &IO, Function &F) {
IO.mapRequired("Name", F.Name);
+ IO.mapOptional("Where", F.Where);
IO.mapOptional("Parameters", F.Params);
IO.mapOptional("Nullability", F.Nullability);
IO.mapOptional("NullabilityOfRet", F.NullabilityOfRet, std::nullopt);
@@ -1137,6 +1151,12 @@ class YAMLConverter {
}
for (const auto &CXXMethod : T.Methods) {
+ if (CXXMethod.Where && CXXMethod.Where->Parameters) {
+ emitError(
+ "'Where.Parameters' is not supported by binary API notes yet");
+ continue;
+ }
+
CXXMethodInfo MI;
convertFunction(CXXMethod, MI);
Writer.addCXXMethod(TagCtxID, CXXMethod.Name, MI, SwiftVersion);
@@ -1210,6 +1230,12 @@ class YAMLConverter {
// Write all global functions.
llvm::StringSet<> KnownFunctions;
for (const auto &Function : TLItems.Functions) {
+ if (Function.Where && Function.Where->Parameters) {
+ emitError(
+ "'Where.Parameters' is not supported by binary API notes yet");
+ continue;
+ }
+
// Check for duplicate global functions.
if (!KnownFunctions.insert(Function.Name).second) {
emitError(llvm::Twine("multiple definitions of global function '") +
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersMapElement.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersMapElement.apinotes
new file mode 100644
index 0000000000000..13d5d0e73378d
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersMapElement.apinotes
@@ -0,0 +1,8 @@
+---
+Name: WhereParametersMapElement
+Functions:
+- Name: makeWidget
+ Where:
+ Parameters:
+ - Type: int
+ SwiftName: makeWidget(_:)
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersMethodWhereSequence.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersMethodWhereSequence.apinotes
new file mode 100644
index 0000000000000..f55d7c1577b53
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersMethodWhereSequence.apinotes
@@ -0,0 +1,9 @@
+---
+Name: WhereParametersMethodWhereSequence
+Tags:
+- Name: Widget
+ Methods:
+ - Name: setValue
+ Where:
+ - Parameters:
+ - int
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersMissingName.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersMissingName.apinotes
new file mode 100644
index 0000000000000..dd2ee3ed7fa03
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersMissingName.apinotes
@@ -0,0 +1,7 @@
+---
+Name: WhereParametersMissingName
+Functions:
+- Where:
+ Parameters:
+ - int
+ SwiftName: makeWidget(_:)
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersParser.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersParser.apinotes
new file mode 100644
index 0000000000000..90dfb555259a3
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersParser.apinotes
@@ -0,0 +1,50 @@
+---
+Name: WhereParametersParser
+Functions:
+- Name: makeWidget
+ Where:
+ Parameters:
+ - int
+ SwiftName: makeWidget(_:)
+- Name: makeWidget
+ Where:
+ Parameters:
+ - double
+ - const char *
+ SwiftName: makeWidget(_:_:)
+- Name: currentWidget
+ Where:
+ Parameters: []
+ SwiftName: currentWidget()
+- Name: makeWidget
+ SwiftName: makeWidget(_:)
+- Name: legacyFunction
+ Parameters:
+ - Position: 0
+ Type: int
+ SwiftName: legacyFunction(_:)
+Tags:
+- Name: Widget
+ Methods:
+ - Name: setValue
+ Where:
+ Parameters:
+ - int
+ SwiftName: setIntValue(_:)
+ - Name: setValue
+ Where:
+ Parameters:
+ - double
+ - const char *
+ SwiftName: setValue(_:_:)
+ - Name: reset
+ Where:
+ Parameters: []
+ SwiftName: reset()
+ - Name: setValue
+ SwiftName: setValue(_:)
+ - Name: legacy
+ Parameters:
+ - Position: 0
+ Type: int
+ SwiftName: legacy(_:)
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersScalar.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersScalar.apinotes
new file mode 100644
index 0000000000000..e116af3ed28be
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersScalar.apinotes
@@ -0,0 +1,7 @@
+---
+Name: WhereParametersScalar
+Functions:
+- Name: makeWidget
+ Where:
+ Parameters: int
+ SwiftName: makeWidget(_:)
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersUnknownWhereKey.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersUnknownWhereKey.apinotes
new file mode 100644
index 0000000000000..55d676400c23c
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersUnknownWhereKey.apinotes
@@ -0,0 +1,7 @@
+---
+Name: WhereParametersUnknownWhereKey
+Functions:
+- Name: makeWidget
+ Where:
+ ResultType: int
+ SwiftName: makeWidget(_:)
diff --git a/clang/test/APINotes/Inputs/Headers/WhereParametersWhereSequence.apinotes b/clang/test/APINotes/Inputs/Headers/WhereParametersWhereSequence.apinotes
new file mode 100644
index 0000000000000..3ba8a5295e29b
--- /dev/null
+++ b/clang/test/APINotes/Inputs/Headers/WhereParametersWhereSequence.apinotes
@@ -0,0 +1,8 @@
+---
+Name: WhereParametersWhereSequence
+Functions:
+- Name: makeWidget
+ Where:
+ - Parameters:
+ - int
+ SwiftName: makeWidget(_:)
diff --git a/clang/test/APINotes/where-parameters-yaml.test b/clang/test/APINotes/where-parameters-yaml.test
new file mode 100644
index 0000000000000..0c657ac0e15ea
--- /dev/null
+++ b/clang/test/APINotes/where-parameters-yaml.test
@@ -0,0 +1,56 @@
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersParser.apinotes | FileCheck %s
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersMissingName.apinotes 2>&1 | FileCheck %s --check-prefix=MISSING-NAME
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersWhereSequence.apinotes 2>&1 | FileCheck %s --check-prefix=WHERE-SEQUENCE
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersScalar.apinotes 2>&1 | FileCheck %s --check-prefix=PARAMETERS-SCALAR
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersMapElement.apinotes 2>&1 | FileCheck %s --check-prefix=PARAMETERS-MAP-ELEMENT
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersUnknownWhereKey.apinotes 2>&1 | FileCheck %s --check-prefix=UNKNOWN-WHERE-KEY
+RUN: apinotes-test %S/Inputs/Headers/WhereParametersMethodWhereSequence.apinotes 2>&1 | FileCheck %s --check-prefix=METHOD-WHERE-SEQUENCE
+
+CHECK: Name: WhereParametersParser
+CHECK: Functions:
+CHECK: - Name: makeWidget
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - int
+CHECK: - Name: makeWidget
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - double
+CHECK-NEXT: - 'const char *'
+CHECK: - Name: currentWidget
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters: []
+CHECK: - Name: makeWidget
+CHECK-NEXT: SwiftName: 'makeWidget(_:)'
+CHECK: - Name: legacyFunction
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - Position: 0
+CHECK-NEXT: Type: int
+CHECK: Tags:
+CHECK: - Name: Widget
+CHECK: Methods:
+CHECK: - Name: setValue
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - int
+CHECK: - Name: setValue
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - double
+CHECK-NEXT: - 'const char *'
+CHECK: - Name: reset
+CHECK-NEXT: Where:
+CHECK-NEXT: Parameters: []
+CHECK: - Name: setValue
+CHECK-NEXT: SwiftName: 'setValue(_:)'
+CHECK: - Name: legacy
+CHECK-NEXT: Parameters:
+CHECK-NEXT: - Position: 0
+CHECK-NEXT: Type: int
+
+MISSING-NAME: missing required key 'Name'
+WHERE-SEQUENCE: not a mapping
+PARAMETERS-SCALAR: not a sequence
+PARAMETERS-MAP-ELEMENT: unexpected scalar
+UNKNOWN-WHERE-KEY: unknown key 'ResultType'
+METHOD-WHERE-SEQUENCE: not a mapping
More information about the cfe-commits
mailing list