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

📄 udoslnk.c

📁 DALLAS 1 Wire 总线 SDK 支持多种高级语言
💻 C
📖 第 1 页 / 共 2 页
字号:
//---------Copyright (C) 1997 Dallas Semiconductor Corporation--------------
//
//  COMUT.C - This source file contains the COM specific utility funcs
//            for 16 bit COM communication.
//
//  Compiler: VC
//  Version:
//

// includes
#include <windows.h>
#include <stdio.h>
#include <conio.h>
#include "dos.h"
#include "ownet.h"
#include "ds2480.h"

// local function prototypes
SMALLINT OpenCOM(int, char *);
SMALLINT SetupCOM(int, ulong);
void     FlushCOM(int);
void     CloseCOM(int);
int      WriteCOM(int, int, uchar *);
int      ReadCOM(int, int, uchar *);
void     BreakCOM(int);
void     SetBaudCOM(int, uchar);
void PowerCOM(int, short);
//IBAPI RTSCOM(short, short);
//void StdFunc WaitWriteCOM(short);
void     MarkTime(void);
SMALLINT ElapsedTime(long);
//IBAPI DSRHigh(short);
void     msDelay(int);
void     Sleep(long);
long     msGettick(void);


// serial interrupt service routines
void __interrupt __far  com_serial_int4(ushort,ushort,ushort,ushort,ushort,ushort,ushort,ushort,ushort,
                                                          ushort,ushort,ushort,ushort);
void __interrupt __far  com_serial_int3(ushort,ushort,ushort,ushort,ushort,ushort,ushort,ushort,ushort,
                                                          ushort,ushort,ushort,ushort);

// globals to be used in communication routines
#define INBUF_MASK  63    // mask to and with current pointer
#define INBUFSIZ    64    // number of chars in buffer, 64
// defines to make Microsoft C compatible
#define inportb   inp
#define outportb  outp

static ulong TimeStamp;
static ulong BigTimeStamp;
static ulong MilliSec=2386;
static HANDLE ComID[MAX_PORTNUM];
static SMALLINT PortState_init = FALSE;


// structure to reference 8250 registers
typedef struct
{
  union
  {
     int com_regs[7];
     struct
     {
          union
          {
               ushort lsb;    // least significant byte of divisor
               ushort rbr;    // receive buffer register
               ushort tbr;    // transmit buffer register
          }  a;
          union
          {
               ushort msb;    // most significant byte of divisor
               ushort ier;    // interrupt enable register
          }  b;
          ushort iir;       // interrupt id register
          ushort lcr;       // line control register
          ushort mcr;       // modem control register
          ushort lsr;       // line status register
          ushort msr;       // modem status register
     } nam;
  };
} comtype;

// structure to hold the state of the port
typedef struct
{
   ushort com_vec_n;        // vector number com jumps through
   ushort m8259_mask;       // 8259 interrupt request mask
   ushort port_adr;         // address of port.  3f8 or 2f8
   uchar  inbuf[INBUFSIZ];  // input buffer
   ushort inbuf_n;          // number of chars in buffer
   ushort inbuf_get;        // point to beginning of buffer
   ushort inbuf_put;        // next incoming char goes here
   void (_interrupt _far *save_vec)();
   comtype com;

} PortStateType;

volatile PortStateType PortState[16];


// last port written/read from
volatile short LastPrt=0;

//---------------------------------------------------------------------------
// Attempt to open a com port.  Keep the handle in ComID.
// Set the starting baud rate to 9600.
//
// 'portnum'   - number 0 to MAX_PORTNUM-1.  This number provided will
//               be used to indicate the port number desired when calling
//               all other functions in this library.
//
//
// Returns: the port number if it was succesful otherwise -1
//
int OpenCOMEx(char *port_zstr)
{
   int portnum;

   if(!PortState_init)
   {
      int i;
      for(i=0; i<MAX_PORTNUM; i++)
         PortState[i].port_adr = 0;
      PortState_init = TRUE;
   }

   // check to find first available handle slot
   for(portnum = 0; portnum<MAX_PORTNUM; portnum++)
   {
      if(!ComID[portnum])
         break;
   }

   OWASSERT( portnum<MAX_PORTNUM, OWERROR_PORTNUM_ERROR, -1 );

   if(!OpenCOM(portnum, port_zstr))
   {
      return -1;
   }

   return portnum;
}

