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)
- 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):
* auto-crc calculation in .bit file
* support lm32 or openrisc core, either via libfpga or iverilog backend
* ipv6 or vnc in hardware?
* iverilog fpga backend
* design fpga 'core' that uses high-speed icap/reconfig to process data
ChangeLog

View File

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

View File

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

View File

@ -8,6 +8,7 @@
#include "model.h"
#include "floorplan.h"
#include "control.h"
#include "parts.h"
/*
This C design corresponds to the following Verilog:
@ -33,7 +34,7 @@ int main(int argc, char** argv)
struct fpgadev_logic logic_cfg;
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);
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 "model.h"
#include "parts.h"
#define VERT_TILE_SPACING 45
#define HORIZ_TILE_SPACING 160
@ -46,7 +47,7 @@ int main(int argc, char** argv)
// on the output for now
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))
goto fail;

View File

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

View File

@ -8,6 +8,7 @@
#include "model.h"
#include "floorplan.h"
#include "control.h"
#include "parts.h"
/*
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;
int rc;
if ((rc = fpga_build_model(&model, XC6SLX9_ROWS, XC6SLX9_COLUMNS,
XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING))) FAIL(rc);
if ((rc = fpga_build_model(&model, XC6SLX9, XC6SLX9_ROWS,
XC6SLX9_COLUMNS, XC6SLX9_LEFT_WIRING, XC6SLX9_RIGHT_WIRING)))
FAIL(rc);
if ((rc = fpga_find_iob(&model, "P45", &iob_inA_y, &iob_inA_x,
&iob_inA_type_idx))) FAIL(rc);

View File

@ -26,6 +26,7 @@
#define FAIL(code) do { HERE(); rc = (code); goto fail; } while (0)
#define XOUT() do { HERE(); goto xout; } 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)

View File

@ -56,6 +56,7 @@ struct fpga_model
{
int rc; // if rc != 0, all function calls will immediately return
const struct xc_info *xci;
int cfg_rows;
char cfg_columns[512];
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_BOT_INNER_IO 0x1000
#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
// multiple checks are combined with OR logic
@ -775,7 +778,7 @@ struct fpga_tile
};
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);
// returns model->rc (model itself will be memset to 0)
int fpga_free_model(struct fpga_model* model);
@ -853,6 +856,8 @@ struct w_point // wire point
#define NO_INCREMENT 0
#define MAX_NET_POINTS 128
struct w_net
{
// 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
int last_inc;
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);
@ -878,11 +883,12 @@ int replicate_switches_and_names(struct fpga_model* model,
struct seed_data
{
int x_flags;
int flags;
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
@ -1016,6 +1022,10 @@ enum extra_wires {
LOGICIN_S36,
LOGICIN_S44,
LOGICIN_S62,
IOCE,
IOCLK,
PLLCE,
PLLCLK,
VCC_WIRE = 150,
GND_WIRE,
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;
// MCB
if ((rc = add_dev(model, XC6_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, LEFT_MCB_COL, 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
x = LEFT_IO_DEVS;

View File

@ -9,7 +9,7 @@
#include "model.h"
#include "parts.h"
#define NUM_PF_BUFS 16
#define NUM_PF_BUFS 32
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))
prefix = "CMT_PLL_";
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_";
else {
const int mui_pos[] = {41, 44, 48, 51, 54, 57, 60, 64};
for (i = 0; i < sizeof(mui_pos)/sizeof(*mui_pos); i++) {
if (y == mui_pos[i]) {
for (i = 0; i < model->xci->num_mui; i++) {
if (y == model->xci->mui_pos[i]+1) {
prefix = "MCB_MUI_";
break;
}
}
if (i >= sizeof(mui_pos)/sizeof(*mui_pos))
if (i >= model->xci->num_mui)
prefix = "MCB_INT_";
}
} else if (is_atx(X_INNER_RIGHT, model, x))
@ -524,18 +523,30 @@ fail:
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;
for (x = 0; x < model->x_width; x++) {
model->tmp_str[x] = 0;
for (i = 0; data[i].x_flags; i++) {
if (is_atx(data[i].x_flags, model, x))
for (i = 0; data[i].flags; i++) {
if (is_atx(data[i].flags, model, x))
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)
{
int i;

View File

@ -11,12 +11,14 @@
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)
{
int rc;
memset(model, 0, sizeof(*model));
model->xci = xc_info(idcode);
if (!model->xci) FAIL(EINVAL);
model->cfg_rows = fpga_rows;
strncpy(model->cfg_columns, columns, sizeof(model->cfg_columns)-1);
strncpy(model->cfg_left_wiring, left_wiring,

View File

@ -408,6 +408,7 @@ int init_tiles(struct fpga_model* model)
// +3
//
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;
} else { // unwired
if (k == model->cfg_rows-1 && !l) {
@ -507,9 +508,10 @@ int init_tiles(struct fpga_model* model)
//
// -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;
else {
} else {
if (k == model->cfg_rows-1 && l == 0)
model->tiles[(row_top_y+l)*tile_columns + tile_columns - 4].type = CORNER_TR_UPPER;
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)
{
static const struct xc_info xc6slx9_info = {
.idcode = XC6SLX9,
.num_rows = 4,
.left_wiring =
/* row 3 */ "UWUWUWUW" "WWWWUUUU" \
@ -361,7 +362,10 @@ const struct xc_info* xc_info(int idcode)
[220] = { XC_T2_IOB_UNBONDED, 97 },
[221] = { XC_T2_IOB_UNBONDED, 98 },
[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) {
case XC6SLX9: return &xc6slx9_info;
}

View File

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

View File

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