打印

STM8 关于LIN总线的通讯请教

[复制链接]
6350|2
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
a7208184|  楼主 | 2011-2-12 19:01 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
大家好!

     小弟现在遇到一个奇怪的问题。

     硬件测试环境:板子是STM8S208,板子上有两个LIN接口,一个做主机,一个做从机,用一条串口线将两个口连接起来通信。

     问题:主机发送断开符和界定符,但是监测不到断开符检测标志位的变化,也就是断开符发送不成功。但是我确信主机有发送断开符,不过就是检测不到。

     希望有这方面经验的朋友帮帮忙,小弟刚开始搞这个,有点找不到方向了!!

现在贴出代码,希望大家帮忙分析下。

/********************************************************************************
* 函数名称:LIN_HostModeInit
* 功能描述: LIN的主模式初始化
* 参数说明:
*        ucUartPort[IN]:需要操作的串口号
*        nUartBandrate[IN]:波特率
* 返 回 值:无
********************************************************************************/
void LIN_HostModeInit(u8 ucUartPort, u32 nUartBandrate)
{
u16 nUartDiv = 0x0;

nUartDiv = (u16)(CLK_GetClockFreqHZ()/nUartBandrate);

switch(ucUartPort)
{
  case 1:
      //配置UARTDIV
      UART1->BRR2 = (u8)((u8)((u8)(nUartDiv & 0x000f) | (u8)((u8)(nUartDiv & 0xf000) << 4)));
      UART1->BRR1 = (u8)(((u8)(nUartDiv >> 4)) | ((u8)((u8)(nUartDiv >> 8) << 4)));
   
      UART1->CR1 &= (u8)(~(0x01 << 4));//配置数据位
      UART1->CR3 &= (u8)(~(0x01 << 4));//配置停止位
      UART1->CR2 |= (u8)((0x01 << 2) | (0x01 << 3) | (0x01 << 5));//允许发送和接收,能够产生接收中断,打开UART
      UART1->CR4 |= (u8)((0x01 << 5) | (0x01 << 6));//LIN断开符检测长度11位,且打开断开符检测中断使能
      UART1->CR3 |= (u8)(0x01 << 6);//打开LIN模式
      break;
  case 2:
      //配置UARTDIV
      UART2->BRR2 = (u8)((u8)((u8)(nUartDiv & 0x000f) | (u8)((u8)(nUartDiv & 0xf000) << 4)));
      UART2->BRR1 = (u8)(((u8)(nUartDiv >> 4)) | ((u8)((u8)(nUartDiv >> 8) << 4)));
      
      UART2->CR1 &= (u8)(~(0x01 << 4));//配置数据位
      UART2->CR3 &= (u8)(~(0x01 << 4));//配置停止位
      UART2->CR2 |= (u8)((0x01 << 2) | (0x01 << 3) | (0x01 << 5));//允许发送和接收,能够产生接收中断,打开UART
      UART2->CR4 |= (u8)((0x01 << 5) | (0x01 << 6));//LIN断开符检测长度11位,且打开断开符检测中断使能
      UART2->CR3 |= (u8)(0x01 << 6);//打开LIN模式
      break;
  case 3:
      //配置UARTDIV
      UART3->BRR2 = (u8)((u8)((u8)(nUartDiv & 0x000f) | (u8)((u8)(nUartDiv & 0xf000) << 4)));
      UART3->BRR1 = (u8)(((u8)(nUartDiv >> 4)) | ((u8)((u8)(nUartDiv >> 8) << 4)));
      
      UART3->CR1 &= (u8)(~(0x01 << 4));//配置数据位
      UART3->CR3 &= (u8)(~(0x01 << 4));//配置停止位
      UART3->CR2 |= (u8)((0x01 << 2) | (0x01 << 3) | (0x01 << 5));//允许发送和接收,能够产生接收中断,打开UART
      UART3->CR4 |= (u8)((0x01 << 5) | (0x01 << 6));//LIN断开符检测长度11位,且打开断开符检测中断使能
      UART3->CR3 |= (u8)(0x01 << 6);//打开LIN模式
      break;
  default:
      break;
}
}

