exeex/edge-cores

Public

The shortest path from PyTorch to custom ASICs.

  • Stars129+17 tuần này
  • Forks6
  • Watchers1
  • Issues0
  • Ngày tạo08/08/2026
  • Cập nhật gần nhất28/10/2026
  • Ngôn ngữVerilog
  • Giấy phépApache-2.0
README.md27.0 KBRaw

edge-cores

The shortest way from PyTorch to ASICs.

Export PyTorch models to bare-metal C++ and run them on ASIC RTL with Verilator. Bring your own accelerator to the open-source edge-32 control processor, or start with the source-available edge-e3 reference NPU.

The flow uses the standard Clang/LLVM toolchain--installed with apt-get install on Ubuntu--instead of a custom compiler or patched LLVM/MLIR stack. Rather than adding an ASIC backend to the compiler, each ASIC exposes its operations through a C++ intrinsics header such as edge_intrinsic.hpp.

Document that interface in an intrinsic manual and capture the kernel workflow in a SKILL.md. GPT-5.5 and GPT-5.6 coding agents can then create hardware-aware kernels with the same ordinary clang++ toolchain on any ASIC platform. This removes custom compiler bring-up from the critical path and makes zero-day support for newly released Hugging Face models practical.

The simpler toolchain does not come at the expense of accelerator utilization. The maintained example/tensor reaches 93.59% effective MAC utilization on a 64x64x128 BF16 matmul, including packed weight DMA, circular weight loads, Tensor execution, and synchronization.

Run Llama 3 and Qwen 3.6 on edge-e3enc ASIC RTL

The current public flow demonstrates a single Llama 3 transformer block and a reduced single Qwen 3.6 full-attention decoder layer running on the edge-e3enc ASIC RTL through Verilator. The simulator combines the encrypted e3 core, public Edge32 RTL, and SRAM boundary models from edge-e3enc. The 8x8 BF16 Tensor ASIC has 128 KB of DTCM. This MVP demonstrates the complete PyTorch-to-ASIC path with compact single-layer workloads.

Both examples start as small PyTorch modules, compile to bare-metal C++, execute on the RTL, and compare their BF16 outputs with PyTorch.

The Qwen 3.6 path also demonstrates the zero-day workflow. After Llama 3 was supported, a follow-up agent prompt added the reduced Qwen 3.6 path in about five minutes without changing the existing C++ kernels. This is an MVP result, not a general five-minute guarantee; a new model requiring additional adaptation is expected to take closer to half an hour rather than days of compiler development.

First follow the edge-bringup workflow. It installs the required public submodules and creates the repository-owned .venv used by the commands below.

Run the Llama 3 block:

PYTHON=.venv/bin/python ./example/llama/run.sh

Run the Qwen 3.6 layer:

PYTHON=.venv/bin/python ./example/llama/run.sh \
  --model-file nnc/test/qwen36_source.py

The Qwen example is a 32-token, 64-wide, one-head compatibility slice. It preserves Q/K RMSNorm, the attention-output gate, SwiGLU MLP, and residual structure. See qwen36_coverage.md for the current MVP coverage and next implementation steps.

PyTorch to ASIC RTL: Minimal Example

The SiLU smoke test demonstrates the complete path with the smallest useful model.

1. Write and export a PyTorch model

import torch
import torch.nn as nn
import torch.nn.functional as F


class SmokeSilu(nn.Module):
    def forward(self, x: torch.Tensor) -> torch.Tensor:
        return F.silu(x)


model = SmokeSilu().eval()
example_args = (torch.randn(64, 64),)
exported = torch.export.export(model, example_args)

NNC consumes the same model and example arguments. Internally it reads the ExportedProgram, maps the exported aten.silu node to the Edge operator, and infers the generated ABI and tensor shapes.

2. Generate bare-metal C++

The compiler turns the exported graph into forward.hpp, init.hpp, and an optional weight.bin. The generated forward path contains a direct libnn call:

nnedge::op::silu(silu, x);

The generated headers are compiled with the shared C++ runtime into a freestanding RV32 ELF. There is no host-side PyTorch dependency in the target program.

3. Run it on the Verilated RTL

