[LLVM-C] [bindings/go] Add C and Golang bindings for COMDAT

Patch by Ben Clayton

Differential Revision: https://reviews.llvm.org/D44086

llvm-svn: 327551
This commit is contained in:
Reid Kleckner 2018-03-14 18:33:53 +00:00
parent 5a48cf86f1
commit e66458a841
5 changed files with 186 additions and 10 deletions

View File

@ -15,6 +15,7 @@ package llvm
/*
#include "llvm-c/Core.h"
#include "llvm-c/Comdat.h"
#include "IRBindings.h"
#include <stdlib.h>
*/
@ -37,6 +38,9 @@ type (
Value struct {
C C.LLVMValueRef
}
Comdat struct {
C C.LLVMComdatRef
}
BasicBlock struct {
C C.LLVMBasicBlockRef
}
@ -61,14 +65,15 @@ type (
Attribute struct {
C C.LLVMAttributeRef
}
Opcode C.LLVMOpcode
TypeKind C.LLVMTypeKind
Linkage C.LLVMLinkage
Visibility C.LLVMVisibility
CallConv C.LLVMCallConv
IntPredicate C.LLVMIntPredicate
FloatPredicate C.LLVMRealPredicate
LandingPadClause C.LLVMLandingPadClauseTy
Opcode C.LLVMOpcode
TypeKind C.LLVMTypeKind
Linkage C.LLVMLinkage
Visibility C.LLVMVisibility
CallConv C.LLVMCallConv
ComdatSelectionKind C.LLVMComdatSelectionKind
IntPredicate C.LLVMIntPredicate
FloatPredicate C.LLVMRealPredicate
LandingPadClause C.LLVMLandingPadClauseTy
)
func (c Context) IsNil() bool { return c.C == nil }
@ -248,6 +253,18 @@ const (
X86FastcallCallConv CallConv = C.LLVMX86FastcallCallConv
)
//-------------------------------------------------------------------------
// llvm.ComdatSelectionKind
//-------------------------------------------------------------------------
const (
AnyComdatSelectionKind ComdatSelectionKind = C.LLVMAnyComdatSelectionKind
ExactMatchComdatSelectionKind ComdatSelectionKind = C.LLVMExactMatchComdatSelectionKind
LargestComdatSelectionKind ComdatSelectionKind = C.LLVMLargestComdatSelectionKind
NoDuplicatesComdatSelectionKind ComdatSelectionKind = C.LLVMNoDuplicatesComdatSelectionKind
SameSizeComdatSelectionKind ComdatSelectionKind = C.LLVMSameSizeComdatSelectionKind
)
//-------------------------------------------------------------------------
// llvm.IntPredicate
//-------------------------------------------------------------------------
@ -1029,6 +1046,25 @@ func AddAlias(m Module, t Type, aliasee Value, name string) (v Value) {
return
}
// Operations on comdat
func (m Module) Comdat(name string) (c Comdat) {
cname := C.CString(name)
defer C.free(unsafe.Pointer(cname))
c.C = C.LLVMGetOrInsertComdat(m.C, cname)
return
}
func (v Value) Comdat() (c Comdat) { c.C = C.LLVMGetComdat(v.C); return }
func (v Value) SetComdat(c Comdat) { C.LLVMSetComdat(v.C, c.C) }
func (c Comdat) SelectionKind() ComdatSelectionKind {
return ComdatSelectionKind(C.LLVMGetComdatSelectionKind(c.C))
}
func (c Comdat) SetSelectionKind(k ComdatSelectionKind) {
C.LLVMSetComdatSelectionKind(c.C, (C.LLVMComdatSelectionKind)(k))
}
// Operations on functions
func AddFunction(m Module, name string, ft Type) (v Value) {
cname := C.CString(name)

View File

@ -0,0 +1,75 @@
/*===-- llvm-c/Comdat.h - Module Comdat C Interface -------------*- C++ -*-===*\
|* *|
|* The LLVM Compiler Infrastructure *|
|* *|
|* This file is distributed under the University of Illinois Open Source *|
|* License. See LICENSE.TXT for details. *|
|* *|
|*===----------------------------------------------------------------------===*|
|* *|
|* This file defines the C interface to COMDAT. *|
|* *|
\*===----------------------------------------------------------------------===*/
#ifndef LLVM_C_COMDAT_H
#define LLVM_C_COMDAT_H
#include "llvm-c/Types.h"
#ifdef __cplusplus
extern "C" {
#endif
typedef enum {
LLVMAnyComdatSelectionKind, ///< The linker may choose any COMDAT.
LLVMExactMatchComdatSelectionKind, ///< The data referenced by the COMDAT must
///< be the same.
LLVMLargestComdatSelectionKind, ///< The linker will choose the largest
///< COMDAT.
LLVMNoDuplicatesComdatSelectionKind, ///< No other Module may specify this
///< COMDAT.
LLVMSameSizeComdatSelectionKind ///< The data referenced by the COMDAT must be
///< the same size.
} LLVMComdatSelectionKind;
/**
* Return the Comdat in the module with the specified name. It is created
* if it didn't already exist.
*
* @see llvm::Module::getOrInsertComdat()
*/
LLVMComdatRef LLVMGetOrInsertComdat(LLVMModuleRef M, const char *Name);
/**
* Get the Comdat assigned to the given global object.
*
* @see llvm::GlobalObject::getComdat()
*/
LLVMComdatRef LLVMGetComdat(LLVMValueRef V);
/**
* Assign the Comdat to the given global object.
*
* @see llvm::GlobalObject::setComdat()
*/
void LLVMSetComdat(LLVMValueRef V, LLVMComdatRef C);
/*
* Get the conflict resolution selection kind for the Comdat.
*
* @see llvm::Comdat::getSelectionKind()
*/
LLVMComdatSelectionKind LLVMGetComdatSelectionKind(LLVMComdatRef C);
/*
* Set the conflict resolution selection kind for the Comdat.
*
* @see llvm::Comdat::setSelectionKind()
*/
void LLVMSetComdatSelectionKind(LLVMComdatRef C, LLVMComdatSelectionKind Kind);
#ifdef __cplusplus
}
#endif
#endif

View File

@ -134,6 +134,11 @@ typedef struct LLVMOpaqueAttributeRef *LLVMAttributeRef;
*/
typedef struct LLVMOpaqueDiagnosticInfo *LLVMDiagnosticInfoRef;
/**
* @see llvm::Comdat
*/
typedef struct LLVMComdat *LLVMComdatRef;
/**
* @}
*/

View File

@ -16,6 +16,9 @@
#ifndef LLVM_IR_COMDAT_H
#define LLVM_IR_COMDAT_H
#include "llvm-c/Types.h"
#include "llvm/Support/CBindingWrapping.h"
namespace llvm {
class raw_ostream;
@ -55,6 +58,9 @@ private:
SelectionKind SK = Any;
};
// Create wrappers for C Binding types (see CBindingWrapping.h).
DEFINE_SIMPLE_CONVERSION_FUNCTIONS(Comdat, LLVMComdatRef)
inline raw_ostream &operator<<(raw_ostream &OS, const Comdat &C) {
C.print(OS);
return OS;

View File

@ -7,13 +7,16 @@
//
//===----------------------------------------------------------------------===//
//
// This file implements the Comdat class.
// This file implements the Comdat class (including the C bindings).
//
//===----------------------------------------------------------------------===//
#include "llvm/IR/Comdat.h"
#include "llvm-c/Comdat.h"
#include "llvm/ADT/StringMap.h"
#include "llvm/ADT/StringRef.h"
#include "llvm/IR/Comdat.h"
#include "llvm/IR/GlobalObject.h"
#include "llvm/IR/Module.h"
using namespace llvm;
@ -22,3 +25,54 @@ Comdat::Comdat(Comdat &&C) : Name(C.Name), SK(C.SK) {}
Comdat::Comdat() = default;
StringRef Comdat::getName() const { return Name->first(); }
LLVMComdatRef LLVMGetOrInsertComdat(LLVMModuleRef M, const char *Name) {
return wrap(unwrap(M)->getOrInsertComdat(Name));
}
LLVMComdatRef LLVMGetComdat(LLVMValueRef V) {
GlobalObject *G = unwrap<GlobalObject>(V);
return wrap(G->getComdat());
}
void LLVMSetComdat(LLVMValueRef V, LLVMComdatRef C) {
GlobalObject *G = unwrap<GlobalObject>(V);
G->setComdat(unwrap(C));
}
LLVMComdatSelectionKind LLVMGetComdatSelectionKind(LLVMComdatRef C) {
switch (unwrap(C)->getSelectionKind()) {
case Comdat::Any:
return LLVMAnyComdatSelectionKind;
case Comdat::ExactMatch:
return LLVMExactMatchComdatSelectionKind;
case Comdat::Largest:
return LLVMLargestComdatSelectionKind;
case Comdat::NoDuplicates:
return LLVMNoDuplicatesComdatSelectionKind;
case Comdat::SameSize:
return LLVMSameSizeComdatSelectionKind;
}
llvm_unreachable("Invalid Comdat SelectionKind!");
}
void LLVMSetComdatSelectionKind(LLVMComdatRef C, LLVMComdatSelectionKind kind) {
Comdat *Cd = unwrap(C);
switch (kind) {
case LLVMAnyComdatSelectionKind:
Cd->setSelectionKind(Comdat::Any);
break;
case LLVMExactMatchComdatSelectionKind:
Cd->setSelectionKind(Comdat::ExactMatch);
break;
case LLVMLargestComdatSelectionKind:
Cd->setSelectionKind(Comdat::Largest);
break;
case LLVMNoDuplicatesComdatSelectionKind:
Cd->setSelectionKind(Comdat::NoDuplicates);
break;
case LLVMSameSizeComdatSelectionKind:
Cd->setSelectionKind(Comdat::SameSize);
break;
}
}