刘毅 刘伟
摘要:本文主要介绍模拟复印机生产组装过程中,在TM与IOT组装前设计一个检测装置,对TM的各组件状态及传感器进行检测,确保组装到IOT整机后,TM均为良品。以此解决原生产方式中的弊端。
关键词:单片机串口通信TM(Tray Module)IOT(Image Output Terminal)
中图分类号:TS261 文献标识码:A 文章编号:1672-3791(2012)08(c)-0030-02
1设计构想
多功能复印机现有工程生产方式如图1,这种生产方式操作麻烦,且容易造成二次人为故障,生产效率低。基于这种考虑,将生产过程改良如下,可解决原生产方式的弊端(如图2)。
2检测器设计
TM与IOT由物理层,数据连接层,虚拟命令层构成。本设计利用虚拟命令层获取相关信息,完成检测目的。综合考虑成本,设计周期,难易度等因素,最终选定单片机+LCD作为设计课题。
检测器系统如图3所示,单片机:采用ATMEGA48单片机完成整个检测器的控制;LCD:显示TM的动态信息,TM内部故障发生时报警;电源控制:当检测器检测到正确连接到TM时,启动按键,延时1秒钟向TM供电,检测过程中,一时发生故障,系统自动供电电源,防止二次故障发生;LED蜂鸣:LED显示数据的发送接收状态,有数据传输时LED闪烁,异常时蜂鸣器报警。
3程序设计
主程序中各子程序通过标识状态作相应处理。串口数據读取利用单片机串口中断函数,非常方便于数据的连续发送与接收。
3.1 程序代码
3.1.1 主程序
/************************************** *************************************************
#include "common.h"
………
intmain(void)
{ Sys_Init(); //系统初始化
………….
TIMSK0 |=(1< sei(); while(1) {wdt_reset();//喂狗 if(Key_Ctr==1){Key_Control(); Key_Ctr=0;} // 按键处理 if(Buzzer_F!=0){Buzzer_On(Buzzer_F);Buzzer_F=0;} // 蜂鸣 if((Error_F!=0)&&(Run_F!=0)){Buzzer_F=1;} // 报警处理 if(Send_F==1){USART_Data_Send();Send_F=0;} // 数据传送 if(rx_buffer.flag == FLAG_RECEIVE_OK) // 如果串口接收到完整的数据帧,则进行处理 {USART_CMDProcess(); USART_ClearRXBuffer(); Time_Out=0;//通信超时计时结束 Time_Out_Sec=0; } if(tx_buffer.flag == FLAG_SEND_REQUEST) // 如果串口发送缓冲区有发送请求,执行发送 {USART_SendString(); tx_buffer.flag = FLAG_EMPTY; Time_Out=1; //通信超时计时开始} if(RefreshLCD_F){ RefreshLCD();RefreshLCD_F=0;} // 如果LCD有刷新请求,则刷新LCD}} 3.1.2 串口中断程序代码 #include "common.h" ……… RX_BUFFER rx_buffer;//接收数据结构体实例 TX_BUFFER tx_buffer;//发送数据结构体实例 static ucharNO_CMD_D5[5]={0xD5,0x00,0x00,0x00,0x55}; ……………. /****************************** ******************************************串口初始化 voidUSART_init(uint baud) {UBRR0H=baud>>8; UBRR0L=baud&0x00FF; UCSR0A=0x00; //U2xn=0,波特率无倍速 UCSR0B=(1< UCSR0C=(1< USART_ClearRXBuffer(); USART_ClearTXBuffer();} /******************************** *****************************************数组发送 void USART_Data_Send(void) {uchar i; switch(Data_F) { case 1:{for(i=0;i
………
case 6:{for(i=0;i default:; }} /************************************** *****************************TRAY-STS数据处理 void USART_CMDProcess(void) {if(rx_buffer.buff[1]==0x03)//本组数据为TM 版本数据 {Ver_D=(rx_buffer.buff[3]>>3)&0x03;; //实验/恒久 Ver_H=rx_buffer.buff[3]&0x07;//TM版本上位 Ver_L=rx_buffer.buff[2]&0x3F;//TM版本下位 RefreshLCD_F=2;} else if(rx_buffer.buff[1]==0x04) //本组数据为TRAY_STS { TM_No=rx_buffer.buff[2]&0x03;//取出TRAY编号 00->No2 01->No3 10->No4 TM_Status=(rx_buffer.buff[2]>>2)&0x07; //TRAY状态 000->准备好 001->上升 010->Tary拔 出 011->无纸 100->上升NG 101->NC 110->上升3次NG 111->SizeSensor NG ASize=(rx_buffer.buff[2]>>5)|(rx_buffer.buff[3]<<2); //SizeSensor模拟电压AD值 DSize=(rx_buffer.buff[3]>>6)&0x01;//SizeSensor数字位 0,1 RefreshLCD_F=3;} else; } /****************************** **************************************清空接收缓冲区 void USART_ClearRXBuffer(void) { uchar i; for(i=0; i rx_buffer.rxcount = 0; // 计数值清零 rx_buffer.flag = FLAG_EMPTY;} /************************ *******************************向接收缓冲区中添加一个字节 uchar USART_AddToRXBuffer(uchar ch) { if(rx_buffer.rxcount >= RX_MAX){ return ERROR_RXBUFFER_FULL;} // 缓冲区满 else { rx_buffer.buff[rx_buffer.rxcount] = ch;// 将要添加的字节保存到当前计数值指向的位置 rx_buffer.rxcount ++; // 缓冲区的长度增加1 wdt_reset();//喂狗 return ADD_CHAR_OK; // 返回添加成功信息}} /**************************** *******************************清空发送缓冲区 void USART_ClearTXBuffer(void) { uchar i; for(i=0; i { tx_buffer.buff[i] = 0x00; // 缓冲区当前元素清空 wdt_reset();//喂狗} tx_buffer.txcount = 0; // 计数值清零 tx_buffer.flag = FLAG_EMPTY;} /**************************** *******************************向发送缓冲区中添加一个字节 uchar USART_AddToTXBuffer(uchar ch) {if(tx_buffer.txcount > TX_MAX){ return ERROR_TXBUFFER_FULL;} // 缓冲区满 else {wdt_reset(); tx_buffer.buff[tx_buffer.txcount] = ch;// 将要添加的字节保存到当前计数值指向的位置 tx_buffer.txcount ++; // 缓冲区的长度增加1 wdt_reset();//喂狗 if(tx_buffer.txcount == TX_MAX) {tx_buffer.flag = FLAG_SEND_REQUEST; // 填充完毕指定数量数据,设置发送请求} return ADD_CHAR_OK; // 返回添加成功信息}} /************************ ***************************将发送缓冲区的内容一次性发送 void USART_SendString(void)
{ UDR0=tx_buffer.buff[0]; //从结构数据的第1个数开始发送
tx_buffer.txcount=0;}
/**************************** ************************串口發送中断服务函数
SIGNAL(SIG_USART_TRANS)
{ if(++tx_buffer.txcount else if(tx_buffer.txcount==TX_MAX) { USART_ClearTXBuffer(); //发送完毕 USART_ClearRXBuffer(); //作好接收准备 } else;} /************************** ***************************串口接收完毕中断服务函数 SIGNAL(SIG_USART_RECV) {rx_buffer.buff[rx_buffer.rxcount] = UDR0; rx_buffer.rxcount ++; if(rx_buffer.rxcount >= RX_MAX){ rx_buffer.flag = FLAG_RECEIVE_OK;}} 3.1.3 LCD显示程序代码(纸型检出部份) void RefreshLCD(void)/*刷新LCD显示*/ {if(RefreshLCD_F==1)//LCD刷新标识 0:无效 1:框架显示 2:版本显示3:数据显示4:刷新机种 { if(TM_Status==2){disp_String(x,y,(uchar *)"已取出");}//纸盒拔出 else{ if((199 {disp_String(x,y,(uchar *)"A5 SEF");} else if((184 {disp_String(x,y,(uchar *)"B5 SEF");} …………….. else if((0 {disp_String(x,y,(uchar *)"11x17SEF");} else{disp_String(x,3,(uchar *)" ErrorSize"); }//纸型错误} } 4结果测试 只要是TM组件自身的故障都就能检出,如TM纸型感知传感器未安装或接触不良、TM控制器版本错误等。目前为止,没有一件因TM不良而导致整机拆卸的维修事件,提高了生产效率。 参考文献 [1] 芯艺.AVR单片机GCC程序设计[J].单片机技术应用,2005,1,1. [2] 陈勇.基础工业工程[J].工业技术,2010,7,1. [3] 吴锴,郭海霞.单片机串行口的扩展研究[J].单片机技术,2010,5,19.