diff --git a/.aspect/cli/config.yml b/.aspect/cli/config.yml new file mode 100644 index 00000000..f1bf7adb --- /dev/null +++ b/.aspect/cli/config.yml @@ -0,0 +1,4 @@ +lint: + aspects: + - //tools/bazel:lint.bzl%ruff + - //tools/bazel:lint.bzl%clang_tidy diff --git a/.bazeliskrc b/.bazeliskrc new file mode 100644 index 00000000..897c6dfd --- /dev/null +++ b/.bazeliskrc @@ -0,0 +1,2 @@ +BAZELISK_BASE_URL=https://static.aspect.build/aspect +USE_BAZEL_VERSION=aspect/2025.06.52 diff --git a/.clang-tidy b/.clang-tidy index 1d664e14..ec5061b6 100644 --- a/.clang-tidy +++ b/.clang-tidy @@ -1,33 +1,53 @@ -Checks: 'clang-diagnostic-*,clang-analyzer-*,cppcoreguidelines-*,modernize-*,-modernize-use-trailing-return-type' +# .clang-tidy + +# Enable broad sets, disable one modernize check explicitly. +Checks: > + clang-diagnostic-*, + clang-analyzer-*, + cppcoreguidelines-*, + modernize-*, + -modernize-use-trailing-return-type + +# Lint everything. Set a regex (e.g. ^src/|^include/) to scope. HeaderFilterRegex: '' -AnalyzeTemporaryDtors: false -FormatStyle: google + +# Use clang-format's "google" style when auto-fixing. +FormatStyle: google + +# Per-check options, grouped for readability. CheckOptions: - - key: cert-dcl16-c.NewSuffixes - value: 'L;LL;LU;LLU' - - key: cert-oop54-cpp.WarnOnlyIfThisHasSuspiciousField - value: '0' - - key: cppcoreguidelines-explicit-virtual-functions.IgnoreDestructors - value: '1' - - key: cppcoreguidelines-non-private-member-variables-in-classes.IgnoreClassesWithAllMemberVariablesBeingPublic - value: '1' - - key: google-readability-braces-around-statements.ShortStatementLines - value: '1' - - key: google-readability-function-size.StatementThreshold - value: '800' - - key: google-readability-namespace-comments.ShortNamespaceLines - value: '10' - - key: google-readability-namespace-comments.SpacesBeforeComments - value: '2' - - key: modernize-loop-convert.MaxCopySize - value: '16' - - key: modernize-loop-convert.MinConfidence - value: reasonable - - key: modernize-loop-convert.NamingStyle - value: CamelCase - - key: modernize-pass-by-value.IncludeStyle - value: llvm - - key: modernize-replace-auto-ptr.IncludeStyle - value: llvm - - key: modernize-use-nullptr.NullMacros - value: 'NULL' + # --- CERT --- + - key: cert-dcl16-c.NewSuffixes + value: 'L;LL;LU;LLU' + - key: cert-oop54-cpp.WarnOnlyIfThisHasSuspiciousField + value: '0' + + # --- CppCoreGuidelines --- + - key: cppcoreguidelines-explicit-virtual-functions.IgnoreDestructors + value: '1' + - key: cppcoreguidelines-non-private-member-variables-in-classes.IgnoreClassesWithAllMemberVariablesBeingPublic + value: '1' + + # --- Google Readability --- + - key: google-readability-braces-around-statements.ShortStatementLines + value: '1' + - key: google-readability-function-size.StatementThreshold + value: '800' + - key: google-readability-namespace-comments.ShortNamespaceLines + value: '10' + - key: google-readability-namespace-comments.SpacesBeforeComments + value: '2' + + # --- Modernize --- + - key: modernize-loop-convert.MaxCopySize + value: '16' + - key: modernize-loop-convert.MinConfidence + value: 'reasonable' + - key: modernize-loop-convert.NamingStyle + value: 'CamelCase' + - key: modernize-pass-by-value.IncludeStyle + value: 'llvm' + - key: modernize-replace-auto-ptr.IncludeStyle + value: 'llvm' + - key: modernize-use-nullptr.NullMacros + value: 'NULL' diff --git a/.flake8 b/.flake8 deleted file mode 100644 index 5daec749..00000000 --- a/.flake8 +++ /dev/null @@ -1,24 +0,0 @@ -[flake8] - -### Rules ### -# F401 - module imported but unused -# F403 - ‘from module import *’ used; unable to detect undefined names -exclude = - __init__.py::F401,F403 - -# E124 - closing bracket does not match visual indentation -ignore = - E124 - - -### File patterns ### -exclude = - .git, - __pycache__ - -filename = - *.py - -### Options ### -max-line-length = 150 -max-doc-length = 150 \ No newline at end of file diff --git a/.github/Dockerfile b/.github/Dockerfile new file mode 100644 index 00000000..9dc0cbed --- /dev/null +++ b/.github/Dockerfile @@ -0,0 +1,21 @@ +FROM debian:latest + +ARG USER=ci +ARG BAZELISK_TAG=v1.19.0 + +RUN apt-get update && apt-get install -y --no-install-recommends \ + ca-certificates curl git \ + build-essential gcc g++ \ + clang lld ninja-build sudo \ + python3 \ + && rm -rf /var/lib/apt/lists/* + +RUN curl -fsSL -o /usr/local/bin/bazelisk \ + "https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64" \ + && chmod 0755 /usr/local/bin/bazelisk \ + && ln -s /usr/local/bin/bazelisk /usr/local/bin/bazel + +RUN useradd -m ${USER} \ + && echo "${USER} ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers + +WORKDIR /home/${USER}/workspace diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 00000000..ca79ca5b --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,6 @@ +version: 2 +updates: + - package-ecosystem: github-actions + directory: / + schedule: + interval: weekly diff --git a/images/logo.png b/.github/images/logo.png similarity index 100% rename from images/logo.png rename to .github/images/logo.png diff --git a/.github/images/logo_dark.png b/.github/images/logo_dark.png new file mode 100644 index 00000000..deecfc02 Binary files /dev/null and b/.github/images/logo_dark.png differ diff --git a/images/screenshot.png b/.github/images/screenshot.png similarity index 100% rename from images/screenshot.png rename to .github/images/screenshot.png diff --git a/.github/workflows/distro-ci.yml b/.github/workflows/distro-ci.yml deleted file mode 100644 index d7860526..00000000 --- a/.github/workflows/distro-ci.yml +++ /dev/null @@ -1,51 +0,0 @@ -name: HyperCPU CI/CD Pipeline (build HyperCPU on different platforms) - -on: - pull_request: - branches: - - master - -permissions: - contents: read - -jobs: - build: - runs-on: ubuntu-latest - container: - image: hyperwin/hcpu-ci:${{ matrix.config.tag }} - # see https://github.com/bazelbuild/bazel/issues/13823 - options: --init - name: "Build on ${{matrix.config.name}}" - strategy: - matrix: - config: - - tag: fedora - name: Fedora - - tag: debian-stable - name: Debian Stable - - tag: debian-unstable - name: Debian Unstable - - tag: archlinux - name: Arch Linux - - tag: gentoo-glibc - name: Gentoo GLibc -# - tag: gentoo-musl -# name: Gentoo Musl -# - tag: alpine -# name: Alpine - - tag: ubuntu - name: Ubuntu - - steps: - - run: | - set -e - DISTRO=$( cat /etc/*-release | tr [:upper:] [:lower:] | grep -Poi '(debian|ubuntu|fedora|gentoo|alpine)' | uniq ) - if [ "$DISTRO" == "gentoo" ]; then - source /etc/profile - fi - git clone https://github.com/${{ github.event.pull_request.head.repo.full_name }}.git && cd HyperCPU - git checkout ${{ github.event.pull_request.head.sha }} - git submodule update --init --recursive - - conan profile detect && conan install . --build=cmake --build=missing - bazelisk build //src/... //tests/... --config=linux-opt diff --git a/.github/workflows/docker-autobuild.yml b/.github/workflows/docker-autobuild.yml deleted file mode 100644 index db5b838e..00000000 --- a/.github/workflows/docker-autobuild.yml +++ /dev/null @@ -1,104 +0,0 @@ -name: HyperCPU CI/CD Pipeline (update Docker images) - -on: - schedule: - - cron: "0 0 */7 * *" - push: - paths: - - 'docker/**' - -permissions: - contents: read - -jobs: - build: - runs-on: ubuntu-latest - name: "Update ${{ matrix.config.name }} Docker image" - strategy: - matrix: - config: - - tag: fedora - name: Fedora - - tag: debian-stable - name: Debian Stable - - tag: debian-unstable - name: Debian Unstable - - tag: archlinux - name: Arch Linux - - tag: gentoo-glibc - name: Gentoo GLibc - - tag: alpine - name: Alpine - - tag: ubuntu - name: Ubuntu - - steps: - - name: Install Docker Buildx - uses: docker/setup-buildx-action@v3 - - - name: Login to DockerHub - uses: docker/login-action@v3 - with: - username: hyperwin - password: ${{ secrets.DOCKERHUB_PASSWORD }} - - - name: Checkout repository - uses: actions/checkout@v4 - with: - fetch-depth: 2 - submodules: true - - - name: Build and push - uses: docker/build-push-action@v6 - with: - context: "{{ defaultContext }}:docker/${{ matrix.config.tag }}" - push: true - tags: hyperwin/hcpu-ci:${{ matrix.config.tag }} - - build-gentoo-musl-stage1: - runs-on: ubuntu-latest - name: "Update Gentoo Musl Docker image - stage 1" - steps: - - name: Login to DockerHub - uses: docker/login-action@v3 - with: - username: hyperwin - password: ${{ secrets.DOCKERHUB_PASSWORD }} - - - name: Checkout repository - uses: actions/checkout@v4 - with: - fetch-depth: 2 - submodules: true - - - name: Build and push - uses: docker/build-push-action@v6 - with: - context: "{{ defaultContext }}:docker/gentoo-musl/stage1" - push: true - tags: hyperwin/hcpu-ci:gentoo-musl-build - - build-gentoo-musl-stage2: - runs-on: ubuntu-latest - name: "Update Gentoo Musl Docker image - stage 2" - needs: build-gentoo-musl-stage1 - steps: - - name: Login to DockerHub - uses: docker/login-action@v3 - with: - username: hyperwin - password: ${{ secrets.DOCKERHUB_PASSWORD }} - - - name: Checkout repository - uses: actions/checkout@v4 - with: - fetch-depth: 2 - submodules: true - - - name: Build and push - uses: docker/build-push-action@v6 - with: - context: "{{ defaultContext }}:docker/gentoo-musl/stage2" - push: true - tags: hyperwin/hcpu-ci:gentoo-musl - diff --git a/.github/workflows/mainline-compile.yml b/.github/workflows/mainline-compile.yml new file mode 100644 index 00000000..0986cd2f --- /dev/null +++ b/.github/workflows/mainline-compile.yml @@ -0,0 +1,52 @@ +name: HyperCPU CI/CD Pipeline (compile project) + +on: + workflow_call: + +jobs: + testing: + name: Compile (${{ matrix.compiler }}) + runs-on: ubuntu-latest + container: + image: ghcr.io/hypercpu-project/hypercpu-builder:latest + options: --init + permissions: + contents: read + packages: read + + strategy: + fail-fast: false + matrix: + compiler: [gcc, clang] + + steps: + - name: Checkout code + uses: actions/checkout@v4 + with: + submodules: true + fetch-depth: 0 + + - name: Cache Bazel + uses: actions/cache@v4 + with: + path: | + ~/.cache/bazel + key: bazel-${{ runner.os }}-${{ matrix.compiler }}-${{ hashFiles('**/*.bazel', '**/*.bzl') }} + restore-keys: | + bazel-${{ runner.os }}-${{ matrix.compiler }}- + bazel-${{ runner.os }}- + + - name: Fix permissions + run: chown -R ci:ci "$GITHUB_WORKSPACE" + + - name: Bazel build (linux-opt mode, with ${{ matrix.compiler }} compiler) + run: sudo -u ci bazelisk build //... --config=linux-opt --compiler=${{ matrix.compiler }} + + - name: Upload package tarball + uses: actions/upload-artifact@v4 + with: + name: hcpu-tarballs-${{ matrix.compiler }} + path: | + bazel-bin/tools/packaging/*.tar.gz + !bazel-bin/tools/packaging/hcpu.tar.gz + if-no-files-found: error diff --git a/.github/workflows/mainline-format.yml b/.github/workflows/mainline-format.yml new file mode 100644 index 00000000..4183bb57 --- /dev/null +++ b/.github/workflows/mainline-format.yml @@ -0,0 +1,27 @@ +name: HyperCPU CI/CD Pipeline (format) + +on: + workflow_call: + +jobs: + format: + runs-on: ubuntu-latest + container: + image: ghcr.io/hypercpu-project/hypercpu-builder:latest + options: --init + permissions: + contents: read + packages: read + + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Fix permissions + run: chown -R ci:ci "$GITHUB_WORKSPACE" + + - name: Run formatters + run: sudo -u ci bazelisk run :format + + - name: Check diff + run: sudo -u ci git diff --quiet diff --git a/.github/workflows/mainline-lint.yml b/.github/workflows/mainline-lint.yml new file mode 100644 index 00000000..17c8d592 --- /dev/null +++ b/.github/workflows/mainline-lint.yml @@ -0,0 +1,28 @@ +name: HyperCPU CI/CD Pipeline (lint) + +on: + workflow_call: + +jobs: + lint: + runs-on: ubuntu-latest + container: + image: ghcr.io/hypercpu-project/hypercpu-builder:latest + options: --init + permissions: + contents: read + packages: read + + steps: + - name: Checkout + uses: actions/checkout@v4 + with: + fetch-depth: 0 + submodules: true + + - name: Fix permissions + run: chown -R ci:ci "$GITHUB_WORKSPACE" + + - name: Run linters + continue-on-error: true + run: sudo -u ci bazelisk lint //src/... --aspect:interactive=false -k --config=linux-dbg diff --git a/.github/workflows/mainline-prepare.yml b/.github/workflows/mainline-prepare.yml new file mode 100644 index 00000000..bf062ee4 --- /dev/null +++ b/.github/workflows/mainline-prepare.yml @@ -0,0 +1,35 @@ +name: Build & Push GHCR HyperCPU Builder Image (prepare environment) + +on: + workflow_call: + +jobs: + build-docker-image: + runs-on: ubuntu-latest + permissions: + contents: read + packages: write + + steps: + - name: Checkout + uses: actions/checkout@v4 + + - name: Log in to GHCR + uses: docker/login-action@v3 + with: + registry: ghcr.io + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Build and push + uses: docker/build-push-action@v6 + with: + context: . + file: .github/Dockerfile + push: true + tags: ghcr.io/hypercpu-project/hypercpu-builder:latest + cache-from: type=gha + cache-to: type=gha,mode=max diff --git a/.github/workflows/mainline-test.yml b/.github/workflows/mainline-test.yml new file mode 100644 index 00000000..b4d0cbb2 --- /dev/null +++ b/.github/workflows/mainline-test.yml @@ -0,0 +1,42 @@ +name: HyperCPU CI/CD Pipeline (install & smoke) + +on: + workflow_call: + inputs: + artifact_name: + type: string + default: "hcpu-tarballs*" + +jobs: + install-and-test: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + include: + - name: Debian + image: debian:stable + - name: Fedora + image: fedora:latest + - name: Arch Linux + image: archlinux:base-devel + + container: + image: ${{ matrix.image }} + + steps: + - name: Download tarball artifacts + uses: actions/download-artifact@v4 + with: + pattern: ${{ inputs.artifact_name }} + merge-multiple: true + path: artifacts/ + + - name: Extract and run tarballs + run: | + for archive in artifacts/*.tar.gz; do + tar -xpf "$archive" -C / --overwrite + for f in /opt/hcpu/tests/*; do + [ -f "$f" ] && [ -x "$f" ] && "$f" + done + done diff --git a/.github/workflows/mainline.yml b/.github/workflows/mainline.yml new file mode 100644 index 00000000..ababaf32 --- /dev/null +++ b/.github/workflows/mainline.yml @@ -0,0 +1,28 @@ +# Main workflow file. This complex workflow declares +# primary automated jobs that are relevant to +# building and testing HyperCPU. + +name: HyperCPU CI/CD Pipeline + +on: + push: + +jobs: + prepare: + uses: ./.github/workflows/mainline-prepare.yml + + package: + needs: prepare + uses: ./.github/workflows/mainline-compile.yml + + format: + needs: prepare + uses: ./.github/workflows/mainline-format.yml + + lint: + needs: prepare + uses: ./.github/workflows/mainline-lint.yml + + tests: + needs: package + uses: ./.github/workflows/mainline-test.yml \ No newline at end of file diff --git a/.github/workflows/run-tests-feature-branch.yml b/.github/workflows/run-tests-feature-branch.yml deleted file mode 100644 index f162b636..00000000 --- a/.github/workflows/run-tests-feature-branch.yml +++ /dev/null @@ -1,33 +0,0 @@ -name: HyperCPU CI/CD Pipeline (feature branch) - -on: - push: - -jobs: - testing: - runs-on: ubuntu-latest - container: - image: hyperwin/hcpu-ci:debian-unstable - # see https://github.com/bazelbuild/bazel/issues/13823 - options: --init - if: (github.ref != 'refs/heads/master' && github.ref != 'refs/heads/dev') || !contains(github.event.head_commit.message, '[ci skip]') - - steps: - - name: Checkout code - uses: actions/checkout@v4 - with: - submodules: "true" - - - name: Install conan dependecies - run: | - conan profile detect && conan install . --build=missing - - - name: Build and test with GCC on Release profile - run: | - bazelisk test //src/... //tests/... --config=linux-dbg --compiler=gcc - bazelisk clean --expunge - - - name: Build and test with LLVM on Release profile - run: | - bazelisk test //src/... //tests/... --config=linux-dbg --compiler=clang - bazelisk clean --expunge diff --git a/.github/workflows/testing.yml b/.github/workflows/testing.yml deleted file mode 100644 index cf42f349..00000000 --- a/.github/workflows/testing.yml +++ /dev/null @@ -1,45 +0,0 @@ -name: HyperCPU CI/CD Pipeline - -on: - pull_request: - branches: - - master - -jobs: - testing: - runs-on: ubuntu-latest - container: - image: hyperwin/hcpu-ci:debian-unstable - # see https://github.com/bazelbuild/bazel/issues/13823 - options: --init - name: Run full test suite - - steps: - - name: Checkout code - uses: actions/checkout@v4 - with: - submodules: "true" - - - name: Install conan dependecies - run: | - conan profile detect && conan install . --build=missing - - - name: Build and test with GCC on Debug profile - run: | - bazelisk test //src/... //tests/... --config=linux-dbg --compiler=gcc - bazelisk clean --expunge - - - name: Build and test with GCC on Release profile - run: | - bazelisk test //src/... //tests/... --config=linux-opt --compiler=gcc - bazelisk clean --expunge - - - name: Build and test with LLVM on Debug profile - run: | - bazelisk test //src/... //tests/... --config=linux-dbg --compiler=clang - bazelisk clean --expunge - - - name: Build and test with LLVM on Release profile - run: | - bazelisk test //src/... //tests/... --config=linux-opt --compiler=clang - bazelisk clean --expunge diff --git a/.github/workflows/version-increment.yml b/.github/workflows/version-increment.yml index 887ea69e..8d21cb58 100644 --- a/.github/workflows/version-increment.yml +++ b/.github/workflows/version-increment.yml @@ -6,58 +6,42 @@ on: - master jobs: - versioning-patch-increment: + versioning-increment: runs-on: ubuntu-latest container: image: hyperwin/hcpu-ci:debian-unstable - options: --user root - if: "contains(github.event.head_commit.message, '[ci patch inc]')" - permissions: - contents: write - - steps: - - name: Checkout code - uses: actions/checkout@v4 - with: - fetch-depth: "0" - - - name: Setup git user - uses: fregante/setup-git-user@v1 - - - name: Increment version (patch) - run: | - tools/increment_version.py --increment patch - - - name: Push changes to master branch - run: | - git config --global --add safe.directory '*' - git add . - git commit -m "[auto]: Increment patch version" - git push origin master - versioning-minor-increment: - runs-on: ubuntu-latest - container: hyperwin/hcpu-ci:debian-unstable - if: "contains(github.event.head_commit.message, '[ci minor inc]')" permissions: contents: write + strategy: + matrix: + include: + - increment: patch + marker: '[ci-patch-increase]' + - increment: minor + marker: '[ci-minor-increase]' + - increment: major + marker: '[ci-major-increase]' + + if: > + contains(github.event.head_commit.message, '[ci-patch-increase]') || + contains(github.event.head_commit.message, '[ci-minor-increase]') || + contains(github.event.head_commit.message, '[ci-major-increase]') + steps: - - name: Checkout code - uses: actions/checkout@v4 + - uses: actions/checkout@v4 with: - fetch-depth: "0" + fetch-depth: 0 - - name: Setup git user - uses: fregante/setup-git-user@v1 + - uses: fregante/setup-git-user@v1 - - name: Increment version (minor) + - name: Fire increment version script (${{ matrix.increment }}) + id: increment run: | - tools/increment_version.py --increment minor + tools/increment_version.py --increment ${{ matrix.increment }} >> $GITHUB_OUTPUT - - name: Push changes to master branch - run: | - git config --global --add safe.directory '*' - git add . - git commit -m "[auto]: Increment minor version" - git push origin master + - name: Commit changes + uses: EndBug/add-and-commit@v9 + with: + message: "Increment ${{ matrix.increment }} version to ${{ steps.increment.outputs }}" diff --git a/.gitignore b/.gitignore index 8856848f..691671db 100644 --- a/.gitignore +++ b/.gitignore @@ -101,6 +101,6 @@ conan/ # Bazel builds with four directories, see for info: # https://bazel.build/remote/output-directories -bazel-* -bazel -output \ No newline at end of file +bazel-*/ +bazel/ +output/ diff --git a/.gitmodules b/.gitmodules index 62e35b98..953052d6 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,12 @@ [submodule "dist/HPool"] path = dist/HPool url = https://github.com/randommfs/HPool +[submodule "foreign/eternal"] + path = foreign/eternal + url = https://github.com/mapbox/eternal +[submodule "foreign/HPool"] + path = foreign/HPool + url = https://github.com/randommfs/HPool +[submodule "foreign/libbacktrace"] + path = foreign/libbacktrace + url = https://github.com/ianlancetaylor/libbacktrace diff --git a/BUILD.bazel b/BUILD.bazel index 76e2bfa1..c191ce24 100644 --- a/BUILD.bazel +++ b/BUILD.bazel @@ -16,6 +16,7 @@ config_setting( refresh_compile_commands( name = "refresh_compile_commands", + exclude_external_sources = True, targets = { "//src/...": "--config=linux-dbg", "//tests/...": "--config=linux-dbg", @@ -32,6 +33,14 @@ refresh_compile_commands( # ) ) +exports_files( + [ + ".ruff.toml", + ".clang-tidy", + ], + visibility = ["//visibility:public"], +) + format_multirun( name = "format", cc = "@llvm_toolchain//:bin/clang-format", diff --git a/MODULE.bazel b/MODULE.bazel index 77feb092..7ecc8417 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -6,40 +6,43 @@ module( compatibility_level = 1, ) -# We use conan for deps management -conan = use_extension("//conan:conan_deps_module_extension.bzl", "conan_extension") -use_repo( - conan, - "abseil", - "argparse", - "benchmark", - "boost", - "bzip2", - "eternal", - "fmt", - "gtest", - "libbacktrace", - "libunwind", - "re2", - "spdlog", - "xz_utils", - "zlib", -) +######################### +# Starlark dependencies # +######################### + +# Rules for building cpp objects: shared & static libs, binaries etc. +bazel_dep(name = "rules_cc", version = "0.1.2") -bazel_dep(name = "rules_cc", version = "0.0.17") -bazel_dep(name = "aspect_rules_lint", version = "1.3.5") +# Bazel skylib: core library for starlark. bazel_dep(name = "bazel_skylib", version = "1.7.1") +# Bazel helpers to include other projects. +bazel_dep(name = "rules_foreign_cc", version = "0.14.0") + +# These rules provide hooks for compile_commands.json generation - useful for clangd. bazel_dep(name = "hedron_compile_commands", dev_dependency = True) -bazel_dep(name = "buildifier_prebuilt", version = "8.0.3", dev_dependency = True) +# Rules for creating tarballs with our precious binaries. +bazel_dep(name = "rules_pkg", version = "1.1.0", dev_dependency = True) + +# Rules to constraint buildsystem. +bazel_dep(name = "platforms", version = "1.0.0", dev_dependency = True) + +# For formatting/linting. +bazel_dep(name = "aspect_rules_lint", version = "1.5.3", dev_dependency = True) + +# Formal bazel itself. +bazel_dep(name = "buildifier_prebuilt", version = "8.2.0.2") + +# Bazel deps are normally pulled from BCR (registry), but sometimes +# it is needed to fetch them elsewhere. This command does exactly that. git_override( module_name = "hedron_compile_commands", - commit = "4f28899228fb3ad0126897876f147ca15026151e", + commit = "abb61a688167623088f8768cc9264798df6a9d10", remote = "https://github.com/hedronvision/bazel-compile-commands-extractor.git", ) -# We use this for static analysis +# We use this for static analysis (and formatting). bazel_dep(name = "toolchains_llvm", version = "1.4.0", dev_dependency = True) llvm = use_extension("@toolchains_llvm//toolchain/extensions:llvm.bzl", "llvm") @@ -47,3 +50,19 @@ llvm.toolchain( llvm_version = "19.1.7", ) use_repo(llvm, "llvm_toolchain") + +################################ +# Actual HyperCPU dependencies # +################################ + +# These come from Google. +bazel_dep(name = "abseil-cpp", version = "20250512.1") +bazel_dep(name = "re2", version = "2024-07-02.bcr.1") +bazel_dep(name = "googletest", version = "1.17.0") +bazel_dep(name = "google_benchmark", version = "1.9.1") + +# These do not come from Google but we love them still. +bazel_dep(name = "fmt", version = "11.2.0") +bazel_dep(name = "spdlog", version = "1.15.3") +bazel_dep(name = "libunwind", version = "1.8.1") +bazel_dep(name = "argparse", version = "3.2.0") diff --git a/README.md b/README.md index 0250ffc2..3e2d91d8 100644 --- a/README.md +++ b/README.md @@ -1,16 +1,36 @@
- HyperCPU -

