CSDN博客

img xiyuxi2001

vxWorks下编写字符设备驱动程序的方法。

发表于2004/10/19 18:41:00  997人阅读


1, 标准I/o 函数为 open, create, read, write, ioctl, close , remove.
2,核心结构为   a,   设备列表 iosDevShow  or devs可以查看系统中安装的设备
                          b,   驱动程序描述表 iosDrvShow可以查看系统中的驱动程序的个数和各个io函数的地址
                          c,  文件描述符表, i/o系统将文件描述符与驱动程序,设备对应起来的手段

3,fd = open(”/xxDev”, O_READ, 0)的过程 是 先通过/xxDev文件名找到设备(在设备列表中),根据设备描述结构找到驱动程序索引号,找到驱动程序, 返回文件描述符
4, read(fd, &buf, nBytes)的过程是通过文件描述符表直接找到驱动程序索引号。使用驱动程序。
5, src
6,.h
     //data struct
#ifndef __XYXTYDRV_H__
#define __XYXTYDRV_H__

#ifdef __cplusplus
extern "C"{
#endif

typedef struct
{
 DEV_HED devHdr;
 BOOL    isCreate;
 BOOL    isOpen;
        UINT32  RegMEMBase;
        UINT32  ioAddr;
 SEL_WAKEUP_LIST selWakeupList;
 BOOL ReadyToRead;
 BOOL ReadyToWrite;
} ttyXyx_DEV;

#ifdef __cplusplus
}
#endif

#endif
7, .c

#include "xyxtyDrv.h"

LOCAL int ttyXyxDrvNum=0;

//install
STATUS ttyXyxDrv()
{
 if(ttyXyxDrvNum>0) return(OK);
 
 //drv init code here 
 
 //put the drv into drv table
 if(ttyXyxDrvNum = iosDrvInstall(ttyXyxOpen, ttyXyxDelete, ttyXyxOpen, ttyXyxClose,/
   ttyXyxRead, ttyXyxWrite, ttyXyxIoctl) == ERROR)
 {
  return (ERROR);
 }

 return (OK);
}

//drv create

STATUS ttyXyxDevCreate(char * devName)
{
 ttyXyx_DEV *pttyxyxDev;
 
 if(ttyXyxDrvNum < 1)
 {
  errno = S_ioLib_NO_DRIVER;
  return (ERROR);
 }
 
 if((pttyxyxDev = (ttyXyx_DEV *)malloc( sizeof(ttyXyx_DEV))) == NULL)
 {
  return (ERROR);
 }
 bzero(pttyxyxDev, sizeof(ttyXyx_DEV));
 selWakeupListInit(&pttyxyxDev->selWakeupList);
 //init pttyxyxDev
 if( iosDevAdd(&pttyxyxDev->devHdr, devName, ttyXyxDrvNum) == ERROR)
 {
  free((char *)pttyxyxDev);
  return (ERROR);
 }
 return (OK);
}

// open function
int ttyXyxOpen(DEV_HDR *pttyDevHdr, int option, int flags)
{
 ttyXyx_DEV *pttyDev = (ttyXyxDEV *)pttyDevHdr;
 if(pttyDev == NULL)
 {
  errnoSet(S_xyx_NODEV);
  return (ERROR);
 } 
 
 if(pttyDev->isOpen)
 {
  errnoSet(S_xyx_DEVOPENED);
  return (ERROR);
 } 
 pttyDev->isOpen = TRUE;
 //....init
 
 return (int)pttyDevHdr);
}

//read function
int ttyXyxRead(int ttyDevId, char *pBuf, int nBytes)
{
 ttyXyx_DEV *pttyXyxDev = (ttyXyx_DEV *)ttyDevId;
 int ReadLength = ERROR;
 BOOL FoundError;
  
 if(pttyXyxDev = (ttyXyx_DEV *)NULL)
 {
  errnoSet(S_xyx_NODEV);
  return ERROR;
 } 
 
 if(pttyXyxDev->ReadyToRead)
 {
  ReadLength = 0;
  while(ReadLength < nBytes)
  {
   ReadLength++;   
  }
  // judge the register and received nbytes
  if(FoundError)
   return (ERROR);
  return (ReadLength);
 }
 return (ReadLength);
}

//write function
int ttyXyxWrite(int ttyDevId, char *pBuf, int nBytes)
{
 ttyXyx_DEV *pttyXyxDev = (ttyXyx_DEV *)ttyDevId;
 int WriteLength = 0;
 BOOL FoundError;

 if(pttyXyxDev == (ttyXyx_DEV *)NULL)
 {
  errnoSet(S_xyx_NODEV);
  return (ERROR);
 }
 
 if(pttyXyxDev->ReadyToWrite)
 {
  pttyXyxDev->ReadToWrite = FALSE;
  //write data to data
  //judge the state
 }
 pttyXyxDev->ReadyToWrite = TRUE;
 if(FoundError)
  return (ERROR);

 return (WriteLength);
}

//ioctl function
int ttyXyxIoctl(int ttyDevId, int cmd, int arg)
{
 int status;
 ttyXyx_DEV *pttyXyxDev = (ttyXyx_DEV *)ttyDevId;
 
 switch(cmd)
 {
  case FIOSELECT:
   selNodeAdd(&pttyXyxDev->selWakeupList, (SEL_WAKUP_NODE *)arg);
   if((selWakeupType((SEL_WAKUP_NODE *)arg) == SELREAD) && (&pttyXyxDev->ReadyToRead)
    selWakeup((SEL_WAKUP_NODE *)arg);
   if((selWakeupType((SEL_WAKUP_NODE *)arg) == SELWRITE) && (&pttyXyxDev->ReadyToWrite)
    selWakeup((SEL_WAKUP_NODE *)arg);
   break;
  case FIOUNSELECt:
   selNodeDelete(&pttyXyxDev->selWakeupList, (SEL_WAKUP_NODE *)arg);
   break;
  case xx_STATUS_GET:
   status = xxStatusGet(&arg);
  case xx_CONTROL_SET:
   status = xxCMDSet(arg);
   break;
  //other cmd
  default:
   errno=S_ioLib_UNKNOWN_REQUEST;
   status=ERROR;  
 }
 return (status);
 
}

//close function
int ttyXyxClose(int ttyDevId)
{
 ttyXyx_DEV *pttyXyxDev = (ttyXyx_DEV *)ttyDevId;
 if(pttyXyxDev = (ttyXyx_DEV *)NULL)
 {
  errnoSet(S_xyx_NoMEM);
  return (ERROR);
 }
 // deal with equipment
 //release resourse
 free(pttyXyxDev);
}

//unsintall function
STATUS ttyXyxDelete(char *devName)
{
 DEV_HDR *pDevHdr;
 char *pNameTail;
 //search dev
 pDevHdr=iosDevFind(devName, pNameTail);
 if(pDevHdr == NULL || *pNameTail !='/0')
  return (ERROR);

 //release resourse sample sam wakeup signal

 //uninstall
 iosDevDelete(pDevHdr);
 return (OK);
}

LOCAL ULONG ttyXyxIntHandler(int ttyDevId)
{
 ttyXyx_DEV *pttyXyxDev = (ttyXyx_DEV *)ttyDevId;
 if(pttyXyxDev = (ttyXyx_DEV *)NULL)
 {
  errnoSet(S_xyx_NoMEM);
  return (ERROR);
 } 
 
 // read the interrupt status

 //if can receive
 pttyXyxDev->ReadyToRead = TRUE;

 pttyXyxDev->ReadyToWrite = FALSE;
 // clear the interrupt
}

阅读全文
0 0

相关文章推荐

img
取 消
img