diff --git a/MakeRemote b/MakeRemote index 96388d6..1f96097 100644 --- a/MakeRemote +++ b/MakeRemote @@ -23,7 +23,8 @@ install: $(LIB) sudo install -m 0644 libpigpiod_if.a /usr/local/lib sudo install -m 0755 -d /usr/local/bin sudo install -m 0755 pigs /usr/local/bin - sudo python setup.py install + sudo python2 setup.py install + sudo python3 setup.py install sudo install -m 0755 -d /usr/local/man/man1 sudo install -m 0644 *.1 /usr/local/man/man1 sudo install -m 0755 -d /usr/local/man/man3 diff --git a/command.c b/command.c index 36f8f9e..23f372b 100644 --- a/command.c +++ b/command.c @@ -26,7 +26,7 @@ For more information, please refer to */ /* -This version is for pigpio version 18+ +This version is for pigpio version 21+ */ #include @@ -454,6 +454,9 @@ static errInfo_t errInfo[]= {PI_SER_READ_FAILED , "ser read failed"}, {PI_SER_READ_NO_DATA , "ser read no data available"}, {PI_UNKNOWN_COMMAND , "unknown command"}, + {PI_SPI_XFER_FAILED , "spi xfer/read/write failed"}, + {PI_BAD_POINTER , "bad (NULL) pointer"}, + {PI_NO_AUX_SPI , "need a B+ for auxiliary SPI"}, }; diff --git a/pigpio.3 b/pigpio.3 index 7089390..824c3e2 100644 --- a/pigpio.3 +++ b/pigpio.3 @@ -2370,6 +2370,13 @@ active low chip select. .br +.br +An auxiliary SPI device is available on the B+ and may be +selected by setting the A bit in the flags. The auxiliary +device has 3 chip selects and a selectable word size in bits. + +.br + .br .EX @@ -2377,7 +2384,7 @@ active low chip select. .br spiBaud: >1 .br -spiFlags: 0-0xFF +spiFlags: see below .br .EE @@ -2386,21 +2393,21 @@ spiFlags: 0-0xFF .br Returns a handle (>=0) if OK, otherwise PI_BAD_SPI_CHANNEL, -PI_BAD_SPI_SPEED, PI_BAD_FLAGS, or PI_SPI_OPEN_FAILED. +PI_BAD_SPI_SPEED, PI_BAD_FLAGS, PI_NO_AUX_SPI, or PI_SPI_OPEN_FAILED. .br .br -spiFlags consists of the least significant 8 bits. +spiFlags consists of the least significant 22 bits. .br .br .EX -7 6 5 4 3 2 1 0 +21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 .br -n n n n W P m m + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m .br .EE @@ -2431,19 +2438,51 @@ Mode POL PHA .br .br -P is 0 for active low chip select (normal) and 1 for active high. +px is 0 if CEx is active low (default) and 1 for active high. .br .br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. +ux is 0 if the CEx gpio is reserved for SPI (default) and 1 otherwise. + +.br + +.br +A is 0 for the standard SPI device, 1 for the auxiliary SPI. The +auxiliary device is only present on the B+. + +.br + +.br +W is 0 if the device is not 3-wire, 1 if the device is 3-wire. Standard +SPI device only. .br .br nnnn defines the number of bytes (0-15) to write before switching the MOSI line to MISO to read data. This field is ignored -if W is not set. +if W is not set. Standard SPI device only. + +.br + +.br +T is 1 if the least significant bit is transmitted on MOSI first, the +default (0) shifts the most significant bit out first. Auxiliary SPI +device only. + +.br + +.br +R is 1 if the least significant bit is received on MISO first, the +default (0) receives the most significant bit first. Auxiliary SPI +device only. + +.br + +.br +bbbbbb defines the word size in bits (0-32). The default (0) +sets 8 bits per word. Auxiliary SPI device only. .br @@ -3611,7 +3650,7 @@ Returns the actual length of the delay in microseconds. .br .br -Delays of 50 microseconds or less use busy waits. +Delays of 100 microseconds or less use busy waits. .IP "\fBuint32_t gpioTick(void)\fP" .IP "" 4 @@ -4728,6 +4767,26 @@ typedef struct .br +.IP "\fBgpioSample_t\fP" 0 + +.EX +typedef struct +.br +{ +.br + uint32_t tick; +.br + uint32_t level; +.br +} gpioSample_t; +.br + +.EE + +.br + +.br + .IP "\fBgpioSignalFunc_t\fP" 0 .EX @@ -5195,7 +5254,7 @@ PI_PUD_UP 2 .br .br -An array of pulsed to be added to a waveform. +An array of pulses to be added to a waveform. .br @@ -5519,64 +5578,7 @@ A SPI channel, 0 or 1. .br .br -spiFlags consists of the least significant 8 bits. - -.br - -.br - -.EX -7 6 5 4 3 2 1 0 -.br -n n n n W P m m -.br - -.EE - -.br - -.br -mm defines the SPI mode. - -.br - -.br - -.EX -Mode POL PHA -.br - 0 0 0 -.br - 1 0 1 -.br - 2 1 0 -.br - 3 1 1 -.br - -.EE - -.br - -.br -P is 0 for active low chip select (normal) and 1 for active high. - -.br - -.br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - -.br - -.br -nnnn defines the number of bytes (0-15) to write before switching -the MOSI line to MISO to read data. This field is ignored -if W is not set. - -.br - -.br -The other bits in flags should be set to zero. +See \fBspiOpen\fP. .br @@ -6174,6 +6176,8 @@ A 16-bit word value. .br #define PI_BAD_POINTER -90 // bad (NULL) pointer .br +#define PI_NO_AUX_SPI -91 // need a B+ for auxiliary SPI +.br .br diff --git a/pigpio.c b/pigpio.c index 8ddab17..ec1f3d6 100644 --- a/pigpio.c +++ b/pigpio.c @@ -25,7 +25,7 @@ OTHER DEALINGS IN THE SOFTWARE. For more information, please refer to */ -/* pigpio version 20 */ +/* pigpio version 21 */ #include #include @@ -286,6 +286,7 @@ bit 0 READ_LAST_NOT_SET_ERROR #define DMA_BUS_ADR 0x40000000 +#define AUX_BASE 0x20215000 #define CLK_BASE 0x20101000 #define DMA_BASE 0x20007000 #define DMA15_BASE 0x20E05000 @@ -294,9 +295,8 @@ bit 0 READ_LAST_NOT_SET_ERROR #define PWM_BASE 0x2020C000 #define SPI_BASE 0x20204000 #define SYST_BASE 0x20003000 -#define UART0_BASE 0x20201000 -#define UART1_BASE 0x20215000 +#define AUX_LEN 0xD8 #define CLK_LEN 0xA8 #define DMA_LEN 0x1000 /* allow access to all channels */ #define GPIO_LEN 0xB4 @@ -491,23 +491,21 @@ bit 0 READ_LAST_NOT_SET_ERROR #define SPI_LTOH 4 #define SPI_DC 5 -#define SPI_CS_LEN_LONG (1<<25) -#define SPI_CS_DMA_LEN (1<<24) -#define SPI_CS_CSPOL2 (1<<23) -#define SPI_CS_CSPOL1 (1<<22) -#define SPI_CS_CSPOL0 (1<<21) -#define SPI_CS_RXF (1<<20) -#define SPI_CS_RXR (1<<19) -#define SPI_CS_TXD (1<<18) -#define SPI_CS_RXD (1<<17) -#define SPI_CS_DONE (1<<16) -#define SPI_CS_LEN (1<<13) -#define SPI_CS_REN (1<<12) -#define SPI_CS_ADCS (1<<11) -#define SPI_CS_INTR (1<<10) -#define SPI_CS_INTD (1<<9) -#define SPI_CS_DMAEN (1<<8) -#define SPI_CS_TA (1<<7) +#define SPI_CS_LEN_LONG (1<<25) +#define SPI_CS_DMA_LEN (1<<24) +#define SPI_CS_CSPOLS(x) ((x)<<21) +#define SPI_CS_RXF (1<<20) +#define SPI_CS_RXR (1<<19) +#define SPI_CS_TXD (1<<18) +#define SPI_CS_RXD (1<<17) +#define SPI_CS_DONE (1<<16) +#define SPI_CS_LEN (1<<13) +#define SPI_CS_REN (1<<12) +#define SPI_CS_ADCS (1<<11) +#define SPI_CS_INTR (1<<10) +#define SPI_CS_INTD (1<<9) +#define SPI_CS_DMAEN (1<<8) +#define SPI_CS_TA (1<<7) #define SPI_CS_CSPOL(x) ((x)<<6) #define SPI_CS_CLEAR(x) ((x)<<4) #define SPI_CS_MODE(x) ((x)<<2) @@ -527,7 +525,7 @@ bit 0 READ_LAST_NOT_SET_ERROR #define SPI_CS1 1 #define SPI_CS2 2 -/* SPI gpios. */ +/* standard SPI gpios (ALT0) */ #define PI_SPI_CE0 8 #define PI_SPI_CE1 7 @@ -535,6 +533,80 @@ bit 0 READ_LAST_NOT_SET_ERROR #define PI_SPI_MISO 9 #define PI_SPI_MOSI 10 +/* auxiliary SPI gpios (ALT4) */ + +#define PI_ASPI_CE0 18 +#define PI_ASPI_CE1 17 +#define PI_ASPI_CE2 16 +#define PI_ASPI_MISO 19 +#define PI_ASPI_MOSI 20 +#define PI_ASPI_SCLK 21 + +/* AUX */ + +#define AUX_IRQ 0 +#define AUX_ENABLES 1 + +#define AUX_MU_IO_REG 16 +#define AUX_MU_IER_REG 17 +#define AUX_MU_IIR_REG 18 +#define AUX_MU_LCR_REG 19 +#define AUX_MU_MCR_REG 20 +#define AUX_MU_LSR_REG 21 +#define AUX_MU_MSR_REG 22 +#define AUX_MU_SCRATCH 23 +#define AUX_MU_CNTL_REG 24 +#define AUX_MU_STAT_REG 25 +#define AUX_MU_BAUD_REG 26 + +#define AUX_SPI0_CNTL0_REG 32 +#define AUX_SPI0_CNTL1_REG 33 +#define AUX_SPI0_STAT_REG 34 +#define AUX_SPI0_PEEK_REG 35 + +#define AUX_SPI0_IO_REG 40 +#define AUX_SPI0_TX_HOLD 44 + +#define AUX_SPI1_CNTL0_REG 48 +#define AUX_SPI1_CNTL1_REG 49 +#define AUX_SPI1_STAT_REG 50 +#define AUX_SPI1_PEEK_REG 51 + +#define AUX_SPI1_IO_REG 56 +#define AUX_SPI1_TX_HOLD 60 + +#define AUXENB_SPI2 (1<<2) +#define AUXENB_SPI1 (1<<1) +#define AUXENB_UART (1<<0) + +#define AUXSPI_CNTL0_SPEED(x) ((x)<<20) +#define AUXSPI_CNTL0_CS(x) ((x)<<17) +#define AUXSPI_CNTL0_POSTINP (1<<16) +#define AUXSPI_CNTL0_VAR_CS (1<<15) +#define AUXSPI_CNTL0_VAR_WIDTH (1<<14) +#define AUXSPI_CNTL0_DOUT_HOLD(x) ((x)<<12) +#define AUXSPI_CNTL0_ENABLE (1<<11) +#define AUXSPI_CNTL0_IN_RISING(x) ((x)<<10) +#define AUXSPI_CNTL0_CLR_FIFOS (1<<9) +#define AUXSPI_CNTL0_OUT_RISING(x) ((x)<<8) +#define AUXSPI_CNTL0_INVERT_CLK(x) ((x)<<7) +#define AUXSPI_CNTL0_MSB_FIRST(x) ((x)<<6) +#define AUXSPI_CNTL0_SHIFT_LEN(x) ((x)<<0) + +#define AUXSPI_CNTL1_CS_HIGH(x) ((x)<<8) +#define AUXSPI_CNTL1_TX_IRQ (1<<7) +#define AUXSPI_CNTL1_DONE_IRQ (1<<6) +#define AUXSPI_CNTL1_MSB_FIRST(x)((x)<<1) +#define AUXSPI_CNTL1_KEEP_INPUT (1<<0) + +#define AUXSPI_STAT_TX_FIFO(x) ((x)<<28) +#define AUXSPI_STAT_RX_FIFO(x) ((x)<<20) +#define AUXSPI_STAT_TX_FULL (1<<10) +#define AUXSPI_STAT_TX_EMPTY (1<<9) +#define AUXSPI_STAT_RX_EMPTY (1<<7) +#define AUXSPI_STAT_BUSY (1<<6) +#define AUXSPI_STAT_BITS(x) ((x)<<0) + /* --------------------------------------------------------------- */ #define NORMAL_DMA (DMA_NO_WIDE_BURSTS | DMA_WAIT_RESP) @@ -781,6 +853,19 @@ typedef struct uint32_t flags; } spiInfo_t; +#define PI_SPI_FLAGS_CHANNEL(x) ((x&7)<<29) + +#define PI_SPI_FLAGS_GET_CHANNEL(x) (((x)>>29)&7) +#define PI_SPI_FLAGS_GET_BITLEN(x) (((x)>>16)&63) +#define PI_SPI_FLAGS_GET_RX_LSB(x) (((x)>>15)&1) +#define PI_SPI_FLAGS_GET_TX_LSB(x) (((x)>>14)&1) +#define PI_SPI_FLAGS_GET_3WREN(x) (((x)>>10)&15) +#define PI_SPI_FLAGS_GET_3WIRE(x) (((x)>>9)&1) +#define PI_SPI_FLAGS_GET_AUX_SPI(x) (((x)>>8)&1) +#define PI_SPI_FLAGS_GET_RESVD(x) (((x)>>5)&7) +#define PI_SPI_FLAGS_GET_CSPOLS(x) (((x)>>2)&7) +#define PI_SPI_FLAGS_GET_MODE(x) ((x)&3) + typedef struct { uint32_t startTick; @@ -982,16 +1067,17 @@ static dmaIPage_t * * dmaIPhys = MAP_FAILED; static dmaOPage_t * * dmaOVirt = MAP_FAILED; static dmaOPage_t * * dmaOPhys = MAP_FAILED; -static volatile uint32_t * clkReg = MAP_FAILED; -static volatile uint32_t * dmaReg = MAP_FAILED; -static volatile uint32_t * gpioReg = MAP_FAILED; -static volatile uint32_t * pcmReg = MAP_FAILED; -static volatile uint32_t * pwmReg = MAP_FAILED; -static volatile uint32_t * spiReg = MAP_FAILED; -static volatile uint32_t * systReg = MAP_FAILED; +static volatile uint32_t * auxReg = MAP_FAILED; +static volatile uint32_t * clkReg = MAP_FAILED; +static volatile uint32_t * dmaReg = MAP_FAILED; +static volatile uint32_t * gpioReg = MAP_FAILED; +static volatile uint32_t * pcmReg = MAP_FAILED; +static volatile uint32_t * pwmReg = MAP_FAILED; +static volatile uint32_t * spiReg = MAP_FAILED; +static volatile uint32_t * systReg = MAP_FAILED; -static volatile uint32_t * dmaIn = MAP_FAILED; -static volatile uint32_t * dmaOut = MAP_FAILED; +static volatile uint32_t * dmaIn = MAP_FAILED; +static volatile uint32_t * dmaOut = MAP_FAILED; /* constant data */ @@ -2852,6 +2938,10 @@ int i2cClose(unsigned handle) /* ======================================================================= */ +/*SPI */ + +static uint32_t spi_dummy; /* only used to prevent warning */ + static unsigned old_mode_ce0; static unsigned old_mode_ce1; static unsigned old_mode_sclk; @@ -2861,52 +2951,223 @@ static unsigned old_mode_mosi; static uint32_t old_spi_cs; static uint32_t old_spi_clk; -static uint32_t spi_dummy; /* only used to prevent warning */ +static unsigned old_mode_ace0; +static unsigned old_mode_ace1; +static unsigned old_mode_ace2; +static unsigned old_mode_asclk; +static unsigned old_mode_amiso; +static unsigned old_mode_amosi; -static void spiInit(void) +static uint32_t old_spi_cntl0; +static uint32_t old_spi_cntl1; + +static void spiInit(uint32_t flags) { - old_mode_ce0 = gpioGetMode(PI_SPI_CE0); - old_mode_ce1 = gpioGetMode(PI_SPI_CE1); - old_mode_sclk = gpioGetMode(PI_SPI_SCLK); - old_mode_miso = gpioGetMode(PI_SPI_MISO); - old_mode_mosi = gpioGetMode(PI_SPI_MOSI); + int resvd; - gpioSetMode(PI_SPI_CE0, PI_ALT0); - gpioSetMode(PI_SPI_CE1, PI_ALT0); - gpioSetMode(PI_SPI_SCLK, PI_ALT0); - gpioSetMode(PI_SPI_MISO, PI_ALT0); - gpioSetMode(PI_SPI_MOSI, PI_ALT0); + resvd = PI_SPI_FLAGS_GET_RESVD(flags); - old_spi_cs = spiReg[SPI_CS]; - old_spi_clk = spiReg[SPI_CLK]; + if (PI_SPI_FLAGS_GET_AUX_SPI(flags)) + { + /* enable module and access to registers */ + + auxReg[AUX_ENABLES] |= AUXENB_SPI1; + + /* save original state */ + + old_mode_ace0 = gpioGetMode(PI_ASPI_CE0); + old_mode_ace1 = gpioGetMode(PI_ASPI_CE1); + old_mode_ace2 = gpioGetMode(PI_ASPI_CE2); + old_mode_asclk = gpioGetMode(PI_ASPI_SCLK); + old_mode_amiso = gpioGetMode(PI_ASPI_MISO); + old_mode_amosi = gpioGetMode(PI_ASPI_MOSI); + + old_spi_cntl0 = auxReg[AUX_SPI0_CNTL0_REG]; + old_spi_cntl1 = auxReg[AUX_SPI0_CNTL1_REG]; + + /* set gpios to SPI mode */ + + if (!(resvd&1)) gpioSetMode(PI_ASPI_CE0, PI_ALT4); + if (!(resvd&2)) gpioSetMode(PI_ASPI_CE1, PI_ALT4); + if (!(resvd&4)) gpioSetMode(PI_ASPI_CE2, PI_ALT4); + + gpioSetMode(PI_ASPI_SCLK, PI_ALT4); + gpioSetMode(PI_ASPI_MISO, PI_ALT4); + gpioSetMode(PI_ASPI_MOSI, PI_ALT4); + } + else + { + /* save original state */ + + old_mode_ce0 = gpioGetMode(PI_SPI_CE0); + old_mode_ce1 = gpioGetMode(PI_SPI_CE1); + old_mode_sclk = gpioGetMode(PI_SPI_SCLK); + old_mode_miso = gpioGetMode(PI_SPI_MISO); + old_mode_mosi = gpioGetMode(PI_SPI_MOSI); + + old_spi_cs = spiReg[SPI_CS]; + old_spi_clk = spiReg[SPI_CLK]; + + /* set gpios to SPI mode */ + + if (!(resvd&1)) gpioSetMode(PI_SPI_CE0, PI_ALT0); + if (!(resvd&2)) gpioSetMode(PI_SPI_CE1, PI_ALT0); + + gpioSetMode(PI_SPI_SCLK, PI_ALT0); + gpioSetMode(PI_SPI_MISO, PI_ALT0); + gpioSetMode(PI_SPI_MOSI, PI_ALT0); + } } -static void spiTerm(void) -{ - gpioSetMode(PI_SPI_CE0, old_mode_ce0); - gpioSetMode(PI_SPI_CE1, old_mode_ce1); - gpioSetMode(PI_SPI_SCLK, old_mode_sclk); - gpioSetMode(PI_SPI_MISO, old_mode_miso); - gpioSetMode(PI_SPI_MOSI, old_mode_mosi); +void spiTerm(uint32_t flags) +{ + int resvd; - spiReg[SPI_CS] = old_spi_cs; - spiReg[SPI_CLK] = old_spi_clk; + resvd = PI_SPI_FLAGS_GET_RESVD(flags); + + if (PI_SPI_FLAGS_GET_AUX_SPI(flags)) + { + /* restore original state */ + + if (!(resvd&1)) gpioSetMode(PI_ASPI_CE0, old_mode_ace0); + if (!(resvd&2)) gpioSetMode(PI_ASPI_CE1, old_mode_ace1); + if (!(resvd&4)) gpioSetMode(PI_ASPI_CE2, old_mode_ace2); + + gpioSetMode(PI_ASPI_SCLK, old_mode_asclk); + gpioSetMode(PI_ASPI_MISO, old_mode_amiso); + gpioSetMode(PI_ASPI_MOSI, old_mode_amosi); + + auxReg[AUX_SPI0_CNTL0_REG] = old_spi_cntl0; + auxReg[AUX_SPI0_CNTL1_REG] = old_spi_cntl1; + } + else + { + /* restore original state */ + + if (!(resvd&1)) gpioSetMode(PI_SPI_CE0, old_mode_ce0); + if (!(resvd&2)) gpioSetMode(PI_SPI_CE1, old_mode_ce1); + + gpioSetMode(PI_SPI_SCLK, old_mode_sclk); + gpioSetMode(PI_SPI_MISO, old_mode_miso); + gpioSetMode(PI_SPI_MOSI, old_mode_mosi); + + spiReg[SPI_CS] = old_spi_cs; + spiReg[SPI_CLK] = old_spi_clk; + } } -#define PI_SPI_FLAGS_CHAN(x) ((x)<<30) +uint32_t _spiTXBits(char *buf, int pos, int bitlen, int msbf) +{ + uint32_t bits=0; -/* -3 3 2 2 2 2 2 2 2 2 2 2 1 1 1 1 1 1 1 1 1 1 -1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 -C C - - - - - - - - - - - - - - - - - - - - - - N N N N 3 P M M + if (buf) + { + if (bitlen <= 8) bits = *((( uint8_t*)buf)+pos); + else if (bitlen <= 16) bits = *(((uint16_t*)buf)+pos); + else bits = *(((uint32_t*)buf)+pos); -CC channel -NNNN switch to 3-wire after NNNN bytes -3 3-wire part -P CS polarity -MM mode -*/ -static void spiGo( + if (msbf) bits <<= (32-bitlen); + } + + return bits; +} + +void _spiRXBits(char *buf, int pos, int bitlen, int msbf, uint32_t bits) +{ + if (buf) + { + if (!msbf) bits >>= (32-bitlen); + + if (bitlen <= 8) *((( uint8_t*)buf)+pos) = bits; + else if (bitlen <= 16) *(((uint16_t*)buf)+pos) = bits; + else *(((uint32_t*)buf)+pos) = bits; + } +} + + +void spiGoA( + unsigned speed, /* bits per second */ + uint32_t flags, /* flags */ + char *txBuf, /* tx buffer */ + char *rxBuf, /* rx buffer */ + unsigned count) /* number of bytes */ +{ + char bit_cs; + char bit_ir[4] = {1, 0, 1, 0}; + char bit_or[4] = {0, 1, 0, 1}; + char bit_ic[4] = {0, 0, 1, 1}; + + int mode, bitlen, txmsbf, rxmsbf, channel; + unsigned txCnt=0; + unsigned rxCnt=0; + uint32_t spiDefaults; + uint32_t statusReg; + int txFull, rxEmpty; + + channel = PI_SPI_FLAGS_GET_CHANNEL(flags); + mode = PI_SPI_FLAGS_GET_MODE (flags); + bitlen = PI_SPI_FLAGS_GET_BITLEN (flags); + if (!bitlen) bitlen = 8; + txmsbf = !PI_SPI_FLAGS_GET_TX_LSB (flags); + rxmsbf = !PI_SPI_FLAGS_GET_RX_LSB (flags); + + bit_cs = ~PI_SPI_FLAGS_GET_CSPOLS(flags); + bit_cs = (1<>28)&15) > 2); + + if (rxCnt < count) + { + if (!rxEmpty) + { + _spiRXBits(rxBuf, rxCnt++, bitlen, rxmsbf, auxReg[AUX_SPI0_IO_REG]); + } + } + + if (txCnt < count) + { + if (!txFull) + { + if (txCnt != (count-1)) + { + auxReg[AUX_SPI0_TX_HOLD] = + _spiTXBits(txBuf, txCnt++, bitlen, txmsbf); + } + else + { + auxReg[AUX_SPI0_IO_REG] = + _spiTXBits(txBuf, txCnt++, bitlen, txmsbf); + } + } + } + } + + while ((auxReg[AUX_SPI0_STAT_REG] & AUXSPI_STAT_BUSY)) ; + + auxReg[AUX_SPI0_CNTL0_REG] = spiDefaults; /* stop */ +} + +static void spiGoS( unsigned speed, uint32_t flags, char *txBuf, @@ -2917,17 +3178,20 @@ static void spiGo( unsigned rxCnt=0; unsigned cnt, cnt4w, cnt3w; uint32_t spiDefaults; - unsigned mode, channel, cspol, flag3w, ren3w; + unsigned mode, channel, cspol, cspols, flag3w, ren3w; + uint32_t status; - mode = flags & 3; - cspol = (flags >> 2) & 1; - flag3w = (flags >> 3) & 1; - ren3w = (flags >> 4) & 15; - channel = (flags >> 30) & 3; + channel = PI_SPI_FLAGS_GET_CHANNEL(flags); + mode = PI_SPI_FLAGS_GET_MODE (flags); + cspols = PI_SPI_FLAGS_GET_CSPOLS(flags); + cspol = (cspols>>channel) & 1; + flag3w = PI_SPI_FLAGS_GET_3WIRE(flags); + ren3w = PI_SPI_FLAGS_GET_3WREN(flags); - spiDefaults = SPI_CS_MODE(mode) | - SPI_CS_CS(channel) | - SPI_CS_CSPOL(cspol) | + spiDefaults = SPI_CS_MODE(mode) | + SPI_CS_CSPOLS(cspols) | + SPI_CS_CS(channel) | + SPI_CS_CSPOL(cspol) | SPI_CS_CLEAR(3); if (flag3w) @@ -2957,19 +3221,21 @@ static void spiGo( while((txCnt < cnt) || (rxCnt < cnt)) { - while((txCnt < cnt) && ((spiReg[SPI_CS] & SPI_CS_TXD))) - { - if (txBuf) spiReg[SPI_FIFO] = txBuf[txCnt]; - else spiReg[SPI_FIFO] = 0; - txCnt++; - } + status = spiReg[SPI_CS]; - while((rxCnt < cnt) && ((spiReg[SPI_CS] & SPI_CS_RXD))) + while((rxCnt < cnt) && ((status & SPI_CS_RXD))) { if (rxBuf) rxBuf[rxCnt] = spiReg[SPI_FIFO]; else spi_dummy = spiReg[SPI_FIFO]; rxCnt++; } + + while((txCnt < cnt) && ((status & SPI_CS_TXD))) + { + if (txBuf) spiReg[SPI_FIFO] = txBuf[txCnt]; + else spiReg[SPI_FIFO] = 0; + txCnt++; + } } while (!(spiReg[SPI_CS] & SPI_CS_DONE)) ; @@ -2978,23 +3244,25 @@ static void spiGo( cnt += cnt3w; + spiReg[SPI_CS] |= SPI_CS_REN; + while((txCnt < cnt) || (rxCnt < cnt)) { - spiReg[SPI_CS] |= SPI_CS_REN; + status = spiReg[SPI_CS]; - while((txCnt < cnt) && ((spiReg[SPI_CS] & SPI_CS_TXD))) - { - if (txBuf) spiReg[SPI_FIFO] = txBuf[txCnt]; - else spiReg[SPI_FIFO] = 0; - txCnt++; - } - - while((rxCnt < cnt) && ((spiReg[SPI_CS] & SPI_CS_RXD))) + while((rxCnt < cnt) && ((status & SPI_CS_RXD))) { if (rxBuf) rxBuf[rxCnt] = spiReg[SPI_FIFO]; else spi_dummy = spiReg[SPI_FIFO]; rxCnt++; } + + while((txCnt < cnt) && ((status & SPI_CS_TXD))) + { + if (txBuf) spiReg[SPI_FIFO] = txBuf[txCnt]; + else spiReg[SPI_FIFO] = 0; + txCnt++; + } } while (!(spiReg[SPI_CS] & SPI_CS_DONE)) ; @@ -3002,13 +3270,30 @@ static void spiGo( spiReg[SPI_CS] = spiDefaults; /* stop */ } -static int spiAnyOpen(void) +static void spiGo( + unsigned speed, + uint32_t flags, + char *txBuf, + char *rxBuf, + unsigned count) { - int i; + if (PI_SPI_FLAGS_GET_AUX_SPI(flags)) + spiGoA(speed, flags, txBuf, rxBuf, count); + else + spiGoS(speed, flags, txBuf, rxBuf, count); +} + +static int spiAnyOpen(uint32_t flags) +{ + int i, aux; + + aux = PI_SPI_FLAGS_GET_AUX_SPI(flags); for (i=0; i= PI_NUM_SPI_CHANNEL) + if (PI_SPI_FLAGS_GET_AUX_SPI(spiFlags)) + { + if (gpioHardwareRevision() < 16) + SOFT_ERROR(PI_NO_AUX_SPI, "no auxiliary SPI, need a B+"); + + i = PI_NUM_AUX_SPI_CHANNEL; + } + else + i = PI_NUM_STD_SPI_CHANNEL; + + if (spiChan >= i) SOFT_ERROR(PI_BAD_SPI_CHANNEL, "bad spiChan (%d)", spiChan); - if (!spiBaud) + if ((spiBaud < MIN_SPI_SPEED) || (spiBaud > MAX_SPI_SPEED)) SOFT_ERROR(PI_BAD_SPI_SPEED, "bad spiBaud (%d)", spiBaud); - if (spiFlags > 256) + if (spiFlags > (1<<22)) SOFT_ERROR(PI_BAD_FLAGS, "bad spiFlags (0x%X)", spiFlags); - if (!spiAnyOpen()) spiInit(); /* initialise on first open */ + if (!spiAnyOpen(spiFlags)) spiInit(spiFlags); /* initialise on first open */ slot = -1; @@ -3049,7 +3344,7 @@ int spiOpen(unsigned spiChan, unsigned spiBaud, unsigned spiFlags) SOFT_ERROR(PI_NO_HANDLE, "no SPI handles"); spiInfo[slot].speed = spiBaud; - spiInfo[slot].flags = spiFlags | PI_SPI_FLAGS_CHAN(spiChan); + spiInfo[slot].flags = spiFlags | PI_SPI_FLAGS_CHANNEL(spiChan); return slot; } @@ -3068,7 +3363,8 @@ int spiClose(unsigned handle) spiInfo[handle].state = PI_I2C_CLOSED; - if (!spiAnyOpen()) spiTerm(); /* terminate on last close */ + if (!spiAnyOpen(spiInfo[handle].flags)) + spiTerm(spiInfo[handle].flags); /* terminate on last close */ return 0; } @@ -4979,6 +5275,11 @@ static int initPeripherals(void) if (pcmReg == MAP_FAILED) SOFT_ERROR(PI_INIT_FAILED, "mmap pcm failed (%m)"); + auxReg = initMapMem(fdMem, AUX_BASE, AUX_LEN); + + if (auxReg == MAP_FAILED) + SOFT_ERROR(PI_INIT_FAILED, "mmap aux failed (%m)"); + return 0; } @@ -5120,9 +5421,10 @@ static int initDMAcbs(void) DBG(DBG_STARTUP, "dmaBloc=%08X dmaIn=%08X", (uint32_t)dmaBloc, (uint32_t)dmaIn); - DBG(DBG_STARTUP, "gpioReg=%08X pwmReg=%08X pcmReg=%08X clkReg=%08X", + DBG(DBG_STARTUP, + "gpioReg=%08X pwmReg=%08X pcmReg=%08X clkReg=%08X auxReg=%08X", (uint32_t)gpioReg, (uint32_t)pwmReg, - (uint32_t)pcmReg, (uint32_t)clkReg); + (uint32_t)pcmReg, (uint32_t)clkReg, (uint32_t)auxReg); for (i=0; i #include #include -#define PIGPIO_VERSION 20 +#define PIGPIO_VERSION 21 /*TEXT @@ -483,20 +483,30 @@ typedef void *(gpioThreadFunc_t) (void *); /* I2C, SPI, SER */ +#define MIN_SPI_SPEED 32000 +#define MAX_SPI_SPEED 125000000 + #define PI_I2C_SLOTS 32 -#define PI_SPI_SLOTS 8 +#define PI_SPI_SLOTS 16 #define PI_SER_SLOTS 8 #define PI_NUM_I2C_BUS 2 -#define PI_NUM_SPI_CHANNEL 2 + +#define PI_NUM_AUX_SPI_CHANNEL 3 +#define PI_NUM_STD_SPI_CHANNEL 2 #define PI_MAX_I2C_DEVICE_COUNT 8192 #define PI_MAX_SPI_DEVICE_COUNT 8192 -#define PI_SPI_FLAGS_3WREN(x) ((x)<<4) -#define PI_SPI_FLAGS_3WIRE(x) ((x)<<3) -#define PI_SPI_FLAGS_CSPOL(x) ((x)<<2) -#define PI_SPI_FLAGS_MODE(x) ((x)<<0) +#define PI_SPI_FLAGS_BITLEN(x) ((x&63)<<16) +#define PI_SPI_FLAGS_RX_LSB(x) ((x&1)<<15) +#define PI_SPI_FLAGS_TX_LSB(x) ((x&1)<<14) +#define PI_SPI_FLAGS_3WREN(x) ((x&15)<<10) +#define PI_SPI_FLAGS_3WIRE(x) ((x&1)<<9) +#define PI_SPI_FLAGS_AUX_SPI(x) ((x&1)<<8) +#define PI_SPI_FLAGS_RESVD(x) ((x&7)<<5) +#define PI_SPI_FLAGS_CSPOLS(x) ((x&7)<<2) +#define PI_SPI_FLAGS_MODE(x) ((x&3)) /* Longest busy delay */ @@ -1886,20 +1896,24 @@ Data will be transferred at baud bits per second. The flags may be used to modify the default behaviour of 4-wire operation, mode 0, active low chip select. +An auxiliary SPI device is available on the B+ and may be +selected by setting the A bit in the flags. The auxiliary +device has 3 chip selects and a selectable word size in bits. + . . spiChan: 0-1 spiBaud: >1 -spiFlags: 0-0xFF +spiFlags: see below . . Returns a handle (>=0) if OK, otherwise PI_BAD_SPI_CHANNEL, -PI_BAD_SPI_SPEED, PI_BAD_FLAGS, or PI_SPI_OPEN_FAILED. +PI_BAD_SPI_SPEED, PI_BAD_FLAGS, PI_NO_AUX_SPI, or PI_SPI_OPEN_FAILED. -spiFlags consists of the least significant 8 bits. +spiFlags consists of the least significant 22 bits. . . -7 6 5 4 3 2 1 0 -n n n n W P m m +21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m . . mm defines the SPI mode. @@ -1912,13 +1926,30 @@ Mode POL PHA 3 1 1 . . -P is 0 for active low chip select (normal) and 1 for active high. +px is 0 if CEx is active low (default) and 1 for active high. -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. +ux is 0 if the CEx gpio is reserved for SPI (default) and 1 otherwise. + +A is 0 for the standard SPI device, 1 for the auxiliary SPI. The +auxiliary device is only present on the B+. + +W is 0 if the device is not 3-wire, 1 if the device is 3-wire. Standard +SPI device only. nnnn defines the number of bytes (0-15) to write before switching the MOSI line to MISO to read data. This field is ignored -if W is not set. +if W is not set. Standard SPI device only. + +T is 1 if the least significant bit is transmitted on MOSI first, the +default (0) shifts the most significant bit out first. Auxiliary SPI +device only. + +R is 1 if the least significant bit is received on MISO first, the +default (0) receives the most significant bit first. Auxiliary SPI +device only. + +bbbbbb defines the word size in bits (0-32). The default (0) +sets 8 bits per word. Auxiliary SPI device only. The other bits in flags should be set to zero. D*/ @@ -2614,7 +2645,7 @@ micros: the number of microseconds to sleep Returns the actual length of the delay in microseconds. -Delays of 50 microseconds or less use busy waits. +Delays of 100 microseconds or less use busy waits. D*/ @@ -3230,6 +3261,15 @@ typedef struct } gpioPulse_t; . . +gpioSample_t:: +. . +typedef struct +{ + uint32_t tick; + uint32_t level; +} gpioSample_t; +. . + gpioSignalFunc_t:: . . typedef void (*gpioSignalFunc_t) (int signum); @@ -3415,7 +3455,7 @@ pulseLen:: *pulses:: -An array of pulsed to be added to a waveform. +An array of pulses to be added to a waveform. pulsewidth::0, 500-2500 . . @@ -3546,32 +3586,7 @@ A SPI channel, 0 or 1. spiFlags:: -spiFlags consists of the least significant 8 bits. - -. . -7 6 5 4 3 2 1 0 -n n n n W P m m -. . - -mm defines the SPI mode. - -. . -Mode POL PHA - 0 0 0 - 1 0 1 - 2 1 0 - 3 1 1 -. . - -P is 0 for active low chip select (normal) and 1 for active high. - -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - -nnnn defines the number of bytes (0-15) to write before switching -the MOSI line to MISO to read data. This field is ignored -if W is not set. - -The other bits in flags should be set to zero. +See [*spiOpen*]. spiSS:: @@ -3903,6 +3918,7 @@ after this command is issued. #define PI_UNKNOWN_COMMAND -88 // unknown command #define PI_SPI_XFER_FAILED -89 // spi xfer/read/write failed #define PI_BAD_POINTER -90 // bad (NULL) pointer +#define PI_NO_AUX_SPI -91 // need a B+ for auxiliary SPI /*DEF_E*/ diff --git a/pigpio.py b/pigpio.py index ab17673..4fb947e 100644 --- a/pigpio.py +++ b/pigpio.py @@ -246,7 +246,7 @@ import os import atexit import codecs -VERSION = "1.10" +VERSION = "1.11" exceptions = True @@ -485,6 +485,8 @@ PI_SER_READ_FAILED =-86 PI_SER_READ_NO_DATA =-87 PI_UNKNOWN_COMMAND =-88 PI_SPI_XFER_FAILED =-89 +_PI_BAD_POINTER =-90 +PI_NO_AUX_SPI =-91 # pigpio error text @@ -576,6 +578,8 @@ _errors=[ [PI_SER_READ_NO_DATA , "ser read no data available"], [PI_UNKNOWN_COMMAND , "unknown command"], [PI_SPI_XFER_FAILED , "SPI xfer/read/write failed"], + [_PI_BAD_POINTER , "bad (NULL) pointer"], + [PI_NO_AUX_SPI , "need a B+ for auxiliary SPI"], ] class _socklock: @@ -1745,7 +1749,7 @@ class pi(): Normally you would only use the [*i2c_**] functions if you are or will be connecting to the Pi over a network. If you will always run on the local Pi use the standard smbus - modules instead. + module instead. ... h = pi.i2c_open(1, 0x53) # open device at address 0x53 on bus 1 @@ -2100,7 +2104,7 @@ class pi(): # Don't raise exception. Must release lock. bytes = u2i(_pigpio_command_ext( - self.sl, _PI_CMD_I2CPK, handle, reg, len(data), [data]), False) + self.sl, _PI_CMD_I2CPK, handle, reg, len(data), [data], False)) if bytes > 0: data = self._rxbuf(bytes) else: @@ -2169,7 +2173,7 @@ class pi(): # Don't raise exception. Must release lock. bytes = u2i(_pigpio_command_ext( - self.sl, _PI_CMD_I2CRI, handle, reg, 4, extents), False) + self.sl, _PI_CMD_I2CRI, handle, reg, 4, extents, False)) if bytes > 0: data = self._rxbuf(bytes) else: @@ -2184,6 +2188,11 @@ class pi(): modify the default behaviour of 4-wire operation, mode 0, active low chip select. + An auxiliary SPI device is available on the B+ and may be + selected by setting the A bit in the flags. The auxiliary + device has 3 chip selects and a selectable word size in bits. + + spi_channel:= 0 or 1, the SPI channel. spi_baud:= >0, the transmission rate in bits per second. spi_flags:= see below. @@ -2191,32 +2200,50 @@ class pi(): Normally you would only use the [*spi_**] functions if you are or will be connecting to the Pi over a network. If you will always run on the local Pi use the standard SPI - modules instead. + module instead. - spiFlags consists of the least significant 8 bits. + spi_flags consists of the least significant 22 bits. . . - 7 6 5 4 3 2 1 0 - n n n n W P m m + 21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m . . mm defines the SPI mode. . . Mode POL PHA - 0 0 0 - 1 0 1 - 2 1 0 - 3 1 1 + 0 0 0 + 1 0 1 + 2 1 0 + 3 1 1 . . - P is 0 for active low chip select (normal) and 1 for active high. + px is 0 if CEx is active low (default) and 1 for active high. + + ux is 0 if the CEx gpio is reserved for SPI (default) + and 1 otherwise. + + A is 0 for the standard SPI device, 1 for the auxiliary SPI. + The auxiliary device is only present on the B+. W is 0 if the device is not 3-wire, 1 if the device is 3-wire. + Standard SPI device only. - nnnn defines the number of bytes (0-15) to write before switching - the MOSI line to MISO to read data. This field is ignored - if W is not set. + nnnn defines the number of bytes (0-15) to write before + switching the MOSI line to MISO to read data. This field + is ignored if W is not set. Standard SPI device only. + + T is 1 if the least significant bit is transmitted on MOSI + first, the default (0) shifts the most significant bit out + first. Auxiliary SPI device only. + + R is 1 if the least significant bit is received on MISO + first, the default (0) receives the most significant bit + first. Auxiliary SPI device only. + + bbbbbb defines the word size in bits (0-32). The default (0) + sets 8 bits per word. Auxiliary SPI device only. The other bits in flags should be set to zero. @@ -2333,7 +2360,7 @@ class pi(): # Don't raise exception. Must release lock. bytes = u2i(_pigpio_command_ext( - self.sl, _PI_CMD_SPIX, handle, 0, len(data), [data]), False) + self.sl, _PI_CMD_SPIX, handle, 0, len(data), [data], False)) if bytes > 0: data = self._rxbuf(bytes) else: @@ -2353,7 +2380,7 @@ class pi(): Normally you would only use the [*serial_**] functions if you are or will be connecting to the Pi over a network. If you will always run on the local Pi use the standard serial - modules instead. + module instead. ... h1 = pi.serial_open("/dev/ttyAMA0", 300) @@ -3066,33 +3093,7 @@ def xref(): A SPI channel. spi_flags: 32 bit - - spi_flags consists of the least significant 8 bits. - - . . - 7 6 5 4 3 2 1 0 - n n n n W P m m - . . - - mm defines the SPI mode. - - . . - Mode POL PHA - 0 0 0 - 1 0 1 - 2 1 0 - 3 1 1 - . . - - P is 0 for active low chip select (normal) and 1 for active high. - - W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - - nnnn defines the number of bytes (0-15) to write before switching - the MOSI line to MISO to read data. This field is ignored - if W is not set. - - The other bits in flags should be set to zero. + See [*spi_open*]. t1: A tick (earlier). diff --git a/pigpiod_if.3 b/pigpiod_if.3 index 10f8644..ea4346c 100644 --- a/pigpiod_if.3 +++ b/pigpiod_if.3 @@ -2228,6 +2228,13 @@ active low chip select. .br +.br +An auxiliary SPI device is available on the B+ and may be +selected by setting the A bit in the flags. The auxiliary +device has 3 chip selects and a selectable word size in bits. + +.br + .br .EX @@ -2244,21 +2251,21 @@ spi_channel: 0-1. .br Returns a handle (>=0) if OK, otherwise PI_BAD_SPI_CHANNEL, -PI_BAD_SPI_SPEED, PI_BAD_FLAGS, or PI_SPI_OPEN_FAILED. +PI_BAD_SPI_SPEED, PI_BAD_FLAGS, PI_NO_AUX_SPI, or PI_SPI_OPEN_FAILED. .br .br -spiFlags consists of the least significant 8 bits. +spi_flags consists of the least significant 22 bits. .br .br .EX -7 6 5 4 3 2 1 0 +21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 .br -n n n n W P m m + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m .br .EE @@ -2289,19 +2296,51 @@ Mode POL PHA .br .br -P is 0 for active low chip select (normal) and 1 for active high. +px is 0 if CEx is active low (default) and 1 for active high. .br .br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. +ux is 0 if the CEx gpio is reserved for SPI (default) and 1 otherwise. + +.br + +.br +A is 0 for the standard SPI device, 1 for the auxiliary SPI. The +auxiliary device is only present on the B+. + +.br + +.br +W is 0 if the device is not 3-wire, 1 if the device is 3-wire. Standard +SPI device only. .br .br nnnn defines the number of bytes (0-15) to write before switching the MOSI line to MISO to read data. This field is ignored -if W is not set. +if W is not set. Standard SPI device only. + +.br + +.br +T is 1 if the least significant bit is transmitted on MOSI first, the +default (0) shifts the most significant bit out first. Auxiliary SPI +device only. + +.br + +.br +R is 1 if the least significant bit is received on MISO first, the +default (0) receives the most significant bit first. Auxiliary SPI +device only. + +.br + +.br +bbbbbb defines the word size in bits (0-32). The default (0) +sets 8 bits per word. Auxiliary SPI device only. .br @@ -3156,7 +3195,7 @@ PI_PUD_UP 2 .br .IP "\fB*pulses\fP" 0 -An array of pulsed to be added to a waveform. +An array of pulses to be added to a waveform. .br @@ -3270,10 +3309,6 @@ The speed in bits per second to use for the SPI device. .br -.br - -.br - .IP "\fBspi_channel\fP" 0 A SPI channel, 0 or 1. @@ -3282,64 +3317,7 @@ A SPI channel, 0 or 1. .br .IP "\fBspi_flags\fP" 0 -spi_flags consists of the least significant 8 bits. - -.br - -.br - -.EX -7 6 5 4 3 2 1 0 -.br -n n n n W P m m -.br - -.EE - -.br - -.br -mm defines the SPI mode. - -.br - -.br - -.EX -Mode POL PHA -.br - 0 0 0 -.br - 1 0 1 -.br - 2 1 0 -.br - 3 1 1 -.br - -.EE - -.br - -.br -P is 0 for active low chip select (normal) and 1 for active high. - -.br - -.br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - -.br - -.br -nnnn defines the number of bytes (0-15) to write before switching -the MOSI line to MISO to read data. This field is ignored -if W is not set. - -.br - -.br -The other bits in flags should be set to zero. +See \fBspi_open\fP. .br diff --git a/pigpiod_if.c b/pigpiod_if.c index 2e4927f..1524481 100644 --- a/pigpiod_if.c +++ b/pigpiod_if.c @@ -25,7 +25,7 @@ OTHER DEALINGS IN THE SOFTWARE. For more information, please refer to */ -/* PIGPIOD_IF_VERSION 8 */ +/* PIGPIOD_IF_VERSION 9 */ #include #include diff --git a/pigpiod_if.h b/pigpiod_if.h index e62ff83..89affb4 100644 --- a/pigpiod_if.h +++ b/pigpiod_if.h @@ -30,7 +30,7 @@ For more information, please refer to #include "pigpio.h" -#define PIGPIOD_IF_VERSION 8 +#define PIGPIOD_IF_VERSION 9 /*TEXT @@ -1564,6 +1564,10 @@ Data will be transferred at baud bits per second. The flags may be used to modify the default behaviour of 4-wire operation, mode 0, active low chip select. +An auxiliary SPI device is available on the B+ and may be +selected by setting the A bit in the flags. The auxiliary +device has 3 chip selects and a selectable word size in bits. + . . spi_channel: 0-1. spi_baud: >1. @@ -1571,13 +1575,13 @@ spi_channel: 0-1. . . Returns a handle (>=0) if OK, otherwise PI_BAD_SPI_CHANNEL, -PI_BAD_SPI_SPEED, PI_BAD_FLAGS, or PI_SPI_OPEN_FAILED. +PI_BAD_SPI_SPEED, PI_BAD_FLAGS, PI_NO_AUX_SPI, or PI_SPI_OPEN_FAILED. -spiFlags consists of the least significant 8 bits. +spi_flags consists of the least significant 22 bits. . . -7 6 5 4 3 2 1 0 -n n n n W P m m +21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m . . mm defines the SPI mode. @@ -1590,13 +1594,30 @@ Mode POL PHA 3 1 1 . . -P is 0 for active low chip select (normal) and 1 for active high. +px is 0 if CEx is active low (default) and 1 for active high. -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. +ux is 0 if the CEx gpio is reserved for SPI (default) and 1 otherwise. + +A is 0 for the standard SPI device, 1 for the auxiliary SPI. The +auxiliary device is only present on the B+. + +W is 0 if the device is not 3-wire, 1 if the device is 3-wire. Standard +SPI device only. nnnn defines the number of bytes (0-15) to write before switching the MOSI line to MISO to read data. This field is ignored -if W is not set. +if W is not set. Standard SPI device only. + +T is 1 if the least significant bit is transmitted on MOSI first, the +default (0) shifts the most significant bit out first. Auxiliary SPI +device only. + +R is 1 if the least significant bit is received on MISO first, the +default (0) receives the most significant bit first. Auxiliary SPI +device only. + +bbbbbb defines the word size in bits (0-32). The default (0) +sets 8 bits per word. Auxiliary SPI device only. The other bits in flags should be set to zero. D*/ @@ -2047,7 +2068,7 @@ pulseLen:: 1-100, the length of a trigger pulse in microseconds. *pulses:: -An array of pulsed to be added to a waveform. +An array of pulses to be added to a waveform. pulsewidth::0, 500-2500 . . @@ -2095,37 +2116,11 @@ A standard type used to indicate the size of an object in bytes. spi_baud:: The speed in bits per second to use for the SPI device. - spi_channel:: A SPI channel, 0 or 1. spi_flags:: -spi_flags consists of the least significant 8 bits. - -. . -7 6 5 4 3 2 1 0 -n n n n W P m m -. . - -mm defines the SPI mode. - -. . -Mode POL PHA - 0 0 0 - 1 0 1 - 2 1 0 - 3 1 1 -. . - -P is 0 for active low chip select (normal) and 1 for active high. - -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - -nnnn defines the number of bytes (0-15) to write before switching -the MOSI line to MISO to read data. This field is ignored -if W is not set. - -The other bits in flags should be set to zero. +See [*spi_open*]. *str:: An array of characters. diff --git a/pigs.1 b/pigs.1 index d3ad8a3..251312d 100644 --- a/pigs.1 +++ b/pigs.1 @@ -1337,8 +1337,7 @@ The frequencies for each sample rate are: 5us 8000 4000 2000 1600 1000 800 500 400 320 8us 5000 2500 1250 1000 625 500 313 250 200 10us 4000 2000 1000 800 500 400 250 200 160 - -.br + #10 #11 #12 #13 #14 #15 #16 #17 #18 1us 1250 1000 800 500 400 250 200 100 50 2us 625 500 400 250 200 125 100 50 25 @@ -2168,8 +2167,7 @@ will be returned. .IP "" 4 .br -This command returns a handle to a SPI device on channel \fBc\fP. -.br +This command returns a handle to a SPI device on channel \fBc\fP. .br Data will be transferred at \fBb\fP bits per second. The flags \fBspf\fP @@ -2177,14 +2175,19 @@ may be used to modify the default behaviour of 4-wire operation, mode 0, active low chip select. .br -The flags consists of the least significant 8 bits. +An auxiliary SPI device is available on the B+ and may be +selected by setting the A bit in the flags. The auxiliary +device has 3 chip selects and a selectable word size in bits. + +.br +The flags consists of the least significant 22 bits. .br .EX -7 6 5 4 3 2 1 0 +21 20 19 18 17 16 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 .br -n n n n W P m m + b b b b b b R T n n n n W A u2 u1 u0 p2 p1 p0 m m .br .EE @@ -2209,15 +2212,37 @@ Mode POL PHA .EE .br -P is 0 for active low chip select (normal) and 1 for active high. +px is 0 if CEx is active low (default) and 1 for active high. .br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. +ux is 0 if the CEx gpio is reserved for SPI (default) and 1 otherwise. + +.br +A is 0 for the standard SPI device, 1 for the auxiliary SPI. The +auxiliary device is only present on the B+. + +.br +W is 0 if the device is not 3-wire, 1 if the device is 3-wire. Standard +SPI device only. .br nnnn defines the number of bytes (0-15) to write before switching the MOSI line to MISO to read data. This field is ignored -if W is not set. +if W is not set. Standard SPI device only. + +.br +T is 1 if the least significant bit is transmitted on MOSI first, the +default (0) shifts the most significant bit out first. Auxiliary SPI +device only. + +.br +R is 1 if the least significant bit is received on MISO first, the +default (0) receives the most significant bit first. Auxiliary SPI +device only. + +.br +bbbbbb defines the word size in bits (0-32). The default (0) +sets 8 bits per word. Auxiliary SPI device only. .br The other bits in flags should be set to zero. @@ -3187,50 +3212,7 @@ The command expects a script id as returned by a call to \fBPROC\fP. .br .IP "\fBspf\fP - SPI flags (32 bits)" 0 -The flags consists of the least significant 8 bits. - -.br - -.EX -7 6 5 4 3 2 1 0 -.br -n n n n W P m m -.br - -.EE - -.br -mm defines the SPI mode. - -.br - -.EX -Mode POL PHA -.br - 0 0 0 -.br - 1 0 1 -.br - 2 1 0 -.br - 3 1 1 -.br - -.EE - -.br -P is 0 for active low chip select (normal) and 1 for active high. - -.br -W is 0 if the device is not 3-wire, 1 if the device is 3-wire. - -.br -nnnn defines the number of bytes (0-15) to write before switching -the MOSI line to MISO to read data. This field is ignored -if W is not set. - -.br -The other bits in flags should be set to zero. +See \fBSPIO\fP. .br diff --git a/setup.py b/setup.py index 84dd5da..f483a93 100644 --- a/setup.py +++ b/setup.py @@ -3,7 +3,7 @@ from distutils.core import setup setup(name='pigpio', - version='1.10', + version='1.11', author='joan', author_email='joan@abyz.co.uk', maintainer='joan', diff --git a/x_pigs b/x_pigs index d2d9b9d..4991cc1 100755 --- a/x_pigs +++ b/x_pigs @@ -86,7 +86,7 @@ s=$(pigs pfs $GPIO 800) if [[ $s = 800 ]]; then echo "PFS-b ok"; else echo "PFS-b fail ($s)"; fi s=$(pigs pigpv) -if [[ $s = 20 ]]; then echo "PIGPV ok"; else echo "PIGPV fail ($s)"; fi +if [[ $s = 21 ]]; then echo "PIGPV ok"; else echo "PIGPV fail ($s)"; fi s=$(pigs prs $GPIO 255) if [[ $s = 250 ]]; then echo "PRG-a ok"; else echo "PRG-a fail ($s)"; fi diff --git a/x_pipe b/x_pipe index 0e9f877..2ae3599 100755 --- a/x_pipe +++ b/x_pipe @@ -119,7 +119,7 @@ if [[ $s = 800 ]]; then echo "PFS-b ok"; else echo "PFS-b fail ($s)"; fi echo "pigpv" >/dev/pigpio read -t 1 s /dev/pigpio read -t 1 s