//---------------------------------------------------------------
//  Description:
//     Attept to open a com port.
//  portnum    - number 0 to MAX_PORTNUM-1.  This number is provided to
//                 indicate the symbolic port number.
//  port_zstr  - the string of the port to be used
//
//     Returns FALSE if unsuccessful and TRUE if successful.
//
SMALLINT OpenCOM(int portnum, char *port_zstr)
{
   ushort i,port_val;
   ushort far *ptr = (ushort far *) 0x00400000;
   ushort Prt = atoi(&port_zstr[3]);
   uchar buff[5];

   if(!PortState_init)
   {
      for(i=0; i<MAX_PORTNUM; i++)
         PortState[i].port_adr = 0;
      PortState_init = 1;
   }

   OWASSERT( portnum<MAX_PORTNUM && portnum>=0 && !PortState[portnum].port_adr,
             OWERROR_PORTNUM_ERROR, FALSE );

   // reset the state of this port
   PortState[portnum].port_adr = 0;
   PortState[portnum].inbuf_n = 0;
   PortState[portnum].inbuf_get = 0;
   PortState[portnum].inbuf_put = 0;

   // check if already setup
   if (PortState[portnum].port_adr != 0)
      return SetupCOM(portnum,9600);

   port_val = *(ptr + Prt - 1);    // get the port base

   if (port_val == 0x3f8 || port_val == 0x3e8) // COM1 or COM3
   {
       PortState[portnum].com_vec_n  = 0x0c;            // jump thru vectory C
       PortState[portnum].m8259_mask = 0x0ef;           // mask bit 4
   }
   else if (port_val == 0x2f8 || port_val == 0x2e8)  // COM2 or COM4
   {
       PortState[portnum].com_vec_n  = 0x0b;            // jump thru vectory B
       PortState[portnum].m8259_mask = 0x0f7;           // mask bit 3
   }
   else                             // must have found a non standard base
       return FALSE;

   PortState[portnum].port_adr = port_val;             // global assignments

   for (i = 0; i < 7; ++i)          // set the port values of the registers
      PortState[portnum].com.com_regs[i] = PortState[portnum].port_adr + i;

   PortState[portnum].save_vec = _dos_getvect(PortState[portnum].com_vec_n);  // save the current ISR vector

   // setup ISR depending on interrupt
   if (PortState[portnum].com_vec_n  == 0x0c)
   {
      printf("setting up com1 interupt.\n");
      _dos_setvect(PortState[portnum].com_vec_n, com_serial_int4);
   }
   else
      _dos_setvect(PortState[portnum].com_vec_n, com_serial_int3);

   _disable();         // disable interrupts while setting up ISR

   // clear dlab in LCR
   i = inportb(PortState[portnum].com.nam.lcr);
   outportb(PortState[portnum].com.nam.lcr,(uchar)(0x7F & i));

   // set rts and dtr in MCR
   outportb(PortState[portnum].com.nam.mcr,0x0B);

   // interrupt on received data available in IER
   outportb(PortState[portnum].com.nam.b.ier,0x01);

   // clear bit (3 or 4) so it interrupts unmasked
   i = inportb(0x21);
   outportb(0x21,(uchar)(PortState[portnum].m8259_mask & i));

   // read in what is there
   i = inportb(PortState[portnum].com.nam.a.rbr);

   // set the baudrate
   SetupCOM(portnum,9600);

   // clear the interrupt
   inportb(PortState[LastPrt].com.nam.iir);

   // reset the buffer counters
   PortState[portnum].inbuf_n   = 0;
   PortState[portnum].inbuf_get = 0;
   PortState[portnum].inbuf_put = 0;
   LastPrt = portnum;

   _enable();         // re-enble interrupts

   // make sure the device is powered
   outportb(PortState[portnum].com.nam.mcr,0x0B);

   // reset byte operation
   FlushCOM(portnum);
   buff[0] = (uchar) (CMD_COMM | FUNCTSEL_RESET | 0);
   if(!WriteCOM(portnum,1,buff))
      return FALSE;
   Sleep(5);
   FlushCOM(portnum);

   return TRUE;         // return success
}


//-------------------------------------------------------------------
//  Description:
//     Closes the connection to the port.
//
//  portnum    - number 0 to MAX_PORTNUM-1.  This number is provided to
//                 indicate the symbolic port number.
//
//     Returns FALSE if unsuccessful and TRUE if successful.
//
void CloseCOM(int portnum)
{
   // clear port address (use as flag)
   PortState[portnum].port_adr = 0;

   // restore previous interrupt
   _dos_setvect(PortState[portnum].com_vec_n, PortState[portnum].save_vec);

   _disable();                    // disable interrupts

   // set bit (3 or 4) so it interrupts unmasked
   outportb(0x21,(uchar)(~PortState[portnum].m8259_mask | inportb(0x21)));

   // clear dlab in LCR
   outportb(PortState[portnum].com.nam.lcr, (0x7f & inportb(PortState[portnum].com.nam.lcr)));

   // clear interrupt on receive in IER
   outportb(PortState[portnum].com.nam.b.ier, 0);

   // rts and out2 off. leave dtr alone in MCR
   //????????outportb(PortState[Prt].com.nam.mcr, (0x01 & inport(PortState[Prt].com.nam.mcr)));

   _enable();                     // re-enable interrupts

}


//-------------------------------------------------------------------
// Read an array of bytes to the COM port, verify that it was
// sent out.  Assume that baud rate has been set and the buffers have
// been flushed.
//
//  portnum    - number 0 to MAX_PORTNUM-1.  This number is provided to
//                 indicate the symbolic port number.
//  inlen      - the length of the data that was read
//  outbuf     - the input data
//
// Returns number of characters read
//
int ReadCOM(int portnum, int inlen, uchar *inbuf)
{
   short cnt=0;
   ulong far *sysclk = (ulong far *) 0x0040006c;
   ulong M;
   ulong more;

   // get a time limit
   M = *sysclk + 3;

   // remember this as the last port
   LastPrt = portnum;

   // loop to get all of the characters or timeout
   do
   {
      if (PortState[portnum].inbuf_n)
      {
         inbuf[cnt++] = PortState[portnum].inbuf[PortState[portnum].inbuf_get++];   // got it
         PortState[portnum].inbuf_get &= INBUF_MASK;   // wrap around
         --PortState[portnum].inbuf_n;                 // one less char in buffer
      }
   }
   while ((cnt < inlen) && (M > *sysclk));

   // check for more
   more = PortState[portnum].inbuf_n;

   return cnt;
}


//-------------------------------------------------------------------
// Write an array of bytes to the COM port, verify that it was
// sent out.  Assume that baud rate has been set and the buffers have
// been flushed.
//
//  portnum    - number 0 to MAX_PORTNUM-1.  This number is provided to
//                 indicate the symbolic port number.
//  outlen     - the length of the data to be written
//  outbuf     - the output data

⌨️ 快捷键说明

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