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

📄 iicdev.c

📁 经典 WxWorks下的IIC字符设备驱动
💻 C
字号:
/* iicdev.c - s3c2440 IIC character device driver */
 
/* Copyright 2007-2008 zyyt  Inc. */

/*
modification history
--------------------
01a,16jul07,ZhouJianJun  written 163haole@163.com
*/

/*
DESCRIPTION
This module implements a character device driver
 应用程序中安装驱动和创建设备代码:

iicDrv(); 
iicDevCreate(“/IIC"); 

*/
/* includes */
#include "vxWorks.h"
#include "iv.h"
#include "ioLib.h"
#include "iosLib.h"
#include "intLib.h"
#include "errnoLib.h"
#include "sysLib.h"

/*#include "drv/XXX/XXX.h"*/

#include "s3c2410x.h"
#include "s3c2440IIC.h"
#include "IICdev.h"
#include "s3c2410xSio.h"
/* defines */

#ifndef s3c2410x_BAUD_MIN
#define s3c2410x_BAUD_MIN         18
#endif
#ifndef s3c2410x_BAUD_MAX
#define s3c2410x_BAUD_MAX         1152000
#endif

#ifndef s3c2410x_SIO_DEFAULT_BAUD
#define s3c2410x_SIO_DEFAULT_BAUD 1152000
#endif


#define iic_INT_NUM 0


/* hardware access methods */
#ifndef s3c2440_IIC_REG_READ
#define s3c2440_IIC_REG_READ(reg,result) \
	((result) = *(volatile UINT32 *)(reg))
#endif

#ifndef s3c2440_IIC_REG_WRITE
#define s3c2440_IIC_REG_WRITE(reg,data) \
	(*((volatile UINT32 *)(reg)) = (data))
#endif
#ifndef s3c2410x_INT_REG_READ
#define s3c2410x_INT_REG_READ(reg,result) \
	((result) = *(volatile UINT32 *)(reg))
#endif

#ifndef s3c2410x_INT_REG_WRITE
#define s3c2410x_INT_REG_WRITE(reg,data) \
	(*((volatile UINT32 *)(reg)) = (data))
#endif

/* local routines */
void iicIntHandler(int iicDevId);
int iicOpen(DEV_HDR *pDevHdr, int option, int flags);
STATUS iicDelete(char *devName);
int iicClose(int iicDevId);
int iicRead(int iicDevId, char *pBuf, int nBytes);
int iicWrite(int iicDevId, char *pBuf, int nBytes);
int iicIoctl(int iicDevId, int cmd, int arg);

LOCAL int iicDrvNum = 0;
LOCAL IIC_DEV  myiicDev;

//extern unsigned char dprintf(char *fmt, ...);

/* iicDrv() 安装驱动例程
   入口参数: 无
   返回值:
   ------OK: 驱动安装成功
   ------ERROR: 驱动安装失败

 */
/*
* xxDrv - driver initialization routine
* xxDrv() init’s the driver. It installs the driver via iosDrvInstall.
* It may allocate data structures, connect ISRs, and initialize hardware
*/
STATUS iicDrv(void)
{
  if(iicDrvNum > 0)
  {
     return(OK); /* 驱动程序已经安装,直接返回 */
  }

 /* 驱动初始化代码 */
 
  
 /* 中断向量初始化 */
/*
 if(intConnect(INUM_TO_IVEC(iic_INT_NUM), iicIntHandler, (int)(&myiicDev)) == ERROR)
    return (ERROR);
 if(intEnable(iic_INT_NUM)==ERROR)
    return (ERROR);
*/ 
 /* 调用iosDrvInstall()安装驱动 */
 if((iicDrvNum = iosDrvInstall(iicOpen, iicDelete, iicOpen, iicClose, \
     iicRead, iicWrite, iicIoctl)) == ERROR)
     return (ERROR);
  return (OK);
}

/* iicDevCreate()创建设备例程
   入口参数:
   ----devname: 所要创建的设备名称;
   返回值:
   ----OK: 创建设备成功;
   ----ERROR: 创建设备失败;  
  
 */
/************************************************************************
* xxDevCreate - device creation routine
* Called to add a device called <name> to be svced by this driver. Other
* driver-dependent arguments may include buffer sizes, device addresses.
* The routine adds the device to the I/O system by calling iosDevAdd.
* It may also allocate and initialize data structures for the device,
* initialize semaphores, initialize device hardware, and so on.
*/

STATUS iicDevCreate(char * devName)/* name of device to create */
{
 IIC_DEV *piicDev; /* = &myiicDev;pointer to device descriptor*/
 
 if(iicDrvNum < 1)
 {
  errnoSet(S_ioLib_NO_DRIVER);
  return (ERROR);
 }
// /*
 if ((piicDev = (IIC_DEV *)malloc(sizeof(IIC_DEV))) == NULL)
 {   
   logMsg("malloc ERROR!\n",0,0,0,0,0);
   return ERROR;
 }
 //*/
 /* init piicDev */
 if( iosDevAdd(&piicDev->devHdr, devName, iicDrvNum) == ERROR)
 {
    return (ERROR);
 }

 selWakeupListInit(&piicDev->selWakeupList);
 /* init other */

 s3c2440IICInit(piicDev);



 return (OK);
}

