⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vaccum.c

📁 C8051f020与气压传感器HP03S制作的气压测试仪
💻 C
📖 第 1 页 / 共 2 页
字号:
/************************************************************************
        copyright (c) 2007                                                           
Titl    Altitud meter
Current version:          v1.0 
Function:      		Measure temperature / pressure / altitude           
Processor                    C8051F230 + HP03S
Clock:                          22.1184MHz Crystal 
Author:                       jIM tIEN 
Company:                      cROSSMIND
Contact:                      +86-0755-3880100 
E-MAIL:                        txj@crossmind.cn
Date:                            2008-4-11                                        

                        P0.4---------------->SCL         
                        P0.5<--------------->SDA 
                        P0.6---------------->XCLR 
                        P0.7---------------->MCLK 
********************************************************************/ 
#include <c8051f200.h>
#include <stdio.h>
//#include <reg52.h>
#include <math.h> 
#define MaxPress    1100      //1100Hpa 
#define SYSCLK		22118400		//11059200
#define HP03SMCLK	32768
//V3.1
//#define BAUDRATE	115200

//V3.2
#define BAUDRATE 	38400

#define RS485
#define TIMEOUT		60 				//unit: =60*0.5 second

#define INBUF_LEN 	5   		//数据长度
#define STARTBYTE	0x24		//
#define MYADD		0xE4		//Barmeter Add = 0xE4
//MOTOR MODULE ADD = 0xE3	, 0xE2 - LDDRIVER, 0xE1 - PZT DRIVER	
#define GETTEMP		0xAA		//取温度/压力值命令
#define GETPRESS	0XBB		//压力值命令
#define SETDATA		0xCC		//设置相对气压值
#define ORIGNAL		0xDD		//设置当前气压为基准气压
#define VACCUMON	0x01		//启动抽气机
#define VACCUMOFF	0x00		//关闭抽气机
#define RELEASEON	0x02		//排空阀ON
#define RELEASEOFF	0x03		//排空阀OFF

unsigned char inbuf1[INBUF_LEN];
unsigned char count;
bit read_flag = 0;

//function declaration 
//*****************
void IIC_ReadCalData(void); 
void ReadTemperaturePreesureAD(void);
unsigned int IIC_ReadTempretureAD(void);
unsigned int IIC_ReadPressureAD(void); 
void CalculatePressTemp(bit); 
void CalculateAltitude(void); 
void IIC_ReadCalData(void); 
unsigned char IIC_ReadByte(void);
void IIC_WriteByte( unsigned char);
void IIC_Start(void); 
void IIC_Stop(void); 
void IIC_ACK(void); 
void IIC_NoAck(void);
void IIC_SDA_HIGH(void);
void IIC_SDA_LOW(void); 
void IIC_SCL_HIGH(void); 
void IIC_SCL_LOW(void); 
void IIC_XCLR_LOW(void); 
void IIC_XCLR_HIGH(void); 
void SysDelay2ms(unsigned int);//
void SysDelay20us(void);// 
void ClockDelay2ms(unsigned int);//

void MCLKOn(void);

//symbol defined   
sbit SCL = P2^0;
sbit SDA = P2^1; 
sbit XCLR = P2^2;
sbit MCLK = P2^3; 
#ifdef RS485
sbit    RS485_DE = P1^0;
#endif
sbit RELAY = P1^1;      //CONTROL VACCUM
sbit RELAY2 = P1^3;		//排空阀 
sbit TestPin = P1^2;

unsigned int C1;
unsigned int C2 ; 
unsigned int C3 ; 
unsigned int C4 ; 
unsigned int C5 ; 
unsigned int C6 ; 
unsigned int C7 ; 

unsigned char AAA;
unsigned char BB ; 
unsigned char CC ; 
unsigned char DD ; 
unsigned int D1;
unsigned int D2 ;
long float DUT;
long float OFF; 
long float SENS;
long float X; 
long float    Press;
long float    Temp; 
long    Altitude;

