int SPI::writeByte(uint8_t byteSent) { int ret; uint8_t tx[1] = {byteSent}; uint8_t rx[ARRAY_SIZE(tx)] = {0,}; struct spi_ioc_transfer tr; tr.tx_buf = (unsigned long)tx; tr.rx_buf = (unsigned long)rx; tr.len = ARRAY_SIZE(tx); tr.delay_usecs = _delay; tr.speed_hz = _speed; tr.bits_per_word = _bits; ret = ioctl(_fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) { printf("SPI writeByte : can't send spi message\n"); } return ret; }
uint8_t SPI::transfer(uint8_t tx) { struct spi_ioc_transfer tr; memset(&tr, 0, sizeof(tr)); tr.tx_buf = (unsigned long)&tx; uint8_t rx; tr.rx_buf = (unsigned long)℞ tr.len = sizeof(tx); tr.speed_hz = _spi_speed; //RF24_SPIDEV_SPEED; tr.delay_usecs = 0; tr.bits_per_word = RF24_SPIDEV_BITS; tr.cs_change = 0; int ret; ret = ioctl(this->fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) throw SPIException("can't send spi message"); /*{ perror("can't send spi message"); abort(); }*/ return rx; }
boolean spi_write(SpiDevice *spidev, int demux_BA, uint8_t *data, int length) { struct spi_ioc_transfer spi; if (!spi_demux_select(spidev, demux_BA)) return FALSE; memset (&spi, 0, sizeof(spi)); /* clear padding bytes?? */ spi.tx_buf = (unsigned long) data; spi.rx_buf = 0; spi.len = length; spi.delay_usecs = spi_delay; spi.speed_hz = spidev->speed[demux_BA]; spi.bits_per_word = spi_bpw; if (ioctl(spidev->fd, SPI_IOC_MESSAGE(1), &spi) < 0) { printf("spi_write() ioctl() failed: %s\n", strerror(errno)); return FALSE; } return TRUE; }
bool CDeviceSPI::WriteBuffer() { spi_ioc_transfer spi = {}; spi.tx_buf = (__u64)m_buff; spi.len = m_buffsize; int returnv = ioctl(m_fd, SPI_IOC_MESSAGE(1), &spi); if (returnv == -1) { LogError("%s: %s %s", m_name.c_str(), m_output.c_str(), GetErrno().c_str()); return false; } if (m_debug) { for (int i = 0; i < m_buffsize; i++) printf("%x ", m_buff[i]); printf("\n"); } return true; }
int SPI::xfer1(uint8_t wbuf[], uint8_t rbuf[], int len) { struct spi_ioc_transfer txinfo; txinfo.tx_buf = (__u64 ) wbuf; txinfo.rx_buf = (__u64 ) rbuf; txinfo.len = len; txinfo.delay_usecs = 0; txinfo.speed_hz = speed; txinfo.bits_per_word = bpw; txinfo.cs_change = 1; int r = ioctl(fd, SPI_IOC_MESSAGE(1), &txinfo); if (r < 0) { printf("ioctl(fd, SPI_IOC_MESSAGE(1), &txinfo): %s (len=%d)\n", strerror(r), len); return r; } //deactivate CS line //uint8_t tmp; //::read(fd, &tmp, 0); return len; }
bool BlackSPI::transfer(uint8_t *writeBuffer, uint8_t *readBuffer, size_t bufferSize, uint16_t wait_us) { if( ! this->isOpenFlag ) { this->spiErrors->openError = true; this->spiErrors->transferError = true; return false; } this->spiErrors->openError = false; uint8_t tempReadBuffer[ bufferSize ]; memset( tempReadBuffer, 0, bufferSize); spi_ioc_transfer package; package.tx_buf = (unsigned long)writeBuffer; package.rx_buf = (unsigned long)tempReadBuffer; package.len = bufferSize; package.delay_usecs = wait_us; package.speed_hz = this->currentProperties.spiSpeed; package.bits_per_word = this->currentProperties.spiBitsPerWord; if( ::ioctl(this->spiFD, SPI_IOC_MESSAGE(1), &package) >= 0) { this->spiErrors->transferError = false; memcpy(readBuffer, tempReadBuffer, bufferSize); return true; } else { this->spiErrors->transferError = true; return false; } }
int raspberrypiSPIDataRW(int channel, unsigned char *data, int len) { struct spi_ioc_transfer spi; memset(&spi, 0, sizeof(spi)); // found at http://www.raspberrypi.org/forums/viewtopic.php?p=680665#p680665 channel &= 1; spi.tx_buf = (unsigned long)data; spi.rx_buf = (unsigned long)data; spi.len = len; spi.delay_usecs = spiDelay; spi.speed_hz = spiSpeeds[channel]; spi.bits_per_word = spiBPW; #ifdef SPI_IOC_WR_MODE32 spi.tx_nbits = 0; #endif #ifdef SPI_IOC_RD_MODE32 spi.rx_nbits = 0; #endif if(ioctl(spiFds[channel], SPI_IOC_MESSAGE(1), &spi) < 0) { wiringXLog(LOG_ERR, "raspberrypi->SPIDataRW: Unable to read/write from channel %d: %s", channel, strerror(errno)); return -1; } return 0; }
uint8_t BlackSPI::transfer(uint8_t writeByte, uint16_t wait_us) { uint8_t tempReadByte = 0x00; if( ! this->isOpenFlag ) { this->spiErrors->openError = true; this->spiErrors->transferError = true; return tempReadByte; } this->spiErrors->openError = false; spi_ioc_transfer package; package.tx_buf = (unsigned long)&writeByte; package.rx_buf = (unsigned long)&tempReadByte; package.len = 1; package.delay_usecs = wait_us; package.speed_hz = this->currentProperties.spiSpeed; package.bits_per_word = this->currentProperties.spiBitsPerWord; if( ::ioctl(this->spiFD, SPI_IOC_MESSAGE(1), &package) >= 0) { this->spiErrors->transferError = false; return tempReadByte; } else { this->spiErrors->transferError = true; return tempReadByte; } }
int ProviderSpi::writeBytes(const unsigned size, const uint8_t * data) { if (_fid < 0) { return -1; } _spi.tx_buf = __u64(data); _spi.len = __u32(size); if (_spiDataInvert) { uint8_t * newdata = (uint8_t *)malloc(size); for (unsigned i = 0; i<size; i++) { newdata[i] = data[i] ^ 0xff; } _spi.tx_buf = __u64(newdata); } int retVal = ioctl(_fid, SPI_IOC_MESSAGE(1), &_spi); ErrorIf((retVal < 0), _log, "SPI failed to write. errno: %d, %s", errno, strerror(errno) ); return retVal; }
static void transfer(int fd, uint8_t const *tx, uint8_t const *rx, size_t len) { int ret; int out_fd; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = len, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; if (mode & SPI_TX_QUAD) tr.tx_nbits = 4; else if (mode & SPI_TX_DUAL) tr.tx_nbits = 2; if (mode & SPI_RX_QUAD) tr.rx_nbits = 4; else if (mode & SPI_RX_DUAL) tr.rx_nbits = 2; if (!(mode & SPI_LOOP)) { if (mode & (SPI_TX_QUAD | SPI_TX_DUAL)) tr.rx_buf = 0; else if (mode & (SPI_RX_QUAD | SPI_RX_DUAL)) tr.tx_buf = 0; } ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); if (verbose) hex_dump(tx, len, 32, "TX"); if (output_file) { out_fd = open(output_file, O_WRONLY | O_CREAT | O_TRUNC, 0666); if (out_fd < 0) pabort("could not open output file"); ret = write(out_fd, rx, len); if (ret != len) pabort("not all bytes written to output file"); close(out_fd); } if (verbose || !output_file) hex_dump(rx, len, 32, "RX"); } static void print_usage(const char *prog) { printf("Usage: %s [-DsbdlHOLC3]\n", prog); puts(" -D --device device to use (default /dev/spidev1.1)\n" " -s --speed max speed (Hz)\n" " -d --delay delay (usec)\n" " -b --bpw bits per word\n" " -i --input input data from a file (e.g. \"test.bin\")\n" " -o --output output data to a file (e.g. \"results.bin\")\n" " -l --loop loopback\n" " -H --cpha clock phase\n" " -O --cpol clock polarity\n" " -L --lsb least significant bit first\n" " -C --cs-high chip select active high\n" " -3 --3wire SI/SO signals shared\n" " -v --verbose Verbose (show tx buffer)\n" " -p Send data (e.g. \"1234\\xde\\xad\")\n" " -N --no-cs no chip select\n" " -R --ready slave pulls low to pause\n" " -2 --dual dual transfer\n" " -4 --quad quad transfer\n"); exit(1); }
bool SPIDevice::transfer(const uint8_t *send, uint32_t send_len, uint8_t *recv, uint32_t recv_len) { struct spi_ioc_transfer msgs[2] = { }; unsigned nmsgs = 0; assert(_bus.fd >= 0); if (send && send_len != 0) { msgs[nmsgs].tx_buf = (uint64_t) send; msgs[nmsgs].rx_buf = 0; msgs[nmsgs].len = send_len; msgs[nmsgs].speed_hz = _speed; msgs[nmsgs].delay_usecs = 0; msgs[nmsgs].bits_per_word = _desc.bits_per_word; msgs[nmsgs].cs_change = 0; nmsgs++; } if (recv && recv_len != 0) { msgs[nmsgs].tx_buf = 0; msgs[nmsgs].rx_buf = (uint64_t) recv; msgs[nmsgs].len = recv_len; msgs[nmsgs].speed_hz = _speed; msgs[nmsgs].delay_usecs = 0; msgs[nmsgs].bits_per_word = _desc.bits_per_word; msgs[nmsgs].cs_change = 0; nmsgs++; } if (!nmsgs) { return false; } int r; if (_bus.last_mode == _desc.mode) { /* the mode in the kernel is not tied to the file descriptor, so there is a chance some other process has changed it since we last used the bus. We want to report when this happens so the user has a chance of figuring out when there is conflicted use of the SPI bus. Unfortunately this costs us an extra syscall per transfer. */ uint8_t current_mode; if (ioctl(_bus.fd, SPI_IOC_RD_MODE, ¤t_mode) < 0) { hal.console->printf("SPIDevice: error on getting mode fd=%d (%s)\n", _bus.fd, strerror(errno)); _bus.last_mode = -1; } else if (current_mode != _bus.last_mode) { hal.console->printf("SPIDevice: bus mode conflict fd=%d mode=%u/%u\n", _bus.fd, (unsigned)_bus.last_mode, (unsigned)current_mode); _bus.last_mode = -1; } } if (_desc.mode != _bus.last_mode) { r = ioctl(_bus.fd, SPI_IOC_WR_MODE, &_desc.mode); if (r < 0) { hal.console->printf("SPIDevice: error on setting mode fd=%d (%s)\n", _bus.fd, strerror(errno)); return false; } _bus.last_mode = _desc.mode; } _cs_assert(); r = ioctl(_bus.fd, SPI_IOC_MESSAGE(nmsgs), &msgs); _cs_release(); if (r == -1) { hal.console->printf("SPIDevice: error transferring data fd=%d (%s)\n", _bus.fd, strerror(errno)); return false; } return true; }
static int transfer(int fd, char *tbuf, char *rbuf, int bytes) { int ret; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tbuf, .rx_buf = (unsigned long)rbuf, .len = bytes, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret == 1) printf("can't send spi message"); return ret; } int execute_buffer_test(int spi_id, int len, char *buffer) { char *rbuf; int res = 0; int fd = -1; if (spi_id == 0) { fd = open(DEV_SPI1, O_RDWR); } else if (spi_id == 1) { fd = open(DEV_SPI2, O_RDWR); } else if (spi_id == 2) { fd = open(DEV_SPI3, O_RDWR); } if (fd < 0) { printf("Error:cannot open device " "(Maybe not present in your board?)\n"); return -1; } res = ioctl(fd, SPI_IOC_WR_MODE, &mode); if (res == -1) { printf("can't set spi mode"); goto exit; } res = ioctl(fd, SPI_IOC_RD_MODE, &mode); if (res == -1) { printf("can't set spi mode"); goto exit; } /* * bits per word */ res = ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &bits_per_word); if (res == -1) { printf("can't set bits per word"); goto exit; } res = ioctl(fd, SPI_IOC_RD_BITS_PER_WORD, &bits_per_word); if (res == -1) { printf("can't get bits per word"); goto exit; } /* * max speed hz */ res = ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed); if (res == -1) { printf("can't set max speed hz"); goto exit; } res = ioctl(fd, SPI_IOC_RD_MAX_SPEED_HZ, &speed); if (res == -1) { printf("can't get max speed hz"); goto exit; } printf("spi mode: %d\n", mode); printf("bits per word: %d\n", bits_per_word); printf("max speed: %d Hz (%d KHz)\n", speed, speed/1000); rbuf = malloc(len); memset(rbuf, 0, len); res = transfer(fd, buffer, rbuf, len); if (res < 0) { printf("Failed transferring data: %d\n", errno); return -1; } res = check_data_integrity(buffer, rbuf, len); printf("Data sent : %s\n", (char *)buffer); printf("Data received : %s\n", (char *)rbuf); if (res != 0) { printf("Test FAILED.\n"); } else { printf("Test PASSED.\n"); } free(rbuf); exit: close(fd); return 0; }
static PyObject * SpiDev_xfer2(SpiDevObject *self, PyObject *args) { static char *msg = "Argument must be a list of at least one, " "but not more than 4096 integers"; int status; uint16_t delay_usecs = 0; uint32_t speed_hz = 0; uint8_t bits_per_word = 0; uint16_t ii, len; PyObject *list; struct spi_ioc_transfer xfer; uint8_t *txbuf, *rxbuf; if (!PyArg_ParseTuple(args, "O|IHB:xfer2", &list, &speed_hz, &delay_usecs, &bits_per_word)) return NULL; if (!PyList_Check(list)) { PyErr_SetString(PyExc_TypeError, wrmsg); return NULL; } if ((len = PyList_GET_SIZE(list)) > SPIDEV_MAXPATH) { PyErr_SetString(PyExc_OverflowError, wrmsg); return NULL; } txbuf = malloc(sizeof(__u8) * len); rxbuf = malloc(sizeof(__u8) * len); for (ii = 0; ii < len; ii++) { PyObject *val = PyList_GET_ITEM(list, ii); if (!PyInt_Check(val)) { PyErr_SetString(PyExc_TypeError, msg); return NULL; } txbuf[ii] = (__u8)PyInt_AS_LONG(val); } xfer.tx_buf = (unsigned long)txbuf; xfer.rx_buf = (unsigned long)rxbuf; xfer.len = len; xfer.delay_usecs = delay_usecs; xfer.speed_hz = speed_hz ? speed_hz : self->max_speed_hz; xfer.bits_per_word = bits_per_word ? bits_per_word : self->bits_per_word; status = ioctl(self->fd, SPI_IOC_MESSAGE(1), &xfer); if (status < 0) { PyErr_SetFromErrno(PyExc_IOError); return NULL; } for (ii = 0; ii < len; ii++) { PyObject *val = Py_BuildValue("l", (long)rxbuf[ii]); PyList_SET_ITEM(list, ii, val); } // WA: // in CS_HIGH mode CS isnt pulled to low after transfer // reading 0 bytes doesn't really matter but brings CS down status = read(self->fd, &rxbuf[0], 0); free(txbuf); free(rxbuf); Py_INCREF(list); return list; }
static PyObject * SpiDev_xfer(SpiDevObject *self, PyObject *args) { uint16_t ii, len; int status; uint16_t delay_usecs = 0; uint32_t speed_hz = 0; uint8_t bits_per_word = 0; PyObject *list; #ifdef SPIDEV_SINGLE struct spi_ioc_transfer *xferptr; #else struct spi_ioc_transfer xfer; #endif uint8_t *txbuf, *rxbuf; if (!PyArg_ParseTuple(args, "O|IHB:xfer", &list, &speed_hz, &delay_usecs, &bits_per_word)) return NULL; if (!PyList_Check(list)) { PyErr_SetString(PyExc_TypeError, wrmsg); return NULL; } if ((len = PyList_GET_SIZE(list)) > SPIDEV_MAXPATH) { PyErr_SetString(PyExc_OverflowError, wrmsg); return NULL; } txbuf = malloc(sizeof(__u8) * len); rxbuf = malloc(sizeof(__u8) * len); #ifdef SPIDEV_SINGLE xferptr = (struct spi_ioc_transfer*) malloc(sizeof(struct spi_ioc_transfer) * len); for (ii = 0; ii < len; ii++) { PyObject *val = PyList_GET_ITEM(list, ii); if (!PyInt_Check(val)) { PyErr_SetString(PyExc_TypeError, wrmsg); return NULL; } txbuf[ii] = (__u8)PyInt_AS_LONG(val); xferptr[ii].tx_buf = (unsigned long)&txbuf[ii]; xferptr[ii].rx_buf = (unsigned long)&rxbuf[ii]; xferptr[ii].len = 1; xferptr[ii].delay_usecs = delay; xferptr[ii].speed_hz = speed_hz ? speed_hz : self->max_speed_hz; xferptr[ii].bits_per_word = bits_per_word ? bits_per_word : self->bits_per_word; } status = ioctl(self->fd, SPI_IOC_MESSAGE(len), xferptr); if (status < 0) { PyErr_SetFromErrno(PyExc_IOError); return NULL; } #else for (ii = 0; ii < len; ii++) { PyObject *val = PyList_GET_ITEM(list, ii); if (!PyInt_Check(val)) { PyErr_SetString(PyExc_TypeError, wrmsg); return NULL; } txbuf[ii] = (__u8)PyInt_AS_LONG(val); } xfer.tx_buf = (unsigned long)txbuf; xfer.rx_buf = (unsigned long)rxbuf; xfer.len = len; xfer.delay_usecs = delay_usecs; xfer.speed_hz = speed_hz ? speed_hz : self->max_speed_hz; xfer.bits_per_word = bits_per_word ? bits_per_word : self->bits_per_word; status = ioctl(self->fd, SPI_IOC_MESSAGE(1), &xfer); if (status < 0) { PyErr_SetFromErrno(PyExc_IOError); return NULL; } #endif for (ii = 0; ii < len; ii++) { PyObject *val = Py_BuildValue("l", (long)rxbuf[ii]); PyList_SET_ITEM(list, ii, val); } // WA: // in CS_HIGH mode CS isn't pulled to low after transfer, but after read // reading 0 bytes doesnt matter but brings cs down status = read(self->fd, &rxbuf[0], 0); free(txbuf); free(rxbuf); Py_INCREF(list); return list; }
int main() { // Change status gpio pins to inputs // ... should be done in device tree overlay... gpio_export(AZIMUTH_STATUS_PIN); gpio_export(ELEVATION_STATUS_PIN); gpio_set_dir(AZIMUTH_STATUS_PIN, INPUT_PIN); gpio_set_dir(ELEVATION_STATUS_PIN, INPUT_PIN); // The raw values from the sensors. RESPONSE_TYPE rsp_azimuth; while(1) { // ----------------- READ AZIMUTH ----------------- int fd_azimuth = open(AZIMUTH_DEVICE_FILE, O_RDWR); if (fd_azimuth < 0) { perror("Could not open azimuth device file!"); abort(); } rsp_azimuth = -1; unsigned int azimuth_status; gpio_get_value(AZIMUTH_STATUS_PIN, &azimuth_status); if (1){ //if (azimuth_status == HIGH){ #if USE_IOCTL_API // Configure the SPI port struct spi_ioc_transfer tr_azimuth[1]; memset(&tr_azimuth[0], 0, sizeof(tr_azimuth)); tr_azimuth[0].rx_buf = &rsp_azimuth; // Throws warning tr_azimuth[0].tx_buf = 0; // NULL pointer is OK // Below for bits per word "correct" //tr_azimuth[1].len = 0; // crash! Inappropriate ioctl for device tr_azimuth[0].len = 2; // No time varying data gets through //tr_azimuth[0].len = 2; // No time varying data gets through //tr_azimuth[0].len = 3; // No time varying data gets through //tr_azimuth[0].len = 4; // 2 bit shift per read //tr_azimuth[0].len = 5; // 1 bit shift per read //tr_azimuth[0].len = 6; // 1 bit shift per read //tr_azimuth[0].len = 7; // 1 bit shift per read //tr_azimuth[0].len = 8; // 1 bit shift per read //tr_azimuth[0].len = 9; // varying 0-1 bit shift per read //tr_azimuth[0].len = 10; // varying 0-1 bit shift per read //tr_azimuth[0].len = 11; // varying 0-1 bit shift per read //tr_azimuth[0].len = 12; // 2 bit shift per read //tr_azimuth[0].len = 13; // crash! bad file descriptor //tr_azimuth[0].len = 14; // crash! bad file descriptor //tr_azimuth[1].len = 15; // crash! bad file descriptor //tr_azimuth[0].len = 16; // crash! bad file descriptor //tr_azimuth[0].len = 8*sizeof(RESPONSE_TYPE); // in bits, causes crash! //tr_azimuth[0].len = sizeof(RESPONSE_TYPE); // in bytes tr_azimuth[0].delay_usecs = 100; tr_azimuth[0].speed_hz = 100000; //tr_azimuth[0].bits_per_word = sizeof(RESPONSE_TYPE)*8; // Below for len "correct" tr_azimuth[0].bits_per_word =8; //tr_azimuth[0].bits_per_word = 1; // crash! tr_azimuth[0].cs_change = 1; int ret_azimuth = ioctl(fd_azimuth, SPI_IOC_MESSAGE(1), &tr_azimuth); if (ret_azimuth < 0) perror("ioctl"); #else read(fd_azimuth, &rsp_azimuth, sizeof(RESPONSE_TYPE)); #endif // Print the values to sanity check them printf("0x%.8X ", rsp_azimuth); int i; for(i=sizeof(rsp_azimuth)*8-1; i>=0; i--) { printf("%i", rsp_azimuth>>i & (RESPONSE_TYPE)1); } printf("\n"); } else{ printf("Warning, Low status pin!!!\n"); } int ret = close(fd_azimuth); if(ret<0) { perror("Could not close the device file!"); abort();} //uint16_t azimuth_swapped = __builtin_bswap16(rsp_azimuth[0]); //printf("rsp_azimuth = %x\n", rsp_azimuth[0]); //double azimuth = (double) azimuth_swapped * 360.0 / (1<<16); // degrees //double elevation = (double) (*rsp_elevation) *360.0 / (1<<16); // degrees //printf("azimuth = %f \n", azimuth_swapped); //printf("elevation = %f, azimuth = %f \n", elevation, azimuth); //usleep(500000); };
static void send_frame(int fileDescriptor, uint8_t txbuf[], int buffsize) { #ifdef OLIMEX ////("olimex sendframe \n"); // GPIO 65 = LED // GPIO 20 = SSP2_MOSI = LED DATA = OL Micro CON2 pin 10 = OL Maxi UEXT pin 8 // GPIO 24 = SSP2_SCK = LED CLOCK = OL Micro CON2 pin 11 = OL Maxi UEXT pin 9 GPIO_WRITE_PIN(65,1); uint8_t i, j, v, b; for (i=0; i<buffsize; i++) { v = txbuf[i]; b = 0x80; for (j=0; j<bits; j++) { GPIO_WRITE_PIN(20,v&b); b >>= 1; GPIO_WRITE_PIN(24,1); GPIO_WRITE_PIN(24,0); } } GPIO_WRITE_PIN(65,0); #else int ret; int j = 0; int offset; uint8_t rx[385] = { 0, }; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)txbuf, .rx_buf = (unsigned long)rx, .len = buffsize, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; //////("buffsize %d\n", buffsize); ret = ioctl(fileDescriptor, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); #endif } //move to lightnames.c? int set_to_canonical(int outer, int face, int row, int col) { // Need to check for out-of-bounds here, but meh. // outer? face row col int outermap[NUM_FACES][ROWS_PER_FACE][COLS_PER_FACE] = { /* 1 3 0 0 */ CANONICAL_OUTER_RIGHT_POSTERIOR_TOP /* 1 3 0 1 */ ,CANONICAL_OUTER_RIGHT_POSTERIOR_CENTER /* 1 3 0 2 */ ,CANONICAL_OUTER_RIGHT_POSTERIOR_BOTTOM /* 1 3 1 0 */ ,CANONICAL_OUTER_RIGHT_CENTER_TOP /* 1 3 1 1 */ ,CANONICAL_OUTER_RIGHT_CENTER_CENTER /* 1 3 1 2 */ ,CANONICAL_OUTER_RIGHT_CENTER_BOTTOM /* 1 3 2 0 */ ,CANONICAL_OUTER_RIGHT_FRONT_TOP /* 1 3 2 1 */ ,CANONICAL_OUTER_RIGHT_FRONT_CENTER /* 1 3 2 2 */ ,CANONICAL_OUTER_RIGHT_FRONT_BOTTOM /* 1 2 0 0 */ ,CANONICAL_OUTER_BOTTOM_POSTERIOR_RIGHT /* 1 2 0 1 */ ,CANONICAL_OUTER_BOTTOM_POSTERIOR_CENTER /* 1 2 0 2 */ ,CANONICAL_OUTER_BOTTOM_POSTERIOR_LEFT /* 1 2 1 0 */ ,CANONICAL_OUTER_BOTTOM_CENTER_RIGHT /* 1 2 1 1 */ ,CANONICAL_OUTER_BOTTOM_CENTER_CENTER /* 1 2 1 2 */ ,CANONICAL_OUTER_BOTTOM_CENTER_LEFT /* 1 2 2 0 */ ,CANONICAL_OUTER_BOTTOM_FRONT_RIGHT /* 1 2 2 1 */ ,CANONICAL_OUTER_BOTTOM_FRONT_CENTER /* 1 2 2 2 */ ,CANONICAL_OUTER_BOTTOM_FRONT_LEFT /* 1 1 0 0 */ ,CANONICAL_OUTER_LEFT_POSTERIOR_BOTTOM /* 1 1 0 1 */ ,CANONICAL_OUTER_LEFT_POSTERIOR_CENTER /* 1 1 0 2 */ ,CANONICAL_OUTER_LEFT_POSTERIOR_TOP /* 1 1 1 0 */ ,CANONICAL_OUTER_LEFT_CENTER_BOTTOM /* 1 1 1 1 */ ,CANONICAL_OUTER_LEFT_CENTER_CENTER /* 1 1 1 2 */ ,CANONICAL_OUTER_LEFT_CENTER_TOP /* 1 1 2 0 */ ,CANONICAL_OUTER_LEFT_FRONT_BOTTOM /* 1 1 2 1 */ ,CANONICAL_OUTER_LEFT_FRONT_CENTER /* 1 1 2 2 */ ,CANONICAL_OUTER_LEFT_FRONT_TOP /* 1 0 0 0 */ ,CANONICAL_OUTER_TOP_POSTERIOR_LEFT /* 1 0 0 1 */ ,CANONICAL_OUTER_TOP_POSTERIOR_CENTER /* 1 0 0 2 */ ,CANONICAL_OUTER_TOP_POSTERIOR_RIGHT /* 1 0 1 0 */ ,CANONICAL_OUTER_TOP_CENTER_LEFT /* 1 0 1 1 */ ,CANONICAL_OUTER_TOP_CENTER_CENTER /* 1 0 1 2 */ ,CANONICAL_OUTER_TOP_CENTER_RIGHT /* 1 0 2 0 */ ,CANONICAL_OUTER_TOP_FRONT_LEFT /* 1 0 2 1 */ ,CANONICAL_OUTER_TOP_FRONT_CENTER /* 1 0 2 2 */ ,CANONICAL_OUTER_TOP_FRONT_RIGHT }; int innermap[NUM_FACES][BULBS_INSIDE] = { /* 0 0 3 */ CANONICAL_INNER_RIGHT_POSTERIOR_TOP /* 0 0 1 */ ,CANONICAL_INNER_RIGHT_FRONT_TOP /* 0 0 2 */ ,CANONICAL_INNER_RIGHT_POSTERIOR_BOTTOM /* 0 0 0 */ ,CANONICAL_INNER_RIGHT_FRONT_BOTTOM /* 0 0 3 */ ,CANONICAL_INNER_BOTTOM_POSTERIOR_RIGHT /* 0 0 1 */ ,CANONICAL_INNER_BOTTOM_FRONT_RIGHT /* 0 0 2 */ ,CANONICAL_INNER_BOTTOM_POSTERIOR_LEFT /* 0 0 0 */ ,CANONICAL_INNER_BOTTOM_FRONT_LEFT /* 0 0 3 */ ,CANONICAL_INNER_LEFT_POSTERIOR_BOTTOM /* 0 0 1 */ ,CANONICAL_INNER_LEFT_FRONT_BOTTOM /* 0 0 2 */ ,CANONICAL_INNER_LEFT_POSTERIOR_TOP /* 0 0 0 */ ,CANONICAL_INNER_LEFT_FRONT_TOP /* 0 0 3 */ ,CANONICAL_INNER_TOP_POSTERIOR_LEFT /* 0 0 1 */ ,CANONICAL_INNER_TOP_FRONT_LEFT /* 0 0 2 */ ,CANONICAL_INNER_TOP_POSTERIOR_RIGHT /* 0 0 0 */ ,CANONICAL_INNER_TOP_FRONT_RIGHT }; if(outer) { return outermap[face][row][col]; } else { return innermap[face][row]; } }
static void transfer(int fd, uint8_t * message, size_t message_size) { int ret; sleep(.5); GPIOWrite(CEPIN, 0); sleep(.5); uint8_t rx[message_size]; printf("Array size %i \n", message_size); struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)message, .rx_buf = (unsigned long)rx, .len = message_size, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); sleep(3); GPIOWrite(CEPIN, 1); sleep(.5); } int main(int argc, char *argv[]) { /* * Enable GPIO pins */ if (-1 == GPIOExport(CEPIN)) return(1); /* * Set GPIO directions */ if (-1 == GPIODirection(CEPIN, OUT)) return(2); // Reset VGATonic to ensure we are at pixel 0,0 sleep(.5); GPIOWrite(CEPIN, 1); sleep(.5); GPIOWrite(CEPIN, 0); sleep(.5); GPIOWrite(CEPIN, 1); sleep(.5); GPIOWrite(CEPIN, 0); sleep(.5); GPIOWrite(CEPIN, 1); sleep(.5); int ret = 0; int fd; fd = open(device, O_RDWR); if (fd < 0) pabort("can't open device"); /* * spi mode */ ret = ioctl(fd, SPI_IOC_WR_MODE, &mode); if (ret == -1) pabort("can't set spi mode"); ret = ioctl(fd, SPI_IOC_RD_MODE, &mode); if (ret == -1) pabort("can't get spi mode"); /* * bits per word */ ret = ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &bits); if (ret == -1) pabort("can't set bits per word"); ret = ioctl(fd, SPI_IOC_RD_BITS_PER_WORD, &bits); if (ret == -1) pabort("can't get bits per word"); /* * max speed hz */ ret = ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed); if (ret == -1) pabort("can't set max speed hz"); ret = ioctl(fd, SPI_IOC_RD_MAX_SPEED_HZ, &speed); if (ret == -1) pabort("can't get max speed hz"); printf("spi mode: %d\n", mode); printf("bits per word: %d\n", bits); printf("max speed: %d Hz (%d KHz)\n", speed, speed/1000); while (1) { transfer(fd, doge, 307200); transfer(fd, guitars, 307200); } close(fd); return ret; }
int main() { int ret = -1; //返回值变量 int fd= -1; //SPI文件描述符 int fd204,fd205,fd206,fd207,fd212,fd213,fd214,fd215,fd307,fd315,fd327; //GPIO管脚文件描述符 int i; const unsigned char ip_a = 192 ; const unsigned char ip_b = 168 ; const int lens=3000; //SPI通讯最大数据长度 int recv_len=0; //网络接收数据实际长度 unsigned int cnt=0; //SPI通信实际数据长度 unsigned char value=0; //FPGA有数标识 /**SPI 参数设置**/ uint8_t mode = SPI_MODE_0; uint8_t bits = 8; uint32_t speed = 20000000; uint16_t delay = 0; struct spi_ioc_transfer transfer; struct spi_ioc_transfer receiver; uint8_t tx[lens]; //SPI通信 uint8_t rx[lens]; //SPI通信 uint8_t sendbuf[lens]; //网络数据发送缓冲区 uint8_t recivebuf[lens]; //网络数据接收缓冲区 memset(tx,0,sizeof(tx)); memset(rx,0,sizeof(rx)); memset(sendbuf,0,sizeof(sendbuf)); memset(recivebuf,0,sizeof(recivebuf)); /**Init Socket**/ if (m287_socket_init() <0) { printf("网络初始化失败\n"); return 0 ; } /**Init watchdog**/ if(m287_watchdog_init()<0) { printf("看门狗初始化失败\n"); return 0 ; } /************Init gpio3.7|gpio3.15| gpio3.27***************/ fd315 = open(gpio3_15, O_RDWR); if (fd315 < 0) pabort("can't open gpio3.15_device"); fd327 = open(gpio3_27, O_RDWR); if (fd327 < 0) pabort("can't open gpio3.27_device"); fd307 = open(gpio3_7, O_RDWR); if (fd307 < 0) pabort("can't open gpio3.7_device"); /************Init gpio2.4~~gpio2.7***************/ fd204 = open(gpio2_4, O_RDWR); if (fd204 < 0) pabort("can't open gpio2.4_device"); fd205 = open(gpio2_5, O_RDWR); if (fd205 < 0) pabort("can't open gpio2.5_device"); fd206 = open(gpio2_6, O_RDWR); if (fd206 < 0) pabort("can't open gpio2.6_device"); fd207 = open(gpio2_7, O_RDWR); if (fd207 < 0) pabort("can't open gpio2.7_device"); /************Init gpio2.12~~gpio2.15***************/ fd212 = open(gpio2_12, O_RDWR); if (fd212 < 0) pabort("can't open gpio2.12_device"); fd213 = open(gpio2_13, O_RDWR); if (fd213 < 0) pabort("can't open gpio2.13_device"); fd214 = open(gpio2_14, O_RDWR); if (fd214 < 0) pabort("can't open gpio2.14_device"); fd215 = open(gpio2_15, O_RDWR); if (fd215 < 0) pabort("can't open gpio2.15_device"); /************Init SPI*************/ fd = open(spi_device, O_RDWR); if (fd < 0) pabort("can't open spi_device"); /* * spi mode */ ret = ioctl(fd, SPI_IOC_WR_MODE, &mode); if (ret == -1) pabort("can't set wr spi mode"); ret = ioctl(fd, SPI_IOC_RD_MODE, &mode); if (ret == -1) pabort("can't get spi mode"); /* * bits per word */ ret = ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &bits); if (ret == -1) pabort("can't set bits per word"); ret = ioctl(fd, SPI_IOC_RD_BITS_PER_WORD, &bits); if (ret == -1) pabort("can't get bits per word"); /* * max speed hz */ ret = ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed); if (ret == -1) pabort("can't set max speed hz"); ret = ioctl(fd, SPI_IOC_RD_MAX_SPEED_HZ, &speed); if (ret == -1) pabort("can't get max speed hz"); printf("spi mode: %d\n", mode); printf("bits per word: %d\n", bits); printf("max speed: %d Hz (%d KHz)\n", speed, speed/1000); transfer.tx_buf = (unsigned long)tx; transfer.rx_buf = 0; transfer.len = lens; transfer.delay_usecs = delay; transfer.speed_hz = speed; transfer.bits_per_word = bits; receiver.tx_buf = 0; receiver.rx_buf = (unsigned long)rx; receiver.len = lens; receiver.delay_usecs = delay; receiver.speed_hz = speed; receiver.bits_per_word = bits; m287_errSend("net starting....",15); while(1) { lseek(fd315, 0, SEEK_SET); read(fd315, &value, 1); if(value=='1') { write(fd206, "0", 1); write(fd205, "0", 1); write(fd204, "1", 1); write(fd207, "1", 1); write(fd207, "0", 1); write(fd206, "0", 1); write(fd205, "1", 1); write(fd204, "0", 1); write(fd207, "1", 1); write(fd207, "0", 1); receiver.len = 8; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &receiver); if (ret < 0) pabort("can't receive spi message"); cnt = (rx[0]<<8)+rx[1]; //通过SPI从FPGA中得到数据长度 if (cnt > 2900 || cnt <= 30 || rx[2] != ip_a || rx[3] != ip_b) //数据长度大于预定长度,直接进行下一次循环 { if (cnt >2900) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data overflow , len from FPGA is %d",cnt); } if (cnt ==0) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data LEN is 0"); } if (rx[2] != ip_a || rx[3] != ip_b) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data ip err , ip from FPGA is %d-%d",rx[2],rx[3]); } else { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data len too short , len from FPGA is %d",cnt); } m287_errSend(err_log_buf,err_log_buf_len); clear_err_buf(); continue ; } else printf("recive from FPGA and send to Hmi %d lens\n" , cnt); write(fd206, "0", 1); write(fd205, "1", 1); write(fd204, "1", 1); write(fd207, "1", 1); write(fd207, "0", 1); receiver.len = cnt+1; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &receiver); if (ret < 0) pabort("can't receive spi message"); write(fd206, "0", 1); write(fd205, "0", 1); write(fd204, "0", 1); write(fd207, "1", 1); write(fd207, "0", 1); for(i=0;i<cnt;i++) { sendbuf[i] = rx[i+1]; //printf("data[%02d] is 0x%02x\n",i,sendbuf[i]); } //udp发送数据 m287_udpSend(sendbuf,cnt) ; } lseek(fd327, 0, SEEK_SET); read(fd327, &value, 1); if(value=='1') { write(fd206, "1", 1); write(fd205, "0", 1); write(fd204, "1", 1); write(fd207, "1", 1); write(fd207, "0", 1); write(fd206, "1", 1); write(fd205, "1", 1); write(fd204, "0", 1); write(fd207, "1", 1); write(fd207, "0", 1); receiver.len = 8; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &receiver); if (ret < 0) pabort("can't receive spi message"); cnt = (rx[0]<<8)+rx[1]; if (cnt > 2900 || cnt <= 30 || rx[2] != ip_a || rx[3] != ip_b) //FPGA 数据有错误,直接进行下一次循环 { if (cnt >2900) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data overflow , len from FPGA is %d",cnt); } if (cnt ==0) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data LEN is 0"); } if (rx[2] != ip_a || rx[3] != ip_b) { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data ip err , ip from FPGA is %d-%d",rx[2],rx[3]); } else { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "FPGA data len too short , len from FPGA is %d",cnt); } m287_errSend(err_log_buf,err_log_buf_len); clear_err_buf(); continue ; } else printf("recive from FPGA and send to Hmi %d lens\n" , cnt); write(fd206, "1", 1); write(fd205, "1", 1); write(fd204, "1", 1); write(fd207, "1", 1); write(fd207, "0", 1); receiver.len = cnt+1; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &receiver); if (ret < 0) pabort("can't receive spi message"); write(fd206, "0", 1); write(fd205, "0", 1); write(fd204, "0", 1); write(fd207, "1", 1); write(fd207, "0", 1); for(i=0;i<cnt;i++) //由于FPGA程序问题,数据向右偏移了一个字节,这里偏移回去,得到真是数据 { sendbuf[i] = rx[i+1]; //printf("data[%02d] is 0x%02x\n",i,sendbuf[i]); } //udp发送数据 m287_udpSend(sendbuf,cnt) ; } recv_len = m287_udpRecive(tx , lens); if(recv_len>20 && recv_len < 50) { //帧头55AA ,tx[11]为接收战场编号 if(tx[0]==0x55 && tx[1]==0xaa && tx[11]>0x0 &&tx[11]<0x0b) { write(fd215, "1", 1); write(fd214, "1", 1); write(fd213, "0", 1); write(fd212, "0", 1); write(fd307, "1", 1); write(fd307, "0", 1); if(tx[11]==0x01) { write(fd215, "0", 1); write(fd214, "0", 1); write(fd213, "0", 1); write(fd212, "1", 1); } else if(tx[11]==0x02) { write(fd215, "0", 1); write(fd214, "0", 1); write(fd213, "1", 1); write(fd212, "0", 1); } else if(tx[11]==0x03) { write(fd215, "0", 1); write(fd214, "0", 1); write(fd213, "1", 1); write(fd212, "1", 1); } else if(tx[11]==0x04) { write(fd215, "0", 1); write(fd214, "1", 1); write(fd213, "0", 1); write(fd212, "0", 1); } else if(tx[11]==0x05) { write(fd215, "0", 1); write(fd214, "1", 1); write(fd213, "0", 1); write(fd212, "1", 1); } else if(tx[11]==0x06) { write(fd215, "0", 1); write(fd214, "1", 1); write(fd213, "1", 1); write(fd212, "0", 1); } else if(tx[11]==0x07) { write(fd215, "0", 1); write(fd214, "1", 1); write(fd213, "1", 1); write(fd212, "1", 1); } else if(tx[11]==0x08) { write(fd215, "1", 1); write(fd214, "0", 1); write(fd213, "0", 1); write(fd212, "0", 1); } else if(tx[11]==0x09) { write(fd215, "1", 1); write(fd214, "0", 1); write(fd213, "0", 1); write(fd212, "1", 1); } else if(tx[11]==0x0a) { write(fd215, "1", 1); write(fd214, "0", 1); write(fd213, "1", 1); write(fd212, "0", 1); } write(fd307, "1", 1); write(fd307, "0", 1); transfer.len = recv_len; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &transfer); if (ret < 0) pabort("can't send spi message"); write(fd215, "1", 1); write(fd214, "1", 1); write(fd213, "1", 1); write(fd212, "0", 1); write(fd307, "1", 1); write(fd307, "0", 1); write(fd215, "0", 1); write(fd214, "0", 1); write(fd213, "0", 1); write(fd212, "0", 1); write(fd307, "1", 1); write(fd307, "0", 1); } //控显机数据帧头错误 else { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "HMI data err , data from HMI is %s", tx); m287_errSend(err_log_buf, err_log_buf_len); clear_err_buf(); } } //控显机数据长度错误 else { err_log_buf_len += snprintf(err_log_buf + err_log_buf_len, ERR_LOG_BUFF_SIZE - err_log_buf_len, "HMI data len err , len from HMI is %d,data is %s",cnt,tx); } m287_watchdog_keepalive();//喂狗 cnt = 0 ; clear_err_buf(); usleep(1000); //延时一毫秒 } close(fd); close(fd204); close(fd205); close(fd206); close(fd207); close(fd212); close(fd213); close(fd214); close(fd215); close(fd307); close(fd315); close(fd327); m287_socket_release(); m287_watchdog_closefd(); }
} static uint32_t write_command(uint16_t addr, unsigned nelem) { bool increment = true; return (addr << 16) | 0xB000 | (increment ? 0x800 : 0) | (nelem << 4); } static int do_pending(hm2_spi_t *this) { if(this->nbuf == 0) return 0; struct spi_ioc_transfer t; t = this->settings; t.tx_buf = t.rx_buf = (uint64_t)(uintptr_t)this->trxbuf; t.len = 4 * this->nbuf; int r = ioctl(this->fd, SPI_IOC_MESSAGE(1), &t); if(r < 0) { rtapi_print_msg(RTAPI_MSG_ERR, "hm2_spi: SPI_IOC_MESSAGE: %s\n", strerror(errno)); this->nbuf = 0; return -errno; } // because linux manages SPI chip select behind our backs, we can't know // whether to expect the "AAAAAAAA" cookie to appear in the first // word of the response. that's too bad, because checking this // would give a minimum level of detection of gross problems such as // a disconnected cable. uint32_t *buf = this->trxbuf; uint32_t **scatter = this->scatter; int i=0;
static PyObject* transfer(PyObject* self, PyObject* arg) { PyObject* transferTuple; if(!PyArg_ParseTuple(arg, "O", &transferTuple)) // "O" - Gets non-NULL borrowed reference to Python argument. return NULL; // As far as I can tell, it's mostly just copying arg[0] into transferTuple // and making sure at least one arg has been passed (I think) if(!PyTuple_Check(transferTuple)) // The only argument we support is a single tuple. pabort("Only accepts a single tuple as an argument\n"); uint32_t tupleSize = PyTuple_Size(transferTuple); // printf("size is %d\n", tupleSize); uint8_t tx[tupleSize]; uint8_t rx[tupleSize]; PyObject* tempItem; uint32_t i=0; while(i < tupleSize) { tempItem = PyTuple_GetItem(transferTuple, i); // if(!PyInt_Check(tempItem)) { pabort("non-integer contained in tuple\n"); } tx[i] = (uint8_t)PyInt_AsSsize_t(tempItem); i++; } struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = tupleSize, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, .cs_change = 1, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); transferTuple = PyTuple_New(tupleSize); for(i=0;i<tupleSize;i++) PyTuple_SetItem(transferTuple, i, Py_BuildValue("i",rx[i])); return transferTuple; } static PyObject* closeSPI(PyObject* self,PyObject* args) { close(fd); Py_RETURN_NONE; }
int main(int argc, char *argv[]) { FILE *file; //input spidev0_0 FILE *file2; //input spidev1_1 file = fopen("input0.txt", "a+"); //apend file file2 = fopen("input1.txt", "a+"); //initialize led gpio interface if (!bcm2835_init()) return 1; bcm2835_gpio_fsel(LED_PIN, BCM2835_GPIO_FSEL_OUTP); bcm2835_gpio_fsel(NEURON_SIGNAL, BCM2835_GPIO_FSEL_OUTP); int fd; int fd2; parse_opts(argc, argv); fd = open(device, O_RDWR); fd2 = open(device2, O_RDWR); /* * spi mode */ ioctl(fd, SPI_IOC_WR_MODE, &mode); ioctl(fd, SPI_IOC_RD_MODE, &mode); ioctl(fd2, SPI_IOC_WR_MODE, &mode); ioctl(fd2, SPI_IOC_RD_MODE, &mode); /* * bits per word */ ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &bits); ioctl(fd, SPI_IOC_RD_BITS_PER_WORD, &bits); ioctl(fd2, SPI_IOC_WR_BITS_PER_WORD, &bits); ioctl(fd2, SPI_IOC_RD_BITS_PER_WORD, &bits); /* * max speed hz */ ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed); ioctl(fd, SPI_IOC_RD_MAX_SPEED_HZ, &speed); ioctl(fd2, SPI_IOC_WR_MAX_SPEED_HZ, &speed); ioctl(fd2, SPI_IOC_RD_MAX_SPEED_HZ, &speed); printf("spi mode: %d\n", mode); printf("bits per word: %d\n", bits); printf("max speed: %d Hz (%d KHz)\n", speed, speed/1000); //Begin Transfer Function int counter = 0; uint16_t rx_buffer[1000]; uint16_t rx_buffer2[1000]; char str[16]; //transmit data uint8_t tx[] = { 0xFF, 0xFF, }; //initialize receive array uint8_t rx[ARRAY_SIZE(tx)] = {0, }; uint8_t rx2[ARRAY_SIZE(tx)] = {0, }; //setup transfer object struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; struct spi_ioc_transfer tr2 = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx2, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; //sets timer for the LED int timer_flag = 0; //sets timer between input signal pulses int input_flag = 0; //tells whether or not a peak has been detected on one of the channels int peak_flag1 = 0; int peak_flag2 = 0; //counts peaks when both flags are not high int peak_count1 = 0; int peak_count2 = 0; int nSig = 1; //Corresponds to NEURON_SIGNAL time_t startTime = time(NULL); bcm2835_gpio_write(NEURON_SIGNAL, HIGH); char timebuffer[30]; struct timeval tv; time_t curtime; while(1) { gettimeofday(&tv, NULL); curtime=tv.tv_sec; strftime(timebuffer,30,"%m-%d-%Y %T.",localtime(&curtime)); printf("%s%ld\n",timebuffer,tv.tv_usec); //send the voltage source to neurons if((nSig != 1) && (input_flag == 1) && ((time(NULL) - startTime) > 500)) bcm2835_gpio_write(NEURON_SIGNAL, HIGH); nSig = 1; //acquire data from first input 0_0 ioctl(fd, SPI_IOC_MESSAGE(1), &tr); /*incoming stream consists of 14 bits, MSB first. 2 setup bits followed by the 12 bit digital input. Following bits are garbage.*/ uint16_t received = ((uint16_t)rx[0] << 8) | (uint16_t)rx[1]; received = received & 0011111111111111; received = received >> 2; rx_buffer[counter] = received; //acquire data from second input 1_1 ioctl(fd2, SPI_IOC_MESSAGE(1), &tr2); /*incoming stream consists of 14 bits, MSB first. 2 setup bits followed by the 12 bit digital input. Following bits are garbage.*/ uint16_t received2 = ((uint16_t)rx2[0] << 8) | (uint16_t)rx2[1]; received2 = received & 0011111111111111; received2 = received >> 2; rx_buffer2[counter] = received2; if((nSig == 1) && (timer_flag == 0)){ if((rx_buffer[counter] > 100) && (peak_flag1 == 0)) peak_flag1 = 1; else if((rx_buffer[counter] < 100) && (peak_flag1 == 1)){ peak_count1 = peak_count1 + 1; peak_flag1 = 0; } if((rx_buffer2[counter] > 100) && (peak_flag2 == 0)) peak_flag2 = 1; else if(rx_buffer2[counter] < 100 && peak_flag2 == 1){ peak_count2 = peak_count2 + 1; peak_flag2 = 0; } rx_buffer[counter+1] = 9000 + peak_count1; counter = counter + 1; } if(((peak_count1 == 3) /*|| (peak_count2 == 3)*/) && (timer_flag == 0)){ bcm2835_gpio_write(LED_PIN, HIGH); //fprintf(file, "%s\n", "OH HERRO!!!!!!!"); startTime = time(NULL); //return current time in seconds timer_flag = 1; } if((timer_flag == 1) && (time(NULL)-startTime > 3)) { bcm2835_gpio_write(LED_PIN, LOW); timer_flag = 0; peak_count1 = 0; peak_count2 = 0; printf("HERROOOOOO!!!!!!!!!!\n"); bcm2835_gpio_write(NEURON_SIGNAL, LOW); nSig = 0; startTime = time(NULL); input_flag = 1; } counter = counter + 1; //dump data from buffer into file if (counter > 1000){ int i; i = 0; while(i++ < 1000){ //fprintf(file, "Count: %d\n", peak_count1); //must move this to be inputted into the array to get realtime data //print 0_0 data into the first file fprintf(file, "%d\n", rx_buffer[i]); //print 1_1 data into the second file fprintf(file2, "%d\n", rx_buffer2[i]); //fwrite(rx_buffer, 16, 1000, file); //for future implementations... slightly faster } counter = 0; } } fclose(file); return 1; }
int main(int argc, char *argv[]) { __u8 miso[MAX_LENGTH]; __u8 mosi[MAX_LENGTH]; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)mosi, .rx_buf = (unsigned long)miso, .delay_usecs = 1, .speed_hz = 8000000, .bits_per_word = 8, .len = 1, }; char *device_name = NULL; char *mosi_str = "FF"; int opt_i = 0; int c; int fd; int ret; static struct option long_opts[] = { { "device", required_argument, 0, 'd' }, { "length", required_argument, 0, 'l' }, { "mosi", required_argument, 0, 'm' }, { "speed", required_argument, 0, 's' }, { "help", no_argument, 0, '?' }, { 0, 0, 0, 0 }, }; while ((c = getopt_long(argc, argv, "d:l:m:s:?", long_opts, &opt_i)) != -1) { switch (c) { case 'd': device_name = optarg; break; case 'l': tr.len = MIN(atoi(optarg), MAX_LENGTH); break; case 'm': mosi_str = optarg; break; case 's': tr.speed_hz = atoi(optarg); break; case '?': print_usage(); return 0; } } if (!device_name) { fprintf(stderr, "Missing required device argument.\n"); print_usage(); return -1; } fd = open(device_name, O_RDWR); if (fd == -1) { fprintf(stderr, "main: opening device file: %s: %s\n", device_name, strerror(errno)); return -1; } string2hex(mosi_str, mosi, tr.len); printf("Sending to %s at %ld Hz\n", device_name, tr.speed_hz); ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret == -1) fprintf(stderr, "main: ioctl SPI_IOC_MESSAGE: %s: %s\n", device_name, strerror(errno)); else print_spi_transaction(miso, mosi, tr.len); close(fd); return ret; }
static PyObject * SpiDev_xfer2(SpiDevObject *self, PyObject *args) { int status; uint16_t delay_usecs = 0; uint32_t speed_hz = 0; uint8_t bits_per_word = 0; uint16_t ii, len; PyObject *obj; PyObject *seq; struct spi_ioc_transfer xfer; Py_BEGIN_ALLOW_THREADS memset(&xfer, 0, sizeof(xfer)); Py_END_ALLOW_THREADS uint8_t *txbuf, *rxbuf; char wrmsg_text[4096]; if (!PyArg_ParseTuple(args, "O|IHB:xfer2", &obj, &speed_hz, &delay_usecs, &bits_per_word)) return NULL; seq = PySequence_Fast(obj, "expected a sequence"); len = PySequence_Fast_GET_SIZE(seq); if (!seq || len <= 0) { PyErr_SetString(PyExc_TypeError, wrmsg_list0); return NULL; } if (len > SPIDEV_MAXPATH) { snprintf(wrmsg_text, sizeof(wrmsg_text) - 1, wrmsg_listmax, SPIDEV_MAXPATH); PyErr_SetString(PyExc_OverflowError, wrmsg_text); return NULL; } Py_BEGIN_ALLOW_THREADS txbuf = malloc(sizeof(__u8) * len); rxbuf = malloc(sizeof(__u8) * len); Py_END_ALLOW_THREADS for (ii = 0; ii < len; ii++) { PyObject *val = PySequence_Fast_GET_ITEM(seq, ii); #if PY_MAJOR_VERSION < 3 if (PyInt_Check(val)) { txbuf[ii] = (__u8)PyInt_AS_LONG(val); } else #endif { if (PyLong_Check(val)) { txbuf[ii] = (__u8)PyLong_AS_LONG(val); } else { snprintf(wrmsg_text, sizeof (wrmsg_text) - 1, wrmsg_val, val); PyErr_SetString(PyExc_TypeError, wrmsg_text); free(txbuf); free(rxbuf); return NULL; } } } if (PyTuple_Check(obj)) { Py_DECREF(seq); seq = PySequence_List(obj); } Py_BEGIN_ALLOW_THREADS xfer.tx_buf = (unsigned long)txbuf; xfer.rx_buf = (unsigned long)rxbuf; xfer.len = len; xfer.delay_usecs = delay_usecs; xfer.speed_hz = speed_hz ? speed_hz : self->max_speed_hz; xfer.bits_per_word = bits_per_word ? bits_per_word : self->bits_per_word; status = ioctl(self->fd, SPI_IOC_MESSAGE(1), &xfer); Py_END_ALLOW_THREADS if (status < 0) { PyErr_SetFromErrno(PyExc_IOError); free(txbuf); free(rxbuf); return NULL; } for (ii = 0; ii < len; ii++) { PyObject *val = Py_BuildValue("l", (long)rxbuf[ii]); PySequence_SetItem(seq, ii, val); } // WA: // in CS_HIGH mode CS isnt pulled to low after transfer // reading 0 bytes doesn't really matter but brings CS down // tomdean: // Stop generating an extra CS except in mode CS_HOGH if (self->mode & SPI_CS_HIGH) status = read(self->fd, &rxbuf[0], 0); Py_BEGIN_ALLOW_THREADS free(txbuf); free(rxbuf); Py_END_ALLOW_THREADS if (PyTuple_Check(obj)) { PyObject *old = seq; seq = PySequence_Tuple(seq); Py_DECREF(old); } return seq; }
unsigned long Swift_SPI_IOC_MESSAGE(int arg) { return SPI_IOC_MESSAGE(arg); }
//*------------------------------------------------------------------------------------------------ //* 函数名称 : ReadAdcSampling //* 功能描述 : 读ADC的采样值 //* 入口参数 : <fd>[in] 指定ADC设备的句柄(即OpenAdc()的返回值) //* : <channel>[in] 指定需要读取的采样通道号 //* : 指定通道号>0: 读取指定的某单一通道 //* : 指定通道号=0: 读取所有通道 //* : <buffer>[in/out] 读取的采样值缓冲区 //* : <len>[in/out] 指定读取的采样值数,并返回实际读取的采样值数目 //* : 读取单一通道时,len指定读取该通道的总采样值个数 //* : 同时读取所有通道时,len指定针对每一通道的采样值个数 //* : <timesout>[in] 目前不支持 //* 返回值 : 返回操作状态信息(0:成功, -1:失败) //* 备 注 : 1、分配采样值存放缓冲区时,一定要足够存放指定的采样值个数: //* : 读取单一通道时: 缓冲区大小 >= len * sizeof(cyg_adc_sample) //* : 读取所有通道时: 缓冲区大小 >= TOTALCHAN * len * sizeof(cyg_adc_sample) //*------------------------------------------------------------------------------------------------ int ReadAdcSampling(int fd, unsigned int channel, cyg_adc_sample * buffer, unsigned int *len, int timesout) { int err = 0; unsigned int length = 0, ret = 0, i = 0,j=0; struct spi_ioc_transfer xfer; unsigned char wrbuf[2],rdbuf[2]; if (!buffer) return -1; if(channel>TOTALADCCHAN) return -1; length = (*len) ; memset(&xfer, 0, sizeof xfer); memset(wrbuf, 0, sizeof wrbuf); memset(rdbuf, 0, sizeof rdbuf); //采集指定通道 if(channel) { wrbuf[0] = 0x0; wrbuf[1] = __ChanCmd[channel-1]; xfer.tx_buf = (unsigned long) wrbuf; xfer.rx_buf = (unsigned long) rdbuf; xfer.len = 2; //first sample ignored ret = ioctl(fd, SPI_IOC_MESSAGE(1), &xfer); if (ret == 1) { printf("can't send spi message"); return -1; } // for(i=0;i<(length+1);i++) { ret = ioctl(fd, SPI_IOC_MESSAGE(1), &xfer); if (ret == 1) { printf("can't send spi message"); return -1; } if(i>0) buffer[i-1] = ((unsigned short)rdbuf[1]<<8 | rdbuf[0]); } } else { wrbuf[0] = 0x0; wrbuf[1] = __ChanCmd[0]; xfer.tx_buf = (unsigned long) wrbuf; xfer.rx_buf = (unsigned long) rdbuf; xfer.len = 2; // for(i=0;i<length;i++) { for(j=0;j<TOTALADCCHAN;j++) { wrbuf[1] = __ChanCmd[j]; //first read ret = ioctl(fd, SPI_IOC_MESSAGE(1), &xfer); if (ret == 1) { printf("can't send spi message"); return -1; } if(j>0) buffer[i*TOTALADCCHAN + j-1] = ((unsigned short)rdbuf[1]<<8 | rdbuf[0]); } //last channel ret = ioctl(fd, SPI_IOC_MESSAGE(1), &xfer); if (ret == 1) { printf("can't send spi message"); return -1; } buffer[i*TOTALADCCHAN + TOTALADCCHAN -1] = ((unsigned short)rdbuf[1]<<8 | rdbuf[0]); } } return err; }
static void status() { int ret; uint8_t tx[2]; uint8_t rx[2]; tx[0] = 0x04; tx[1] = 0x05; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); printf("Charging = %x\n", (rx[1] >> 2) & 1); printf("Power Fail = %x\n", (rx[1] >> 3) & 1); printf("DCDIV = %x\n", (rx[1] >> 4) & 1); printf("Low Power = %x\n", (rx[1] >> 5) & 1); printf("Fault = %x\n", (rx[1] >> 6) & 1); } static void charge(int battery) { int ret; uint8_t tx[1]; uint8_t rx[1]; tx[0] = battery | CHARGE_CMD; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); } static void voltage_dac(double voltage) { int ret; int vdac; int i; uint8_t tx[2]; uint8_t rx[2]; tx[0] = 0x01; tx[1] = 0x08; vdac = (int) floor(((voltage-.8)/32.752) * 2047); for(i=0;i<10;i++) { if(i<7) tx[0] |= (vdac & (1 << i)) ? (1 << (7-i)) : 0; else tx[1] |= (vdac & (1 << i)) ? (1 << (14-i)) : 0; } struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); do { tx[0] = 0x01; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = 1, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); } while(rx[0]==0xFF); } static void current_dac(double current, int low_current) { int ret; int cdac; int i; uint8_t tx[2]; uint8_t rx[2]; tx[0] = 0x01; tx[1] = 0x00; cdac = (int) (((current)*1023*0.05)/0.1023); for(i=0;i<10;i++) { if(i<7) tx[0] |= (cdac & (1 << i)) ? (1 << (7-i)) : 0; else tx[1] |= (cdac & (1 << i)) ? (1 << (14-i)) : 0; } tx[1] |= (low_current) ? 0x10 : 0x00; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); do { tx[0] = 0x01; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = 1, .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); } while(rx[0]==0xFF); } void charge_timer(int i) { if(battery_sel) charge(battery_sel); signal(SIGALRM, charge_timer); } void init_timer() { tout_val.it_interval.tv_sec = 1; /* Next Value in seconds */ tout_val.it_interval.tv_usec = 1; /* Next Value in microseconds */ tout_val.it_value.tv_sec = 1; /* Current Value in seconds */ tout_val.it_value.tv_usec = 1; /* Current Value in microseconds */ setitimer(ITIMER_REAL, &tout_val, 0); signal(SIGALRM, charge_timer); } int main(int argc, char *argv[]) { int ret = 0; int done = 0; int low_current = 0; char key; double voltage, current; fd = open(device, O_RDWR); if (fd < 0) pabort("Cannot open device"); ret = ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &bits); if (ret == -1) pabort("Cannot set bits per word"); ret = ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &speed); if (ret == -1) pabort("Cannot set max speed hz"); init_timer(); printf("LTC1960 Battery Charger Demo\n\n"); current = 2.0; voltage = 12.8; voltage_dac(voltage); current_dac(current, low_current); while(!done) { status(); printf("\n"); printf("Battery 1 is %s.\n", (battery_sel==CHARGE_BAT1) ? "charging" : "not charging"); printf("Battery 2 is %s.\n", (battery_sel==CHARGE_BAT2) ? "charging" : "not charging"); printf("Current = %lfA\n",current); printf("Voltage = %lfV\n",voltage); printf("Low Current Mode %s.\n", (low_current) ? "ON" : "OFF"); printf("\n"); printf("1: Set battery voltage.\n"); printf("2: Set battery current.\n"); printf("3: Charge battery 1. \n"); printf("4: Charge battery 2. \n"); printf("5: Toggle Low Current Mode. \n"); printf("6: Stop Charging. \n"); printf("7: Print smart battery info.\n"); printf("q: Quit Program\n"); printf("\nInput: "); do { scanf("%c", &key); } while(key == '\n'); printf("\n\n"); switch(key) { case '1': printf("Voltage = "); scanf("%lf", &voltage); voltage_dac(voltage); break; case '2': printf("Current = "); scanf("%lf", ¤t); current_dac(current, low_current); break; case '3': battery_sel = CHARGE_BAT1; charge(battery_sel); break; case '4': battery_sel = CHARGE_BAT2; charge(battery_sel); break; case '5': low_current ^=1; current_dac(current, low_current); break; case '6': battery_sel = 0; sleep(1); break; case '7': system("cat /sys/class/power_supply/battery/uevent"); break; case 'q': done = 1; break; default: continue; } } close(fd); return ret; }
/** * @brief configure lms6002's Frequency. * * @param[in] fd spi file descriptor * @param[in] freq frequency to be configured * @param[in] channel RF channel * @retval void * */ int snowleo_sdr_set_freq(int fd, unsigned int freq, uint8_t channel) { int ret; unsigned char value; unsigned int value2, net_data = freq; unsigned int NINT,NFRAC; double x = (double)net_data/(double)1000000000.0; printf("x = %f\n", x); if(x >= 3.72) return -1; if(x>0.2325&&x<0.285625) value = 0x27;//100111 else if(x>0.285625&&x<0.336875) value = 0x2f;//101111 else if(x>0.336875&&x<0.405) value = 0x37;//110111 else if(x>0.405&&x<0.465) value = 0x3f;//111111 else if(x>0.465&&x<0.57125) value = 0x26;//100110 else if(x>0.57125&&x<0.67375) value = 0x2e;//101110 else if(x>0.67375&&x<0.81) value = 0x36;//110110 else if(x>0.81&&x<0.93) value = 0x3e;//111110 else if(x>0.93&&x<1.1425) value = 0x25;//100101 else if(x>1.1425&&x<1.3475) value = 0x2d;//101101 else if(x>1.3475&&x<1.62) value = 0x35;//110101 else if(x>1.62&&x<1.86) value = 0x3d;//111101 else if(x>1.86&&x<2.285) value = 0x24;//100100 else if(x>2.285&&x<2.695) value = 0x2c;//101100 else if(x>2.695&&x<3.24) value = 0x34;//110100 else if(x>3.24&&x<3.72) value = 0x3c;//111100 else value = 0; value2 = 2<<((value&0x07)-4); //printf("value = 0x%x,value2 = %d,(value&0x07)-3 = %d\n",value, value2,(value&0x07)-3); NINT= (double)value2*(double)net_data/30.72/1000000.0; NFRAC = (2<<22)*((double)value2*(double)net_data/30.72/1000000.0-NINT); printf("NINT = %d; NFRAC = %d\n", NINT,NFRAC); uint8_t rf_en = 0; snowleo_spi_read(fd, 0x05, &rf_en); if(channel == RF_TX_CHANNEL) rf_en = rf_en | 0x08; else rf_en = rf_en | 0x04; uint8_t tx[] = { 0x05|(0x1<<7), rf_en, 0x09|(0x1<<7), 0x85, // (0x10+channel)|(0x1<<7), (uint8_t)(NINT>>1), (0x11+channel)|(0x1<<7), (((uint8_t)NINT&0x01)<<7)|((uint8_t)(NFRAC>>16)&0x7f), (0x12+channel)|(0x1<<7), (uint8_t)(NFRAC>>8), (0x13+channel)|(0x1<<7), (uint8_t)(NFRAC), (0x15+channel)|(0x1<<7), (value<<2)|(0x01), //(0x15+channel)|(0x1<<7), (value<<2)|(0x10), (0x19+channel)|(0x1<<7), (0x2<<6)|64, (0x5a)|(0x1<<7), 0xb0, }; struct spi_ioc_transfer tr_freq = { .tx_buf = (unsigned long)tx, .rx_buf = 0, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr_freq); if (ret < 1) pabort("can't send spi message"); if(channel == RF_RX_CHANNEL) { uint8_t send_read_rx_reg[] = { 0x05, 0x09, // (0x10+channel), (0x11+channel), (0x12+channel), (0x13+channel), (0x15+channel), (0x19+channel), 0x65, 0x75, }; uint8_t recv_read_rx_reg[] = { 0, }; struct spi_ioc_transfer tr1[2]; memset(tr1, 0, sizeof(tr1)); int i = 0; for(i = 0; i< ARRAY_SIZE(send_read_rx_reg); i++){ tr1[0].tx_buf = (unsigned long)&send_read_rx_reg[i]; tr1[0].len = 1; tr1[1].rx_buf = (unsigned long)&recv_read_rx_reg[i]; tr1[1].len = 1; ret = ioctl(fd, SPI_IOC_MESSAGE(2), tr1); if (ret < 1) pabort("can't send spi message"); //printf("reg[0x%x] = 0x%x\n", send_read_rx_reg[i], recv_read_rx_reg[i]); } }else{ uint8_t send_read_tx_reg[] = { 0x05, 0x09, (0x10+channel), (0x11+channel), (0x12+channel), (0x13+channel), (0x15+channel), (0x19+channel), 0x41, 0x45, 0x44, }; uint8_t recv_read_tx_reg[] = { 0, }; struct spi_ioc_transfer tr1[2]; memset(tr1, 0, sizeof(tr1)); int i = 0; for(i = 0; i< ARRAY_SIZE(send_read_tx_reg); i++){ tr1[0].tx_buf = (unsigned long)&send_read_tx_reg[i]; tr1[0].len = 1; tr1[1].rx_buf = (unsigned long)&recv_read_tx_reg[i]; tr1[1].len = 1; ret = ioctl(fd, SPI_IOC_MESSAGE(2), tr1); if (ret < 1) pabort("can't send spi message"); //printf("reg[0x%x] = 0x%x\n", send_read_tx_reg[i], recv_read_tx_reg[i]); } } /*************************Calibrate VCO*************************************/ uint8_t Vtune_H = 0; uint8_t Vtune_L = 0; uint8_t cmin = 0; uint8_t cmax = 0; uint8_t incr_value = 31, temp_value = 0; spi_write_vco(fd, 31, channel); spi_check_vco(fd, &temp_value, channel); Vtune_H = (temp_value&0x80)>>7; Vtune_L = (temp_value&0x40)>>6; printf("Vtune_H=%d Vtune_L=%d\n", Vtune_H, Vtune_L); if(Vtune_H==0&&Vtune_L==0){ do{ incr_value-=1; spi_write_vco(fd, incr_value, channel); spi_check_vco(fd, &temp_value, channel); Vtune_H = (temp_value&0x80)>>7; Vtune_L = (temp_value&0x40)>>6; //}while((Vtune_H!=1&&Vtune_L!=0&&incr_value>0)); }while((Vtune_H!=1&&Vtune_L==0&&incr_value>0)); cmin = incr_value; incr_value = 31; do{ incr_value+=1; spi_write_vco(fd, incr_value, channel); spi_check_vco(fd, &temp_value, channel); Vtune_H = (temp_value&0x80)>>7; Vtune_L = (temp_value&0x40)>>6; //}while((Vtune_H!=0&&Vtune_L!=1&&incr_value<63)); }while((Vtune_H==0&&Vtune_L!=1&&incr_value<63)); cmax = incr_value; incr_value = round(((1.9-2.5)*(cmax-cmin)/(2.5-0.5))+cmax); } else if(Vtune_H==0&&Vtune_L==1){ do{ incr_value-=1; spi_write_vco(fd, incr_value, channel); spi_check_vco(fd, &temp_value, channel); Vtune_H = (temp_value&0x80)>>7; Vtune_L = (temp_value&0x40)>>6; //}while((Vtune_H!=0&&Vtune_L!=0)); }while((Vtune_H==0&&Vtune_L!=0)); cmin = incr_value; do{ incr_value-=1; spi_write_vco(fd, incr_value, channel); spi_check_vco(fd, &temp_value, channel); Vtune_H = (temp_value&0x80)>>7; Vtune_L = (temp_value&0x40)>>6; //}while((Vtune_H!=1&&Vtune_L!=0&&incr_value>0)); }while((Vtune_H!=1&&Vtune_L==0&&incr_value>0)); cmax = incr_value; incr_value = round(((1.9-2.5)*(cmax-cmin)/(2.5-0.5))+cmax); } else if(Vtune_H==1&&Vtune_L==0){
/** * @brief lms6002 initial operation function. * * @param[in] fd spi file descriptor * @retval void * */ void transfer(int fd) { int ret; uint8_t tx[] = { 0x82,0x1f, 0x83,0x08, 0x85,0x3e, 0x86,0x0d, 0x87,0x00, 0x88,0x00, 0x89,0x85, 0x8a,0x00, 0x8b,0x08, /*0x90,0x4e, tx freq 2417M 0x91,0xad, 0x92,0xaa, 0x93,0xaa, 0x94,0x88, 0x95,0xb1, 0x96,0x8c, 0x97,0xfe, 0x98,0x40, 0x99,0x98,*/ 0x90,0x3d, 0x91,0xd9, 0x92,0x55, 0x93,0x55, 0x94,0x88, 0x95,0x91, 0x96,0x8c, 0x97,0xfe, 0x98,0x40, 0x99,(2<<6|14), /*0xa0,0x4e, //rx freq 2417 0xa1,0xad, 0xa2,0xaa, 0xa3,0xaa, 0xa4,0x88, 0xa5,0xb1, 0xa6,0x8c, 0xa7,0xfe, 0xa8,0x40, 0xa9,0x98,*/ 0xa0,0x3d, 0xa1,0xd9, 0xa2,0x55, 0xa3,0x55, 0xa4,0x88, 0xa5,0x91, 0xa6,0x8c, 0xa7,0xfe, 0xa8,0x40, 0xa9,(2<<6|14), 0xb2,0x1f, 0xb3,0x09, 0xb4,0x02, 0xb5,0x0c, 0xd2,0x1f, 0xd3,0x08, 0xd4,0x02, 0xd5,0x0c, 0xd6,0x30, 0xd7,0xd4, 0xd8,0x00, 0xd9,0x29, 0xda,0xb0, 0xdb,0x00, 0xdc,0x00, 0xdd,0x00, 0xde,0x00, 0xdf,0x1f, 0xc0,0x02, 0xc1,0x15, 0xc2,0x80, 0xc3,0x80, 0xc4,0x0b, 0xc5,0x00, 0xc6,0x00, 0xc7,0x40, 0xc8,0x0c, 0xc9,0x0c, 0xca,0x18, 0xcb,0xff, 0xcc,0x00, 0xcd,0x00, 0xce,0x00, 0xcf,0x00, 0xe2,0x1f, 0xe3,0x08, 0xe4,0x1e, 0xe5,0x01, 0xe6,0x00, 0xe7,0x00, 0xe8,0x01, 0xf0,0x01, 0xf1,0x80, 0xf2,0x80, 0xf3,0x00, 0xf4,0x00, 0xf5,0xd0, 0xf6,0x78, 0xf7,0x00, 0xf8,0x1c, 0xf9,0x37, 0xfa,0x77, 0xfb,0x77, 0xfc,0x18 }; uint8_t rx[ARRAY_SIZE(tx)] = {0, }; struct spi_ioc_transfer tr = { .tx_buf = (unsigned long)tx, .rx_buf = (unsigned long)rx, .len = ARRAY_SIZE(tx), .delay_usecs = delay, .speed_hz = speed, .bits_per_word = bits, }; ret = ioctl(fd, SPI_IOC_MESSAGE(1), &tr); if (ret < 1) pabort("can't send spi message"); } /** * @brief check lms6002's vco. * * @param[in] fd spi file descriptor * @param[out] value read back data * @param[in] channel RF channel * @retval void * */ static void spi_check_vco(int fd, uint8_t *value, uint8_t channel) { int ret; uint8_t tx1[] = {0x1A+channel,}; uint8_t rx1[] = {0,}; struct spi_ioc_transfer tr1[2]; memset(tr1, 0, sizeof(tr1)); tr1[0].tx_buf = (unsigned long)tx1; tr1[0].len = ARRAY_SIZE(tx1); tr1[1].rx_buf = (unsigned long)rx1; tr1[1].len = ARRAY_SIZE(tx1); ret = ioctl(fd, SPI_IOC_MESSAGE(2), tr1); if (ret < 1) pabort("can't send spi message"); //printf("rx1 = 0x%x\n", rx1[0]); *value = rx1[0]; }
int main(int argc, char* argv[]) { int fd; int ret; int i; int nb; unsigned int cmd=0; unsigned int level=0; uint8_t spi_config=0; uint8_t spi_bits=8; uint32_t spi_speed; //=32768; spi_speed=32768000; // this can take a few specific values spi_speed=1310720; // we have some longer wiring spi_t spi; unsigned char txbuf[4099]; unsigned char rxbuf[4099]; int j; unsigned int servo[8]; if (argc>1) { sscanf(argv[1], "%d", &cmd); } if (argc>2) { sscanf(argv[2], "%d", &level); } //printf("cmd is %d\n", cmd); //fprintf(stderr, "Hello stderr from app\n"); //fprintf(stdout, "Hello stdout from app\n"); //printf("Hello printf from app\n"); fd=open(device, O_RDWR); if (fd<0) { fprintf(stderr, "Error opening device: %s\n", strerror(errno)); exit(1); } //spi_config |= SPI_CS_HIGH; ret=ioctl(fd, SPI_IOC_WR_MODE, &spi_config); if (ret<0) { fprintf(stderr, "Error setting SPI write mode: %s\n", strerror(errno)); exit(1); } ret=ioctl(fd, SPI_IOC_RD_MODE, &spi_config); if (ret<0) { fprintf(stderr, "Error setting SPI read mode: %s\n", strerror(errno)); exit(1); } ret=ioctl(fd, SPI_IOC_WR_BITS_PER_WORD, &spi_bits); if (ret<0) { fprintf(stderr, "Error setting SPI write bits: %s\n", strerror(errno)); exit(1); } ret=ioctl(fd, SPI_IOC_RD_BITS_PER_WORD, &spi_bits); if (ret<0) { fprintf(stderr, "Error setting SPI read bits: %s\n", strerror(errno)); exit(1); } ret=ioctl(fd, SPI_IOC_WR_MAX_SPEED_HZ, &spi_speed); if (ret<0) { fprintf(stderr, "Error setting SPI write speed: %s\n", strerror(errno)); exit(1); } ret=ioctl(fd, SPI_IOC_RD_MAX_SPEED_HZ, &spi_speed); if (ret<0) { fprintf(stderr, "Error setting SPI read speed: %s\n", strerror(errno)); exit(1); } // clean receive buffer for (i=0; i<20; i++) { rxbuf[i]=0; } // send to tag 0x03 txbuf[0]=0x03; txbuf[1]=0x0f; txbuf[2]=0xa0; spi.len=4003; nb=4003; if (cmd==3) // request trace { txbuf[0]=0x03; txbuf[1]=0x00; txbuf[2]=0x01; spi.len=4; nb=4; } else if (cmd==0) // retrieve trace { //delay_ms(99); txbuf[0]=0x00; txbuf[1]=0x03; txbuf[2]=0xe8; spi.len=1003; nb=1003; } else if (cmd==4) // set timebase { txbuf[0]=0x04; txbuf[1]=0x00; txbuf[2]=0x01; txbuf[3]=level; spi.len=4; nb=4; } else if (cmd==6) // set triglevel { if (level>255) level=255; txbuf[0]=0x06; txbuf[1]=0x00; txbuf[2]=0x01; txbuf[3]=level; spi.len=4; nb=4; } else if (cmd==8) // set trigdir { txbuf[0]=0x08; txbuf[1]=0x00; txbuf[2]=0x01; txbuf[3]=level; spi.len=4; nb=4; } else if (cmd==10) // set trigmode (cont/norm/single) { txbuf[0]=0x0a; txbuf[1]=0x00; txbuf[2]=0x01; txbuf[3]=level; spi.len=4; nb=4; } spi.delay_usecs=0; spi.speed_hz=spi_speed; spi.bits_per_word=spi_bits; spi.cs_change=0; spi.tx_buf=(unsigned long)txbuf; spi.rx_buf=(unsigned long)rxbuf; ret=ioctl(fd, SPI_IOC_MESSAGE(1), &spi); if (ret<0) { fprintf(stderr, "Error performing SPI exchange: %s\n", strerror(errno)); exit(1); } fprintf(stdout, "%02x", rxbuf[0]); for (i=1; i<(nb-3); i++) { fprintf(stdout, ",%02x", rxbuf[i]); } fprintf(stdout, "\n"); close(fd); return(0); }
void lcd_writedata(unsigned char c) //write data { int ret; GPIO_SET = 1<<LCD_RS_GPIO; //set RS high for writing data txbuf[0]=c; spi.len=1; spi.delay_usecs=0; spi.speed_hz=spi_speed; spi.bits_per_word=spi_bits; spi.cs_change=0; spi.tx_buf=(unsigned long)txbuf; spi.rx_buf=(unsigned long)rxbuf; ret=ioctl(lcd_fd, SPI_IOC_MESSAGE(1), &spi); if (ret<0) { fprintf(stderr, "Error performing SPI exchange: %s\n", strerror(errno)); exit(1); } }