Repository: storm Updated Branches: refs/heads/STORM-1040 92a3fcde7 -> df69f3dd9
STORM-1080. Compiler SQL literals to LLVM constants. Project: http://git-wip-us.apache.org/repos/asf/storm/repo Commit: http://git-wip-us.apache.org/repos/asf/storm/commit/df69f3dd Tree: http://git-wip-us.apache.org/repos/asf/storm/tree/df69f3dd Diff: http://git-wip-us.apache.org/repos/asf/storm/diff/df69f3dd Branch: refs/heads/STORM-1040 Commit: df69f3dd964cf0b188c993df3670e9b4cab43834 Parents: 92a3fcd Author: Haohui Mai <whe...@apache.org> Authored: Wed Sep 30 16:45:50 2015 -0700 Committer: Haohui Mai <whe...@apache.org> Committed: Sun Oct 4 14:11:55 2015 -0700 ---------------------------------------------------------------------- .travis.yml | 13 ++- .../storm-sql-core/src/native/CMakeLists.txt | 6 +- .../src/native/cmake/FindLLVM.cmake | 14 +-- .../src/native/lib/CMakeLists.txt | 2 + .../src/native/lib/compiler/CMakeLists.txt | 19 +++++ .../src/native/lib/compiler/expr_compiler.cc | 69 +++++++++++++++ .../src/native/lib/compiler/expr_compiler.h | 42 +++++++++ .../src/native/lib/compiler/expr_visitor.cc | 43 ++++++++++ .../src/native/lib/compiler/expr_visitor.h | 73 ++++++++++++++++ .../src/native/lib/compiler/typesystem.cc | 60 +++++++++++++ .../src/native/lib/compiler/typesystem.h | 54 ++++++++++++ .../src/native/test/CMakeLists.txt | 18 ++++ .../src/native/test/compiler/CMakeLists.txt | 23 +++++ .../native/test/compiler/expr_compiler_test.cc | 90 ++++++++++++++++++++ .../sql/compiler/TestCalcitePlanSerializer.java | 90 ++++++++++++++++---- 15 files changed, 591 insertions(+), 25 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/.travis.yml ---------------------------------------------------------------------- diff --git a/.travis.yml b/.travis.yml index ed8920c..f08c07b 100644 --- a/.travis.yml +++ b/.travis.yml @@ -11,6 +11,17 @@ # limitations under the License. language: java +addons: + apt: + sources: + - ubuntu-toolchain-r-test + - llvm-toolchain-precise-3.6 + packages: + - clang-3.6 + - llvm-3.6 + - llvm-3.6-dev + - libedit-dev + jdk: - oraclejdk7 - oraclejdk8 @@ -19,7 +30,7 @@ before_install: - rvm use 2.1.5 --install - nvm install 0.12.2 - nvm use 0.12.2 - - export CXX="clang++" + - export CXX="clang++-3.6" install: /bin/bash ./dev-tools/travis/travis-install.sh `pwd` http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/CMakeLists.txt b/external/sql/storm-sql-core/src/native/CMakeLists.txt index 9e81c6b..e722c4f 100644 --- a/external/sql/storm-sql-core/src/native/CMakeLists.txt +++ b/external/sql/storm-sql-core/src/native/CMakeLists.txt @@ -34,7 +34,7 @@ endif() enable_testing() if(UNIX) -set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra -pedantic -std=c++11 -g -fPIC -fno-strict-aliasing -fno-exceptions") +set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wall -Wextra -pedantic -std=c++11 -g -fPIC -fno-strict-aliasing -fno-exceptions -fno-rtti") endif() if(APPLE) @@ -43,9 +43,11 @@ endif() include_directories( include + lib third_party/gmock-1.7.0 third_party/json11) add_subdirectory(lib) -add_subdirectory(bindings) add_subdirectory(third_party) +add_subdirectory(bindings) +add_subdirectory(test) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/cmake/FindLLVM.cmake ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/cmake/FindLLVM.cmake b/external/sql/storm-sql-core/src/native/cmake/FindLLVM.cmake index f2416c0..affa0ca 100644 --- a/external/sql/storm-sql-core/src/native/cmake/FindLLVM.cmake +++ b/external/sql/storm-sql-core/src/native/cmake/FindLLVM.cmake @@ -15,13 +15,18 @@ # See the License for the specific language governing permissions and # limitations under the License. # + if (LLVM_INCLUDE_DIR) set(LLVM_FOUND TRUE) endif() +set(LLVM_CONFIG_NAMES llvm-config-3.7 llvm-config37 + llvm-config-3.6 llvm-config36 + llvm-config) + if (NOT LLVM_FOUND) if (NOT LLVM_CONFIG) - find_program(LLVM_CONFIG NAMES llvm-config DOC "llvm-config executable") + find_program(LLVM_CONFIG NAMES ${LLVM_CONFIG_NAMES} DOC "llvm-config executable") if (${LLVM_CONFIG} STREQUAL LLVM_CONFIG-NOTFOUND) message(FATAL_ERROR "Cannot find llvm-config") endif() @@ -29,10 +34,9 @@ if (NOT LLVM_FOUND) endif () execute_process(COMMAND ${LLVM_CONFIG} --cxxflags OUTPUT_VARIABLE LLVM_CXXFLAGS OUTPUT_STRIP_TRAILING_WHITESPACE) - - execute_process(COMMAND ${LLVM_CONFIG} --ldflags --libs core OUTPUT_VARIABLE LLVM_LDFLAGS OUTPUT_STRIP_TRAILING_WHITESPACE) - - set(LLVM_LIBRARIES ${LLVM_LDFLAGS}) + execute_process(COMMAND ${LLVM_CONFIG} --ldflags OUTPUT_VARIABLE LLVM_LDFLAGS OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND ${LLVM_CONFIG} --libs core OUTPUT_VARIABLE LLVM_LIBRARIES OUTPUT_STRIP_TRAILING_WHITESPACE) + execute_process(COMMAND ${LLVM_CONFIG} --system-libs OUTPUT_VARIABLE LLVM_SYSTEM_LIBRARIES OUTPUT_STRIP_TRAILING_WHITESPACE) mark_as_advanced(LLVM_LIBRARIES) execute_process(COMMAND ${LLVM_CONFIG} --version OUTPUT_VARIABLE LLVM_VERSION OUTPUT_STRIP_TRAILING_WHITESPACE) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/CMakeLists.txt b/external/sql/storm-sql-core/src/native/lib/CMakeLists.txt index 055d8dd..2e7475c 100644 --- a/external/sql/storm-sql-core/src/native/lib/CMakeLists.txt +++ b/external/sql/storm-sql-core/src/native/lib/CMakeLists.txt @@ -16,4 +16,6 @@ # limitations under the License. # +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LLVM_CXXFLAGS}") +add_subdirectory(compiler) add_subdirectory(tool) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/CMakeLists.txt b/external/sql/storm-sql-core/src/native/lib/compiler/CMakeLists.txt new file mode 100644 index 0000000..440301e --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/CMakeLists.txt @@ -0,0 +1,19 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LLVM_CXXFLAGS}") +add_library(compiler typesystem.cc expr_visitor.cc expr_compiler.cc) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.cc ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.cc b/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.cc new file mode 100644 index 0000000..b077a7c --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.cc @@ -0,0 +1,69 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "expr_compiler.h" + +#include <llvm/IR/Constants.h> +#include <functional> + +using json11::Json; +using llvm::cast; +using llvm::APFloat; +using llvm::BinaryOperator; +using llvm::CmpInst; +using llvm::ConstantDataArray; +using llvm::ConstantFP; +using llvm::ConstantInt; +using llvm::IntegerType; +using llvm::SMDiagnostic; +using llvm::SourceMgr; +using llvm::Type; +using llvm::Value; +using std::back_inserter; +using std::map; +using std::vector; +using std::string; +using std::transform; + +namespace stormsql { + +ExprCompiler::ExprCompiler(const string &err_ctx, TypeSystem *typesystem) + : err_ctx_(err_ctx), typesystem_(typesystem) {} + +Value *ExprCompiler::VisitLiteral(const Json &type, const Json &value) { + TypeSystem::SqlType sql_ty = typesystem_->GetSqlTypeId(type); + Type *ty = typesystem_->GetLLVMType(type); + switch (sql_ty) { + case TypeSystem::kIntegerTy: { + long long v = strtoll(value.string_value().c_str(), nullptr, 0); + return ConstantInt::get(cast<IntegerType>(ty), v); + } + case TypeSystem::kBooleanTy: { + return value.string_value() == "true" ? ConstantInt::getTrue(ty) + : ConstantInt::getFalse(ty); + } + case TypeSystem::kDecimalTy: { + APFloat fp(APFloat::IEEEdouble, value.string_value()); + return ConstantFP::get(ty->getContext(), fp); + } + case TypeSystem::kStringTy: { + return ConstantDataArray::getString(ty->getContext(), value.string_value()); + } + } +} +} http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.h ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.h b/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.h new file mode 100644 index 0000000..44c7a87 --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/expr_compiler.h @@ -0,0 +1,42 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +#ifndef STORM_SQL_COMPILER_EXPR_COMPILER_H_ +#define STORM_SQL_COMPILER_EXPR_COMPILER_H_ + +#include "expr_visitor.h" +#include "typesystem.h" +#include <llvm/IR/IRBuilder.h> +#include <llvm/Support/SourceMgr.h> +#include <map> + +namespace stormsql { + +/** + * Compile a SQL expression down to LLVM IR + **/ +class ExprCompiler : public ExprVisitor<ExprCompiler, llvm::Value *> { +public: + explicit ExprCompiler(const std::string &err_ctx, TypeSystem *typesystem); + llvm::Value *VisitLiteral(const Json &type, const Json &value); + +private: + const std::string err_ctx_; + TypeSystem *typesystem_; +}; +} +#endif http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.cc ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.cc b/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.cc new file mode 100644 index 0000000..c5c322c --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.cc @@ -0,0 +1,43 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "expr_visitor.h" + +using llvm::BinaryOperator; +using llvm::CmpInst; +using std::map; +using std::string; + +namespace stormsql { +const map<string, CmpInst::Predicate> ExprVisitorBase::kCmpPredicates = { + {"=", CmpInst::Predicate::ICMP_EQ}, + {"<>", CmpInst::Predicate::ICMP_NE}, + {">", CmpInst::Predicate::ICMP_SGT}, + {">=", CmpInst::Predicate::ICMP_SGE}, + {"<", CmpInst::Predicate::ICMP_SLT}, + {"<=", CmpInst::Predicate::ICMP_SLE}}; + +const map<string, BinaryOperator::BinaryOps> ExprVisitorBase::kBinaryOps = { + {"+", BinaryOperator::BinaryOps::Add}, + {"-", BinaryOperator::BinaryOps::Sub}, + {"*", BinaryOperator::BinaryOps::Mul}, + {"/", BinaryOperator::BinaryOps::SDiv}, + {"/INT", BinaryOperator::BinaryOps::SDiv}, + {"AND", BinaryOperator::BinaryOps::And}, + {"OR", BinaryOperator::BinaryOps::Or}}; +} http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.h ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.h b/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.h new file mode 100644 index 0000000..728a4db --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/expr_visitor.h @@ -0,0 +1,73 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyrighRetTy ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may noRetTy use this file excepRetTy in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOURetTy WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +#ifndef STORM_SQL_COMPILER_EXPR_VISITOR_H_ +#define STORM_SQL_COMPILER_EXPR_VISITOR_H_ + +#include <json11/json11.hpp> +#include <llvm/IR/InstrTypes.h> +#include <cassert> +#include <map> + +namespace stormsql { + +class ExprVisitorBase { +protected: + static const std::map<std::string, llvm::CmpInst::Predicate> kCmpPredicates; + static const std::map<std::string, llvm::BinaryOperator::BinaryOps> + kBinaryOps; +}; + +template <class SubClass, class RetTy = void> +class ExprVisitor : ExprVisitorBase { +public: + typedef json11::Json Json; + RetTy Visit(const Json &json) { + const Json &value = json["value"]; + const Json &type = json["type"]; + std::string inst = value["inst"].string_value(); + if (inst == "call") { + const std::string &op = value["operator"].string_value(); + if (kCmpPredicates.count(op)) { + return static_cast<SubClass *>(this)->VisitCmp( + kCmpPredicates.at(op), value["operands"][0], value["operands"][1]); + } else if (kBinaryOps.count(op)) { + return static_cast<SubClass *>(this)->VisitBinaryOperator( + kBinaryOps.at(op), value["operands"][0], value["operands"][1]); + } + } else if (inst == "literal") { + return static_cast<SubClass *>(this)->VisitLiteral(type, value["value"]); + } else { + assert(0 && "Unknown expression!"); + } + return RetTy(); + } + + RetTy VisitCmp(llvm::CmpInst::Predicate predicate, const Json &LHS, + const Json &RHS) { + return RetTy(); + } + + RetTy VisitBinaryOperator(llvm::BinaryOperator::BinaryOps opcdoe, + const Json &LHS, const Json &RHS) { + return RetTy(); + } + + RetTy VisitLiteral(const Json &type, const Json &value) { return RetTy(); } +}; +} +#endif http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.cc ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.cc b/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.cc new file mode 100644 index 0000000..67938c5 --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.cc @@ -0,0 +1,60 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "typesystem.h" +#include <llvm/IR/DerivedTypes.h> +#include <cassert> + +using json11::Json; +using llvm::Type; +using std::map; +using std::string; + +namespace stormsql { + +const map<string, TypeSystem::SqlType> TypeSystem::sql_type_map_ = { + {"INTEGER", TypeSystem::SqlType::kIntegerTy}, + {"BOOLEAN", TypeSystem::SqlType::kBooleanTy}, + {"DECIMAL", TypeSystem::SqlType::kDecimalTy}, + {"CHAR", TypeSystem::SqlType::kStringTy}}; + +Table::Table(std::vector<Field> &&fields) : fields_(std::move(fields)) {} + +TypeSystem::TypeSystem(llvm::LLVMContext *ctx) : ctx_(*ctx) {} + +TypeSystem::SqlType TypeSystem::GetSqlTypeId(const Json &type) { + auto it = sql_type_map_.find(type.string_value()); + assert(it != sql_type_map_.end() && "Unsupported type"); + return it->second; +} + +Type *TypeSystem::GetLLVMType(const Json &type) { + switch (GetSqlTypeId(type)) { + case kIntegerTy: + return Type::getInt32Ty(ctx_); + case kBooleanTy: + return Type::getInt1Ty(ctx_); + case kDecimalTy: + // SQL supports arbitary precision decimal type. For now the type system + // returns a double + return Type::getDoubleTy(ctx_); + case kStringTy: + return Type::getInt8PtrTy(ctx_); + } +} +} http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.h ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.h b/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.h new file mode 100644 index 0000000..7e4b88f --- /dev/null +++ b/external/sql/storm-sql-core/src/native/lib/compiler/typesystem.h @@ -0,0 +1,54 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef STORM_SQL_COMPILER_TYPESYSTEM_H_ +#define STORM_SQL_COMPILER_TYPESYSTEM_H_ + +#include <json11/json11.hpp> +#include <llvm/IR/Type.h> + +#include <map> +#include <memory> +#include <vector> + +namespace stormsql { + +class Table { +public: + typedef std::pair<std::string, llvm::Type *> Field; + explicit Table(std::vector<Field> &&fields); + const std::vector<Field> &fields() const { return fields_; } + +private: + std::vector<Field> fields_; +}; + +class TypeSystem { +public: + enum SqlType { kIntegerTy, kDecimalTy, kBooleanTy, kStringTy }; + explicit TypeSystem(llvm::LLVMContext *ctx); + llvm::Type *GetLLVMType(const json11::Json &type); + static SqlType GetSqlTypeId(const json11::Json &type); + +private: + llvm::LLVMContext &ctx_; + static const std::map<std::string, SqlType> sql_type_map_; +}; +} + +#endif http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/test/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/test/CMakeLists.txt b/external/sql/storm-sql-core/src/native/test/CMakeLists.txt new file mode 100644 index 0000000..56cf46f --- /dev/null +++ b/external/sql/storm-sql-core/src/native/test/CMakeLists.txt @@ -0,0 +1,18 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +add_subdirectory(compiler) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/test/compiler/CMakeLists.txt ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/test/compiler/CMakeLists.txt b/external/sql/storm-sql-core/src/native/test/compiler/CMakeLists.txt new file mode 100644 index 0000000..4fd24b4 --- /dev/null +++ b/external/sql/storm-sql-core/src/native/test/compiler/CMakeLists.txt @@ -0,0 +1,23 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LLVM_CXXFLAGS}") +set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} ${LLVM_LDFLAGS}") +add_executable(expr_compiler_test expr_compiler_test.cc) +target_link_libraries(expr_compiler_test compiler json11 gmock_main ${LLVM_LIBRARIES} ${LLVM_SYSTEM_LIBRARIES}) +add_test(expr_compiler expr_compiler_test) http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/native/test/compiler/expr_compiler_test.cc ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/native/test/compiler/expr_compiler_test.cc b/external/sql/storm-sql-core/src/native/test/compiler/expr_compiler_test.cc new file mode 100644 index 0000000..cbf5393 --- /dev/null +++ b/external/sql/storm-sql-core/src/native/test/compiler/expr_compiler_test.cc @@ -0,0 +1,90 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "compiler/typesystem.h" +#include "compiler/expr_compiler.h" + +#include <llvm/IR/Constants.h> +#include <llvm/IR/DerivedTypes.h> +#include <llvm/IR/Function.h> +#include <llvm/IR/Module.h> + +#include <gtest/gtest.h> +#include <memory> + +using llvm::dyn_cast; +using llvm::APFloat; +using llvm::BasicBlock; +using llvm::ConstantDataSequential; +using llvm::ConstantInt; +using llvm::ConstantFP; +using llvm::Function; +using llvm::FunctionType; +using llvm::LLVMContext; +using llvm::Module; +using llvm::SMDiagnostic; +using llvm::Type; +using llvm::Value; +using json11::Json; +using std::map; +using std::string; +using std::to_string; +using std::unique_ptr; + +using namespace stormsql; + +static inline Json GetLiteral(const string &type, const string &value) { + map<string, Json> v({{"inst", "literal"}, {"value", value}}); + map<string, Json> r({{"type", type}, {"value", Json(v)}}); + return Json(r); +} +static inline Json LiteralBool(bool v) { + return GetLiteral("BOOLEAN", v ? "true" : "false"); +} +static inline Json LiteralInt(int v) { + return GetLiteral("INTEGER", to_string(v)); +} +static inline Json LiteralDouble(double v) { + return GetLiteral("DECIMAL", to_string(v)); +} +static inline Json LiteralString(const string &v) { + return GetLiteral("CHAR", v); +} + +TEST(TestExprCompiler, TestLiteral) { + LLVMContext ctx; + unique_ptr<BasicBlock> BB(BasicBlock::Create(ctx)); + TypeSystem ts(&ctx); + ExprCompiler compiler("TestLiteral", &ts); + Value *v = compiler.Visit(LiteralBool(1)); + ConstantInt *CI = dyn_cast<ConstantInt>(v); + ASSERT_TRUE(CI && CI == ConstantInt::getTrue(CI->getType())); + + v = compiler.Visit(LiteralInt(1)); + CI = dyn_cast<ConstantInt>(v); + ASSERT_TRUE(CI && CI->getValue() == 1); + + v = compiler.Visit(LiteralDouble(1.0)); + ConstantFP *CF = dyn_cast<ConstantFP>(v); + ASSERT_TRUE(CF && + CF->getValueAPF().compare(APFloat(1.0)) == APFloat::cmpEqual); + + v = compiler.Visit(LiteralString("foo")); + ConstantDataSequential *CDS = dyn_cast<ConstantDataSequential>(v); + ASSERT_TRUE(CDS && CDS->getAsCString() == "foo"); +} http://git-wip-us.apache.org/repos/asf/storm/blob/df69f3dd/external/sql/storm-sql-core/src/test/org/apache/storm/sql/compiler/TestCalcitePlanSerializer.java ---------------------------------------------------------------------- diff --git a/external/sql/storm-sql-core/src/test/org/apache/storm/sql/compiler/TestCalcitePlanSerializer.java b/external/sql/storm-sql-core/src/test/org/apache/storm/sql/compiler/TestCalcitePlanSerializer.java index a40b283..d82476c 100644 --- a/external/sql/storm-sql-core/src/test/org/apache/storm/sql/compiler/TestCalcitePlanSerializer.java +++ b/external/sql/storm-sql-core/src/test/org/apache/storm/sql/compiler/TestCalcitePlanSerializer.java @@ -6,9 +6,9 @@ * to you under the Apache License, Version 2.0 (the * "License"); you may not use this file except in compliance * with the License. You may obtain a copy of the License at - * <p> + * <p/> * http://www.apache.org/licenses/LICENSE-2.0 - * <p> + * <p/> * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. @@ -22,44 +22,100 @@ import org.apache.calcite.rel.RelNode; import org.apache.calcite.schema.SchemaPlus; import org.apache.calcite.schema.Table; import org.apache.calcite.sql.SqlNode; +import org.apache.calcite.sql.parser.SqlParseException; import org.apache.calcite.sql.type.SqlTypeName; import org.apache.calcite.tools.FrameworkConfig; import org.apache.calcite.tools.Frameworks; import org.apache.calcite.tools.Planner; +import org.apache.calcite.tools.RelConversionException; +import org.apache.calcite.tools.ValidationException; import org.junit.Test; import java.util.HashMap; import java.util.List; import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertNotNull; public class TestCalcitePlanSerializer { @Test @SuppressWarnings("unchecked") - public void testSerializeTableSchema() throws Exception { + public void testTableSchema() throws Exception { + String sql = "SELECT 1 FROM FOO"; + CalciteState state = sqlOverDummyTable(sql); + String res = new CalcitePlanSerializer(state.schema, state.tree).toJson(); + + ObjectMapper m = new ObjectMapper(); + HashMap<String, Object> o = m.readValue(res, HashMap.class); + List<HashMap<String, Object>> tables = asList(o.get("tables")); + HashMap<String, Object> t = tables.get(0); + assertEquals("FOO", t.get("name")); + List<HashMap<String, Object>> fields = asList(t.get("fields")); + assertEquals(1, fields.size()); + HashMap<String, Object> field = fields.get(0); + assertEquals("ID", field.get("name")); + assertEquals("INTEGER", field.get("type")); + } + + @Test + @SuppressWarnings("unchecked") + public void testLiteral() throws Exception { + String sql = "SELECT 1,1.0,TRUE,'FOO' FROM FOO"; + CalciteState state = sqlOverDummyTable(sql); + String res = new CalcitePlanSerializer(state.schema, state.tree).toJson(); + + ObjectMapper m = new ObjectMapper(); + HashMap<String, Object> o = m.readValue(res, HashMap.class); + List<HashMap<String, Object>> stages = asList(o.get("stages")); + HashMap<String, Object> project = null; + for (HashMap<String, Object> s : stages) { + if ("LogicalProject".equals(s.get("type"))) { + project = s; + break; + } + } + assertNotNull(project); + List<HashMap<String, Object>> exprs = asList(project.get("exprs")); + assertEquals(4, exprs.size()); + checkLiteral("INTEGER", Integer.toString(1), exprs.get(0)); + } + + private static class CalciteState { + private final SchemaPlus schema; + private final RelNode tree; + + private CalciteState(SchemaPlus schema, RelNode tree) { + this.schema = schema; + this.tree = tree; + } + } + + @SuppressWarnings("unchecked") + private List<HashMap<String, Object>> asList(Object p) { + return (List<HashMap<String, Object>>) p; + } + + private CalciteState sqlOverDummyTable(String sql) + throws RelConversionException, ValidationException, SqlParseException { SchemaPlus schema = Frameworks.createRootSchema(true); Table table = TestUtils.newTable().field("ID", SqlTypeName.INTEGER).build(); schema.add("FOO", table); FrameworkConfig config = Frameworks.newConfigBuilder().defaultSchema( schema).build(); Planner planner = Frameworks.getPlanner(config); - String sql = "SELECT 1 + 2 FROM FOO WHERE 5 > 3"; SqlNode parse = planner.parse(sql); SqlNode validate = planner.validate(parse); RelNode tree = planner.convert(validate); - String res = new CalcitePlanSerializer(schema, tree).toJson(); + return new CalciteState(schema, tree); + } - ObjectMapper m = new ObjectMapper(); - HashMap<String, Object> o = m.readValue(res, HashMap.class); - List<HashMap<String, Object>> tables = (List<HashMap<String, Object>>) o.get( - "tables"); - HashMap<String, Object> t = tables.get(0); - assertEquals("FOO", t.get("name")); - List<HashMap<String, Object>> fields = (List<HashMap<String, Object>>) t.get( - "fields"); - assertEquals(1, fields.size()); - HashMap<String, Object> field = fields.get(0); - assertEquals("ID", field.get("name")); - assertEquals("INTEGER", field.get("type")); + @SuppressWarnings("unchecked") + private void checkLiteral(String type, String value, Object l) { + HashMap<String, Object> e = (HashMap<String, Object>) ((HashMap<String, Object>) l).get( + "expr"); + assertEquals(type, e.get("type")); + HashMap<String, Object> v = (HashMap<String, Object>) e.get("value"); + assertEquals("literal", v.get("inst")); + assertEquals(value, v.get("value")); } }