summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDan Gohman <dan433584@gmail.com>2018-02-09 23:13:22 +0000
committerDan Gohman <dan433584@gmail.com>2018-02-09 23:13:22 +0000
commitdb1916a64620b3261fed450cbde047c730d758b5 (patch)
treeea5c58b41aae499f81679568893c6062ec390f88
parent861bec2b7c69d885586725b9b0166913dbae6826 (diff)
downloadbcm5719-llvm-db1916a64620b3261fed450cbde047c730d758b5.tar.gz
bcm5719-llvm-db1916a64620b3261fed450cbde047c730d758b5.zip
[WebAssembly] Add mechanisms for specifying an explicit import module name.
This adds a wasm-import-module function attribute and a .import_module assembler directive, for specifying module import names for WebAssembly. Currently these may only be used for function symbols; global variables may be considered in the future. WebAssembly has a two-level namespace scheme for symbols, and it's normally the linker's job to assign the module name, which is the first-level name. The attributes here allow users to specify their own module names explicitly, which is useful for tools generating bindings to modules defined in other languages. This feature is not fully usable yet. It will evolve along with the ongoing symbol table and lld changes. Differential Revision: https://reviews.llvm.org/D42520 llvm-svn: 324778
-rw-r--r--llvm/include/llvm/MC/MCSymbolWasm.h1
-rw-r--r--llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.cpp15
-rw-r--r--llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.h6
-rw-r--r--llvm/lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp10
-rw-r--r--llvm/test/CodeGen/WebAssembly/import-module.ll19
-rw-r--r--llvm/test/MC/WebAssembly/external-func-address.ll9
6 files changed, 57 insertions, 3 deletions
diff --git a/llvm/include/llvm/MC/MCSymbolWasm.h b/llvm/include/llvm/MC/MCSymbolWasm.h
index dc8d26a8858..37c2848e617 100644
--- a/llvm/include/llvm/MC/MCSymbolWasm.h
+++ b/llvm/include/llvm/MC/MCSymbolWasm.h
@@ -54,6 +54,7 @@ public:
void setComdat(bool isComdat) { IsComdat = isComdat; }
const StringRef getModuleName() const { return ModuleName; }
+ void setModuleName(StringRef Name) { ModuleName = Name; }
const SmallVector<wasm::ValType, 1> &getReturns() const {
assert(ReturnsSet);
diff --git a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.cpp b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.cpp
index b1222283598..739044f6c40 100644
--- a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.cpp
+++ b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.cpp
@@ -107,6 +107,11 @@ void WebAssemblyTargetAsmStreamer::emitGlobalImport(StringRef name) {
OS << "\t.import_global\t" << name << '\n';
}
+void WebAssemblyTargetAsmStreamer::emitImportModule(MCSymbolWasm *Sym,
+ StringRef ModuleName) {
+ OS << "\t.import_module\t" << Sym->getName() << ", " << ModuleName << '\n';
+}
+
void WebAssemblyTargetAsmStreamer::emitIndIdx(const MCExpr *Value) {
OS << "\t.indidx \t" << *Value << '\n';
}
@@ -144,6 +149,11 @@ void WebAssemblyTargetELFStreamer::emitIndirectFunctionType(
void WebAssemblyTargetELFStreamer::emitGlobalImport(StringRef name) {
}
+void WebAssemblyTargetELFStreamer::emitImportModule(MCSymbolWasm *Sym,
+ StringRef ModuleName) {
+ llvm_unreachable(".import_module encoding not yet implemented");
+}
+
void WebAssemblyTargetWasmStreamer::emitParam(MCSymbol *Symbol,
ArrayRef<MVT> Types) {
SmallVector<wasm::ValType, 4> Params;
@@ -211,3 +221,8 @@ void WebAssemblyTargetWasmStreamer::emitIndirectFunctionType(
void WebAssemblyTargetWasmStreamer::emitGlobalImport(StringRef name) {
llvm_unreachable(".global_import is not needed for direct wasm output");
}
+
+void WebAssemblyTargetWasmStreamer::emitImportModule(MCSymbolWasm *Sym,
+ StringRef ModuleName) {
+ Sym->setModuleName(ModuleName);
+}
diff --git a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.h b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.h
index 539ca9ee8ce..a4ebf27cfa7 100644
--- a/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.h
+++ b/llvm/lib/Target/WebAssembly/MCTargetDesc/WebAssemblyTargetStreamer.h
@@ -24,6 +24,7 @@ namespace llvm {
class MCELFStreamer;
class MCWasmStreamer;
+class MCSymbolWasm;
/// WebAssembly-specific streamer interface, to implement support
/// WebAssembly-specific assembly directives.
@@ -47,6 +48,8 @@ public:
virtual void emitIndIdx(const MCExpr *Value) = 0;
/// .import_global
virtual void emitGlobalImport(StringRef name) = 0;
+ /// .import_module
+ virtual void emitImportModule(MCSymbolWasm *Sym, StringRef ModuleName) = 0;
protected:
void emitValueType(wasm::ValType Type);
@@ -68,6 +71,7 @@ public:
SmallVectorImpl<MVT> &Results) override;
void emitIndIdx(const MCExpr *Value) override;
void emitGlobalImport(StringRef name) override;
+ void emitImportModule(MCSymbolWasm *Sym, StringRef ModuleName) override;
};
/// This part is for ELF object output
@@ -84,6 +88,7 @@ public:
SmallVectorImpl<MVT> &Results) override;
void emitIndIdx(const MCExpr *Value) override;
void emitGlobalImport(StringRef name) override;
+ void emitImportModule(MCSymbolWasm *Sym, StringRef ModuleName) override;
};
/// This part is for Wasm object output
@@ -100,6 +105,7 @@ public:
SmallVectorImpl<MVT> &Results) override;
void emitIndIdx(const MCExpr *Value) override;
void emitGlobalImport(StringRef name) override;
+ void emitImportModule(MCSymbolWasm *Sym, StringRef ModuleName) override;
};
} // end namespace llvm
diff --git a/llvm/lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp b/llvm/lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp
index 204d97cbdd4..40eed593f07 100644
--- a/llvm/lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp
+++ b/llvm/lib/Target/WebAssembly/WebAssemblyAsmPrinter.cpp
@@ -84,8 +84,14 @@ void WebAssemblyAsmPrinter::EmitEndOfAsmFile(Module &M) {
SmallVector<MVT, 4> Results;
SmallVector<MVT, 4> Params;
ComputeSignatureVTs(F, TM, Params, Results);
- getTargetStreamer()->emitIndirectFunctionType(getSymbol(&F), Params,
- Results);
+ MCSymbolWasm *Sym = cast<MCSymbolWasm>(getSymbol(&F));
+ getTargetStreamer()->emitIndirectFunctionType(Sym, Params, Results);
+
+ if (F.hasFnAttribute("wasm-import-module")) {
+ StringRef Name = F.getFnAttribute("wasm-import-module")
+ .getValueAsString();
+ getTargetStreamer()->emitImportModule(Sym, Name);
+ }
}
}
for (const auto &G : M.globals()) {
diff --git a/llvm/test/CodeGen/WebAssembly/import-module.ll b/llvm/test/CodeGen/WebAssembly/import-module.ll
new file mode 100644
index 00000000000..e748b7ec1c7
--- /dev/null
+++ b/llvm/test/CodeGen/WebAssembly/import-module.ll
@@ -0,0 +1,19 @@
+; RUN: llc < %s -asm-verbose=false | FileCheck %s
+
+target datalayout = "e-m:e-p:32:32-i64:64-n32:64-S128"
+target triple = "wasm32-unknown-unknown-wasm"
+
+define void @test() {
+ call void @foo()
+ call void @plain()
+ ret void
+}
+
+declare void @foo() #0
+declare void @plain()
+
+attributes #0 = { "wasm-import-module"="bar" }
+
+; CHECK-NOT: .import_module plain
+; CHECK: .import_module foo, bar
+; CHECK-NOT: .import_module plain
diff --git a/llvm/test/MC/WebAssembly/external-func-address.ll b/llvm/test/MC/WebAssembly/external-func-address.ll
index 940f54cb077..05a335b848a 100644
--- a/llvm/test/MC/WebAssembly/external-func-address.ll
+++ b/llvm/test/MC/WebAssembly/external-func-address.ll
@@ -5,6 +5,11 @@ target triple = "wasm32-unknown-unknown-wasm"
; Verify that addresses of external functions generate correctly typed
; imports and relocations or type R_TABLE_INDEX_I32.
+declare void @f0(i32) #0
+@ptr_to_f0 = hidden global void (i32)* @f0, align 4
+
+attributes #0 = { "wasm-import-module"="somewhere" }
+
declare void @f1(i32) #1
@ptr_to_f1 = hidden global void (i32)* @f1, align 4
@@ -24,6 +29,8 @@ declare void @f1(i32) #1
; CHECK-NEXT: Field: __linear_memory
; CHECK: - Module: env
; CHECK-NEXT: Field: __indirect_function_table
+; CHECK: - Module: somewhere
+; CHECK-NEXT: Field: f0
; CHECK: - Module: env
; CHECK-NEXT: Field: f1
; CHECK-NEXT: Kind: FUNCTION
@@ -33,7 +40,7 @@ declare void @f1(i32) #1
; CHECK-NEXT: - Offset:
; CHECK-NEXT: Opcode: I32_CONST
; CHECK-NEXT: Value: 1
-; CHECK-NEXT: Functions: [ 0 ]
+; CHECK-NEXT: Functions: [ 0, 1 ]
; CHECK: - Type: DATA
; CHECK-NEXT: Relocations:
; CHECK-NEXT: - Type: R_WEBASSEMBLY_TABLE_INDEX_I32
OpenPOWER on IntegriCloud