uboot/drivers/fpga/virtex2.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0+
   2/*
   3 * (C) Copyright 2002
   4 * Rich Ireland, Enterasys Networks, rireland@enterasys.com.
   5 * Keith Outwater, keith_outwater@mvis.com
   6 */
   7
   8/*
   9 * Configuration support for Xilinx Virtex2 devices.  Based
  10 * on spartan2.c (Rich Ireland, rireland@enterasys.com).
  11 */
  12
  13#include <common.h>
  14#include <console.h>
  15#include <virtex2.h>
  16
  17#if 0
  18#define FPGA_DEBUG
  19#endif
  20
  21#ifdef  FPGA_DEBUG
  22#define PRINTF(fmt,args...)     printf (fmt ,##args)
  23#else
  24#define PRINTF(fmt,args...)
  25#endif
  26
  27/*
  28 * If the SelectMap interface can be overrun by the processor, define
  29 * CONFIG_SYS_FPGA_CHECK_BUSY and/or CONFIG_FPGA_DELAY in the board configuration
  30 * file and add board-specific support for checking BUSY status. By default,
  31 * assume that the SelectMap interface cannot be overrun.
  32 */
  33#ifndef CONFIG_SYS_FPGA_CHECK_BUSY
  34#undef CONFIG_SYS_FPGA_CHECK_BUSY
  35#endif
  36
  37#ifndef CONFIG_FPGA_DELAY
  38#define CONFIG_FPGA_DELAY()
  39#endif
  40
  41#ifndef CONFIG_SYS_FPGA_PROG_FEEDBACK
  42#define CONFIG_SYS_FPGA_PROG_FEEDBACK
  43#endif
  44
  45/*
  46 * Don't allow config cycle to be interrupted
  47 */
  48#ifndef CONFIG_SYS_FPGA_CHECK_CTRLC
  49#undef CONFIG_SYS_FPGA_CHECK_CTRLC
  50#endif
  51
  52/*
  53 * Check for errors during configuration by default
  54 */
  55#ifndef CONFIG_SYS_FPGA_CHECK_ERROR
  56#define CONFIG_SYS_FPGA_CHECK_ERROR
  57#endif
  58
  59/*
  60 * The default timeout in mS for INIT_B to deassert after PROG_B has
  61 * been deasserted. Per the latest Virtex II Handbook (page 347), the
  62 * max time from PORG_B deassertion to INIT_B deassertion is 4uS per
  63 * data frame for the XC2V8000.  The XC2V8000 has 2860 data frames
  64 * which yields 11.44 mS.  So let's make it bigger in order to handle
  65 * an XC2V1000, if anyone can ever get ahold of one.
  66 */
  67#ifndef CONFIG_SYS_FPGA_WAIT_INIT
  68#define CONFIG_SYS_FPGA_WAIT_INIT       CONFIG_SYS_HZ/2 /* 500 ms */
  69#endif
  70
  71/*
  72 * The default timeout for waiting for BUSY to deassert during configuration.
  73 * This is normally not necessary since for most reasonable configuration
  74 * clock frequencies (i.e. 66 MHz or less), BUSY monitoring is unnecessary.
  75 */
  76#ifndef CONFIG_SYS_FPGA_WAIT_BUSY
  77#define CONFIG_SYS_FPGA_WAIT_BUSY       CONFIG_SYS_HZ/200       /* 5 ms*/
  78#endif
  79
  80/* Default timeout for waiting for FPGA to enter operational mode after
  81 * configuration data has been written.
  82 */
  83#ifndef CONFIG_SYS_FPGA_WAIT_CONFIG
  84#define CONFIG_SYS_FPGA_WAIT_CONFIG     CONFIG_SYS_HZ/5 /* 200 ms */
  85#endif
  86
  87static int virtex2_ssm_load(xilinx_desc *desc, const void *buf, size_t bsize);
  88static int virtex2_ssm_dump(xilinx_desc *desc, const void *buf, size_t bsize);
  89
  90static int virtex2_ss_load(xilinx_desc *desc, const void *buf, size_t bsize);
  91static int virtex2_ss_dump(xilinx_desc *desc, const void *buf, size_t bsize);
  92
  93static int virtex2_load(xilinx_desc *desc, const void *buf, size_t bsize,
  94                        bitstream_type bstype)
  95{
  96        int ret_val = FPGA_FAIL;
  97
  98        switch (desc->iface) {
  99        case slave_serial:
 100                PRINTF ("%s: Launching Slave Serial Load\n", __FUNCTION__);
 101                ret_val = virtex2_ss_load(desc, buf, bsize);
 102                break;
 103
 104        case slave_selectmap:
 105                PRINTF ("%s: Launching Slave Parallel Load\n", __FUNCTION__);
 106                ret_val = virtex2_ssm_load(desc, buf, bsize);
 107                break;
 108
 109        default:
 110                printf ("%s: Unsupported interface type, %d\n",
 111                                __FUNCTION__, desc->iface);
 112        }
 113        return ret_val;
 114}
 115
 116static int virtex2_dump(xilinx_desc *desc, const void *buf, size_t bsize)
 117{
 118        int ret_val = FPGA_FAIL;
 119
 120        switch (desc->iface) {
 121        case slave_serial:
 122                PRINTF ("%s: Launching Slave Serial Dump\n", __FUNCTION__);
 123                ret_val = virtex2_ss_dump(desc, buf, bsize);
 124                break;
 125
 126        case slave_parallel:
 127                PRINTF ("%s: Launching Slave Parallel Dump\n", __FUNCTION__);
 128                ret_val = virtex2_ssm_dump(desc, buf, bsize);
 129                break;
 130
 131        default:
 132                printf ("%s: Unsupported interface type, %d\n",
 133                                __FUNCTION__, desc->iface);
 134        }
 135        return ret_val;
 136}
 137
 138static int virtex2_info(xilinx_desc *desc)
 139{
 140        return FPGA_SUCCESS;
 141}
 142
 143/*
 144 * Virtex-II Slave SelectMap configuration loader. Configuration via
 145 * SelectMap is as follows:
 146 * 1. Set the FPGA's PROG_B line low.
 147 * 2. Set the FPGA's PROG_B line high.  Wait for INIT_B to go high.
 148 * 3. Write data to the SelectMap port.  If INIT_B goes low at any time
 149 *    this process, a configuration error (most likely CRC failure) has
 150 *    ocurred.  At this point a status word may be read from the
 151 *    SelectMap interface to determine the source of the problem (You
 152 *    could, for instance, put this in your 'abort' function handler).
 153 * 4. After all data has been written, test the state of the FPGA
 154 *    INIT_B and DONE lines.  If both are high, configuration has
 155 *    succeeded. Congratulations!
 156 */
 157static int virtex2_ssm_load(xilinx_desc *desc, const void *buf, size_t bsize)
 158{
 159        int ret_val = FPGA_FAIL;
 160        xilinx_virtex2_slave_selectmap_fns *fn = desc->iface_fns;
 161
 162        PRINTF ("%s:%d: Start with interface functions @ 0x%p\n",
 163                        __FUNCTION__, __LINE__, fn);
 164
 165        if (fn) {
 166                size_t bytecount = 0;
 167                unsigned char *data = (unsigned char *) buf;
 168                int cookie = desc->cookie;
 169                unsigned long ts;
 170
 171                /* Gotta split this one up (so the stack won't blow??) */
 172                PRINTF ("%s:%d: Function Table:\n"
 173                                "  base   0x%p\n"
 174                                "  struct 0x%p\n"
 175                                "  pre    0x%p\n"
 176                                "  prog   0x%p\n"
 177                                "  init   0x%p\n"
 178                                "  error  0x%p\n",
 179                                __FUNCTION__, __LINE__,
 180                                &fn, fn, fn->pre, fn->pgm, fn->init, fn->err);
 181                PRINTF ("  clock  0x%p\n"
 182                                "  cs     0x%p\n"
 183                                "  write  0x%p\n"
 184                                "  rdata  0x%p\n"
 185                                "  wdata  0x%p\n"
 186                                "  busy   0x%p\n"
 187                                "  abort  0x%p\n"
 188                                "  post   0x%p\n\n",
 189                                fn->clk, fn->cs, fn->wr, fn->rdata, fn->wdata,
 190                                fn->busy, fn->abort, fn->post);
 191
 192#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 193                printf ("Initializing FPGA Device %d...\n", cookie);
 194#endif
 195                /*
 196                 * Run the pre configuration function if there is one.
 197                 */
 198                if (*fn->pre) {
 199                        (*fn->pre) (cookie);
 200                }
 201
 202                /*
 203                 * Assert the program line.  The minimum pulse width for
 204                 * Virtex II devices is 300 nS (Tprogram parameter in datasheet).
 205                 * There is no maximum value for the pulse width.  Check to make
 206                 * sure that INIT_B goes low after assertion of PROG_B
 207                 */
 208                (*fn->pgm) (true, true, cookie);
 209                udelay (10);
 210                ts = get_timer (0);
 211                do {
 212                        if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT_INIT) {
 213                                printf ("%s:%d: ** Timeout after %d ticks waiting for INIT"
 214                                                " to assert.\n", __FUNCTION__, __LINE__,
 215                                                CONFIG_SYS_FPGA_WAIT_INIT);
 216                                (*fn->abort) (cookie);
 217                                return FPGA_FAIL;
 218                        }
 219                } while (!(*fn->init) (cookie));
 220
 221                (*fn->pgm) (false, true, cookie);
 222                CONFIG_FPGA_DELAY ();
 223                (*fn->clk) (true, true, cookie);
 224
 225                /*
 226                 * Start a timer and wait for INIT_B to go high
 227                 */
 228                ts = get_timer (0);
 229                do {
 230                        CONFIG_FPGA_DELAY ();
 231                        if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT_INIT) {
 232                                printf ("%s:%d: ** Timeout after %d ticks waiting for INIT"
 233                                                " to deassert.\n", __FUNCTION__, __LINE__,
 234                                                CONFIG_SYS_FPGA_WAIT_INIT);
 235                                (*fn->abort) (cookie);
 236                                return FPGA_FAIL;
 237                        }
 238                } while ((*fn->init) (cookie) && (*fn->busy) (cookie));
 239
 240                (*fn->wr) (true, true, cookie);
 241                (*fn->cs) (true, true, cookie);
 242
 243                udelay (10000);
 244
 245                /*
 246                 * Load the data byte by byte
 247                 */
 248                while (bytecount < bsize) {
 249#ifdef CONFIG_SYS_FPGA_CHECK_CTRLC
 250                        if (ctrlc ()) {
 251                                (*fn->abort) (cookie);
 252                                return FPGA_FAIL;
 253                        }
 254#endif
 255
 256                        if ((*fn->done) (cookie) == FPGA_SUCCESS) {
 257                            PRINTF ("%s:%d:done went active early, bytecount = %d\n",
 258                                    __FUNCTION__, __LINE__, bytecount);
 259                            break;
 260                        }
 261
 262#ifdef CONFIG_SYS_FPGA_CHECK_ERROR
 263                        if ((*fn->init) (cookie)) {
 264                                printf ("\n%s:%d:  ** Error: INIT asserted during"
 265                                                " configuration\n", __FUNCTION__, __LINE__);
 266                                printf ("%d = buffer offset, %d = buffer size\n",
 267                                        bytecount, bsize);
 268                                (*fn->abort) (cookie);
 269                                return FPGA_FAIL;
 270                        }
 271#endif
 272
 273                        (*fn->wdata) (data[bytecount++], true, cookie);
 274                        CONFIG_FPGA_DELAY ();
 275
 276                        /*
 277                         * Cycle the clock pin
 278                         */
 279                        (*fn->clk) (false, true, cookie);
 280                        CONFIG_FPGA_DELAY ();
 281                        (*fn->clk) (true, true, cookie);
 282
 283#ifdef CONFIG_SYS_FPGA_CHECK_BUSY
 284                        ts = get_timer (0);
 285                        while ((*fn->busy) (cookie)) {
 286                                if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT_BUSY) {
 287                                        printf ("%s:%d: ** Timeout after %d ticks waiting for"
 288                                                        " BUSY to deassert\n",
 289                                                        __FUNCTION__, __LINE__, CONFIG_SYS_FPGA_WAIT_BUSY);
 290                                        (*fn->abort) (cookie);
 291                                        return FPGA_FAIL;
 292                                }
 293                        }
 294#endif
 295
 296#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 297                        if (bytecount % (bsize / 40) == 0)
 298                                putc ('.');
 299#endif
 300                }
 301
 302                /*
 303                 * Finished writing the data; deassert FPGA CS_B and WRITE_B signals.
 304                 */
 305                CONFIG_FPGA_DELAY ();
 306                (*fn->cs) (false, true, cookie);
 307                (*fn->wr) (false, true, cookie);
 308
 309#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 310                putc ('\n');
 311#endif
 312
 313                /*
 314                 * Check for successful configuration.  FPGA INIT_B and DONE should
 315                 * both be high upon successful configuration.
 316                 */
 317                ts = get_timer (0);
 318                ret_val = FPGA_SUCCESS;
 319                while (((*fn->done) (cookie) == FPGA_FAIL) || (*fn->init) (cookie)) {
 320                        if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT_CONFIG) {
 321                                printf ("%s:%d: ** Timeout after %d ticks waiting for DONE to"
 322                                                "assert and INIT to deassert\n",
 323                                                __FUNCTION__, __LINE__, CONFIG_SYS_FPGA_WAIT_CONFIG);
 324                                (*fn->abort) (cookie);
 325                                ret_val = FPGA_FAIL;
 326                                break;
 327                        }
 328                }
 329
 330                if (ret_val == FPGA_SUCCESS) {
 331#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 332                        printf ("Initialization of FPGA device %d complete\n", cookie);
 333#endif
 334                        /*
 335                         * Run the post configuration function if there is one.
 336                         */
 337                        if (*fn->post) {
 338                                (*fn->post) (cookie);
 339                        }
 340                } else {
 341#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 342                        printf ("** Initialization of FPGA device %d FAILED\n",
 343                                        cookie);
 344#endif
 345                }
 346        } else {
 347                printf ("%s:%d: NULL Interface function table!\n",
 348                                __FUNCTION__, __LINE__);
 349        }
 350        return ret_val;
 351}
 352
 353/*
 354 * Read the FPGA configuration data
 355 */
 356static int virtex2_ssm_dump(xilinx_desc *desc, const void *buf, size_t bsize)
 357{
 358        int ret_val = FPGA_FAIL;
 359        xilinx_virtex2_slave_selectmap_fns *fn = desc->iface_fns;
 360
 361        if (fn) {
 362                unsigned char *data = (unsigned char *) buf;
 363                size_t bytecount = 0;
 364                int cookie = desc->cookie;
 365
 366                printf ("Starting Dump of FPGA Device %d...\n", cookie);
 367
 368                (*fn->cs) (true, true, cookie);
 369                (*fn->clk) (true, true, cookie);
 370
 371                while (bytecount < bsize) {
 372#ifdef CONFIG_SYS_FPGA_CHECK_CTRLC
 373                        if (ctrlc ()) {
 374                                (*fn->abort) (cookie);
 375                                return FPGA_FAIL;
 376                        }
 377#endif
 378                        /*
 379                         * Cycle the clock and read the data
 380                         */
 381                        (*fn->clk) (false, true, cookie);
 382                        (*fn->clk) (true, true, cookie);
 383                        (*fn->rdata) (&(data[bytecount++]), cookie);
 384#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 385                        if (bytecount % (bsize / 40) == 0)
 386                                putc ('.');
 387#endif
 388                }
 389
 390                /*
 391                 * Deassert CS_B and cycle the clock to deselect the device.
 392                 */
 393                (*fn->cs) (false, false, cookie);
 394                (*fn->clk) (false, true, cookie);
 395                (*fn->clk) (true, true, cookie);
 396
 397#ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK
 398                putc ('\n');
 399#endif
 400                puts ("Done.\n");
 401        } else {
 402                printf ("%s:%d: NULL Interface function table!\n",
 403                                __FUNCTION__, __LINE__);
 404        }
 405        return ret_val;
 406}
 407
 408static int virtex2_ss_load(xilinx_desc *desc, const void *buf, size_t bsize)
 409{
 410        printf ("%s: Slave Serial Loading is unsupported\n", __FUNCTION__);
 411        return FPGA_FAIL;
 412}
 413
 414static int virtex2_ss_dump(xilinx_desc *desc, const void *buf, size_t bsize)
 415{
 416        printf ("%s: Slave Serial Dumping is unsupported\n", __FUNCTION__);
 417        return FPGA_FAIL;
 418}
 419
 420/* vim: set ts=4 tw=78: */
 421
 422struct xilinx_fpga_op virtex2_op = {
 423        .load = virtex2_load,
 424        .dump = virtex2_dump,
 425        .info = virtex2_info,
 426};
 427