STM32F103 CANBus Problemi

Başlatan baran123, 25 Nisan 2017, 22:29:57

baran123

Bitirme ödevine kaldığım yerden devam ediyorum fakat hatada kaldığı yerden devam ediyor :)
STM32F103C8T6 işlemci ile MCP2551 kullanıyorum fakat CANBus'dan bir türlü veri gönderemiyorum.
CANTX ve CANRX 10K ile Pull-UP(5V)
MCP2551 5V bağlı.
RS pini GND bağlı.

Logic Analyzer ile ölçümlerde hiç bir şey göremiyorum fakat pic ile yaptığımda gayet güzel çalışıyor.

Kod
#include "stm32f10x_conf.h"

#define GPIO_ToggleBit(GPIOx, GPIO_Pin) (GPIOx->ODR ^= 1 << GPIO_Pin)

static void Clock_Config(void);
static void RCC_Config(void);
static void GPIO_Config(void);
static void CAN_Config(void);
static void Delay_ms(uint32_t miliSecond);

CanTxMsg TxMessage;
CanRxMsg RxMessage;

uint32_t systickCounter = 0;
uint32_t systickControl = 0;

int main(void)
{
    Clock_Config();
    RCC_Config();
    GPIO_Config();
    CAN_Config();

    TxMessage.StdId = 0x7E5;
    TxMessage.RTR = CAN_RTR_DATA;
    TxMessage.IDE = CAN_ID_STD;
    TxMessage.DLC = 8;
    TxMessage.Data[0] = 0xFF;
    TxMessage.Data[1] = 0xFF;
    TxMessage.Data[2] = 0xFF;
    TxMessage.Data[3] = 0xFF;
    TxMessage.Data[4] = 0xAA;
    TxMessage.Data[5] = 0xBB;
    TxMessage.Data[6] = 0xCB;
    TxMessage.Data[7] = 0x24;

    for(;;)
    {
        CAN_Transmit(CAN1, &TxMessage);

        GPIO_ToggleBit(GPIOC, 13);

        Delay_ms(1000);
    }
}

static void Clock_Config(void)
{
    /* Error Status Definition */
    ErrorStatus HSEStartUpStatus;

    /* RCC system reset(for debug purpose) */
    RCC_DeInit();

    /* Enable HSE */
    RCC_HSEConfig(RCC_HSE_ON);

    /* Wait till HSE is ready */
    HSEStartUpStatus = RCC_WaitForHSEStartUp();

    if(HSEStartUpStatus == SUCCESS)
    {
        /* Enable Prefetch Buffer */
        FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);

        /* Flash 2 wait state */
        FLASH_SetLatency(FLASH_Latency_2);

        /* HCLK = SYSCLK */
        RCC_HCLKConfig(RCC_SYSCLK_Div1);

        /* PCLK2 = HCLK */
        RCC_PCLK2Config(RCC_HCLK_Div1);

        /* PCLK1 = HCLK/2 */
        RCC_PCLK1Config(RCC_HCLK_Div2);

        /* PLLCLK = 8MHz * 9 = 72 MHz */
        RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_9);

        /* Enable PLL */
        RCC_PLLCmd(ENABLE);

        /* Wait till PLL is ready */
        while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET);

        /* Select PLL as system clock source */
        RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);

        /* Wait till PLL is used as system clock source */
        while(RCC_GetSYSCLKSource() != 0x08);
    }

    /*****************************************/
    /** SystemFrequency / 1000      1ms      */
    /** SystemFrequency / 100000    10us     */
    /** SystemFrequency / 1000000   1us      */
    /*****************************************/
    while (SysTick_Config(SystemCoreClock / 1000) != 0);
}

static void RCC_Config(void)
{
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC, ENABLE);

    RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM1 | RCC_APB2Periph_AFIO, ENABLE);

    RCC_APB1PeriphClockCmd(RCC_APB1Periph_CAN1, ENABLE);
}

static void GPIO_Config(void)
{
    GPIO_InitTypeDef    GPIO_InitStructure;

    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOC, &GPIO_InitStructure);
}