HyperCPU

-

- GitHub opened issues - Version - CI status - Status - License - Stars -

+ + + + HyperCPU +
+

HyperCPU — the hyper toolkit for custom hyper ISA

+ +

+ + GitHub opened issues + Version + CI status + Status + License + Stars +

+ +>[!IMPORTANT] +> HyperCPU is almost ready for use! Wait for 1.0 release to try it out or build the project yourself, test it and report issues. + +HyperCPU screenshot + +### What is this + HyperCPU is a set of programs created to work with my own simple ISA (instruction set architecture). The project was created for fun, but it took a lot of time (and nerves), and I learned a lot while working on it. HyperCPU project includes: @@ -23,7 +43,7 @@ See [ROADMAP.md](ROADMAP.md) for project ideas and tasks. >[!IMPORTANT] > HyperCPU is almost ready for use! Wait for 1.0 release to try it out or build the project yourself, test it and report issues. -HyperCPU screenshot +HyperCPU screenshot ### Installation diff --git a/conandata.yml b/conandata.yml deleted file mode 100644 index aa465698..00000000 --- a/conandata.yml +++ /dev/null @@ -1,12 +0,0 @@ -requirements: - gtest: "1.14.0" - benchmark: "1.9.1" - abseil: "20240116.1" - libbacktrace: "cci.20210118" - argparse: "3.2" - eternal: "1.0.1" - re2: "20230801" - fmt: "11.0.2" - libunwind: "1.8.1" - boost: "1.87.0" - spdlog: "1.15.0" diff --git a/conanfile.py b/conanfile.py deleted file mode 100644 index 0707284c..00000000 --- a/conanfile.py +++ /dev/null @@ -1,26 +0,0 @@ -from typing import Dict, Any, Collection -from functools import cached_property, lru_cache - -from conan import ConanFile -from conan.tools.google import bazel_layout - - -class HyperCPU(ConanFile): - name: "HyperCPU" - settings = ["os", "compiler", "build_type", "arch"] - - # conan data is fetched dynamically from - # conandata.yml - conan_data: Dict[str, Any] - - @cached_property - def generators(self) -> Collection[str]: - return ["BazelToolchain", "BazelDeps"] - - @lru_cache - def requirements(self) -> None: - for req, version in self.conan_data["requirements"].items(): - self.requires(f"{req}/{version}") - - def layout(self): - bazel_layout(self) diff --git a/dist/BUILD.bazel b/dist/BUILD.bazel deleted file mode 100644 index 39a3d6eb..00000000 --- a/dist/BUILD.bazel +++ /dev/null @@ -1,13 +0,0 @@ -load("@rules_cc//cc:defs.bzl", "cc_library") - -package( - default_visibility = [ - "//:__subpackages__", - ], -) - -cc_library( - name = "hpool", - hdrs = ["HPool/hpool.hpp"], - includes = ["HPool"], -) diff --git a/dist/CMakeLists.txt b/dist/CMakeLists.txt deleted file mode 100644 index 756d643c..00000000 --- a/dist/CMakeLists.txt +++ /dev/null @@ -1,8 +0,0 @@ -cmake_minimum_required(VERSION 3.22) - -# hpool -set(HPOOL_BUILD_TESTS OFF CACHE BOOL "Whether to include test target into configuration" FORCE) -set(HPOOL_BUILD_BENCHMARKS OFF CACHE BOOL "Whether to include benchmark target into configuration" FORCE) -add_subdirectory(HPool) - -add_library(dist::hpool ALIAS hpool) diff --git a/dist/HPool b/dist/HPool deleted file mode 160000 index 352cdd4e..00000000 --- a/dist/HPool +++ /dev/null @@ -1 +0,0 @@ -Subproject commit 352cdd4e5eb2bfb091bd4970386387b6d6f027b1 diff --git a/docker/alpine/Dockerfile b/docker/alpine/Dockerfile deleted file mode 100644 index ecea2c60..00000000 --- a/docker/alpine/Dockerfile +++ /dev/null @@ -1,11 +0,0 @@ -FROM alpine:latest - -ARG BAZELISK_TAG=v1.15.0 - -RUN apk update \ - && apk add --no-cache python3 py3-pip clang gcc git cmake make ninja grep g++ linux-headers wget \ - && pip3 install --no-cache-dir --break-system-packages conan - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/archlinux/Dockerfile b/docker/archlinux/Dockerfile deleted file mode 100644 index 655622db..00000000 --- a/docker/archlinux/Dockerfile +++ /dev/null @@ -1,13 +0,0 @@ -FROM archlinux:latest - -ARG BAZELISK_TAG=v1.15.0 - -RUN pacman -Syu --noconfirm --needed \ - python python-pip git cmake clang gcc \ - base-devel wget \ - && pip install --no-cache-dir --break-system-packages conan \ - && pacman -Scc --noconfirm - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/debian-stable/Dockerfile b/docker/debian-stable/Dockerfile deleted file mode 100644 index 041d377b..00000000 --- a/docker/debian-stable/Dockerfile +++ /dev/null @@ -1,12 +0,0 @@ -FROM debian:latest - -ARG BAZELISK_TAG=v1.15.0 - -RUN apt-get update && apt-get install -y --no-install-recommends \ - git cmake clang libre2-9 libre2-dev python3 python3-pip cmake wget make gcc g++ \ - && pip3 install --no-cache-dir --break-system-packages conan \ - && rm -rf /var/lib/apt/lists/* - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/debian-unstable/Dockerfile b/docker/debian-unstable/Dockerfile deleted file mode 100644 index 5e84b468..00000000 --- a/docker/debian-unstable/Dockerfile +++ /dev/null @@ -1,12 +0,0 @@ -FROM debian:unstable - -ARG BAZELISK_TAG=v1.15.0 - -RUN apt-get update && apt-get install -y --no-install-recommends \ - git cmake clang libre2-11 libre2-dev python3 python3-pip cmake wget make gcc g++ \ - && pip3 install --no-cache-dir --break-system-packages conan \ - && rm -rf /var/lib/apt/lists/* - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/fedora/Dockerfile b/docker/fedora/Dockerfile deleted file mode 100644 index 09d4a225..00000000 --- a/docker/fedora/Dockerfile +++ /dev/null @@ -1,14 +0,0 @@ -FROM fedora:latest - -ARG BAZELISK_TAG=v1.15.0 - -RUN dnf update -y \ - && dnf install -y --setopt=install_weak_deps=False git cmake \ - clang gcc which nodejs python3 python3-pip make awk wget \ - && pip3 install --no-cache-dir --break-system-packages conan \ - && dnf clean all \ - && rm -rf /var/cache/dnf - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/gentoo-glibc/Dockerfile b/docker/gentoo-glibc/Dockerfile deleted file mode 100644 index d67b47d2..00000000 --- a/docker/gentoo-glibc/Dockerfile +++ /dev/null @@ -1,12 +0,0 @@ -FROM gentoo/stage3:systemd - -ARG BAZELISK_TAG=v1.15.0 - -RUN emerge --sync > /dev/null && \ - getuto && \ - emerge llvm-core/clang cmake dev-vcs/git re2 libfmt gtest which wget conan --getbinpkg -j2 && \ - rm -rf /var/lib/repos/gentoo - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/gentoo-musl/stage1/Dockerfile b/docker/gentoo-musl/stage1/Dockerfile deleted file mode 100644 index 15412712..00000000 --- a/docker/gentoo-musl/stage1/Dockerfile +++ /dev/null @@ -1,6 +0,0 @@ -FROM gentoo/stage3:musl - -RUN emerge --sync > /dev/null && \ - getuto && \ - sed -i 's/^MAKEOPTS=".*"/MAKEOPTS="& -j8"/' /etc/portage/make.conf && \ - emerge llvm-core/llvm cmake gtest re2 libfmt dev-vcs/git conan --getbinpkg diff --git a/docker/gentoo-musl/stage2/Dockerfile b/docker/gentoo-musl/stage2/Dockerfile deleted file mode 100644 index b39ee4ab..00000000 --- a/docker/gentoo-musl/stage2/Dockerfile +++ /dev/null @@ -1,10 +0,0 @@ -FROM hyperwin/hcpu-ci:gentoo-musl-build - -ARG BAZELISK_TAG=v1.15.0 - -RUN emerge llvm-core/clang --getbinpkg && \ - rm -rf /var/lib/repos/gentoo - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/docker/ubuntu/Dockerfile b/docker/ubuntu/Dockerfile deleted file mode 100644 index 88d785f4..00000000 --- a/docker/ubuntu/Dockerfile +++ /dev/null @@ -1,13 +0,0 @@ -FROM ubuntu:latest - -ARG USER=bazel -ARG BAZELISK_TAG=v1.15.0 - -RUN apt update && apt install -y --no-install-recommends \ - git cmake clang libre2-10 libre2-dev python3 python3-pip cmake wget make gcc g++ \ - && pip3 install --no-cache-dir --break-system-packages conan \ - && rm -rf /var/lib/apt/lists/* - -RUN wget https://github.com/bazelbuild/bazelisk/releases/download/${BAZELISK_TAG}/bazelisk-linux-amd64 && \ - chmod 755 bazelisk-linux-amd64 && \ - mv bazelisk-linux-amd64 /usr/bin/bazelisk diff --git a/foreign/BUILD.bazel b/foreign/BUILD.bazel new file mode 100644 index 00000000..0cedd4a3 --- /dev/null +++ b/foreign/BUILD.bazel @@ -0,0 +1,24 @@ +"Foreign deps" + +# Here we have projects that we rely on, but +# cannot fetch from registry. + +load("@rules_cc//cc:defs.bzl", "cc_library") + +package( + default_visibility = [ + "//:__subpackages__", + ], +) + +cc_library( + name = "hpool", + hdrs = ["HPool/hpool.hpp"], + includes = ["HPool"], +) + +cc_library( + name = "eternal", + hdrs = ["eternal/include/mapbox/eternal.hpp"], + includes = ["eternal/include"], +) diff --git a/foreign/HPool b/foreign/HPool new file mode 160000 index 00000000..6b165437 --- /dev/null +++ b/foreign/HPool @@ -0,0 +1 @@ +Subproject commit 6b1654378a084f4e7cc7324670543df86d03b7fa diff --git a/foreign/eternal b/foreign/eternal new file mode 160000 index 00000000..dd2f5b9f --- /dev/null +++ b/foreign/eternal @@ -0,0 +1 @@ +Subproject commit dd2f5b9ff38fcd36b59efd9d289127fa73efc6cb diff --git a/ruff.toml b/ruff.toml new file mode 100644 index 00000000..a69393f3 --- /dev/null +++ b/ruff.toml @@ -0,0 +1,61 @@ +# Exclude a variety of commonly ignored directories. +exclude = [ + ".bzr", + ".direnv", + ".eggs", + ".git", + ".git-rewrite", + ".hg", + ".ipynb_checkpoints", + ".mypy_cache", + ".nox", + ".pants.d", + ".pyenv", + ".pytest_cache", + ".pytype", + ".ruff_cache", + ".svn", + ".tox", + ".venv", + ".vscode", + "__pypackages__", + "_build", + "buck-out", + "build", + "dist", + "node_modules", + "site-packages", + "venv", +] + +# Same as Black. +line-length = 88 +indent-width = 4 + +# Assume Python 3.9 +target-version = "py39" + +[lint] +# Enable Pyflakes (`F`) and a subset of the pycodestyle (`E`) codes by default. +select = ["E4", "E7", "E9", "F"] +ignore = [] + +# Allow fix for all enabled rules (when `--fix`) is provided. +fixable = ["ALL"] +unfixable = [] + +# Allow unused variables when underscore-prefixed. +dummy-variable-rgx = "^(_+|(_+[a-zA-Z0-9_]*[a-zA-Z0-9]+?))$" + +[format] +# Like Black, use double quotes for strings. +quote-style = "double" + +# Like Black, indent with spaces, rather than tabs. +indent-style = "space" + +# Like Black, respect magic trailing commas. +skip-magic-trailing-comma = false + +# Like Black, automatically detect the appropriate line ending. +line-ending = "auto" diff --git a/src/Assembler/BUILD.bazel b/src/Assembler/BUILD.bazel index 8d09b706..8c9df9f2 100644 --- a/src/Assembler/BUILD.bazel +++ b/src/Assembler/BUILD.bazel @@ -9,13 +9,12 @@ cc_library( hdrs = glob(["**/*.hpp"]), visibility = ["//visibility:public"], deps = [ - "//dist:hpool", + "//foreign:eternal", + "//foreign:hpool", "//src/Common:hcpu_common", "//src/PCH:pch_cstd", "//src/Pog:pog", - "@eternal", "@fmt", - "@re2", "@spdlog", ], ) @@ -23,9 +22,10 @@ cc_library( cc_binary( name = "hcasm", srcs = ["Main.cpp"], - visibility = ["//visibility:private"], + visibility = ["//visibility:public"], deps = [ ":assembler_core", "@argparse", + "@re2", ], ) diff --git a/src/Assembler/Core/BinaryTransformer.cpp b/src/Assembler/Core/BinaryTransformer.cpp index f27fdd11..757eb883 100644 --- a/src/Assembler/Core/BinaryTransformer.cpp +++ b/src/Assembler/Core/BinaryTransformer.cpp @@ -2,9 +2,9 @@ #include "Assembler/Core/BinaryTransformer.hpp" #include "Assembler/Core/Compiler.hpp" +#include "Common/Exit.hpp" #include "Common/LanguageSpec/Flags.hpp" #include "Common/LanguageSpec/Opcodes.hpp" -#include "Common/Exit.hpp" #include "PCH/CStd.hpp" HyperCPU::OperandTypes HCAsm::BinaryTransformer::DetermineOperandTypes(Operand& op1, Operand& op2) { @@ -12,51 +12,51 @@ HyperCPU::OperandTypes HCAsm::BinaryTransformer::DetermineOperandTypes(Operand& Op2T tp2 = Op2T::NONE; // Placeholder switch (op1.type) { - case HCAsm::OperandType::reg: - tp1 = Op1T::R; - break; - case HCAsm::OperandType::mem_reg_add_int: - case HCAsm::OperandType::memaddr_reg: - tp1 = Op1T::RM; - break; - case HCAsm::OperandType::sint: - case HCAsm::OperandType::uint: - case HCAsm::OperandType::label: - tp1 = Op1T::IMM; - break; - case HCAsm::OperandType::memaddr_int: - case HCAsm::OperandType::memaddr_lbl: - tp1 = Op1T::M; - break; - case HCAsm::OperandType::none: - tp1 = Op1T::NONE; - break; - default: - HyperCPU::unreachable(); + case HCAsm::OperandType::reg: + tp1 = Op1T::R; + break; + case HCAsm::OperandType::mem_reg_add_int: + case HCAsm::OperandType::memaddr_reg: + tp1 = Op1T::RM; + break; + case HCAsm::OperandType::sint: + case HCAsm::OperandType::uint: + case HCAsm::OperandType::label: + tp1 = Op1T::IMM; + break; + case HCAsm::OperandType::memaddr_int: + case HCAsm::OperandType::memaddr_lbl: + tp1 = Op1T::M; + break; + case HCAsm::OperandType::none: + tp1 = Op1T::NONE; + break; + default: + HyperCPU::unreachable(); } switch (op2.type) { - case HCAsm::OperandType::reg: - tp2 = Op2T::R; - break; - case HCAsm::OperandType::mem_reg_add_int: - case HCAsm::OperandType::memaddr_reg: - tp2 = Op2T::RM; - break; - case HCAsm::OperandType::sint: - case HCAsm::OperandType::uint: - case HCAsm::OperandType::label: - tp2 = Op2T::IMM; - break; - case HCAsm::OperandType::memaddr_int: - case HCAsm::OperandType::memaddr_lbl: - tp2 = Op2T::M; - break; - case HCAsm::OperandType::none: - tp2 = Op2T::NONE; - break; - default: - HyperCPU::unreachable(); + case HCAsm::OperandType::reg: + tp2 = Op2T::R; + break; + case HCAsm::OperandType::mem_reg_add_int: + case HCAsm::OperandType::memaddr_reg: + tp2 = Op2T::RM; + break; + case HCAsm::OperandType::sint: + case HCAsm::OperandType::uint: + case HCAsm::OperandType::label: + tp2 = Op2T::IMM; + break; + case HCAsm::OperandType::memaddr_int: + case HCAsm::OperandType::memaddr_lbl: + tp2 = Op2T::M; + break; + case HCAsm::OperandType::none: + tp2 = Op2T::NONE; + break; + default: + HyperCPU::unreachable(); } return QuickCast(QuickOR(tp1, tp2)); diff --git a/src/Assembler/Core/Compiler.cpp b/src/Assembler/Core/Compiler.cpp index 1f8438e6..a0bcb9dd 100644 --- a/src/Assembler/Core/Compiler.cpp +++ b/src/Assembler/Core/Compiler.cpp @@ -2,8 +2,8 @@ #include "Assembler/Core/BinaryTransformer.hpp" #include "Assembler/Core/Compiler.hpp" -#include "Common/Helpers/Classes.hpp" #include "Common/Exit.hpp" +#include "Common/Helpers/Classes.hpp" #include "PCH/CStd.hpp" #include "Pog/Pog.hpp" @@ -21,8 +21,8 @@ HCAsm::HCAsmCompiler::HCAsmCompiler() parser.get_line_offset() += tok.length(); return {}; }); - parser.token("\\/\\/.*"); // Single line comment - parser.token("\\/\\*[\\S\\s]+\\*\\/"); /* Multi-line comment */ + parser.token("\\/\\/.*"); // Single line comment + parser.token(R"(\/\*[\S\s]+\*\/)"); /* Multi-line comment */ parser.token(R"(\+)") .symbol("+"); parser.token(R"(-)") @@ -66,7 +66,7 @@ HCAsm::HCAsmCompiler::HCAsmCompiler() parser.token("[a-zA-Z_][a-zA-Z0-9_]*") .symbol("ident") .action(TokenizeIdentifier); - parser.token("\"((?:\\\\[\\s\\S]|[^\"\\\\])*)\"") + parser.token(R"lit("((?:\\[\s\S]|[^"\\])*)")lit") .symbol("string") .action(TokenizeString); parser.token(R"(0s[0-9]+)") @@ -313,35 +313,27 @@ HCAsm::BinaryResult HCAsm::HCAsmCompiler::TransformToBinary(HCAsm::CompilerState spdlog::info("Running pass 1 - counting code size"); for (auto& instr : ir.ir) { - VisitVariant(instr, - [this, &ir](Instruction& instruction) mutable -> void { - ir.code_size += InstructionSize(instruction); - }, - [&ir](Label& label) mutable -> void { + VisitVariant(instr, [this, &ir](Instruction& instruction) mutable -> void { ir.code_size += InstructionSize(instruction); }, [&ir](Label& label) mutable -> void { ir.labels[label.name] = ir.code_size; if (label.is_entry_point) { ir.entry_point = ir.code_size; - } - }, - [&ir](RawValue& raw) mutable -> void { - ir.code_size += [&raw]() -> std::uint8_t { - switch (raw.mode) { - case Mode::b8_str: - return std::get>(raw.value.variant)->size(); - case Mode::b8: - return 1; - case Mode::b16: - return 2; - case Mode::b32: - return 4; - case Mode::b64_label: - case Mode::b64: - return 8; - default: - std::abort(); - } - }(); - }); + } }, [&ir](RawValue& raw) mutable -> void { ir.code_size += [&raw]() -> std::uint8_t { + switch (raw.mode) { + case Mode::b8_str: + return std::get>(raw.value.variant)->size(); + case Mode::b8: + return 1; + case Mode::b16: + return 2; + case Mode::b32: + return 4; + case Mode::b64_label: + case Mode::b64: + return 8; + default: + std::abort(); + } + }(); }); } // Resolve references - pass 2 @@ -374,11 +366,7 @@ HCAsm::BinaryResult HCAsm::HCAsmCompiler::TransformToBinary(HCAsm::CompilerState BinaryTransformer transformer(binary, &ir); for (auto& instr : ir.ir) { - VisitVariant(instr, - [&transformer](Instruction& instruction) mutable -> void { - transformer.EncodeInstruction(instruction); - }, - [&binary, &ir, this](RawValue& raw) mutable -> void { + VisitVariant(instr, [&transformer](Instruction& instruction) mutable -> void { transformer.EncodeInstruction(instruction); }, [&binary, &ir, this](RawValue& raw) mutable -> void { switch (raw.mode) { case Mode::b8_str: binary.push(*std::get>(raw.value.variant)); @@ -403,10 +391,7 @@ HCAsm::BinaryResult HCAsm::HCAsmCompiler::TransformToBinary(HCAsm::CompilerState break; default: HyperCPU::unreachable(); - } - }, - [](Label&) {} - ); + } }, [](Label&) {}); } binary.entry_point = ir.entry_point; @@ -449,7 +434,7 @@ std::string_view HCAsm::FindLine(const pog::LineSpecialization& line_spec, const } void HCAsm::WriteResultFile(HyperCPU::FileType type, HCAsm::BinaryResult& result, std::ofstream& output, std::uint32_t code_size, std::uint32_t entry_point) { - HyperCPU::GenericHeader gen_header; + HyperCPU::GenericHeader gen_header{}; gen_header.type = type; gen_header.magic = HyperCPU::magic; gen_header.version = HyperCPU::current_version; diff --git a/src/Assembler/Core/Parsers.cpp b/src/Assembler/Core/Parsers.cpp index af56dd90..ccc2f7ae 100644 --- a/src/Assembler/Core/Parsers.cpp +++ b/src/Assembler/Core/Parsers.cpp @@ -73,10 +73,9 @@ Value HCAsm::ParseOperand4(pog::Parser& parser, std::vector(args[1].value.val) != "ptr") { - ThrowError( - args[1], - parser, - fmt::format("unknown keyword \"{}\" specified, \"ptr\" expected", std::get(args[1].value.val))); + ThrowError(args[1], parser, + fmt::format(R"(unknown keyword "{}" specified, "ptr" expected)", + std::get(args[1].value.val))); } return { @@ -103,10 +102,9 @@ Value HCAsm::ParseOperand5(pog::Parser& parser, std::vector(args[1].value.val) != "ptr") [[unlikely]] { - ThrowError( - args[1], - parser, - fmt::format("unknown keyword \"{}\" specified, \"ptr\" expected", std::get(args[1].value.val))); + ThrowError(args[1], parser, + fmt::format(R"(unknown keyword "{}" specified, "ptr" expected)", + std::get(args[1].value.val))); } return { @@ -133,10 +131,9 @@ Value HCAsm::ParseOperand6(pog::Parser& parser, std::vector(args[1].value.val) != "ptr") { - ThrowError( - args[1], - parser, - fmt::format("unknown keyword \"{}\" specified, \"ptr\" expected", std::get(args[1].value.val))); + ThrowError(args[1], parser, + fmt::format(R"(unknown keyword "{}" specified, "ptr" expected)", + std::get(args[1].value.val))); } else if (std::get(args[5].value.val) > 255) [[unlikely]] { ThrowError( args[5], diff --git a/src/Assembler/Core/StatementCompilers.cpp b/src/Assembler/Core/StatementCompilers.cpp index 61739997..83e5d2ba 100644 --- a/src/Assembler/Core/StatementCompilers.cpp +++ b/src/Assembler/Core/StatementCompilers.cpp @@ -15,10 +15,10 @@ Value HCAsm::CompileStatement1([[maybe_unused]] pog::Parser& parser, std: ++current_index; - current_state->ir.push_back(Instruction{ - opcode_assoc.at(instr_name.c_str()), - std::get(args[1].value.val), - std::get(args[3].value.val)}); + current_state->ir.emplace_back( + Instruction{.opcode = opcode_assoc.at(instr_name.c_str()), + .op1 = std::get(args[1].value.val), + .op2 = std::get(args[3].value.val)}); if (std::get(args[1].value.val).type == OperandType::label) { parser.get_compiler_state()->pending_resolves.push_back(PendingLabelReferenceResolve{ @@ -44,10 +44,10 @@ Value HCAsm::CompileStatement2(pog::Parser& parser, std::vector(args[1].value.val); - current_state->ir.push_back(Instruction{ - opcode_assoc.at(instr_name.c_str()), - tmp_op, - {HCAsm::OperandType::none}}); + current_state->ir.emplace_back( + Instruction{.opcode = opcode_assoc.at(instr_name.c_str()), + .op1 = tmp_op, + .op2 = {.type = HCAsm::OperandType::none}}); if (tmp_op.type == OperandType::label) { parser.get_compiler_state()->pending_resolves.push_back(PendingLabelReferenceResolve{ @@ -67,10 +67,10 @@ Value HCAsm::CompileStatement3(pog::Parser& parser, std::vectorir.push_back(Instruction{ - opcode_assoc.at(instr_name.c_str()), - {HCAsm::OperandType::none}, - {HCAsm::OperandType::none}}); + current_state->ir.emplace_back( + Instruction{.opcode = opcode_assoc.at(instr_name.c_str()), + .op1 = {.type = HCAsm::OperandType::none}, + .op2 = {.type = HCAsm::OperandType::none}}); return {}; } @@ -86,7 +86,8 @@ Value HCAsm::CompileLabel(pog::Parser& parser, std::vectorir.push_back(HCAsm::Label{name, current_index++, false}); + current_state->ir.emplace_back(HCAsm::Label{ + .name = name, .index = current_index++, .is_entry_point = false}); current_state->labels[name] = current_index - 1; return {}; } @@ -103,7 +104,8 @@ Value HCAsm::CompileEntryLabel(pog::Parser& parser, std::vectorir.push_back(HCAsm::Label{name, current_index++, true}); + current_state->ir.emplace_back(HCAsm::Label{ + .name = name, .index = current_index++, .is_entry_point = true}); current_state->labels[name] = current_index - 1; return {}; } @@ -112,7 +114,8 @@ Value HCAsm::CompileRawValueb8(pog::Parser& parser, std::vector(args[1].value.val).type != OperandType::uint) { ThrowError(*std::get(args[1].value.val).tokens[0], parser, "invalid operand type for directive '.b8', expected uint"); } - current_state->ir.push_back(HCAsm::RawValue{Mode::b8, std::get(args[1].value.val)}); + current_state->ir.emplace_back(HCAsm::RawValue{ + .mode = Mode::b8, .value = std::get(args[1].value.val)}); return {}; } @@ -121,10 +124,10 @@ Value HCAsm::CompileRawValueb8_str([[maybe_unused]] pog::Parser& parser, ThrowError(*std::get(args[1].value.val).tokens[0], parser, "invalid operand type for directive '.b8' expected uint or string"); } - current_state->ir.push_back(HCAsm::RawValue{ - Mode::b8_str, - Operand{ - .variant = std::make_shared(std::move(std::get(args[1].value.val)))}}); + current_state->ir.emplace_back(HCAsm::RawValue{ + .mode = Mode::b8_str, + .value = Operand{.variant = std::make_shared(std::move( + std::get(args[1].value.val)))}}); return {}; } @@ -133,7 +136,8 @@ Value HCAsm::CompileRawValueb16(pog::Parser& parser, std::vector(args[1].value.val).type != OperandType::uint) { ThrowError(*std::get(args[1].value.val).tokens[0], parser, "invalid operand type for directive '.b16' expected uint"); } - current_state->ir.push_back(HCAsm::RawValue{Mode::b16, std::get(args[1].value.val)}); + current_state->ir.emplace_back(HCAsm::RawValue{ + .mode = Mode::b16, .value = std::get(args[1].value.val)}); return {}; } @@ -141,7 +145,8 @@ Value HCAsm::CompileRawValueb32(pog::Parser& parser, std::vector(args[1].value.val).type != OperandType::uint) { ThrowError(*std::get(args[1].value.val).tokens[0], parser, "invalid operand type for directive '.b32', expected uint"); } - current_state->ir.push_back(HCAsm::RawValue{Mode::b32, std::get(args[1].value.val)}); + current_state->ir.emplace_back(HCAsm::RawValue{ + .mode = Mode::b32, .value = std::get(args[1].value.val)}); return {}; } @@ -150,10 +155,12 @@ Value HCAsm::CompileRawValueb64(pog::Parser& parser, std::vectorir.push_back(HCAsm::RawValue{Mode::b64, op}); + current_state->ir.emplace_back( + HCAsm::RawValue{.mode = Mode::b64, .value = op}); break; case HCAsm::OperandType::label: - current_state->ir.push_back(HCAsm::RawValue{Mode::b64_label, op}); + current_state->ir.emplace_back( + HCAsm::RawValue{.mode = Mode::b64_label, .value = op}); break; default: ThrowError(*std::get(args[1].value.val).tokens[0], parser, "invalid operand type for directive '.b64', label or uint expected"); diff --git a/src/Assembler/Core/Tokenizers.cpp b/src/Assembler/Core/Tokenizers.cpp index b3488796..4d79103e 100644 --- a/src/Assembler/Core/Tokenizers.cpp +++ b/src/Assembler/Core/Tokenizers.cpp @@ -88,7 +88,7 @@ Value HCAsm::TokenizeChar(std::string_view str) { } Value HCAsm::TokenizeHexadecimal(std::string_view str) { - std::uint64_t x; + std::uint64_t x = 0; std::stringstream ss; ss << std::hex << str.begin() + 2; ss >> x; diff --git a/src/Assembler/Main.cpp b/src/Assembler/Main.cpp index b0c4bce9..1ad3d217 100644 --- a/src/Assembler/Main.cpp +++ b/src/Assembler/Main.cpp @@ -78,7 +78,7 @@ int main(int argc, char** argv) { } spdlog::error("Source and destination files handles acquired"); - HyperCPU::GenericHeader hdr; + HyperCPU::GenericHeader hdr{}; src.read(reinterpret_cast(&hdr), sizeof(hdr)); if (hdr.magic == HyperCPU::magic) { HyperCPU::PrintUnsupported("Linking object files is not implemented!"); @@ -90,7 +90,7 @@ int main(int argc, char** argv) { (std::istreambuf_iterator(src)), std::istreambuf_iterator()); - std::uint32_t code_size; + std::uint32_t code_size = 0; auto binary = compiler.Compile(contents, code_size); diff --git a/src/BacktraceProvider/BUILD.bazel b/src/BacktraceProvider/BUILD.bazel index b4222290..c8fe5ef1 100644 --- a/src/BacktraceProvider/BUILD.bazel +++ b/src/BacktraceProvider/BUILD.bazel @@ -8,7 +8,6 @@ cc_library( deps = [ "//src/PCH:pch_cstd", "@fmt", - "@libbacktrace", "@libunwind", ], ) diff --git a/src/Common/Exit.hpp b/src/Common/Exit.hpp index db3fb111..c853c562 100644 --- a/src/Common/Exit.hpp +++ b/src/Common/Exit.hpp @@ -6,7 +6,7 @@ namespace HyperCPU { When the program was compiled on debug profile, any exit must be easy to catch by debugger - same thing with unreachable call, as using this can cause serious bugs. When we are on release profile - allow these things to behave how they were intented. */ - + [[noreturn]] constexpr void exit([[maybe_unused]] int code) { #ifdef NDEBUG std::abort(); @@ -22,4 +22,4 @@ namespace HyperCPU { __builtin_unreachable(); #endif } -} \ No newline at end of file +} // namespace HyperCPU \ No newline at end of file diff --git a/src/Emulator/BUILD.bazel b/src/Emulator/BUILD.bazel index 93cf1423..80e4da5f 100644 --- a/src/Emulator/BUILD.bazel +++ b/src/Emulator/BUILD.bazel @@ -9,10 +9,10 @@ cc_library( hdrs = glob(["**/*.hpp"]), visibility = ["//visibility:public"], deps = [ + "//foreign:eternal", "//src/Assembler:assembler_core", "//src/PCH:pch_cstd", "//src/Pog:pog", - "@eternal", "@fmt", ], ) @@ -20,7 +20,7 @@ cc_library( cc_binary( name = "hcemul", srcs = ["Main.cpp"], - visibility = ["//visibility:private"], + visibility = ["//visibility:public"], deps = [ ":emulator_core", "@argparse", diff --git a/src/Emulator/Core/CPU/CPU.cpp b/src/Emulator/Core/CPU/CPU.cpp index 472c15af..31a37361 100644 --- a/src/Emulator/Core/CPU/CPU.cpp +++ b/src/Emulator/Core/CPU/CPU.cpp @@ -6,68 +6,63 @@ #include "Emulator/Core/CPU/Decoders/StdDecoder.hpp" #include "Emulator/Core/MemoryController/MemoryControllerST.hpp" -HyperCPU::CPU::CPU(std::uint16_t core_count, std::uint64_t mem_size, char* binary, std::uint64_t binary_size) - : mem_controller(dynamic_cast(new MemoryControllerST(mem_size, this))), +HyperCPU::CPU::CPU(std::uint16_t core_count, std::uint64_t mem_size, + char* binary, std::uint64_t binary_size) + : mem_controller(dynamic_cast( + new MemoryControllerST(mem_size, this))), core_count(core_count), total_mem(mem_size), binary_size(binary_size), halted(false), + x0(&data[0]), + x1(&data[1]), + x2(&data[2]), + x3(&data[3]), + x4(&data[4]), + x5(&data[5]), + x6(&data[6]), + x7(&data[7]), + xl0(reinterpret_cast(&data[0])), + xl1(reinterpret_cast(&data[1])), + xl2(reinterpret_cast(&data[2])), + xl3(reinterpret_cast(&data[3])), + xl4(reinterpret_cast(&data[4])), + xl5(reinterpret_cast(&data[5])), + xl6(reinterpret_cast(&data[6])), + xl7(reinterpret_cast(&data[7])), + xh0(reinterpret_cast(&data[0]) + 1), + xh1(reinterpret_cast(&data[1]) + 1), + xh2(reinterpret_cast(&data[2]) + 1), + xh3(reinterpret_cast(&data[3]) + 1), + xh4(reinterpret_cast(&data[4]) + 1), + xh5(reinterpret_cast(&data[5]) + 1), + xh6(reinterpret_cast(&data[6]) + 1), + xh7(reinterpret_cast(&data[7]) + 1), + xll0(reinterpret_cast(&data[0])), + xll1(reinterpret_cast(&data[1])), + xll2(reinterpret_cast(&data[2])), + xll3(reinterpret_cast(&data[3])), + xllh0(reinterpret_cast(&data[0]) + 1), + xllh1(reinterpret_cast(&data[1]) + 1), + xllh2(reinterpret_cast(&data[2]) + 1), + xllh3(reinterpret_cast(&data[3]) + 1), + xlll0(reinterpret_cast(&data[0])), + xlll1(reinterpret_cast(&data[1])), + xlll2(reinterpret_cast(&data[2])), + xlll3(reinterpret_cast(&data[3])), + xbp(&data[8]), + xsp(&data[9]), + xip(&data[10]), + xgdp(&data[11]), + xivt(&data[12]), ivt_initialized(false), + crf(false), + ovf(false), + udf(false), + zrf(false), io_ctl(std::make_unique()) { // Initializing all register pointers std::memset(&data, 0, sizeof(data)); - x0 = &data[0]; - x1 = &data[1]; - x2 = &data[2]; - x3 = &data[3]; - x4 = &data[4]; - x5 = &data[5]; - x6 = &data[6]; - x7 = &data[7]; - - xl0 = reinterpret_cast(&data[0]); - xl1 = reinterpret_cast(&data[1]); - xl2 = reinterpret_cast(&data[2]); - xl3 = reinterpret_cast(&data[3]); - xl4 = reinterpret_cast(&data[4]); - xl5 = reinterpret_cast(&data[5]); - xl6 = reinterpret_cast(&data[6]); - xl7 = reinterpret_cast(&data[7]); - - xh0 = reinterpret_cast(&data[0]) + 1; - xh1 = reinterpret_cast(&data[1]) + 1; - xh2 = reinterpret_cast(&data[2]) + 1; - xh3 = reinterpret_cast(&data[3]) + 1; - xh4 = reinterpret_cast(&data[4]) + 1; - xh5 = reinterpret_cast(&data[5]) + 1; - xh6 = reinterpret_cast(&data[6]) + 1; - xh7 = reinterpret_cast(&data[7]) + 1; - - xll0 = reinterpret_cast(&data[0]); - xll1 = reinterpret_cast(&data[1]); - xll2 = reinterpret_cast(&data[2]); - xll3 = reinterpret_cast(&data[3]); - - xllh0 = reinterpret_cast(&data[0]) + 1; - xllh1 = reinterpret_cast(&data[1]) + 1; - xllh2 = reinterpret_cast(&data[2]) + 1; - xllh3 = reinterpret_cast(&data[3]) + 1; - - xlll0 = reinterpret_cast(&data[0]); - xlll1 = reinterpret_cast(&data[1]); - xlll2 = reinterpret_cast(&data[2]); - xlll3 = reinterpret_cast(&data[3]); - - xbp = &data[8]; - xsp = &data[9]; - xip = &data[10]; - xgdp = &data[11]; - xivt = &data[12]; - - crf = false; - ovf = false; - udf = false; - zrf = false; // TODO: Use std::bind instead of lambdas opcode_handler_assoc[static_cast(HyperCPU::Opcode::HALT)] = @@ -252,7 +247,7 @@ void HyperCPU::CPU::Run() { pending_interrupt.reset(); continue; } - + buffer = m_decoder->FetchAndDecode(); switch (buffer.m_opcode) { diff --git a/src/Emulator/Core/CPU/Decoders/StdDecoder.cpp b/src/Emulator/Core/CPU/Decoders/StdDecoder.cpp index 73a28e23..b0e8dbca 100644 --- a/src/Emulator/Core/CPU/Decoders/StdDecoder.cpp +++ b/src/Emulator/Core/CPU/Decoders/StdDecoder.cpp @@ -44,8 +44,8 @@ bool HyperCPU::Decoder::IsHalted() const noexcept { } HyperCPU::IInstruction HyperCPU::Decoder::FetchAndDecode() { - std::uint16_t opcode; - std::uint8_t flags; + std::uint16_t opcode = 0; + std::uint8_t flags = 0; IInstruction instruction; // Fetch opcode and check if its valid diff --git a/src/Emulator/Core/CPU/IO/Simple.cpp b/src/Emulator/Core/CPU/IO/Simple.cpp index 01af7a4e..c0ad1f14 100644 --- a/src/Emulator/Core/CPU/IO/Simple.cpp +++ b/src/Emulator/Core/CPU/IO/Simple.cpp @@ -7,9 +7,12 @@ #include "Emulator/Misc/bit_cast.hpp" HyperCPU::SimpleIOImpl::SimpleIOImpl() - : state(CurrentState::Default), was_printing(true), printing(true) { + : state(CurrentState::Default), + was_printing(true), + printing(true), + newt(oldt) { tcgetattr(STDIN_FILENO, &oldt); - newt = oldt; + newt.c_lflag &= ~(ICANON | ECHO); newt.c_cc[VMIN] = 1; newt.c_cc[VTIME] = 0; @@ -51,17 +54,17 @@ void HyperCPU::SimpleIOImpl::Putchar(std::uint8_t c) { } std::uint8_t HyperCPU::SimpleIOImpl::Getchar() { - char c; + char c = 0; [[maybe_unused]] auto t = read(STDIN_FILENO, &c, 1); return c; } std::function HyperCPU::SimpleIOImpl::GetPutchar() { - return std::bind(&SimpleIOImpl::Putchar, this, std::placeholders::_1); + return [this](auto&& PH1) { Putchar(std::forward(PH1)); }; } std::function HyperCPU::SimpleIOImpl::GetGetchar() { - return std::bind(&SimpleIOImpl::Getchar, this); + return [this] { return Getchar(); }; } void HyperCPU::SimpleIOImpl::DisablePrinting() { diff --git a/src/Emulator/Core/CPU/InstructionsImpl/ADC.cpp b/src/Emulator/Core/CPU/InstructionsImpl/ADC.cpp index 243a290d..6aa3e43a 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/ADC.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/ADC.cpp @@ -42,7 +42,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -85,7 +85,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -130,7 +130,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); if (crf) @@ -139,7 +139,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); if (crf) @@ -148,7 +148,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); if (crf) @@ -157,7 +157,7 @@ void HyperCPU::CPU::ExecADC(const IInstruction& instr, OperandContainer op1, Ope } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); if (crf) diff --git a/src/Emulator/Core/CPU/InstructionsImpl/ADD.cpp b/src/Emulator/Core/CPU/InstructionsImpl/ADD.cpp index 1c3769c9..2abd63fb 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/ADD.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/ADD.cpp @@ -32,7 +32,7 @@ void HyperCPU::CPU::ExecADD(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -67,7 +67,7 @@ void HyperCPU::CPU::ExecADD(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -104,28 +104,28 @@ void HyperCPU::CPU::ExecADD(const IInstruction& instr, OperandContainer op1, Ope case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = AdditionWillOverflow(op1.deref(), val); op1.deref() = HyperALU::__hcpu_add(op1.deref(), val); break; diff --git a/src/Emulator/Core/CPU/InstructionsImpl/AND.cpp b/src/Emulator/Core/CPU/InstructionsImpl/AND.cpp index 71301391..e38fcab6 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/AND.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/AND.cpp @@ -29,7 +29,7 @@ void HyperCPU::CPU::ExecAND(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -60,7 +60,7 @@ void HyperCPU::CPU::ExecAND(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -93,25 +93,25 @@ void HyperCPU::CPU::ExecAND(const IInstruction& instr, OperandContainer op1, Ope case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_and(op1.deref(), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_and(op1.deref(), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_and(op1.deref(), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_and(op1.deref(), val); break; } diff --git a/src/Emulator/Core/CPU/InstructionsImpl/ANDN.cpp b/src/Emulator/Core/CPU/InstructionsImpl/ANDN.cpp index bf1b3568..66cabb07 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/ANDN.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/ANDN.cpp @@ -37,7 +37,7 @@ void HyperCPU::CPU::ExecANDN(const IInstruction& instr, OperandContainer op1, Op } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -72,7 +72,7 @@ void HyperCPU::CPU::ExecANDN(const IInstruction& instr, OperandContainer op1, Op } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -109,28 +109,28 @@ void HyperCPU::CPU::ExecANDN(const IInstruction& instr, OperandContainer op1, Op case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); auto& dst = op1.deref(); dst = __hcpu_and(__hcpu_not(dst), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); auto& dst = op1.deref(); dst = __hcpu_and(__hcpu_not(dst), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); auto& dst = op1.deref(); dst = __hcpu_and(__hcpu_not(dst), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); auto& dst = op1.deref(); dst = __hcpu_and(__hcpu_not(dst), val); break; diff --git a/src/Emulator/Core/CPU/InstructionsImpl/CMP.cpp b/src/Emulator/Core/CPU/InstructionsImpl/CMP.cpp index 957ab3fb..e6be9218 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/CMP.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/CMP.cpp @@ -28,7 +28,7 @@ void HyperCPU::CPU::ExecCMP(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr; + std::uint64_t ptr = 0; std::memcpy(&ptr, op2.ptr(), 8); switch (instr.m_opcode_mode) { @@ -96,7 +96,7 @@ void HyperCPU::CPU::ExecCMP(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::RM_M: { - std::uint64_t ptr1, ptr2 = 0; + std::uint64_t ptr1 = 0, ptr2 = 0; std::memcpy(&ptr1, op1.ptr(), 8); ptr2 = HyperCPU::bit_cast(op2); @@ -167,7 +167,7 @@ void HyperCPU::CPU::ExecCMP(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::M_R: { - std::size_t ptr = HyperCPU::bit_cast(op1); + auto ptr = HyperCPU::bit_cast(op1); switch (instr.m_opcode_mode) { case Mode::b8: @@ -195,16 +195,16 @@ void HyperCPU::CPU::ExecCMP(const IInstruction& instr, OperandContainer op1, Ope switch (res) { case -1: - zrf = 0; - crf = 1; + zrf = false; + crf = true; break; case 0: - zrf = 1; - crf = 0; + zrf = true; + crf = false; break; case 1: - zrf = 0; - crf = 0; + zrf = false; + crf = false; break; } } diff --git a/src/Emulator/Core/CPU/InstructionsImpl/DIV.cpp b/src/Emulator/Core/CPU/InstructionsImpl/DIV.cpp index 820f65b3..f09f2ba9 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/DIV.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/DIV.cpp @@ -12,7 +12,7 @@ void HyperCPU::CPU::ExecDIV(const IInstruction& instr, OperandContainer op1, Ope switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t& dst = op1.deref(); + auto& dst = op1.deref(); *x1 = __hcpu_div_remainder(dst, static_cast(*x2)); dst = __hcpu_div(dst, static_cast(*x2)); break; diff --git a/src/Emulator/Core/CPU/InstructionsImpl/MOV.cpp b/src/Emulator/Core/CPU/InstructionsImpl/MOV.cpp index d873c6c5..211d03f4 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/MOV.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/MOV.cpp @@ -24,7 +24,7 @@ void HyperCPU::CPU::ExecMOV(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr; + std::uint64_t ptr = 0; std::memcpy(&ptr, op2.ptr(), 8); switch (instr.m_opcode_mode) { @@ -92,7 +92,7 @@ void HyperCPU::CPU::ExecMOV(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::RM_M: { - std::uint64_t ptr1, ptr2 = 0; + std::uint64_t ptr1 = 0, ptr2 = 0; std::memcpy(&ptr1, op1.ptr(), 8); ptr2 = op2; @@ -167,7 +167,7 @@ void HyperCPU::CPU::ExecMOV(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::M_R: { - std::size_t ptr1 = HyperCPU::bit_cast(op1); + auto ptr1 = HyperCPU::bit_cast(op1); switch (instr.m_opcode_mode) { case Mode::b8: { diff --git a/src/Emulator/Core/CPU/InstructionsImpl/MUL.cpp b/src/Emulator/Core/CPU/InstructionsImpl/MUL.cpp index 177be42f..2dadd284 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/MUL.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/MUL.cpp @@ -33,7 +33,7 @@ void HyperCPU::CPU::ExecMUL(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -68,7 +68,7 @@ void HyperCPU::CPU::ExecMUL(const IInstruction& instr, OperandContainer op1, Ope } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -105,28 +105,28 @@ void HyperCPU::CPU::ExecMUL(const IInstruction& instr, OperandContainer op1, Ope case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = multiplication_will_overflow(op1.deref(), val); op1.deref() = __hcpu_mul(op1.deref(), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = multiplication_will_overflow(op1.deref(), val); op1.deref() = __hcpu_mul(op1.deref(), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = multiplication_will_overflow(op1.deref(), val); op1.deref() = __hcpu_mul(op1.deref(), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); ovf = multiplication_will_overflow(op1.deref(), val); op1.deref() = __hcpu_mul(op1.deref(), val); break; diff --git a/src/Emulator/Core/CPU/InstructionsImpl/OR.cpp b/src/Emulator/Core/CPU/InstructionsImpl/OR.cpp index b8265ef9..67a883b9 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/OR.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/OR.cpp @@ -27,7 +27,7 @@ void HyperCPU::CPU::ExecOR(const IInstruction& instr, OperandContainer op1, Oper } case OperandTypes::R_RM: { - std::uint64_t ptr = HyperCPU::bit_cast_from(op2.ptr()); + auto ptr = HyperCPU::bit_cast_from(op2.ptr()); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -58,7 +58,7 @@ void HyperCPU::CPU::ExecOR(const IInstruction& instr, OperandContainer op1, Oper } case OperandTypes::R_M: { - std::uint64_t ptr = HyperCPU::bit_cast(op2); + auto ptr = HyperCPU::bit_cast(op2); switch (instr.m_opcode_mode) { case Mode::b8: { @@ -91,25 +91,25 @@ void HyperCPU::CPU::ExecOR(const IInstruction& instr, OperandContainer op1, Oper case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_or(op1.deref(), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_or(op1.deref(), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_or(op1.deref(), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() = __hcpu_or(op1.deref(), val); break; } diff --git a/src/Emulator/Core/CPU/InstructionsImpl/SHFL.cpp b/src/Emulator/Core/CPU/InstructionsImpl/SHFL.cpp index 73771961..2adfb09e 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/SHFL.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/SHFL.cpp @@ -26,25 +26,25 @@ void HyperCPU::CPU::ExecSHFL(const IInstruction& instr, OperandContainer op1, Op case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() <<= val; break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() <<= val; break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() <<= val; break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() <<= val; break; } diff --git a/src/Emulator/Core/CPU/InstructionsImpl/SHFR.cpp b/src/Emulator/Core/CPU/InstructionsImpl/SHFR.cpp index 27ffbb7a..853aa78c 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/SHFR.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/SHFR.cpp @@ -26,25 +26,25 @@ void HyperCPU::CPU::ExecSHFR(const IInstruction& instr, OperandContainer op1, Op case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() >>= val; break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() >>= val; break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() >>= val; break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); op1.deref() >>= val; break; } diff --git a/src/Emulator/Core/CPU/InstructionsImpl/SUB.cpp b/src/Emulator/Core/CPU/InstructionsImpl/SUB.cpp index 18eaae71..4796b374 100644 --- a/src/Emulator/Core/CPU/InstructionsImpl/SUB.cpp +++ b/src/Emulator/Core/CPU/InstructionsImpl/SUB.cpp @@ -105,28 +105,28 @@ void HyperCPU::CPU::ExecSUB(const IInstruction& instr, OperandContainer op1, Ope case OperandTypes::R_IMM: { switch (instr.m_opcode_mode) { case Mode::b8: { - std::uint8_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); udf = SubtractionWillUnderflow(op1.deref(), val); op1.deref() = __hcpu_sub(op1.deref(), val); break; } case Mode::b16: { - std::uint16_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); udf = SubtractionWillUnderflow(op1.deref(), val); op1.deref() = __hcpu_sub(op1.deref(), val); break; } case Mode::b32: { - std::uint32_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); udf = SubtractionWillUnderflow(op1.deref(), val); op1.deref() = __hcpu_sub(op1.deref(), val); break; } case Mode::b64: { - std::uint64_t val = HyperCPU::bit_cast(op2); + auto val = HyperCPU::bit_cast(op2); udf = SubtractionWillUnderflow(op1.deref(), val); op1.deref() = __hcpu_sub(op1.deref(), val); break; diff --git a/src/Emulator/Core/CPU/Interrupts/InterruptHandler.cpp b/src/Emulator/Core/CPU/Interrupts/InterruptHandler.cpp index 09eeedb2..78c4083b 100644 --- a/src/Emulator/Core/CPU/Interrupts/InterruptHandler.cpp +++ b/src/Emulator/Core/CPU/Interrupts/InterruptHandler.cpp @@ -10,7 +10,7 @@ void HyperCPU::CPU::TriggerInterrupt(HyperCPU::cpu_exceptions exception) { spdlog::error("XIP exceeded the binary size, aborting!"); std::abort(); } - + if (!ivt_initialized || pending_interrupt.has_value()) { spdlog::error("Interrupt was triggered, but failed to execute handler! XIP: {}", *xip); std::abort(); @@ -29,7 +29,7 @@ void HyperCPU::CPU::TriggerInterrupt(HyperCPU::cpu_exceptions exception) { } void HyperCPU::CPU::RunInterruptSubroutine() { - while (1) { + while (true) { if (halted) return; diff --git a/src/Emulator/Core/CPU/OperandsEvaluation.cpp b/src/Emulator/Core/CPU/OperandsEvaluation.cpp index efbba705..3c0f6188 100644 --- a/src/Emulator/Core/CPU/OperandsEvaluation.cpp +++ b/src/Emulator/Core/CPU/OperandsEvaluation.cpp @@ -121,22 +121,22 @@ std::pair HyperCPU::CPU: case OperandTypes::R_IMM: { switch (md) { case Mode::b8: { - std::uint8_t imm8; + std::uint8_t imm8 = 0; std::memcpy(&imm8, &op2, sizeof(std::uint8_t)); return std::make_pair(GetRegister(op1), OperandContainer{HyperCPU::bit_cast(imm8)}); } case Mode::b16: { - std::uint16_t imm16; + std::uint16_t imm16 = 0; std::memcpy(&imm16, &op2, sizeof(std::uint16_t)); return std::make_pair(GetRegister(op1), OperandContainer{HyperCPU::bit_cast(imm16)}); } case Mode::b32: { - std::uint32_t imm32; + std::uint32_t imm32 = 0; std::memcpy(&imm32, &op2, sizeof(std::uint32_t)); return std::make_pair(GetRegister(op1), OperandContainer{HyperCPU::bit_cast(imm32)}); } case Mode::b64: { - std::uint64_t imm64; + std::uint64_t imm64 = 0; std::memcpy(&imm64, &op2, sizeof(std::uint64_t)); return std::make_pair(GetRegister(op1), OperandContainer{HyperCPU::bit_cast(imm64)}); } diff --git a/src/Emulator/Main.cpp b/src/Emulator/Main.cpp index 80634cef..ee067845 100644 --- a/src/Emulator/Main.cpp +++ b/src/Emulator/Main.cpp @@ -11,7 +11,7 @@ #endif HyperCPU::GenericHeader ParseHeader(std::ifstream& file) { - HyperCPU::GenericHeader header; + HyperCPU::GenericHeader header{}; file.read(reinterpret_cast(&header), sizeof(header)); return header; @@ -44,7 +44,7 @@ std::uint64_t ParseMemoryString(const std::string& str) { return std::numeric_limits::max(); } - std::uint64_t multiplier; + std::uint64_t multiplier = 0; switch (suffix) { case 'K': multiplier = 1024ULL; @@ -62,7 +62,7 @@ std::uint64_t ParseMemoryString(const std::string& str) { return std::numeric_limits::max(); } - std::uint64_t result; + std::uint64_t result = 0; auto [ptr, ec] = std::from_chars(numeric_part.data(), numeric_part.end(), result); if (ec != std::errc() || ptr != numeric_part.end()) { return std::numeric_limits::max(); @@ -80,37 +80,37 @@ int VerifyBinaryFile(std::int64_t filesize, HyperCPU::GenericHeader header) { spdlog::error("Invalid binary header! (excepted {} bytes, got {})", sizeof(HyperCPU::GenericHeader), filesize); return 1; } - + if (header.magic != HyperCPU::magic) { spdlog::error("Invalid magic!"); return 1; } switch (header.version) { - case HyperCPU::Version::PreRelease: - case HyperCPU::Version::Release1_0: - break; - default: - spdlog::error("Invalid release field!"); - return 1; + case HyperCPU::Version::PreRelease: + case HyperCPU::Version::Release1_0: + break; + default: + spdlog::error("Invalid release field!"); + return 1; } switch (header.type) { - case HyperCPU::FileType::Binary: - break; - case HyperCPU::FileType::Object: - spdlog::error("Executing object files is not supported, please link it first!"); - return 1; - default: - spdlog::error("Invalid type field!"); - return 1; - } - + case HyperCPU::FileType::Binary: + break; + case HyperCPU::FileType::Object: + spdlog::error("Executing object files is not supported, please link it first!"); + return 1; + default: + spdlog::error("Invalid type field!"); + return 1; + } + if (filesize != (sizeof(HyperCPU::GenericHeader) + header.code_size)) { spdlog::error("Invalid binary code! (expected {} bytes, got {})", header.code_size, (filesize - sizeof(HyperCPU::GenericHeader))); return 1; } - + return 0; } @@ -155,7 +155,7 @@ int main(int argc, char** argv) { spdlog::error("The binary file is too small! (No binary header?)"); return 1; } - + std::int64_t filesize = std::filesystem::file_size(source); std::int64_t binarysize = filesize - sizeof(HyperCPU::GenericHeader); @@ -164,7 +164,7 @@ int main(int argc, char** argv) { if (VerifyBinaryFile(filesize, header)) { return 1; } - + std::unique_ptr buf(new char[binarysize]); file.read(buf.get(), binarysize); diff --git a/src/Pog/BUILD.bazel b/src/Pog/BUILD.bazel index 5cd65d04..9143bf5b 100644 --- a/src/Pog/BUILD.bazel +++ b/src/Pog/BUILD.bazel @@ -8,10 +8,6 @@ cc_library( exclude = ["Pog.hpp"], ), visibility = ["//visibility:private"], - deps = [ - "@fmt", - "@re2", - ], ) precompiled_headers( @@ -20,5 +16,7 @@ precompiled_headers( visibility = ["//visibility:public"], deps = [ ":pog_core", + "@fmt", + "@re2", ], ) diff --git a/src/Pog/Token.hpp b/src/Pog/Token.hpp index 239f95d7..2f049fd6 100644 --- a/src/Pog/Token.hpp +++ b/src/Pog/Token.hpp @@ -5,7 +5,7 @@ #include #include -#include +#include "re2/re2.h" #include "Pog/Symbol.hpp" diff --git a/tests/BUILD.bazel b/tests/BUILD.bazel index 4a50d10c..35ba797f 100644 --- a/tests/BUILD.bazel +++ b/tests/BUILD.bazel @@ -11,7 +11,7 @@ precompiled_headers( name = "pch_gtest", main = "gtest.hpp", deps = [ - "@gtest//:gtest-libgtest", + "@googletest//:gtest", ], ) diff --git a/tests/Integration/BUILD.bazel b/tests/Integration/BUILD.bazel index f5269665..b21f54ff 100644 --- a/tests/Integration/BUILD.bazel +++ b/tests/Integration/BUILD.bazel @@ -1,16 +1,31 @@ -load("@rules_cc//cc:defs.bzl", "cc_test") +load("@rules_cc//cc:defs.bzl", "cc_binary", "cc_library", "cc_test") -cc_test( - name = "integration-test", +cc_library( + name = "integration_tests_lib", srcs = glob(["**/*.cpp"]), - linkstatic = True, deps = [ "//src/Assembler:assembler_core", "//src/Emulator:emulator_core", "//src/PCH:pch_cstd", "//tests:pch_gtest", "//tests:test_fixtures", - "@fmt", - "@gtest//:gtest-gmock_main", + ], + alwayslink = True, +) + +cc_test( + name = "integration-test", + deps = [ + ":integration_tests_lib", + "@googletest//:gtest_main", + ], +) + +cc_binary( + name = "packaged-integration-test", + visibility = ["//tools/packaging:__pkg__"], + deps = [ + ":integration_tests_lib", + "@googletest//:gtest_main", ], ) diff --git a/tests/Modular/BUILD.bazel b/tests/Modular/BUILD.bazel index 04a2b0bd..2a74c439 100644 --- a/tests/Modular/BUILD.bazel +++ b/tests/Modular/BUILD.bazel @@ -1,19 +1,31 @@ -load("@rules_cc//cc:defs.bzl", "cc_test") +load("@rules_cc//cc:defs.bzl", "cc_binary", "cc_library", "cc_test") -cc_test( - name = "modular-test", - # TODO: remove when tests are fixed - srcs = glob( - ["**/*.cpp"] - ), - linkstatic = True, +cc_library( + name = "modular_tests_lib", + srcs = glob(["**/*.cpp"]), deps = [ "//src/Assembler:assembler_core", "//src/Emulator:emulator_core", "//src/PCH:pch_cstd", "//tests:pch_gtest", "//tests:test_fixtures", - "@fmt", - "@gtest//:gtest-gmock_main", + ], + alwayslink = True, +) + +cc_test( + name = "modular-test", + deps = [ + ":modular_tests_lib", + "@googletest//:gtest_main", + ], +) + +cc_binary( + name = "packaged-modular-test", + visibility = ["//tools/packaging:__pkg__"], + deps = [ + ":modular_tests_lib", + "@googletest//:gtest_main", ], ) diff --git a/tests/Pog/BUILD.bazel b/tests/Pog/BUILD.bazel index 05d3a74e..ea09cdfd 100644 --- a/tests/Pog/BUILD.bazel +++ b/tests/Pog/BUILD.bazel @@ -1,14 +1,29 @@ -load("@rules_cc//cc:defs.bzl", "cc_test") +load("@rules_cc//cc:defs.bzl", "cc_binary", "cc_library", "cc_test") -cc_test( - name = "test-pog", +cc_library( + name = "pog_tests_lib", srcs = glob(["**/*.cpp"]), deps = [ "//src/PCH:pch_cstd", "//src/Pog:pog", "//tests:pch_gtest", - "@fmt", - "@gtest//:gtest-gmock_main", - "@re2", + ], + alwayslink = True, +) + +cc_test( + name = "test-pog", + deps = [ + ":pog_tests_lib", + "@googletest//:gtest_main", + ], +) + +cc_binary( + name = "packaged-test-pog", + visibility = ["//tools/packaging:__pkg__"], + deps = [ + ":pog_tests_lib", + "@googletest//:gtest_main", ], ) diff --git a/tools/bazel/BUILD.bazel b/tools/bazel/BUILD.bazel index 69b83cbe..488453fb 100644 --- a/tools/bazel/BUILD.bazel +++ b/tools/bazel/BUILD.bazel @@ -1 +1,9 @@ "Common macros, rules etc. used by HyperCPU" + +load("@bazel_skylib//rules:native_binary.bzl", "native_binary") + +native_binary( + name = "clang_tidy", + src = "@llvm_toolchain//:bin/clang-tidy", + out = "clang_tidy", +) diff --git a/tools/bazel/lint.bzl b/tools/bazel/lint.bzl new file mode 100644 index 00000000..e499a5c2 --- /dev/null +++ b/tools/bazel/lint.bzl @@ -0,0 +1,18 @@ +"Aspects for linting" + +load("@aspect_rules_lint//lint:clang_tidy.bzl", "lint_clang_tidy_aspect") +load("@aspect_rules_lint//lint:ruff.bzl", "lint_ruff_aspect") + +ruff = lint_ruff_aspect( + binary = Label("@aspect_rules_lint//format:ruff"), + configs = [ + Label("@//:.ruff.toml"), + ], +) + +clang_tidy = lint_clang_tidy_aspect( + binary = Label("//tools/bazel:clang_tidy"), + configs = [ + Label("@//:.clang-tidy"), + ], +) diff --git a/tools/bazel/pch.bzl b/tools/bazel/pch.bzl index 6f7eb9ae..3f141405 100644 --- a/tools/bazel/pch.bzl +++ b/tools/bazel/pch.bzl @@ -1,29 +1,25 @@ -"Custom target to support precompiled headers. Notice, this is relevant to end-consumer project, like ours" -# Inspired by: https://github.com/erenon/rules_pch +"Precompile Headers. Note: this is quite experimental." load("@bazel_tools//tools/cpp:toolchain_utils.bzl", "find_cpp_toolchain") load("@rules_cc//cc:action_names.bzl", "CPP_COMPILE_ACTION_NAME") -def _global_flags(ctx, cc_toolchain): - feature_configuration = cc_common.configure_features( - ctx = ctx, - cc_toolchain = cc_toolchain, - ) +def _feature_conf(ctx, cc_toolchain): + return cc_common.configure_features(ctx = ctx, cc_toolchain = cc_toolchain) + +def _global_flags(ctx, cc_toolchain, feature_configuration): compile_variables = cc_common.create_compile_variables( feature_configuration = feature_configuration, cc_toolchain = cc_toolchain, user_compile_flags = ctx.fragments.cpp.cxxopts + ctx.fragments.cpp.copts, ) - tc_flags = cc_common.get_memory_inefficient_command_line( + flags = cc_common.get_memory_inefficient_command_line( feature_configuration = feature_configuration, action_name = CPP_COMPILE_ACTION_NAME, variables = compile_variables, ) - if cc_toolchain.needs_pic_for_dynamic_libraries(feature_configuration = feature_configuration): - return tc_flags + ["-fPIC"] - - return tc_flags + flags = flags + ["-fPIC"] + return flags def _precompiled_headers_impl(ctx): files = ctx.attr.main.files.to_list() @@ -31,74 +27,103 @@ def _precompiled_headers_impl(ctx): fail("expected a single aggregated header to compile, got: {}".format(files)) main_file = files[0] - args = ctx.actions.args() - - # add args specified by the toolchain and on the command line cc_toolchain = find_cpp_toolchain(ctx) - args.add_all(_global_flags(ctx, cc_toolchain)) - - # collect headers, include paths and defines of dependencies - headers = [] - for dep in ctx.attr.deps: - if not CcInfo in dep: - fail("dep arguments must provide CcInfo (e.g: cc_library)") + feature_configuration = _feature_conf(ctx, cc_toolchain) - # collect exported header files - compilation_context = dep[CcInfo].compilation_context - headers.append(compilation_context.headers) + dep_ctxs = [] + for d in ctx.attr.deps: + if CcInfo in d: + dep_ctxs.append(d[CcInfo].compilation_context) + else: + fail("dep arguments must provide CcInfo (e.g. cc_library): {}".format(d)) - # add defines - for define in compilation_context.defines.to_list(): - args.add("-D" + define) + merged_ctx = cc_common.merge_compilation_contexts( + compilation_contexts = dep_ctxs, + ) - # add include dirs - for i in compilation_context.includes.to_list(): - args.add("-I" + i) + args = ctx.actions.args() + args.add_all(_global_flags(ctx, cc_toolchain, feature_configuration)) - args.add_all(compilation_context.quote_includes.to_list(), before_each = "-iquote") - args.add_all(compilation_context.system_includes.to_list(), before_each = "-isystem") + for define in merged_ctx.defines.to_list(): + args.add("-D" + define) + for define in getattr(merged_ctx, "local_defines", depset()).to_list(): + args.add("-D" + define) - inputs = depset(direct = [main_file], transitive = headers + [cc_toolchain.all_files]) + args.add_all(merged_ctx.system_includes.to_list(), before_each = "-isystem") + args.add_all(merged_ctx.includes.to_list() + merged_ctx.quote_includes.to_list(), before_each = "-I") - # add args specified for this rule args.add_all(ctx.attr.copts) - - # force compilation of header args.add("-xc++-header") args.add(main_file.path) - # specify output output = ctx.actions.declare_file("{}.pch".format(main_file.basename)) args.add("-o", output.path) - # Unless -MD is specified while creating the precompiled file, - # the .d file of the user of the precompiled file will not - # show the precompiled file: therefore bazel will not rebuild - # the user if the pch file changes. args.add("-MD") args.add("-MF", "/dev/null") + inputs = depset( + direct = [main_file], + transitive = [merged_ctx.headers, cc_toolchain.all_files], + ) + + compiler_tool = cc_common.get_tool_for_action( + feature_configuration = feature_configuration, + action_name = CPP_COMPILE_ACTION_NAME, + ) or cc_toolchain.compiler_executable + ctx.actions.run( inputs = inputs, outputs = [output], - executable = cc_toolchain.compiler_executable, + executable = compiler_tool, arguments = [args], mnemonic = "PrecompileHdrs", progress_message = "Pre-compiling header: {}".format(main_file.basename), ) - # create a CcInfo output that cc_binary rules can depend on - compilation_context = cc_common.create_compilation_context( + pch_ctx = cc_common.create_compilation_context( headers = depset(direct = [output, main_file]), includes = depset(direct = [output.dirname]), ) - main_cc_info = CcInfo(compilation_context = compilation_context, linking_context = None) - cc_info = cc_common.merge_cc_infos( - direct_cc_infos = [main_cc_info], - cc_infos = [dep[CcInfo] for dep in ctx.attr.deps if CcInfo in dep], + + merged_headers = depset(transitive = [merged_ctx.headers, pch_ctx.headers]) + merged_includes = depset(transitive = [ + merged_ctx.includes, + merged_ctx.quote_includes, + pch_ctx.includes, + ]) + + merged_quote_includes = depset(transitive = [ + merged_ctx.quote_includes, + ]) + + merged_system_includes = depset(transitive = [ + merged_ctx.system_includes, + ]) + + merged_out_compilation_ctx = cc_common.create_compilation_context( + headers = merged_headers, + includes = merged_includes, + quote_includes = merged_quote_includes, + system_includes = merged_system_includes, + defines = merged_ctx.defines, + local_defines = getattr(merged_ctx, "local_defines", depset()), + framework_includes = getattr(merged_ctx, "framework_includes", depset()), + ) + + dep_cc_infos = [d[CcInfo] for d in ctx.attr.deps if CcInfo in d] + merged_linking_ctx = cc_common.merge_linking_contexts( + linking_contexts = [ + i.linking_context + for i in dep_cc_infos + if hasattr(i, "linking_context") and i.linking_context + ], ) - return [cc_info] + return [CcInfo( + compilation_context = merged_out_compilation_ctx, + linking_context = merged_linking_ctx, + )] precompiled_headers = rule( implementation = _precompiled_headers_impl, @@ -106,7 +131,9 @@ precompiled_headers = rule( "main": attr.label(allow_files = True, mandatory = True), "deps": attr.label_list(), "copts": attr.string_list(), - "_cc_toolchain": attr.label(default = Label("@bazel_tools//tools/cpp:current_cc_toolchain")), + "_cc_toolchain": attr.label( + default = Label("@bazel_tools//tools/cpp:current_cc_toolchain"), + ), }, toolchains = ["@bazel_tools//tools/cpp:toolchain_type"], fragments = ["cpp"], diff --git a/tools/increment_version.py b/tools/increment_version.py index d2d43e34..d1582c8f 100755 --- a/tools/increment_version.py +++ b/tools/increment_version.py @@ -94,7 +94,7 @@ def update_module_file(self, file: Path, version: Version): module = self.__bazel_find_module(contents) current_version = self.__bazel_find_version(module) newly_versioned_module = module.replace( - current_version, f"version = \"{str(version)}\"" + current_version, f'version = "{str(version)}"' ) contents = contents.replace(module, newly_versioned_module) @@ -106,7 +106,7 @@ def update_readme(self, file: Path, version: Version): with open(file, "r") as fd: content = fd.read() - new_version = f'