diff --git a/dataflow_neuro/coders.act b/dataflow_neuro/coders.act index 5d112a8..82c94b2 100644 --- a/dataflow_neuro/coders.act +++ b/dataflow_neuro/coders.act @@ -477,35 +477,35 @@ namespace tmpl { /** * Neuron handshaking. * Looks for a rising edge on the neuron req. - * Then performs a 2d handshake out out_y then out_x. + * Then performs a 2d handshake out outy then outx. */ export - defproc neuron_hs_2D(a1of1 in; a1of1 out_x; a1of1 out_y; power supply; bool reset_B) { + defproc neuron_hs_2D(a1of1 in; a1of1 outx; a1of1 outy; power supply; bool reset_B) { bool _reset_BX; BUF_X2 reset_buf(.a = reset_B, .y = _reset_BX, .vdd = supply.vdd, .vss = supply.vss); bool _en, _req; A_1C2N_RB_X1 A_ack(.c1 = _en, .n1 = _req, .n2 = in.r, .y = in.a, - .sr_B = _reset_BX, .sr_B = _reset_BX, .vss = supply.vss, .vdd = supply.vdd); + .pr_B = _reset_BX, .sr_B = _reset_BX, .vss = supply.vss, .vdd = supply.vdd); A_1C1P_X1 A_en(.p1 = _req, .c1 = in.a, .y = _en, .vss = supply.vss, .vdd = supply.vdd); bool _y_a_B, _x_a_B; - INV_X2 inv_x(.a = out_x.a, .y = _x_a_B, .vss = supply.vss, .vdd = supply.vdd); - INV_X2 inv_y(.a = out_y.a, .y = _y_a_B, .vss = supply.vss, .vdd = supply.vdd); + INV_X2 inv_x(.a = outx.a, .y = _x_a_B, .vss = supply.vss, .vdd = supply.vdd); + INV_X2 inv_y(.a = outy.a, .y = _y_a_B, .vss = supply.vss, .vdd = supply.vdd); - A_2C1P1N_RB_X1 A_req(.p1 = _x_a_B, .c1 = _en, .c2 = _y_a_B, .n1 = in.r, - .sr_B = _reset_BX, .sr_B = _reset_BX, .vdd = supply.vdd, .vss = supply.vss); + A_2C1P1N_RB_X1 A_req(.p1 = _x_a_B, .c1 = _en, .c2 = _y_a_B, .n1 = in.r, .y = _req, + .pr_B = _reset_BX, .sr_B = _reset_BX, .vdd = supply.vdd, .vss = supply.vss); // y_req pull up NAND2_X1 nand_y(.a = _y_a_B, .b = _req, .vdd = supply.vdd, .vss = supply.vss); - PULLUP_X4 pu_y(.a = nand_y.y, .y = out_y.r, .vdd = supply.vdd, .vss = supply.vss); + PULLUP_X4 pu_y(.a = nand_y.y, .y = outy.r, .vdd = supply.vdd, .vss = supply.vss); // x_req pull up - NAND3_X1 nand_x(.a = _x_a_B, .b = _req, .c = out_y.a, .vdd = supply.vdd, .vss = supply.vss); - PULLUP_X4 pu_x(.a = nand_x.y, .y = out_x.r, .vdd = supply.vdd, .vss = supply.vss); + NAND3_X1 nand_x(.a = _x_a_B, .b = _req, .c = outy.a, .vdd = supply.vdd, .vss = supply.vss); + PULLUP_X4 pu_x(.a = nand_x.y, .y = outx.r, .vdd = supply.vdd, .vss = supply.vss); } @@ -513,14 +513,14 @@ namespace tmpl { export defproc line_end_pull_down (bool? in; bool? reset_B; power supply; bool! out) { - bool _out, __out, nor_out; + bool _out, __out, nand_out; BUF_X1 buf1(.a=in, .y=_out, .vdd=supply.vdd,.vss=supply.vss); BUF_X1 buf2(.a=_out, .y=__out, .vdd=supply.vdd,.vss=supply.vss); INV_X1 inv(.a = __out, .vdd=supply.vdd,.vss =supply.vss); - NAND2_X1 aenor(.a=inv.y, .b=reset_B, .y = nor_out, .vdd=supply.vdd,.vss=supply.vss); + NAND2_X1 aenor(.a=inv.y, .b=reset_B, .y = nand_out, .vdd=supply.vdd,.vss=supply.vss); - PULLDOWN_X4 pull_down(.a=nor_out, .y=out); + PULLDOWN_X4 pull_down(.a=nand_out, .y=out); } @@ -529,9 +529,12 @@ namespace tmpl { * A 2d grid of neuron handshakers. * Should then slot into the encoder. * Each neuron has an a1of1 channel (in), which is tripped when a neuron spikes. + * N_dly is number of delay elements to add to line pull down, + * for the purpose of running ACT sims. + * It should probably be set to 0 though. */ - export template - defproc neuron_hs_2D_array(a1of1 in[Nx*Ny]; a1of1 out_x[Nx], out_y[Ny]; + export template + defproc nrn_hs_2D_array(a1of1 in[Nx*Ny]; a1of1 outx[Nx], outy[Ny]; power supply; bool reset_B) { // Make hella signal buffers @@ -542,6 +545,7 @@ namespace tmpl { rsb[j].supply = supply; ) + // Create handshake grid pint index; neuron_hs_2D neurons[Nx*Ny]; @@ -551,32 +555,63 @@ namespace tmpl { neurons[index].supply = supply; neurons[index].reset_B = rsb[j].out[i]; neurons[index].in = in[index]; - neurons[index].out_x = out_x[i]; - neurons[index].out_y = out_y[j]; + neurons[index].outx = outx[i]; + neurons[index].outy = outy[j]; ) ) - // Create line req pull downs + // Hacks to maybe construct some fifos, ignore. + [N_dly >= 1 -> + delay_fifo dly_x[Nx]; + delay_fifo dly_y[Ny]; + ] + + // Create x line req pull downs line_end_pull_down pd_x[Nx]; sigbuf rsb_pd_x(.in = reset_B, .supply = supply); (i:0..Nx-1: - pd_x[i].in = out_x[i].a; - pd_x[i].out = out_x[i].r; + [ N_dly = 0 -> + pd_x[i].in = outx[i].a; + [] N_dly >= 1 -> + dly_x[i].supply = supply; + dly_x[i].in = outx[i].a; + pd_x[i].in = dly_x[i].out; + ] + pd_x[i].out = outx[i].r; pd_x[i].reset_B = rsb_pd_x.out[i]; pd_x[i].supply = supply; ) - // Create line req pull downs + // Create y line req pull downs line_end_pull_down pd_y[Ny]; sigbuf rsb_pd_y(.in = reset_B, .supply = supply); (j:0..Ny-1: - pd_y[j].in = out_y[j].a; - pd_y[j].out = out_y[j].r; + [ N_dly = 0 -> + pd_y[j].in = outy[j].a; + [] N_dly >= 1 -> + dly_y[j].supply = supply; + dly_y[j].in = outy[j].a; + pd_y[j].in = dly_y[j].out; + ] + pd_y[j].out = outy[j].r; pd_y[j].reset_B = rsb_pd_y.out[j]; pd_y[j].supply = supply; ) + // Add keeps + KEEP_X1 keep_x[Nx]; + (i:Nx: + keep_x[i].vdd = supply.vdd; + keep_x[i].vss = supply.vss; + keep_x[i].y = outx[i].r; + ) + KEEP_X1 keep_y[Ny]; + (j:Ny: + keep_y[j].vdd = supply.vdd; + keep_y[j].vss = supply.vss; + keep_y[j].y = outy[j].r; + ) }