home *** CD-ROM | disk | FTP | other *** search
/ CD Actual 3 / CD ACTUAL 3.iso / linux / sonido / mod-0.000 / mod-0 / mod / player.c < prev    next >
Encoding:
C/C++ Source or Header  |  1994-11-10  |  4.0 KB  |  173 lines

  1. /*
  2.  *  player.c - Player process handling.
  3.  *
  4.  *  (C) 1994 Mikael Nordqvist (d91mn@efd.lth.se, mech@df.lth.se)
  5.  */
  6.  
  7. #include <stdio.h>
  8. #include <sys/types.h>
  9. #include <unistd.h>
  10. #include <stdlib.h>
  11. #include <string.h>
  12. #include <fcntl.h>
  13. #include <sys/ioctl.h>
  14. #include <sys/soundcard.h>
  15. #include <sys/ultrasound.h>
  16. #include <limits.h>
  17. #include <sys/time.h>
  18.  
  19. #include "mod.h"
  20. #include "message.h"
  21.  
  22. SEQ_DECLAREBUF();
  23. extern int seqfd, gus_dev;
  24. extern struct mod_info M;
  25. extern struct options opt;
  26.  
  27. extern int player2main_synced[2];
  28. extern int main2player[2];
  29.  
  30. extern int songpos, linepos, speed, tempo;
  31. extern char song_end;
  32. extern double mod_time;
  33.  
  34. /* Used when keypresses changes pos */
  35. static unsigned char song_jump, song_jump_pos, song_jump_speed,
  36.                      song_jump_tempo;
  37. static char aborting;
  38.  
  39. void play_module(void)
  40. {
  41.     info("Hinote: %d Lonote: %d\n\nPlaying module '%s'\n",
  42.      opt.high_note, opt.low_note, M.name);
  43.     
  44.     if(opt.start_pos >= M.songlength)
  45.     opt.start_pos=0;
  46.     
  47.     /* Make sure everything gets correctly initialized on the 1st iteration */
  48.     total_reset(opt.speed, opt.tempo, opt.start_pos);
  49.     aborting=0;
  50.  
  51.     while(!aborting) {
  52.     if(song_jump) {
  53.         total_reset(song_jump_speed, song_jump_tempo, song_jump_pos);
  54.         song_jump=0;
  55.         drain_pipes(1); /* Drain all pipes */
  56.         send_ack();     /* Tell main we are ready to restart playing */
  57.     }
  58.  
  59.     play_tick();
  60.     if(_seqbufptr)
  61.         handle_IO(); /* Flush events and check for messages */
  62.     }
  63. }
  64.  
  65.  
  66. void handle_IO(void)
  67. {
  68.     struct mod_message mess;
  69.     fd_set rset, wset;
  70.     int nr, maxfd;
  71.     char idling;
  72.  
  73.     maxfd=MAX(seqfd, main2player[PIPE_READ])+1;
  74.     idling=0;
  75.  
  76.     do {
  77.     FD_ZERO(&rset);
  78.     FD_ZERO(&wset);
  79.     if(_seqbufptr)
  80.         FD_SET(seqfd, &wset);
  81.     FD_SET(main2player[PIPE_READ], &rset);
  82.     if((nr=select(maxfd, &rset, &wset, 0, 0)) > 0) {
  83.         /* Write what we can */
  84.         if(FD_ISSET(seqfd, &wset)) {
  85.         while(_seqbufptr) {
  86.             if((nr=write(seqfd, _seqbuf, _seqbufptr)) == -1) {
  87.             if(errno == EAGAIN)
  88.                 break; /* Queue full */
  89.             else
  90.                 error("write(seqfd) failed (errno=%d)\n", errno);
  91.             }
  92.             
  93.             if(nr < _seqbufptr) {
  94.             memmove(_seqbuf, &(_seqbuf[nr]),
  95.                 _seqbufptr-nr);
  96.             _seqbufptr-=nr;
  97.             }
  98.             else
  99.             _seqbufptr=0;
  100.         }
  101.         }
  102.         
  103.         /* Check for messages */
  104.         if(FD_ISSET(main2player[PIPE_READ], &rset)) {
  105.         safe_read(main2player[PIPE_READ], &mess, sizeof(mess));
  106.         switch(mess.type) {
  107.           case MESSAGE_STOP:
  108.             idling=1;
  109.             total_reset(6, 125, 0);
  110.             song_jump=0;
  111.             drain_pipes(1);
  112.             send_ack();
  113.             break;
  114.           case MESSAGE_EXIT:
  115.             aborting=1;
  116.             idling=song_end=_seqbufptr=0;
  117.             break;
  118.           case MESSAGE_JUMPPATTERN:
  119.             song_jump=1;
  120.             song_jump_pos=mess.a1.songpos;
  121.             safe_read(main2player[PIPE_READ], &mess, sizeof(mess));
  122.             safe_read(main2player[PIPE_READ],
  123.                   (struct mod_message *)&opt.active_voices,
  124.                   sizeof(opt.active_voices));
  125.             song_jump_speed=mess.a1.speed;
  126.             song_jump_tempo=mess.a2.tempo;
  127.             idling=song_end=_seqbufptr=0;
  128.             break;
  129.           case MESSAGE_RESTART:
  130.             safe_read(main2player[PIPE_READ],
  131.                   (struct mod_message *)&opt.active_voices,
  132.                   sizeof(opt.active_voices));
  133.             song_jump=1;
  134.             song_jump_pos=opt.start_pos;
  135.             song_jump_speed=opt.speed;
  136.             song_jump_tempo=opt.tempo;
  137.             idling=song_end=_seqbufptr=0;
  138.             break;
  139.           case MESSAGE_NOP:
  140.             debug("Player got NOP-message\n");
  141.             break;
  142.           default:
  143.             error("Unknown message rcvd by player.\n");
  144.         }
  145.         }
  146.     }
  147.     }
  148.     while(_seqbufptr || song_end || idling);
  149. }
  150.  
  151.  
  152. void send_line(void)
  153. {
  154.     struct mod_message mess;
  155.     
  156.     mess.type=MESSAGE_PRINTLINE;
  157.     mess.a1.songpos=songpos;
  158.     mess.a2.line=linepos;
  159.     safe_write(player2main_synced[PIPE_WRITE], &mess, sizeof(mess));
  160.     SEQ_ECHO_BACK(MESSAGE_PRINTLINE);
  161. }
  162.  
  163. void send_speed(void)
  164. {
  165.     struct mod_message mess;
  166.     
  167.     mess.type=MESSAGE_PRINTSPEED;
  168.     mess.a1.speed=speed;
  169.     mess.a2.tempo=tempo;
  170.     safe_write(player2main_synced[PIPE_WRITE], &mess, sizeof(mess));
  171.     SEQ_ECHO_BACK(MESSAGE_PRINTSPEED);
  172. }
  173.