fhl2397 发表于 2010-7-29 13:26:49

9234模拟串口源代码

由于9234只有一个通讯口,所以在需要多个通讯口的场合就很不方便,换芯片的话成本就会增加很多,所以就研究了模拟串口的方法。

在该方案中,波特率采用4800,1位起始位,8位数据位,偶校验,两位停止位,波特率是用定时器来控制的,经过测试,在常温和70度左右的情况下,通讯出错率均小于1%。基于硬件限制,收发数据依然采用P43,P44口,该口工作于I/O端口状态

希望这个程序对大家有用。

欢迎大家加我的QQ:386132185,留言说明是在学习nec的,我们可以互相学习,共同提高

另欢迎大家加入12580452 QQ群。


由于本人经验有限,程序中难免会有缺陷,欢迎大家拍砖。



点击此处下载 ourdev_571508.pdf(文件大小:59K) (原文件名:9234模拟串口通讯.pdf)



/*******************************************************************************
//功能:      模拟UART,当芯片自身的通讯口有限时,可以用该方法模拟通讯
//数据模式:    波特率:4800,1位起始位,8位数据位,偶校验,2位停止位,
//            经过测试,通讯出错率小于1%
//            基于硬件限制,该程序中用于模拟通讯的口仍选择P43,P44口,P43,P44口
//            工作在I/O口状态
//作者:      范 坤
//公司:      上海耘和空调科技有限公司
//完成日期:    2010.07.28
*******************************************************************************/
#include<io78f9234.h>
#include<intrinsiCS.h>

/*--------------------选项字节配置------------------------*/
/*-----------------------------------------------------------
内部时钟,
-----------------------------------------------------------*/
#pragma location = 0X0080
__root const unsigned char XUAN=0X9c;//选项字节,设置实用内部高速时钟电路,低速内部振荡器时钟可由软件停止

#define ucharunsigned char
#define uint   unsigned int
#define ushort   unsigned short

/*以下声明是对寄存器的操作,分别对寄存器的某一位清零或置一*/
#define        clearbit(Reg, ClrBitMap)        Reg &= ~ClrBitMap//清零操作
#define        setbit(Reg, SetBitMap)        Reg |= SetBitMap//置1操作

#define        DI()        __disable_interrupt()//屏蔽所有中断
#define        EI()        __enable_interrupt()//使能所有中断
#define        NOP()        __no_operation()//空操作


#define P00 P0_bit.no0
#define P01 P0_bit.no1
#define P02 P0_bit.no2
#define P03 P0_bit.no3

#define P120 P12_bit.no0
#define P121 P12_bit.no1
#define P122 P12_bit.no2
#define P123 P12_bit.no3

#define P130 P13_bit.no0

#define P20 P2_bit.no0
#define P21 P2_bit.no1
#define P22 P2_bit.no2
#define P23 P2_bit.no3

#define P30 P3_bit.no0
#define P31 P3_bit.no1
#define P32 P3_bit.no2
#define P33 P3_bit.no3

#define P40 P4_bit.no0
#define P41 P4_bit.no1
#define P42 P4_bit.no2
#define P43 P4_bit.no3
#define P44 P4_bit.no4
#define P45 P4_bit.no5
#define P46 P4_bit.no6
#define P47 P4_bit.no7

#define TXD P4_bit.no3
#define RXD P4_bit.no4


__saddr uchar sendbuffer;//发送缓存
__saddr uchar recbuffer;//接收缓存
__saddr uchar rxd_count;//该组参数用于记录接收或发送的数据的位数



void clock();//时钟初始化函数
void PORT_Init();//端口初始化函数
void TMH1_Init();//定时器初始化函数
void main();//主函数
void TMH1_Start();//启动定时器函数
void TMH1_Stop();//停止定时器函数
void delayms(uint ms);//准确延时1ms,当ms=1时

void send_data(uchar data);//发送数据函数
uchar rec_data();//接收数据函数,返回值为接收到数据的内容



/****简单延时函数,在该延时函数中,当ms=1时,可以准确实现延时1ms***************/
void delayms(uint ms)//准确延时1ms,当ms=1时
{
uint i,j;
for(i=0;i<ms;i++)
    for(j=0;j<460;j++);
}

/**********************时钟初始化函数,系统时钟为8MHz***************************/
void clock()
{
PPCC=0X00;
PCC=0X00;
}

/******************************端口初始化函数**********************************/
void PORT_Init(void)
{
        clearbit(PM3,0X02);//P31设定为输出口
        clearbit(PM4,0X28);//P43,P45设定为输出口
      setbit(PM4,0X10);//P44设定为输入口
      
      setbit(P4, 0x08);                /* port setting in transmit/receive mode */
      
      PM2=0X00;
}


/********************定时器初始化函数,定时204us,实现4800波特率***************/
void TMH1_Init(void)
{
        TMHE1 = 0;        /* disable TMH1 counter */
        TMMKH1 = 1;        /* disable INTTMH1 */
        TMIFH1 = 0;        /* enable INTTMH1 */
        /* TMH1 interval mode */
        TMHMD1 = 0x20;
        CMP01 = 0x68;
}

/***************************启动定时器函数*************************************/
void TMH1_Start(void)
{
        TMHE1 = 1;        /* enable TMH1 counter */
}

/***************************停止定时器函数*************************************/
void TMH1_Stop(void)
{
        TMHE1 = 0;        /* disable TMH1 counter */
}

/********************************发送数据函数**********************************/
void send_data(uchar data)
{
uchar txd_count=0;//该参数用于记录发送数据的位数
uchar even_count=0;//该参数用于记录发送的数据位1的位数,从而判断发送的偶校验位的值
P31=1;//发送数据使能
NOP();

/*************发送起始位,1位起始位,低电平***********/
TXD=0;
TMH1_Start();//开定时器中断
while(!TMIFH1) //没有产生中断就等待
    NOP();
TMIFH1=0;

/*************发送数据位,8位数据位***********/
while(txd_count<8)
{
    if(data&0x01)
    {
      TXD=1;
      even_count++;
    }
    else
      TXD=0;
   
    TMH1_Start();//开定时器中断
    while(!TMIFH1)
      NOP();
    TMIFH1=0;
    txd_count++;
    data=data>>1;
}

/*************发送校验位,在该系统中采用偶校验的方式***********/
if(even_count%2) TXD=1;
else TXD=0;
while(!TMIFH1)
    NOP();
TMIFH1=0;
TMH1_Start();//开定时器中断

/*************发送停止位,两位停止位***********/
TXD=1;
while(!TMIFH1)
    NOP();
TMIFH1=0;
TMH1_Start();//开定时器中断
TXD=1;
while(!TMIFH1)
    NOP();
TMIFH1=0;
TMH1_Stop();
}

/********************************接收数据函数**********************************/
uchar rec_data()
{
uchar data=0xff;//该参数用于记录接收到的数据
uchar rxd_count=8;//该参数用于记录接收数据的位数
uchar even_count=0;//该参数用于记录发送的数据位1的位数,从而判断发送的偶校验位的值
uchar even;//该参数用于存储接收到的校验位
uchar a,b;//该组参数用于存储接收到的停止位

P31=0;//接收数据使能
while(RXD&0X01)//等待起始位
{
    NOP();
}
CMP01 = 0x9c;//错后半位,抗干扰
TMH1_Start();//开定时器中断
while(!TMIFH1) //没有产生中断就等待
    NOP();
TMIFH1=0;
while(rxd_count)
{
    data>>=1;//低位在前传送
      
    if(RXD)
    {
      data=data|0X80;
      even_count++;
    }
    else
    {
      data=data|0X00;
    }
      
    CMP01 = 0x68;//保持错后半位检测
    TMH1_Start();//开定时器中断
    while(!TMIFH1) //没有产生中断就等待
      NOP();
    TMIFH1=0;
    rxd_count--;
}
even=RXD;//接收到的校验位
TMH1_Start();//开定时器中断
while(!TMIFH1) //没有产生中断就等待
    NOP();
TMIFH1=0;
a=RXD;
while(!TMIFH1) //没有产生中断就等待
    NOP();
TMIFH1=0;
b=RXD;
while(!TMIFH1) //没有产生中断就等待
    NOP();
TMIFH1=0;

TMH1_Stop();

recbuffer=data;
if(even&&a&&b)
    return 0;
else
    return 1;
}

/************************************主函数*************************************/
void main()
{
DI();//关总中断
LSRSTOP=0x01;//停止低速内部振荡器
WDTM=0X77;//屏蔽看门狗
clock();//时钟初始化
PORT_Init();//端口初始化
TMH1_Init();//定时器初始化
EI();//开总中断
while(1)
{
    rec_data();
    send_data(recbuffer);
    delayms(10);
    /*------------------------
    for(uchar i=0;i<8;i++)
    {
      P45=recbuffer&0x01;
      recbuffer=recbuffer>>1;
      delayms(10);
    }
    -----------------------*/
}
}

jiaweiqiang 发表于 2010-8-13 11:39:02

留个记号,顶!

fhl2397 发表于 2010-8-25 09:36:23

自己顶一下

menghai029 发表于 2010-12-31 15:01:53

有需要 F9234 开发板的联系 QQ:277581646
提供技术支持
http://ourdev.cn/bbs/bbs_content.jsp?bbs_sn=4454176&bbs_page_no=1&bbs_id=3013

skdyu 发表于 2011-2-7 21:08:44

谢谢楼主分享快乐,学习一下。

zhangjin327 发表于 2011-2-15 11:50:36

好东西,谢谢分享
页: [1]
查看完整版本: 9234模拟串口源代码