Skip to content

Commit 4ee025d

Browse files
committed
Merge branch 'main' into feature/compact-pipeline
2 parents 373f019 + c55b00a commit 4ee025d

File tree

5 files changed

+76
-58
lines changed

5 files changed

+76
-58
lines changed

generator/cdc_utils.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ def _assign():
2222

2323

2424
@block
25-
def ff_synchronizer(clk, rst, chain_out, chain_in, stages=2, chain_rst_value=0):
25+
def ff_synchronizer(clk, rst, chain_out, chain_in, stages=3, chain_rst_value=0):
2626
"""
2727
Flip-Flop based synchronizer. Can be used to stabilize signals which are crossing clock domains.
2828
Generates a chain with ff_stages flip flops. Use only with 1 bit values if you are not certain
@@ -43,7 +43,7 @@ def ff_synchronizer(clk, rst, chain_out, chain_in, stages=2, chain_rst_value=0):
4343

4444

4545
@block
46-
def areset_synchronizer(clk, async_rst, sync_rst, min_reset_cycles=2):
46+
def areset_synchronizer(clk, async_rst, sync_rst, min_reset_cycles=3):
4747
"""
4848
Synchronizer for async reset signals. Uses internally a flip-flop synchronizer.
4949
:param clk: clock of target domain

