MusicKit  0.0.0
DSPMessage.h
00001 #ifndef __MK_DSPMessage_H___
00002 #define __MK_DSPMessage_H___
00003 /* DSPMessage.h - procedure prototypes having to do with DSP messages.
00004  * Copyright 1988-1992, NeXT Inc.  All rights reserved.
00005  * Author: Julius O. Smith III
00006  */
00007 
00008 #include "MKDSPDefines.h"
00009 
00010 /******************************** DSP MESSAGES *******************************/
00011 
00012 /* 
00013  * Any unsolicited single word written by the DSP to the host (via RX) 
00014  * is defined as a "DSP Message".  This 24-bit message consist of a high-order
00015  * "opcode" byte, and two low-order "data" bytes. 
00016  *
00017  * If  "DSPEnableHostMsg()" is called before opening the DSP, 
00018  * "Host Message protocol" is used by the DSP driver.  In terms of the 
00019  * Sound/DSP driver protocol bits, "host message mode" is defined as
00020  * SNDDRIVER_DSP_PROTO_{DSPMSG|DSPERR|HFABORT|RAW}.
00021  * In this mode, RREQ is kept on in the DSP interface,
00022  * and each "DSP message" causes an interrupt in the host.  The DSP messages 
00023  * are buffered up by the driver.  When not using host message protocol,
00024  * RXDF is ignored, and only "data" is assumed to come from the DSP.
00025  * The data does not go into a driver buffer.  Instead, the user
00026  * explicitly reads data from the RX register.
00027  *
00028  * Note that "complex DMA mode" also
00029  * forces the driver to "listen" to the DSP.  In that case, if an 
00030  * unrecognized DSP message comes in (anything other than a DMA request)
00031  * the message goes to the DSP message buffer as in host message protocol
00032  * mode.
00033  * 
00034  * In the functions below, those with "Message" in their name are intended
00035  * to be used in host message mode, and those with "Data" in their name
00036  * are intended to be used outside of host message mode.  There exist
00037  * functions DSP{Set,Clear}HostMessageMode() for toggling between the two
00038  * states dynamically (i.e., while the DSP is open).
00039  *
00040  * The following macro
00041  *
00042  * #import "/LocalDeveloper/Headers/dsp/dsp.h"
00043  * #import <sound/sound.h>
00044  * #define DSP_CAN_INTERRUPT ( !(DSPGetProtocol() & SNDDRIVER_DSP_PROTO_RAW) \
00045  *      || (DSPGetProtocol() \
00046  *          & (SNDDRIVER_DSP_PROTO_DSPMSG | SNDDRIVER_DSP_PROTO_C_DMA)) \
00047  *      )
00048  *
00049  * can be used as follows, for example:
00050  *
00051  * if (DSP_CAN_INTERRUPT)
00052  *    return DSPReadMessages(msTimeLimit? msTimeLimit : _DSP_MACH_FOREVER);
00053  *  else
00054  *    return DSPAwaitCondition((DSP_ISR_RXDF<<8),
00055  *                             (DSP_ISR_RXDF<<8),
00056  *                             msTimeLimit);
00057  *
00058  */
00059 
00060 MKDSP_API int DSPDataIsAvailable(void);
00061 /*
00062  * Return nonzero if RXDF is set.
00063  */
00064 
00065 MKDSP_API int DSPAwaitData(int msTimeLimit);
00066 /*
00067  * Block until RXDF is set in the DSP host interface.
00068  * An msTimeLimit of zero means wait forever.
00069  * Returns 0 when data available, nonzero if
00070  * no data available before time-out.
00071  */
00072 
00073 MKDSP_API int DSPMessageIsAvailable(void);
00074 /*
00075  * Return nonzero if DSP has one or more pending DSP messages waiting in the
00076  * DSP host interface.  
00077  * Only useable in host message protocol mode or to look for unrecognized
00078  * messages in complex DMA mode.
00079  */
00080 
00081 MKDSP_API int DSPAwaitMessages(int msTimeLimit);
00082 /*
00083  * Block until DSPMessageIsAvailable() will return nonzero.
00084  * An msTimeLimit of zero means wait forever.
00085  * Returns 0 when a message is available, nonzero on time-out.
00086  * Only useable in host message protocol mode.
00087  */
00088 
00089 MKDSP_API int DSPReadMessages(int msTimeLimit);
00090 /*
00091  * Read messages from DSP into internal buffers.
00092  * Returns 0 if DSP messages were read by msTimeLimit milliseconds.
00093  * A 0 msTimeLimit means DON'T WAIT if there are no messages waiting
00094  * from the DSP.  See DSPMessage.h for functions which process the messages.
00095  * Only useable in host message protocol mode or to look for unrecognized
00096  * messages in complex DMA mode.
00097  */
00098 
00099 MKDSP_API int DSPMessageGet(int *msgp);
00100 /*
00101  * Return a single DSP message in *msgp, if one is waiting,
00102  * otherwise wait DSPDefaultTimeLimit for it (0 => wait forever). 
00103  * On time-out, returns the DSP error code DSP_ENOMSG.
00104  * The DSP message returned in *msgp is 24 bits, right justified.
00105  * Only called when a message is really expected.
00106  * Use DSPAwaitMessages(msTimeLimit) to obtain a precise time-limit.
00107  * Use DSPMessageIsAvailable() to determine if a message is waiting.
00108  */
00109 
00110 MKDSP_API int DSPFlushMessages(void);
00111 /*
00112  * Flush any unread messages from the DSP.
00113  */
00114 
00115 MKDSP_API int DSPFlushMessageBuffer(void);
00116 /*
00117  * Flush any DSP messages cached internally in libdsp.
00118  * Same as DSPFlushMessages() except that the DSP
00119  * is not checked for more messages.  Anything
00120  * queued up in the driver buffer will stay there.
00121  * Use DSPFlushMessages() to flush the driver's message queue.
00122  * Note: since there is no input-data buffer in the driver,
00123  * there is no DSPFlushDataBuffer() function.
00124  */
00125 
00126 
00127 MKDSP_API int DSPBreakPoint(int dsp_bp_msg);
00128 /*
00129  * Process a breakpoint generated by DSP software.  A "breakpoint" is just a
00130  * "DSP message" with an op-code of 0x80.
00131  * It currently just prints the DSP breakpoint message, reads any messages
00132  * trying to get out of the DSP, and pauses so that the Ariel debugger (Bug56)
00133  * can be used to see what's going on before anything else happens.
00134  * Only useable in host message protocol mode.
00135  */
00136 
00137 
00138 MKDSP_API int DSPMessagesOff(void);
00139 /* 
00140  * Turn off DSP messages at their source in the DSP.  The messages will pile
00141  * up in the DSP until its "DSP Message Queue" (DMQ) fills up, unless the
00142  * host message DSP_HM_BLOCK_OFF was sent to it.  The Music Kit and array
00143  * processing DSP monitors support this protocol.
00144  */
00145 
00146 
00147 MKDSP_API int DSPMessagesOn(void);
00148 /* 
00149  * Enable DSP messages in the MK or AP monitor (on by default).
00150  */
00151 
00152 
00153 MKDSP_API int DSPMessageGet(int *msgp);
00154 /*
00155  * Return a single DSP message in *msgp, if one is waiting,
00156  * otherwise it returns the DSP error code DSP_ENOMSG.
00157  * The DSP message returned in *msgp is 24 bits, right justified.
00158  */
00159 
00160 
00161 MKDSP_API int DSPAwaitAnyMessage(
00162     int *dspackp,               /* returned DSP message */
00163     int msTimeLimit);           /* time-out in milliseconds */
00164 /*
00165  * Await any message from the DSP.
00166  */
00167 
00168 
00169 MKDSP_API int DSPAwaitUnsignedReply(
00170     DSPAddress opcode,         /* opcode of expected DSP message */
00171     DSPFix24 *datum,           /* datum of  expected DSP message (returned) */
00172     int msTimeLimit);          /* time-out in milliseconds */
00173 /* 
00174  * Wait for specific DSP message containing an unsigned datum.
00175  */
00176 
00177 
00178 MKDSP_API int DSPAwaitSignedReply(
00179     DSPAddress opcode,      /* opcode of expected DSP message */
00180     int *datum,             /* datum of  expected DSP message (returned) */
00181     int msTimeLimit);       /* time-out in milliseconds */
00182 /* 
00183  * Wait for specific DSP message containing a signed datum.
00184  */
00185 
00186 
00187 MKDSP_API int DSPAwaitMessage(
00188     DSPAddress opcode,          /* opcode of expected DSP message */
00189     int msTimeLimit);           /* time-out in milliseconds */
00190 /* 
00191  * Return specific DSP message, declaring any others as errors.
00192  */
00193 
00194 
00195 MKDSP_API int DSPHostMessage(int msg);
00196 /* 
00197  * Issue untimed DSP "host message" (minus args) by issuing "xhm" 
00198  * host command.  Example: DSPHostMessage(DSP_HM_ABORT).
00199  */
00200 
00201 
00202 MKDSP_API int DSPMKHostMessageTimed(DSPFix48 *aTimeStampP, int msg);
00203 
00204 /* 
00205  * Issue timed or untimed DSP "host message" (0 args) by issuing "xhm" 
00206  * host command.  Example: DSPMKHostMessageTimed(aTimeStampP,DSP_HM_ABORT).
00207  */
00208 
00209 
00210 MKDSP_API int DSPMKHostMessageTimedFromInts(
00211     int msg,          /* Host message opcode. */
00212     int hiwd,         /* High word of time stamp. */
00213     int lowd);        /* Lo   word of time stamp. */
00214 /* 
00215  * Same as DSPMKHostMessageTimed(), but taking time stamp from ints
00216  * instead of a DSPFix48 struct.
00217  */
00218 
00219 
00220 MKDSP_API int DSPCall(
00221     DSPAddress hm_opcode,
00222     int nArgs,
00223     DSPFix24 *argArray);
00224 /*
00225  * Send an untimed host message to the DSP.
00226  */
00227 
00228 
00229 MKDSP_API int DSPCallB(
00230     DSPAddress hm_opcode,
00231     int nArgs,
00232     DSPFix24 *argArray);
00233 /*
00234  * Same as DSPCall() except that the argArray is sent in reverse
00235  * order to the DSP.
00236  */
00237 
00238 
00239 MKDSP_API int DSPCallV(DSPAddress hm_opcode,int nArgs,...);
00240 /*
00241  * Usage is int DSPCallV(hm_opcode,nArgs,arg1,...,ArgNargs);
00242  * Same as DSPCall() except that a variable number of host message arguments 
00243  * is specified explicitly (using varargs) rather than being passed in an
00244  * array.
00245  */
00246 
00247 
00248 MKDSP_API int DSPMKStartReaders(void);
00249 /* 
00250  * Start error and message readers.
00251  * Called by DSPMKInit() after DSPBoot().
00252  * Necessary to field and discard "kernel acks" from the DSP
00253  * during a performance.
00254  */
00255 
00256 MKDSP_API int DSPMKStopMsgReader(void);
00257 /* 
00258  * Stop message reader.  Error reader is stopped by closing DSP.
00259  * The Music Kit calls this before waiting for requesting a 
00260  * message at the end of time. 
00261  */
00262 
00263 MKDSP_API int DSPMKFlushTimedMessages(void);
00264 /* 
00265  * Flush all combined timed messages for the current time. 
00266  * You must send this if you are sending updates to the DSP 
00267  * asynchronously (e.g. in response to mouse events 
00268  * as opposed to via the Music Kit Conductor). The Music Kit
00269  * automatically calls it for Conductor and MIDI events.
00270  */
00271 
00272 MKDSP_API int DSPMKCallTimed(
00273     DSPFix48 *aTimeStampP,
00274     DSPAddress hm_opcode,
00275     int nArgs,
00276     DSPFix24 *argArray);
00277 /*
00278  * Enqueue a timed host message for the DSP.  If the time stamp of the
00279  * host message is greater than that of the host messages currently
00280  * in the timed message buffer, the buffer is flushed before the
00281  * new message is enqueued.  If the timed stamp is equal to those
00282  * currently in the buffer, it is appended to the buffer.  It is an
00283  * error for the time stamp to be less than that of the current
00284  * timed message buffer, unless it is zero; a zero time stamp means
00285  * execute the message at the end of the current "tick" in the DSP.
00286  * If aTimeStamp is NULL, the host message is executed untimed.  
00287  */
00288 
00289 
00290 MKDSP_API int DSPMKCallTimedV(DSPFix48 *aTimeStampP,int hm_opcode,int nArgs,...);
00291 /*
00292  * Usage is int DSPMKCallTimedV(aTimeStampP,hm_opcode,nArgs,arg1,...,ArgNargs);
00293  * Same as DSPMKCallTimed() except that a variable number of host message 
00294  * arguments is specified explicitly in the argument list (using stdarg) 
00295  * rather than being passed in an array.
00296  */
00297 
00298 MKDSP_API int DSPMKAwaitEndOfTime(DSPFix48 *aTimeStampP);
00299 /* 
00300  * Issues a timed message for the specified time, then blocks until that message
00301  * is received. 
00302  */
00303 
00304 #endif