After the initial setup, one command generates the code, builds the RV32 image, runs it on the edge-e3enc Verilator model, and compares the BF16 output against PyTorch:

PYTHON=.venv/bin/python ./example/llama/run.sh \
  --model-file nnc/test/smoke_silu.py

Expected final result:

TEST PASS
COMPARE PASS values=4096

Generated C++, weights, ELF, memory image, simulator output, and comparison logs are kept under example/llama/build/smoke_silu/.

PyTorch model
    -> torch.export
    -> NNC graph lowering
    -> generated bare-metal C++
    -> RV32 ELF
    -> Verilated edge-e3enc RTL
    -> BF16 comparison with PyTorch

Choose Your Path

The maintained Edge example run scripts use scripts/build-verilator.sh, which builds the edge-e3enc simulator. CoreMark also includes a separate C906 run script for comparison.

  • Run edge-e3enc: build the encrypted Verilator model and execute the hello, tensor, and PyTorch-to-NNC examples.
  • Integrate your own accelerator: combine your RTL with edge-32, then define its instruction, memory, and verification paths.
  • Explore architecture research: experiment with dataflows, numerical formats, DMA, SRAM, interconnects, chiplets, or clusters.
  • Contribute to edge-32: file a centralized issue and prepare a focused, tested pull request.

Quick Start

Follow the maintained edge-bringup workflow for dependencies, repository setup, simulator builds, and smoke tests on macOS or Ubuntu.

Use $edge-bringup to set up this machine and run the initial smoke tests.

Architecture

Open RV32 integration platform

edge-32 provides a four-stage, single-issue, in-order RV32IMF processor with Zba for scalar control. It includes instruction decode, accelerator commands, caches, floating point, and integration points for DMA, SRAM, and custom compute.

Composed cores use this naming convention:

rv_core_name@asic_core_name

For example, edge-32@e3 combines the open edge-32 processor with the e3 ASIC set. A custom integration could use a name such as edge-32@your_asic_name.

edge-32@e3 reference composition

edge-32@e3 architecture showing the edge-32 processor, tensor unit, DMA, accelerator units, and shared DTCM

The current reference composition includes:

  • 16 KB instruction cache
  • 16 KB data cache
  • 128 KB DTCM
  • 8x8 BF16 tensor unit
  • DMA, activation(ACTU), comparison(CMPU), and cache-control interfaces

Use edge-e3 as a working system reference, not as a required template. Its public boundaries and encrypted RTL demonstrate one integration while your design retains its own architecture, repository, and license.

Bring Your Own Design

Add an accelerator or ASIC repository below src/ as a Git submodule and connect it to edge-32. A design can range from one operator to a complete compute and memory subsystem.

The integrate-your-design workflow covers the maintained integration path:

  • allocate an opcode8;
  • implement setcsr, start, and sync commands;
  • carry imm8 and GPR parameters through the snapshot path;
  • connect DMA, SRAM, and optional LSU debug access;
  • use the optional low-precision FPU instructions during bring-up; and
  • validate the integration with RTL and C++ tests.

Two development styles are equally welcome:

  • Start from real model, format, latency, cost, and deployment requirements and make product-level tradeoffs.
  • State a research scenario explicitly and push architecture, PPA, memory, or cluster scale as far as the experiment requires.

Example request for Codex:

Use $integrate-your-design to connect my accelerator and define its software, memory, and verification plan.

Reference Products

The Edge E/P families demonstrate complete NPU configurations built on the shared framework. They are reference products rather than limits on what edge-32 can support, and their RTL is not uniformly open.

Product overview

Product Positioning Tensor unit DTCM RTL availability
edge-e3 Transformer and CNN classifiers 8x8 128 KB Encrypted RTL available; open release planned
edge-e4 Compute-intensive workloads such as segmentation 16x16 256 KB Encrypted release planned
edge-e5 LLM inference with Q8/FP8 quantization 32x32 512 KB Not currently available
edge-p3 Higher-throughput classifiers 8x16 128 KB Not currently open
edge-p4 Higher-throughput segmentation 16x32 256 KB Not currently open
edge-p5 LLM inference with Q4/FP4 quantization 32x64 1 MB Not currently open