bit bMCLKOn = 0; 
unsigned int systimer1;

//**********************************   
//comparison table for pressure and altitude 
//***********************************
long code Tab_BasicAltitude[80]={-6983,-6201,-5413,-4620,-3820,-3015,-2203,-1385,-560, 270,    //0.1m 
    //    1100    1090    1080    1070    1060    1050    1040    1030    1020    1010  //hpa
    1108, 1953, 2805, 3664, 4224, 5403, 6284, 7172, 8068, 8972,     
    //    1000    990      980      970      960      950      940      930      920    910     //hpa 
    9885, 10805,11734,12671,13617,14572,15537,16510,17494,18486, 
    //    900      890      880      870      860      850      840      830      820      810       //hpa
    19489,20502,21526,22560,23605,24662,25730,26809,27901,29005, 
    //    800      790      780      770      760      750      740      730      720      710    //hpa
    30121,31251,32394,33551,34721,35906,37106,38322,39553,40800, 
    //    700      690      680      670      660      650      640      630      620      610    //hpa
    42060,43345,44644,45961,47296,48652,50027,51423,52841,54281, 
    //    600      590      580      570      560      550      540      530      520      510    //hpa
    55744,57231,58742,60280,61844,63436,65056,66707,68390,70105, 
    //    500      490      480      470      460      450      440      430      420      410    //hpa
    71854,73639,75461,77323,79226,81172,83164,85204,87294,89438}; 
//    400      390      380      370      360      350      340      330      320      310    //hpa


void SYSCLK_Init(void)
{
    int i;                              // delay counter
    //initial system clock
    OSCXCN = 0x67;                      // start external oscillator with 22.1184MHz crystal
    for (i=0; i < 256; i++) ;           // Wait for osc. to start up
    while (!(OSCXCN & 0x80)) ;          // Wait for crystal osc. to settle
    OSCICN = 0x88;                      // select external oscillator as SYSCLK source and enable missing clock detector
}

void PORT_Init (void)
{
    //uart0, p1.0/p1.1/P1.2/P1.3/p2.0/p2.2/p2.3 push-pull

    PRT0MX    = 0x01;
    PRT1CF    = 0x0F;
    PRT2CF    = 0x0D;
    RELAY     = 0;
}

void Serial_Init(void)
{
    SCON  = 0x50;                      // SCON1: mode 1, 8-bit UART, enable RX
    TMOD  &= 0x0F;
    TMOD  |= 0x20;                      // TMOD: timer 1, mode 2, 8-bit reload
    TH1    = -(SYSCLK/BAUDRATE/16);     // set Timer1 reload value for baudrate
    TL1    = -(SYSCLK/BAUDRATE/16);     // set Timer1 reload value for baudrate
    TR1    = 1;                         // start Timer1
    CKCON |= 0x10;                      // Timer1 uses SYSCLK as time base
    PCON  |= 0x80;                      // SMOD0 = 1
    ES = 1;
    TI = 0;
}


//向串口发送一个字符 
void send_char_com(unsigned char ch)  
{
#ifdef RS485
    RS485_DE = 1;
#endif

    SBUF = ch;
    while (TI == 0);
    TI = 0;
#ifdef RS485
    RS485_DE = 0;
#endif

}

//向串口发送一个字符串,strlen为该字符串长度 
void send_string_com(unsigned char *str,unsigned int strlen)
{
    unsigned int k=0;
    do {
        send_char_com(*(str + k));
        k++;
    } while (k < strlen);
}