generator/generator.py

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -262,9 +262,10 @@ def build(*config_files, name=None, config=None):
262262
2. Invokes :func:`convert` to get generated solver in verilog.
263263
3. Create build directory for synthesis with OPAE tools.
264264
4. Preserving solver.v
265-
5. Start synthesis and fitting.
266-
6. Prepend afu with authentication blocks (with an empty signature chain)
267-
7. Create solver file by combining gbs file and solver config.
265+
5. Patch build process
266+
6. Start synthesis and fitting.
267+
7. Prepend afu with authentication blocks (with an empty signature chain)
268+
8. Create solver file by combining gbs file and solver config.
268269
:return:
269270
"""
270271
if name is None:
@@ -292,9 +293,15 @@ def build(*config_files, name=None, config=None):
292293
generated_solver_path = os.path.join(generator_path, 'out', 'solver.v')
293294
shutil.copy(generated_solver_path, build_path)
294295

295-
# 5. Start synthesis and fitting.
296+
# 5. Patch build process
297+
clock_crossing_sdc_path = os.path.abspath(os.path.join(generator_path, 'static', 'clock_crossing.sdc'))
298+
project_qsf_path = os.path.join(build_path, 'build', 'afu_default.qsf')
299+
with open(project_qsf_path, 'a') as project_file:
300+
project_file.write(f'\nset_global_assignment -name SDC_FILE "{clock_crossing_sdc_path}"\n')
301+
302+
# 6. Start synthesis and fitting.
296303
log_file_path = os.path.join(build_path, 'quartus-run.log')
297-
with open(log_file_path, "w") as log_file:
304+
with open(log_file_path, 'w') as log_file:
298305
subprocess.run(
299306
['${OPAE_PLATFORM_ROOT}/bin/run.sh'],
300307
shell=True,
@@ -303,13 +310,13 @@ def build(*config_files, name=None, config=None):
303310
stderr=subprocess.STDOUT
304311
).check_returncode()
305312

306-
# 6. Prepend afu with authentication blocks (with an empty signature chain)
313+
# 7. Prepend afu with authentication blocks (with an empty signature chain)
307314
subprocess.run(
308315
['PACSign PR -t UPDATE -H openssl_manager -y -i solver.gbs -o solver_signed.gbs'],
309316
shell=True, cwd=build_path
310317
).check_returncode()
311318

312-
# 7. Create solver file by combining gbs file and solver config.
319+
# 8. Create solver file by combining gbs file and solver config.
313320
gbs_path = os.path.join(build_path, 'solver_signed.gbs')
314321
out_path = os.path.join(os.getcwd(), name)
315322
if not os.path.isfile(gbs_path):

generator/hram.py

Lines changed: 50 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
from myhdl import block, always_seq, Signal, instances, ConcatSignal, enum, ResetSignal, always_comb
1+
from myhdl import block, always_seq, Signal, instances, ConcatSignal, enum, always_comb
22

33
from framework.data_desc import get_input_desc, get_output_desc
44
from framework.packed_struct import BitVector
@@ -17,12 +17,7 @@ def hram_handler(config, cp2af, af2cp, csr: CsrSignals, data_out: AsyncFifoProdu
1717
assert data_out.clk == data_in.clk
1818
assert data_out.rst == data_in.rst
1919
clk = data_out.clk
20-
21-
reset = ResetSignal(True, True, False)
22-
23-
@always_comb
24-
def reset_driver():
25-
reset.next = data_out.rst or not csr.enb
20+
reset = data_out.rst
2621

2722
input_desc = get_input_desc(config.system_size)
2823
assert len(input_desc) <= len(CcipClData)
@@ -56,7 +51,7 @@ def output_finished_driver():
5651

5752
@always_seq(clk.posedge, reset=None)
5853
def mem_reads_request():
59-
if reset:
54+
if reset or not csr.enb:
6055
af2cp.c0.hdr.vc_sel.next = 0
6156
af2cp.c0.hdr.rsvd1.next = 0
6257
af2cp.c0.hdr.cl_len.next = 3 # 4 CL's
@@ -99,40 +94,52 @@ def mem_reads_request():
9994
input_data_size = len(input_desc)
10095
input_data_iter = Signal(num.UnsignedIntegerNumberType(32).create(0))
10196

102-
@always_seq(clk.posedge, reset=reset)
97+
@always_seq(clk.posedge, reset=None)
10398
def mem_reads_responses():
104-
if data_out.wr:
105-
if not data_out.full:
106-
nbr_inputs.next = nbr_inputs + 1
107-
if input_data_iter + input_data_size <= chunk_size:
108-
data_out.data.next = input_data_chunk[input_data_iter + input_data_size:input_data_iter]
109-
input_data_iter.next = input_data_iter + input_data_size
110-
else:
111-
data_out.wr.next = False
112-
input_data_iter.next = 0
113-
cl0_rcv.next = False
114-
cl1_rcv.next = False
115-
cl2_rcv.next = False
116-
cl3_rcv.next = False
117-
read_response_processing_ongoing.next = False
118-
elif cl_rcv_vec == 0b1111:
119-
data_out.wr.next = True
120-
data_out.data.next = input_data_chunk[input_data_iter + input_data_size:input_data_iter]
121-
input_data_iter.next = input_data_iter + input_data_size
122-
read_response_processing_ongoing.next = True
123-
elif cp2af.c0.rspValid == 1 and cp2af.c0.hdr.mdata == 0:
124-
if cp2af.c0.hdr.cl_num == 0:
125-
cl0_data.next = cp2af.c0.data
126-
cl0_rcv.next = True
127-
elif cp2af.c0.hdr.cl_num == 1:
128-
cl1_data.next = cp2af.c0.data
129-
cl1_rcv.next = True
130-
elif cp2af.c0.hdr.cl_num == 2:
131-
cl2_data.next = cp2af.c0.data
132-
cl2_rcv.next = True
133-
elif cp2af.c0.hdr.cl_num == 3:
134-
cl3_data.next = cp2af.c0.data
135-
cl3_rcv.next = True
99+
if reset or not csr.enb:
100+
nbr_inputs.next = 0
101+
input_data_iter.next = 0
102+
read_response_processing_ongoing.next = False
103+
104+
data_out.wr.next = False
105+
106+
cl0_rcv.next = False
107+
cl1_rcv.next = False
108+
cl2_rcv.next = False
109+
cl3_rcv.next = False
110+
else:
111+
if data_out.wr:
112+
if not data_out.full:
113+
nbr_inputs.next = nbr_inputs + 1
114+
if input_data_iter + input_data_size <= chunk_size:
115+
data_out.data.next = input_data_chunk[input_data_iter + input_data_size:input_data_iter]
116+
input_data_iter.next = input_data_iter + input_data_size
117+
else:
118+
data_out.wr.next = False
119+
input_data_iter.next = 0
120+
cl0_rcv.next = False
121+
cl1_rcv.next = False
122+
cl2_rcv.next = False
123+
cl3_rcv.next = False
124+
read_response_processing_ongoing.next = False
125+
elif cl_rcv_vec == 0b1111:
126+
data_out.wr.next = True
127+
data_out.data.next = input_data_chunk[input_data_iter + input_data_size:input_data_iter]
128+
input_data_iter.next = input_data_iter + input_data_size
129+
read_response_processing_ongoing.next = True
130+
elif cp2af.c0.rspValid == 1 and cp2af.c0.hdr.mdata == 0:
131+
if cp2af.c0.hdr.cl_num == 0:
132+
cl0_data.next = cp2af.c0.data
133+
cl0_rcv.next = True
134+
elif cp2af.c0.hdr.cl_num == 1:
135+
cl1_data.next = cp2af.c0.data
136+
cl1_rcv.next = True
137+
elif cp2af.c0.hdr.cl_num == 2:
138+
cl2_data.next = cp2af.c0.data
139+
cl2_rcv.next = True
140+
elif cp2af.c0.hdr.cl_num == 3:
141+
cl3_data.next = cp2af.c0.data
142+
cl3_rcv.next = True
136143

137144
# Incremental counter used for iterating trough host array
138145
output_addr_offset = Signal(num.UnsignedIntegerNumberType(32).create(0))
@@ -146,7 +153,7 @@ def mem_reads_responses():
146153

147154
@always_seq(clk.posedge, reset=None)
148155
def reset_padding():
149-
if reset:
156+
if reset or not csr.enb:
150157
output_data_chunk_padding.next = 0
151158
else:
152159
output_data_chunk = ConcatSignal(*reversed(output_data))
@@ -157,7 +164,7 @@ def reset_padding():
157164
# Host Memory Writes
158165
@always_seq(clk.posedge, reset=None)
159166
def mem_writes():
160-
if reset:
167+
if reset or not csr.enb:
161168
af2cp.c1.hdr.rsvd2.next = 0
162169
af2cp.c1.hdr.vc_sel.next = 0
163170
af2cp.c1.hdr.sop.next = 0
Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
1+
# Define the clock groups for the clock domain crossing
12
set_clock_groups -asynchronous -group [get_clocks "*\|outclk1"] -group [get_clocks "*\|clk1x"]
2-
set_net_delay -from [get_registers "*\|solver\|rk_interface_x\[*\]"] -to [get_registers "*\|solver\|af2cp_c2_data\[*\]"] -max -get_value_from_clock_period dst_clock_period -value_multiplier 0.8
3-
set_max_skew -from [get_keepers "*\|solver\|rk_interface_x\[*\]"] -to [get_keepers "*\|solver\|af2cp_c2_data\[*\]"] -get_skew_value_from_clock_period min_clock_period -skew_value_multiplier 0.8
4-
set_net_delay -from [get_registers "*\|solver\|rk_interface_y\[*\]\[*\]"] -to [get_registers "*\|solver\|af2cp_c2_data\[*\]"] -max -get_value_from_clock_period dst_clock_period -value_multiplier 0.8
5-
set_max_skew -from [get_keepers "*\|solver\|rk_interface_y\[*\]\[*\]"] -to [get_keepers "*\|solver\|af2cp_c2_data\[*\]"] -get_skew_value_from_clock_period min_clock_period -skew_value_multiplier 0.8
3+
4+
# Clock domain crossing producer side of all async fifos
5+
set_net_delay -from [get_registers "*\|solver\|async_fifo*_p_wr_addr_gray\[*\]"] -to [get_registers "*\|solver\|async_fifo*_ff_synchronizer*_out_val\[*\]"] -max -get_value_from_clock_period dst_clock_period -value_multiplier 0.8
6+
set_max_skew -from [get_keepers "*\|solver\|async_fifo*_p_wr_addr_gray\[*\]"] -to [get_keepers "*\|solver\|async_fifo*_ff_synchronizer*_out_val\[*\]"] -get_skew_value_from_clock_period min_clock_period -skew_value_multiplier 0.8
7+
8+
# Clock domain crossing consumer side of all async fifos
9+
set_net_delay -from [get_registers "*\|solver\|async_fifo*_c_rd_addr_gray\[*\]"] -to [get_registers "*\|solver\|async_fifo*_ff_synchronizer*_out_val\[*\]"] -max -get_value_from_clock_period dst_clock_period -value_multiplier 0.8
10+
set_max_skew -from [get_keepers "*\|solver\|async_fifo*_c_rd_addr_gray\[*\]"] -to [get_keepers "*\|solver\|async_fifo*_ff_synchronizer*_out_val\[*\]"] -get_skew_value_from_clock_period min_clock_period -skew_value_multiplier 0.8

generator/static/filelist.txt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,5 +9,4 @@ ip_cores/subfp_single.ip
99

1010
ccip_interface_reg.sv
1111
ccip_std_afu.sv
12-
../out/solver.v
13-
clock_crossing.sdc
12+
../out/solver.v

0 commit comments

Comments
 (0)