uboot/drivers/net/e1000_spi.c
<<
>>
Prefs
   1#include <common.h>
   2#include <console.h>
   3#include "e1000.h"
   4#include <linux/compiler.h>
   5
   6/*-----------------------------------------------------------------------
   7 * SPI transfer
   8 *
   9 * This writes "bitlen" bits out the SPI MOSI port and simultaneously clocks
  10 * "bitlen" bits in the SPI MISO port.  That's just the way SPI works.
  11 *
  12 * The source of the outgoing bits is the "dout" parameter and the
  13 * destination of the input bits is the "din" parameter.  Note that "dout"
  14 * and "din" can point to the same memory location, in which case the
  15 * input data overwrites the output data (since both are buffered by
  16 * temporary variables, this is OK).
  17 *
  18 * This may be interrupted with Ctrl-C if "intr" is true, otherwise it will
  19 * never return an error.
  20 */
  21static int e1000_spi_xfer(struct e1000_hw *hw, unsigned int bitlen,
  22                const void *dout_mem, void *din_mem, bool intr)
  23{
  24        const uint8_t *dout = dout_mem;
  25        uint8_t *din = din_mem;
  26
  27        uint8_t mask = 0;
  28        uint32_t eecd;
  29        unsigned long i;
  30
  31        /* Pre-read the control register */
  32        eecd = E1000_READ_REG(hw, EECD);
  33
  34        /* Iterate over each bit */
  35        for (i = 0, mask = 0x80; i < bitlen; i++, mask = (mask >> 1)?:0x80) {
  36                /* Check for interrupt */
  37                if (intr && ctrlc())
  38                        return -1;
  39
  40                /* Determine the output bit */
  41                if (dout && dout[i >> 3] & mask)
  42                        eecd |=  E1000_EECD_DI;
  43                else
  44                        eecd &= ~E1000_EECD_DI;
  45
  46                /* Write the output bit and wait 50us */
  47                E1000_WRITE_REG(hw, EECD, eecd);
  48                E1000_WRITE_FLUSH(hw);
  49                udelay(50);
  50
  51                /* Poke the clock (waits 50us) */
  52                e1000_raise_ee_clk(hw, &eecd);
  53
  54                /* Now read the input bit */
  55                eecd = E1000_READ_REG(hw, EECD);
  56                if (din) {
  57                        if (eecd & E1000_EECD_DO)
  58                                din[i >> 3] |=  mask;
  59                        else
  60                                din[i >> 3] &= ~mask;
  61                }
  62
  63                /* Poke the clock again (waits 50us) */
  64                e1000_lower_ee_clk(hw, &eecd);
  65        }
  66
  67        /* Now clear any remaining bits of the input */
  68        if (din && (i & 7))
  69                din[i >> 3] &= ~((mask << 1) - 1);
  70
  71        return 0;
  72}
  73
  74#ifdef CONFIG_E1000_SPI_GENERIC
  75static inline struct e1000_hw *e1000_hw_from_spi(struct spi_slave *spi)
  76{
  77        return container_of(spi, struct e1000_hw, spi);
  78}
  79
  80/* Not sure why all of these are necessary */
  81void spi_init_r(void) { /* Nothing to do */ }
  82void spi_init_f(void) { /* Nothing to do */ }
  83void spi_init(void)   { /* Nothing to do */ }
  84
  85struct spi_slave *spi_setup_slave(unsigned int bus, unsigned int cs,
  86                unsigned int max_hz, unsigned int mode)
  87{
  88        /* Find the right PCI device */
  89        struct e1000_hw *hw = e1000_find_card(bus);
  90        if (!hw) {
  91                printf("ERROR: No such e1000 device: e1000#%u\n", bus);
  92                return NULL;
  93        }
  94
  95        /* Make sure it has an SPI chip */
  96        if (hw->eeprom.type != e1000_eeprom_spi) {
  97                E1000_ERR(hw, "No attached SPI EEPROM found!\n");
  98                return NULL;
  99        }
 100
 101        /* Argument sanity checks */
 102        if (cs != 0) {
 103                E1000_ERR(hw, "No such SPI chip: %u\n", cs);
 104                return NULL;
 105        }
 106        if (mode != SPI_MODE_0) {
 107                E1000_ERR(hw, "Only SPI MODE-0 is supported!\n");
 108                return NULL;
 109        }
 110
 111        /* TODO: Use max_hz somehow */
 112        E1000_DBG(hw->nic, "EEPROM SPI access requested\n");
 113        return &hw->spi;
 114}
 115
 116void spi_free_slave(struct spi_slave *spi)
 117{
 118        __maybe_unused struct e1000_hw *hw = e1000_hw_from_spi(spi);
 119        E1000_DBG(hw->nic, "EEPROM SPI access released\n");
 120}
 121
 122int spi_claim_bus(struct spi_slave *spi)
 123{
 124        struct e1000_hw *hw = e1000_hw_from_spi(spi);
 125
 126        if (e1000_acquire_eeprom(hw)) {
 127                E1000_ERR(hw, "EEPROM SPI cannot be acquired!\n");
 128                return -1;
 129        }
 130
 131        return 0;
 132}
 133
 134void spi_release_bus(struct spi_slave *spi)
 135{
 136        struct e1000_hw *hw = e1000_hw_from_spi(spi);
 137        e1000_release_eeprom(hw);
 138}
 139
 140/* Skinny wrapper around e1000_spi_xfer */
 141int spi_xfer(struct spi_slave *spi, unsigned int bitlen,
 142                const void *dout_mem, void *din_mem, unsigned long flags)
 143{
 144        struct e1000_hw *hw = e1000_hw_from_spi(spi);
 145        int ret;
 146
 147        if (flags & SPI_XFER_BEGIN)
 148                e1000_standby_eeprom(hw);
 149
 150        ret = e1000_spi_xfer(hw, bitlen, dout_mem, din_mem, true);
 151
 152        if (flags & SPI_XFER_END)
 153                e1000_standby_eeprom(hw);
 154
 155        return ret;
 156}
 157
 158#endif /* not CONFIG_E1000_SPI_GENERIC */
 159
 160#ifdef CONFIG_CMD_E1000
 161
 162/* The EEPROM opcodes */
 163#define SPI_EEPROM_ENABLE_WR    0x06
 164#define SPI_EEPROM_DISABLE_WR   0x04
 165#define SPI_EEPROM_WRITE_STATUS 0x01
 166#define SPI_EEPROM_READ_STATUS  0x05
 167#define SPI_EEPROM_WRITE_PAGE   0x02
 168#define SPI_EEPROM_READ_PAGE    0x03
 169
 170/* The EEPROM status bits */
 171#define SPI_EEPROM_STATUS_BUSY  0x01
 172#define SPI_EEPROM_STATUS_WREN  0x02
 173
 174static int e1000_spi_eeprom_enable_wr(struct e1000_hw *hw, bool intr)
 175{
 176        u8 op[] = { SPI_EEPROM_ENABLE_WR };
 177        e1000_standby_eeprom(hw);
 178        return e1000_spi_xfer(hw, 8*sizeof(op), op, NULL, intr);
 179}
 180
 181/*
 182 * These have been tested to perform correctly, but they are not used by any
 183 * of the EEPROM commands at this time.
 184 */
 185static __maybe_unused int e1000_spi_eeprom_disable_wr(struct e1000_hw *hw,
 186                                                      bool intr)
 187{
 188        u8 op[] = { SPI_EEPROM_DISABLE_WR };
 189        e1000_standby_eeprom(hw);
 190        return e1000_spi_xfer(hw, 8*sizeof(op), op, NULL, intr);
 191}
 192
 193static __maybe_unused int e1000_spi_eeprom_write_status(struct e1000_hw *hw,
 194                                                        u8 status, bool intr)
 195{
 196        u8 op[] = { SPI_EEPROM_WRITE_STATUS, status };
 197        e1000_standby_eeprom(hw);
 198        return e1000_spi_xfer(hw, 8*sizeof(op), op, NULL, intr);
 199}
 200
 201static int e1000_spi_eeprom_read_status(struct e1000_hw *hw, bool intr)
 202{
 203        u8 op[] = { SPI_EEPROM_READ_STATUS, 0 };
 204        e1000_standby_eeprom(hw);
 205        if (e1000_spi_xfer(hw, 8*sizeof(op), op, op, intr))
 206                return -1;
 207        return op[1];
 208}
 209
 210static int e1000_spi_eeprom_write_page(struct e1000_hw *hw,
 211                const void *data, u16 off, u16 len, bool intr)
 212{
 213        u8 op[] = {
 214                SPI_EEPROM_WRITE_PAGE,
 215                (off >> (hw->eeprom.address_bits - 8)) & 0xff, off & 0xff
 216        };
 217
 218        e1000_standby_eeprom(hw);
 219
 220        if (e1000_spi_xfer(hw, 8 + hw->eeprom.address_bits, op, NULL, intr))
 221                return -1;
 222        if (e1000_spi_xfer(hw, len << 3, data, NULL, intr))
 223                return -1;
 224
 225        return 0;
 226}
 227
 228static int e1000_spi_eeprom_read_page(struct e1000_hw *hw,
 229                void *data, u16 off, u16 len, bool intr)
 230{
 231        u8 op[] = {
 232                SPI_EEPROM_READ_PAGE,
 233                (off >> (hw->eeprom.address_bits - 8)) & 0xff, off & 0xff
 234        };
 235
 236        e1000_standby_eeprom(hw);
 237
 238        if (e1000_spi_xfer(hw, 8 + hw->eeprom.address_bits, op, NULL, intr))
 239                return -1;
 240        if (e1000_spi_xfer(hw, len << 3, NULL, data, intr))
 241                return -1;
 242
 243        return 0;
 244}
 245
 246static int e1000_spi_eeprom_poll_ready(struct e1000_hw *hw, bool intr)
 247{
 248        int status;
 249        while ((status = e1000_spi_eeprom_read_status(hw, intr)) >= 0) {
 250                if (!(status & SPI_EEPROM_STATUS_BUSY))
 251                        return 0;
 252        }
 253        return -1;
 254}
 255
 256static int e1000_spi_eeprom_dump(struct e1000_hw *hw,
 257                void *data, u16 off, unsigned int len, bool intr)
 258{
 259        /* Interruptibly wait for the EEPROM to be ready */
 260        if (e1000_spi_eeprom_poll_ready(hw, intr))
 261                return -1;
 262
 263        /* Dump each page in sequence */
 264        while (len) {
 265                /* Calculate the data bytes on this page */
 266                u16 pg_off = off & (hw->eeprom.page_size - 1);
 267                u16 pg_len = hw->eeprom.page_size - pg_off;
 268                if (pg_len > len)
 269                        pg_len = len;
 270
 271                /* Now dump the page */
 272                if (e1000_spi_eeprom_read_page(hw, data, off, pg_len, intr))
 273                        return -1;
 274
 275                /* Otherwise go on to the next page */
 276                len  -= pg_len;
 277                off  += pg_len;
 278                data += pg_len;
 279        }
 280
 281        /* We're done! */
 282        return 0;
 283}
 284
 285static int e1000_spi_eeprom_program(struct e1000_hw *hw,
 286                const void *data, u16 off, u16 len, bool intr)
 287{
 288        /* Program each page in sequence */
 289        while (len) {
 290                /* Calculate the data bytes on this page */
 291                u16 pg_off = off & (hw->eeprom.page_size - 1);
 292                u16 pg_len = hw->eeprom.page_size - pg_off;
 293                if (pg_len > len)
 294                        pg_len = len;
 295
 296                /* Interruptibly wait for the EEPROM to be ready */
 297                if (e1000_spi_eeprom_poll_ready(hw, intr))
 298                        return -1;
 299
 300                /* Enable write access */
 301                if (e1000_spi_eeprom_enable_wr(hw, intr))
 302                        return -1;
 303
 304                /* Now program the page */
 305                if (e1000_spi_eeprom_write_page(hw, data, off, pg_len, intr))
 306                        return -1;
 307
 308                /* Otherwise go on to the next page */
 309                len  -= pg_len;
 310                off  += pg_len;
 311                data += pg_len;
 312        }
 313
 314        /* Wait for the last write to complete */
 315        if (e1000_spi_eeprom_poll_ready(hw, intr))
 316                return -1;
 317
 318        /* We're done! */
 319        return 0;
 320}
 321
 322static int do_e1000_spi_show(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
 323                int argc, char * const argv[])
 324{
 325        unsigned int length = 0;
 326        u16 i, offset = 0;
 327        u8 *buffer;
 328        int err;
 329
 330        if (argc > 2) {
 331                cmd_usage(cmdtp);
 332                return 1;
 333        }
 334
 335        /* Parse the offset and length */
 336        if (argc >= 1)
 337                offset = simple_strtoul(argv[0], NULL, 0);
 338        if (argc == 2)
 339                length = simple_strtoul(argv[1], NULL, 0);
 340        else if (offset < (hw->eeprom.word_size << 1))
 341                length = (hw->eeprom.word_size << 1) - offset;
 342
 343        /* Extra sanity checks */
 344        if (!length) {
 345                E1000_ERR(hw, "Requested zero-sized dump!\n");
 346                return 1;
 347        }
 348        if ((0x10000 < length) || (0x10000 - length < offset)) {
 349                E1000_ERR(hw, "Can't dump past 0xFFFF!\n");
 350                return 1;
 351        }
 352
 353        /* Allocate a buffer to hold stuff */
 354        buffer = malloc(length);
 355        if (!buffer) {
 356                E1000_ERR(hw, "Out of Memory!\n");
 357                return 1;
 358        }
 359
 360        /* Acquire the EEPROM and perform the dump */
 361        if (e1000_acquire_eeprom(hw)) {
 362                E1000_ERR(hw, "EEPROM SPI cannot be acquired!\n");
 363                free(buffer);
 364                return 1;
 365        }
 366        err = e1000_spi_eeprom_dump(hw, buffer, offset, length, true);
 367        e1000_release_eeprom(hw);
 368        if (err) {
 369                E1000_ERR(hw, "Interrupted!\n");
 370                free(buffer);
 371                return 1;
 372        }
 373
 374        /* Now hexdump the result */
 375        printf("%s: ===== Intel e1000 EEPROM (0x%04hX - 0x%04hX) =====",
 376                        hw->name, offset, offset + length - 1);
 377        for (i = 0; i < length; i++) {
 378                if ((i & 0xF) == 0)
 379                        printf("\n%s: %04hX: ", hw->name, offset + i);
 380                else if ((i & 0xF) == 0x8)
 381                        printf(" ");
 382                printf(" %02hx", buffer[i]);
 383        }
 384        printf("\n");
 385
 386        /* Success! */
 387        free(buffer);
 388        return 0;
 389}
 390
 391static int do_e1000_spi_dump(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
 392                int argc, char * const argv[])
 393{
 394        unsigned int length;
 395        u16 offset;
 396        void *dest;
 397
 398        if (argc != 3) {
 399                cmd_usage(cmdtp);
 400                return 1;
 401        }
 402
 403        /* Parse the arguments */
 404        dest = (void *)simple_strtoul(argv[0], NULL, 16);
 405        offset = simple_strtoul(argv[1], NULL, 0);
 406        length = simple_strtoul(argv[2], NULL, 0);
 407
 408        /* Extra sanity checks */
 409        if (!length) {
 410                E1000_ERR(hw, "Requested zero-sized dump!\n");
 411                return 1;
 412        }
 413        if ((0x10000 < length) || (0x10000 - length < offset)) {
 414                E1000_ERR(hw, "Can't dump past 0xFFFF!\n");
 415                return 1;
 416        }
 417
 418        /* Acquire the EEPROM */
 419        if (e1000_acquire_eeprom(hw)) {
 420                E1000_ERR(hw, "EEPROM SPI cannot be acquired!\n");
 421                return 1;
 422        }
 423
 424        /* Perform the programming operation */
 425        if (e1000_spi_eeprom_dump(hw, dest, offset, length, true) < 0) {
 426                E1000_ERR(hw, "Interrupted!\n");
 427                e1000_release_eeprom(hw);
 428                return 1;
 429        }
 430
 431        e1000_release_eeprom(hw);
 432        printf("%s: ===== EEPROM DUMP COMPLETE =====\n", hw->name);
 433        return 0;
 434}
 435
 436static int do_e1000_spi_program(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
 437                int argc, char * const argv[])
 438{
 439        unsigned int length;
 440        const void *source;
 441        u16 offset;
 442
 443        if (argc != 3) {
 444                cmd_usage(cmdtp);
 445                return 1;
 446        }
 447
 448        /* Parse the arguments */
 449        source = (const void *)simple_strtoul(argv[0], NULL, 16);
 450        offset = simple_strtoul(argv[1], NULL, 0);
 451        length = simple_strtoul(argv[2], NULL, 0);
 452
 453        /* Acquire the EEPROM */
 454        if (e1000_acquire_eeprom(hw)) {
 455                E1000_ERR(hw, "EEPROM SPI cannot be acquired!\n");
 456                return 1;
 457        }
 458
 459        /* Perform the programming operation */
 460        if (e1000_spi_eeprom_program(hw, source, offset, length, true) < 0) {
 461                E1000_ERR(hw, "Interrupted!\n");
 462                e1000_release_eeprom(hw);
 463                return 1;
 464        }
 465
 466        e1000_release_eeprom(hw);
 467        printf("%s: ===== EEPROM PROGRAMMED =====\n", hw->name);
 468        return 0;
 469}
 470
 471static int do_e1000_spi_checksum(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
 472                int argc, char * const argv[])
 473{
 474        uint16_t i, length, checksum = 0, checksum_reg;
 475        uint16_t *buffer;
 476        bool upd;
 477
 478        if (argc == 0)
 479                upd = 0;
 480        else if ((argc == 1) && !strcmp(argv[0], "update"))
 481                upd = 1;
 482        else {
 483                cmd_usage(cmdtp);
 484                return 1;
 485        }
 486
 487        /* Allocate a temporary buffer */
 488        length = sizeof(uint16_t) * (EEPROM_CHECKSUM_REG + 1);
 489        buffer = malloc(length);
 490        if (!buffer) {
 491                E1000_ERR(hw, "Unable to allocate EEPROM buffer!\n");
 492                return 1;
 493        }
 494
 495        /* Acquire the EEPROM */
 496        if (e1000_acquire_eeprom(hw)) {
 497                E1000_ERR(hw, "EEPROM SPI cannot be acquired!\n");
 498                return 1;
 499        }
 500
 501        /* Read the EEPROM */
 502        if (e1000_spi_eeprom_dump(hw, buffer, 0, length, true) < 0) {
 503                E1000_ERR(hw, "Interrupted!\n");
 504                e1000_release_eeprom(hw);
 505                return 1;
 506        }
 507
 508        /* Compute the checksum and read the expected value */
 509        for (i = 0; i < EEPROM_CHECKSUM_REG; i++)
 510                checksum += le16_to_cpu(buffer[i]);
 511        checksum = ((uint16_t)EEPROM_SUM) - checksum;
 512        checksum_reg = le16_to_cpu(buffer[i]);
 513
 514        /* Verify it! */
 515        if (checksum_reg == checksum) {
 516                printf("%s: INFO: EEPROM checksum is correct! (0x%04hx)\n",
 517                                hw->name, checksum);
 518                e1000_release_eeprom(hw);
 519                return 0;
 520        }
 521
 522        /* Hrm, verification failed, print an error */
 523        E1000_ERR(hw, "EEPROM checksum is incorrect!\n");
 524        E1000_ERR(hw, "  ...register was 0x%04hx, calculated 0x%04hx\n",
 525                  checksum_reg, checksum);
 526
 527        /* If they didn't ask us to update it, just return an error */
 528        if (!upd) {
 529                e1000_release_eeprom(hw);
 530                return 1;
 531        }
 532
 533        /* Ok, correct it! */
 534        printf("%s: Reprogramming the EEPROM checksum...\n", hw->name);
 535        buffer[i] = cpu_to_le16(checksum);
 536        if (e1000_spi_eeprom_program(hw, &buffer[i], i * sizeof(uint16_t),
 537                        sizeof(uint16_t), true)) {
 538                E1000_ERR(hw, "Interrupted!\n");
 539                e1000_release_eeprom(hw);
 540                return 1;
 541        }
 542
 543        e1000_release_eeprom(hw);
 544        return 0;
 545}
 546
 547int do_e1000_spi(cmd_tbl_t *cmdtp, struct e1000_hw *hw,
 548                int argc, char * const argv[])
 549{
 550        if (argc < 1) {
 551                cmd_usage(cmdtp);
 552                return 1;
 553        }
 554
 555        /* Make sure it has an SPI chip */
 556        if (hw->eeprom.type != e1000_eeprom_spi) {
 557                E1000_ERR(hw, "No attached SPI EEPROM found (%d)!\n",
 558                          hw->eeprom.type);
 559                return 1;
 560        }
 561
 562        /* Check the eeprom sub-sub-command arguments */
 563        if (!strcmp(argv[0], "show"))
 564                return do_e1000_spi_show(cmdtp, hw, argc - 1, argv + 1);
 565
 566        if (!strcmp(argv[0], "dump"))
 567                return do_e1000_spi_dump(cmdtp, hw, argc - 1, argv + 1);
 568
 569        if (!strcmp(argv[0], "program"))
 570                return do_e1000_spi_program(cmdtp, hw, argc - 1, argv + 1);
 571
 572        if (!strcmp(argv[0], "checksum"))
 573                return do_e1000_spi_checksum(cmdtp, hw, argc - 1, argv + 1);
 574
 575        cmd_usage(cmdtp);
 576        return 1;
 577}
 578
 579#endif /* not CONFIG_CMD_E1000 */
 580