At 1 GHz, the E-series BF16 peak throughput ranges from 0.128 TFLOPS for edge-e3 to 2.048 TFLOPS for edge-e5. The P-series range is 0.256 to 4.096 TFLOPS. These are architectural peak values, not measured silicon results.

Release timing and licensing can change. Treat the product repository and its license as the authoritative source for availability.

High-Performance Software

The Edge intrinsic user manual is the main guide for writing efficient bare-metal software on Edge. It documents the DMA, Tensor, ACTU, CMPU, cache, BF16, cycle-counting, and simulator interfaces, with working C++ examples.

More importantly, it explains the programming patterns needed for performance: asynchronous start()/sync(), overlapping scalar and accelerator work, DMA buffer ownership, avoiding unnecessary cache maintenance, DTCM data placement, and circular DMA/weight-loading pipelines. Start there when writing a custom operator or tuning generated C++.

./example/tensor/run.sh

The tensor example is the smallest end-to-end demonstration of these patterns.

Performance Snapshot

The Tensor result below comes from the maintained example on the current edge-e3enc RTL. The Activation results are historical RTL simulation checkpoints. These are not silicon measurements.

Tensor

The maintained example/tensor case runs a 64x64x128 BF16 matrix multiplication with packed weight DMA and transpose circular weight loads:

Ideal MAC cycles Measured rdcycle interval Effective MAC utilization
8,192 8,753 93.59%

Effective MAC utilization is calculated as ideal MAC cycles / cycle_delta. The measured RTL interval starts before the packed weight DMA and ends after both edge_tensor_sync() and edge_dma_sync(), so it includes DMA, circular weight loading, Tensor execution, loop/control overhead, and final synchronization. One-time test-data initialization and the subsequent output copy back to DRAM are outside this interval. Older checkpoints published this same timing boundary through X30; the current example prints cycle_delta. X31 carries the program exit code in the current harness.

Run the same public example with:

./example/tensor/run.sh

Activation

Workload Result
4,096-element BF16 SiLU 99.49% pipeline utilization
4,096-element BF16 Softmax 99.59% pipeline utilization

See the tensor example, ACTU example, and Llama operator profile for implementation and measurement details.

Documentation

Goal Entry point
Set up and run edge-e3 edge-bringup
Integrate an accelerator integrate-your-design
Write high-performance software Edge intrinsic user manual
Run the hello smoke Hello example
Debug FP4 scalar conversion FP4 debug example
Debug FP8/BF16 and floating printf FP8/BF16 debug example
Run tensor matmul Tensor example
Compare scalar CoreMark cycles CoreMark example
Run PyTorch-to-NNC Llama example
Run synthesis profiles Synthesis guide
Understand the SoC harness SoC guide
Contribute a change Contributing guide
Review repository licenses Licensing guide

Research

Use Edge32 to avoid rebuilding scalar control, accelerator command issue, simulation, and software infrastructure for each architecture experiment. Unconventional or deliberately idealized assumptions are welcome when they are stated clearly and help isolate a research question.

When publishing results, distinguish the edge-cores contribution—such as the four-stage, single-issue Edge32 processor and its accelerator integration—from the new accelerator, dataflow, PPA, or application contribution. Use references.bib for the canonical citation.

Contributing

File issues in the centralized edge-cores issue tracker, including issues involving submodules. Do not file them in a submodule's own tracker.

Read CONTRIBUTING.md for the development and validation workflow. Repository templates are provided for both issues and pull requests.

Codex users can also invoke the maintained contribution workflow:

Use $edge-contribution to prepare this change for an edge-cores pull request.

License

The C++ libraries, Python compiler and runtime tools, scripts, examples, SoC harness RTL, documentation, and automation maintained directly in edge-cores are licensed under Apache-2.0.

The reusable edge-32 processor is licensed under CERN-OHL-P-2.0. Edge product repositories and generated RTL may use different licenses. In particular, edge-e3 is source-available under the edge-e3 Hardware License 1.0 and is not OSI-approved open-source hardware.

See LICENSING.md for the repository and submodule boundaries, and src/edge-e3enc/LICENSE.md for the complete edge-e3 terms.

Nội dung README thuộc về exeex và cộng đồng đóng góp, giấy phép Apache-2.0. Nguồn: github.com/exeex/edge-cores