我们将从 ARM 嵌入式 Ubuntu 14.04 (内核3.14)更新到 ARM 嵌入式 Ubuntu 16.04。 在第一个平台上、我们使用 SPIDEV 访问芯片、没有任何问题。 在 Ubuntu 16.04 (Kernel 4.9.59)平台上、在 ioctl SPI_IOC_MESSAGE 之后出现 EINVAL 错误。 内核来自 TI 的 SDK 4.02.00.09。
调用 ioctl 的代码如下所示:请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
器件型号:PROCESSOR-SDK-AM335X 工具/软件:Linux
SpiComm_t::传输(int i4Length){
int ret =-1;
m_tr.len = i4Length;
ret = ioctl (m_FD、SPI_IOC_MESSAGE (1)、&m_tr);
if (ret){
printf ("SPI IOCTL 错误%s\n"、strerror (errno));}
return;
}
SpiComm_t::SpiComm_t( uint32_t w4Bus,
uint32_t w4ChipSelect ) :
m_fd(-1),
m_b0IsInitialized(false),
m_w4Bus(w4Bus),
m_w4ChipSelect(w4ChipSelect)
{
m_tr.tx_buf = (unsigned long)m_c1BufTx;
m_tr.rx_buf = (unsigned long)m_c1BufRx;
m_tr.delay_usecs = SX_1276_SPI_DELAY;
m_tr.speed_hz = SX_1276_SPI_SPEED;
m_tr.bits_per_word = SX_1276_SPI_BITS;
}
m_tr and m_c1BufTx are defined as:
spi_ioc_transfer m_tr;
uint8_t m_c1BufTx[0xff+1];
uint8_t m_c1BufRx[0xff+1];
调用传递函数的代码为:
// Reset memory (Optional... Helps diagnose failures to read.)
memset(m_c1BufTx, 0xFF, sizeof(m_c1BufTx));
// Put address
m_c1BufTx[0] = address;
// Reset memory (optional...)
memset(m_c1BufRx, 0xFF, sizeof(m_c1BufRx));
// Invoke ioctl transaction
int result = Transfer(size+1);
我们使用的是 TI SDK 4.0中的内核4.9.59。 我已将 EINVAL 跟踪到 spidev.c 驱动程序、但无法理解我为什么会遇到错误。
spidev.c 代码为:
tmp = _IOC_SIZE(cmd);
if ((tmp % sizeof(struct spi_ioc_transfer)) != 0)
return ERR_PTR(-EINVAL);
*n_ioc = tmp / sizeof(struct spi_ioc_transfer);
if (*n_ioc == 0)
return NULL;
如果有任何帮助,将不胜感激。