src/audio/openbsd/SDL_openbsdaudio.c
changeset 94 ae6e6b73333f
parent 37 3ad7157c6cfa
child 121 43febd46d49d
equal deleted inserted replaced
93:fc774f445e10 94:ae6e6b73333f
   138 
   138 
   139 /* This function waits until it is possible to write a full sound buffer */
   139 /* This function waits until it is possible to write a full sound buffer */
   140 static void
   140 static void
   141 OBSD_WaitAudio(_THIS)
   141 OBSD_WaitAudio(_THIS)
   142 {
   142 {
   143 #ifndef USE_BLOCKING_WRITES
   143 	/* Check to see if the thread-parent process is still alive */
   144     fd_set fdset;
   144 	{ static int cnt = 0;
   145 
   145 		/* Note that this only works with thread implementations 
   146     /* Check to see if the thread-parent process is still alive */
   146 		   that use a different process id for each thread.
   147     {
   147 		*/
   148 	static int cnt = 0;
   148 		if (parent && (((++cnt)%10) == 0)) { /* Check every 10 loops */
   149 	/* Note that this only works with thread implementations 
   149 			if ( kill(parent, 0) < 0 ) {
   150 	   that use a different process id for each thread. */
   150 				this->enabled = 0;
   151 	if(parent && (((++cnt)%10) == 0)) { /* Check every 10 loops */
   151 			}
   152 	    if(kill(parent, 0) < 0)
   152 		}
       
   153 	}
       
   154 
       
   155 #ifndef USE_BLOCKING_WRITES /* Not necessary when using blocking writes */
       
   156 	/* See if we need to use timed audio synchronization */
       
   157 	if ( frame_ticks ) {
       
   158 		/* Use timer for general audio synchronization */
       
   159 		Sint32 ticks;
       
   160 
       
   161 		ticks = ((Sint32)(next_frame - SDL_GetTicks()))-FUDGE_TICKS;
       
   162 		if ( ticks > 0 ) {
       
   163 			SDL_Delay(ticks);
       
   164 		}
       
   165 	} else {
       
   166 		/* Use select() for audio synchronization */
       
   167 		fd_set fdset;
       
   168 		struct timeval timeout;
       
   169 
       
   170 		FD_ZERO(&fdset);
       
   171 		FD_SET(audio_fd, &fdset);
       
   172 		timeout.tv_sec = 10;
       
   173 		timeout.tv_usec = 0;
       
   174 #ifdef DEBUG_AUDIO
       
   175 		fprintf(stderr, "Waiting for audio to get ready\n");
       
   176 #endif
       
   177 		if ( select(audio_fd+1, NULL, &fdset, NULL, &timeout) <= 0 ) {
       
   178 			const char *message =
       
   179 			"Audio timeout - buggy audio driver? (disabled)";
       
   180 			/* In general we should never print to the screen,
       
   181 			   but in this case we have no other way of letting
       
   182 			   the user know what happened.
       
   183 			*/
       
   184 			fprintf(stderr, "SDL: %s\n", message);
       
   185 			this->enabled = 0;
       
   186 			/* Don't try to close - may hang */
       
   187 			audio_fd = -1;
       
   188 #ifdef DEBUG_AUDIO
       
   189 			fprintf(stderr, "Done disabling audio\n");
       
   190 #endif
       
   191 		}
       
   192 #ifdef DEBUG_AUDIO
       
   193 		fprintf(stderr, "Ready!\n");
       
   194 #endif
       
   195 	}
       
   196 #endif /* !USE_BLOCKING_WRITES */
       
   197 }
       
   198 
       
   199 static void
       
   200 OBSD_PlayAudio(_THIS)
       
   201 {
       
   202 	int written, p=0;
       
   203 
       
   204 	/* Write the audio data, checking for EAGAIN on broken audio drivers */
       
   205 	do {
       
   206 		written = write(audio_fd, &mixbuf[p], mixlen-p);
       
   207 		if (written>0)
       
   208 		   p += written;
       
   209 		if (written == -1 && errno != 0 && errno != EAGAIN && errno != EINTR)
       
   210 		{
       
   211 		   /* Non recoverable error has occurred. It should be reported!!! */
       
   212 		   perror("audio");
       
   213 		   break;
       
   214 		}
       
   215 
       
   216 		if ( p < written || ((written < 0) && ((errno == 0) || (errno == EAGAIN))) ) {
       
   217 			SDL_Delay(1);	/* Let a little CPU time go by */
       
   218 		}
       
   219 	} while ( p < written );
       
   220 
       
   221 	/* If timer synchronization is enabled, set the next write frame */
       
   222 	if ( frame_ticks ) {
       
   223 		next_frame += frame_ticks;
       
   224 	}
       
   225 
       
   226 	/* If we couldn't write, assume fatal error for now */
       
   227 	if ( written < 0 ) {
   153 		this->enabled = 0;
   228 		this->enabled = 0;
   154 	}
   229 	}
   155     }
   230 #ifdef DEBUG_AUDIO
   156 
   231 	fprintf(stderr, "Wrote %d bytes of audio data\n", written);
   157 #ifdef USE_TIMER_SYNC
       
   158     /* See if we need to use timed audio synchronization */
       
   159     if(frame_ticks)
       
   160     {
       
   161 	/* Use timer for general audio synchronization */
       
   162 	Sint32 ticks;
       
   163 
       
   164 	ticks = ((Sint32)(next_frame - SDL_GetTicks())) - FUDGE_TICKS;
       
   165 	if(ticks > 0)
       
   166 	    SDL_Delay(ticks);
       
   167     }
       
   168     else
       
   169 #endif /* USE_TIMER_SYNC */
       
   170     {
       
   171 	/* Use select() for audio synchronization */
       
   172 	struct timeval timeout;
       
   173 	FD_ZERO(&fdset);
       
   174 	FD_SET(audio_fd, &fdset);
       
   175 	timeout.tv_sec = 10;
       
   176 	timeout.tv_usec = 0;
       
   177 	
       
   178 #if defined(DEBUG_AUDIO_STREAM) && defined(DEBUG_AUDIO_STREAM)
       
   179 	OBSD_Status(this);
       
   180 #endif
       
   181 	if(select(audio_fd+1, NULL, &fdset, NULL, &timeout) <= 0)
       
   182 	{
       
   183 	    const char *message =
       
   184 		"Audio timeout - buggy audio driver? (disabled)";
       
   185 	    fprintf(stderr, "SDL: %s\n", message);
       
   186 	    this->enabled = 0;
       
   187 	    audio_fd = -1;
       
   188 	}
       
   189     }
       
   190 #endif /* !USE_BLOCKING_WRITES */
       
   191 
       
   192 }
       
   193 
       
   194 static void
       
   195 OBSD_PlayAudio(_THIS)
       
   196 {
       
   197     int written;
       
   198 
       
   199     /* Write the audio data, checking for EAGAIN on broken audio drivers */
       
   200     do
       
   201     {
       
   202 	written = write(audio_fd, mixbuf, mixlen);
       
   203 	if((written < 0) && ((errno == 0) || (errno == EAGAIN)))
       
   204 	    SDL_Delay(1);
       
   205     }
       
   206     while((written < 0) &&
       
   207 	((errno == 0) || (errno == EAGAIN) || (errno == EINTR)));
       
   208 
       
   209 #ifdef USE_TIMER_SYNC
       
   210     if(frame_ticks)
       
   211 	next_frame += frame_ticks;
       
   212 #endif
       
   213 
       
   214     /* If we couldn't write, assume fatal error for now */
       
   215     if(written < 0)
       
   216 	this->enabled = 0;
       
   217 
       
   218 #ifdef DEBUG_AUDIO_STREAM
       
   219     fprintf(stderr, "Wrote %d bytes of audio data\n", written);
       
   220 #endif
   232 #endif
   221 }
   233 }
   222 
   234 
   223 static Uint8
   235 static Uint8
   224 *OBSD_GetAudioBuf(_THIS)
   236 *OBSD_GetAudioBuf(_THIS)