static void CAN_Config(void)
{
    /**
      * CAN Baudrate = 200 kBit/s
      * Bit Rate = (CanBus Freq = APB1) / (Prescaler * (BS1 + BS2 + SJW))
      * SJW must be 1
      * 36 MHz / (18 * (5 + 4 + 1))
      * 200 kBit/s
      **/

    GPIO_InitTypeDef        GPIO_InitStructure;
    NVIC_InitTypeDef        NVIC_InitStructure;
    CAN_InitTypeDef         CAN_InitStructure;
    CAN_FilterInitTypeDef   CAN_FilterInitStructure;

    NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);

    CAN_DeInit(CAN1);
    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      = ENABLE;
    CAN_InitStructure.CAN_RFLM      = DISABLE;
    CAN_InitStructure.CAN_TXFP      = ENABLE;
    CAN_InitStructure.CAN_Mode      = CAN_Mode_Normal;
    CAN_InitStructure.CAN_SJW       = CAN_SJW_1tq;
    CAN_InitStructure.CAN_BS1       = CAN_BS1_5tq;
    CAN_InitStructure.CAN_BS2       = CAN_BS2_4tq;
    CAN_InitStructure.CAN_Prescaler = 18;
    CAN_Init(CAN1, &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            = 0;
    CAN_FilterInitStructure.CAN_FilterIdLow             = 0;
    CAN_FilterInitStructure.CAN_FilterMaskIdHigh        = 0;
    CAN_FilterInitStructure.CAN_FilterMaskIdLow         = 0;
    CAN_FilterInitStructure.CAN_FilterFIFOAssignment    = CAN_FIFO0;
    CAN_FilterInitStructure.CAN_FilterActivation        = ENABLE;
    CAN_FilterInit(&CAN_FilterInitStructure);

    CAN_ITConfig(CAN1, CAN_IT_FMP0, ENABLE);

    NVIC_InitStructure.NVIC_IRQChannel                    = USB_LP_CAN1_RX0_IRQn;
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority  = 0xFF;
    NVIC_InitStructure.NVIC_IRQChannelSubPriority         = 0xFF;
    NVIC_InitStructure.NVIC_IRQChannelCmd                 = ENABLE;
    NVIC_Init(&NVIC_InitStructure);

    /** CAN1 RX **/
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    /** CAN1 TX **/
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOB, &GPIO_InitStructure);

    /**
     * GPIO_Remap1_CAN1 PINS : PB8 CanRx, PB9 CanTx
     * GPIO_Remap2_CAN1 PINS : PD0 CanRx, PD1 CanTx
     */
    GPIO_PinRemapConfig(GPIO_Remap1_CAN1, ENABLE);
}

static void Delay_ms(uint32_t miliSecond)
{
    systickCounter = miliSecond;

    while (systickControl != 1);

    systickControl = 0;
}

void USB_LP_CAN1_RX0_IRQHandler(void)
{
    if(CAN_GetITStatus(CAN1, CAN_IT_FMP0) != RESET)
    {
        CAN_Receive(CAN1, CAN_FIFO0, &RxMessage);

        if ((RxMessage.IDE == CAN_ID_STD) && (RxMessage.StdId == 0) && (RxMessage.DLC == 8))
        {

        }
    }
    CAN_ClearITPendingBit(CAN1, CAN_IT_FMP0);
}

void SysTick_Handler(void)
{
    if (systickCounter != 0)
        systickCounter--;
    else
        systickControl = 1;
}


baran123

Not : Biraz LoopBack moduna aldığımda canbus çalışıyor. Hemde CanTx pinini gözlemlediğimde Analyzer ile verileri görebiliyorum. Ama CANH veya CANL pinlerinde bir şey göremiyorum.

Erol YILMAZ


baran123

Olabilir hocam sanırım MCP2551 3V3 ile uyumlu değil.
ISO1050 veya SN65HVD232 gibi bir transceiver ile deneme yapacağım artık.

Mucit23

MCP2551 VCC 4.5 ile 5.5V demiş. 3.3V ile besliyorsan problem olabilir

baran123

Hocam VCC'sini 5V ile besledim.

memo333

CANL-H arasında 120r var mı?
Gömülü Linux Notları --> http://linuxedu.xyz/

baran123


skara1214

Karşılığında alan bir alıcı  olmayınca hataya düşüyor. Hata flaglarini inceledinizmi?
Herkes ölür ama herkes gerçekten yaşamaz

baran123

Hocam hangi flagleri kastediyorsunuz ? Karşısına aynı Baud'da pic alıcı ekledim fakat aynı.

skara1214

aynı baudu ayarlabildiğinize eminmisiniz? çünkü yolladığınız datayı karşıdan 1 alıcı  almassa ya surekli yollar yada transmit errora geçer
Herkes ölür ama herkes gerçekten yaşamaz

baran123

#11
@skara1214  Hocam kontrol ettim ayni baudda haberlesmeye calisiyorum.


Hata flaglarinin hangisi bumu belirtiyor ?
Bu arafa daha once mcp 2551  stm ile kullandiniz mi ? Galiba 3.3-5V uyumsuzlugundan kaynaklaniyor

skara1214

MCP yi pic ile kullandım stm ile kullanmadım hiç ama sıkıntı çıkacağını zannetmiyorum
Herkes ölür ama herkes gerçekten yaşamaz

CLR

#13
Mcp2551'i 5V ile beslediysen hiçbir sıkıntı çıkmaz, çok sayıda kullanıldı, teknik açıklamasıda, stm32 can pinleri 5V toleranslı ve ttl uyumludur, 2551 girişleride ttl girişli/çıkışlıdır yani kısacası çalışır.

baudda emin değilsen, 2 tane mcp2551 +stm32 ile testini yapabilirsin, 2. mcp2551'in rx pinini tx pine kısa devre edersen, stm32 ne gönderirse, kendisinede o dönecektirr.
Knowledge and Experience are Power

baran123

#14
@CLR Hocam dediğiniz gibi yaptım fakat durum aynı.
STM32+MCP2551 karşısına sadece MCP2551 bağlayıp bu entegrenin TXD ve RXD kısa devre ediyorum fakat hiç bir veri gidip gelmiyor.

Şöyle bir kod ile test ettiğimde while döngüsüde takılıyor yani gönderme nedense başarısız oluyor. Kafam iyice karıştı. Ben nerede hata yapıyorum bir türlü bulamadım.
CAN_Transmit(CAN1, &TxMessage);
while ((CAN_TransmitStatus(CAN1, 0) != CANTXOK));
LED_On();
Delay_ms(1000);