/********************************************************************************
* 函数名称:LIN_SlaveModeInit
* 功能描述: LIN的从模式初始化
* 参数说明:
*      ucUartPort[IN]: 需要操作的串口号(只能打开2号和3号的串口)
*      nUartBandrate[IN]:波特率
*      ucIdentifer[IN]:标识符
* 返 回 值:无
********************************************************************************/
void LIN_SlaveModeInit(u8 ucUartPort, u32 nUartBandrate, u8 ucIdentifier)
{
u16 nUartDiv = 0x0;
nUartDiv = (u16)(CLK_GetClockFreqHZ()/nUartBandrate);

switch(ucUartPort)
{
  case 2:
      //配置UARTDIV
      UART2->BRR2 = (u8)((u8)((u8)(nUartDiv & 0x000f) | (u8)((u8)(nUartDiv & 0xf000) << 4)));
      UART2->BRR1 = (u8)(((u8)(nUartDiv >> 4)) | ((u8)((u8)(nUartDiv >> 8) << 4)));
      
      UART2->CR1 &= (u8)(~(0x01 << 4)); //配置数据位
      UART2->CR3 &= (u8)(~(0x01 << 4)); //配置停止位
      UART2->CR2 |= (u8)((0x01 << 2) | (0x01 << 3) | (0x01 << 5));//允许发送和接收,能够产生接收中断,打开UART
      UART2->CR6 |= (u8)((0x01 << 2) | (0x01 << 4) | (0x01 << 5) | (0x01 << 7));
      UART2->CR4 |= 0x16;//分配节点地址
      UART2->CR2 |= (u8)(0x01 << 1);//接收器处于静默模式
      UART2->CR3 |= (u8)(0x01 << 6);//打开LIN模式
      break;
  case 3:
      //配置UARTDIV
      UART3->BRR2 = (u8)((u8)((u8)(nUartDiv & 0x000f) | (u8)((u8)(nUartDiv & 0xf000) << 4)));
      UART3->BRR1 = (u8)(((u8)(nUartDiv >> 4)) | ((u8)((u8)(nUartDiv >> 8) << 4)));
      
      UART3->CR1 &= (u8)(~(0x01 << 4)); //配置数据位
      UART3->CR3 &= (u8)(~(0x01 << 4)); //配置停止位
      UART3->CR2 |= (u8)((0x01 << 2) | (0x01 << 3) | (0x01 << 5));//允许发送和接收,能够产生接收中断,打开UART
      UART3->CR6 |= (u8)((0x01 << 2) | (0x01 << 4) | (0x01 << 5) | (0x01 << 7));
      UART3->CR4 |= ucIdentifier;//分配节点地址
      UART3->CR2 |= (u8)(0x01 << 1);  //接收器处于静默模式
      UART3->CR3 |= (u8)(0x01 << 6);//打开LIN模式
      break;
  default:
      break;
}
}
/********************************************************************************
* 函数名称:LIN_Host_IRQHandler
* 功能描述: LIN的主模式中断处理
* 参数说明:无
* 返 回 值:无
* 设计日期: 2010/12/06
********************************************************************************/
@far @interrupt void LIN_Host_IRQHandler(void)
{
if((UART1->CR4 & 0x10) == 0x10)
{
  while(!(UART1->SR & 0x80));
  UART1->DR = 0x55;
  while(!(UART1->SR & 0x80));
  //写入保护域标识符的值
  UART1->DR = 0x16;
  UART1->CR4 &= (u8)(~0x10);
}
else if((UART1->CR4 & 0x20) == 0x20)
{//主模式接收响应
  s_ucHostBuff[s_ucHostCount] = UART1->DR;
  s_ucHostCount++;
  
  if(s_ucHostCount >= 20)
  {
   s_ucHostCount = 0;
  }
}

return;
}
/********************************************************************************
* 函数名称:LIN_Slave_IRQHandler
* 功能描述: LIN的主模式中断处理
* 参数说明:无
* 返 回 值:无
* 设计日期: 2010/12/06
********************************************************************************/
@far @interrupt void LIN_Slave_IRQHandler(void)
{
if((UART2->CR6 & 0x02) == 0x02)
{
  UART2->CR6 &= (u8)(~0x02);
}
else if((UART2->CR4 & 0x20) == 0x20)
{//从模式接收响应
  s_ucSlaveBuff[s_ucSlaveCount] = UART1->DR;
  s_ucSlaveCount++;
  
  if(s_ucSlaveCount >= 20)
  {
   s_ucSlaveCount = 0;
  }
}

return;
}

我的测试方法是主机先发送断开符+界定符。然后检测断开符标志位,然后发送同步场0x55,然后发送数据场。但是现在我检测不到断开符标志位。我确认断开符已经发出去了。

我的硬件环境是:在一个STM8的板子上有两个LIN接口,然后我用串口线将两个接口连接起来,分别作主从机进行通信。

帮忙找下问题。
沙发
jgphu| | 2011-2-23 16:31 | 只看该作者
这么一大堆。。。眼花啊。 你没有接收到断开符,你可以查询一下撒,看那里有问题,你要是使用的中断方法,是不是那里设置不对啊。

使用特权

评论回复
板凳
waterbaby2011| | 2016-8-31 15:48 | 只看该作者
间隔时间是不是设置的不对

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

0

主题

76

帖子

1

粉丝