Alex_Golubev 0 31 августа, 2017 Опубликовано 31 августа, 2017 (изменено) · Жалоба Привет. Столкнулся с проблемой передачи и приема данных по spi. Инициализация spi: void MX_SPI4_Init(void) { hspi4.Instance = SPI4; hspi4.Init.Mode = SPI_MODE_MASTER; hspi4.Init.Direction = SPI_DIRECTION_2LINES; hspi4.Init.DataSize = SPI_DATASIZE_8BIT; hspi4.Init.CLKPolarity = SPI_POLARITY_LOW; hspi4.Init.CLKPhase = SPI_PHASE_1EDGE; hspi4.Init.NSS = SPI_NSS_SOFT; hspi4.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_8; hspi4.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi4.Init.TIMode = SPI_TIMODE_DISABLED; hspi4.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLED; hspi4.Init.CRCPolynomial = 10; HAL_SPI_Init(&hspi4); } void HAL_SPI_MspInit(SPI_HandleTypeDef* hspi) { GPIO_InitTypeDef GPIO_InitStruct; if(hspi->Instance==SPI3) { /* USER CODE BEGIN SPI3_MspInit 0 */ /* USER CODE END SPI3_MspInit 0 */ /* Peripheral clock enable */ __SPI3_CLK_ENABLE(); /**SPI3 GPIO Configuration PC11 ------> SPI3_MISO PC12 ------> SPI3_MOSI PB3 ------> SPI3_SCK */ GPIO_InitStruct.Pin = GPIO_PIN_11|GPIO_PIN_12; GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; GPIO_InitStruct.Alternate = GPIO_AF6_SPI3; HAL_GPIO_Init(GPIOC, &GPIO_InitStruct); GPIO_InitStruct.Pin = GPIO_PIN_3; GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; GPIO_InitStruct.Alternate = GPIO_AF6_SPI3; HAL_GPIO_Init(GPIOB, &GPIO_InitStruct); /* USER CODE BEGIN SPI3_MspInit 1 */ /* USER CODE END SPI3_MspInit 1 */ } else if(hspi->Instance==SPI4) { /* USER CODE BEGIN SPI4_MspInit 0 */ /* USER CODE END SPI4_MspInit 0 */ /* Peripheral clock enable */ __SPI4_CLK_ENABLE(); /**SPI4 GPIO Configuration PE2 ------> SPI4_SCK PE5 ------> SPI4_MISO PE6 ------> SPI4_MOSI */ GPIO_InitStruct.Pin = GPIO_PIN_2|GPIO_PIN_5|GPIO_PIN_6; GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; GPIO_InitStruct.Alternate = GPIO_AF5_SPI4; HAL_GPIO_Init(GPIOE, &GPIO_InitStruct); /* Peripheral DMA init*/ hdma_spi4_rx.Instance = DMA2_Stream3; hdma_spi4_rx.Init.Channel = DMA_CHANNEL_5; hdma_spi4_rx.Init.Direction = DMA_PERIPH_TO_MEMORY; hdma_spi4_rx.Init.PeriphInc = DMA_PINC_DISABLE; hdma_spi4_rx.Init.MemInc = DMA_MINC_ENABLE; hdma_spi4_rx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE; hdma_spi4_rx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE; hdma_spi4_rx.Init.Mode = DMA_NORMAL; hdma_spi4_rx.Init.Priority = DMA_PRIORITY_HIGH; hdma_spi4_rx.Init.FIFOMode = DMA_FIFOMODE_DISABLE; HAL_DMA_Init(&hdma_spi4_rx); __HAL_LINKDMA(hspi,hdmarx,hdma_spi4_rx); hdma_spi4_tx.Instance = DMA2_Stream4; hdma_spi4_tx.Init.Channel = DMA_CHANNEL_5; hdma_spi4_tx.Init.Direction = DMA_MEMORY_TO_PERIPH; hdma_spi4_tx.Init.PeriphInc = DMA_PINC_DISABLE; hdma_spi4_tx.Init.MemInc = DMA_MINC_ENABLE; hdma_spi4_tx.Init.PeriphDataAlignment = DMA_PDATAALIGN_BYTE; hdma_spi4_tx.Init.MemDataAlignment = DMA_MDATAALIGN_BYTE; hdma_spi4_tx.Init.Mode = DMA_NORMAL; hdma_spi4_tx.Init.Priority = DMA_PRIORITY_HIGH; hdma_spi4_tx.Init.FIFOMode = DMA_FIFOMODE_DISABLE; HAL_DMA_Init(&hdma_spi4_tx); __HAL_LINKDMA(hspi,hdmatx,hdma_spi4_tx); /* USER CODE BEGIN SPI4_MspInit 1 */ /* USER CODE END SPI4_MspInit 1 */ } else if(hspi->Instance==SPI5) { /* USER CODE BEGIN SPI5_MspInit 0 */ /* USER CODE END SPI5_MspInit 0 */ /* Peripheral clock enable */ __SPI5_CLK_ENABLE(); /**SPI5 GPIO Configuration PF7 ------> SPI5_SCK PF8 ------> SPI5_MISO PF9 ------> SPI5_MOSI */ GPIO_InitStruct.Pin = GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9; GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; GPIO_InitStruct.Pull = GPIO_NOPULL; GPIO_InitStruct.Speed = GPIO_SPEED_LOW; GPIO_InitStruct.Alternate = GPIO_AF5_SPI5; HAL_GPIO_Init(GPIOF, &GPIO_InitStruct); /* USER CODE BEGIN SPI5_MspInit 1 */ /* USER CODE END SPI5_MspInit 1 */ } } Передаю и принимаю данные с помощью функции: HAL_StatusTypeDef HAL_SPI_TransmitReceive_DMA(SPI_HandleTypeDef *hspi, uint8_t *pTxData, uint8_t *pRxData, uint16_t Size); При первом вызове функции все работает. При повторном вызове данной функции, функция возвращает return HAL_BUSY; HAL_StatusTypeDef HAL_SPI_TransmitReceive_DMA(SPI_HandleTypeDef *hspi, uint8_t *pTxData, uint8_t *pRxData, uint16_t Size) { uint32_t tmpstate = 0; tmpstate = hspi->State; if((tmpstate == HAL_SPI_STATE_READY) || ((hspi->Init.Mode == SPI_MODE_MASTER) && \ (hspi->Init.Direction == SPI_DIRECTION_2LINES) && (tmpstate == HAL_SPI_STATE_BUSY_RX))) { if((pTxData == NULL ) || (pRxData == NULL ) || (Size == 0)) { return HAL_ERROR; } /* Check the parameters */ assert_param(IS_SPI_DIRECTION_2LINES(hspi->Init.Direction)); /* Process locked */ __HAL_LOCK(hspi); /* Don't overwrite in case of HAL_SPI_STATE_BUSY_RX */ if(hspi->State != HAL_SPI_STATE_BUSY_RX) { hspi->State = HAL_SPI_STATE_BUSY_TX_RX; } /* Configure communication */ hspi->ErrorCode = HAL_SPI_ERROR_NONE; hspi->pTxBuffPtr = (uint8_t*)pTxData; hspi->TxXferSize = Size; hspi->TxXferCount = Size; hspi->pRxBuffPtr = (uint8_t*)pRxData; hspi->RxXferSize = Size; hspi->RxXferCount = Size; /*Init field not used in handle to zero */ hspi->RxISR = 0; hspi->TxISR = 0; /* Reset CRC Calculation */ if(hspi->Init.CRCCalculation == SPI_CRCCALCULATION_ENABLE) { SPI_RESET_CRC(hspi); } /* Check if we are in Rx only or in Rx/Tx Mode and configure the DMA transfer complete callback */ if(hspi->State == HAL_SPI_STATE_BUSY_RX) { /* Set the SPI Rx DMA Half transfer complete callback */ hspi->hdmarx->XferHalfCpltCallback = SPI_DMAHalfReceiveCplt; hspi->hdmarx->XferCpltCallback = SPI_DMAReceiveCplt; } else { /* Set the SPI Tx/Rx DMA Half transfer complete callback */ hspi->hdmarx->XferHalfCpltCallback = SPI_DMAHalfTransmitReceiveCplt; hspi->hdmarx->XferCpltCallback = SPI_DMATransmitReceiveCplt; } /* Set the DMA error callback */ hspi->hdmarx->XferErrorCallback = SPI_DMAError; /* Enable the Rx DMA Stream */ HAL_DMA_Start_IT(hspi->hdmarx, (uint32_t)&hspi->Instance->DR, (uint32_t)hspi->pRxBuffPtr, hspi->RxXferCount); /* Enable Rx DMA Request */ hspi->Instance->CR2 |= SPI_CR2_RXDMAEN; /* Set the SPI Tx DMA transfer complete callback as NULL because the communication closing is performed in DMA reception complete callback */ hspi->hdmatx->XferCpltCallback = NULL; if(hspi->State == HAL_SPI_STATE_BUSY_TX_RX) { /* Set the DMA error callback */ hspi->hdmatx->XferErrorCallback = SPI_DMAError; } else { hspi->hdmatx->XferErrorCallback = NULL; } /* Enable the Tx DMA Stream */ HAL_DMA_Start_IT(hspi->hdmatx, (uint32_t)hspi->pTxBuffPtr, (uint32_t)&hspi->Instance->DR, hspi->TxXferCount); /* Process Unlocked */ __HAL_UNLOCK(hspi); /* Check if the SPI is already enabled */ if((hspi->Instance->CR1 &SPI_CR1_SPE) != SPI_CR1_SPE) { /* Enable SPI peripheral */ __HAL_SPI_ENABLE(hspi); } /* Enable Tx DMA Request */ hspi->Instance->CR2 |= SPI_CR2_TXDMAEN; return HAL_OK; } else { return HAL_BUSY; } } Подскажите пожалуйста в чем дело? Почему SPI занят? Изменено 31 августа, 2017 пользователем Alex_Golubev Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
0men 2 31 августа, 2017 Опубликовано 31 августа, 2017 · Жалоба Привет. Столкнулся с проблемой передачи и приема данных по spi. Так может он еще передает? Через какой промежуток идет следующий вызов? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Alex_Golubev 0 31 августа, 2017 Опубликовано 31 августа, 2017 (изменено) · Жалоба Не передает. Пробовал while(HAL_SPI_TransmitReceive_DMA(...)!=HAL_OK); Просто программа весит на цикли и все. Нашел в интернете https://community.st.com/thread/26273 у человека такая же проблема, но не ясно как проблему решили. Изменено 31 августа, 2017 пользователем Alex_Golubev Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
0men 2 31 августа, 2017 Опубликовано 31 августа, 2017 (изменено) · Жалоба Не передает. Пробовал while(HAL_SPI_TransmitReceive_DMA(...)!=HAL_OK); Просто программа весит на цикли и все. клок разрешен? ПС увидел эээ!!! Так у вас в одном место spi3, а в другом spi4 ))) Изменено 31 августа, 2017 пользователем 0men Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Alex_Golubev 0 31 августа, 2017 Опубликовано 31 августа, 2017 (изменено) · Жалоба С spi3 void MX_SPI3_Init(void) { hspi3.Instance = SPI3; hspi3.Init.Mode = SPI_MODE_MASTER; hspi3.Init.Direction = SPI_DIRECTION_2LINES; hspi3.Init.DataSize = SPI_DATASIZE_8BIT; hspi3.Init.CLKPolarity = SPI_POLARITY_LOW; hspi3.Init.CLKPhase = SPI_PHASE_1EDGE; hspi3.Init.NSS = SPI_NSS_SOFT; hspi3.Init.BaudRatePrescaler = SPI_BAUDRATEPRESCALER_8; hspi3.Init.FirstBit = SPI_FIRSTBIT_MSB; hspi3.Init.TIMode = SPI_TIMODE_DISABLED; hspi3.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLED; hspi3.Init.CRCPolynomial = 10; HAL_SPI_Init(&hspi3); } работаю через обычную функцию HAL_StatusTypeDef HAL_SPI_TransmitReceive(SPI_HandleTypeDef *hspi, uint8_t *pTxData, uint8_t *pRxData, uint16_t Size, uint32_t Timeout); Полет нормальный. А вот с spi4 через DMA и вот глюки. Изменено 31 августа, 2017 пользователем Alex_Golubev Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
RusikOk 1 11 июля, 2020 Опубликовано 11 июля, 2020 · Жалоба в чем была проблема? Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться