bug fixing

This commit is contained in:
Wolfgang Spraul 2013-01-21 08:51:38 -05:00
parent e8433414f0
commit 90f5cfe84f
8 changed files with 135 additions and 155 deletions

View File

@ -21,6 +21,7 @@
/*
This C design corresponds to the following Verilog:
TODO
*/
int main(int argc, char** argv)

View File

@ -12,106 +12,7 @@
/*
This C design corresponds to the following Verilog:
// There are 5 registers
// 0x0 R Firmware version
// 0x1 RW Counter enable/disable, enable: 1, disable: 0
// 0x2 RW Counter write enable, enable: 1, disable: 0
// 0x3 RW Counter write Value
// 0x4 R Counter current value
// LED1, on: stop counting, off: counting
// LED2, on: counter > 0, off: counter == 0
module counter(clk, led1, led2);
input clk;
output led1;
output led2;
// synthesis attribute LOC clk "T8 | IOSTANDARD = LVCMOS33"
// synthesis attribute LOC led "R5 | SLEW = QUIETIO | DRIVE = 8"
reg counter_start = 1'b0;
reg counter_we = 1'b0;
reg [31:0] counter = 32'd0;
reg [31:0] counter_set = 32'd0;
always @(posedge clk)
begin
if (counter_start == 1'b1)
counter <= counter + 1;
if (counter_we == 1'b1)
counter <= counter_set;
end
assign led1 = ~counter_start;
assign led2 = counter;
wire jt_capture, jt_drck, jt_reset, jt_sel;
wire jt_shift, jt_tck, jt_tdi, jt_update, jt_tdo;
BSCAN_SPARTAN6 # (.JTAG_CHAIN(1)) jtag_blk (
.CAPTURE(jt_capture),
.DRCK(jt_drck),
.RESET(jt_reset),
.RUNTEST(),
.SEL(jt_sel),
.SHIFT(jt_shift),
.TCK(jt_tck),
.TDI(jt_tdi),
.TDO(jt_tdo),
.TMS(),
.UPDATE(jt_update)
);
reg [37:0] dr;
reg [3:0] addr = 4'hF;
reg checksum;
wire checksum_valid = ~checksum;
wire jtag_we = dr[36];
wire [3:0] jtag_addr = dr[35:32];
assign jt_tdo = dr[0];
always @ (posedge jt_tck)
begin
if (jt_reset == 1'b1)
begin
dr <= 38'd0;
end
else if (jt_capture == 1'b1)
begin
checksum <= 1'b1;
dr[37:32] <= 6'd0;
addr <= 4'hF;
case (addr)
4'h0: dr[31:0] <= 32'h20120911;
4'h1: dr[0] <= counter_start;
4'h2: dr[0] <= counter_we;
4'h3: dr[31:0] <= counter_set;
4'h4: dr[31:0] <= counter;
default: dr[31:0] <= 32'habcdef01;
endcase
end
else if (jt_shift == 1'b1)
begin
dr <= {jt_tdi, dr[37:1]};
checksum <= checksum ^ jt_tdi;
end
else if (jt_update & checksum_valid)
begin
addr <= jtag_addr;
if (jtag_we)
begin
case (jtag_addr)
4'h1: counter_start <= dr[0];
4'h2: counter_we <= dr[0];
4'h3: counter_set <= dr[31:0];
endcase
end
end
end
endmodule
TODO
*/
int main(int argc, char** argv)

View File

