您现在所在的是:

单片机论坛

回帖:2个,阅读:693 [上一页] [1] [下一页]
1000
sunsoncheng
文章数:109
年度积分:50
历史总积分:1000
注册时间:2010/5/25
发站内信
发表于:2010/12/24 22:44:11
#0楼
谢谢各位大哥了,只是因为小菜的C完全不懂的原因
而本人在之前已将其它仪器上收取的数据放在了34H及35H中,相将这两个数由并口中发送出去
再谢
程序硬件平台:11.0592M晶振

/***************************************************************
*     在单片机上模拟了一个串口,使用P2.1作为发送端
*     把单片机中存放的数据通过P2.1作为串口TXD发送出去
***************************************************************/
#include <reg51.h>
#include <stdio.h>
#include <string.h>

typedef unsigned char uchar;

int i;

uchar code info[] =
{
0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55
};

sbit newTXD = P2^1;//模拟串口的发送端设为P2.1

void UartInit()
{
    SCON   = 0x50;   // SCON: serail mode 1, 8-bit UART
    TMOD |= 0x21;   // T0工作在方式1,十六位定时
    PCON |= 0x80;   // SMOD=1;
    TH0       = 0xFE;     // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=11.0592MHz
    TL0   = 0x7F;     // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=11.0592MHz

//     TH0       = 0xFD;     // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=18.432MHz
//     TL0   = 0x7F;     // 定时器0初始值,延时417us,目的是令模拟串口的波特率为2400bps fosc=18.432MHz
}

void WaitTF0(void)
{
    while(!TF0);
    TF0=0;
    TH0=0xFE;     // 定时器重装初值 fosc=11.0592MHz
    TL0=0x7F;     // 定时器重装初值 fosc=11.0592MHz

    //     TH0       = 0xFD;     // 定时器重装初值 fosc=18.432MHz
    //     TL0   = 0x7F;     // 定时器重装初值 fosc=18.432MHz
}

void WByte(uchar input)
{
    //发送启始位
    uchar j=8;
    TR0=1;
    newTXD=(bit)0;
    WaitTF0();
    //发送8位数据位
    while(j--)
    {
        newTXD=(bit)(input&0x01);       //先传低位
        WaitTF0();
        input=input>>1;
    }

    //发送校验位(无)

    //发送结束位
    newTXD=(bit)1;
    WaitTF0();
    TR0=0;
}    

void Sendata()
{
    for(i=0;i<sizeof(info);i++)//外层循环,遍历数组
    {
          WByte(info[i]);
    }
}

void main()
{
    UartInit();
    while(1)
    {
          Sendata();
    }
}

19260
pqsh 版主
文章数:7424
年度积分:1090
历史总积分:19260
注册时间:2006/8/22
发站内信
2018论坛解答高手
发表于:2010/12/25 20:38:40
#1楼
并口?串口?
其实有个很懒的办法,你把上面的C编译以后,在调试debug或者执行文件里,把汇编disassemble拷贝出来就是了.
如果我忘了我
请帮忙记得我
pqsh@163,326199298@v&q同号
1000
sunsoncheng
文章数:109
年度积分:50
历史总积分:1000
注册时间:2010/5/25
发站内信
发表于:2010/12/26 8:45:33
#2楼
newto equ P1.5;用于模拟串口的IO口
       ;同时在p0.0中闪灯

       ORG    0000H
       LJMP   main

main:
       nop

init0:

MOV TMOD,#21H ;定时器1的启动与工作方式2的设定
      MOV PCON,#80H ;波特率翻倍为
MOV TH0, #0FfH ;定时器0高8位初值
MOV TL0, #2FH ;定时器0的低8位初值;4800BPS
t2:
       ;mov r4,#64H
       mov r5,#064H
d2:
mov r7,#0A0H ;以这个数看是不灯在亮?
lcall sendp
djnz r5,d2
       ;djnz r4,d2

t1:
       mov r3,#05H
       mov r4,#0ffH
       mov r5,#0ffH
d1:     setb newto     ;关灯
djnz r5,d1
       djnz r4,d1
       djnz r3,d1
jmp t2

ret

;;============================================================
;;将R7的数据以P0.0口发送出去!波特率未调为2400
;;============================================================


sendp: ;发送字节
       MOV    R6, #08H ;0000 1000
       SETB   TR0 ;开定时器0
clr newto ;清空P1.5口,这时准备工作?发送的前准备?是高还是低?
       clr p0.0
       LCALL  delaybps ;查是否计时到等到一个新的开始
clr c ;发送前先清空一次
sendbit:

       MOV    A, R7 ;这时的R7是什么值?是要发送的字,数据
       RRC    A ;循环右移,这时的状态是将A(只能是A)向右移一位,且被移出的一位去到了CY处
;所以后面要发送的就是C就行了!
MOV    R7, A ;将新的数放回R7以备下次发送
mov newto,C ;将进位标志的值发送到相关口
       mov p0.0 ,c
       LCALL  delaybps ;等一下个周期到

       CLR    C
djnz r6,sendbit ;减一,不为0则转移

exitsend:
setb newto ;发送完成标志
       setb p0.0
       LCALL  delaybps ;等下一个周期
       CLR    TR0 ;关闭定时器0
       RET

;一直等到计时到了再做工作
delaybps:
       JNB    TF0, delaybps ;查计时器0的溢出标志,为0则转移,且不影响标志位

;此时为标志有溢出,即时间到,重新计数
CLR    TF0 ;计时器0溢出标志清空
       MOV    TH0, #0FfH ;重置计时器0的高8位
       MOV    TL0, #2FH ;重置计时器0的低8位
       RET

;;=============================================================================
;;计时式IO口模拟串口工作完成
;;=============================================================================

   END


这是本人与楼上类似的方法反汇编再理解后得到的结果

如按上面的写法,不断的发送,P0.0及P1.5均有输出,
P0.0是装有发光二极管的,也见到了发光!

但将其信号转到PC机的串口的3线时,却不能在串口模拟工具中收到数据
请指教

关于我们 | 联系我们 | 广告服务 | 本站动态 | 友情链接 | 法律声明 | 非法和不良信息举报

工控网客服热线:0755-86369299
版权所有 工控网 Copyright©2024 Gkong.com, All Rights Reserved

46.8003