more switches

This commit is contained in:
Wolfgang Spraul 2012-09-13 09:08:47 +02:00
parent 279cd02600
commit d54a0ff81d
5 changed files with 307 additions and 40 deletions

View File

@ -321,11 +321,12 @@ fail:
return rc; return rc;
} }
static int mip_is_set(struct extract_state* es, int y, int x, static int bitpos_is_set(struct extract_state* es, int y, int x,
struct sw_bitpos* swpos, int* is_set) struct sw_bitpos* swpos, int* is_set)
{ {
int row_num, row_pos, start_in_frame, two_bits_val, rc; int row_num, row_pos, start_in_frame, two_bits_val, rc;
// TODO: does not support minor20 correctly
*is_set = 0; *is_set = 0;
is_in_row(es->model, y, &row_num, &row_pos); is_in_row(es->model, y, &row_num, &row_pos);
if (row_num == -1 || row_pos == -1 if (row_num == -1 || row_pos == -1
@ -353,11 +354,12 @@ fail:
return rc; return rc;
} }
static int mip_clear_bits(struct extract_state* es, int y, int x, static int bitpos_clear_bits(struct extract_state* es, int y, int x,
struct sw_bitpos* swpos) struct sw_bitpos* swpos)
{ {
int row_num, row_pos, start_in_frame, rc; int row_num, row_pos, start_in_frame, rc;
// TODO: does not support minor20 correctly
is_in_row(es->model, y, &row_num, &row_pos); is_in_row(es->model, y, &row_num, &row_pos);
if (row_num == -1 || row_pos == -1 if (row_num == -1 || row_pos == -1
|| row_pos == HCLK_POS) FAIL(EINVAL); || row_pos == HCLK_POS) FAIL(EINVAL);
@ -387,7 +389,7 @@ static int extract_routing_switches(struct extract_state* es, int y, int x)
if (y != 68 || x != 12) return 0; if (y != 68 || x != 12) return 0;
for (i = 0; i < es->num_bit_pos; i++) { for (i = 0; i < es->num_bit_pos; i++) {
rc = mip_is_set(es, y, x, &es->bit_pos[i], &is_set); rc = bitpos_is_set(es, y, x, &es->bit_pos[i], &is_set);
if (rc) FAIL(rc); if (rc) FAIL(rc);
if (!is_set) continue; if (!is_set) continue;
@ -401,7 +403,7 @@ if (y != 68 || x != 12) return 0;
es->yx_pos[es->num_yx_pos].x = x; es->yx_pos[es->num_yx_pos].x = x;
es->yx_pos[es->num_yx_pos].idx = es->bit_pos[i].uni_dir; es->yx_pos[es->num_yx_pos].idx = es->bit_pos[i].uni_dir;
es->num_yx_pos++; es->num_yx_pos++;
rc = mip_clear_bits(es, y, x, &es->bit_pos[i]); rc = bitpos_clear_bits(es, y, x, &es->bit_pos[i]);
if (rc) FAIL(rc); if (rc) FAIL(rc);
} }
return 0; return 0;
@ -483,6 +485,31 @@ static int mod4_calc(int a, int b)
return (unsigned int) (a+b)%4; return (unsigned int) (a+b)%4;
} }
struct sw_mip_src
{
int m0_sw_to;
int m0_two_bits_o;
int m0_two_bits_val;
int m0_one_bit_start;
int m1_sw_to;
int m1_two_bits_o;
int m1_two_bits_val;
int m1_one_bit_start;
int src_wire[6];
};
struct sw_mi20_src
{
int sw_to;
int two_bits_o;
int two_bits_val;
int one_bit_start;
int src_wire[6];
};
static int construct_extract_state(struct extract_state* es, struct fpga_model* model) static int construct_extract_state(struct extract_state* es, struct fpga_model* model)
{ {
char from_str[MAX_WIRENAME_LEN], to_str[MAX_WIRENAME_LEN]; char from_str[MAX_WIRENAME_LEN], to_str[MAX_WIRENAME_LEN];
@ -494,6 +521,35 @@ static int construct_extract_state(struct extract_state* es, struct fpga_model*
if (model->first_routing_y == -1) if (model->first_routing_y == -1)
FAIL(EINVAL); FAIL(EINVAL);
// mip 10
{ const struct sw_mip_src src[] = {
{DW + ((W_EL1*4+2) | DIR_BEG), 0, 2, 3, DW + ((W_NR1*4+3) | DIR_BEG), 14, 1, 2,
{LW + (LO_BMUX|LD1), LW + (LO_DQ|LD1), LW + (LO_D|LD1),
LW + LO_BMUX, LW + LO_DQ, LW + LO_D}}};
for (i = 0; i < sizeof(src)/sizeof(*src); i++) {
for (j = 0; j < sizeof(src[0].src_wire)/sizeof(src[0].src_wire[0]); j++) {
if (src[i].src_wire[j] == UNDEF) continue;
es->bit_pos[es->num_bit_pos].minor = 20;
es->bit_pos[es->num_bit_pos].two_bits_o = src[i].m0_two_bits_o;
es->bit_pos[es->num_bit_pos].two_bits_val = src[i].m0_two_bits_val;
es->bit_pos[es->num_bit_pos].one_bit_o = src[i].m0_one_bit_start + j*2;
es->bit_pos[es->num_bit_pos].uni_dir = fpga_switch_lookup(es->model,
es->model->first_routing_y, es->model->first_routing_x,
fpga_wirestr_i(es->model, src[i].src_wire[j]),
fpga_wirestr_i(es->model, src[i].m0_sw_to));
if (es->bit_pos[es->num_bit_pos].uni_dir == NO_SWITCH) {
fprintf(stderr, "#E routing switch %s -> %s not in model\n",
fpga_wirestr(es->model, src[i].src_wire[j]),
fpga_wirestr(es->model, src[i].m0_sw_to));
FAIL(EINVAL);
}
es->bit_pos[es->num_bit_pos].rev_dir = NO_SWITCH;
es->num_bit_pos++;
}
}}
#if 0
// switches from logicout to dirwires (6*2*2*4*6=576 switches) // switches from logicout to dirwires (6*2*2*4*6=576 switches)
for (i = 0; i < DIRBEG_ROW; i++) { for (i = 0; i < DIRBEG_ROW; i++) {
cur_pair_start = (i/2)*2; cur_pair_start = (i/2)*2;
@ -530,7 +586,8 @@ static int construct_extract_state(struct extract_state* es, struct fpga_model*
} }
} }
} }
#endif
#if 0
// VCC (32 switches) and GFAN (32 switches +4 bidir) // VCC (32 switches) and GFAN (32 switches +4 bidir)
for (i = 12; i <= 18; i+=2) { // mip12/14/16/18 for (i = 12; i <= 18; i+=2) { // mip12/14/16/18
for (j = 0; j <= 3; j++) { // 4 rows for (j = 0; j <= 3; j++) { // 4 rows
@ -610,6 +667,64 @@ static int construct_extract_state(struct extract_state* es, struct fpga_model*
} }
} }
} }
// minor 20 switches (SR, CLK, GFAN = 113 switches (4 bidir added on other side))
{ const struct sw_mi20_src src[] = {
{SR1, 6, 3, 0, {GCLK11, GCLK10, GCLK13, GCLK12, GCLK9, GCLK8}},
{SR1, 6, 2, 0, {DW+W_WR1*4+2, DW+W_NR1*4+2,
VCC_WIRE, GND_WIRE, DW+W_ER1*4+2, DW+W_SR1*4+2}},
{SR1, 6, 1, 0, {FAN_B, LW+(LI_DI|LD1), LW+(LI_BX|LD1),
LW+LI_BX, GCLK15, GCLK14}},
{SR0, 8, 3, 10, {GCLK8, GCLK9, GCLK10, GCLK13, GCLK12, GCLK11}},
{SR0, 8, 2, 10, {GCLK14, GCLK15, LW+(LI_DI|LD1), LW+(LI_BX|LD1),
LW+LI_BX, FAN_B}},
{SR0, 8, 1, 10, {DW+W_SR1*4+2, DW+W_ER1*4+2, DW+W_NR1*4+2,
VCC_WIRE, UNDEF, DW+W_WR1*4+2}},
{CLK0, 16, 3, 18, {GCLK0, GCLK1, GCLK2, GCLK5, GCLK4, GCLK3}},
{CLK0, 16, 2, 18, {GCLK6, GCLK7, GCLK8, GCLK11, GCLK10, GCLK9}},
{CLK0, 16, 1, 18, {GCLK12, GCLK13, GCLK14, LW+(LI_BX|LD1), LW+(LI_CI|LD1), GCLK15}},
{CLK0, 16, 0, 18, {DW+W_NR1*4+2, DW+W_WR1*4+2,
DW+W_SR1*4+1, VCC_WIRE, UNDEF, DW+W_ER1*4+1}},
{CLK1, 46, 3, 40, {GCLK3, GCLK2, GCLK5, GCLK4, GCLK1, GCLK0}},
{CLK1, 46, 2, 40, {GCLK15, GCLK14, LW+(LI_BX|LD1), LW+(LI_CI|LD1), GCLK13, GCLK12}},
{CLK1, 46, 1, 40, {GCLK9, GCLK8, GCLK11, GCLK10, GCLK7, GCLK6}},
{CLK1, 46, 0, 40, {DW+W_ER1*4+1, DW+W_SR1*4+1, VCC_WIRE,
UNDEF, DW+W_WR1*4+2, DW+W_NR1*4+2}},
{GFAN0, 54, 3, 48, {GCLK3, GCLK4, GCLK5, GCLK2, GCLK1, GCLK0}},
{GFAN0, 54, 2, 48, {DW+W_WR1*4+1, GND_WIRE, VCC_WIRE, DW+W_NR1*4+1, DW+W_ER1*4+1, DW+W_SR1*4+1}},
{GFAN0, 54, 1, 48, {LW+(LI_CE|LD1), UNDEF, UNDEF, LW+(LI_CI|LD1), GCLK7, GCLK6}},
{GFAN1, 56, 3, 58, {GCLK0, GCLK1, GCLK4, GCLK5, GCLK2, GCLK3}},
{GFAN1, 56, 2, 58, {GCLK6, GCLK7, LW+(LI_AX|LD1), LW+LI_AX, UNDEF, UNDEF}},
{GFAN1, 56, 1, 58, {DW+W_SR1*4+1, DW+W_ER1*4+1, GND_WIRE, VCC_WIRE, DW+W_NR1*4+1, DW+W_WR1*4+1}}};
for (i = 0; i < sizeof(src)/sizeof(*src); i++) {
for (j = 0; j < sizeof(src[0].src_wire)/sizeof(src[0].src_wire[0]); j++) {
if (src[i].src_wire[j] == UNDEF) continue;
es->bit_pos[es->num_bit_pos].minor = 20;
es->bit_pos[es->num_bit_pos].two_bits_o = src[i].two_bits_o;
es->bit_pos[es->num_bit_pos].two_bits_val = src[i].two_bits_val;
es->bit_pos[es->num_bit_pos].one_bit_o = src[i].one_bit_start + j;
es->bit_pos[es->num_bit_pos].uni_dir = fpga_switch_lookup(es->model,
es->model->first_routing_y, es->model->first_routing_x,
fpga_wirestr_i(es->model, src[i].src_wire[j]),
fpga_wirestr_i(es->model, src[i].sw_to));
if (es->bit_pos[es->num_bit_pos].uni_dir == NO_SWITCH) {
fprintf(stderr, "#E routing switch %s -> %s not in model\n",
fpga_wirestr(es->model, src[i].src_wire[j]),
fpga_wirestr(es->model, src[i].sw_to));
FAIL(EINVAL);
}
es->bit_pos[es->num_bit_pos].rev_dir = NO_SWITCH;
es->num_bit_pos++;
}
}}
#endif
return 0; return 0;
fail: fail:
return rc; return rc;
@ -656,14 +771,17 @@ int printf_swbits(struct fpga_model* model)
{ {
struct extract_state es; struct extract_state es;
char bit_str[129]; char bit_str[129];
int i, j, rc; int i, j, width, rc;
rc = construct_extract_state(&es, model); rc = construct_extract_state(&es, model);
if (rc) FAIL(rc); if (rc) FAIL(rc);
bit_str[128] = 0;
for (i = 0; i < es.num_bit_pos; i++) { for (i = 0; i < es.num_bit_pos; i++) {
for (j = 0; j < 128; j++)
width = (es.bit_pos[i].minor == 20) ? 64 : 128;
for (j = 0; j < width; j++)
bit_str[j] = '0'; bit_str[j] = '0';
bit_str[j] = 0;
if (es.bit_pos[i].two_bits_val & 2) if (es.bit_pos[i].two_bits_val & 2)
bit_str[es.bit_pos[i].two_bits_o] = '1'; bit_str[es.bit_pos[i].two_bits_o] = '1';
if (es.bit_pos[i].two_bits_val & 1) if (es.bit_pos[i].two_bits_val & 1)

112
control.c
View File

@ -344,7 +344,7 @@ str16_t fdev_logic_pinstr_i(struct fpga_model* model, pinw_idx_t idx, int ld1_ty
return str_i; return str_i;
} }
int fdev_logic_inbit(pinw_idx_t idx, int ld1_type) int fdev_logic_inbit(pinw_idx_t idx)
{ {
if (idx & LD1) { if (idx & LD1) {
idx &= ~LD1; idx &= ~LD1;
@ -382,6 +382,45 @@ int fdev_logic_inbit(pinw_idx_t idx, int ld1_type)
return -1; return -1;
} }
int fdev_logic_outbit(pinw_idx_t idx)
{
if (idx & LD1) {
idx &= ~LD1;
switch (idx) {
case LO_A: return M_A;
case LO_AMUX: return M_AMUX;
case LO_AQ: return M_AQ;
case LO_B: return M_B;
case LO_BMUX: return M_BMUX;
case LO_BQ: return M_BQ;
case LO_C: return M_C;
case LO_CMUX: return M_CMUX;
case LO_CQ: return M_CQ;
case LO_D: return M_D;
case LO_DMUX: return M_DMUX;
case LO_DQ: return M_DQ;
}
HERE();
return -1;
}
switch (idx) {
case LO_A: return X_A;
case LO_AMUX: return X_AMUX;
case LO_AQ: return X_AQ;
case LO_B: return X_B;
case LO_BMUX: return X_BMUX;
case LO_BQ: return X_BQ;
case LO_C: return X_C;
case LO_CMUX: return X_CMUX;
case LO_CQ: return X_CQ;
case LO_D: return X_D;
case LO_DMUX: return X_DMUX;
case LO_DQ: return X_DQ;
}
HERE();
return -1;
}
static int reset_required_pins(struct fpga_device* dev) static int reset_required_pins(struct fpga_device* dev)
{ {
int rc; int rc;
@ -1788,3 +1827,74 @@ void fprintf_net(FILE* f, struct fpga_model* model, net_idx_t net_i)
net->el[i].x, net->el[i].idx)); net->el[i].x, net->el[i].idx));
} }
} }
const char* fpga_wirestr(struct fpga_model* model, enum extra_wires wire)
{
enum { NUM_BUFS = 8, BUF_SIZE = 64 };
static char buf[NUM_BUFS][BUF_SIZE];
static int last_buf = 0;
switch (wire) {
case GFAN0: return "GFAN0";
case GFAN1: return "GFAN1";
case CLK0: return "CLK0";
case CLK1: return "CLK1";
case SR0: return "SR0";
case SR1: return "SR1";
case GND_WIRE: return "GND_WIRE";
case VCC_WIRE: return "VCC_WIRE";
case FAN_B: return "FAN_B";
case LOGICIN20: return "LOGICIN20";
case LOGICIN21: return "LOGICIN21";
case LOGICIN44: return "LOGICIN44";
case LOGICIN52: return "LOGICIN52";
case LOGICIN_N21: return "LOGICIN_N21";
case LOGICIN_N28: return "LOGICIN_N28";
case LOGICIN_N52: return "LOGICIN_N52";
case LOGICIN_N60: return "LOGICIN_N60";
case LOGICIN_S20: return "LOGICIN_S20";
case LOGICIN_S36: return "LOGICIN_S36";
case LOGICIN_S44: return "LOGICIN_S44";
case LOGICIN_S62: return "LOGICIN_S62";
default: ;
}
last_buf = (last_buf+1)%NUM_BUFS;
buf[last_buf][0] = 0;
if (wire >= GCLK0 && wire <= GCLK15)
snprintf(buf[last_buf], sizeof(buf[0]), "GCLK%i", wire-GCLK0);
else if (wire >= DW && wire <= DW_LAST) {
char beg_end;
int s0n3_flag;
wire -= DW;
beg_end = (wire & DIR_BEG) ? 'B' : 'E';
s0n3_flag = wire & DIR_S0N3;
wire &= ~(DIR_BEG|DIR_S0N3);
if (s0n3_flag) {
if (wire%4 == 0) {
snprintf(buf[last_buf], sizeof(buf[0]),
"%s%c_S0", wire_base(wire/4), beg_end);
} else if (wire%4 == 3) {
snprintf(buf[last_buf], sizeof(buf[0]),
"%s%c_N3", wire_base(wire/4), beg_end);
} else HERE();
} else
snprintf(buf[last_buf], sizeof(buf[0]),
"%s%c%i", wire_base(wire/4), beg_end, wire%4);
} else if (wire >= LW && wire <= LW_LAST) {
wire -= LW;
if ((wire&(~LD1)) >= LI_FIRST && (wire&(~LD1)) <= LI_LAST)
snprintf(buf[last_buf], sizeof(buf[0]), "LOGICIN_B%i", fdev_logic_inbit(wire));
else if ((wire&(~LD1)) >= LO_FIRST && (wire&(~LD1)) <= LO_LAST)
snprintf(buf[last_buf], sizeof(buf[0]), "LOGICOUT%i", fdev_logic_outbit(wire));
else HERE();
} else HERE();
return buf[last_buf];
}
str16_t fpga_wirestr_i(struct fpga_model* model, enum extra_wires wire)
{
return strarray_find(&model->str, fpga_wirestr(model, wire));
}