@ -10,6 +10,8 @@
#include "control.h"
#undef DBG_EXTRACT_T2
#undef DBG_EXTRACT_LOGIC_SW
#undef DBG_EXTRACT_ROUTING_SW
static uint8_t* get_first_minor(struct fpga_bits* bits, int row, int major)
{
@ -80,7 +82,9 @@ struct sw_yxpos
swidx_t idx;
};
#define MAX_YX_SWITCHES 1024
// random value of about 10kk switches for now, meaning
// about 100MB memory usage
#define MAX_YX_SWITCHES 10*1024*1024
struct extract_state
{
@ -89,7 +93,7 @@ struct extract_state
// yx switches are fully extracted ones pointing into the
// model, stored here for later processing into nets.
int num_yx_pos;
struct sw_yxpos yx_pos[MAX_YX_SWITCHES]; // needs to be dynamically alloced...
struct sw_yxpos *yx_pos;
};
static int find_es_switch(struct extract_state* es, int y, int x, swidx_t sw)
@ -675,6 +679,26 @@ fail:
return rc;
}
static int back_to_cout(struct fpga_model *model, int cin_y, int cin_x,
str16_t cin_str, int *cout_y, int *cout_x, str16_t *cout_str)
{
int connpt_dests_o, num_dests, i;
RC_CHECK(model);
if (fpga_connpt_find(model, cin_y, cin_x, cin_str,
&connpt_dests_o, &num_dests) == NO_CONN)
RC_FAIL(model, EINVAL);
RC_ASSERT(model, num_dests == 1 || num_dests == 2);
for (i = 0; i < num_dests; i++) {
fpga_conn_dest(model, cin_y, cin_x, connpt_dests_o+i, cout_y, cout_x, cout_str);
if (has_device(model, *cout_y, *cout_x, DEV_LOGIC))
break;
}
if (i >= num_dests)
RC_FAIL(model, EINVAL);
RC_RETURN(model);
}
static int extract_logic(struct extract_state* es)
{
int row, row_pos, x, y, i, byte_off, last_minor, lut5_used, rc;
@ -1389,21 +1413,16 @@ static int extract_logic(struct extract_state* es)
&& (cfg_ml.a2d[LUT_A].out_mux == MUX_XOR
|| cfg_ml.a2d[LUT_A].ff_mux == MUX_XOR
|| cfg_ml.a2d[LUT_A].cy0)) {
int connpt_dests_o, num_dests, cout_y, cout_x;
int cout_y, cout_x;
str16_t cout_str;
if ((fpga_connpt_find(es->model, y, x,
dev_ml->pinw[LI_CIN], &connpt_dests_o,
&num_dests) == NO_CONN)
|| num_dests != 1) {
HERE();
} else {
fpga_conn_dest(es->model, y, x, connpt_dests_o,
&cout_y, &cout_x, &cout_str);
if (find_es_switch(es, cout_y, cout_x,fpga_switch_first(
es->model, cout_y, cout_x, cout_str, SW_TO)))
cfg_ml.precyinit = PRECYINIT_0;
}
rc = back_to_cout(es->model, y, x, dev_ml->pinw[LI_CIN],
&cout_y, &cout_x, &cout_str);
if (rc) FAIL(rc);
if (find_es_switch(es, cout_y, cout_x,fpga_switch_first(
es->model, cout_y, cout_x, cout_str, SW_TO)))
cfg_ml.precyinit = PRECYINIT_0;
}
//
@ -1561,6 +1580,7 @@ static int extract_routing_switches(struct extract_state* es, int y, int x)
{
struct fpga_tile* tile;
swidx_t sw_idx;
str16_t from_str, to_str;
int i, is_set, rc;
RC_CHECK(es->model);
@ -1571,16 +1591,26 @@ static int extract_routing_switches(struct extract_state* es, int y, int x)
if (rc) RC_FAIL(es->model, rc);
if (!is_set) continue;
sw_idx = fpga_switch_lookup(es->model, y, x,
fpga_wire2str_i(es->model, es->model->sw_bitpos[i].from),
fpga_wire2str_i(es->model, es->model->sw_bitpos[i].to));
from_str = fpga_wire2str_yx(es->model, es->model->sw_bitpos[i].from, y, x);
to_str = fpga_wire2str_yx(es->model, es->model->sw_bitpos[i].to, y, x);
#ifdef DBG_EXTRACT_ROUTING_SW
fprintf(stderr, "#D %s:%i y%i x%i from %i (%s) to %i (%s)\n",
__FILE__, __LINE__, y, x,
es->model->sw_bitpos[i].from,
strarray_lookup(&es->model->str, from_str),
es->model->sw_bitpos[i].to,
strarray_lookup(&es->model->str, to_str));
#endif
sw_idx = fpga_switch_lookup(es->model, y, x, from_str, to_str);
if (sw_idx == NO_SWITCH) RC_FAIL(es->model, EINVAL);
// todo: es->model->sw_bitpos[i].bidir handling
if (tile->switches[sw_idx] & SWITCH_BIDIRECTIONAL)
HERE();
fprintf(stderr, "#E %s:%i BIDIR not supported yet\n",
__FILE__, __LINE__);
if (tile->switches[sw_idx] & SWITCH_USED)
HERE();
fprintf(stderr, "#E %s:%i switch already in use\n",
__FILE__, __LINE__);
if (es->num_yx_pos >= MAX_YX_SWITCHES)
{ RC_FAIL(es->model, ENOTSUP); }
es->yx_pos[es->num_yx_pos].y = y;
@ -1616,36 +1646,37 @@ static int extract_logic_switches(struct extract_state* es, int y, int x)
if (frame_get_bit(u8_p + minor*FRAME_SIZE, byte_off*8 + XC6_ML_CIN_USED)) {
struct fpga_device* dev;
int connpt_dests_o, num_dests, cout_y, cout_x;
int cout_y, cout_x;
str16_t cout_str;
swidx_t cout_sw;
dev = fdev_p(es->model, y, x, DEV_LOGIC, DEV_LOG_M_OR_L);
if (!dev) FAIL(EINVAL);
if ((fpga_connpt_find(es->model, y, x,
dev->pinw[LI_CIN], &connpt_dests_o,
&num_dests) == NO_CONN)
|| num_dests != 1) {
HERE();
} else {
fpga_conn_dest(es->model, y, x, connpt_dests_o,
&cout_y, &cout_x, &cout_str);
cout_sw = fpga_switch_first(es->model, cout_y,
cout_x, cout_str, SW_TO);
if (cout_sw == NO_SWITCH) HERE();
else {
if (es->num_yx_pos >= MAX_YX_SWITCHES)
{ FAIL(ENOTSUP); }
es->yx_pos[es->num_yx_pos].y = cout_y;
es->yx_pos[es->num_yx_pos].x = cout_x;
es->yx_pos[es->num_yx_pos].idx = cout_sw;
es->num_yx_pos++;
rc = back_to_cout(es->model, y, x, dev->pinw[LI_CIN],
&cout_y, &cout_x, &cout_str);
if (rc) FAIL(rc);
#ifdef DBG_EXTRACT_LOGIC_SW
fprintf(stderr, "#D %s:%i cin y%i x%i %s cout y%i x%i %s\n",
__FILE__, __LINE__,
y, x, strarray_lookup(&es->model->str, dev->pinw[LI_CIN]),
cout_y, cout_x, strarray_lookup(&es->model->str, cout_str));
#endif
frame_clear_bit(u8_p + minor*FRAME_SIZE,
byte_off*8 + XC6_ML_CIN_USED);
}
}
cout_sw = fpga_switch_first(es->model, cout_y,
cout_x, cout_str, SW_TO);
if (cout_sw == NO_SWITCH)
FAIL(EINVAL);
if (es->num_yx_pos >= MAX_YX_SWITCHES)
{ FAIL(ENOTSUP); }
es->yx_pos[es->num_yx_pos].y = cout_y;
es->yx_pos[es->num_yx_pos].x = cout_x;
es->yx_pos[es->num_yx_pos].idx = cout_sw;
es->num_yx_pos++;
frame_clear_bit(u8_p + minor*FRAME_SIZE,
byte_off*8 + XC6_ML_CIN_USED);
}
return 0;
fail:
@ -2205,9 +2236,17 @@ static int construct_extract_state(struct extract_state* es,
RC_CHECK(model);
memset(es, 0, sizeof(*es));
es->model = model;
es->yx_pos = malloc(MAX_YX_SWITCHES * sizeof(*es->yx_pos));
if (!es->yx_pos) { HERE(); return ENOMEM; }
return 0;
}
static void destruct_extract_state(struct extract_state *es)
{
free(es->yx_pos);
es->yx_pos = 0;
}
int extract_model(struct fpga_model* model, struct fpga_bits* bits)
{
struct extract_state es;
@ -2219,28 +2258,32 @@ int extract_model(struct fpga_model* model, struct fpga_bits* bits)
if (rc) RC_FAIL(model, rc);
es.bits = bits;
for (i = 0; i < sizeof(s_default_bits)/sizeof(s_default_bits[0]); i++) {
if (!get_bitp(bits, &s_default_bits[i]))
RC_FAIL(model, EINVAL);
if (!get_bitp(bits, &s_default_bits[i])) {
RC_SET(model, EINVAL);
goto out;
}
clear_bitp(bits, &s_default_bits[i]);
}
rc = extract_switches(&es);
if (rc) RC_FAIL(model, rc);
if (rc) { RC_SET(model, rc); goto out; }
rc = extract_type2(&es);
if (rc) RC_FAIL(model, rc);
if (rc) { RC_SET(model, rc); goto out; }
rc = extract_logic(&es);
if (rc) RC_FAIL(model, rc);
if (rc) { RC_SET(model, rc); goto out; }
// turn switches into nets
if (model->nets)
HERE(); // should be empty here
for (i = 0; i < es.num_yx_pos; i++) {
rc = fnet_new(model, &net_idx);
if (rc) RC_FAIL(model, rc);
if (rc) { RC_SET(model, rc); goto out; }
rc = fnet_add_sw(model, net_idx, es.yx_pos[i].y,
es.yx_pos[i].x, &es.yx_pos[i].idx, 1);
if (rc) RC_FAIL(model, rc);
if (rc) { RC_SET(model, rc); goto out; }
}
out:
destruct_extract_state(&es);
RC_RETURN(model);
}

View File

@ -1010,7 +1010,7 @@ static int dump_maj_macc(const uint8_t* bits, int row, int major)
static int dump_bits(struct fpga_config* cfg)
{
int idcode, num_rows, row, major, off, rc;
struct xc_die* die_info;
const struct xc_die* die_info;
if (cfg->idcode_reg == -1) FAIL(EINVAL);
idcode = cfg->reg[cfg->idcode_reg].int_v;

View File

@ -1000,8 +1000,12 @@ int fpga_connpt_find(struct fpga_model* model, int y, int x,
if (tile->conn_point_names[i*2+1] == name_i)
break;
}
if (i >= tile->num_conn_point_names)
{ HERE(); goto fail; }
if (i >= tile->num_conn_point_names) {
fprintf(stderr, "#E %s:%i cannot find y%i x%i connpt %s\n",
__FILE__, __LINE__, y, x,
strarray_lookup(&model->str, name_i));
goto fail;
}
if (num_dests) {
*num_dests = (i < tile->num_conn_point_names-1)
? tile->conn_point_names[(i+1)*2]

View File

@ -30,6 +30,7 @@
#define RC_CHECK(model) do { if ((model)->rc) RC_RETURN(model); } while (0)
#define RC_ASSERT(model, what) do { RC_CHECK(model); if (!(what)) RC_FAIL(model, EINVAL); } while (0)
#define RC_SET(model, code) do { HERE(); if (!(model)->rc) (model)->rc = (code); } while (0)
#define RC_FAIL(model, code) do { HERE(); if (!(model)->rc) (model)->rc = (code); RC_RETURN(model); } while (0)
#define RC_RETURN(model) return (model)->rc

View File

@ -133,6 +133,7 @@ enum fpga_tile_type
#define HALF_ROW 8
#define HCLK_POS 8 // hclk pos in row
#define LAST_POS_IN_ROW 16 // including hclk at 8
#define LAST_REGULAR_ROW_POS 15 // without hclk
#define ROW_SIZE (HALF_ROW+1+HALF_ROW)
#define CENTER_X_PLUS_1 1 // routing col adjacent to center
@ -1056,6 +1057,8 @@ enum extra_wires {
const char *fpga_connpt_str(struct fpga_model *model, enum extra_wires wire,
int y, int x, int dest_y, int dest_x);
str16_t fpga_wire2str_yx(struct fpga_model *model, enum extra_wires wire,
int y, int x);
const char* fpga_wire2str(enum extra_wires wire);
str16_t fpga_wire2str_i(struct fpga_model* model, enum extra_wires wire);
enum extra_wires fpga_str2wire(const char* str);

View File

@ -1580,11 +1580,38 @@ const char *fpga_connpt_str(struct fpga_model *model, enum extra_wires wire,
"REGR_%s", fpga_wire2str(wire));
else HERE();
} else HERE();
} else HERE();
} else {
fprintf(stderr, "#E %s:%i fpga_connpt_str() wire %i unsupported\n", __FILE__, __LINE__, wire);
sprintf(buf[last_buf], "UNSUP_%i", wire);
}
return buf[last_buf];
}
const char* fpga_wire2str(enum extra_wires wire)
str16_t fpga_wire2str_yx(struct fpga_model *model, enum extra_wires wire,
int y, int x)
{
char buf[MAX_WIRENAME_LEN];
int str_i, row_num, row_pos;
if (wire >= GCLK0 && wire <= GCLK15) {
is_in_row(model, y, &row_num, &row_pos);
if (row_pos != LAST_POS_IN_ROW
|| (!row_num && !is_atx(X_FABRIC_BRAM_ROUTING_COL|X_FABRIC_MACC_ROUTING_COL, model, x))
|| (row_num == model->die->num_rows/2 && is_atx(X_LEFT_IO_ROUTING_COL|X_RIGHT_IO_ROUTING_COL, model, x)))
return fpga_wire2str_i(model, wire);
snprintf(buf, sizeof(buf), "%s_BRK", fpga_wire2str(wire));
} else
return fpga_wire2str_i(model, wire);
str_i = strarray_find(&model->str, buf);
if (OUT_OF_U16(str_i)) {
HERE();
str_i = STRIDX_NO_ENTRY;
}
return str_i;
}
const char *fpga_wire2str(enum extra_wires wire)
{
enum { NUM_BUFS = 8, BUF_SIZE = MAX_WIRENAME_LEN };
static char buf[NUM_BUFS][BUF_SIZE];