pub
Fork of CANnucleo by
Embed:
(wiki syntax)
Show/hide line numbers
stm32f0xx_hal_msp.c
Go to the documentation of this file.
00001 /** 00002 ****************************************************************************** 00003 * @file stm32f0xx_hal_msp.c 00004 * @author MCD Application Team 00005 * @version V1.0.0 00006 * @date 17-December-2014 00007 * @brief HAL MSP module. 00008 ****************************************************************************** 00009 * @attention 00010 * 00011 * <h2><center>© COPYRIGHT(c) 2014 STMicroelectronics</center></h2> 00012 * 00013 * Redistribution and use in source and binary forms, with or without modification, 00014 * are permitted provided that the following conditions are met: 00015 * 1. Redistributions of source code must retain the above copyright notice, 00016 * this list of conditions and the following disclaimer. 00017 * 2. Redistributions in binary form must reproduce the above copyright notice, 00018 * this list of conditions and the following disclaimer in the documentation 00019 * and/or other materials provided with the distribution. 00020 * 3. Neither the name of STMicroelectronics nor the names of its contributors 00021 * may be used to endorse or promote products derived from this software 00022 * without specific prior written permission. 00023 * 00024 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 00025 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00026 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE 00027 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE 00028 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 00029 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 00030 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 00031 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 00032 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 00033 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 00034 * 00035 ****************************************************************************** 00036 * 00037 * Modified by Zoltan Hudak <hudakz@outlook.com> 00038 * 00039 ****************************************************************************** 00040 */ 00041 #if defined(TARGET_NUCLEO_F072RB) || \ 00042 defined(TARGET_NUCLEO_F091RC) 00043 00044 #include "cannucleo_api.h" 00045 #include "pinmap.h" 00046 00047 CAN_HandleTypeDef _canHandle; 00048 CanRxMsgTypeDef _canRxMsg; 00049 CanTxMsgTypeDef _canTxMsg; 00050 PinName _rxPin; 00051 PinName _txPin; 00052 00053 void (*rxCompleteCallback)(void); 00054 00055 /** 00056 * @brief CAN initialization. 00057 * @param obj: can_t object 00058 * @param rxPin: RX pin name 00059 * @param txPin: TX pin name 00060 * @param abom: Automatic recovery from bus-off state 00061 * @retval None 00062 */ 00063 void initCAN(PinName rxPin, PinName txPin, FunctionalState abom) { 00064 _rxPin = rxPin; 00065 _txPin = txPin; 00066 00067 _canHandle.Instance = ((CAN_TypeDef*)CAN_BASE); 00068 _canHandle.pTxMsg = &_canTxMsg; 00069 _canHandle.pRxMsg = &_canRxMsg; 00070 00071 _canHandle.Init.TTCM = DISABLE; 00072 _canHandle.Init.ABOM = abom; 00073 _canHandle.Init.AWUM = DISABLE; 00074 _canHandle.Init.NART = DISABLE; 00075 _canHandle.Init.RFLM = DISABLE; 00076 _canHandle.Init.TXFP = DISABLE; 00077 _canHandle.Init.Mode = CAN_MODE_NORMAL; 00078 00079 // 125kbps bit rate (default) 00080 // APB1 peripheral clock = 48000000Hz 00081 _canHandle.Init.Prescaler = 24; // number of time quanta = 48000000/24/125000 = 16 00082 _canHandle.Init.SJW = CAN_SJW_1TQ; 00083 _canHandle.Init.BS1 = CAN_BS1_11TQ; // sample point at: (1 + 11) / 16 * 100 = 75% 00084 _canHandle.Init.BS2 = CAN_BS2_4TQ; 00085 00086 HAL_CAN_Init(&_canHandle); 00087 } 00088 00089 /** 00090 * @brief CAN MSP Initialization 00091 * @param hcan: CAN handle pointer 00092 * @retval None 00093 */ 00094 void HAL_CAN_MspInit(CAN_HandleTypeDef* hcan) { 00095 GPIO_InitTypeDef GPIO_InitStruct; 00096 00097 if((_rxPin == PA_11) && (_txPin == PA_12)) { 00098 00099 /* CAN1 Periph clock enable */ 00100 __CAN_CLK_ENABLE(); 00101 00102 /* Enable GPIO clock */ 00103 __GPIOA_CLK_ENABLE(); 00104 00105 /* CAN1 RX GPIO pin configuration */ 00106 GPIO_InitStruct.Pin = GPIO_PIN_11; 00107 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; 00108 GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; 00109 GPIO_InitStruct.Pull = GPIO_NOPULL; 00110 GPIO_InitStruct.Alternate = GPIO_AF4_CAN; 00111 HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); 00112 00113 /* CAN1 TX GPIO pin configuration */ 00114 GPIO_InitStruct.Pin = GPIO_PIN_12; 00115 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; 00116 GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; 00117 GPIO_InitStruct.Pull = GPIO_NOPULL; 00118 GPIO_InitStruct.Alternate = GPIO_AF4_CAN; 00119 HAL_GPIO_Init(GPIOA, &GPIO_InitStruct); 00120 } 00121 else 00122 if((_rxPin == PB_8) && (_txPin == PB_9)) { 00123 /* CAN1 Periph clock enable */ 00124 __CAN_CLK_ENABLE(); 00125 00126 /* Enable GPIO clock */ 00127 __GPIOB_CLK_ENABLE(); 00128 00129 /* CAN1 RX GPIO pin configuration */ 00130 GPIO_InitStruct.Pin = GPIO_PIN_8; 00131 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; 00132 GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; 00133 GPIO_InitStruct.Pull = GPIO_NOPULL; 00134 GPIO_InitStruct.Alternate = GPIO_AF4_CAN; 00135 HAL_GPIO_Init(GPIOB, &GPIO_InitStruct); 00136 00137 /* CAN1 TX GPIO pin configuration */ 00138 GPIO_InitStruct.Pin = GPIO_PIN_9; 00139 GPIO_InitStruct.Mode = GPIO_MODE_AF_PP; 00140 GPIO_InitStruct.Speed = GPIO_SPEED_HIGH; 00141 GPIO_InitStruct.Pull = GPIO_NOPULL; 00142 GPIO_InitStruct.Alternate = GPIO_AF4_CAN; 00143 HAL_GPIO_Init(GPIOB, &GPIO_InitStruct); 00144 } 00145 else 00146 return; 00147 /* NVIC configuration for CAN1 Reception complete interrupt */ 00148 HAL_NVIC_SetPriority(CAN_IRQ, 1, 0); 00149 HAL_NVIC_EnableIRQ(CAN_IRQ); 00150 } 00151 00152 /** 00153 * @brief CAN MSP De-Initialization 00154 * This function frees the hardware resources used: 00155 * - Disable the Peripheral's clock 00156 * - Revert GPIO to their default state 00157 * @param hcan: CAN handle pointer 00158 * @retval None 00159 */ 00160 void HAL_CAN_MspDeInit(CAN_HandleTypeDef* hcan) { 00161 00162 /* Reset peripherals */ 00163 00164 __CAN_FORCE_RESET(); 00165 __CAN_RELEASE_RESET(); 00166 00167 /* Disable peripherals and GPIO Clocks */ 00168 if((_rxPin == PA_11) && (_txPin == PA_12)) { 00169 /* De-initialize the CAN1 RX GPIO pin */ 00170 HAL_GPIO_DeInit(GPIOA, GPIO_PIN_11); 00171 00172 /* De-initialize the CAN1 TX GPIO pin */ 00173 HAL_GPIO_DeInit(GPIOA, GPIO_PIN_12); 00174 } 00175 else { 00176 00177 /* De-initialize the CAN1 RX GPIO pin */ 00178 HAL_GPIO_DeInit(GPIOB, GPIO_PIN_8); 00179 00180 /* De-initialize the CAN1 TX GPIO pin */ 00181 HAL_GPIO_DeInit(GPIOB, GPIO_PIN_9); 00182 } 00183 00184 00185 /* Disable the NVIC for CAN reception */ 00186 HAL_NVIC_DisableIRQ(CAN_IRQ); 00187 } 00188 00189 /** 00190 * @brief Handles CAN RX interrupt request. 00191 * @param None 00192 * @retval None 00193 */ 00194 void CEC_CAN_IRQHandler(void) { 00195 HAL_CAN_IRQHandler(&_canHandle); 00196 } 00197 00198 /** 00199 * @brief Reception complete callback in non blocking mode 00200 * @param _canHandle: pointer to a CAN_HandleTypeDef structure that contains 00201 * the configuration information for the specified CAN. 00202 * @retval None 00203 */ 00204 void HAL_CAN_RxCpltCallback(CAN_HandleTypeDef* _canHandle) { 00205 // if(HAL_CAN_Receive_IT(_canHandle, CAN_FIFO0) == HAL_OK) { 00206 // if(rxCompleteCallback != NULL) 00207 // rxCompleteCallback(); 00208 // } 00209 // else { 00210 // error_handler(error); 00211 // } 00212 00213 // BUG: CAN race condition if HAL_CAN_Receive_IT() is used. 00214 // See https://my.st.com/public/STe2ecommunities/mcu/Lists/STM32Java/Flat.aspx?RootFolder=%2Fpublic%2FSTe2ecommunities%2Fmcu%2FLists%2FSTM32Java%2FBUG%20CAN%20race%20condition%20if%20HAL%5FCAN%5FReceive%5FIT%20is%20used 00215 // 00216 // Fixed by Mark Burton: 00217 // ideally, we should be able to call HAL_CAN_Receive_IT() here to set up for another 00218 // receive but the API is flawed because that function will fail if HAL_CAN_Transmit() 00219 // had already locked the handle when the receive interrupt occurred - so we do what 00220 // HAL_CAN_Receive_IT() would do 00221 00222 if (rxCompleteCallback != 0) 00223 rxCompleteCallback(); 00224 00225 if (_canHandle->State == HAL_CAN_STATE_BUSY_TX) 00226 _canHandle->State = HAL_CAN_STATE_BUSY_TX_RX; 00227 else { 00228 _canHandle->State = HAL_CAN_STATE_BUSY_RX; 00229 00230 /* Set CAN error code to none */ 00231 _canHandle->ErrorCode = HAL_CAN_ERROR_NONE; 00232 00233 /* Enable Error warning Interrupt */ 00234 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_EWG); 00235 00236 /* Enable Error passive Interrupt */ 00237 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_EPV); 00238 00239 /* Enable Bus-off Interrupt */ 00240 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_BOF); 00241 00242 /* Enable Last error code Interrupt */ 00243 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_LEC); 00244 00245 /* Enable Error Interrupt */ 00246 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_ERR); 00247 } 00248 00249 // Enable FIFO 0 message pending Interrupt 00250 __HAL_CAN_ENABLE_IT(_canHandle, CAN_IT_FMP0); 00251 } 00252 #endif 00253 00254 00255
Generated on Sat Jul 16 2022 03:43:32 by 1.7.2