dispatch.c

来自「这个linux源代码是很全面的~基本完整了~使用c编译的~由于时间问题我没有亲自」· C语言 代码 · 共 567 行

C
567
字号
/* *  Broadcom Cryptonet Driver software is distributed as is, without any warranty *  of any kind, either express or implied as further specified in the GNU Public *  License. This software may be used and distributed according to the terms of *  the GNU Public License. * * Cryptonet is a registered trademark of Broadcom Corporation. *//****************************************************************************** * *  Copyright 2000 *  Broadcom Corporation *  16215 Alton Parkway *  PO Box 57013 *  Irvine CA 92619-7013 * *****************************************************************************//*  * Broadcom Corporation uBSec SDK  *//* * dispatch.c: Character driver interface to the ubsec driver *//* Revision History: * * May   2000 SOR Created * March 2001 PW Release for Linux 2.4 UP and SMP kernel  * May   2001 PW added selftest for bcmdiag * May   2001 SRM added support for dumping statistics to the proc *   		  file system * May   2001 SRM change stats file name to bcm5820  * May   2001 SRM Move snmp related stuff to snmp.c. Also support *		  statistics thru' snmp for linux kernel less than *		  2 2 17. * June  2001 SRM Added per device testing and forced device failure.  * July  2001 RJT Added support for BCM5821 * Dec   2001 SRM stats ioctl */#define MODULE#define NUMBER_OF_KEY_MCRS 128#define NUMBER_OF_CRYPTO_MCRS 512 #include "cdevincl.h"#ifdef BCM_OEM_1#include "bcm_oem_1.h"#endifchar kernel_version[] = UTS_RELEASE;#undef  KERN_DEBUG#define KERN_DEBUG "<1>"static int ubsec_ioctl(struct inode *inode, struct file *filp,unsigned int cmd, unsigned long arg);static int ubsec_open(struct inode *inode, struct file *filp);static int ubsec_release(struct inode *inode, struct file *filp);#ifdef DVTDVT_Params_t DVTparams;extern unsigned long Page_Size;extern int power_of_2(unsigned long);extern unsigned long next_smaller_power_of_2(unsigned long);#endif /* DVT */void get_ubsec_Function_Ptrs(ubsec_Function_Ptrs_t *fptrs); /* for function ptrs access */int PInt_Contents;int NumDevices=0;ubsec_chipinfo_io_t   ExtChipInfo;int UserCopySize;int GetDeviceStatus(DeviceInfo_t Device){   return Device.DeviceStatus;}int SetDeviceStatus(DeviceInfo_pt pDevice, int Status){   return pDevice->DeviceStatus = Status;}unsigned short Version=0x0181; /* Upper byte is major, lower byte is Minor */static char *version_string="%s driver v%x.%02x";int ubsec_major_number = -1;static int SelectedDevice=0;/* *  UBSEC's set of file operations.  This is the data structure that *  will be passed when we call register_chrdev(). */#ifndef LINUX2dot2static struct file_operations ubsec_file_ops = {         owner:          THIS_MODULE,        ioctl:          ubsec_ioctl,        open:           ubsec_open,        release:        ubsec_release,}; #else       struct file_operations ubsec_file_ops = {  NULL,          /* lseek   */  NULL,          /* read    */  NULL,          /* write   */  NULL,          /* readdir */  NULL,          /* select  */  ubsec_ioctl,/* ioctl   */  NULL,          /* mmap    */  ubsec_open,          /* open    */  NULL,          /* flush    */  ubsec_release,          /* release */  NULL           /* fsync   */  /* fill any remaining entries with NULL */};#endif/************************************************************************** * *  Function:  ubsec_ioctl * *************************************************************************/static int ubsec_ioctl(struct inode *inode,struct file *filp,unsigned int cmd, unsigned long arg){  long			Retval=0;  int                   status = 0;  int                   deadlockctr = 0;    unsigned short        value;      /* Simple round robin scheduling of device. We need to increment     first since the keysetup command may block. */   TheBeginning:  deadlockctr = 0;  do {    /* For diagnostic related stuff do not try any available devices */    /* Try the intended device or all devices as directed by the command */    if (cmd >= UBSEC_DEVICEDUMP || cmd == UBSEC_SELFTEST || cmd == UBSEC_FAILDEVICE) {      break;    }    if(++deadlockctr == (NumDevices * 2)) {  /* to be conservative... */#ifdef DEBUG_FAILOVER      PRINTK("dispatch found no more devices.\n");#endif      return 1; /* error: no more devices */    }    if ((++SelectedDevice) == NumDevices)      SelectedDevice=0;  } while(GetDeviceStatus(DeviceInfoList[SelectedDevice]));#ifdef DEBUG_FAILOVER  printk("\n");  PRINTK("dsptch-pre: SltdDev=%d,DevStati=%d %d\n", 	 SelectedDevice, DeviceInfoList[0].DeviceStatus, DeviceInfoList[1].DeviceStatus);#endif  switch(cmd) {#ifdef BCM_OEM_1  case BCM_OEM_1_IOCTL1:	BCM_OEM1_IOCTL1_HANDLER();	break;  case BCM_OEM_1_IOCTL2:	BCM_OEM1_IOCTL2_HANDLER();	break;#endif /* BCM_OEM_1 */  case UBSEC_ENCRYPT_DECRYPT_FUNC:    status = do_encrypt(DeviceInfoList[SelectedDevice].Context, 			(void *)arg, DeviceInfoList[SelectedDevice].Features);    break;  case UBSEC_KEY_SETUP_FUNC:    status = ubsec_keysetup(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;  case UBSEC_MATH_FUNC:    status = ubsec_math(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;  case UBSEC_RNG_FUNC:    if (DeviceInfoList[SelectedDevice].Features & UBSEC_EXTCHIPINFO_RNG)      status = ubsec_rng(DeviceInfoList[SelectedDevice].Context, (void *)arg);    else      status = UBSEC_STATUS_NO_DEVICE;    break;      case UBSEC_TLS_HMAC_FUNC:    status = ubsec_tlsmac(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;      case UBSEC_SSL_MAC_FUNC:    status = ubsec_sslmac(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;      case UBSEC_SSL_HASH_FUNC:    status = ubsec_hash(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;  case UBSEC_SSL_DES_FUNC:    status = ubsec_sslcipher(DeviceInfoList[SelectedDevice].Context, (void *)arg,			     DeviceInfoList[SelectedDevice].Features);    break;  case UBSEC_SSL_ARC4_FUNC:    if (DeviceInfoList[SelectedDevice].Features & UBSEC_EXTCHIPINFO_ARC4)      status = ubsec_sslarc4(DeviceInfoList[SelectedDevice].Context, (void *)arg);    else      status = UBSEC_STATUS_NO_DEVICE;    break;  case UBSEC_CHIPINFO_FUNC:    status = obsolete_chipinfo(DeviceInfoList[SelectedDevice].Context, (void *)arg);    break;  case UBSEC_STATS_FUNC:    {      ubsec_stats_io_t IOInfo;      int device_num;      copy_from_user((void *) &IOInfo,(void *) arg, sizeof(ubsec_stats_io_t));       device_num  = IOInfo.device_num;	if ( (device_num >= NumDevices) || (device_num < 0) )		return -1;      ubsec_GetStatistics(DeviceInfoList[device_num].Context, &IOInfo.dev_stats);      copy_to_user((void *) arg, (void *) &IOInfo, sizeof(ubsec_stats_io_t));    }    break;      case UBSEC_EXTCHIPINFO_FUNC:    copy_from_user((void *)&ExtChipInfo, (void *)arg, sizeof(ubsec_chipinfo_io_t));     if (ExtChipInfo.Status !=sizeof(ubsec_chipinfo_io_t)) {      UserCopySize = sizeof(ubsec_chipinfo_io_t);      if (UserCopySize > ExtChipInfo.Status)	UserCopySize = ExtChipInfo.Status;      ExtChipInfo.Status = UBSEC_STATUS_NO_DEVICE;      copy_to_user((void *)arg, (void *)&ExtChipInfo, UserCopySize);      return(-1);    }    else if ((ExtChipInfo.CardNum >= NumDevices) || (ExtChipInfo.CardNum < 0)) {      ExtChipInfo.CardNum = NumDevices;       ExtChipInfo.Status = UBSEC_STATUS_INVALID_PARAMETER;     }    else {      status = ubsec_chipinfo(DeviceInfoList[ExtChipInfo.CardNum].Context, &ExtChipInfo);       ExtChipInfo.NumDevices = NumDevices;       ExtChipInfo.Features &= DeviceInfoList[ExtChipInfo.CardNum].Features;      ExtChipInfo.Status = UBSEC_STATUS_SUCCESS;     }    copy_to_user((void *)arg, (void *)&ExtChipInfo, sizeof(ubsec_chipinfo_io_t));     if (ExtChipInfo.Status != UBSEC_STATUS_SUCCESS)      return(-1);    else      return(0);    break;      case UBSEC_DEVICEDUMP:    copy_from_user((void *)&PInt_Contents, (void *)arg, sizeof(int));    Retval=DumpDeviceInfo((PInt)&PInt_Contents);    if (Retval)      return(-1); /* Error */    break;  case UBSEC_FAILDEVICE:    copy_from_user((void *)&PInt_Contents, (void *)arg, sizeof(int));    Retval=FailDevices((PInt)&PInt_Contents);    if (Retval)      return(-1); /* Error */    break;  case UBSEC_SELFTEST:#ifdef BCM_OEM_1	DISABLE_BCM_OEM1();#endif /*BCM_OEM_1 */    copy_from_user((void *)&PInt_Contents, (void *)arg, sizeof(int));    Retval=TestDevices((PInt)&PInt_Contents);#ifdef BCM_OEM_1	ENABLE_BCM_OEM1();#endif /*BCM_OEM_1 */    if (Retval)      return (Retval); /* Error */  case UBSEC_GETVERSION:    copy_from_user((void *)&PInt_Contents, (void *)arg, sizeof(int));    Retval=GetHardwareVersion((PInt)&PInt_Contents); /* For the moment one card */    Retval=Retval<<16;    Retval+=Version;    #ifdef LINUX_IA64    return Retval;    #else    return(-Retval);    #endif    break;  case UBSEC_GETNUMCARDS:	copy_to_user((void *)arg,&NumDevices,sizeof(int));    return NumDevices;  case  UBSEC_GET_FUNCTION_PTRS:	{	ubsec_Function_Ptrs_t fptrs;	get_ubsec_Function_Ptrs(&fptrs);      	copy_to_user((void *) arg, (void *) &fptrs, sizeof(ubsec_Function_Ptrs_t));	}    break;#ifdef DVT   case UBSEC_RESERVED:    copy_from_user((void *)&DVTparams, (void *)arg, sizeof(DVT_Params_t));    if ((DVTparams.CardNum >= NumDevices) || (DVTparams.CardNum < 0)) {      {PRINTK("Invalid CardNum (%d), must be 0",DVTparams.CardNum);}      if (NumDevices == 1)	printk("\n");      else	printk("-%d\n",NumDevices-1);      return -1;     }    switch (DVTparams.Command) {    case UBSEC_DVT_PAGESIZE: /* Wrapper command */      DVTparams.OutParameter = Page_Size;      if (!DVTparams.InParameter) {	DVTparams.OutParameter = Page_Size = PAGE_SIZE;	DVTparams.Status = UBSEC_STATUS_SUCCESS;	Retval = UBSEC_STATUS_SUCCESS;      }            else if ((DVTparams.InParameter > PAGE_SIZE) ||	       (DVTparams.InParameter < 2)) {	DVTparams.Status = UBSEC_STATUS_INVALID_PARAMETER;      }      else {	if (!power_of_2(DVTparams.InParameter))	  DVTparams.InParameter = next_smaller_power_of_2(DVTparams.InParameter);	DVTparams.OutParameter = Page_Size; 	Page_Size = DVTparams.InParameter; 	DVTparams.Status = UBSEC_STATUS_SUCCESS;	Retval = UBSEC_STATUS_SUCCESS;      }      break;    default:      /* Pass all other commands down to the SRL */      Retval=ubsec_dvt_handler((void *)DeviceInfoList[DVTparams.CardNum].Context,(void *)&DVTparams);     };    copy_to_user((void *)arg, (void *)&DVTparams, sizeof(DVT_Params_t));    return(Retval);    break;#endif /* DVT */  default:    return -EINVAL;  }  #ifdef DEBUG_FAILOVER  PRINTK("dsptch-pst: SltdDev=%d,DevStati=%d %d\n", 	 SelectedDevice, DeviceInfoList[0].DeviceStatus, DeviceInfoList[1].DeviceStatus);  if((status == ETIMEDOUT) || (status == -ETIMEDOUT)) {    PRINTK("dispatch.c: TIMED OUT SelectedDevice=%d, DeviceStatus=%d\n", 	   SelectedDevice, DeviceInfoList[SelectedDevice].DeviceStatus);  }#endif  switch(status) {  case 0:    break;  case (ETIMEDOUT):    status = -ETIMEDOUT;  case (-ETIMEDOUT):    DeviceInfoList[SelectedDevice].DeviceStatus = TestDevice(SelectedDevice);    /*  goto TheBeginning; */    return(status);    break;      default:    /*  goto TheBeginning; */    return(status);    break;  }    return 0;}/************************************************************************** * *  Function:  init_module *    *************************************************************************/int init_module(void){  printk(version_string,UBS_DEVICE_TYPE,Version>>8,Version&0xff);#ifdef DEBUG  printk(" (SRL v%d.%x%c):\n",UBSEC_VERSION_MAJOR,UBSEC_VERSION_MINOR,UBSEC_VERSION_REV);#else  printk(":\n");#endif/* * First try to find and initialize the ubsec devices. */ if ((NumDevices=InitDevices(NUMBER_OF_CRYPTO_MCRS,NUMBER_OF_KEY_MCRS)) ==0) {   PRINTK(KERN_DEBUG "Device startup failed\n");   return -ENOMEM; }#ifdef BCM_OEM_1	INIT_BCM_OEM_1();#endif if (init_keyif() < 0) {   PRINTK(KERN_DEBUG "no memory for key buffer\n");   return(ENOMEM); } if (init_mathif() < 0) {   PRINTK(KERN_DEBUG "no memory for mathif buffer\n");   shutdown_keyif();   return(ENOMEM); } if (init_rngif() < 0) {   PRINTK(KERN_DEBUG "no memory for rng buffer\n");   shutdown_keyif();   shutdown_mathif();   return(ENOMEM); } if (init_cryptoif() < 0) {   PRINTK(KERN_DEBUG "crypto init failed\n");   shutdown_keyif();   shutdown_mathif();   return(ENOMEM); } if(init_arc4if() < 0) {   PRINTK(KERN_DEBUG "ssl init failed\n");   shutdown_cryptoif();   shutdown_rngif();   shutdown_keyif();   shutdown_mathif();   return(ENOMEM); } /* create a /proc/net/ubsec entry for possible SNMP support */#if (defined(UBSEC_STATS) && defined(CONFIG_PROC_FS))  init_snmp_stats_support();#endif  /*   *  Register the device -- ask for a dnynamicly assigned major number   */ ubsec_major_number = register_chrdev(0, UBSEC_KEYDEVICE_NAME, &ubsec_file_ops); if(ubsec_major_number < 0 ) /* Bound? */   return(ubsec_major_number);#if 0 register_chrdev(ubsec_major_number, UBSEC_KEYDEVICE_NAME, &ubsec_file_ops);#endif EXPORT_NO_SYMBOLS; return 0; /* success */}/************************************************************************** * *  Function:  cleanup_module * *************************************************************************/voidcleanup_module(void){  int i;#ifdef BCM_OEM_1	SHUTDOWN_BCM_OEM_1();#endif /* BCM_OEM_1 */  shutdown_keyif();  shutdown_mathif();  shutdown_rngif();  shutdown_cryptoif();  shutdown_arc4if();#if (defined(UBSEC_STATS) && defined(CONFIG_PROC_FS))  shutdown_snmp_stats_support();#endif#if 0  unregister_chrdev(ubsec_major_number, UBSEC_DEVICE_NAME);#endif  unregister_chrdev(ubsec_major_number, UBSEC_KEYDEVICE_NAME);  /* Shutdown all the devices. */  for (i=0; i < NumDevices ; i++)    ubsec_ShutdownDevice(DeviceInfoList[i].Context); /* Shutdown the device */  PRINTK("Module unloaded\n");}/* * ubsec_open: */static intubsec_open(struct inode *inode, struct file *filp){  MOD_INC_USE_COUNT;  return 0;}/* * ubsec_release: */static intubsec_release(struct inode *inode, struct file *filp){  MOD_DEC_USE_COUNT;  return 0; }/** get_ubsec_Function_Ptrs * copies the function ptrs for DeviceInfoList, crypto,RNG and DMA Memory access*/void get_ubsec_Function_Ptrs(ubsec_Function_Ptrs_t *fptrs){extern void * Linux_AllocateDMAMemory(ubsec_DeviceContext_t *context, int size);extern void  Linux_FreeDMAMemory(void * virtual , int size);	fptrs->PhysDeviceInfoList_Ptr = DeviceInfoList;	fptrs->OS_AllocateDMAMemory_Fptr = Linux_AllocateDMAMemory;	fptrs->OS_FreeDMAMemory_Fptr = Linux_FreeDMAMemory;	fptrs->ubsec_InitHMACState_Fptr = ubsec_InitHMACState;	fptrs->ubsec_CipherCommand_Fptr = ubsec_CipherCommand;	fptrs->ubsec_RNGCommand_Fptr = ubsec_RNGCommand;	return;}MODULE_LICENSE("GPL");

⌨️ 快捷键说明

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