home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / audiopdd.zip / ioctl.c < prev    next >
C/C++ Source or Header  |  1999-02-21  |  6KB  |  235 lines

  1. //
  2. // ioctl.c
  3. // 2-Feb-99
  4. //
  5. // VOID ioctlStrat(REQPACK __far *rpPtr, USHORT lDev);
  6.  
  7. #include "cs40.h"
  8.  
  9. #define VSD_RCID  99    // as in VSD RCID
  10.  
  11.  
  12. // mixer/line stuff not yet done
  13.  
  14.  
  15. // -------------------------
  16. // in: rpPtr -> request pack
  17. //     lDev = logical device
  18. //out: n/a
  19. //nts: this checks that the SFN is not already a registered stream, and
  20. //     then
  21.  
  22. static VOID ioctlAudioInit(REQPACK __far *rpPtr, USHORT lDev) {
  23.  
  24.  WAVESTREAM *wsPtr;
  25.  STREAM *streamPtr;
  26.  USHORT devType;
  27.  USHORT rc;
  28.  
  29.  MCI_AUDIO_INIT __far *mciInitPtr = rpPtr->ioctl.dataPtr;
  30.  USHORT SFN = rpPtr->ioctl.SFN;
  31.  
  32. // !!!
  33. //ddprintf("@ioctlAudioInit...\n");
  34.  
  35.  // if idle or deinit request, get the stream object based on SFN and set state to idle...
  36.  
  37.  if (mciInitPtr->sMode == IDLE) {
  38.     streamPtr = streamFindStreamSFN(SFN);
  39.     if (streamPtr) streamPtr->streamState = streamPtr->streamState | STREAM_IDLE;
  40.     //mciInitPtr->pvReserved = (VOID __far *)((ULONG)SFN);  // have to... done at good exit
  41.     rc = 0;
  42.     goto ExitNow;
  43.  }
  44.  else {
  45.  
  46.     // check for stream with same SFN already -- if so and is idle, reset idle bit
  47.     // this has to be done because mmpm passes the idle state down if the stream is
  48.     // losing the hardware to another app (usually to another app) -- if not now idle,
  49.     // then the stream is either not registered or is being re-initialized (o) in another
  50.     // mode or with different file attributes (quote) ... this reinit is "a total hack on
  51.     // the part of mmpm since it should instead deregister the stream, then init a new
  52.     // stream, but mmpm doesn't do it that way" (at least, the VSD doesn't, supposedly)
  53.     // anyway, if this is the case, delete the current stream and make a new one based on
  54.     // this req pack
  55.  
  56.     streamPtr = streamFindStreamSFN(SFN);
  57.     if (streamPtr) {
  58.        if (streamPtr->streamState & STREAM_IDLE) {
  59.           streamPtr->streamState = streamPtr->streamState & STREAM_NOT_IDLE;
  60.           //mciInitPtr->pvReserved = (VOID __far *)((ULONG)SFN);  // have to... done at good exit
  61.           rc = 0;
  62.           goto ExitNow;
  63.        }
  64.        else {
  65.           //streamDeinit(streamPtr);      // was "delete pstream" (use wavestreamDeinit() instead)
  66.           wavestreamDeinit(streamPtr->wsParentPtr);
  67.        }
  68.     }
  69.  }
  70.  
  71.  devType = hwGetType(mciInitPtr->sMode, (USHORT)mciInitPtr->ulOperation, lDev);  // AUDIOHW_WAVE_PLAY/CAPTURE
  72.  if (devType == AUDIOHW_INVALID_DEVICE) {
  73.     rc = INVALID_REQUEST;
  74.     goto ExitNow;
  75.  }
  76.  
  77.  mciInitPtr->ulFlags = 0;
  78.  
  79.  if (devType == AUDIOHW_WAVE_PLAY || devType == AUDIOHW_WAVE_CAPTURE) {
  80.  
  81.     wsPtr = malloc(sizeof(WAVESTREAM));   // wsPtr will be stored/tracked in streamPtr->wsParentPtr
  82.     if (wsPtr) {
  83.        MEMSET(wsPtr,0,sizeof(WAVESTREAM));
  84.        streamPtr = wavestreamInit(devType, mciInitPtr, wsPtr);  // wavestreamInit() allocates streamPtr
  85.        if (streamPtr == 0) {
  86.           rc = INVALID_REQUEST;
  87.           goto ExitNow;
  88.        }
  89.     }
  90.     else {
  91.        rc = INVALID_REQUEST;    // rc = 8; probably not a valid rc, but could use it in rp.status...
  92.        goto ExitNow;            // see audio.h for valid return codes...
  93.     }
  94.  }
  95.  else {
  96.     rc = INVALID_REQUEST;
  97.     goto ExitNow;
  98.  }
  99.  
  100.  mciInitPtr->ulFlags = mciInitPtr->ulFlags | VOLUME | INPUT | OUTPUT | MONITOR; // have to modify
  101.  mciInitPtr->sDeviceID = VSD_RCID; // reported in VSD DLL (I'll have to come up with my own, say 40)
  102.  
  103.  streamPtr->SFN = SFN;
  104.  rc = 0;
  105.  
  106.  
  107. ExitNow:
  108.  
  109. // !!!
  110. //ddprintf("...mciInit.flags=%lx\n",mciInitPtr->ulFlags);
  111.  
  112.  if (rc == 0) {
  113.     mciInitPtr->pvReserved = (VOID __far *)((ULONG)SFN);  // since common in all rc==0
  114.     // think this is for sending in, as in driver version needed?
  115.     // mciInitPtr->ulVersionLevel = DRIVER_VERSION;
  116.  }
  117.  
  118.  mciInitPtr->sReturnCode = rc;
  119.  if (rc) rpPtr->status = rpPtr->status | RPERR;
  120.  
  121.  return;
  122. }
  123.  
  124.  
  125. // -------------------------
  126. // in: rpPtr -> request pack
  127. //     lDev = logical device
  128. //out: n/a
  129. //nts:
  130.  
  131. static VOID ioctlAudioCaps(REQPACK __far *rpPtr, USHORT lDev) {
  132.  
  133.  USHORT devType;
  134.  USHORT rc = 0;
  135.  
  136.  MCI_AUDIO_CAPS __far *devCapsPtr = rpPtr->ioctl.dataPtr;
  137.  
  138.  devType = hwGetType((USHORT)devCapsPtr->ulDataType, (USHORT)devCapsPtr->ulOperation, lDev);
  139.  if (devType == AUDIOHW_INVALID_DEVICE) {
  140.     rc = UNSUPPORTED_DATATYPE;
  141.     goto ExitNow;
  142.  }
  143.  
  144.  waDevCaps(devCapsPtr);
  145.  rc = devCapsPtr->ulSupport;
  146.  
  147. ExitNow:
  148.  devCapsPtr->ulSupport = rc;
  149.  if (rc) rpPtr->status = rpPtr->status | RPERR;
  150.  
  151.  return;
  152. }
  153.  
  154.  
  155. // -------------------------
  156. // in: rpPtr -> request pack
  157. //out: n/a
  158. //nts:
  159. // * if it's AUDIO_CHANGE, just report success, otherwise report failure
  160. // * this is because we don't support volume, balance, multiple in/out devices,
  161. // * etc.  Also, START, STOP, RESUME, and PAUSE are redundant, so we don't
  162. // * support those either.
  163.  
  164. static VOID ioctlAudioControl(REQPACK __far *rpPtr) {
  165.  
  166.  MCI_AUDIO_CONTROL __far *controlPtr = rpPtr->ioctl.dataPtr;
  167.  
  168.  if (controlPtr->usIOCtlRequest == AUDIO_CHANGE) {
  169.     controlPtr->sReturnCode = 0;
  170.  }
  171.  else {
  172.     controlPtr->sReturnCode = INVALID_REQUEST;
  173.  }
  174.  
  175.  return;
  176. }
  177.  
  178.  
  179. // -------------------------
  180. // in: rpPtr -> request pack (.status RPDONE bit already set)
  181. //     lDev = logical device (first header device is 0, second (if any) is 1, and so on)
  182. //out: n/a
  183. //nts: generic ioctl strategy entry
  184. //     cat80 is all that's supported...
  185.  
  186. VOID ioctlStrat(REQPACK __far *rpPtr, USHORT lDev) {
  187.  
  188. // !!!
  189.  
  190. #ifdef TRACE_STRAT_GENIOCTL
  191.  tracePerf(rpPtr->ioctl.category | TRACE_IN, rpPtr->ioctl.function);
  192. #endif
  193.  
  194.  if (rpPtr->ioctl.category == AUDIO_IOCTL_CAT) {
  195.  
  196.     switch(rpPtr->ioctl.function) {
  197.     case AUDIO_INIT:
  198.        ioctlAudioInit(rpPtr,lDev);
  199.        break;
  200.     case AUDIO_CONTROL:
  201.        ioctlAudioControl(rpPtr);
  202.        break;
  203.     case AUDIO_CAPABILITY:
  204.        ioctlAudioCaps(rpPtr,lDev);
  205.        break;
  206.     case MIX_GETCONNECTIONS:
  207.     case MIX_SETCONNECTIONS:
  208.     case MIX_GETLINEINFO:
  209.     case MIX_GETCONTROL:
  210.     case MIX_SETCONTROL:
  211.  
  212. // !!!
  213. ddprintf("ioctl mixer calls, %u\n",rpPtr->ioctl.function);
  214.  
  215.        break;
  216.     default:
  217.        rpPtr->status = rpPtr->status | RPERR | RPBADCMD;
  218.        break;
  219.     }
  220.  }
  221.  else {
  222.     rpPtr->status = rpPtr->status | RPERR | RPBADCMD;
  223.  
  224. // !!!
  225.  
  226. #ifdef TRACE_STRAT_GENIOCTL
  227.  tracePerf(rpPtr->ioctl.category | TRACE_OUT, rpPtr->ioctl.function);
  228. #endif
  229.  
  230.  }
  231.  
  232.  return;
  233. }
  234.  
  235.