1 /* 2 * (C) Copyright 2002 3 * Rich Ireland, Enterasys Networks, rireland@enterasys.com. 4 * 5 * SPDX-License-Identifier: GPL-2.0+ 6 */ 7 8 /* 9 * Configuration support for Xilinx Spartan3 devices. Based 10 * on spartan2.c (Rich Ireland, rireland@enterasys.com). 11 */ 12 13 #include <common.h> /* core U-Boot definitions */ 14 #include <spartan3.h> /* Spartan-II device family */ 15 16 /* Define FPGA_DEBUG to get debug printf's */ 17 #ifdef FPGA_DEBUG 18 #define PRINTF(fmt,args...) printf (fmt ,##args) 19 #else 20 #define PRINTF(fmt,args...) 21 #endif 22 23 #undef CONFIG_SYS_FPGA_CHECK_BUSY 24 25 /* Note: The assumption is that we cannot possibly run fast enough to 26 * overrun the device (the Slave Parallel mode can free run at 50MHz). 27 * If there is a need to operate slower, define CONFIG_FPGA_DELAY in 28 * the board config file to slow things down. 29 */ 30 #ifndef CONFIG_FPGA_DELAY 31 #define CONFIG_FPGA_DELAY() 32 #endif 33 34 #ifndef CONFIG_SYS_FPGA_WAIT 35 #define CONFIG_SYS_FPGA_WAIT CONFIG_SYS_HZ/100 /* 10 ms */ 36 #endif 37 38 static int spartan3_sp_load(xilinx_desc *desc, const void *buf, size_t bsize); 39 static int spartan3_sp_dump(xilinx_desc *desc, const void *buf, size_t bsize); 40 /* static int spartan3_sp_info(xilinx_desc *desc ); */ 41 42 static int spartan3_ss_load(xilinx_desc *desc, const void *buf, size_t bsize); 43 static int spartan3_ss_dump(xilinx_desc *desc, const void *buf, size_t bsize); 44 /* static int spartan3_ss_info(xilinx_desc *desc); */ 45 46 /* ------------------------------------------------------------------------- */ 47 /* Spartan-II Generic Implementation */ 48 static int spartan3_load(xilinx_desc *desc, const void *buf, size_t bsize, 49 bitstream_type bstype) 50 { 51 int ret_val = FPGA_FAIL; 52 53 switch (desc->iface) { 54 case slave_serial: 55 PRINTF ("%s: Launching Slave Serial Load\n", __FUNCTION__); 56 ret_val = spartan3_ss_load(desc, buf, bsize); 57 break; 58 59 case slave_parallel: 60 PRINTF ("%s: Launching Slave Parallel Load\n", __FUNCTION__); 61 ret_val = spartan3_sp_load(desc, buf, bsize); 62 break; 63 64 default: 65 printf ("%s: Unsupported interface type, %d\n", 66 __FUNCTION__, desc->iface); 67 } 68 69 return ret_val; 70 } 71 72 static int spartan3_dump(xilinx_desc *desc, const void *buf, size_t bsize) 73 { 74 int ret_val = FPGA_FAIL; 75 76 switch (desc->iface) { 77 case slave_serial: 78 PRINTF ("%s: Launching Slave Serial Dump\n", __FUNCTION__); 79 ret_val = spartan3_ss_dump(desc, buf, bsize); 80 break; 81 82 case slave_parallel: 83 PRINTF ("%s: Launching Slave Parallel Dump\n", __FUNCTION__); 84 ret_val = spartan3_sp_dump(desc, buf, bsize); 85 break; 86 87 default: 88 printf ("%s: Unsupported interface type, %d\n", 89 __FUNCTION__, desc->iface); 90 } 91 92 return ret_val; 93 } 94 95 static int spartan3_info(xilinx_desc *desc) 96 { 97 return FPGA_SUCCESS; 98 } 99 100 101 /* ------------------------------------------------------------------------- */ 102 /* Spartan-II Slave Parallel Generic Implementation */ 103 104 static int spartan3_sp_load(xilinx_desc *desc, const void *buf, size_t bsize) 105 { 106 int ret_val = FPGA_FAIL; /* assume the worst */ 107 xilinx_spartan3_slave_parallel_fns *fn = desc->iface_fns; 108 109 PRINTF ("%s: start with interface functions @ 0x%p\n", 110 __FUNCTION__, fn); 111 112 if (fn) { 113 size_t bytecount = 0; 114 unsigned char *data = (unsigned char *) buf; 115 int cookie = desc->cookie; /* make a local copy */ 116 unsigned long ts; /* timestamp */ 117 118 PRINTF ("%s: Function Table:\n" 119 "ptr:\t0x%p\n" 120 "struct: 0x%p\n" 121 "pre: 0x%p\n" 122 "pgm:\t0x%p\n" 123 "init:\t0x%p\n" 124 "err:\t0x%p\n" 125 "clk:\t0x%p\n" 126 "cs:\t0x%p\n" 127 "wr:\t0x%p\n" 128 "read data:\t0x%p\n" 129 "write data:\t0x%p\n" 130 "busy:\t0x%p\n" 131 "abort:\t0x%p\n", 132 "post:\t0x%p\n\n", 133 __FUNCTION__, &fn, fn, fn->pre, fn->pgm, fn->init, fn->err, 134 fn->clk, fn->cs, fn->wr, fn->rdata, fn->wdata, fn->busy, 135 fn->abort, fn->post); 136 137 /* 138 * This code is designed to emulate the "Express Style" 139 * Continuous Data Loading in Slave Parallel Mode for 140 * the Spartan-II Family. 141 */ 142 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 143 printf ("Loading FPGA Device %d...\n", cookie); 144 #endif 145 /* 146 * Run the pre configuration function if there is one. 147 */ 148 if (*fn->pre) { 149 (*fn->pre) (cookie); 150 } 151 152 /* Establish the initial state */ 153 (*fn->pgm) (true, true, cookie); /* Assert the program, commit */ 154 155 /* Get ready for the burn */ 156 CONFIG_FPGA_DELAY (); 157 (*fn->pgm) (false, true, cookie); /* Deassert the program, commit */ 158 159 ts = get_timer (0); /* get current time */ 160 /* Now wait for INIT and BUSY to go high */ 161 do { 162 CONFIG_FPGA_DELAY (); 163 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 164 puts ("** Timeout waiting for INIT to clear.\n"); 165 (*fn->abort) (cookie); /* abort the burn */ 166 return FPGA_FAIL; 167 } 168 } while ((*fn->init) (cookie) && (*fn->busy) (cookie)); 169 170 (*fn->wr) (true, true, cookie); /* Assert write, commit */ 171 (*fn->cs) (true, true, cookie); /* Assert chip select, commit */ 172 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 173 174 /* Load the data */ 175 while (bytecount < bsize) { 176 /* XXX - do we check for an Ctrl-C press in here ??? */ 177 /* XXX - Check the error bit? */ 178 179 (*fn->wdata) (data[bytecount++], true, cookie); /* write the data */ 180 CONFIG_FPGA_DELAY (); 181 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 182 CONFIG_FPGA_DELAY (); 183 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 184 185 #ifdef CONFIG_SYS_FPGA_CHECK_BUSY 186 ts = get_timer (0); /* get current time */ 187 while ((*fn->busy) (cookie)) { 188 /* XXX - we should have a check in here somewhere to 189 * make sure we aren't busy forever... */ 190 191 CONFIG_FPGA_DELAY (); 192 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 193 CONFIG_FPGA_DELAY (); 194 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 195 196 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 197 puts ("** Timeout waiting for BUSY to clear.\n"); 198 (*fn->abort) (cookie); /* abort the burn */ 199 return FPGA_FAIL; 200 } 201 } 202 #endif 203 204 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 205 if (bytecount % (bsize / 40) == 0) 206 putc ('.'); /* let them know we are alive */ 207 #endif 208 } 209 210 CONFIG_FPGA_DELAY (); 211 (*fn->cs) (false, true, cookie); /* Deassert the chip select */ 212 (*fn->wr) (false, true, cookie); /* Deassert the write pin */ 213 214 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 215 putc ('\n'); /* terminate the dotted line */ 216 #endif 217 218 /* now check for done signal */ 219 ts = get_timer (0); /* get current time */ 220 ret_val = FPGA_SUCCESS; 221 while ((*fn->done) (cookie) == FPGA_FAIL) { 222 /* XXX - we should have a check in here somewhere to 223 * make sure we aren't busy forever... */ 224 225 CONFIG_FPGA_DELAY (); 226 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 227 CONFIG_FPGA_DELAY (); 228 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 229 230 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 231 puts ("** Timeout waiting for DONE to clear.\n"); 232 (*fn->abort) (cookie); /* abort the burn */ 233 ret_val = FPGA_FAIL; 234 break; 235 } 236 } 237 238 /* 239 * Run the post configuration function if there is one. 240 */ 241 if (*fn->post) 242 (*fn->post) (cookie); 243 244 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 245 if (ret_val == FPGA_SUCCESS) 246 puts ("Done.\n"); 247 else 248 puts ("Fail.\n"); 249 #endif 250 251 } else { 252 printf ("%s: NULL Interface function table!\n", __FUNCTION__); 253 } 254 255 return ret_val; 256 } 257 258 static int spartan3_sp_dump(xilinx_desc *desc, const void *buf, size_t bsize) 259 { 260 int ret_val = FPGA_FAIL; /* assume the worst */ 261 xilinx_spartan3_slave_parallel_fns *fn = desc->iface_fns; 262 263 if (fn) { 264 unsigned char *data = (unsigned char *) buf; 265 size_t bytecount = 0; 266 int cookie = desc->cookie; /* make a local copy */ 267 268 printf ("Starting Dump of FPGA Device %d...\n", cookie); 269 270 (*fn->cs) (true, true, cookie); /* Assert chip select, commit */ 271 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 272 273 /* dump the data */ 274 while (bytecount < bsize) { 275 /* XXX - do we check for an Ctrl-C press in here ??? */ 276 277 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 278 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 279 (*fn->rdata) (&(data[bytecount++]), cookie); /* read the data */ 280 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 281 if (bytecount % (bsize / 40) == 0) 282 putc ('.'); /* let them know we are alive */ 283 #endif 284 } 285 286 (*fn->cs) (false, false, cookie); /* Deassert the chip select */ 287 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 288 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 289 290 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 291 putc ('\n'); /* terminate the dotted line */ 292 #endif 293 puts ("Done.\n"); 294 295 /* XXX - checksum the data? */ 296 } else { 297 printf ("%s: NULL Interface function table!\n", __FUNCTION__); 298 } 299 300 return ret_val; 301 } 302 303 304 /* ------------------------------------------------------------------------- */ 305 306 static int spartan3_ss_load(xilinx_desc *desc, const void *buf, size_t bsize) 307 { 308 int ret_val = FPGA_FAIL; /* assume the worst */ 309 xilinx_spartan3_slave_serial_fns *fn = desc->iface_fns; 310 int i; 311 unsigned char val; 312 313 PRINTF ("%s: start with interface functions @ 0x%p\n", 314 __FUNCTION__, fn); 315 316 if (fn) { 317 size_t bytecount = 0; 318 unsigned char *data = (unsigned char *) buf; 319 int cookie = desc->cookie; /* make a local copy */ 320 unsigned long ts; /* timestamp */ 321 322 PRINTF ("%s: Function Table:\n" 323 "ptr:\t0x%p\n" 324 "struct: 0x%p\n" 325 "pgm:\t0x%p\n" 326 "init:\t0x%p\n" 327 "clk:\t0x%p\n" 328 "wr:\t0x%p\n" 329 "done:\t0x%p\n\n", 330 __FUNCTION__, &fn, fn, fn->pgm, fn->init, 331 fn->clk, fn->wr, fn->done); 332 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 333 printf ("Loading FPGA Device %d...\n", cookie); 334 #endif 335 336 /* 337 * Run the pre configuration function if there is one. 338 */ 339 if (*fn->pre) { 340 (*fn->pre) (cookie); 341 } 342 343 /* Establish the initial state */ 344 (*fn->pgm) (true, true, cookie); /* Assert the program, commit */ 345 346 /* Wait for INIT state (init low) */ 347 ts = get_timer (0); /* get current time */ 348 do { 349 CONFIG_FPGA_DELAY (); 350 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 351 puts ("** Timeout waiting for INIT to start.\n"); 352 if (*fn->abort) 353 (*fn->abort) (cookie); 354 return FPGA_FAIL; 355 } 356 } while (!(*fn->init) (cookie)); 357 358 /* Get ready for the burn */ 359 CONFIG_FPGA_DELAY (); 360 (*fn->pgm) (false, true, cookie); /* Deassert the program, commit */ 361 362 ts = get_timer (0); /* get current time */ 363 /* Now wait for INIT to go high */ 364 do { 365 CONFIG_FPGA_DELAY (); 366 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 367 puts ("** Timeout waiting for INIT to clear.\n"); 368 if (*fn->abort) 369 (*fn->abort) (cookie); 370 return FPGA_FAIL; 371 } 372 } while ((*fn->init) (cookie)); 373 374 /* Load the data */ 375 if(*fn->bwr) 376 (*fn->bwr) (data, bsize, true, cookie); 377 else { 378 while (bytecount < bsize) { 379 380 /* Xilinx detects an error if INIT goes low (active) 381 while DONE is low (inactive) */ 382 if ((*fn->done) (cookie) == 0 && (*fn->init) (cookie)) { 383 puts ("** CRC error during FPGA load.\n"); 384 if (*fn->abort) 385 (*fn->abort) (cookie); 386 return (FPGA_FAIL); 387 } 388 val = data [bytecount ++]; 389 i = 8; 390 do { 391 /* Deassert the clock */ 392 (*fn->clk) (false, true, cookie); 393 CONFIG_FPGA_DELAY (); 394 /* Write data */ 395 (*fn->wr) ((val & 0x80), true, cookie); 396 CONFIG_FPGA_DELAY (); 397 /* Assert the clock */ 398 (*fn->clk) (true, true, cookie); 399 CONFIG_FPGA_DELAY (); 400 val <<= 1; 401 i --; 402 } while (i > 0); 403 404 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 405 if (bytecount % (bsize / 40) == 0) 406 putc ('.'); /* let them know we are alive */ 407 #endif 408 } 409 } 410 411 CONFIG_FPGA_DELAY (); 412 413 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 414 putc ('\n'); /* terminate the dotted line */ 415 #endif 416 417 /* now check for done signal */ 418 ts = get_timer (0); /* get current time */ 419 ret_val = FPGA_SUCCESS; 420 (*fn->wr) (true, true, cookie); 421 422 while (! (*fn->done) (cookie)) { 423 /* XXX - we should have a check in here somewhere to 424 * make sure we aren't busy forever... */ 425 426 CONFIG_FPGA_DELAY (); 427 (*fn->clk) (false, true, cookie); /* Deassert the clock pin */ 428 CONFIG_FPGA_DELAY (); 429 (*fn->clk) (true, true, cookie); /* Assert the clock pin */ 430 431 putc ('*'); 432 433 if (get_timer (ts) > CONFIG_SYS_FPGA_WAIT) { /* check the time */ 434 puts ("** Timeout waiting for DONE to clear.\n"); 435 ret_val = FPGA_FAIL; 436 break; 437 } 438 } 439 putc ('\n'); /* terminate the dotted line */ 440 441 /* 442 * Run the post configuration function if there is one. 443 */ 444 if (*fn->post) 445 (*fn->post) (cookie); 446 447 #ifdef CONFIG_SYS_FPGA_PROG_FEEDBACK 448 if (ret_val == FPGA_SUCCESS) 449 puts ("Done.\n"); 450 else 451 puts ("Fail.\n"); 452 #endif 453 454 } else { 455 printf ("%s: NULL Interface function table!\n", __FUNCTION__); 456 } 457 458 return ret_val; 459 } 460 461 static int spartan3_ss_dump(xilinx_desc *desc, const void *buf, size_t bsize) 462 { 463 /* Readback is only available through the Slave Parallel and */ 464 /* boundary-scan interfaces. */ 465 printf ("%s: Slave Serial Dumping is unavailable\n", 466 __FUNCTION__); 467 return FPGA_FAIL; 468 } 469 470 struct xilinx_fpga_op spartan3_op = { 471 .load = spartan3_load, 472 .dump = spartan3_dump, 473 .info = spartan3_info, 474 }; 475