diff --git a/op-finder/OperationFinder.cpp b/op-finder/OperationFinder.cpp index dc5e6bd..bc4eef3 100644 --- a/op-finder/OperationFinder.cpp +++ b/op-finder/OperationFinder.cpp @@ -48,19 +48,13 @@ OperationFinder::OperationFinder(IOperationOutput* storage) void OperationFinder::processArithmetic(const clang::BinaryOperator* op, const clang::SourceManager& source_manager) { - const auto [file_name, line_number, column_number] = resolveLocations(op, source_manager); + auto [file_name, log] = _createBaseOperationLog(op, source_manager); + const std::string op_code = getOpcode(op).str(); - llvm::outs() << file_name << ":" - << line_number << ":" - << column_number << ":" - << "Binary arithmetic: Type: " << getOpcode(op) << " LHS: "; + llvm::outs() << "\n\tBinary arithmetic: Type: " << op_code; - OperationLog log; - log.line = line_number; log.entry_type = OperationLog::BasicOperation::TYPE_NAME; - log.entry = _createBasicOperationLogEntry(op, op->getLHS(), op->getRHS()); - log.current_for_loops = _for_loop_stack; - log.is_fallthrough = _in_fallthrough; + log.entry = _createBasicOperationLogEntry(op_code, op, op->getLHS(), op->getRHS()); _storage->pushOperation(file_name, std::move(log)); @@ -69,24 +63,13 @@ void OperationFinder::processArithmetic(const clang::BinaryOperator* op, const c void OperationFinder::processUnaryArithmetic(const clang::UnaryOperator* op, const clang::SourceManager& source_manager) { - const Expr* lhs = op->getExprStmt(); + auto [file_name, log] = _createBaseOperationLog(op, source_manager); + const std::string op_code = getOpcode(op).str(); - assert(op); - assert(lhs); + llvm::outs() << "\n\tUnary arithmetic: Type: " << op_code; - const auto [file_name, line_number, column_number] = resolveLocations(op, source_manager); - - llvm::outs() << file_name << ":" - << line_number << ":" - << column_number << ":" - << "Unary arithmetic: Type: " << getOpcode(op) << " LHS: "; - - OperationLog log; - log.line = line_number; log.entry_type = OperationLog::BasicOperation::TYPE_NAME; - log.entry = _createBasicOperationLogEntry(op, lhs, nullptr); - log.current_for_loops = _for_loop_stack; - log.is_fallthrough = _in_fallthrough; + log.entry = _createBasicOperationLogEntry(op_code, op, op->getExprStmt(), nullptr); _storage->pushOperation(file_name, std::move(log)); @@ -99,29 +82,37 @@ void OperationFinder::processFunctionCall(const clang::CallExpr* call, const Sou assert(func); - const auto [file_name, line_number, column_number] = resolveLocations(call, source_manager); - - const std::string res_type = ResolveTypeName(func->getType()); + auto [file_name, log] = _createBaseOperationLog(call, source_manager); const std::string func_name = func->getNameAsString(); - llvm::outs() << file_name << ":" - << line_number << ":" - << column_number << ":" - << "Function call: name: " << func_name << " Restype: " - << res_type << "\n"; + llvm::outs() << "\n\tFunction call: func name: " << func_name << "\n\tResult eval type: "; + + const std::string res_type = ResolveTypeName(func->getType()); auto func_call = std::make_unique(); func_call->function_name = func_name; func_call->call_result_type = res_type; - OperationLog log; - log.line = line_number; log.entry_type = OperationLog::FunctionCall::TYPE_NAME; log.entry = std::move(func_call); - log.current_for_loops = _for_loop_stack; - log.is_fallthrough = _in_fallthrough; _storage->pushOperation(file_name, std::move(log)); + + llvm::outs() << "\n"; +} + +void OperationFinder::processArraySubscript(const clang::ArraySubscriptExpr* subscript, const clang::SourceManager& source_manager) +{ + auto [file_name, log] = _createBaseOperationLog(subscript, source_manager); + + llvm::outs() << "\n\tSubscript:"; + + log.entry_type = OperationLog::BasicOperation::TYPE_NAME; + log.entry = _createBasicOperationLogEntry("subscript", subscript, subscript->getBase(), subscript->getIdx()); + + _storage->pushOperation(file_name, std::move(log)); + + llvm::outs() << "\n"; } void OperationFinder::fallthroughBranchEntered() @@ -147,11 +138,13 @@ void OperationFinder::forLoopExited() } std::unique_ptr - OperationFinder::_createBasicOperationLogEntry(const Expr* source, const Expr* op1, const Expr* op2) + OperationFinder::_createBasicOperationLogEntry(const std::string& opcode, const Expr* source, const Expr* op1, const Expr* op2) { auto log = std::make_unique(); - llvm::outs() << "Expression types:\n\tExpression eval type: "; + log->operation_name = opcode; + + llvm::outs() << "\n\tExpression eval type: "; log->type_result = ResolveTypeName(source->getType()); if (op1) @@ -167,3 +160,19 @@ std::unique_ptr return log; } + +std::pair OperationFinder::_createBaseOperationLog(const clang::Stmt* stmt, const clang::SourceManager& source_manager) +{ + const auto [file_name, line_number, column_number] = resolveLocations(stmt, source_manager); + + OperationLog log; + log.line = line_number; + log.current_for_loops = _for_loop_stack; + log.is_fallthrough = _in_fallthrough; + + llvm::outs() << file_name << ":" + << line_number << ":" + << column_number << ":"; + + return { file_name, std::move(log) }; +} diff --git a/op-finder/OperationFinder.hpp b/op-finder/OperationFinder.hpp index 48ef482..780771a 100644 --- a/op-finder/OperationFinder.hpp +++ b/op-finder/OperationFinder.hpp @@ -17,6 +17,7 @@ public: void processArithmetic(const clang::BinaryOperator* op, const clang::SourceManager& source_manager); void processUnaryArithmetic(const clang::UnaryOperator* op, const clang::SourceManager& source_manager); void processFunctionCall(const clang::CallExpr* call, const clang::SourceManager& source_manager); + void processArraySubscript(const clang::ArraySubscriptExpr* subscript, const clang::SourceManager& source_manager); void fallthroughBranchEntered(); void fallthroughBranchExited(); @@ -26,7 +27,9 @@ public: private: std::unique_ptr - _createBasicOperationLogEntry(const clang::Expr* source, const clang::Expr* op1, const clang::Expr* op2); + _createBasicOperationLogEntry(const std::string& opcode, const clang::Expr* source, const clang::Expr* op1, const clang::Expr* op2); + + std::pair _createBaseOperationLog(const clang::Stmt* stmt, const clang::SourceManager& source_manager); int _next_for_loop_id = 0; bool _in_fallthrough = false; diff --git a/op-finder/OperationFinderAstVisitor.cpp b/op-finder/OperationFinderAstVisitor.cpp index ef91717..ce9178d 100644 --- a/op-finder/OperationFinderAstVisitor.cpp +++ b/op-finder/OperationFinderAstVisitor.cpp @@ -52,6 +52,15 @@ bool OperationFinderAstVisitor::VisitCallExpr(clang::CallExpr* call) return true; } +bool OperationFinderAstVisitor::VisitArraySubscriptExpr(clang::ArraySubscriptExpr* subscript) +{ + assert(_context); + + _op_finder->processArraySubscript(subscript, _context->getSourceManager()); + + return true; +} + bool OperationFinderAstVisitor::dataTraverseStmtPre(clang::Stmt* stmt) { assert(_context); diff --git a/op-finder/OperationFinderAstVisitor.hpp b/op-finder/OperationFinderAstVisitor.hpp index d1408f7..d82fe46 100644 --- a/op-finder/OperationFinderAstVisitor.hpp +++ b/op-finder/OperationFinderAstVisitor.hpp @@ -21,6 +21,7 @@ public: bool VisitBinaryOperator(clang::BinaryOperator* op); bool VisitUnaryOperator(clang::UnaryOperator* op); bool VisitCallExpr(clang::CallExpr* call); + bool VisitArraySubscriptExpr(clang::ArraySubscriptExpr* subscript); bool dataTraverseStmtPre(clang::Stmt* stmt); bool dataTraverseStmtPost(clang::Stmt* stmt); diff --git a/op-finder/OperationLog.hpp b/op-finder/OperationLog.hpp index 5bf6d1e..d55c8f7 100644 --- a/op-finder/OperationLog.hpp +++ b/op-finder/OperationLog.hpp @@ -31,6 +31,7 @@ struct OperationLog { static constexpr char TYPE_NAME[] = "basic_operation"; + std::string operation_name; std::string type_lhs; std::string type_rhs; std::string type_result; @@ -84,6 +85,7 @@ inline void from_json(const nlohmann::json& j, OperationLog& l) inline void to_json(nlohmann::json& j, const OperationLog::BasicOperation& bo) { j = nlohmann::json{ + {"operation_name", bo.operation_name}, {"type_lhs", bo.type_lhs}, {"type_rhs", bo.type_rhs}, {"type_result", bo.type_result} @@ -92,6 +94,7 @@ inline void to_json(nlohmann::json& j, const OperationLog::BasicOperation& bo) inline void from_json(const nlohmann::json& j, OperationLog::BasicOperation& bo) { + j.at("operation_name").get_to(bo.operation_name); j.at("type_lhs").get_to(bo.type_lhs); j.at("type_rhs").get_to(bo.type_rhs); j.at("type_result").get_to(bo.type_result);