/*
 iicOpen() 打开设备
 入口参数: 参考open();
 返回值:
 -------ERROR:失败
 -------指向设备的句柄
 */
int iicOpen(DEV_HDR *pDevHdr, int option, int flags)
{
 IIC_DEV *piicDev = (IIC_DEV *)pDevHdr;

 if(piicDev == NULL)
 {
  return (ERROR);
 }
 

 return ((int)pDevHdr);
}

/*
 读设备

 */

int iicRead(int iicDevId, char *pBuf, int nBytes)
{
 IIC_DEV *piicDev = (IIC_DEV *)iicDevId;
 int ReadLength;
 
 ReadLength=0;
 if(piicDev == (IIC_DEV *)NULL)
 {
  return ERROR;
 }

 /*read code here*/
  /*TODO: Place code here to read form device*/

 s3c2440IICRcvStr(iicDevId,pBuf,nBytes);
 return (ReadLength);
}

/* 写设备 */

int iicWrite(int iicDevId, char *pBuf, int nBytes)
{
 IIC_DEV *piicDev = (IIC_DEV *)iicDevId;
 int WriteLength = 0;
 //printf("call s3c2440Uart2Write1\n");
 if(piicDev == (IIC_DEV *)NULL)
 {
  return (ERROR);
 }
 /*TODO: Place code here to write to device*/
//  printf("iicWrite  zhoujinjun/n");
 // dprintf("%s","iic write");
 //printf("call s3c2440Uart2Write2\n");

 s3c2440IICSendStr(iicDevId,pBuf, nBytes);

 return (WriteLength);
}

/* 设备控制 */
int iicIoctl(int iicDevId, int cmd, int arg)
{

 IIC_DEV *piicDev = (IIC_DEV *)iicDevId;
 int status;
 /*UCHAR temp;*/
  int oldlevel;        /* current interrupt level mask */
 UINT32 tempUINT32 = 0;
 int lvl;
 

 status = OK;

 switch(cmd)
 {
  case FIOSELECT:
    /* add node to wakeup list */
   selNodeAdd(&piicDev->selWakeupList, (SEL_WAKEUP_NODE *)arg);
   if((selWakeupType((SEL_WAKEUP_NODE *)arg) == SELREAD) && (piicDev->readyRead))
       /* data available, make sure task does not pend */
	   selWakeup((SEL_WAKEUP_NODE *)arg);
   if((selWakeupType((SEL_WAKEUP_NODE *)arg) == SELWRITE) && (piicDev->readyWrite))
       /* device ready for writing, make sure task does not pend */
	   selWakeup((SEL_WAKEUP_NODE *)arg);
   break;
  case FIOUNSELECT:
   /* delete node from wakeup list */
   selNodeDelete(&piicDev->selWakeupList, (SEL_WAKEUP_NODE *)arg);
   break;
 
  /* other cmd */
  case IIC_SLAVEADD_SET:
	if(arg < s3c2410x_BAUD_MIN || arg > s3c2410x_BAUD_MAX) return(EIO);
     piicDev->slaveAdd= arg; 

	break;
  case IIC_SLAVEADD_GET:
	*(int *)arg = piicDev->slaveAdd;
	break;
  case IIC_SUBADD_SET:
	
     piicDev->pSubadd=(UINT8 *)arg; 

	break;
  case IIC_SUBADD_GET:
	*(int *)arg = piicDev->pSubadd;
	break;
	
  case IIC_CLOCK_SET:
	piicDev->iicCon = ((piicDev->iicCon&(~0xf))|(IICCLK/arg-1));//IICCLK = fPCLK /512
	piicDev->iicTxClock = arg;
	
	break;
  case IIC_CLOCK_GET:
	*(int *)arg = piicDev->iicTxClock;	
		break;
 		
  default:
   errnoSet(S_ioLib_UNKNOWN_REQUEST);
   status = ERROR; 
 }
 return (status);
}

/* 关闭设备 */
int iicClose(int iicDevId)
{
 IIC_DEV *piicDev = (IIC_DEV *)iicDevId;
 
 if(piicDev == (IIC_DEV *)NULL)
 {
  return (ERROR);
 }
 /* */
 piicDev->opened = FALSE;
 return (OK);
}

/* 删除设备 */
STATUS iicDelete(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);
}

/* 设备中断处理 */
void iicIntHandler(int iicDevId)
{
 
 /* interrupt process */
 IIC_DEV *piicDev = (IIC_DEV *)iicDevId;


 selWakeupAll(&piicDev->selWakeupList,SELREAD); /* 若支持SELECT机制 */

 selWakeupAll(&piicDev->selWakeupList,SELWRITE); /* 若支持SELECT机制 */
}


⌨️ 快捷键说明

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