#include "stm32f4xx.h"
#include "stm32f4_discovery.h"
#include <stdio.h>
#ifdef __GNUC__
#define PUTCHAR_PROTOTYPE int __io_putchar(int ch)
#else
#define PUTCHAR_PROTOTYPE int fputc(int ch, FILE *f)
#endif /* __GNUC__ */
/*
static void delay(volatile unsigned int number)
{
for(; number>0; number--);
}
*/
PUTCHAR_PROTOTYPE
{
/* Write a character to the USART */
if( ch == '\n') {
USART_SendData(USART1, '\r');
while(USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET);
USART_SendData(USART1, '\n');
}else {
USART_SendData(USART1, (u8) ch);
}
/* Loop until the end of transmission */
while(USART_GetFlagStatus(USART1, USART_FLAG_TXE) == RESET);
return ch;
}
void USART1_Configuration(void)
{
/* USART1 clock enable */
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1, ENABLE);
/* GPIOB clock enable */
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
/*-------------------------- GPIO Configuration ----------------------------*/
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 | GPIO_Pin_7;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_Init(GPIOB, &GPIO_InitStructure);
/* Connect USART pins to AF */
GPIO_PinAFConfig(GPIOB, GPIO_PinSource6, GPIO_AF_USART1); // USART1_TX
GPIO_PinAFConfig(GPIOB, GPIO_PinSource7, GPIO_AF_USART1); // USART1_RX
USART_InitTypeDef USART_InitStructure;
/* USARTx configuration ------------------------------------------------------*/
/* USARTx configured as follow:
- BaudRate = 115200 baud
- Word Length = 8 Bits
- One Stop Bit
- No parity
- Hardware flow control disabled (RTS and CTS signals)
- Receive and transmit enabled
*/
USART_InitStructure.USART_BaudRate = 115200;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
USART_Init(USART1, &USART_InitStructure);
USART_Cmd(USART1, ENABLE);
}
#include "drv_can.h"
SCan sCan[CAN_MAX_ID];
CanRxMsg RxMessage0;
CanTxMsg TxMessage;
void Can_Init()
{
GPIO_InitTypeDef GPIO_InitStructure;
CAN_InitTypeDef CAN_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_CAN1, ENABLE);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource8, GPIO_AF_CAN1);
GPIO_PinAFConfig(GPIOB, GPIO_PinSource9, GPIO_AF_CAN1);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8 | GPIO_Pin_9;
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(GPIOB, &GPIO_InitStructure);
CAN_DeInit(CAN1);
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 = ENABLE;
CAN_InitStructure.CAN_Mode = CAN_Mode_Normal;
CAN_InitStructure.CAN_SJW = CAN_SJW_1tq;
CAN_InitStructure.CAN_BS1 = CAN_BS1_4tq;
CAN_InitStructure.CAN_BS2 = CAN_BS2_2tq;
CAN_InitStructure.CAN_Prescaler = 60;
CAN_Init(CAN1, &CAN_InitStructure);
CAN_ITConfig(CAN1, CAN_IT_FMP0, ENABLE);
NVIC_InitStructure.NVIC_IRQChannel = CAN1_RX0_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
/*
filterMode = CAN_FilterMode_IdMask, CAN_FilterMode_IdList
FiltNum = 0~13
*/
void Can_FilterConfig(uint8_t filterMode, uint8_t FiltNum, uint16_t IDHigh, uint16_t IDLow, uint16_t MaskHigh, uint16_t MaskLow)
{
CAN_FilterInitTypeDef CAN_FilterInitStructure;
CAN_FilterInitStructure.CAN_FilterNumber = FiltNum;
CAN_FilterInitStructure.CAN_FilterMode = filterMode;
CAN_FilterInitStructure.CAN_FilterScale = CAN_FilterScale_16bit;
CAN_FilterInitStructure.CAN_FilterIdHigh = IDHigh << 5;
CAN_FilterInitStructure.CAN_FilterIdLow = IDLow<<5;
CAN_FilterInitStructure.CAN_FilterMaskIdHigh = MaskHigh;
CAN_FilterInitStructure.CAN_FilterMaskIdLow = MaskLow;
CAN_FilterInitStructure.CAN_FilterFIFOAssignment = 0;
CAN_FilterInitStructure.CAN_FilterActivation = ENABLE;
CAN_FilterInit(&CAN_FilterInitStructure);
}
/*
index = 0~CAN_MAX_ID 구조체 순번
id = 각 구조체의 CanID
func = 데이터 수신 시 실행될 함수
*/
void Can_SetID(uint8_t index, uint16_t id, void (*func)(void))
{
sCan[index].CanID = id;
sCan[index].CanFlag = 0;
if ( func )
{
sCan[index].m_fp = func;
}
}
void Can_TxMessage(uint16_t id, uint8_t length, uint8_t* data)
{
uint8_t i;
for ( i = 0 ; i < length ; i ++ )
TxMessage.Data[i] = data[i];
TxMessage.DLC = length;
TxMessage.RTR = CAN_RTR_DATA;
TxMessage.IDE = CAN_ID_STD;
TxMessage.StdId = id;
CAN_Transmit(CAN1, &TxMessage);
}
void CAN1_RX0_IRQHandler(void)
{
uint8_t id;
printf("can");
CAN_Receive(CAN1, CAN_FIFO0, &RxMessage0);
CAN_ClearITPendingBit(CAN1, CAN_IT_TME);
for ( id = 0 ; id < CAN_MAX_ID ; id ++ )
{
if ( sCan[id].CanID == RxMessage0.StdId)
{
sCan[id].CanRxMessage = RxMessage0;
sCan[id].CanFlag = 1;
if ( sCan[id].m_fp )
{
sCan[id].m_fp();
}
}
}
}
void test1()
{
printf("ID 0x700, DLC: %d, data0= %d\r\n", sCan[0].CanRxMessage.DLC, sCan[0].CanRxMessage.Data[3]);
}
void test2()
{
printf("ID 0x701, DLC: %d, data0= %d\r\n", sCan[1].CanRxMessage.DLC, sCan[1].CanRxMessage.Data[3]);
}
int main(void)
{
uint8_t data[4]={0};
USART1_Configuration();
Can_Init();
Can_FilterConfig(CAN_FilterMode_IdMask, 0, 0x700, 0, 0x7f0, 0x0);
Can_SetID(0, 0x700, test1);
Can_SetID(1, 0x701, test2);
RCC_ClocksTypeDef RCC_Clocks;
RCC_GetClocksFreq(&RCC_Clocks);
printf("SYS:%d H:%d, P1:%d, P2:%d\r\n",
RCC_Clocks.SYSCLK_Frequency,
RCC_Clocks.HCLK_Frequency, // AHB
RCC_Clocks.PCLK1_Frequency, // APB1
RCC_Clocks.PCLK2_Frequency); // APB2
//printf("HELLO WORLD!");
while(1)
{
data[0] = 1; data[1] = 2; data[2] = 3; data[3] = 'd';
Can_TxMessage(0x700, 4, data);
}
}