View File

@ -44,7 +44,8 @@ const char* fdev_pinw_idx2str(int devtype, pinw_idx_t idx);
// the second logic device (L or M). // the second logic device (L or M).
const char* fdev_logic_pinstr(pinw_idx_t idx, int ld1_type); const char* fdev_logic_pinstr(pinw_idx_t idx, int ld1_type);
str16_t fdev_logic_pinstr_i(struct fpga_model* model, pinw_idx_t idx, int ld1_type); str16_t fdev_logic_pinstr_i(struct fpga_model* model, pinw_idx_t idx, int ld1_type);
int fdev_logic_inbit(pinw_idx_t idx, int ld1_type); int fdev_logic_inbit(pinw_idx_t idx);
int fdev_logic_outbit(pinw_idx_t idx);
// lut_a2d is LUT_A to LUT_D value, lut_5or6 is int 5 or int 6. // lut_a2d is LUT_A to LUT_D value, lut_5or6 is int 5 or int 6.
int fdev_logic_set_lut(struct fpga_model* model, int y, int x, int type_idx, int fdev_logic_set_lut(struct fpga_model* model, int y, int x, int type_idx,
@ -324,3 +325,6 @@ int fpga_net_remove_sw(struct fpga_model* model, net_idx_t net_i,
void fpga_net_free_all(struct fpga_model* model); void fpga_net_free_all(struct fpga_model* model);
void fprintf_net(FILE* f, struct fpga_model* model, net_idx_t net_i); void fprintf_net(FILE* f, struct fpga_model* model, net_idx_t net_i);
const char* fpga_wirestr(struct fpga_model* model, enum extra_wires wire);
str16_t fpga_wirestr_i(struct fpga_model* model, enum extra_wires wire);

89
model.h
View File

@ -362,8 +362,11 @@ enum { LOGIC_M = 1, LOGIC_L, LOGIC_X };
// All LOGICIN_IN A..D sequences must be exactly sequential as // All LOGICIN_IN A..D sequences must be exactly sequential as
// here to match initialization in model_devices.c:init_logic() // here to match initialization in model_devices.c:init_logic()
// and control.c:fdev_set_required_pins(). // and control.c:fdev_set_required_pins().
enum { // input: enum {
LI_A1 = 0, // input:
LI_FIRST = 0,
LI_A1 = LI_FIRST,
LI_A2, LI_A3, LI_A4, LI_A5, LI_A6, LI_A2, LI_A3, LI_A4, LI_A5, LI_A6,
LI_B1, LI_B2, LI_B3, LI_B4, LI_B5, LI_B1, LI_B2, LI_B3, LI_B4, LI_B5,
LI_B6, LI_B6,
@ -377,13 +380,18 @@ enum { // input:
LI_CIN, // only some L and M devs have this LI_CIN, // only some L and M devs have this
// only for M: // only for M:
LI_WE, LI_AI, LI_BI, LI_CI, LI_DI, LI_WE, LI_AI, LI_BI, LI_CI, LI_DI,
LI_LAST = LI_DI,
// output: // output:
LO_A, LO_B, LO_C, LO_D, LO_FIRST,
LO_A = LO_FIRST, LO_B, LO_C, LO_D,
LO_AMUX, LO_BMUX, LO_CMUX, LO_DMUX, LO_AMUX, LO_BMUX, LO_CMUX, LO_DMUX,
LO_AQ, LO_BQ, LO_CQ, LO_DQ, LO_AQ, LO_BQ, LO_CQ, LO_DQ,
LO_COUT }; // only some L and M devs have this LO_COUT, // only some L and M devs have this
#define LOGIC_LAST_INPUT_PINW LI_DI
#define LOGIC_LAST_OUTPUT_PINW LO_COUT LO_LAST = LO_COUT };
#define LOGIC_PINW_STR \ #define LOGIC_PINW_STR \
{ "A1", "A2", "A3", "A4", "A5", "A6", \ { "A1", "A2", "A3", "A4", "A5", "A6", \
"B1", "B2", "B3", "B4", "B5", "B6", \ "B1", "B2", "B3", "B4", "B5", "B6", \
@ -703,27 +711,6 @@ enum logicout_wire {
const char* logicin_str(enum logicin_wire w); const char* logicin_str(enum logicin_wire w);
const char* logicout_str(enum logicout_wire w); const char* logicout_str(enum logicout_wire w);
// The extra wires must not overlap with logicin_wire or logicout_wire
// namespaces so that they can be combined with either of them.
enum extra_wires {
UNDEF = 100,
FAN_B,
GFAN0,
GFAN1,
LOGICIN20,
LOGICIN21,
LOGICIN44,
LOGICIN52,
LOGICIN_N21,
LOGICIN_N28,
LOGICIN_N52,
LOGICIN_N60,
LOGICIN_S20,
LOGICIN_S36,
LOGICIN_S44,
LOGICIN_S62
};
// The wires are ordered clockwise. Order is important for // The wires are ordered clockwise. Order is important for
// wire_to_NESW4(). // wire_to_NESW4().
enum wire_type enum wire_type
@ -778,3 +765,51 @@ enum wire_type
const char* wire_base(enum wire_type w); const char* wire_base(enum wire_type w);
enum wire_type rotate_wire(enum wire_type cur, int off); enum wire_type rotate_wire(enum wire_type cur, int off);
enum wire_type wire_to_len(enum wire_type w, int first_len); enum wire_type wire_to_len(enum wire_type w, int first_len);
// Those two flags can be OR'ed into the DW..DW_LAST range.
// DIR_BEG signals a 'B' line - the default is 'E' endpoint.
// DIR_S0N3 turns 0 into _S0 and 3 into _N3.
#define DIR_BEG 0x100
#define DIR_S0N3 0x200
// The extra wires must not overlap with logicin_wire or logicout_wire
// namespaces so that they can be combined with either of them.
enum extra_wires {
UNDEF = 100,
FAN_B,
GFAN0,
GFAN1,
CLK0,
CLK1,
SR0,
SR1,
LOGICIN20,
LOGICIN21,
LOGICIN44,
LOGICIN52,
LOGICIN_N21,
LOGICIN_N28,
LOGICIN_N52,
LOGICIN_N60,
LOGICIN_S20,
LOGICIN_S36,
LOGICIN_S44,
LOGICIN_S62,
VCC_WIRE = 150,
GND_WIRE,
GCLK0 = 200, GCLK1, GCLK2, GCLK3, GCLK4, GCLK5, GCLK6, GCLK7,
GCLK8, GCLK9, GCLK10, GCLK11, GCLK12, GCLK13, GCLK14, GCLK15,
// direction wires
DW = 500,
// dirwires can be encoded times-4, for example
// NL1E2 = DW + W_NL1*4 + 2
// DIR_BEG and DIR_S0N3 can be OR'ed into this range.
DW_LAST = 1499,
// logic wires
LW,
// logic wires are encoded here as LOGIC_BEG+LI_A1. LD1 (0x100)
// can be OR'ed to the LI or LO value.
LW_LAST = 1999
};

View File

@ -453,11 +453,11 @@ static int init_logic(struct fpga_model* model, int y, int x, int idx)
? "XX_" : "X_"; ? "XX_" : "X_";
} else FAIL(EINVAL); } else FAIL(EINVAL);
tile->devs[idx].pinw = calloc((LOGIC_LAST_OUTPUT_PINW+1) tile->devs[idx].pinw = calloc((LO_LAST+1)
*sizeof(tile->devs[idx].pinw[0]), /*elsize*/ 1); *sizeof(tile->devs[idx].pinw[0]), /*elsize*/ 1);
if (!tile->devs[idx].pinw) FAIL(ENOMEM); if (!tile->devs[idx].pinw) FAIL(ENOMEM);
tile->devs[idx].num_pinw_total = LOGIC_LAST_OUTPUT_PINW+1; tile->devs[idx].num_pinw_total = LO_LAST+1;
tile->devs[idx].num_pinw_in = LOGIC_LAST_INPUT_PINW+1; tile->devs[idx].num_pinw_in = LI_LAST+1;
for (i = 0; i < 4; i++) { // 'A' to 'D' for (i = 0; i < 4; i++) { // 'A' to 'D'
for (j = 0; j < 6; j++) { for (j = 0; j < 6; j++) {