00001 #ifndef __MK_DSPObject.ReaderThreadForAll_H___ 00002 #define __MK_DSPObject.ReaderThreadForAll_H___ 00003 /* DSPObject.h - Low level DSP access and control functions. 00004 * Copyright 1988-1992, NeXT Inc. All rights reserved. 00005 * Author: Julius O. Smith III 00006 */ 00007 00008 /* 00009 * This file is organized logically with respect to the DSPOpen*() 00010 * routines in that functions apearing before the open routines must be 00011 * called before the DSP is opened (or any time), and functions apearing 00012 * after the open routines must be (or are typically) called after the 00013 * DSP is opened. 00014 * 00015 * The functions which depend on the Music Kit DSP monitor have the 00016 * prefix "DSPMK". The prefix "DSP" may either be independent of the 00017 * monitor used, or require the array processing monitor. Generally, 00018 * functions with prefix "DSP are monitor-independent unless they involve 00019 * input/output to or from private DSP memory, i.e., unless they require 00020 * services of a DSP monitor to carry out their function. 00021 * To upgrade your own DSP monitor to support these DSP functions, lift 00022 * out the I/O support in the array processing monitor. The sources are 00023 * distributed online in /usr/local/lib/dsp/smsrc (system monitor source). 00024 */ 00025 00026 #import <stdio.h> 00027 #import "dsp_types.h" 00028 #import "dsp_structs.h" 00029 00030 extern int DSPGetHostTime(void); 00031 /* 00032 * Returns the time in microseconds since it was last called. 00033 */ 00034 00035 00036 /*********** Utilities global with respect to all DSP instances **************/ 00037 00038 00039 extern int DSPGetDSPCount(void); 00040 /* 00041 * Return number of DSPs in current system. 00042 */ 00043 00044 00045 extern int DSPSetHostName(char *newHost); 00046 /* 00047 * Set name of host on which to open the DSP. 00048 * The default is NULL which means that of the local processor. 00049 * Currently, only one DSP can be open at a time. 00050 */ 00051 00052 extern char *DSPGetHostName(void); 00053 /* 00054 * Get name of host on which the DSP is being or will be used. 00055 * NULL means that of the local processor. 00056 * Use gethostname(2) to retrieve the local processor's host name. 00057 */ 00058 00059 extern int DSPSetCurrentDSP(int newidsp); 00060 /* 00061 * Set DSP number. Calls to functions in this file will act on that DSP. 00062 */ 00063 00064 extern int DSPGetCurrentDSP(void); 00065 /* 00066 * Returns currently selected DSP number. 00067 */ 00068 00069 /*************** Getting and setting "DSP instance variables" ****************/ 00070 00071 /* 00072 * DSP "get" functions do not follow the convention of returning an error code. 00073 * Instead (because there can be no error), they return the requested value. 00074 * Each functions in this class has a name beginning with "DSPGet". 00075 */ 00076 00077 00078 extern int DSPGetMessagePriority(void); 00079 /* 00080 * Return DSP Mach message priority: 00081 * 00082 * DSP_MSG_HIGH 0 00083 * DSP_MSG_MED 1 00084 * DSP_MSG_LOW 2 00085 * 00086 * Only medium and low priorities are used by user-initiated messages. 00087 * Normally, low priority should be used, and high priority messages 00088 * will bypass low priority messages enqueued in the driver. Note, 00089 * however, that a multi-component message cannot be interrupted once it 00090 * has begun. The Music Kit uses low priority for all timed messages 00091 * and high priority for all untimed messages (so that untimed messages 00092 * may bypass any enqueued timed messages). 00093 * 00094 */ 00095 00096 00097 extern int DSPSetMessagePriority(int pri); 00098 /* 00099 * Set DSP message priority for future messages sent to the kernel. 00100 * Can be called before or after DSP is opened. 00101 */ 00102 00103 00104 extern double DSPMKGetSamplingRate(void); 00105 /* 00106 * Returns sampling rate assumed by DSP software in Hz. 00107 */ 00108 00109 00110 extern int DSPMKSetSamplingRate(double srate); 00111 /* 00112 * Set sampling rate assumed by DSP software to rate in samples per 00113 * second (Hz). Note that only sampling rates 22050.0 and 44100.0 00114 * are supported for real time digital audio output. Use of other sampling 00115 * rates implies non-real-time processing or sound-out through the DSP serial 00116 * port to external hardware. 00117 */ 00118 00119 00120 extern int DSPEnableMachMessageOptimization(void); 00121 extern int DSPDisableMachMessageOptimization(void); 00122 /* 00123 * By default, optimization is enabled. In this mode, as many Mach 00124 * message components as possible are combined into a single, multicomponent 00125 * message. This minimizes context-switching between the application and 00126 * the kernel. The ability to turn it off exists solely to provide a 00127 * workaround in the event a bug turns up in it. We know there is a problem 00128 * with non-dma 16-bit and 8-bit data messages which are not at the beginning 00129 * of the message, and in these cases optimization is always disabled. 00130 */ 00131 00132 00133 /*********** Enable/Disable/Query for DSP open-state variables ************/ 00134 00135 /* 00136 * In general, the enable/disable functions must be called BEFORE the DSP 00137 * is "opened" via DSPInit(), DSPAPInit(), DSPMKInit(), DSPBoot(), or one of 00138 * the DSPOpen*() functions. They have the effect of selecting various open 00139 * modes for the DSP. The function which ultimately acts on them is 00140 * DSPOpenNoBoot() (which is called by the Init and Boot functions above). 00141 */ 00142 00143 00144 extern int DSPGetOpenPriority(void); 00145 /* 00146 * Return DSP open priority. 00147 * 0 = low priority (default). 00148 * 1 = high priority (used by DSP debugger, for example) 00149 * If the open priority is high when DSPOpenNoBoot is called, 00150 * the open will proceed in spite of the DSP already being in use. 00151 * In this case, a new pointer to the DSP owner port is returned. 00152 * Typically, the task already in control of the DSP is frozen and 00153 * the newly opening task is a DSP debugger stepping in to look around. 00154 * Otherwise, the two tasks may confuse the DSP with interleaved commands. 00155 * Note that deallocating the owner port will give up ownership capability 00156 * for all owners. 00157 */ 00158 00159 00160 extern int DSPSetOpenPriority(int pri); 00161 /* 00162 * Set DSP open priority. 00163 * The new priority has effect when DSPOpenNoBoot is next called. 00164 * 0 = low priority (default). 00165 * 1 = high priority (used by DSP debugger, for example) 00166 */ 00167 00168 00169 extern int DSPGetMessageAtomicity(void); 00170 /* 00171 * Returns nonzero if libdsp Mach messages are atomic, zero otherwise. 00172 */ 00173 00174 00175 extern int DSPSetMessageAtomicity(int atomicity); 00176 /* 00177 * If atomicity is nonzero, future libdsp Mach messages will be atomic. 00178 * Otherwise they will not be atomic. If not atomic, DMA complete interrupts, 00179 * and DSP DMA requests, for example, can get in between message components, 00180 * unless they are at priority DSP_MSG_HIGH. 00181 * (DMA related messages queued by the driver in response to DSP or user 00182 * DMA initiation are at priority DSP_MSG_HIGH, while libdsp uses 00183 * DSP_MSG_LOW for timed messages and DSP_MSG_MED for untimed messages to 00184 * the DSP. 00185 */ 00186 00187 00188 int DSPEnableHostMsg(void); 00189 /* 00190 * Enable DSP host message protocol. 00191 * This has the side effect that all unsolicited "DSP messages" 00192 * (writes from the DSP to the host) are split into two streams. 00193 * All 24-bit words from the DSP with the most significant bit set 00194 * are interpreted as error messages and split off to an error port. 00195 * On the host side, a thread is spawned which sits in msg_receive() 00196 * waiting for DSP error messages, and it forwards then to the DSP 00197 * error log, if enabled. Finally, the DSP can signal an abort by 00198 * setting both HF2 and HF3. In the driver, the protocol bits set by 00199 * enabling this mode are (cf. <sound/sounddriver.h>): 00200 * SND_DSP_PROTO_{DSPMSG|DSPERR|HFABORT|RAW}. 00201 */ 00202 00203 00204 int DSPDisableHostMsg(void); 00205 /* 00206 * Disable DSP host message protocol. 00207 * All writes from the DSP come in on the "DSP message" port. 00208 * The "DSP errors" port will remain silent. 00209 * This corresponds to setting the DSP protocol int to 0 in 00210 * the DSP driver. (cf. snddriver_dsp_protocol().) 00211 */ 00212 00213 00214 extern int DSPHostMsgIsEnabled(void); 00215 /* 00216 * Return state of HostMsg enable flag. 00217 */ 00218 00219 00220 extern int DSPMKIsWithSoundOut(void); 00221 /* 00222 * Returns nonzero if the DSP is linked to sound out. 00223 */ 00224 00225 00226 extern int DSPMKEnableSoundOut(void); 00227 /* 00228 * Enable DSP linkage to sound out. 00229 * When DSP is next opened, it will be linked to sound out. 00230 */ 00231 00232 00233 extern int DSPMKDisableSoundOut(void); 00234 /* 00235 * Disable DSP linkage to sound out. 00236 * When DSP is next opened, it will not be linked to sound out. 00237 */ 00238 00239 00240 extern int DSPMKSoundOutIsEnabled(void); 00241 /* 00242 * Return state of SoundOut enable flag. 00243 */ 00244 00245 00246 /* Sound out to the serial port */ 00247 00248 extern int DSPMKEnableSSISoundOut(void); 00249 /* 00250 * Enable DSP serial port sound out. 00251 * When DSP is next opened with a Music Kit DSP system, it will be 00252 * configured to have SSI sound out. 00253 */ 00254 00255 00256 extern int DSPMKDisableSSISoundOut(void); 00257 /* 00258 * Disable DSP serial port sound out. 00259 * When DSP is next opened with a Music Kit DSP system, the SSI 00260 * port of the DSP will not be used. 00261 */ 00262 00263 00264 extern int DSPMKSSISoundOutIsEnabled(void); 00265 /* 00266 * Return state of serial port SoundOut enable flag. 00267 */ 00268 00269 00270 extern int DSPMKStartSSISoundOut(void); 00271 /* 00272 * Tell DSP to send sound-out data to the SSI serial port in the DSP. 00273 * The DSP will block until the SSI port has read the current sound-out 00274 * buffer. SSI sound-out to the SSI can not occur simultaneously with 00275 * sound-out to the host. 00276 */ 00277 00278 00279 extern int DSPMKStopSSISoundOut(void); 00280 /* 00281 * Tell DSP not to send sound-out data to the SSI serial port. 00282 */ 00283 00284 00285 /* Sound in from the serial port */ 00286 00287 extern int DSPMKEnableSSIReadData(void); 00288 /* 00289 * Enable DSP serial port sound in. 00290 * When DSP is next opened with a Music Kit DSP system, it will be 00291 * configured to have SSI sound in. 00292 */ 00293 00294 00295 extern int DSPMKDisableSSIReadData(void); 00296 /* 00297 * Disable DSP serial port sound in. 00298 * When DSP is next opened with a Music Kit DSP system, the SSI 00299 * port of the DSP will not be used. 00300 */ 00301 00302 00303 extern int DSPMKSSIReadDataIsEnabled(void); 00304 /* 00305 * Return state of serial port ReadData enable flag. 00306 */ 00307 00308 00309 extern int DSPMKStartSSIReadData(void); 00310 /* 00311 * Tell DSP to read sound-in data from the SSI serial port in the DSP. 00312 * The DSP will block until the SSI port has written the current sound-in 00313 * buffer. Sound-in from the SSI can occur simultaneously with SSI sound-out 00314 */ 00315 00316 00317 extern int DSPMKStopSSIReadData(void); 00318 /* 00319 * Tell DSP not to take sound-in data from the SSI serial port. 00320 */ 00321 00322 00323 extern int DSPMKEnableSmallBuffers(void); 00324 /* 00325 * Enable use of small buffers for DSP sound-out. 00326 * This is something worth doing when real-time response 00327 * is desired. Normally, the sound-out driver uses 00328 * four 8K byte buffers. With small buffers enabled, 00329 * four 1K byte buffers are used. 00330 */ 00331 00332 00333 extern int DSPMKDisableSmallBuffers(void); 00334 /* 00335 * Disable use of small buffers for DSP sound-out. 00336 */ 00337 00338 00339 extern int DSPMKSmallBuffersIsEnabled(void); 00340 /* 00341 * Return true if small sound-out buffers are enabled. 00342 */ 00343 00344 00345 extern int DSPMKEnableTMFlush(void); 00346 /* 00347 * Enable flushing timed messages every message. 00348 * This is for debugging so it is easy to see each message go by. 00349 * It also can be tried if a bug is suspected in the timed message 00350 * optimization. 00351 */ 00352 00353 00354 extern int DSPMKDisableTMFlush(void); 00355 /* 00356 * Disable auto-flushing timed messages. 00357 */ 00358 00359 00360 extern int DSPMKTMFlushIsEnabled(void); 00361 /* 00362 * Return true if auto-flushing timed messages is enabled. 00363 */ 00364 00365 00366 extern int DSPMKEnableBlockingOnTMQEmptyTimed(DSPFix48 *aTimeStampP); 00367 /* 00368 * Tell the DSP to block when the Timed Message Queue is empty. 00369 * This prevents the possibility of late score information. 00370 * It is necessary to call DSPMKDisableBlockingOnTMQEmptyTimed() 00371 * after the last time message is sent to the DSP to enable the 00372 * computing of all sound after the time of the last message. 00373 */ 00374 00375 00376 extern int DSPMKDisableBlockingOnTMQEmptyTimed(DSPFix48 *aTimeStampP); 00377 /* 00378 * Tell the DSP to NOT block when the Timed Message Queue is empty. 00379 */ 00380 00381 /****************** Getting and setting DSP system files *********************/ 00382 00383 /* 00384 * Get/set various DSP system file names. 00385 * The default filenames are defined in dsp.h. 00386 * The "get" versions return an absolute path. 00387 * The "set" versions take a relative path. 00388 * The environment variable $DSP must be overwritten appropriately 00389 * before a "get" version will return what the "set" version set. 00390 * Or, one could place custom system files in the $DSP directory. 00391 */ 00392 00393 00394 /* Misc. routines for getting various directories. */ 00395 const char *DSPGetDSPDirectory(void); /* DSP_SYSTEM_DIRECTORY or $DSP if set */ 00396 char *DSPGetSystemDirectory(void); /* <DSPDirectory>/monitor */ 00397 char *DSPGetAPDirectory(void); /* <DSPDirectory>/DSP_AP_BIN_DIRECTORY */ 00398 00399 extern int DSPSetSystem(DSPLoadSpec *system); 00400 /* 00401 * Set the DSP system image (called by DSPBoot.c) 00402 * If the system name begins with "MKMON" or "APMON", 00403 * all system filenames (binary, link, and map) are set accordingly. 00404 */ 00405 00406 00407 char *DSPGetSystemBinaryFile(void); 00408 /* 00409 * Get system binary filename. 00410 * Used by DSPBoot.c. 00411 */ 00412 00413 00414 char *DSPGetSystemLinkFile(void); 00415 /* 00416 * Get system linkfile name. 00417 * Used by _DSPMakeMusicIncludeFiles.c. 00418 */ 00419 00420 00421 char *DSPGetSystemMapFile(void); 00422 /* 00423 * Get system linkfile name. 00424 * Used by _DSPRelocateUser.c. 00425 */ 00426 00427 00428 extern int DSPMonitorIsMK(void); 00429 /* 00430 * Returns true if the currently set DSP system is of the 00431 * for "mkmon*.dsp", otherwise false. 00432 */ 00433 00434 00435 extern int DSPSetMKSystemFiles(void); 00436 /* 00437 * Set the system binary, link, and map files to the MK world. 00438 */ 00439 00440 00441 extern int DSPMonitorIsAP(void); 00442 /* 00443 * Returns true if the currently set DSP system is of the 00444 * form "apmon*.dsp", otherwise false. 00445 */ 00446 00447 00448 extern int DSPSetAPSystemFiles(void); 00449 /* 00450 * Set the system binary, link, and map files to the AP world. 00451 */ 00452 00453 00454 /***************************** WriteData Setup *******************************/ 00455 00456 /* 00457 * "Write data" is DSP sound data which is being recorded to disk. 00458 */ 00459 00460 00461 extern int DSPMKSetWriteDataFile(const char *fn); 00462 /* 00463 * Set the file-name for DSP write-data to fn. 00464 */ 00465 00466 00467 char *DSPMKGetWriteDataFile(void); 00468 /* 00469 * Read the file-name being used for DSP write-data. 00470 */ 00471 00472 00473 extern int DSPMKEnableWriteData(void); 00474 /* 00475 * Enable DSP write data. 00476 * When DSP is next opened, stream ports will be set up between the 00477 * DSP, host, and sound-out such that write-data can be used. 00478 * 00479 * After opening the DSP with DSPMKInit(), call DSPMKStartWriteDataTimed() 00480 * (described below) to spawn the thread which reads DSP data to disk. 00481 * 00482 * Bug: Audible sound-out is disabled during write data. 00483 */ 00484 00485 00486 extern int DSPMKDisableWriteData(void); 00487 /* 00488 * Disable DSP write data (default). 00489 */ 00490 00491 00492 extern int DSPMKWriteDataIsEnabled(void); 00493 /* 00494 * Return state of DSP write-data enable flag. 00495 */ 00496 00497 00498 extern int DSPMKWriteDataIsRunning(void); 00499 /* 00500 * Return nonzero if DSP write data thread is still running. 00501 */ 00502 00503 00504 /* 00505 * The write-data time-out is the number of milliseconds to wait in 00506 * msg_receive() for a write-data sound buffer from the DSP. 00507 * On time-out, it is assumed that the DSP is not sending any more 00508 * write-data, and the thread reading write data terminates. 00509 */ 00510 00511 00512 extern int DSPMKGetWriteDataTimeOut(void); 00513 /* 00514 * Get number of milliseconds to wait in msg_receive() for a sound buffer 00515 * from the DSP before giving up. 00516 */ 00517 00518 00519 extern int DSPMKSetWriteDataTimeOut(int to); 00520 /* 00521 * Set number of milliseconds to wait in msg_receive() for a sound buffer 00522 * from the DSP before giving up. The default is 60 seconds. It must be 00523 * made larger if the DSP program might take longer than this to compute 00524 * a single buffer of data, and it can be set shorter to enable faster 00525 * detection of a hung DSP program. 00526 */ 00527 00528 00529 extern int DSPMKSoundOutDMASize(void); 00530 /* 00531 * Returns the size of single DMA transfer used for DSP sound-out 00532 * 16-bit words. This may change at run time depending on whether 00533 * read-data is used or if a smaller buffer size is requested. 00534 */ 00535 00536 00537 extern int DSPMKClearDSPSoundOutBufferTimed(DSPTimeStamp *aTimeStamp); 00538 /* 00539 * Clears the DSP's sound-out buffer. Normally, this is unnecessary 00540 * because the DSP orchestra puts out zeros by default. 00541 */ 00542 00543 /***************************** ReadData Setup *******************************/ 00544 00545 /* 00546 * "Read data" is DSP sound data (stereo or mono) which is being read from 00547 * disk and sent to a Music Kit Orchestra running on the DSP. 00548 */ 00549 00550 00551 extern int DSPMKEnableReadData(void); 00552 /* 00553 * Enable DSP read data. 00554 * When the DSP is next opened, a read-data stream to the DSP will be opened. 00555 */ 00556 00557 00558 extern int DSPMKDisableReadData(void); 00559 /* 00560 * Disable DSP read data (default). 00561 */ 00562 00563 00564 extern int DSPMKReadDataIsEnabled(void); 00565 /* 00566 * Return state of DSP read-data enable flag. 00567 */ 00568 00569 00570 extern int DSPMKSetReadDataFile(const char *fn); 00571 /* 00572 * Set the read-data file-name to fn. 00573 */ 00574 00575 00576 /*********************** OPENING AND CLOSING THE DSP ***********************/ 00577 00578 extern int DSPOpenNoBootHighPriority(void); 00579 /* 00580 * Open the DSP at highest priority. 00581 * This will normally only be called by a debugger trying to obtain 00582 * ownership of the DSP when another task has ownership already. 00583 */ 00584 00585 00586 extern int DSPOpenNoBoot(void); 00587 /* 00588 * Open the DSP in the state implied by the DSP state variables. 00589 * If the open is successful or DSP is already open, 0 is returned. 00590 * After DSPOpenNoBoot, the DSP is open in the reset state awaiting 00591 * a bootstrap program download. Normally, only DSPBoot or a debugger 00592 * will ever call this routine. More typically, DSPInit() is called 00593 * to open and reboot the DSP. 00594 */ 00595 00596 00597 extern int DSPIsOpen(void); 00598 /* 00599 * Returns nonzero if the DSP is open. 00600 */ 00601 00602 00603 DSPLoadSpec *DSPGetSystemImage(void); 00604 /* 00605 * Get pointer to struct containing DSP load image installed by DSPBoot(). 00606 * If no system has been loaded, NULL is returned. 00607 */ 00608 00609 00610 extern int DSPClose(void); 00611 /* 00612 * Close the DSP device (if open). If sound-out DMA is in progress, 00613 * it is first turned off which leaves the DSP in a better state. 00614 * Similarly, SSI sound-out from the DSP, if running, is halted. 00615 */ 00616 00617 00618 extern int DSPCloseSaveState(void); 00619 /* 00620 * Same as DSPClose(), but retains all enabled features such that 00621 * a subsequent DSPBoot() or DSPOpenNoBoot() will come up in the same mode. 00622 * If sound-out DMA is in progress, it is first turned off. 00623 * If SSI sound-out is running, it is halted. 00624 */ 00625 00626 00627 extern int DSPRawCloseSaveState(void); 00628 /* 00629 * Close the DSP device without trying to clean up things in the DSP, 00630 * and without clearing the open state (so that a subsequent open 00631 * will be with the same modes). 00632 * This function is normally only called by DSPCloseSaveState, but it is nice 00633 * to have interactively from gdb when the DSP is wedged. 00634 */ 00635 00636 00637 extern int DSPRawClose(void); 00638 /* 00639 * Close the DSP device without trying to clean up things in the DSP. 00640 * This function is normally only called by DSPClose, but it is nice 00641 * to have interactively from gdb when the DSP is known to be hosed. 00642 */ 00643 00644 00645 extern int DSPOpenWhoFile(void); 00646 /* 00647 * Open DSP "who file" (unless already open) and log PID and time of open. 00648 * This file is read to find out who has the DSP when an attempt to 00649 * access the DSP fails because another task has ownership of the DSP 00650 * device port. The file is removed by DSPClose(). If a task is 00651 * killed before it can delete the who file, nothing bad will happen. 00652 * It will simply be overwritten by the next open. 00653 */ 00654 00655 00656 extern int DSPCloseWhoFile(void); 00657 /* 00658 * Close and delete the DSP lock file. 00659 */ 00660 00661 00662 char *DSPGetOwnerString(void); 00663 /* 00664 * Return string containing information about the current task owning 00665 * the DSP. An example of the returned string is as follows: 00666 * 00667 * DSP opened in PID 351 by me on Sun Jun 18 17:50:46 1989 00668 * 00669 * The string is obtained from the file /tmp/dsp_lock and was written 00670 * when the DSP was initialized. If the DSP is not in use, or if there 00671 * was a problem reading the lock file, NULL is returned. 00672 * The owner string is returned without a newline. 00673 */ 00674 00675 00676 extern int DSPReset(void); 00677 /* 00678 * Reset the DSP. 00679 * The DSP must be open. 00680 * On return, the DSP should be awaiting a 512-word bootstrap program. 00681 */ 00682 00683 00684 /************************ Opening the DSP in special modes **************************/ 00685 00686 /* 00687 * These are equivalent to some combination of DSPEnable*() and/or DSPDisable*() 00688 * function calls followed by DSPOpen(). 00689 */ 00690 00691 #define DSP_8K (0x1bff) /* 7k-1 */ 00692 #define DSP_32K (0x7bff) /* 31k-1 */ 00693 #define DSP_64K (0xfbff) /* 63k-1 */ 00694 00695 extern int DSPSenseMem(int *memCount); 00696 /* Returns 0 for success, 1 otherwise. 00697 * If successful, *memCount is DSP_8K, DSP_32K or DSP_64K (or 64k x 3 = 192K) 00698 */ 00699 00700 00701 extern int DSPMKInit(void); 00702 /* NOTE: The Music Kit currently uses its own version of this function 00703 * so that it can check the "app wrapper" for a version of the monitor. 00704 * 00705 * Open and reset the DSP such that it is ready to receive a user 00706 * orchestra program. It is the same as DSPBoot(musicKitSystem) 00707 * followed by starting up sound-out or write-data, if enabled. 00708 * Also differs from DSPInit() in that "Host Message" protocol is enabled. 00709 * This protocol implies that DSP messages (any word sent by the DSP 00710 * to the host outside of a data transfer is a DSP message) with the 00711 * high-order bit on are error messages, and they are routed to an 00712 * error port separate from the DSP message port. Only the Music Kit 00713 * currently uses this protocol. 00714 */ 00715 00716 00717 extern int DSPMKInitWithSoundOut(int lowSamplingRate); 00718 /* 00719 * Open and reset the DSP such that it is ready to receive a user 00720 * orchestra program. Also set up link from DSP to sound-out. 00721 * If lowSamplingRate is TRUE, the sound-output sampling rate is set 00722 * to 22KHz, otherwise it is set to 44KHz. 00723 */ 00724 00725 00726 /****************************** SoundOut Handling ****************************/ 00727 00728 extern int DSPMKStartSoundOut(void); 00729 /* 00730 * Tell the DSP to begin sending sound-out packets which were linked 00731 * to the sound-out hardware by calling DSPMKEnableSoundOut(). 00732 * The DSP must have been initialized via DSPMKInit() already. 00733 */ 00734 00735 00736 extern int DSPMKStopSoundOut(void); 00737 /* 00738 * Tell DSP to stop sending sound-out packets. 00739 */ 00740 00741 00742 /***************************** WriteData Handling ****************************/ 00743 00744 extern int DSPMKStartWriteDataTimed(DSPTimeStamp *aTimeStampP); 00745 /* 00746 * Tell the DSP to start sending sound-out requests to the DSP driver when a 00747 * buffer of sound-out data is ready in the DSP. A thread is spawned which 00748 * blocks in msg_receive() until each record region is received, and the 00749 * buffers are written to disk in the file established by 00750 * DSPMKSetWriteDataFile(). A second effect of this function is that the 00751 * DSP will now block until the driver reads each sound-out buffer. 00752 * This function must be called after the DSP is initialized by DSPMKInit(). 00753 * 00754 * If sound-out is also requested (via DSPMKEnableSoundOut()), each buffer 00755 * will be played immediately after it is written to disk. In this case, 00756 * there is no need to also call DSPMKStartSoundOut(). 00757 * 00758 * Bug: Audible sound-out is disabled during write data. 00759 * Since this should be fixed in the future, do not call both 00760 * DSPMKEnableSoundOut() and DSPMKEnableWriteData() if you want 00761 * the same behavior in future releases. 00762 */ 00763 00764 00765 extern int DSPMKStartWriteData(void); 00766 /* 00767 * Equivalent to DSPMKStartWriteDataTimed(DSPMK_UNTIMED); 00768 */ 00769 00770 00771 extern int DSPMKGetWriteDataSampleCount(void); 00772 /* 00773 * Get number of samples written to disk since write-data was initialized. 00774 */ 00775 00776 00777 extern int DSPMKStopWriteDataTimed(DSPTimeStamp *aTimeStampP); 00778 /* 00779 * Tell DSP not to generate write-data requests. 00780 * If write-data is going to disk, it does NOT tell the write-data thread 00781 * to exit. This must be the case since only the DSP knows when to turn 00782 * off write-data. Call DSPMKStopWriteData() to halt the write-data thread, 00783 * or let it time-out and abort on its own, (cf. DSPMKSetWriteDataTimeOut()). 00784 * Note that as far as the DSP is concerned, there is no difference between 00785 * write-data and sound-out. Thus, calling this function will also turn off 00786 * sound-out, if it was enabled, whether or not write data was specifically 00787 * enabled. A byproduct of this function is that the DSP stops blocking 00788 * until each sound-out buffer is read by the driver. The timed start/stop 00789 * write-data functions can be used to write out specific sections of 00790 * a Music Kit performance, running as fast as possible (silently, throwing 00791 * away sound output buffers) during intervals between the stop and start 00792 * times. 00793 */ 00794 00795 00796 extern int DSPMKStopWriteData(void); 00797 /* 00798 * Same as DSPMKStopWriteDataTimed(aTimeStampP) but using an untimed 00799 * host message to the DSP. Called by DSPMKStopSoundOut(). 00800 * If write-data is going to disk, also tells write-data thread 00801 * to exit. See DSPMKStopWriteDataTimed() above. 00802 */ 00803 00804 00805 extern int DSPMKRewindWriteData(void); 00806 /* 00807 * Rewind write-data to beginning of file. 00808 * DSPMKStopWriteData() must have been called first to terminate 00809 * the thread which actively writes the file. 00810 * After this, write-data can be resumed by DSPMKStartWriteData{Timed}(). 00811 */ 00812 00813 extern int DSPMKCloseWriteDataFile(void); 00814 /* 00815 * Close the write-data file. 00816 * DSPMKStopWriteData() is called automatically if write-data is running. 00817 * This function is called by DSPClose(), so it is normally not used 00818 * unless the file is needed as an input before the DSP is next closed and 00819 * reopened. 00820 */ 00821 00822 /***************************** ReadData Handling ****************************/ 00823 00824 extern int DSPMKStartReadDataTimed(DSPTimeStamp *aTimeStampP); 00825 /* 00826 * Start read-data flowing from disk to the DSP. 00827 * This function must be called after the DSP is initialized by DSPMKInit() 00828 * with read-data enabled by DSPMKEnableReadData(), and with 00829 * the input disk file having been specified by DSPMKSetReadDataFile(). 00830 * The first two buffers of read-data are sent to the DSP immediately, 00831 * and a timed message is sent to the DSP saying when to start consumption. 00832 * A thread is spawned which blocks in msg_send() until each buffer is taken. 00833 * The DSP will request buffer refills from the driver as needed. 00834 * There is no timeout as there is for write data because the thread knows 00835 * how much data to expect from the file, and it waits forever trying to give 00836 * buffers to the DSP. 00837 * 00838 * A second effect of this function is that the DSP orchestra program will 00839 * begin blocking on read-data underrun. There are two read-data buffers in 00840 * the DSP, so blocking tends not happen if the host is able to convey sound 00841 * from the disk to the DSP in real time or better, on average. 00842 * 00843 * If aTimeStamp == DSPMK_UNTIMED, the read-data is started in the PAUSED 00844 * state. A subsequent DSPMKResumeReadDataTimed() is necessary to tell the 00845 * DSP when to begin consuming the read data. The time-stamp can be set to 00846 * contain zero which means start read data immediately in the DSP. 00847 * 00848 * Note that DSPMKStartReadDataTimed(ts) is equivalent to 00849 * DSPMKStartReadDataPaused() followed by DSPMKResumeReadDataTimed(ts). 00850 */ 00851 00852 00853 extern int DSPMKStartReadDataPaused(void); 00854 /* 00855 * Equivalent to DSPMKStartReadDataTimed(DSPMK_UNTIMED); 00856 */ 00857 00858 00859 extern int DSPMKStartReadData(void); 00860 /* 00861 * Equivalent to DSPMKStartReadDataTimed(&DSPMKTimeStamp0); 00862 * Read-data starts in the DSP immediately. 00863 */ 00864 00865 00866 extern int DSPMKGetReadDataSampleCount(void); 00867 /* 00868 * Get number of samples sent to the DSP since read-data was started. 00869 */ 00870 00871 00872 extern int DSPMKPauseReadDataTimed(DSPTimeStamp *aTimeStampP); 00873 /* 00874 * Tell the DSP to stop requesting read-data buffer refills at the 00875 * specified time. When this happens, the read-data stream going from 00876 * disk to the DSP will block. 00877 * 00878 * This function and its "resume" counterpart provide 00879 * a way to save disk space in the read-data file when there are stretches 00880 * of time in the Music Kit performance during which no read-data is needed. 00881 * Silence in the read-data file can be squeezed out, and the pause/resume 00882 * functions can be used to read in the sound sections only when needed. 00883 */ 00884 00885 00886 extern int DSPMKResumeReadDataTimed(DSPTimeStamp *aTimeStampP); 00887 /* 00888 * Tell the DSP to resume read-data at the specified time. 00889 */ 00890 00891 00892 extern int DSPMKReadDataIsRunning(void); 00893 /* 00894 * Return nonzero if DSP read data thread is still running. 00895 * "Paused" is considered a special case of "running" since the 00896 * thread which spools data to the DSP is still alive. 00897 */ 00898 00899 00900 extern int DSPMKStopReadData(void); 00901 /* 00902 * Tell DSP to stop read-data consumption, if active, and tell the host 00903 * read-data thread to exit. See also DSPMKPauseReadDataTimed() above. 00904 */ 00905 00906 00907 extern int DSPMKRewindReadData(void); 00908 /* 00909 * Rewind read-data to beginning of file. 00910 * The read-data thread should be paused or stopped during this operation. 00911 */ 00912 00913 00914 extern int DSPMKSetReadDataBytePointer(int offset); 00915 /* 00916 * Move read-data file pointer to given offset in bytes. 00917 * Returns file pointer in bytes from beginning of file after the seek 00918 * or -1 if an error occurs. 00919 * The read-data thread should be paused or stopped during this operation. 00920 */ 00921 00922 extern int DSPMKIncrementReadDataBytePointer(int offset); 00923 /* 00924 * Move read-data file pointer to given offset from current location in bytes. 00925 * Returns file pointer in bytes from beginning of file after the seek 00926 * or -1 if an error occurs. 00927 * The read-data thread should be paused or stopped during this operation. 00928 */ 00929 00930 00931 /******************************* DSP Negotiation Port ************************/ 00932 00933 int DSPSetNegotiationPort(mach_port_t neg_port); 00934 /* 00935 * Set port given to anyone attempting to open the DSP. 00936 */ 00937 00938 mach_port_t DSPGetNegotiationPort(void); 00939 /* 00940 * Get port set by DSPSetNegotiationPort(). 00941 */ 00942 00943 /******************************* Port fetching *******************************/ 00944 00945 /* 00946 * In all these routines for obtaining Mach ports, 00947 * the DSP must be opened before asking for the ports. 00948 */ 00949 00950 mach_port_t DSPGetOwnerPort(void); 00951 /* 00952 * Get port conveying DSP and sound-out ownership capability. 00953 */ 00954 00955 00956 mach_port_t DSPGetHostMessagePort(void); 00957 /* 00958 * Get port used to send "host messages" to the DSP. 00959 * Also called the "command port" in other contexts. 00960 */ 00961 00962 00963 mach_port_t DSPGetDSPMessagePort(void); 00964 /* 00965 * Get port used to send "DSP messages" from the DSP to the host. 00966 * Messages on this port are enabled by DSPEnableHostMsg(). 00967 */ 00968 00969 00970 mach_port_t DSPGetErrorPort(void); 00971 /* 00972 * Get port used to send "DSP error messages" from the DSP to the host. 00973 * Error messages on this port are enabled by DSPEnableHostMsg(). 00974 */ 00975 00976 00977 mach_port_t DSPGetSoundPort(void); 00978 /* 00979 * Get sound device port. 00980 */ 00981 00982 00983 mach_port_t DSPMKGetWriteDataStreamPort(void); 00984 /* 00985 * Get stream port used to receive "DSP write data" buffers from the DSP. 00986 */ 00987 00988 00989 mach_port_t DSPMKGetSoundOutStreamPort(void); 00990 /* 00991 * Get stream port used to convey "sound out" buffers from the DSP 00992 * to the stereo DAC. 00993 */ 00994 00995 mach_port_t DSPMKGetWriteDataReplyPort(void); 00996 /* 00997 * Get reply port used to receive status information on "DSP write data" 00998 * buffers transfers from the DSP. 00999 */ 01000 01001 /************************ SIMULATOR FILE MANAGEMENT **************************/ 01002 01003 extern int DSPIsSimulated(void); 01004 /* 01005 * Returns nonzero if the DSP is simulated. 01006 */ 01007 01008 01009 extern int DSPIsSimulatedOnly(void); 01010 /* 01011 * Returns nonzero if the DSP simulator output is open but the DSP device 01012 * is not open. This would happen if DSPOpenSimulatorFile() were called 01013 * without opening the DSP. 01014 */ 01015 01016 01017 FILE *DSPGetSimulatorFP(void); 01018 /* 01019 * Returns file pointer used for the simulator output file, if any. 01020 */ 01021 01022 01023 extern int DSPOpenSimulatorFile(char *fn); 01024 /* 01025 * Open simulator output file fn. 01026 */ 01027 01028 01029 extern int DSPStartSimulator(void); 01030 /* 01031 * Initiate simulation mode, copying DSP commumications to the simulator 01032 * file pointer. 01033 */ 01034 01035 01036 extern int DSPStartSimulatorFP(FILE *fp); 01037 /* 01038 * Initiate simulation mode, copying DSP commumications to the file pointer fp. 01039 * If fp is NULL, the previously set fp, if any, will be used. 01040 */ 01041 01042 01043 extern int DSPStopSimulator(void); 01044 /* 01045 * Clear simulation bit, halting DSP command output to the simulator file. 01046 */ 01047 01048 01049 extern int DSPCloseSimulatorFile(void); 01050 /* 01051 * Close simulator output file. 01052 */ 01053 01054 /*********************** DSP COMMANDS FILE MANAGEMENT ************************/ 01055 01056 extern int DSPIsSavingCommands(void); 01057 /* 01058 * Returns nonzero if a "DSP commands file" is open. 01059 */ 01060 01061 extern int DSPIsSavingCommandsOnly(void); 01062 /* 01063 * Returns nonzero if the DSP commands file is open but the DSP device 01064 * is not open. This would happen if DSPOpenCommandsFile() were called 01065 * without opening the DSP. 01066 */ 01067 01068 extern int DSPOpenCommandsFile(const char *fn); 01069 /* 01070 * Opens a "DSP Commands file" which will receive all Mach messages 01071 * to the DSP. The filename suffix should be ".snd". This pseudo- 01072 * sound file can be played by the sound library. 01073 */ 01074 01075 extern int DSPCloseCommandsFile(DSPFix48 *endTimeStamp); 01076 /* 01077 * Closes a "DSP Commands file". The endTimeStamp is used by the 01078 * sound library to terminate the DSP-sound playback thread. 01079 */ 01080 01081 /******************************* DSP Driver Protocol *******************************/ 01082 01083 int DSPGetProtocol(void); 01084 /* 01085 * Returns the DSP protocol int in effect. Some of the relevant bits are 01086 * 01087 * SNDDRIVER_DSP_PROTO_RAW - disable all DSP interrupts 01088 * SNDDRIVER_DSP_PROTO_DSPMSG - enable DSP messages (via intrpt) 01089 * SNDDRIVER_DSP_PROTO_DSPERR - enable DSP error messages (hi bit on) 01090 * SNDDRIVER_DSP_PROTO_C_DMA - enable "complex DMA mode" 01091 * SNDDRIVER_DSP_PROTO_HFABORT - recognize HF2&HF3 as "DSP aborted" 01092 * 01093 * See the snddriver function documentation for more information (e.g. 01094 * snddriver_dsp_protocol()). 01095 */ 01096 01097 int DSPSetProtocol(int newProto); 01098 /* 01099 * Sets the protocol used by the DSP driver. 01100 * This function logically calls snddriver_dsp_proto(), but it's faster 01101 * inside libdsp optimization blocks. (As many Mach messages as possible are 01102 * combined into a single message to maximize performance.) 01103 */ 01104 01105 extern int DSPSetComplexDMAModeBit(int bit); 01106 /* 01107 * Set or clear the bit "SNDDRIVER_DSP_PROTO_C_DMA" in the DSP driver protocol. 01108 * For DMA transfers carried out by libdsp, this protocol bit is automatically 01109 * set before and cleared after the transfer. If you use 01110 * snddriver_dsp_dma_{read,write}() to carry out DMA transfers between the 01111 * DSP and main memory, you must set the C_DMA protocol bit yourself. 01112 */ 01113 01114 extern int DSPSetHostMessageMode(void); 01115 /* 01116 * Set "Host Message" protocol. This is the dynamic version of DSPEnableHostMsg() 01117 * followed by a form of DSPOpen(). It can be called after the DSP is already open. 01118 * Host message mode consists of the driver protocol flags 01119 * SNDDRIVER_DSP_PROTO_{DSPMSG|DSPERR} in addition to the flags enabled by libdsp 01120 * when not in host message mode, which are SNDDRIVER_DSP_PROTO_{RAW|HFABORT}. 01121 */ 01122 01123 extern int DSPClearHostMessageMode(void); 01124 /* 01125 * Clear "Host Message" protocol. This is the dynamic version of DSPDisableHostMsg() 01126 * followed by a form of DSPOpen(). It can be called after the DSP is already open. 01127 * Clearing host message mode means clearing the driver protocol flags 01128 * SNDDRIVER_DSP_PROTO_{DSPMSG|DSPERR}. The usual protocol bits 01129 * SNDDRIVER_DSP_PROTO_{RAW|HFABORT} are left on. 01130 * 01131 * Note that the "complex DMA mode bit " bit is not touched. 01132 * If you have enabled the SNDDRIVER_DSP_PROTO_C_DMA protocol bit, 01133 * clearing host message mode will probably not do what you want (prevent the driver 01134 * from taking DSP interrupts and filling the message buffer with whatever the 01135 * DSP has to send). In general, the driver is taking DSP interrupts whenever 01136 * SNDDRIVER_DSP_PROTO_RAW is off and when any of 01137 * SNDDRIVER_DSP_PROTO_{DSPMSG|DSPERR|C_DMA} are set. 01138 * 01139 * When the "RAW" mode bit is off, you can think of it as "release 1.0 mode", 01140 * where you get DSPERR mode by default, even with no other protocol bits enabled. 01141 * Consult the snddriver function documentation for more details 01142 * of this complicated protocol business. Yes, there's actually documentation. 01143 * ("Inside every mode, there is a simpler mode struggling to get out.") 01144 */ 01145 01146 /****************************** DSP Symbols *********************************/ 01147 01148 /* 01149 * DSP symbols are produced by asm56000, the DSP56000/1 assembler. 01150 * They are written into either a .lnk or .lod file, depending on 01151 * whether the assembly was "relative" or "absolute", respectively. 01152 * When DSPReadFile() reads one of these files (ASCII), or their .dsp file 01153 * counterparts (binary), all symbols are loaded as well into the 01154 * structs described in /usr/include/dsp/dsp_structs.h. The functions 01155 * below support finding these symbols and their values. Because the 01156 * assembler does not fully support mixed case, all symbol names are 01157 * converted to upper case when read in, and any name to be searched for 01158 * in the symbol table is converted to upper case before the search. 01159 */ 01160 01161 01162 extern int DSPSymbolIsFloat(DSPSymbol *sym); 01163 /* 01164 * Returns TRUE if the DSP assembler symbol is type 'F'. 01165 */ 01166 01167 01168 extern DSPSymbol *DSPGetSectionSymbol(char *name, DSPSection *sec); 01169 /* 01170 * Find symbol within the given DSPSection with the given name. 01171 * See "/LocalDeveloper/Headers/dsp/dsp_structs.h" for the definition of a 01172 * DSPSection. Equivalent to trying DSPGetSectionSymbolInLC() for each of 01173 * the 12 DSP location counters. 01174 */ 01175 01176 01177 extern DSPSymbol *DSPGetSectionSymbolInLC(char *name, DSPSection *sec, 01178 DSPLocationCounter lc); 01179 /* 01180 * Find symbol within the given DSPSection and location counter 01181 * with the given name. See "/LocalDeveloper/Headers/dsp/dsp_structs.h" 01182 * for an lc list. 01183 */ 01184 01185 01186 extern int DSPReadSectionSymbolAddress(DSPMemorySpace *spacep, 01187 DSPAddress *addressp, 01188 char *name, 01189 DSPSection *sec); 01190 /* 01191 * Returns the space and address of symbol with the given name in the 01192 * given DSP section. Note that there is no "Get" version because 01193 * both space and address need to be returned. 01194 */ 01195 01196 extern int DSPGetSystemSymbolValue(char *name); 01197 /* 01198 * Returns the value of the symbol "name" in the DSP system image, or -1 if 01199 * the symbol is not found or the DSP is not opened. 01200 * 01201 * The "system image" is that of the currently loaded monitor in the currently 01202 * selected DSP. The current DSP must be open so for this monitor image to 01203 * be available. 01204 * 01205 * The requested symbol 01206 * is assumed to be type "I" and residing in the GLOBAL section under location 01207 * counter "DSP_LC_N" (i.e., no memory space is associated with the symbol). 01208 * No fixups are performed, i.e., the symbol is assumed to belong to an 01209 * absolute (non-relocatable) section. 01210 * See /usr/local/lib/dsp/monitor/apmon_8k.lod and mkmon_A_8k.lod for example 01211 * system files which compatibly define system symbols. 01212 * 01213 * Equivalent to 01214 * DSPGetSectionSymbol(name,DSPGetUserSection(DSPGetSystemImage())); 01215 * (because the DSP system is assembled in absolute mode, and there 01216 * is only one section, the global section, for absolute assemblies). 01217 */ 01218 01219 extern int DSPGetSystemSymbolValueInLC(char *name, DSPLocationCounter lc); 01220 /* 01221 * Same as DSPGetSystemSymbolValue() except faster because the location 01222 * counter is known, and the rest are not searched. 01223 */ 01224 01225 int DSPReadSystemSymbolAddress(DSPMemorySpace *spacep, DSPAddress *addressp, 01226 char *name); 01227 /* 01228 * Same as DSPReadSectionSymbolAddress() except it knows to look in the 01229 * system section (GLOBAL). 01230 */ 01231 01232 #endif