Skip to content

Commit

Permalink
Merge branch 'main' into fix.128.support
Browse files Browse the repository at this point in the history
  • Loading branch information
dawa79 authored Oct 24, 2024
2 parents 5185f6c + d89e27e commit beb0c46
Show file tree
Hide file tree
Showing 213 changed files with 11,777 additions and 8,560 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ jobs:
if: ${{ always() }}
run: |
nix log .#hobbesPackages/gcc-${{ matrix.gcc }}/llvm-${{ matrix.llvm }}/hobbes &> ${{ matrix.os }}-gcc-${{ matrix.gcc }}-llvm-${{ matrix.llvm }}-hobbes.log
- name: upload log ${{ matrix.os }}-gcc-${{ matrix.gcc }}-llvm-${{ matrix.gitllvm }}-hobbes.log
- name: upload log ${{ matrix.os }}-gcc-${{ matrix.gcc }}-llvm-${{ matrix.llvm }}-hobbes.log
if: ${{ always() }}
uses: actions/upload-artifact@v3
with:
Expand Down
76 changes: 76 additions & 0 deletions .gitlab-ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
# This file is a template, and might need editing before it works on your project.
# To contribute improvements to CI/CD templates, please follow the Development guide at:
# https://docs.gitlab.com/ee/development/cicd/templates.html
# This specific template is located at:
# https://gitlab.com/gitlab-org/gitlab/-/blob/master/lib/gitlab/ci/templates/Getting-Started.gitlab-ci.yml

# This is a sample GitLab CI/CD configuration file that should run without any modifications.
# It demonstrates a basic 3 stage CI/CD pipeline. Instead of real tests or scripts,
# it uses echo commands to simulate the pipeline execution.
#
# A pipeline is composed of independent jobs that run scripts, grouped into stages.
# Stages run in sequential order, but jobs within stages run in parallel.
#
# For more information, see: https://docs.gitlab.com/ee/ci/yaml/README.html#stages
image: nixpkgs/nix-flakes:latest
stages: # List of stages for jobs, and their order of execution
- build
- test
- deploy

build-job-gcc10-llvm11: # This job runs in the build stage, which runs first.
stage: build
script:
- echo "Compiling the code..."
- nix build .#hobbesPackages/gcc-10/llvm-11/hobbes
- echo "Compile complete."
after_script:
- echo "nix log .#hobbesPackages/gcc-10/llvm-11/hobbes..."
- mkdir -pv log-job-gcc10-llvm11
- nix log .#hobbesPackages/gcc-10/llvm-11/hobbes > log-job-gcc10-llvm11/nix.log
- echo "nix log .#hobbesPackages/gcc-10/llvm-11/hobbes complete."
artifacts:
name: "$CI_COMMIT_REF_SLUG"
paths:
- log-job-gcc10-llvm11/
expire_in: 1 week
when: always

build-job-clang11: # This job runs in the build stage, which runs first.
stage: build
script:
- mkdir -pv log-clang-11
- echo "Compiling the code..."
- nix build .#hobbesPackages/clang-11/hobbes; nix log .#hobbesPackages/clang-11/hobbes > log-job-clang-11/nix.log
- echo "Compile complete."
after_script:
- echo "nix log .#hobbesPackages/clang-11/hobbes..."
- mkdir -pv log-job-clang-11
- nix log .#hobbesPackages/clang-11/hobbes > log-job-clang-11/nix.log
- echo "nix log .#hobbesPackages/clang-11/hobbes complete."
artifacts:
name: "$CI_COMMIT_REF_SLUG"
paths:
- log-job-clang-11/
expire_in: 1 week
when: always

unit-test-job-gcc: # This job runs in the test stage.
stage: test # It only starts when the job in the build stage completes successfully.
script:
- echo "Running unit tests... This will take about 60 seconds."
- sleep 60
- echo "Code coverage is 90%"

lint-test-job: # This job also runs in the test stage.
stage: test # It can run at the same time as unit-test-job (in parallel).
script:
- echo "Linting code... This will take about 10 seconds."
- sleep 10
- echo "No lint issues found."

deploy-job: # This job runs in the deploy stage.
stage: deploy # It only runs when *both* jobs in the test stage complete successfully.
script:
- echo "Deploying application..."
- echo "Application successfully deployed."
31 changes: 22 additions & 9 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -14,22 +14,21 @@ find_package(Curses REQUIRED)
include_directories(${CURSES_INCLUDE_DIRS})

find_package(LLVM REQUIRED CONFIG)
include_directories(${LLVM_INCLUDE_DIRS})
include_directories(SYSTEM ${LLVM_INCLUDE_DIRS})
add_definitions(${LLVM_DEFINITIONS})

if (${LLVM_PACKAGE_VERSION} VERSION_LESS "10.0")
set(CMAKE_CXX_STANDARD 11)
else()
set(CMAKE_CXX_STANDARD 14)
endif()
set(CMAKE_CXX_STANDARD 14)

if (${LLVM_PACKAGE_VERSION} VERSION_LESS "3.6")
set(jit_lib jit)
else()
elseif(${LLVM_PACKAGE_VERSION} VERSION_LESS "11.0")
set(jit_lib mcjit)
else()
set(jit_lib mcjit orcjit)
endif()