//串口接收中断函数 
void serial () interrupt 4 using 3 
{
    unsigned char ch;

    ES = 0;
    if (RI && read_flag==0) {
        RI = 0;
        ch = SBUF;
        if ( count ==0) {          //startbyte
            if (ch == STARTBYTE)
                inbuf1[count++] = ch;
        } else
            if (count == 1) {      //add
            if (ch == MYADD)
                inbuf1[count++] = ch;
            else
                count = 0;
        } else {
            inbuf1[count++] = ch;
            if ( inbuf1[2]== SETDATA) {
                if ( count == INBUF_LEN) {
                    count =0;
                    read_flag = 1;
                }
            } else
                if (count == INBUF_LEN -1) {
                count =0;
                read_flag = 1;
            }
        }
    }
    ES = 1;

}


void Timer_Init(void) 
{   
    TMOD &= 0xF0;
    TMOD |= 0x02;           //TIMER0: MODE2, 8BIT AUTO-RELOAD, TIMER1: MODE 1, 16BIT
    TH0 = 256 - SYSCLK/12/(2*HP03SMCLK);
    TL0 = 256 - SYSCLK/12/(2*HP03SMCLK);
    PT0 = 1;
    ET0 = 1; 
    TR0 = 1; 

}

bit SetVaccum(int Vaccum)
{
    unsigned int i=0,testpress;
    unsigned char breach = 0;

    RELAY = 1;              //start bumper
    while (1) 
	{
        TestPin = ~TestPin;          
        i++;
        ClockDelay2ms(250);     //delay 500ms

        //check pressure
        ReadTemperaturePreesureAD(); 
        CalculatePressTemp(0);          //don't test temperature

        testpress =  (unsigned int)(Press/10.0);

        if (testpress < Vaccum)
            breach ++;
        else
            breach = 0;

        if (breach >= 3) {
            RELAY = 0;
            return 1;
        } else if (i >= TIMEOUT) {       //
            RELAY = 0;
            return 0;
    }
    }
}

void main(void) 
{
    unsigned int ipress, ipress0 = 0;
    int ripress=0;
    int itemp;
	P1 = 0;
    WDTCN = 0xDE;       //0xDE and 0xAD:disable, 0xA5:enable
    WDTCN = 0xAD;
    SYSCLK_Init();
    PORT_Init();
    RELAY = 0;
	RELAY2 = 0;

    Serial_Init();
    Timer_Init();
    EA = 1; 

    SysDelay2ms(50); 
    IIC_ReadCalData(); 

#ifdef RS485
    RS485_DE = 0;
#endif

    ReadTemperaturePreesureAD(); 
    CalculatePressTemp(0); 
    ipress0 = (unsigned int)(Press/10.0);

    while (1) {
        if (read_flag) {  //如果取数标志已置位,就将读到的数从串口发出 
            ES = 0;       //禁止串口中断

            if (inbuf1[2]== GETPRESS && inbuf1[3]==GETPRESS) {
                ReadTemperaturePreesureAD(); 
                CalculatePressTemp(0); 

                ipress =  (unsigned int)(Press/10.0);
                inbuf1[2] = ipress >>8;     //high byte
                inbuf1[3] = ipress &0x00ff; //low byte

                send_string_com(inbuf1,INBUF_LEN - 1);

            } else if (inbuf1[2]== GETTEMP && inbuf1[3]==GETTEMP) {
                ReadTemperaturePreesureAD(); 
                CalculatePressTemp(1); 

                itemp =  (int)Temp;
                inbuf1[2] = itemp >>8;      //high byte
                inbuf1[3] = itemp &0x00ff;  //low byte

                send_string_com(inbuf1,INBUF_LEN - 1);

                ipress =  (unsigned int)(Press/10.0);
                inbuf1[2] = ipress >>8;     //high byte
                inbuf1[3] = ipress &0x00ff; //low byte

                send_string_com(inbuf1,INBUF_LEN - 1);

            } else if (inbuf1[2] == ORIGNAL) {
                ReadTemperaturePreesureAD(); 
                CalculatePressTemp(0); 
                ipress0 =  (unsigned int)(Press/10.0);
                send_string_com(inbuf1,INBUF_LEN - 1);

            } else if (inbuf1[2]== SETDATA) {
                ripress = inbuf1[3];
                ripress <<= 8;
                ripress |= inbuf1[4];
                if (ripress > 0) {
                    inbuf1[3] = 0;
                    inbuf1[4] = 0;
                } else if (!SetVaccum(ipress0 + ripress)) {
                    inbuf1[3] = 0xff;
                    inbuf1[4] = 0xff;   
                }

                send_string_com(inbuf1,INBUF_LEN);
            } 
			else if(inbuf1[2]== VACCUMON) {
					RELAY = 1;
					send_string_com(inbuf1,INBUF_LEN - 1);
			 }
			else if(inbuf1[2]== VACCUMOFF) {
					RELAY = 0;
					send_string_com(inbuf1,INBUF_LEN - 1);
			}
			else if(inbuf1[2]== RELEASEON) {
					RELAY2 = 1;
					send_string_com(inbuf1,INBUF_LEN - 1);
 		    }
			else if(inbuf1[2]== RELEASEOFF) {
					RELAY2 = 0;
					send_string_com(inbuf1,INBUF_LEN - 1);
			}
            read_flag=0; //取数标志清0 
            ES = 1;
        }
    }
} 

