X-Git-Url: https://git.kernelconcepts.de/?p=karo-tx-uboot.git;a=blobdiff_plain;f=common%2Fcmd_spi.c;h=64c3ffcf423b35fc1b0a65daccb99d490a053c5f;hp=76044221416c9fbd194828b6f4c6bd35fdd461fd;hb=1157a161b0a579c7021a10384b7042a75b0cb229;hpb=fe08fb658008cd4be54758faa5d382a2b3b1f86a diff --git a/common/cmd_spi.c b/common/cmd_spi.c index 7604422141..64c3ffcf42 100644 --- a/common/cmd_spi.c +++ b/common/cmd_spi.c @@ -2,23 +2,7 @@ * (C) Copyright 2002 * Gerald Van Baren, Custom IDEAS, vanbaren@cideas.com * - * See file CREDITS for list of people who contributed to this - * project. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU General Public License as - * published by the Free Software Foundation; either version 2 of - * the License, or (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, - * MA 02111-1307 USA + * SPDX-License-Identifier: GPL-2.0+ */ /* @@ -27,6 +11,8 @@ #include #include +#include +#include #include /*----------------------------------------------------------------------- @@ -37,20 +23,73 @@ # define MAX_SPI_BYTES 32 /* Maximum number of bytes we can handle */ #endif -/* - * External table of chip select functions (see the appropriate board - * support for the actual definition of the table). - */ -extern spi_chipsel_type spi_chipsel[]; -extern int spi_chipsel_cnt; +#ifndef CONFIG_DEFAULT_SPI_BUS +# define CONFIG_DEFAULT_SPI_BUS 0 +#endif +#ifndef CONFIG_DEFAULT_SPI_MODE +# define CONFIG_DEFAULT_SPI_MODE SPI_MODE_0 +#endif /* * Values from last command. */ -static int device; -static int bitlen; -static uchar dout[MAX_SPI_BYTES]; -static uchar din[MAX_SPI_BYTES]; +static unsigned int bus; +static unsigned int cs; +static unsigned int mode; +static int bitlen; +static uchar dout[MAX_SPI_BYTES]; +static uchar din[MAX_SPI_BYTES]; + +static int do_spi_xfer(int bus, int cs) +{ + struct spi_slave *slave; + int ret = 0; + +#ifdef CONFIG_DM_SPI + char name[30], *str; + struct udevice *dev; + + snprintf(name, sizeof(name), "generic_%d:%d", bus, cs); + str = strdup(name); + ret = spi_get_bus_and_cs(bus, cs, 1000000, mode, "spi_generic_drv", + str, &dev, &slave); + if (ret) + return ret; +#else + slave = spi_setup_slave(bus, cs, 1000000, mode); + if (!slave) { + printf("Invalid device %d:%d\n", bus, cs); + return -EINVAL; + } +#endif + + ret = spi_claim_bus(slave); + if (ret) + goto done; + ret = spi_xfer(slave, bitlen, dout, din, + SPI_XFER_BEGIN | SPI_XFER_END); +#ifndef CONFIG_DM_SPI + /* We don't get an error code in this case */ + if (ret) + ret = -EIO; +#endif + if (ret) { + printf("Error %d during SPI transaction\n", ret); + } else { + int j; + + for (j = 0; j < ((bitlen + 7) / 8); j++) + printf("%02X", din[j]); + printf("\n"); + } +done: + spi_release_bus(slave); +#ifndef CONFIG_DM_SPI + spi_free_slave(slave); +#endif + + return ret; +} /* * SPI read/write @@ -63,12 +102,11 @@ static uchar din[MAX_SPI_BYTES]; * The command prints out the hexadecimal string received via SPI. */ -int do_spi (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) +int do_spi (cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { char *cp = 0; uchar tmp; int j; - int rcode = 0; /* * We use the last specified parameters, unless new ones are @@ -77,8 +115,18 @@ int do_spi (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) if ((flag & CMD_FLAG_REPEAT) == 0) { - if (argc >= 2) - device = simple_strtoul(argv[1], NULL, 10); + if (argc >= 2) { + mode = CONFIG_DEFAULT_SPI_MODE; + bus = simple_strtoul(argv[1], &cp, 10); + if (*cp == ':') { + cs = simple_strtoul(cp+1, &cp, 10); + } else { + cs = bus; + bus = CONFIG_DEFAULT_SPI_BUS; + } + if (*cp == '.') + mode = simple_strtoul(cp+1, NULL, 10); + } if (argc >= 3) bitlen = simple_strtoul(argv[2], NULL, 10); if (argc >= 4) { @@ -90,7 +138,7 @@ int do_spi (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) if(tmp > 15) tmp -= ('a' - 'A'); if(tmp > 15) { - printf("Hex conversion error on %c, giving up.\n", *cp); + printf("Hex conversion error on %c\n", *cp); return 1; } if((j % 2) == 0) @@ -101,39 +149,26 @@ int do_spi (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) } } - if ((device < 0) || (device >= spi_chipsel_cnt)) { - printf("Invalid device %d, giving up.\n", device); - return 1; - } if ((bitlen < 0) || (bitlen > (MAX_SPI_BYTES * 8))) { - printf("Invalid bitlen %d, giving up.\n", bitlen); + printf("Invalid bitlen %d\n", bitlen); return 1; } - debug ("spi_chipsel[%d] = %08X\n", - device, (uint)spi_chipsel[device]); - - if(spi_xfer(spi_chipsel[device], bitlen, dout, din) != 0) { - printf("Error with the SPI transaction.\n"); - rcode = 1; - } else { - cp = (char *)din; - for(j = 0; j < ((bitlen + 7) / 8); j++) { - printf("%02X", *cp++); - } - printf("\n"); - } + if (do_spi_xfer(bus, cs)) + return 1; - return rcode; + return 0; } /***************************************************/ U_BOOT_CMD( sspi, 5, 1, do_spi, - "sspi - SPI utility commands\n", - " - Send bits from out the SPI\n" - " - Identifies the chip select of the device\n" + "SPI utility command", + "[:][.] - Send and receive bits\n" + " - Identifies the SPI bus\n" + " - Identifies the chip select\n" + " - Identifies the SPI mode to use\n" " - Number of bits to send (base 10)\n" - " - Hexadecimal string that gets sent\n" + " - Hexadecimal string that gets sent" );