Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/main' into sgh/tcp
Browse files Browse the repository at this point in the history
  • Loading branch information
sgherbst committed May 31, 2024
2 parents e223d47 + 2292247 commit 135ea6c
Show file tree
Hide file tree
Showing 12 changed files with 526 additions and 158 deletions.
2 changes: 1 addition & 1 deletion examples/umi_endpoint/test.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ def main():
dut = build_testbench()

# create queues
umi = UmiTxRx("to_rtl.q", "from_rtl.q", fresh=True)
umi = UmiTxRx("udev_req.q", "udev_resp.q", fresh=True)

# launch the simulation
dut.simulate()
Expand Down
6 changes: 1 addition & 5 deletions examples/umi_endpoint/testbench.sv
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,7 @@ module testbench (
parameter integer CW=32;
parameter integer AW=64;

`SB_UMI_WIRES(udev_req, DW, CW, AW);
`QUEUE_TO_UMI_SIM(udev_req, DW, CW, AW, "to_rtl.q");

`SB_UMI_WIRES(udev_resp, DW, CW, AW);
`UMI_TO_QUEUE_SIM(udev_resp, DW, CW, AW, "from_rtl.q");
`SWITCHBOARD_SIM_PORT(udev, DW);

reg nreset = 1'b0;
wire [AW-1:0] loc_addr;
Expand Down
2 changes: 1 addition & 1 deletion examples/umi_gpio/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,4 +21,4 @@ Here's what the interaction looks like from the Python perspective (with referen

Under the hood, these reads and writes are implemented using UMI transactions. For example, if you write `gpio.o[7:0] = 42`, a UMI write request is sent to a switchboard connection, indicating that bits 7-0 should be written to the value `42`.

From the RTL simulation perspective, bit-level interaction happens through instances of the `umi_gpio` module, which is provided by the switchboard repository and automatically included when using `SbDut`. Connect bit-level signals to be read from Python to the `gpio_in` port of `umi_gpio`, and similarly connect bit-level signals to be written from Python to the `gpio_out` port of `umi_gpio`. The width of the `gpio_in` port is set by the `IWIDTH` parameter and the width of the `gpio_out` port is set by the `OWIDTH` parameter; the values set for those parameters in RTL should match the values provided to the `UmiTxRx.gpio(...)` method when constructing a `UmiGpio` object.
From the RTL simulation perspective, bit-level interaction happens through instances of the `umi_gpio` module, which is provided by the switchboard repository. Connect bit-level signals to be read from Python to the `gpio_in` port of `umi_gpio`, and similarly connect bit-level signals to be written from Python to the `gpio_out` port of `umi_gpio`. The width of the `gpio_in` port is set by the `IWIDTH` parameter and the width of the `gpio_out` port is set by the `OWIDTH` parameter; the values set for those parameters in RTL should match the values provided to the `UmiTxRx.gpio(...)` method when constructing a `UmiGpio` object.
39 changes: 39 additions & 0 deletions examples/umi_gpio/funcs.v
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
// Copyright (c) 2024 Zero ASIC Corporation
// This code is licensed under Apache License 2.0 (see LICENSE for details)

`default_nettype none

module funcs (
input [7:0] a,
input [7:0] b,
output [7:0] c,
output [7:0] d,
input [127:0] e,
output [127:0] f,
output [127:0] g,
input h,
input i,
output j,
output k,
output l,
input [7:0] m,
input [7:0] n,
output [7:0] o,
input p,
output q,
inout vdd,
inout vss
);

assign c = a + 8'd12;
assign d = b - 8'd34;
assign f = e;
assign g = ~e;
assign j = h ^ i;
assign k = h & i;
assign o = m + n;
assign q = p;

endmodule

`default_nettype wire
140 changes: 121 additions & 19 deletions examples/umi_gpio/test.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,26 +5,53 @@
# Copyright (c) 2024 Zero ASIC Corporation
# This code is licensed under Apache License 2.0 (see LICENSE for details)

import random
from switchboard import UmiTxRx, SbDut
import umi
import random
from switchboard import SbNetwork, sb_path


def main():
# build the simulator
dut = build_testbench()

# create queues
umi = UmiTxRx("to_rtl.q", "from_rtl.q", fresh=True)
owidth = 512
iwidth = 512

net = SbNetwork(cmdline=True, single_netlist=True)

umi_gpio = net.instantiate(make_umi_gpio(net, owidth=owidth, iwidth=iwidth))
funcs = net.instantiate(make_funcs(net))

net.connect(umi_gpio.gpio_out[7:0], funcs.a)
net.connect(funcs.b, umi_gpio.gpio_out[15:8])
net.connect(umi_gpio.gpio_in[7:0], funcs.c)
net.connect(funcs.d, umi_gpio.gpio_in[15:8])
net.connect(umi_gpio.gpio_out[127:0], funcs.e)
net.connect(funcs.f, umi_gpio.gpio_in[255:128])
net.connect(umi_gpio.gpio_in[383:256], funcs.g)
net.connect(umi_gpio.gpio_out[128], funcs.h)
net.connect(funcs.i, umi_gpio.gpio_out[129])
net.connect(umi_gpio.gpio_in[384], funcs.j)
net.connect(funcs.k, umi_gpio.gpio_in[385])
net.connect(funcs.m[1:0], 3)
net.connect(umi_gpio.gpio_out[132:129], funcs.m[5:2])
net.connect(2, funcs.m[7:6])
net.connect(funcs.n, 33)
net.connect(umi_gpio.gpio_in[393:386], funcs.o)
net.connect(funcs.p, 1)
net.connect(umi_gpio.gpio_in[394], funcs.q)
net.connect(funcs.vss, 0)

net.external(umi_gpio.udev_req, txrx='udev')
net.external(umi_gpio.udev_resp, txrx='udev')

# launch the simulation
dut.simulate()
net.build()
net.simulate()

# instantiate TX and RX queues. note that these can be instantiated without
# specifying a URI, in which case the URI can be specified later via the
# "init" method

gpio = umi.gpio(owidth=128, iwidth=384, init=0xcafed00d)
umi = net.intfs['udev']
gpio = umi.gpio(owidth=owidth, iwidth=iwidth, init=0xcafed00d)

print(f'Initial value: 0x{gpio.o[:]:x}')
assert gpio.o[:] == 0xcafed00d
Expand Down Expand Up @@ -55,8 +82,8 @@ def main():

stimulus = random.randint(0, (1 << 128) - 1)

gpio.o[:] = stimulus
print(f'Wrote gpio.o[:] = 0x{gpio.o[:]:032x}')
gpio.o[127:0] = stimulus
print(f'Wrote gpio.o[127:0] = 0x{gpio.o[127:0]:032x}')

c = gpio.i[255:128]
print(f'Read gpio.i[255:128] = 0x{c:032x}')
Expand All @@ -66,20 +93,95 @@ def main():
print(f'Read gpio.i[383:256] = 0x{d:032x}')
assert d == (~stimulus) & ((1 << 128) - 1)

print('PASS!')
for h in [0, 1]:
for i in [0, 1]:
gpio.o[128] = h
gpio.o[129] = i

j = gpio.i[384]
k = gpio.i[385]

def build_testbench():
dut = SbDut(cmdline=True)
print(f'Wrote gpio.o[128]={h}, gpio.o[129]={i}')
print(f'Read gpio.i[384]={j}, gpio.i[385]={k}')

dut.input('testbench.sv')
assert j == h ^ i
assert k == h & i

dut.use(umi)
dut.add('option', 'library', 'umi')
gpio.o[132:129] = 0b1010
o = gpio.i[393:386]
print(f'Wrote gpio.o[132:129]=0b1010, read gpio.i[393:386]={o}')
assert o == 204

q = gpio.i[394]
print(f'Read gpio.i[394]={q}')
assert q == 1

print('PASS!')

dut.build()

return dut
def make_umi_gpio(net, owidth, iwidth):
dw = 256
aw = 64
cw = 32

parameters = dict(
DW=dw,
AW=aw,
CW=cw,
OWIDTH=owidth,
IWIDTH=iwidth
)

interfaces = {
'udev_req': dict(type='umi', dw=dw, aw=aw, cw=cw, direction='input'),
'udev_resp': dict(type='umi', dw=dw, aw=aw, cw=cw, direction='output'),
'gpio_out': dict(type='gpio', direction='output', width=owidth),
'gpio_in': dict(type='gpio', direction='input', width=iwidth)
}

resets = ['nreset']

block = net.make_dut('umi_gpio', parameters=parameters, interfaces=interfaces, resets=resets)

block.use(umi)
block.add('option', 'library', 'umi')

block.input(sb_path() / 'verilog' / 'common' / 'umi_gpio.v')

return block


def make_funcs(net):
interfaces = {
'a': dict(type='gpio', direction='input', width=8),
'b': dict(type='gpio', direction='input', width=8),
'c': dict(type='gpio', direction='output', width=8),
'd': dict(type='gpio', direction='output', width=8),
'e': dict(type='gpio', direction='input', width=128),
'f': dict(type='gpio', direction='output', width=128),
'g': dict(type='gpio', direction='output', width=128),
'h': dict(type='gpio', direction='input', width=1),
'i': dict(type='gpio', direction='input'),
'j': dict(type='gpio', direction='output'),
'k': dict(type='gpio', direction='output', width=1),
'l': dict(type='gpio', direction='output', width=8), # intentionally unused
'm': dict(type='gpio', direction='input', width=8),
'n': dict(type='gpio', direction='input', width=8),
'o': dict(type='gpio', direction='output', width=8),
'p': dict(type='gpio', direction='input'),
'q': dict(type='gpio', direction='output'),
'vss': dict(type='gpio', direction='inout')
}

tieoffs = {
'vdd': "1'b1"
}

block = net.make_dut('funcs', interfaces=interfaces, tieoffs=tieoffs, clocks=[])

block.input('funcs.v')

return block


if __name__ == '__main__':
Expand Down
61 changes: 0 additions & 61 deletions examples/umi_gpio/testbench.sv

This file was deleted.

2 changes: 1 addition & 1 deletion setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
from setuptools import setup, find_packages
from pybind11.setup_helpers import Pybind11Extension, build_ext

__version__ = "0.2.3"
__version__ = "0.2.5"

#################################################################################
# parse_reqs, long_desc from https://github.com/siliconcompiler/siliconcompiler #
Expand Down
1 change: 1 addition & 0 deletions switchboard/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,3 +22,4 @@
from .axi import AxiTxRx
from .network import SbNetwork, TcpIntf
from .autowrap import flip_intf
from .switchboard import path as sb_path
Loading

0 comments on commit 135ea6c

Please sign in to comment.