+ if(!(audio->dsp_cap&DSP_CAP_DUPLEX)) {
+ puts("[audio] no duplex support");
+ return A_ERROR;
+ }
+
+ return A_SUCCESS;
+}
+
+int audio_setup(t_audio *audio) {
+
+ int tmp;
+
+ puts("[audio] setting up sound device & allocating record/playback buffer");
+
+ tmp=audio->fmt;
+ if(ioctl(audio->dsp_fd,SNDCTL_DSP_SETFMT,&tmp)==-1) {
+ perror("[audio] ioctl call (SNDCTL_DSP_SETFMT)");
+ return A_ERROR;
+ }
+ if(tmp!=audio->fmt) {
+ puts("[audio] FMT not supported");
+ return A_ERROR;
+ }
+
+ tmp=audio->speed;
+ if(ioctl(audio->dsp_fd,SNDCTL_DSP_SPEED,&tmp)==-1) {
+ perror("[audio] ioctl call (SNDCTL_DSP_SPEED)");
+ return A_ERROR;
+ }
+ if(tmp!=audio->speed) {
+ puts("[audio] SPEED not supported");
+ return A_ERROR;
+ }
+
+ if(ioctl(audio->dsp_fd,SNDCTL_DSP_GETBLKSIZE,&(audio->blksize))==-1) {
+ perror("[audio] ioctl call (SNDCTL_DSP_GETBLKSIZE)");
+ return A_ERROR;
+ }
+
+ if((audio->play_data=(unsigned char *)malloc(audio->blksize))==NULL) {
+ perror("[audio] malloc call");
+ return A_ERROR;
+ }
+ if((audio->rec_data=(unsigned char *)malloc(audio->blksize))==NULL) {
+ perror("[audio] malloc call");
+ return A_ERROR;
+ }
+
+ return A_SUCCESS;
+}
+
+int audio_shutdown(t_audio *audio) {
+
+ puts("[audio] shutdown");
+
+ free(audio->play_data);
+ free(audio->rec_data);
+
+ if(close(audio->dsp_fd)==-1) {
+ perror("[audio] close call");
+ return A_ERROR;
+ }
+
+ return A_SUCCESS;
+}
+
+int audio_play(t_audio *audio,int len) {
+
+ int count,left;
+
+ count=0;
+ left=len;
+
+ while(left) {
+ if((count=write(audio->dsp_fd,audio->play_data+len-left,left))==-1) {
+ perror("[audio] write call");
+ return A_ERROR;
+ }
+ left-=count;
+ }
+
+ return A_SUCCESS;
+}
+
+int audio_record(t_audio *audio,int len) {
+
+ int count,left;
+
+ count=0;
+ left=len;
+
+ while(left) {
+ if((count=read(audio->dsp_fd,audio->rec_data+len-left,left))==-1) {
+ perror("[audio] read call");
+ return A_ERROR;
+ }
+ left-=count;
+ }
+
+ return A_SUCCESS;
+}