usbcalls.c revision 59190ecd61435d19ba3515b876272aee7bd12298
#define INCL_DOSERRORS
#define INCL_DOSMEMMGR
#define INCL_DOSSEMAPHORES
#define INCL_DOSDEVICES
#define INCL_DOSDEVIOCTL
#define INCL_DOSMODULEMGR
#include <os2.h>
#if !defined(__GNUC__) || defined(STATIC_USBCALLS)
#include <string.h>
#else
#define memcpy __builtin_memcpy
#endif
#include <stdlib.h>
#include <stdio.h>
#define LOG_GROUP LOG_GROUP_DRV_USBPROXY
#ifdef __GNUC__
#else
# define APIEXPORT
#endif
#ifndef ERROR_USER_DEFINED_BASE
/*#define ERROR_USER_DEFINED_BASE 0xFF00 */
#define ERROR_I24_WRITE_PROTECT 0
#define ERROR_I24_BAD_UNIT 1
#define ERROR_I24_NOT_READY 2
#define ERROR_I24_BAD_COMMAND 3
#define ERROR_I24_CRC 4
#define ERROR_I24_BAD_LENGTH 5
#define ERROR_I24_SEEK 6
#define ERROR_I24_NOT_DOS_DISK 7
#define ERROR_I24_SECTOR_NOT_FOUND 8
#define ERROR_I24_OUT_OF_PAPER 9
#define ERROR_I24_WRITE_FAULT 10
#define ERROR_I24_READ_FAULT 11
#define ERROR_I24_GEN_FAILURE 12
#define ERROR_I24_DISK_CHANGE 13
#define ERROR_I24_WRONG_DISK 15
#define ERROR_I24_UNCERTAIN_MEDIA 16
#define ERROR_I24_CHAR_CALL_INTERRUPTED 17
#define ERROR_I24_NO_MONITOR_SUPPORT 18
#define ERROR_I24_INVALID_PARAMETER 19
#define ERROR_I24_DEVICE_IN_USE 20
#define ERROR_I24_QUIET_INIT_FAIL 21
#endif
#include "usbcalls.h"
#define IOCTLF_AQUIREDEVICE 0x00000033
#define IOCTLF_RELEASEDEVICE 0x00000034
#define IOCTLF_GETSTRING 0x00000035
#define IOCTLF_SENDCONTROLURB 0x00000036
#define IOCTLF_SELECT_BULKPIPE 0x0000003E /* Select which Bulk endpoints can be used via Read/Write */
#define NOTIFY_FREE 0
#define NOTIFY_CHANGE 1
#define NOTIFY_DEVICE 2
#define MAX_NOTIFICATIONS 256
#pragma pack(1)
typedef struct
{
} NOTIFYENTRY, *PNOTIFYENTRY;
#define DEV_SEM_ADD 0x00000001
#define DEV_SEM_REMOVE 0x00000002
#define DEV_SEM_MASK 0x00000003
#define DEV_SEM_VENDORID 0x00000004
#define DEV_SEM_PRODUCTID 0x00000008
#define DEV_SEM_BCDDEVICE 0x00000010
typedef struct{
typedef struct{
} DEVEVENTSET, * PDEVEVENTSET;
typedef struct
{
USHORT usDeviceNumber; /* Get the usDeviceNumber device in the system fi. if 2 aquire the 2nd device
0 means first not aquired device. */
} AQUIREDEV, *PAQUIREDEV;
typedef struct
{
} SETUPPACKET, *PSETUPPACKET;
typedef struct
{
typedef struct
{
#define ISO_DIRMASK 0x80
typedef struct
{
#define USB_TRANSFER_FULL_SIZE 0x01
typedef struct
{
/* ULONG ulID; - yeah, right */
typedef struct
{
typedef struct
{
#pragma pack()
/******************************************************************************/
InitUsbCalls(void)
{
int i;
if (++g_cInit > 1)
return NO_ERROR;
&ulAction,
0,
0 );
if(rc)
{
g_hUSBDrv = 0;
g_cInit = 0;
}
else
{
/* @@ToDO Add EnvVar or INI for dynamically setting the number */
for(i=0;i<MAX_NOTIFICATIONS;i++)
{
g_Notifications[i].hDeviceAdded = 0;
g_Notifications[i].hDeviceRemoved = 0;
g_Notifications[i].usVendor = 0;
g_Notifications[i].usProduct = 0;
g_Notifications[i].usBCDDevice = 0;
}
g_ulNumIsoRingBuffers * sizeof(ISORINGBUFFER),
if(!rc)
{
for(i=0;i< g_ulNumIsoRingBuffers;i++,pIter++)
{
pIter->usPosWrite = 0;
pIter->ucEndpoint = 0;
pIter->ucAltInterface = 0;
/*pIter->ucBuffer */
}
if(!rc)
{
if(rc)
{
}
}
else
{
}
}
if(rc)
{
g_hUSBDrv = 0;
g_cInit = 0;
}
}
}
TermUsbCalls(void)
{
if (!g_cInit)
return ERROR_GEN_FAILURE;
if(!--g_cInit)
{
int i;
for(i=0;i<MAX_NOTIFICATIONS;i++)
if (g_pIsoRingBuffers)
}
return NO_ERROR;
}
#ifdef VBOX /* complete wast of time */
#else
{
}
{
}
#endif
{
if(!g_cInit)
return USB_NOT_INIT;
return ERROR_INVALID_PARAMETER;
*pulNumDev = 0;
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
return ERROR_INVALID_PARAMETER;
return ERROR_INVALID_PARAMETER;
*pulBufLen = 0;
ulParmLen = sizeof(ulDevNumber);
return rc;
}
{
int i;
if(!g_cInit)
return USB_NOT_INIT;
(hDeviceAdded==0 && hDeviceRemoved==0) )
return ERROR_INVALID_PARAMETER;
if(hDeviceAdded!=0)
{
if(rc)
return rc;
}
if(hDeviceRemoved!=0)
{
if(rc)
return rc;
}
if(rc)
return rc;
for(i=0;i<MAX_NOTIFICATIONS;i++)
{
{
g_Notifications[i].usVendor = 0;
g_Notifications[i].usProduct = 0;
g_Notifications[i].usBCDDevice = 0;
break;
}
}
if(i==MAX_NOTIFICATIONS)
return USB_ERROR_NO_MORE_NOTIFICATIONS;
/* @@ToDo come up with a better way to generate IDs */
if(rc)
{
*pNotifyID = 0;
}
return rc;
}
{
int i;
if(!g_cInit)
return USB_NOT_INIT;
hDeviceAdded==0 || hDeviceRemoved==0 ||
return ERROR_INVALID_PARAMETER;
if(rc)
return rc;
if(rc)
return rc;
if(rc)
return rc;
for(i=0;i<MAX_NOTIFICATIONS;i++)
{
{
break;
}
}
if(i==MAX_NOTIFICATIONS)
return USB_ERROR_NO_MORE_NOTIFICATIONS;
/* @@ToDo come up with a better way to generate IDs */
if(rc)
{
*pNotifyID = 0;
}
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
return ERROR_INVALID_PARAMETER;
if(Index % sizeof(NOTIFYENTRY))
return ERROR_INVALID_PARAMETER;
Index /= sizeof(NOTIFYENTRY);
{
case NOTIFY_FREE:
return ERROR_INVALID_PARAMETER;
case NOTIFY_CHANGE:
ulSize = sizeof(STATUSEVENTSET);
break;
case NOTIFY_DEVICE:
ulSize = sizeof(DEVEVENTSET);
break;
default:
return ERROR_GEN_FAILURE;
}
if(0==rc)
{
} else
{
}
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
return ERROR_INVALID_PARAMETER;
ulCat = 0xA0;
ulFunc = 0x33;
/* @@ ToDO maybe gether some info about device here (endpoints etc for savety checks) */
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
ulDataLen = 0;
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
ulParmLen = sizeof(USBCALLS_CTRL_REQ);
{
}
return rc;
}
{
return UsbBulkRead2(Handle, Endpoint, AltInterface, TRUE /* fShortOk */, ulNumBytes, pvData, ulTimeout);
}
{
if(!g_cInit)
return USB_NOT_INIT;
if(*ulNumBytes==0)
return 0;
/* just require this */
return ERROR_INVALID_ADDRESS;
return ERROR_INVALID_ADDRESS;
ulTotalProcessed = 0;
do
{
/* Process up to 64k, making sure we're working on segments. */
if (ulDataLen > ulToProcess)
ulParmLen = sizeof(USBCALLS_BULK_REQ);
BulkRequest.usStatus = 0;
BulkRequest.ulEvent = 0;
//BulkRequest.ulID = (ULONG)pvData;
Log(("BulkRead: usStatus=%d rc=%ld usDataProcessed=%d usDataRemain=%d ulDataLen=%ld\n",
{
break;
}
/* Adjust count and source pointer */
ulToProcess -= ulDataLen;
{
/* Transfered less than we wanted? so something is wrong,
or device doesn't wish to send more, exit loop */
break;
}
} while( ulToProcess>0 );
return rc;
}
{
return UsbBulkWrite2(Handle, Endpoint, AltInterface, FALSE /* fShortOk */, ulNumBytes, pvData, ulTimeout);
}
{
if(!g_cInit)
return USB_NOT_INIT;
/* just require this */
return ERROR_INVALID_ADDRESS;
return ERROR_INVALID_ADDRESS;
do
{
/* Process up to 64k, making sure we're working on segments. */
if (ulDataLen > ulNumBytes)
ulParmLen = sizeof(USBCALLS_BULK_REQ);
BulkRequest.usStatus = 0;
BulkRequest.ulEvent = 0;
//BulkRequest.ulID = (ULONG)pvData;
Log(("BulkWrite: usStatus=%d rc=%ld usDataProcessed=%d usDataRemain=%d ulDataLen=%ld\n",
{
break;
}
/* Adjust count and source pointer */
ulNumBytes -= ulDataLen;
} while( ulNumBytes > 0 );
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
return ERROR_INVALID_PARAMETER;
&hEvent,
FALSE);
if(rc)
return rc;
if(rc)
else
*pHevModified = hEvent;
return rc;
}
{
if(!g_cInit)
return USB_NOT_INIT;
ulDataLen = sizeof(HevModified);
if(!rc)
return rc;
}
{
int i;
if(!g_cInit)
return USB_NOT_INIT;
if(rc)
return rc;
for(i=0;i< g_ulNumIsoRingBuffers;i++,pIter++)
{
{
break;
}
}
if(i==g_ulNumIsoRingBuffers)
return USB_ERROR_OUTOF_RESOURCES;
ulDataLen = sizeof(ISORINGBUFFER);
if(rc)
{
*phIso = 0;
}
else
{
}
return rc;
}
{
ULONG i;
for(i=0;i<g_ulNumIsoRingBuffers;i++,pIter++)
{
return 0;
}
return ERROR_INVALID_PARAMETER;
}
{
if(!g_cInit)
return USB_NOT_INIT;
/* rc = DosDevIOCtl( g_hUSBDrv, */
return rc;
}
{
if(rc)
return rc;
return ERROR_INVALID_PARAMETER;
return rc;
}
{
if(rc)
return rc;
return ERROR_INVALID_PARAMETER;
return rc;
}
{
if(rc)
return rc;
return ERROR_INVALID_PARAMETER;
return rc;
}
{
if(rc)
return rc;
*pulLength = 0;
else
return 0;
}
{
if(!g_cInit)
return USB_NOT_INIT;
/* 10 01 2003 - KIEWITZ -> Still @@ToDo Add Endpoint check based on descriptors
We currently only allow Endpoint-addresses 80h->8Fh here */
return USB_ERROR_INVALID_ENDPOINT;
if(*ulNumBytes==0)
return 0;
IrqRequest.usStatus = 0;
IrqRequest.ulEvent = 0;
ulParmLen = sizeof(LIBUSB_IRQ_REQ);
ulDataLen = *ulNumBytes;
{
} else
{
}
return rc;
}
{
ulParmLen= sizeof(LIBUSB_FIXUP);
{
}
return rc;
}
#ifndef STATIC_USBCALLS
/*+-------------------------------------------------------------------+*/
/*| _CRT_init is the C run-time environment initialization function. |*/
/*|It will return 0 to indicate success and -1 to indicate failure. |*/
/*+-------------------------------------------------------------------+*/
/* int _CRT_init (void); */
/*+-------------------------------------------------------------------+*/
/*| _CRT_term is the C run-time environment termination function. |*/
/*+-------------------------------------------------------------------+*/
/* void _CRT_term (unsigned long);*/
/*+-------------------------------------------------------------------+*/
/*| _DLL_InitTerm is the function that gets called by the operating |*/
/*| system loader when it loads and frees this DLL for each process |*/
/*| that accesses this DLL. However, it only gets called the first |*/
/*| time the DLL is loaded and the last time it is freed for a |*/
/*| particular process. The system linkage convention must be used |*/
/*| because the operating system loader is calling this function. |*/
/*+-------------------------------------------------------------------+*/
#ifdef STATIC_LINK
int _CRT_init (void);
#endif
{
/* If flag is zero then the DLL is being loaded so initialization */
/* should be performed. If flag is 1 then the DLL is being freed */
/* so termination should be performed. */
switch (flag)
{
case 0:
/* The C run-time environment initialization function must */
/* be called before any calls to C run-time functions that */
/* are not inlined. */
#ifdef STATIC_LINK
if (_CRT_init () == -1)
return 0UL;
#endif
InitUsbCalls();
break;
case 1:
TermUsbCalls();
#ifdef STATIC_LINK
#endif
break;
default:
return 0UL;
}
/* A nonzero value must be returned to indicate success. */
return 1UL;
}
#endif /* !STATIC_USBCALLS */