find_program(llvm-config llvm-config PATHS ${LLVM_TOOLS_BINARY_DIR})
find_program(llvm-config llvm-config PATHS ${LLVM_TOOLS_BINARY_DIR} NO_DEFAULT_PATH)
find_program(llvm-config llvm-config)
if (${LLVM_PACKAGE_VERSION} VERSION_LESS "4.0")
execute_process(COMMAND ${llvm-config} --libs x86 ipo ${jit_lib}
OUTPUT_VARIABLE llvm_libs
Expand Down Expand Up @@ -82,6 +81,19 @@ set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${cxx_flags}")
set(CMAKE_CXX_FLAGS_DEBUG "-g")
set(CMAKE_CXX_FLAGS_RELEASE "-O2")

option(USE_ASAN_UBSAN "Use address,undefined sanitizers" OFF)
if(USE_ASAN_AND_UBSAN)
# _FORTIFY_SOURCE doesn't play well with asan
# https://github.com/google/sanitizers/issues/247
add_definitions(-U_FORTIFY_SOURCE)
add_compile_options("-fno-omit-frame-pointer;-fsanitize=address,undefined;-fno-optimize-sibling-calls;-fno-sanitize-recover=all")
add_link_options("-fsanitize=address,undefined;-fno-optimize-sibling-calls;-fno-sanitize-recover=all")
add_compile_options("$<$<OR:$<CXX_COMPILER_ID:Clang>,$<CXX_COMPILER_ID:AppleClang>>:-fsanitize=local-bounds,float-divide-by-zero,nullability,signed-integer-overflow,shift,integer-divide-by-zero>")
add_link_options("$<$<OR:$<CXX_COMPILER_ID:Clang>,$<CXX_COMPILER_ID:AppleClang>>:-fsanitize=local-bounds,float-divide-by-zero,nullability,signed-integer-overflow,shift,integer-divide-by-zero>")
add_compile_options("$<$<CXX_COMPILER_ID:GNU>:--param=max-vartrack-size=60000000>")
message(STATUS "address and undefined sanitizers enabled")
endif()

add_library(hobbes STATIC ${lib_files})
target_link_libraries(hobbes PUBLIC ${llvm_ldflags} ${llvm_libs} ${ZLIB_LIBRARIES} ${CURSES_LIBRARIES} ${sys_libs})
add_library(hobbes-pic STATIC ${lib_files})
Expand All @@ -94,10 +106,11 @@ add_executable(hog ${hog_files})
target_link_libraries(hog PRIVATE hobbes)

enable_testing()
add_executable(mock-proc test/mocks/proc.C)
add_executable(hobbes-test ${test_files})
target_link_libraries(hobbes-test PRIVATE hobbes)
add_test(hobbes-test hobbes-test)
include(FindPythonInterp)
find_package(PythonInterp 2.7 REQUIRED)
set_property(TARGET hobbes-test PROPERTY COMPILE_FLAGS "-DPYTHON_EXECUTABLE=\"${PYTHON_EXECUTABLE}\" -DSCRIPT_DIR=\"${CMAKE_SOURCE_DIR}/scripts/\"")

install(TARGETS hobbes hobbes-pic DESTINATION "lib")
Expand Down
18 changes: 7 additions & 11 deletions bin/hi/cio.H
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@
namespace hi {

// controls display options
typedef unsigned char color;
using color = unsigned char;

DEFINE_STRUCT(ConsoleColors,
(color, promptfg),
Expand Down Expand Up @@ -62,13 +62,13 @@ inline void sendCmd(std::ostream& out, int n0, int n1, int n2, char c) {
}
}

struct setbold { setbold() { } };
struct setbold {};
inline std::ostream& operator<<(std::ostream& lhs, const setbold&) {
sendCmd(lhs, 1, 'm');
return lhs;
}

struct setunderline { setunderline() { } };
struct setunderline {};
inline std::ostream& operator<<(std::ostream& lhs, const setunderline&) {
sendCmd(lhs, 4, 'm');
return lhs;
Expand Down Expand Up @@ -103,18 +103,14 @@ inline std::ostream& operator<<(std::ostream& lhs, const setbgc& c) {
return lhs;
}

struct resetfmt {
resetfmt() { }
};
struct resetfmt {};

inline std::ostream& operator<<(std::ostream& lhs, const resetfmt&) {
sendCmd(lhs, 0, 'm');
return lhs;
}

struct clearscr {
clearscr() { }
};
struct clearscr {};

inline std::ostream& operator<<(std::ostream& lhs, const clearscr&) {
sendCmd(lhs, 2, 'J');
Expand Down Expand Up @@ -151,13 +147,13 @@ inline std::ostream& operator<<(std::ostream& lhs, const movecursor& mc) {
return lhs;
}

struct eraseToEOL { eraseToEOL() { } };
struct eraseToEOL {};
inline std::ostream& operator<<(std::ostream& lhs, const eraseToEOL&) {
sendCmd(lhs, 0, 'K');
return lhs;
}

struct clearline { clearline() { } };
struct clearline {};
inline std::ostream& operator<<(std::ostream& lhs, const clearline&) {
sendCmd(lhs, 2, 'K');
return lhs;
Expand Down
61 changes: 39 additions & 22 deletions bin/hi/evaluator.C
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,27 @@
#include "funcdefs.H"
#include "cio.H"

#include <hobbes/eval/cmodule.H>
#include <hobbes/lang/preds/class.H>
#include <hobbes/db/file.H>
#include <hobbes/eval/cmodule.H>
#include <hobbes/ipc/net.H>
#include <hobbes/lang/preds/class.H>
#include <hobbes/util/perf.H>
#include <hobbes/util/str.H>
#include <hobbes/util/time.H>
#include <iostream>
#include <memory>

namespace {
void defPrintUnreachableMatches(const hobbes::cc::UnreachableMatches& m) {
std::cout << "warning: " << m.la.filename() << ':' << m.la.lineDesc() << " " << m.lines << std::endl;
}
} // namespace

namespace hi {

// allocate a string in global memory
hobbes::array<char>* allocGlobalStr(const char* x, size_t len) {
hobbes::array<char>* r = reinterpret_cast<hobbes::array<char>*>(malloc(sizeof(long) + len * sizeof(char)));
auto* r = reinterpret_cast<hobbes::array<char>*>(malloc(sizeof(long) + len * sizeof(char)));
memcpy(r->data, x, len * sizeof(char));
r->size = len;
return r;
Expand All @@ -30,12 +37,12 @@ void bindArguments(hobbes::cc& ctx, const Args::NameVals& args) {
// type-level binding, for [("foo", "bar"), ...]:
// class Argument a b | a -> b
// instance Argument "foo" "bar"
TClass* tc = new TClass("Argument", 2, TClass::Members(), list(FunDep(list(0), 1)), LexicalAnnotation::null());
auto* tc = new TClass("Argument", 2, TClass::Members(), list(FunDep(list(0), 1)), LexicalAnnotation::null());
Definitions drainDefs;
for (const auto& arg : args) {
tc->insert(
ctx.typeEnv(),
TCInstancePtr(new TCInstance("Argument", list(MonoTypePtr(TString::make(arg.first)), MonoTypePtr(TString::make(arg.second))), MemberMapping(), LexicalAnnotation::null())),
std::make_shared<TCInstance>("Argument", list(MonoTypePtr(TString::make(arg.first)), MonoTypePtr(TString::make(arg.second))), MemberMapping(), LexicalAnnotation::null()),
&drainDefs
);
}
Expand All @@ -45,12 +52,12 @@ void bindArguments(hobbes::cc& ctx, const Args::NameVals& args) {
// value-level binding
// arguments :: [[char]*[char]]
// arguments = [("foo", "bar"), ...]
typedef std::pair<array<char>*, array<char>*> StrPair;
typedef array<StrPair> StrPairs;
using StrPair = std::pair<array<char> *, array<char> *>;
using StrPairs = array<StrPair>;

StrPairs* arguments = reinterpret_cast<StrPairs*>(malloc(sizeof(long) + args.size() * sizeof(StrPair)));
auto* arguments = reinterpret_cast<StrPairs*>(malloc(sizeof(long) + args.size() * sizeof(StrPair)));
arguments->size = 0;
for (auto arg : args) {
for (const auto& arg : args) {
arguments->data[arguments->size].first = allocGlobalStr(arg.first);
arguments->data[arguments->size].second = allocGlobalStr(arg.second);
++arguments->size;
Expand All @@ -59,17 +66,23 @@ void bindArguments(hobbes::cc& ctx, const Args::NameVals& args) {
}

// set up the evaluation environment for our cc
evaluator::evaluator(const Args& args) : silent(args.silent), wwwd(0), opts(args.opts) {
evaluator::evaluator(const Args& args) : silent(args.silent), wwwd(nullptr), opts(args.opts) {
using namespace hobbes;

bindArguments(this->ctx, args.scriptNameVals);
bindHiDefs(this->ctx);

const bool ignoreUM = (std::find(opts.cbegin(), opts.cend(), std::string("IgnoreUnreachableMatches")) != opts.cend());
this->ctx.ignoreUnreachableMatches(ignoreUM);
if (ignoreUM) {
this->ctx.setGatherUnreachableMatchesFn(defPrintUnreachableMatches);
}

// start alternate input services if necessary
if (args.replPort > 0) {
installNetREPL(args.replPort, &this->ctx, [this](ExprPtr const& e) -> ExprPtr { return hobbes::translateExprWithOpts(this->opts, e); });
}

if (args.httpdPort > 0) {
// run a local web server (for diagnostics and alternate queries) if requested
this->wwwd = new WWWServer(args.httpdPort, &this->ctx);
Expand All @@ -81,7 +94,7 @@ evaluator::~evaluator() {
}

bool hiddenFileName(const std::string& fname) {
return fname.size() == 0 || fname[0] == '.';
return fname.empty() || fname[0] == '.';
}

bool loadSilently(const std::string& mfile) {
Expand All @@ -94,7 +107,7 @@ void evaluator::runMachineREPL() {

void evaluator::showClass(const std::string& cname) {
hobbes::UnqualifierPtr uq = this->ctx.typeEnv()->lookupUnqualifier(cname);
if (const hobbes::TClass* c = dynamic_cast<const hobbes::TClass*>(uq.get())) {
if (const auto* c = dynamic_cast<const hobbes::TClass*>(uq.get())) {
c->show(std::cout);
} else {
throw std::runtime_error("Undefined type class: " + cname);
Expand All @@ -103,11 +116,11 @@ void evaluator::showClass(const std::string& cname) {

void evaluator::showInstances(const std::string& cname) {
hobbes::UnqualifierPtr uq = this->ctx.typeEnv()->lookupUnqualifier(cname);
if (const hobbes::TClass* c = dynamic_cast<const hobbes::TClass*>(uq.get())) {
for (auto i : c->instances()) {
if (const auto* c = dynamic_cast<const hobbes::TClass*>(uq.get())) {
for (const auto& i : c->instances()) {
i->show(std::cout);
}
for (auto i : c->instanceFns()) {
for (const auto& i : c->instanceFns()) {
i->show(std::cout);
}
} else {
Expand Down Expand Up @@ -158,7 +171,7 @@ void printConstraint(const hobbes::ConstraintPtr& c) {
}

void printQualType(const hobbes::Constraints& cs, const hobbes::MonoTypePtr& ty) {
if (cs.size() > 0) {
if (!cs.empty()) {
printConstraint(cs[0]);
for (size_t i = 1; i < cs.size(); ++i) {
std::cout << setfgc(colors.stdtextfg) << ", ";
Expand Down Expand Up @@ -192,7 +205,7 @@ void evaluator::printTypeEnv() {
}

hobbes::str::seq evaluator::completionsFor(const std::string& prefix) const {
if (prefix.size() == 0) {
if (prefix.empty()) {
return hobbes::str::seq();
} else {
hobbes::str::seq vars;
Expand Down Expand Up @@ -220,13 +233,13 @@ void evaluator::printAssembly(const std::string& expr, void (*f)(void*,size_t))
}

void evaluator::perfTestExpr(const std::string& expr) {
typedef void (*pvthunk)();
using pvthunk = void (*)();
pvthunk f = this->ctx.compileFn<void()>(readExpr("let x = (" + expr + ") in ()"));
f();

const size_t numRuns = 1000;
unsigned long nsCSum = 0;
unsigned long nsCMin = static_cast<unsigned long>(-1);
auto nsCMin = static_cast<unsigned long>(-1);
unsigned long nsCMax = 0;

for (size_t i = 0; i < numRuns; ++i) {
Expand All @@ -253,7 +266,7 @@ void evaluator::breakdownEvalExpr(const std::string& expr) {
long ust = hobbes::tick() - t0;

t0 = hobbes::tick();
typedef void (*pvthunk)();
using pvthunk = void (*)();
pvthunk f = this->ctx.compileFn<void()>(e);
long ct = hobbes::tick() - t0;

Expand Down Expand Up @@ -283,7 +296,7 @@ bool evaluator::satisfied(const hobbes::ConstraintPtr& c) {
}

void showSearchResults(const std::string&, const hobbes::SearchEntries& ses) {
if (ses.size() > 0) {
if (!ses.empty()) {
std::map<std::string, std::string> stbl;
for (const auto& se : ses) {
stbl[se.sym] = hobbes::show(se.ty);
Expand Down Expand Up @@ -314,6 +327,10 @@ void evaluator::searchDefs(const std::string& expr_to_type) {

void evaluator::setOption(const std::string& o) {
this->opts.push_back(o);
if (o == "IgnoreUnreachableMatches") {
this->ctx.ignoreUnreachableMatches(true);
this->ctx.setGatherUnreachableMatchesFn(defPrintUnreachableMatches);
}
}

hobbes::ExprPtr evaluator::readExpr(const std::string& x) {
Expand Down
Loading

0 comments on commit beb0c46

Please sign in to comment.