[llvm] e130eef - OpaquePtr: print byval types containing anonymous types correctly.
Tim Northover via llvm-commits
llvm-commits at lists.llvm.org
Tue Jan 7 07:11:51 PST 2020
Author: Tim Northover
Date: 2020-01-07T15:11:43Z
New Revision: e130eef58814d12b0490033fbedcf75db8a4f148
URL: https://github.com/llvm/llvm-project/commit/e130eef58814d12b0490033fbedcf75db8a4f148
DIFF: https://github.com/llvm/llvm-project/commit/e130eef58814d12b0490033fbedcf75db8a4f148.diff
LOG: OpaquePtr: print byval types containing anonymous types correctly.
Attribute::getAsString doesn't have enough information to print anonymous
Module-level types correctly, so they come back as "%type 0xabcd". This results
in broken IR when printing as text.
Instead, print type-attributes (currently just byval) using the TypePrinting
infrastructure available in AsmWriter. This only applies to function argument
attributes.
Added:
Modified:
llvm/lib/IR/AsmWriter.cpp
llvm/test/Assembler/byval-type-attr.ll
Removed:
################################################################################
diff --git a/llvm/lib/IR/AsmWriter.cpp b/llvm/lib/IR/AsmWriter.cpp
index cda5fd0a3812..acf0e4afef27 100644
--- a/llvm/lib/IR/AsmWriter.cpp
+++ b/llvm/lib/IR/AsmWriter.cpp
@@ -2399,6 +2399,8 @@ class AssemblyWriter {
void writeAllMDNodes();
void writeMDNode(unsigned Slot, const MDNode *Node);
+ void writeAttribute(const Attribute &Attr, bool InAttrGroup = false);
+ void writeAttributeSet(const AttributeSet &AttrSet, bool InAttrGroup = false);
void writeAllAttributeGroups();
void printTypeIdentities();
@@ -2531,8 +2533,10 @@ void AssemblyWriter::writeParamOperand(const Value *Operand,
// Print the type
TypePrinter.print(Operand->getType(), Out);
// Print parameter attributes list
- if (Attrs.hasAttributes())
- Out << ' ' << Attrs.getAsString();
+ if (Attrs.hasAttributes()) {
+ Out << ' ';
+ writeAttributeSet(Attrs);
+ }
Out << ' ';
// Print the operand
WriteAsOperandInternal(Out, Operand, &TypePrinter, &Machine, TheModule);
@@ -3462,8 +3466,10 @@ void AssemblyWriter::printFunction(const Function *F) {
TypePrinter.print(FT->getParamType(I), Out);
AttributeSet ArgAttrs = Attrs.getParamAttributes(I);
- if (ArgAttrs.hasAttributes())
- Out << ' ' << ArgAttrs.getAsString();
+ if (ArgAttrs.hasAttributes()) {
+ Out << ' ';
+ writeAttributeSet(ArgAttrs);
+ }
}
} else {
// The arguments are meaningful here, print them in detail.
@@ -3549,8 +3555,10 @@ void AssemblyWriter::printArgument(const Argument *Arg, AttributeSet Attrs) {
TypePrinter.print(Arg->getType(), Out);
// Output parameter attributes list
- if (Attrs.hasAttributes())
- Out << ' ' << Attrs.getAsString();
+ if (Attrs.hasAttributes()) {
+ Out << ' ';
+ writeAttributeSet(Attrs);
+ }
// Output name, if available...
if (Arg->hasName()) {
@@ -4126,6 +4134,33 @@ void AssemblyWriter::printMDNodeBody(const MDNode *Node) {
WriteMDNodeBodyInternal(Out, Node, &TypePrinter, &Machine, TheModule);
}
+void AssemblyWriter::writeAttribute(const Attribute &Attr, bool InAttrGroup) {
+ if (!Attr.isTypeAttribute()) {
+ Out << Attr.getAsString(InAttrGroup);
+ return;
+ }
+
+ assert(Attr.hasAttribute(Attribute::ByVal) && "unexpected type attr");
+
+ Out << "byval";
+ if (Type *Ty = Attr.getValueAsType()) {
+ Out << '(';
+ TypePrinter.print(Ty, Out);
+ Out << ')';
+ }
+}
+
+void AssemblyWriter::writeAttributeSet(const AttributeSet &AttrSet,
+ bool InAttrGroup) {
+ bool FirstAttr = true;
+ for (const auto &Attr : AttrSet) {
+ if (!FirstAttr)
+ Out << ' ';
+ writeAttribute(Attr, InAttrGroup);
+ FirstAttr = false;
+ }
+}
+
void AssemblyWriter::writeAllAttributeGroups() {
std::vector<std::pair<AttributeSet, unsigned>> asVec;
asVec.resize(Machine.as_size());
diff --git a/llvm/test/Assembler/byval-type-attr.ll b/llvm/test/Assembler/byval-type-attr.ll
index c868885d2cc5..dd195a39651c 100644
--- a/llvm/test/Assembler/byval-type-attr.ll
+++ b/llvm/test/Assembler/byval-type-attr.ll
@@ -29,3 +29,15 @@ fail:
declare void @baz(%named_type* byval(%named_type))
declare i32 @__gxx_personality_v0(...)
+
+%0 = type opaque
+
+; CHECK: define void @anon({ %0* }* byval({ %0* }) %arg)
+; CHECK: call void @anon_callee({ %0* }* byval({ %0* }) %arg)
+define void @anon({ %0* }* byval({ %0* }) %arg) {
+ call void @anon_callee({ %0* }* byval({ %0* }) %arg)
+ ret void
+}
+
+; CHECK: declare void @anon_callee({ %0* }* byval({ %0* }))
+declare void @anon_callee({ %0* }* byval({ %0* }))
More information about the llvm-commits
mailing list