Skip to content
Snippets Groups Projects
Commit 1be60f30 authored by Regfare's avatar Regfare
Browse files

Ported to release version of MetaCG

parent 871c1f5f
Branches
Tags
No related merge requests found
......@@ -30,6 +30,6 @@ target_include_directories(CTUApex PUBLIC
$<BUILD_INTERFACE:${CMAKE_CURRENT_SOURCE_DIR}/include/>)
target_link_libraries(CTUApex metacg)
target_link_libraries(CTUApex minicpr)
#target_link_libraries(CTUApex minicpr)
target_link_libraries(CTUApex clangTooling)
target_compile_options(CTUApex PUBLIC -fno-rtti)
\ No newline at end of file
......@@ -5,7 +5,7 @@
#ifndef CTUAPEX_EXTRACTIONMETADATA_H
#define CTUAPEX_EXTRACTIONMETADATA_H
#include <MetaData.h>
#include <metadata/MetaData.h>
class ExtractionMetadata : public metacg::MetaData::Registrar<ExtractionMetadata> {
public:
......
......@@ -147,10 +147,14 @@ void CTUApexConsumer::HandleTranslationUnit(clang::ASTContext &Context) {
outFile << getNextExtractionBlock().contents << "\n";
}
outFile.close();
SPDLOG_INFO("Generate wrapper calls");
SPDLOG_CRITICAL("WRAPPER CALLS CAN NOT YET BE IMPLEMENTED");
if(auto md=call_graph->getMain()->checkAndGet<ExtractionMetadata>(); md.first && !md.second->isMarkedToExtract()){
//we have no main function and need to create or own
outFile<<"\nint main(){return 0;}\n";
}
// Outline the code we want
//SPDLOG_DEBUG("Generating outline");
//assert(output.empty());
......@@ -164,6 +168,8 @@ void CTUApexConsumer::HandleTranslationUnit(clang::ASTContext &Context) {
// output = extracted_source;
//}
outFile.close();
SPDLOG_INFO("Clean CG for next run");
for (const auto &node: call_graph->getNodes()) {
if (node.second->has<ExtractionMetadata>()) {
......
......@@ -13,97 +13,12 @@
#include "CTUApexAction.h"
#include "CTUApexConsumer.h"
#include "MCGReader.h"
#include "MCGWriter.h"
#include "io/VersionTwoMCGReader.h"
#include "io/VersionThreeMCGReader.h"
#include "Util.h"
#include "ExtractionMetadata.h"
class FilePropertiesMetaData : public metacg::MetaData::Registrar<FilePropertiesMetaData> {
public:
static constexpr const char *key = "fileProperties";
FilePropertiesMetaData() : origin("INVALID"), fromSystemInclude(false), lineNumber(0) {}
explicit FilePropertiesMetaData(const nlohmann::json &j) {
if (j.is_null()) {
metacg::MCGLogger::instance().getConsole()->trace("Could not retrieve meta data for {}", key);
return;
}
std::string fileOrigin = j["origin"].get<std::string>();
bool isFromSystemInclude = j["systemInclude"].get<bool>();
origin = fileOrigin;
fromSystemInclude = isFromSystemInclude;
}
nlohmann::json to_json() const final {
nlohmann::json j;
j["origin"] = origin;
j["systemInclude"] = fromSystemInclude;
return j;
};
virtual const char *getKey() const final { return key; }
std::string origin;
bool fromSystemInclude;
int lineNumber;
};
class PiraOneData : public metacg::MetaData::Registrar<PiraOneData> {
public:
static constexpr const char *key = "numStatements";
PiraOneData() = default;
explicit PiraOneData(const nlohmann::json &j) {
metacg::MCGLogger::instance().getConsole()->trace("Running PiraOneMetaDataRetriever::read from json");
if (j.is_null()) {
metacg::MCGLogger::instance().getConsole()->trace("Could not retrieve meta data for {}", key);
return;
}
auto jsonNumStmts = j.get<long long int>();
metacg::MCGLogger::instance().getConsole()->debug("Read {} stmts from file", jsonNumStmts);
setNumberOfStatements(jsonNumStmts);
}
nlohmann::json to_json() const final {
nlohmann::json j;
j["numStatements"] = getNumberOfStatements();
return j;
};
virtual const char *getKey() const final { return key; }
void setNumberOfStatements(int numStmts) { this->numStmts = numStmts; }
int getNumberOfStatements() const { return this->numStmts; }
void setHasBody(bool hasBody = true) { this->hasBody = hasBody; }
bool getHasBody() const { return this->hasBody; }
void setDominantRuntime(bool dominantRuntime = true) { this->dominantRuntime = dominantRuntime; }
bool isDominantRuntime() const { return this->dominantRuntime; }
void setComesFromCube(bool fromCube = true) { this->wasInPreviousProfile = fromCube; }
bool comesFromCube() const { return this->wasInPreviousProfile; }
bool inPreviousProfile() const { return wasInPreviousProfile; }
private:
bool wasInPreviousProfile{false};
bool dominantRuntime{false};
bool hasBody{false};
int numStmts{0};
};
inline void to_json(nlohmann::json &j, const PiraOneData &data) {
j = nlohmann::json{{"numStatements", data.getNumberOfStatements()}};
}
//Das sind convenience definitionen, dass wir nicht so viel tippen müssen
using namespace llvm;
......@@ -120,6 +35,16 @@ static cl::opt<std::string> cg_file("cg-file", cl::desc("MetaCG file containing
enum class LogLevel {
Trace, Debug, Info, Warning, Error, /* Critical,*/ Off
};
//static cl::opt<std::string> extractionStart("extract",
// cl::desc("Qualified name of the function to start the extraction from"),
// cl::value_desc("functionname"), cl::Optional, cl::cat(CTUApex));
static cl::list<std::string> extractionPoints("extract",
cl::desc("Qualified names of the function to start the extraction from"),
cl::value_desc("Comma separated list of function names"), cl::Optional,
cl::cat(CTUApex));
static cl::opt<LogLevel> LoggingLevel("log-level", cl::desc("Select log level"),
cl::values(clEnumValN(LogLevel::Trace, "trace", "Enable Trace and higher logs"),
clEnumValN(LogLevel::Debug, "debug", "Enable Debug and higher logs"),
......@@ -129,31 +54,31 @@ static cl::opt<LogLevel> LoggingLevel("log-level", cl::desc("Select log level"),
clEnumValN(LogLevel::Error, "error", "Enable only Error logs"),
clEnumValN(LogLevel::Off, "off", "Disable all logging")),
cl::init(LogLevel::Info), cl::cat(CTUApex));
static cl::opt<bool> OnlyWrapper("generate-only-wrapper", cl::desc("Output only the wrapper function"),
cl::cat(CTUApex));
static cl::opt<bool> DumpAnalysisResult("dump-analysis-result",
cl::desc("Dump the dependence analysis result to stdout"), cl::cat(CTUApex));
class CTUApexFactory : clang::ASTFrontendAction {
public:
CTUApexFactory(metacg::Callgraph &cg) : cg(&cg) {}
template<typename T, class... Args>
std::unique_ptr<clang::tooling::FrontendActionFactory> argumentParsingFrontendActionFactory(Args... args) {
class SimpleFrontendActionFactory : public clang::tooling::FrontendActionFactory {
public:
explicit SimpleFrontendActionFactory(Args... constructorArgs) {
fn1 = [=]() { return std::make_unique<T>(constructorArgs...); };
}
std::unique_ptr<clang::FrontendAction> create() override {
return fn1();
}
std::unique_ptr<clang::ASTConsumer> newASTConsumer() {
return std::unique_ptr<clang::ASTConsumer>(new CTUApexConsumer(cg, includes, macros, pragmas));
}
private:
std::function<std::unique_ptr<T>()> fn1; // function
};
std::unique_ptr<clang::ASTConsumer> CreateASTConsumer([[maybe_unused]] clang::CompilerInstance &compiler,
[[maybe_unused]] llvm::StringRef sr) {
return std::unique_ptr<clang::ASTConsumer>(new CTUApexConsumer(cg, includes, macros, pragmas));
}
return std::unique_ptr<FrontendActionFactory>(new SimpleFrontendActionFactory(args...));
}
private:
std::vector<ExtractionBlock> includes;
std::vector<ExtractionBlock> macros;
std::vector<ExtractionBlock> pragmas;
metacg::Callgraph *cg;
};
void markCalleesToExtract(const size_t nodeID, const metacg::Callgraph &cg) {
......@@ -162,6 +87,7 @@ void markCalleesToExtract(const size_t nodeID, const metacg::Callgraph &cg) {
markCalleesToExtract(call->getId(), cg);
}
}
void markFunctionsAlongCallpaths(metacg::Callgraph &cg) {
SPDLOG_INFO("Compute set of functions to be extracted");
for (const auto &node: cg.getNodes()) {
......@@ -204,18 +130,40 @@ int main(int argc, const char **argv) {
}
CommonOptionsParser &OptionsParser = ExpectedParser.get();
ClangTool Tool(OptionsParser.getCompilations(), OptionsParser.getSourcePathList());
std::string error = "error";
auto fcd = FixedCompilationDatabase::loadFromDirectory("", error);
ClangTool tool(OptionsParser.getCompilations(), OptionsParser.getSourcePathList());
metacg::io::FileSource fs(cg_file.getValue());
metacg::io::VersionTwoMetaCGReader mcgReader(fs);
std::unique_ptr<metacg::io::MetaCGReader> mcgReader;
if (fs.get().at("_MetaCG").at("version") == "3.0") {
mcgReader = std::make_unique<metacg::io::VersionThreeMetaCGReader>(fs);
} else if (fs.get().at("_MetaCG").at("version") == "2.0") {
mcgReader = std::make_unique<metacg::io::VersionTwoMetaCGReader>(fs);
} else {
assert(false && "File corrupt or format not specified");
}
auto &mcgManager = metacg::graph::MCGManager::get();
mcgManager.addToManagedGraphs("emptyGraph", std::make_unique<metacg::Callgraph>());
mcgReader.read(mcgManager);
mcgReader->read(mcgManager);
auto &cg = *mcgManager.getCallgraph();
//Add extraction point gotten via the CLI
for(const auto& extractionFunc : extractionPoints){
if (cg.hasNode(extractionFunc)) {
auto *md = new ExtractionMetadata();
md->setMarkedToExtract(true);
cg.getNode(extractionFunc)->addMetaData(md);
}else{
SPDLOG_ERROR("The given function: "+ extractionFunc + " does not exist in the given callgraph");
}
}
markFunctionsAlongCallpaths(*mcgManager.getCallgraph());
markFunctionsAlongCallpaths(cg);
Tool.run(argumentParsingFrontendActionFactory<CTUApexAction>(mcgManager.getCallgraph()).get());
tool.run(clang::tooling::newFrontendActionFactory<CTUApexFactory>(
new CTUApexFactory(*mcgManager.getCallgraph())).get());
return 0;
}
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment