wire work

This commit is contained in:
Wolfgang Spraul 2012-11-08 13:14:45 +01:00
parent c9c55822be
commit 865dbfbb73
17 changed files with 1222 additions and 819 deletions

7
README
View File

@ -74,11 +74,18 @@ mid-term (6 months):
- inter-tile wire connections (model_conns.c) - inter-tile wire connections (model_conns.c)
- configure devices and route wires - configure devices and route wires
cleanup (whenever convenient):
* use tile flags instead of tile names
* model connections and switches together rather than separately
* describe more wire names/meanings with integers instead of strings
* move all part-specific static data into xc_info()
long-term (>6 months): long-term (>6 months):
* auto-crc calculation in .bit file * auto-crc calculation in .bit file
* support lm32 or openrisc core, either via libfpga or iverilog backend * support lm32 or openrisc core, either via libfpga or iverilog backend
* ipv6 or vnc in hardware? * ipv6 or vnc in hardware?
* iverilog fpga backend * iverilog fpga backend
* design fpga 'core' that uses high-speed icap/reconfig to process data
ChangeLog ChangeLog

View File

@ -10,6 +10,7 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "control.h" #include "control.h"
#include "parts.h"
time_t g_start_time; time_t g_start_time;
#define TIME() (time(0)-g_start_time) #define TIME() (time(0)-g_start_time)
@ -1861,8 +1862,8 @@ int main(int argc, char** argv)
MEMUSAGE(); MEMUSAGE();
printf("O Building memory model...\n"); printf("O Building memory model...\n");
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
goto fail; goto fail;
printf("O Done\n"); printf("O Done\n");
TIME_AND_MEM(); TIME_AND_MEM();

View File

@ -8,6 +8,7 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "bit.h" #include "bit.h"
#include "parts.h"
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
@ -52,8 +53,9 @@ int main(int argc, char** argv)
} }
// build model // build model
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) FAIL(rc); XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
FAIL(rc);
if (print_swbits) { if (print_swbits) {
rc = printf_swbits(&model); rc = printf_swbits(&model);

View File

@ -8,6 +8,7 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "control.h" #include "control.h"
#include "parts.h"
/* /*
This C design corresponds to the following Verilog: This C design corresponds to the following Verilog:
@ -33,7 +34,7 @@ int main(int argc, char** argv)
struct fpgadev_logic logic_cfg; struct fpgadev_logic logic_cfg;
net_idx_t inA_net, inB_net, out_net; net_idx_t inA_net, inB_net, out_net;
fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS, XC6SLX9_COLUMNS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING); XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING);
fpga_find_iob(&model, "P55", &iob_clk_y, &iob_clk_x, &iob_clk_type_idx); fpga_find_iob(&model, "P55", &iob_clk_y, &iob_clk_x, &iob_clk_type_idx);

View File

@ -18,6 +18,7 @@
#include <libxml/xpathInternals.h> #include <libxml/xpathInternals.h>
#include "model.h" #include "model.h"
#include "parts.h"
#define VERT_TILE_SPACING 45 #define VERT_TILE_SPACING 45
#define HORIZ_TILE_SPACING 160 #define HORIZ_TILE_SPACING 160
@ -46,7 +47,7 @@ int main(int argc, char** argv)
// on the output for now // on the output for now
xmlInitParser(); xmlInitParser();
if (fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if (fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS, XC6SLX9_COLUMNS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)) XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))
goto fail; goto fail;

View File

@ -8,6 +8,7 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "bit.h" #include "bit.h"
#include "parts.h"
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
@ -40,8 +41,8 @@ int main(int argc, char** argv)
goto fail; goto fail;
} }
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
goto fail; goto fail;
if ((rc = read_floorplan(&model, fp))) goto fail; if ((rc = read_floorplan(&model, fp))) goto fail;

View File

@ -8,6 +8,7 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "control.h" #include "control.h"
#include "parts.h"
/* /*
This C design corresponds to the following Verilog: This C design corresponds to the following Verilog:
@ -33,8 +34,9 @@ int main(int argc, char** argv)
net_idx_t inA_net, inB_net, out_net; net_idx_t inA_net, inB_net, out_net;
int rc; int rc;
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) FAIL(rc); XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
FAIL(rc);
if ((rc = fpga_find_iob(&model, "P45", &iob_inA_y, &iob_inA_x, if ((rc = fpga_find_iob(&model, "P45", &iob_inA_y, &iob_inA_x,
&iob_inA_type_idx))) FAIL(rc); &iob_inA_type_idx))) FAIL(rc);

View File

@ -26,6 +26,7 @@
#define FAIL(code) do { HERE(); rc = (code); goto fail; } while (0) #define FAIL(code) do { HERE(); rc = (code); goto fail; } while (0)
#define XOUT() do { HERE(); goto xout; } while (0) #define XOUT() do { HERE(); goto xout; } while (0)
#define CHECK_RC(m) do { if ((m)->rc) return (m)->rc; } while (0) #define CHECK_RC(m) do { if ((m)->rc) return (m)->rc; } while (0)
#define ASSERT(what) do { if (!(what)) FAIL(EINVAL); } while (0)
#define OUT_OF_U16(val) ((val) < 0 || (val) > 0xFFFF) #define OUT_OF_U16(val) ((val) < 0 || (val) > 0xFFFF)

View File

@ -56,6 +56,7 @@ struct fpga_model
{ {
int rc; // if rc != 0, all function calls will immediately return int rc; // if rc != 0, all function calls will immediately return
const struct xc_info *xci;
int cfg_rows; int cfg_rows;
char cfg_columns[512]; char cfg_columns[512];
char cfg_left_wiring[1024], cfg_right_wiring[1024]; char cfg_left_wiring[1024], cfg_right_wiring[1024];
@ -236,6 +237,8 @@ enum fpga_tile_type
#define Y_TOP_INNER_IO 0x0800 #define Y_TOP_INNER_IO 0x0800
#define Y_BOT_INNER_IO 0x1000 #define Y_BOT_INNER_IO 0x1000
#define Y_BOT_OUTER_IO 0x2000 #define Y_BOT_OUTER_IO 0x2000
#define Y_TOP_FIRST_REGULAR Y_TOP_OUTER_IO
#define Y_BOT_LAST_REGULAR Y_BOT_OUTER_IO
#define Y_REGULAR_ROW 0x4000 #define Y_REGULAR_ROW 0x4000
// multiple checks are combined with OR logic // multiple checks are combined with OR logic
@ -775,7 +778,7 @@ struct fpga_tile
}; };
int fpga_build_model(struct fpga_model* model, int fpga_build_model(struct fpga_model* model,
int fpga_rows, const char* columns, int idcode, int fpga_rows, const char* columns,
const char* left_wiring, const char* right_wiring); const char* left_wiring, const char* right_wiring);
// returns model->rc (model itself will be memset to 0) // returns model->rc (model itself will be memset to 0)
int fpga_free_model(struct fpga_model* model); int fpga_free_model(struct fpga_model* model);
@ -853,6 +856,8 @@ struct w_point // wire point
#define NO_INCREMENT 0 #define NO_INCREMENT 0
#define MAX_NET_POINTS 128
struct w_net struct w_net
{ {
// if !last_inc, no incrementing will happen (NO_INCREMENT) // if !last_inc, no incrementing will happen (NO_INCREMENT)
@ -860,7 +865,7 @@ struct w_net
// the %i in the name from pt.start_count:last_inc // the %i in the name from pt.start_count:last_inc
int last_inc; int last_inc;
int num_pts; int num_pts;
struct w_point pt[40]; struct w_point pt[MAX_NET_POINTS];
}; };
int add_conn_net(struct fpga_model* model, add_conn_f add_conn_func, const struct w_net *net); int add_conn_net(struct fpga_model* model, add_conn_f add_conn_func, const struct w_net *net);
@ -878,11 +883,12 @@ int replicate_switches_and_names(struct fpga_model* model,
struct seed_data struct seed_data
{ {
int x_flags; int flags;
const char* str; const char* str;
}; };
void seed_strx(struct fpga_model* model, struct seed_data* data); void seed_strx(struct fpga_model *model, struct seed_data *data);
void seed_stry(struct fpga_model *model, struct seed_data *data);
#define MAX_WIRENAME_LEN 64 #define MAX_WIRENAME_LEN 64
@ -1016,6 +1022,10 @@ enum extra_wires {
LOGICIN_S36, LOGICIN_S36,
LOGICIN_S44, LOGICIN_S44,
LOGICIN_S62, LOGICIN_S62,
IOCE,
IOCLK,
PLLCE,
PLLCLK,
VCC_WIRE = 150, VCC_WIRE = 150,
GND_WIRE, GND_WIRE,
GCLK0 = 200, GCLK1, GCLK2, GCLK3, GCLK4, GCLK5, GCLK6, GCLK7, GCLK0 = 200, GCLK1, GCLK2, GCLK3, GCLK4, GCLK5, GCLK6, GCLK7,

File diff suppressed because it is too large Load Diff

View File

@ -60,8 +60,8 @@ int init_devices(struct fpga_model* model)
if ((rc = add_dev(model, y, x, DEV_SUSPEND_SYNC, 0))) goto fail; if ((rc = add_dev(model, y, x, DEV_SUSPEND_SYNC, 0))) goto fail;
// MCB // MCB
if ((rc = add_dev(model, XC6_MCB_YPOS, LEFT_MCB_COL, DEV_MCB, 0))) goto fail; if ((rc = add_dev(model, model->xci->mcb_ypos, LEFT_MCB_COL, DEV_MCB, 0))) goto fail;
if ((rc = add_dev(model, XC6_MCB_YPOS, model->x_width-RIGHT_MCB_O, DEV_MCB, 0))) goto fail; if ((rc = add_dev(model, model->xci->mcb_ypos, model->x_width-RIGHT_MCB_O, DEV_MCB, 0))) goto fail;
// OCT_CALIBRATE // OCT_CALIBRATE
x = LEFT_IO_DEVS; x = LEFT_IO_DEVS;

View File

@ -9,7 +9,7 @@
#include "model.h" #include "model.h"
#include "parts.h" #include "parts.h"
#define NUM_PF_BUFS 16 #define NUM_PF_BUFS 32
const char* pf(const char* fmt, ...) const char* pf(const char* fmt, ...)
{ {
@ -64,17 +64,16 @@ const char* wpref(struct fpga_model* model, int y, int x, const char* wire_name)
else if (is_atx(X_CENTER_CMTPLL_COL, model, x)) else if (is_atx(X_CENTER_CMTPLL_COL, model, x))
prefix = "CMT_PLL_"; prefix = "CMT_PLL_";
else if (is_atx(X_RIGHT_MCB|X_LEFT_MCB, model, x)) { else if (is_atx(X_RIGHT_MCB|X_LEFT_MCB, model, x)) {
if (y == XC6_MCB_YPOS) if (y == model->xci->mcb_ypos)
prefix = "MCB_"; prefix = "MCB_";
else { else {
const int mui_pos[] = {41, 44, 48, 51, 54, 57, 60, 64}; for (i = 0; i < model->xci->num_mui; i++) {
for (i = 0; i < sizeof(mui_pos)/sizeof(*mui_pos); i++) { if (y == model->xci->mui_pos[i]+1) {
if (y == mui_pos[i]) {
prefix = "MCB_MUI_"; prefix = "MCB_MUI_";
break; break;
} }
} }
if (i >= sizeof(mui_pos)/sizeof(*mui_pos)) if (i >= model->xci->num_mui)
prefix = "MCB_INT_"; prefix = "MCB_INT_";
} }
} else if (is_atx(X_INNER_RIGHT, model, x)) } else if (is_atx(X_INNER_RIGHT, model, x))
@ -524,18 +523,30 @@ fail:
return rc; return rc;
} }
void seed_strx(struct fpga_model* model, struct seed_data* data) void seed_strx(struct fpga_model *model, struct seed_data *data)
{ {
int x, i; int x, i;
for (x = 0; x < model->x_width; x++) { for (x = 0; x < model->x_width; x++) {
model->tmp_str[x] = 0; model->tmp_str[x] = 0;
for (i = 0; data[i].x_flags; i++) { for (i = 0; data[i].flags; i++) {
if (is_atx(data[i].x_flags, model, x)) if (is_atx(data[i].flags, model, x))
model->tmp_str[x] = data[i].str; model->tmp_str[x] = data[i].str;
} }
} }
} }
void seed_stry(struct fpga_model *model, struct seed_data *data)
{
int y, i;
for (y = 0; y < model->y_height; y++) {
model->tmp_str[y] = 0;
for (i = 0; data[i].flags; i++) {
if (is_aty(data[i].flags, model, y))
model->tmp_str[y] = data[i].str;
}
}
}
char next_non_whitespace(const char* s) char next_non_whitespace(const char* s)
{ {
int i; int i;

View File

@ -11,12 +11,14 @@
static int s_high_speed_replicate = 1; static int s_high_speed_replicate = 1;
int fpga_build_model(struct fpga_model* model, int fpga_rows, int fpga_build_model(struct fpga_model* model, int idcode, int fpga_rows,
const char* columns, const char* left_wiring, const char* right_wiring) const char* columns, const char* left_wiring, const char* right_wiring)
{ {
int rc; int rc;
memset(model, 0, sizeof(*model)); memset(model, 0, sizeof(*model));
model->xci = xc_info(idcode);
if (!model->xci) FAIL(EINVAL);
model->cfg_rows = fpga_rows; model->cfg_rows = fpga_rows;
strncpy(model->cfg_columns, columns, sizeof(model->cfg_columns)-1); strncpy(model->cfg_columns, columns, sizeof(model->cfg_columns)-1);
strncpy(model->cfg_left_wiring, left_wiring, strncpy(model->cfg_left_wiring, left_wiring,

View File

@ -408,6 +408,7 @@ int init_tiles(struct fpga_model* model)
// +3 // +3
// //
if (model->cfg_left_wiring[(model->cfg_rows-1-k)*16+l] == 'W') { if (model->cfg_left_wiring[(model->cfg_rows-1-k)*16+l] == 'W') {
model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + 3].flags |= TF_IOLOGIC_DELAY_DEV;
model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + 3].type = ROUTING_IO_VIA_L; model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + 3].type = ROUTING_IO_VIA_L;
} else { // unwired } else { // unwired
if (k == model->cfg_rows-1 && !l) { if (k == model->cfg_rows-1 && !l) {
@ -507,9 +508,10 @@ int init_tiles(struct fpga_model* model)
// //
// -4 // -4
// //
if (model->cfg_right_wiring[(model->cfg_rows-1-k)*16+l] == 'W') if (model->cfg_right_wiring[(model->cfg_rows-1-k)*16+l] == 'W') {
model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + tile_columns - 4].flags |= TF_IOLOGIC_DELAY_DEV;
model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + tile_columns - 4].type = ROUTING_IO_VIA_R; model->tiles[(row_top_y+(l<8?l:l+1))*tile_columns + tile_columns - 4].type = ROUTING_IO_VIA_R;
else { } else {
if (k == model->cfg_rows-1 && l == 0) if (k == model->cfg_rows-1 && l == 0)
model->tiles[(row_top_y+l)*tile_columns + tile_columns - 4].type = CORNER_TR_UPPER; model->tiles[(row_top_y+l)*tile_columns + tile_columns - 4].type = CORNER_TR_UPPER;
else if (k == model->cfg_rows-1 && l == 1) else if (k == model->cfg_rows-1 && l == 1)

View File

@ -103,6 +103,7 @@ int xc_num_rows(int idcode)
const struct xc_info* xc_info(int idcode) const struct xc_info* xc_info(int idcode)
{ {
static const struct xc_info xc6slx9_info = { static const struct xc_info xc6slx9_info = {
.idcode = XC6SLX9,
.num_rows = 4, .num_rows = 4,
.left_wiring = .left_wiring =
/* row 3 */ "UWUWUWUW" "WWWWUUUU" \ /* row 3 */ "UWUWUWUW" "WWWWUUUU" \
@ -361,7 +362,10 @@ const struct xc_info* xc_info(int idcode)
[220] = { XC_T2_IOB_UNBONDED, 97 }, [220] = { XC_T2_IOB_UNBONDED, 97 },
[221] = { XC_T2_IOB_UNBONDED, 98 }, [221] = { XC_T2_IOB_UNBONDED, 98 },
[222] = { XC_T2_IOB_PAD, 75 }, [222] = { XC_T2_IOB_PAD, 75 },
[223] = { XC_T2_IOB_PAD, 74 }}}; [223] = { XC_T2_IOB_PAD, 74 }},
.mcb_ypos = 20,
.num_mui = 8,
.mui_pos = { 40, 43, 47, 50, 53, 56, 59, 63 }};
switch (idcode & IDCODE_MASK) { switch (idcode & IDCODE_MASK) {
case XC6SLX9: return &xc6slx9_info; case XC6SLX9: return &xc6slx9_info;
} }

View File

@ -25,6 +25,7 @@
#define XC_MAX_MAJORS 400 #define XC_MAX_MAJORS 400
#define XC_MAX_TYPE2_ENTRIES 2000 #define XC_MAX_TYPE2_ENTRIES 2000
#define XC_MAX_MUI_POS 32
#define XC_MAJ_ZERO 0x00000001 #define XC_MAJ_ZERO 0x00000001
#define XC_MAJ_LEFT 0x00000002 #define XC_MAJ_LEFT 0x00000002
@ -55,6 +56,7 @@ struct xc_type2_info
struct xc_info struct xc_info
{ {
int idcode;
int num_rows; int num_rows;
const char* left_wiring; const char* left_wiring;
const char* right_wiring; const char* right_wiring;
@ -63,6 +65,9 @@ struct xc_info
struct xc_major_info majors[XC_MAX_MAJORS]; struct xc_major_info majors[XC_MAX_MAJORS];
int num_type2; int num_type2;
struct xc_type2_info type2[XC_MAX_TYPE2_ENTRIES]; struct xc_type2_info type2[XC_MAX_TYPE2_ENTRIES];
int mcb_ypos;
int num_mui;
int mui_pos[XC_MAX_MUI_POS];
}; };
const struct xc_info* xc_info(int idcode); const struct xc_info* xc_info(int idcode);
@ -85,8 +90,6 @@ const struct xc_info* xc_info(int idcode);
#define XC6_HCLK_BYTES 2 #define XC6_HCLK_BYTES 2
#define XC6_HCLK_BITS (XC6_HCLK_BYTES*8) #define XC6_HCLK_BITS (XC6_HCLK_BYTES*8)
#define XC6_MCB_YPOS 20
#define XC6_IOB_MASK_IO 0x00FF00FFFF000000 #define XC6_IOB_MASK_IO 0x00FF00FFFF000000
#define XC6_IOB_MASK_IN_TYPE 0x000000000000F000 #define XC6_IOB_MASK_IN_TYPE 0x000000000000F000
#define XC6_IOB_MASK_SLEW 0x0000000000FF0000 #define XC6_IOB_MASK_SLEW 0x0000000000FF0000

View File

@ -7,14 +7,15 @@
#include "model.h" #include "model.h"
#include "floorplan.h" #include "floorplan.h"
#include "parts.h"
int main(int argc, char** argv) int main(int argc, char** argv)
{ {
struct fpga_model model; struct fpga_model model;
int no_conns, rc; int no_conns, rc;
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS, if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
goto fail; goto fail;
no_conns = 0; no_conns = 0;