jenya7 0 4 мая, 2016 Опубликовано 4 мая, 2016 (изменено) · Жалоба CAN не принимает данные. У меня внешний кристал 10М. Поэтому /* PLL configuration: PLLCLK = HSE * 7 = 70 MHz */ RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_PLLSRC | RCC_CFGR_PLLXTPRE | RCC_CFGR_PLLMULL)); RCC->CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_PREDIV1 | RCC_CFGR_PLLMULL7); Исходя из этого настраиваю CAN baud rate 125kBit static void CAN_Config(void) { GPIO_InitTypeDef GPIO_InitStructure; NVIC_InitTypeDef NVIC_InitStructure; CAN_InitTypeDef CAN_InitStructure; CAN_FilterInitTypeDef CAN_FilterInitStructure; /* CAN GPIOs configuration **************************************************/ /* Enable GPIO clock */ RCC_AHBPeriphClockCmd(CAN_GPIO_CLK, ENABLE); /* Connect CAN pins to AF7 */ GPIO_PinAFConfig(CAN_GPIO_PORT, CAN_RX_SOURCE, CAN_AF_PORT); GPIO_PinAFConfig(CAN_GPIO_PORT, CAN_TX_SOURCE, CAN_AF_PORT); /* Configure CAN RX and TX pins */ GPIO_InitStructure.GPIO_Pin = CAN_RX_PIN | CAN_TX_PIN; 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(CAN_GPIO_PORT, &GPIO_InitStructure); /* NVIC configuration *******************************************************/ NVIC_InitStructure.NVIC_IRQChannel = USB_LP_CAN1_RX0_IRQn; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x0; NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x0; NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; NVIC_Init(&NVIC_InitStructure); /* CAN configuration ********************************************************/ /* Enable CAN clock */ RCC_APB1PeriphClockCmd(CAN_CLK, ENABLE); /* CAN register init */ CAN_DeInit(CANx); 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; //70 / ((3+7+10) * 28) = 125000 CAN_InitStructure.CAN_SJW = 3; CAN_InitStructure.CAN_BS1 = 10; CAN_InitStructure.CAN_BS2 = 7; CAN_InitStructure.CAN_Prescaler = 28; CAN_Init(CANx, &CAN_InitStructure); /* CAN filter init */ CAN_FilterInitStructure.CAN_FilterNumber = 0; 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 TxMessage.StdId = 0x321; TxMessage.ExtId = 0x01; TxMessage.RTR = CAN_RTR_DATA; TxMessage.IDE = CAN_ID_STD; TxMessage.DLC = 1; */ /* Enable FIFO 0 message pending Interrupt */ CAN1->IER |= CAN_IER_FMPIE0 | CAN_IER_ERRIE | CAN_IER_BOFIE | CAN_IER_EPVIE; //CAN_ITConfig(CANx, CAN_IT_FMP0, ENABLE); } Запускаю утилиту CAN Monitor и посылаю пакет. На скопе вижу сигнал а прерывание не происходит. void USB_LP_CAN1_RX0_IRQHandler(void) { //FIFO Overrun error if (CAN1->RF0R & CAN_RF0R_FOVR0) { CAN1->RF0R &= ~CAN_RF0R_FOVR0; CAN1->RF0R |= CAN_RF0R_RFOM0; /* release FIFO */ return; } //FIFO Full - ready to read data if (CAN1->RF0R & CAN_RF0R_FULL0) { CAN1->RF0R &= ~CAN_RF0R_FULL0; can_idx=0; while (CAN1->RF0R & CAN_RF0R_FMP0) { memcpy(can_rx_packet+can_idx, (uint8_t *) &CAN1->sFIFOMailBox[0].RDLR, 4); can_idx += 4; memcpy(can_rx_packet+can_idx, (uint8_t *) &CAN1->sFIFOMailBox[0].RDHR, 4); can_idx += 4; CAN1->RF0R |= CAN_RF0R_RFOM0; /* release FIFO to read next message */ } data_ready = 1; } Где может быть проблема? Изменено 5 мая, 2016 пользователем IgorKossak [codebox] для длинного кода. [code]-для короткого!!! Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
KRS 1 4 мая, 2016 Опубликовано 4 мая, 2016 · Жалоба CAN_InitStructure.CAN_BS1 = 10; CAN_InitStructure.CAN_BS2 = 7; А это нормальная конфигурация? Просто обычно sample point все таки в 87.5 или 75% должна быть... Хотя 60% в принципе допустимо... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jenya7 0 4 мая, 2016 Опубликовано 4 мая, 2016 · Жалоба CAN_InitStructure.CAN_BS1 = 10; CAN_InitStructure.CAN_BS2 = 7; А это нормальная конфигурация? Просто обычно sample point все таки в 87.5 или 75% должна быть... Хотя 60% в принципе допустимо... я не уверен что я правильно конфигурирую baud rate. я пользуюсь формулой baud rate = F / ((sjw + bs1 + bs2) * bpr) не уверен что она правильная. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
romas2010 1 4 мая, 2016 Опубликовано 4 мая, 2016 · Жалоба CAN не принимает данные. .............. Где может быть проблема? Несовпадение скоростей 1) ко всем значениям сегментов фазы 1 и 2 и предделителя надо учитывать еще +1 типа BS1=3,-значит на самом деле он равен 4.. 2) каков предделитель на шину APB1 с которой тактируется CAN?...от нее и считается предделитель По своему опыту-выбирайте PLL для проектов с CAN кратно 16 МГц, большой диапазон скоростей и совместимости с другими устройствами Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jenya7 0 4 мая, 2016 Опубликовано 4 мая, 2016 · Жалоба Несовпадение скоростей 1) ко всем значениям сегментов фазы 1 и 2 и предделителя надо учитывать еще +1 типа BS1=3,-значит на самом деле он равен 4.. 2) каков предделитель на шину APB1 с которой тактируется CAN?...от нее и считается предделитель По своему опыту-выбирайте PLL для проектов с CAN кратно 16 МГц, большой диапазон скоростей и совместимости с другими устройствами у меня стоит осцилятор 10М на плате. поэтому я выираю RCC_CFGR_PLLMULL7 что дает мне 70М. попробую сейчас +1. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
romas2010 1 4 мая, 2016 Опубликовано 4 мая, 2016 · Жалоба у меня стоит осцилятор 10М на плате. поэтому я выираю RCC_CFGR_PLLMULL7 что дает мне 70М. попробую сейчас +1. Дело не в осцилляторе на плате,а в частоте шины APB1 к примеру PLL=96 MHz...выбираем делитель APB1=4 получаем 24 Мгц...тогда 24000000/125000=192 то есть получаем (1+BS1+1+BS2+1)*(prescaler+1)=192 соотношение BS2/BS1 должно быть ое 2\3 до 3\4...ну типа 66..75% ну на самом деле не важна PLL важно понимание формулы расчета..как получит PLL,прекрасно описано в мануале на микроконтроллер Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
jenya7 0 5 мая, 2016 Опубликовано 5 мая, 2016 (изменено) · Жалоба Дело не в осцилляторе на плате,а в частоте шины APB1 к примеру PLL=96 MHz...выбираем делитель APB1=4 получаем 24 Мгц...тогда 24000000/125000=192 то есть получаем (1+BS1+1+BS2+1)*(prescaler+1)=192 соотношение BS2/BS1 должно быть ое 2\3 до 3\4...ну типа 66..75% ну на самом деле не важна PLL важно понимание формулы расчета..как получит PLL,прекрасно описано в мануале на микроконтроллер спасибо. вроде понял. :) а что SJW в формуле не учитывается? Изменено 5 мая, 2016 пользователем Jenya7 Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
KRS 1 5 мая, 2016 Опубликовано 5 мая, 2016 · Жалоба спасибо. вроде понял. :) а что SJW в формуле не учитывается? не учитывается! SJW должен быть <= BS2, обычно он равен (4 - 1) = 3 соотношение BS2/BS1 должно быть ое 2\3 до 3\4...ну типа 66..75% можно и так считать, но формально позиция sample point (1+BS1+1)/(1+BS1+1+BS2+1) = от 0.5 до 0.9 но обычно используют 0.75 или 0.875 Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
golf2109 0 9 мая, 2016 Опубликовано 9 мая, 2016 · Жалоба для установки CAN timing лучше использовать CubeMX или программки вроде CAN-калькуляторов Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Сергей Борщ 143 9 мая, 2016 Опубликовано 9 мая, 2016 · Жалоба лучше использовать CubeMX или программки вроде CAN-калькуляторовЧем лучше? Предстоит погрузиться в тему CAN, хотелось бы заранее узнать о нюансах. Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
amiller 2 9 мая, 2016 Опубликовано 9 мая, 2016 · Жалоба для установки CAN timing лучше использовать CubeMX или программки вроде CAN-калькуляторов Тут наверное следует добавить: Если опыта маловато или документацию плохо изучили или принципы работы CAN туманны... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
golf2109 0 11 мая, 2016 Опубликовано 11 мая, 2016 · Жалоба Чем лучше? Предстоит погрузиться в тему CAN, хотелось бы заранее узнать о нюансах. лучше тем, что в CubeMX для конфигурации временных параметров CAN bus применяетмя некое подобие калькулятора и при выборе параметров CAN трудно ошибиться Тут наверное следует добавить: Если опыта маловато или документацию плохо изучили или принципы работы CAN туманны... даже если много опыта и большое желание почитать документацию, то сделать например ремап пинов и инициализацию для случая CAN bus например для STM32F042F4 получится с помощью CubeMX намного быстрее и проще... хотя, если есть желание набраться опыта и почитать докумантацию, а самое главное есть начальство оплачивающее !!! самообразование разработчика в рабочее время, когда проект должен быть сделан "на вчера".... Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться
Ruslan-maniak 0 17 мая, 2016 Опубликовано 17 мая, 2016 · Жалоба лично я использую следующую формулу для расчёта прескаллера uint16_t prescaler = clocks.PCLK1_Frequency/((can->definitions.CAN_SJW + 1 + can->definitions.CAN_BS1 + 1 + can->definitions.CAN_BS2 + 1) * can->baudrate); где clocks.PCLK1_Frequency - частота тактирования периферии, can->definitions.CAN_SJW = CAN_SJW_1tq, can->definitions.CAN_BS1 = CAN_BS1_10tq, can->definitions.CAN_BS2 = CAN_BS2_7tq, can->baudrate - заданная вами частота Цитата Поделиться сообщением Ссылка на сообщение Поделиться на другие сайты Поделиться