这两天玩了一下stm32f042的can,但是折腾了2个晚上,还是没有进展。我知道stm32f042F6P6 ssop20封装的pin17,pin18默认是PA9,PA10的功能,如果想使用PA11和PA12,需要进行端口映射。这样的话,我直接就用了下面的代码,进行端口映射,
- SYSCFG_MemoryRemapConfig(SYSCFG_CFGR1_PA11_PA12_RMP);
复制代码
结果Can总线一直没有波形出来。使用回环模式调试,总线上一直没有波形。
由于CAN的PA11和PA12和串口1的PA9和PA10是复用的,没有第一时间使用串口进行调试。今天晚上下班将usart2飞线飞出来了。使能断言后,发现下面的断言错误。
- DEBUG [D] main:94 hello armwind
- DEBUG [D] assert_failed:94<div> …/Lib/STM32F0xx_StdPeriph_Driver/src/stm32f0xx_syscfg.c,line:119</div>
复制代码
查看源码发现,断言表明,这个方法只能映射系统mem.
- void SYSCFG_MemoryRemapConfig(uint32_t SYSCFG_MemoryRemap)
- {
- uint32_t tmpctrl = 0;
- /* Check the parameter */
- assert_param(IS_SYSCFG_MEMORY_REMAP(SYSCFG_MemoryRemap));
- /* Get CFGR1 register value */
- tmpctrl = SYSCFG->CFGR1;
- /* Clear MEM_MODE bits */
- tmpctrl &= (uint32_t) (~SYSCFG_CFGR1_MEM_MODE);
- /* Set the new MEM_MODE bits value */
- tmpctrl |= (uint32_t) SYSCFG_MemoryRemap;
- /* Set CFGR1 register with the new memory remap configuration */
- SYSCFG->CFGR1 = tmpctrl;
- }
- //宏定义很明显
- #define IS_SYSCFG_MEMORY_REMAP(REMAP) (((REMAP) == SYSCFG_MemoryRemap_Flash) || \
- ((REMAP) == SYSCFG_MemoryRemap_SystemMemory) || \
- ((REMAP) == SYSCFG_MemoryRemap_SRAM))
复制代码
所以使用下面代码即可map成功
- //不要覆盖掉系统原始的配置
- SYSCFG->CFGR1 = SYSCFG->CFGR1 | SYSCFG_CFGR1_PA11_PA12_RMP;
复制代码
完整的Can初始化代码
- void can_init(void)
- {
- GPIO_InitTypeDef GPIO_InitStructure;
- NVIC_InitTypeDef NVIC_InitStructure;
- CAN_InitTypeDef CAN_InitStructure;
- CAN_FilterInitTypeDef CAN_FilterInitStructure;
- RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);
- SYSCFG->CFGR1 = SYSCFG->CFGR1 | SYSCFG_CFGR1_PA11_PA12_RMP;
- //这里一定要先映射GPIO
- /* Enable GPIO clock */
- RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOA, ENABLE);
- /* Connect CAN pins to AF7 */
- /* CAN GPIOs configuration **************************************************/
- GPIO_PinAFConfig(GPIOA, GPIO_PinSource11, GPIO_AF_4);
- GPIO_PinAFConfig(GPIOA, GPIO_PinSource12, GPIO_AF_4);
- /* Configure CAN RX and TX pins */
- GPIO_InitStructure.GPIO_Pin = GPIO_PinSource11 | GPIO_PinSource12;
- GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
- GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
- GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
- GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
- GPIO_Init(GPIOA, &GPIO_InitStructure);
- /* NVIC configuration *******************************************************/
- NVIC_InitStructure.NVIC_IRQChannel = CEC_CAN_IRQn;
- NVIC_InitStructure.NVIC_IRQChannelPriority = 0x0;
- NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
- NVIC_Init(&NVIC_InitStructure);
- /* CAN configuration ********************************************************/
- /* Enable CAN clock */
- RCC_APB1PeriphClockCmd(RCC_APB1Periph_CAN, ENABLE);
- /* CAN register init */
- CAN_DeInit(CAN);
- CAN_StructInit(&CAN_InitStructure);
- /* CAN cell init */
- CAN_InitStructure.CAN_TTCM = DISABLE;
- CAN_InitStructure.CAN_ABOM = DISABLE;
- CAN_InitStructure.CAN_AWUM = DISABLE;
- CAN_InitStructure.CAN_NART = DISABLE;
- CAN_InitStructure.CAN_RFLM = DISABLE;
- CAN_InitStructure.CAN_TXFP = DISABLE;
- CAN_InitStructure.CAN_Mode = CAN_Mode_Normal;
- //CAN_InitStructure.CAN_Mode = CAN_Mode_LoopBack;
- CAN_InitStructure.CAN_SJW = CAN_SJW_1tq;
- //200k的配置
- //48M/12/(CAN_SJW_1tq + CAN_BS1_4tq+CAN_BS2_5tq) == 200k
- /* CAN Baudrate = 1MBps (CAN clocked at 36 MHz) */
- CAN_InitStructure.CAN_BS1 = CAN_BS1_4tq;
- CAN_InitStructure.CAN_BS2 = CAN_BS2_5tq;
- CAN_InitStructure.CAN_Prescaler = 12;
- CAN_Init(CAN, &CAN_InitStructure);
- /* CAN filter init */
- CAN_FilterInitStructure.CAN_FilterNumber = 1;
- CAN_FilterInitStructure.CAN_FilterMode = CAN_FilterMode_IdMask;
- CAN_FilterInitStructure.CAN_FilterScale = CAN_FilterScale_32bit;
- CAN_FilterInitStructure.CAN_FilterIdHigh = 0x0000;
- CAN_FilterInitStructure.CAN_FilterIdLow = 0x0000;
- CAN_FilterInitStructure.CAN_FilterMaskIdHigh = 0x0000;
- CAN_FilterInitStructure.CAN_FilterMaskIdLow = 0x0000;
- CAN_FilterInitStructure.CAN_FilterFIFOAssignment = 0;
- CAN_FilterInitStructure.CAN_FilterActivation = ENABLE;
- CAN_FilterInit(&CAN_FilterInitStructure);
- /* Transmit Structure preparation */
- /* Enable FIFO 0 message pending Interrupt */
- CAN_ITConfig(CAN, CAN_IT_FMP0, ENABLE);
- }
复制代码
|