24小时热门版块排行榜    

Znn3bq.jpeg
查看: 282  |  回复: 2
当前主题已经存档。
当前只显示满足指定条件的回帖,点击这里查看本话题的所有回帖

yaojinling

金虫 (正式写手)

[交流] 用C语言编写串口程序

用C语言编写串口程序
在当今,流行的编程软件种类繁多,它们编程方便、易于维护,但是在与硬件直接打交道和编制系统软件时却束手无策,于是C语言就有了用武之地。C语言作为汇编语言与高级语言之间的一种过渡语言,兼有汇编语言的高效和高级语言的方便。
  在通讯中,为了保证行运安全可靠,标准的串行口必须具有许多握手信号和状态信息。这是因为通讯的各个计算机CPU速度不一样(这会导致“错帧”)以及发送机发送数据速度比接收机接收速度快(这会导致“过冲”)。为解决这个问题,我们采用一个简单的握手信号,即发送机每次仅发送半个字节(低4位)的数据,而另外半个字节(高4位)则用来传送信息。我们可以对信息位(高4位)进行如下简单的编码:
0H:发送的是新的半个字节数据
1H:重新发送上次传送错误的数据
2H:文件名结束
3H:文件结束
这样,每当发送机发送一个字节以后,就等待接受机发回送信号,这回送信号就是发送机发送过来的那个字节。发送机接收到回送信号后,把它与刚发送的字节相比较,如果相同,就发送新的半个字节,否则就重新发送。新数据与旧数据通过信息位来区分。下面就是用C语言编写控制串行口的程序。
#include "dos.h"
#include "stdlib.h"
#include "stdio.h"
#define PORT 0
void SendFile(char *fname); /* 发送文件*/
void Send(int s); /*发送一个字节*/
void SendFileName(char *fname); /*发送文件名*/
void ReceiveFile(); /*接收文件*/
void GetFileName(char *f); /*接收文件名*/
void InitPort(int port,unsigned char para); /*初始化端口*/
void SendPort(int port,char c); /*端口发送*/
int ReadPort(int port); /*读端口字节*/
int CheckState(int port); /*检查端口状态*/
int Receive(int port,int *G); /*接收一个字节*/
main(int argc,char *argv[])
{
  if(argc<2){
           printf("Please input R(receive) or S(sent) parametre:";
           exit(1);
           }
  InitPort(PORT,231);
  if(*argv[1]==''''S'''') /*检查选择的有效性*/
  SendFile(argv[2]);
   else if(*argv[1]==''''R'''')
    ReceiveFile();
   else{
       printf("Error parament.Please input again.";
       exit(1);
      }
}
void SendFile(char *fname)
{
  FILE *fp;
  int ch,s;
  if((fp=fopen(fname,"rb")==NULL)
                      {
                         printf("Can''''t open the file.\n";
                         exit(1);
                       }
  SendFileName(fname);
  do{
      ch=(int)getc(fp);
      if(ferror(fp)){
                   printf("Error reading file.\n";
                   break;
                }
      s=ch%16; /*取文件中一个字节的低4位*/
      Send(s);
      s=ch/16; /*取文件中一个字节的高4位*/
      Send(s);
     }while(!feof(fp));
  s=46; /*发送文件结束信息*/
  Send(s);
  Send(s);
  fclose(fp);
}
void Send(s)
int s;
{
  int G;
  SendPort(PORT,s);
  G=ReadPort(PORT); /*等待握手信号*/
  if(s!=G)
  s=s+16;
  do{
      SendPort(PORT,s);
      G=ReadPort(PORT);/*等待握手信号*/
  }while(s!=G);
}
void SendFileName(fname)
char *fname;
{
  int s,ch;
  printf("Now transmit the file.Please wait...";
  while(*fname){
                ch=(int)fname++;
                s=ch%16; /*取文件名中一个字节的低4位*/
                Send(s);
                s=ch/16;
                Send(s); /*取文件名中一个字节的低4位*/
               }
  s=32; /*发送文件名结束标志*/
  Send(s);
  Send(s);
}
void ReceiveFile(){
                 FILE *fp;
                 char ch;
                 int G1,G2,G3;
                 char fname[15];
                 GetFileName(fname);
                 printf("Receiving file %s.\n",fname);
                 remove(fname);
                 if((fp=fopen(fname,"wb")==NULL)
                     {
                        printf("Can''''t open output file.\n";
                        exit(1);
                     }
/*循环为检测每次接受的数据是否为新数据,如果不是,*/
/*则用此次接收的数据覆盖上次接收的数据*/
G1=ReadPort(PORT);
G2=Receive(PORT,&G1);
do{
     G3=Receive(PORT,&G2);
     ch=(char)(G1%16+G2*16);/*恢复分开的数据,组合高4位和低4位*/
     putc(ch,fp);
     if(ferror(fp)){
                  printf("\nError writing file.";
                  exit(1);
                }
G2=Receive(PORT,&G3);
  G1=G3;
  }while(G1/16!=48);
  printf("\nTransmit finished.";
  fclose(fp);
}
int Receive(port,G)
int port,*G;
{
    int GM;
    SendPort(port,*G);
    GM=ReadPort(port);
    if(GM/16==0)
    return GM;
    else if(GM/16==1){
                      do{
                          *G=GM;
                          SendPort(port,GM);
                          GM=ReadPort(port);
                         }while(GM/16==1);
                    }
     return GM;
}
void GetFileName(char *f)
{
   int G1,G2,G3;
   char ch;
   G1=ReadPort(PORT);
   G2=ReadPort(PORT);
   do{
       G3=Receive(PORT,&G3);
       ch=(char)(G1%16+G2/16);
       *f=ch;
       *f++;
       G2=Receive(PORT,&G3);
       G1=G3;
     }while(G1/16!=32);
    printf("File name transmit finished.\n";
}
void InitPort(port,para)
int port;
unsigned char para;
{
   union REGS reg;
   reg.x.dx=port;
   reg.h.ah=0;
   reg.h.al=para;
   int86(0x14,®,®;
}
void SendPort(port,c)
int port;
char c;
{
   union REGS reg;
   reg.x.dx=port;
   reg.h.al=c;
   reg.h.ah=1;
   int86(0x14,®,®;
   if(reg.h.ah&128){
                   printf("\nSend mistakes!";
                   exit(1);
                 }
}
int ReadPort(port)
int port;
{
   union REGS reg;
   while(!(CheckState(port)&256)){
   if(kbhit()){/*如端口长期无数据可人为终止等待*/
             printf("Press any key to exit.";
             getch();
             exit(1);
           }
}
   reg.x.dx=port;
   reg.h.ah=2;
   int86(0x14,®,®;
   if(reg.h.ah&128){
                   printf("\nRead mistake!";
                   exit(1);
                 }
  return reg.h.al;
}
int CheckState(port)
int port;
{
   union REGS reg;
   reg.x.dx=port;
   reg.h.ah=3;
   int86(0x14,®,®;
   return reg.x.ax;
}

以上程序可传送各种格式的文件,也有一定的自动纠错能力,但对于异常情况的
处理能力比较弱,读者可以自己改进。由于篇幅限制,对于中断14H的功能、入
口参数及返回参数的意义请读者自己查有关资料。

[ Last edited by sdlwwxb on 2005-12-16 at 17:58 ]
回复此楼

» 猜你喜欢

已阅   回复此楼   关注TA 给TA发消息 送TA红花 TA的回帖

imrking

荣誉版主 (著名写手)

下雨了,别忘了打伞,湿身是小,淋病就麻烦啦~~~:)
3楼2005-11-18 19:48:12
已阅   回复此楼   关注TA 给TA发消息 送TA红花 TA的回帖
查看全部 3 个回答

yaojinling01

0.5

谢谢!!!!!!111
2楼2005-11-18 18:33:26
已阅   回复此楼   关注TA 给TA发消息 送TA红花 TA的回帖
普通表情 高级回复 (可上传附件)
最具人气热帖推荐 [查看全部] 作者 回/看 最后发表
[考研] 材料307分求大佬组收留 +17 Hll胡 2026-04-07 17/850 2026-04-09 10:53 by liuhuiying09
[考研] 085600材料与化工专硕329 求调剂 +22 额cc 2026-04-06 23/1150 2026-04-09 09:02 by 5268321
[考研] 二次调剂求老师收留 +3 笑笑袁 2026-04-08 3/150 2026-04-08 23:50 by 醉在风里
[考研] 302分求调剂 +4 凡语祈愿 2026-04-08 5/250 2026-04-08 22:03 by 土木硕士招生
[考研] 324求调剂 +17 想上学求调 2026-04-03 17/850 2026-04-08 20:04 by 我减肥1
[考研] 一志愿郑州大学085600求调剂 +21 吃的不少 2026-04-05 24/1200 2026-04-08 16:47 by sunhuadong
[考研] 化工学硕 285求调剂 +26 Wisjxn 2026-04-07 26/1300 2026-04-08 14:42 by screening
[考研] 求材料调剂,一志愿郑州大学289分 +21 硕星赴 2026-04-03 21/1050 2026-04-08 11:55 by 猪会飞
[考研] 材料专硕 调剂 +17 CXN123456 2026-04-03 17/850 2026-04-08 11:10 by lijunpoly
[考研] 313求调剂 +3 十六拾陆 2026-04-07 3/150 2026-04-07 23:20 by lbsjt
[考研] 材料调剂 +11 一样YWY 2026-04-07 11/550 2026-04-07 15:13 by shdgaomin
[考研] 材料工程302分求调剂 +13 zyx上岸! 2026-04-04 13/650 2026-04-07 11:14 by 诗与自由
[考研] 307求调剂 +3 所念及所望 2026-04-06 3/150 2026-04-06 17:30 by 土木硕士招生
[考研] 生物学求调剂 +5 15064154688 2026-04-03 5/250 2026-04-06 11:56 by lijunpoly
[考研] 324求调剂 +3 k可乐 2026-04-05 4/200 2026-04-06 09:54 by 蓝云思雨
[考研] 一志愿211,化学学硕,310分,本科重点双非,求调剂 +13 努力奋斗112 2026-04-04 13/650 2026-04-06 07:13 by jj987
[考研] 考研调剂 +5 美丽的youth_ 2026-04-04 6/300 2026-04-06 06:57 by houyaoxu
[考研] 一志愿北交大材料工程总分358求调剂 +6 cs0106 2026-04-05 6/300 2026-04-05 16:34 by imissbao
[考研] 11408 一志愿西电,277分求调剂 +4 zhouzhen654 2026-04-03 4/200 2026-04-04 18:10 by 猪会飞
[考研] 数二英二348求调剂 +4 hxdzj1 2026-04-03 5/250 2026-04-03 21:25 by zhq0425
信息提示
请填处理意见