//*************************
//function: calculate power for 2 
//**************************
long int Get2_x(unsigned char i) 
{ 
    long int uiData;
    uiData=2; 
    i=i-1; 
    while (i) {
        uiData <<= 1;
        i--; 
    } 
    return uiData; 
} 

//***********************************
//function:calculate press and temperature 
//input      :D1,D2,C1---C7,AA,BB,CC,DD
//output    :Press, unit: 0.01hpa 
//                temp, unit: 0.1℃ 
//************************
void CalculatePressTemp(bit btesttemp) 
{ 
    long float MiddleData1;
    long float MiddleData2; 
    long float MiddleData3; 
    long float MiddleData4; 

    //   calculate the DUT value 
    if (D2<C5) {
        DUT = D2-C5-((D2-C5)/Get2_x(7))*((D2-C5)/Get2_x(7))*BB/Get2_x(CC); 
        MiddleData1 = (long)D2-C5; 
        MiddleData2 = MiddleData1*MiddleData1/16384;   
        MiddleData3 = MiddleData2*BB; 
        MiddleData4 = Get2_x(CC); 
        MiddleData4 = MiddleData3/MiddleData4; 
        DUT = MiddleData1 - MiddleData4; 
    } else {
        //DUT = D2-C5-((D2-C5)/Get2_x(7))*((D2-C5)/Get2_x(7))*AA/Get2_x(C); 
        MiddleData1 = D2-C5; 
        MiddleData2 = MiddleData1 * MiddleData1 / 16384; 
        MiddleData3 = MiddleData2 * AAA; 
        MiddleData4 = Get2_x(CC); 
        MiddleData4 = MiddleData3/MiddleData4; 
        DUT = MiddleData1 - MiddleData4; 
    } 
    //calculate the OFF value 
    //OFF = (C2+(C4-1024)*DUT/Get2_x(14))*4; 
    MiddleData1 = (long)C4-1024; 
    MiddleData2 = Get2_x(14); 
    MiddleData3 = DUT*MiddleData1; 
    MiddleData4 = MiddleData3/MiddleData2;
    MiddleData4 = (long)C2+MiddleData4; 
    OFF = MiddleData4*4; 

    //calculate the SENS value 
    //SENS = C1+C3*DUT/Get2_x(10); 
    MiddleData1 = (long)C3*DUT; 
    MiddleData2 = Get2_x(10); 
    MiddleData3 = MiddleData1/MiddleData2; 
    SENS = C1+MiddleData3; 

    //calculate the X value 
    //X = SENS*(D1-7168)/Get2_x(14)-OFF; 
    MiddleData1 = Get2_x(14); 
    MiddleData2 = (long)D1-7168;
    MiddleData3 = MiddleData2*SENS;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -