Fix for #431: memory leak due to multiple TargetMachine creation

This commit is contained in:
Dmitry Babokin
2013-03-23 14:33:45 +04:00
parent 0f86255279
commit 7f0c92eb4d
2 changed files with 33 additions and 26 deletions

View File

@@ -145,6 +145,7 @@ static const char *supportedCPUs[] = {
Target::Target(const char *arch, const char *cpu, const char *isa, bool pic) :
m_target(NULL),
m_targetMachine(NULL),
m_valid(false),
m_isa(SSE2),
m_arch(""),
@@ -424,13 +425,31 @@ Target::Target(const char *arch, const char *cpu, const char *isa, bool pic) :
}
if (!error) {
llvm::TargetMachine *targetMachine = this->GetTargetMachine();
// Create TargetMachine
std::string triple = GetTripleString();
llvm::Reloc::Model relocModel = m_generatePIC ? llvm::Reloc::PIC_ :
llvm::Reloc::Default;
std::string featuresString = m_attributes;
llvm::TargetOptions options;
#if !defined(LLVM_3_1)
if (g->opt.disableFMA == false)
options.AllowFPOpFusion = llvm::FPOpFusion::Fast;
#endif // !LLVM_3_1
m_targetMachine =
m_target->createTargetMachine(triple, m_cpu, featuresString, options,
relocModel);
Assert(m_targetMachine != NULL);
m_targetMachine->setAsmVerbosityDefault(true);
// Set is32Bit
#if defined(LLVM_3_1)
const llvm::TargetData *targetData = targetMachine->getTargetData();
const llvm::TargetData *targetData = m_targetMachine->getTargetData();
this->m_is32Bit = (targetData->getPointerSize() == 4);
#else
int addressSpace = 0;
const llvm::DataLayout *dataLayout = targetMachine->getDataLayout();
const llvm::DataLayout *dataLayout = m_targetMachine->getDataLayout();
this->m_is32Bit = (dataLayout->getPointerSize(addressSpace) == 4);
#endif
@@ -507,28 +526,6 @@ Target::GetTripleString() const {
}
llvm::TargetMachine *
Target::GetTargetMachine() const {
std::string triple = GetTripleString();
llvm::Reloc::Model relocModel = m_generatePIC ? llvm::Reloc::PIC_ :
llvm::Reloc::Default;
std::string featuresString = m_attributes;
llvm::TargetOptions options;
#if !defined(LLVM_3_1)
if (g->opt.disableFMA == false)
options.AllowFPOpFusion = llvm::FPOpFusion::Fast;
#endif // !LLVM_3_1
llvm::TargetMachine *targetMachine =
m_target->createTargetMachine(triple, m_cpu, featuresString, options,
relocModel);
Assert(targetMachine != NULL);
targetMachine->setAsmVerbosityDefault(true);
return targetMachine;
}
const char *
Target::GetISAString() const {
switch (m_isa) {

12
ispc.h
View File

@@ -187,7 +187,7 @@ public:
/** Returns the LLVM TargetMachine object corresponding to this
target. */
llvm::TargetMachine *GetTargetMachine() const;
llvm::TargetMachine *GetTargetMachine() const {return m_targetMachine;}
/** Returns a string like "avx" encoding the target. */
const char *GetISAString() const;
@@ -251,6 +251,16 @@ private:
/** llvm Target object representing this target. */
const llvm::Target *m_target;
/** llvm TargetMachine.
Note that it's not destroyed during Target destruction, as
Module::CompileAndOutput() uses TargetMachines after Target is destroyed.
This needs to be changed.
It's also worth noticing, that DataLayout of TargetMachine cannot be
modified and for generic targets it's not what we really need, so it
must not be used.
*/
llvm::TargetMachine *m_targetMachine;
/** flag to report invalid state after construction
(due to bad parameters passed to constructor). */
bool m_valid;