Subversion Repositories shark

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
1664 pj 1
 
2
/*--------------------------------------------------------------*/
3
/*              SIMULATION OF THE HUNGRY SNAKE'S GAME           */
4
 
5
/* AUTHOR : SUNDARA PRABU THESINGU RAJAN
6
 
7
   EMAIL  : Y2KPRABU@YAHOO.COM
8
 
9
   DEVELOPED SYSTEM : AMD DURON 1.1GHz 128MB RAM SVGA MONITOR
10
   OS     : SHARK
11
   GCC    : 3.1 (DJGPP VERSION)
12
 
13
   UNDER THE GUIDANCE OF PROFESSORS:
14
    Mr. Giorgio Buttazzo    <giorgio@sssup.it>
15
    Mr. Giuseppe Lipari     <lipari@sssup.it>
16
    Mr. Paolo Gai           <pj@gandalf.sssup.it>
17
 
18
 
19
/*--------------------------------------------------------------*/
20
 
21
#include <kernel/kern.h>
22
#include <drivers/glib.h>
23
#include <modules/pc.h>
24
#include <drivers/keyb.h>
25
 
26
#include <semaphore.h>
27
#include <stdlib.h>
28
#include <math.h>
29
#include <unistd.h>
30
 
31
#define XMIN     40
32
#define XMAX     600
33
#define YMIN     100
34
#define YMAX     450
35
#define D        3              /* SNAKE RADIUS                 */
36
#define ESC      27             /* ASCII code of ESCAPE key     */
37
#define SNGROUP 1
38
#define FRUIT_WCET 200     //WCET FOR FRUIT
39
#define FRUIT_T    4000000 //PERIOD FOR FRUIT
40
#define SN_WCET    4000    //WCET FOR SNAKE
41
#define SN_T       40000   //PERIOD FOR SNAKE
42
#define FGROUP 2
43
 
44
PID     pid1,pid2,pid3;
45
sem_t   mutex;
46
int dx1,dy1,dx2,dy2; // WHICH DEF NEXT POS OF SNAKE
47
int scr[XMAX][YMAX]={{0},{0}}; // init all to zero
48
void assockey();
49
void endgame();
50
void pk1(KEY_EVT *KP);
51
 
52
        // FUNCTION WHICH DRAWS SNAKES
53
void    draw_sn(int x, int y, int c)
54
{
55
	sem_wait(&mutex);
56
	//grx_rect(x, y,x+5,y+5,c);//x+dx1*D,y+dy1*D, c);
57
    grx_circle(x,y,D,c);
58
	sem_post(&mutex);
59
}
60
 
61
        // FRUIT TASK/THREAD WHICH RANDOMLY APPEARS AND DISAPPEARS
62
TASK FRUIT(void *arg)
63
{
64
 
65
  int xrnd = rand()%(XMAX-10),ox=5;
66
  int yrnd = rand()%(YMAX-10),oy=5;
67
  int colrnd = rand()%15;
68
  time_t seed;
69
  seed=sys_gettime(0);
70
  srand(seed); // RANDOMIZING POSITION OF  FRUIT
71
 
72
  while(1)
73
   {
74
    xrnd = rand()%(XMAX-10);
75
    yrnd = rand()%(YMAX-10);
76
    if ((xrnd > XMIN) &&(yrnd > YMIN)&& (scr[xrnd][yrnd]!=1))
77
    {
78
     sem_wait(&mutex);
79
     grx_disc(ox,oy,4,80);      // ERASE OLD FRUIT
80
     grx_disc(xrnd,yrnd,4,colrnd);     //PRINT NEW FRUIT
81
     sem_post(&mutex);
82
     colrnd = rand()%80;
83
     ox=xrnd; // STORE OLD X AND OLD Y POS TO ERASE OLD FRUIT
84
     oy=yrnd;
85
 
86
    }
87
    task_endcycle();
88
   }
89
  return(0);
90
}
91
 
92
        // KEY HANDLER FOR PLR1
93
void kp1(KEY_EVT *keypr)
94
{
95
  switch(keypr->ascii)
96
  { //grx_text(keypr->ascii, XMIN, YMENU+400, 1, 0);
97
    case 's':
98
     //  grx_text("S Up    pressed", XMIN, YMENU+450, 14, 0);
99
       dx1=0;
100
       dy1=-1;
101
 
102
       break;
103
    case 'x':
104
     //  grx_text("X Down  pressed", XMIN, YMENU+450, 14, 0);
105
       dx1=0;
106
       dy1=1;
107
 
108
       break;
109
    case 'c':
110
     //  grx_text("C Right pressed", XMIN, YMENU+450, 14, 0);
111
       dx1=1;
112
       dy1=0;
113
       break;
114
    case 'z':
115
     //  grx_text("Z Left  pressed", XMIN, YMENU+450, 14, 0);
116
       dx1=-1;
117
       dy1=0;
118
       break;
119
  }
120
}
121
 
122
   //        KEYHANDLER FOR PLR 2
123
void kp2(KEY_EVT *keypr)
124
{ switch(keypr->ascii)
125
  {
126
    case 'k':
127
     //  grx_text("k Up   Pressed", 450, YMENU+450, 14, 0);
128
       dx2=0;
129
       dy2=-1;
130
       break;
131
    case 44:
132
     //  grx_text(", Down Pressed",450, YMENU+450, 14, 0);
133
       dx2=0;
134
       dy2=1;
135
       break;
136
    case 46:
137
     //  grx_text(". Right Pressed",450, YMENU+450, 14, 0);
138
       dx2=1;
139
       dy2=0;
140
       break;
141
    case 'm':
142
     //  grx_text("m Left  Pressed", 450, YMENU+450, 14, 0);
143
       dx2=-1;
144
       dy2=0;
145
       break;
146
  }
147
}
148
     // ASSOCIATE KEYS WITH PLAYER1
149
void assockey1()
150
{
151
    KEY_EVT k;
152
    k.flag = 0;
153
    k.scan = KEY_S  ;// UP
154
    k.ascii = 's';
155
    keyb_hook(k,kp1);
156
 
157
    k.flag = 0;      // DOWN
158
    k.scan = KEY_X;
159
    k.ascii = 'x';
160
    keyb_hook(k,kp1);
161
    k.flag = 0;
162
    k.scan = KEY_Z;  //LEFT
163
    k.ascii = 'z';
164
    keyb_hook(k,kp1);
165
    k.flag = 0;
166
    k.scan = KEY_C;  //RIGHT
167
    k.ascii = 'c';
168
    keyb_hook(k,kp1);
169
}
170
     // ASSOCIATE KEYS WITH PLAYER2
171
void assockey2()
172
{
173
    KEY_EVT k;
174
    k.flag =0;
175
    k.scan =KEY_K;//UP
176
    k.ascii=53;
177
    keyb_hook(k,kp2);
178
 
179
    k.flag = 0;
180
    k.scan = 51;//DOWN
181
    k.ascii = ',';
182
    keyb_hook(k,kp2);
183
    k.flag = 0;
184
    k.scan = KEY_M;//LEFT
185
    k.ascii = 'm';
186
    keyb_hook(k,kp2);
187
    k.flag = 0;     //RIGHT
188
    k.scan = 52;
189
    k.ascii = '.';
190
    keyb_hook(k,kp2);
191
}
192
    // TASK SNAKE 1 .. PLAYER 1
193
 
194
TASK   sn1(void *arg)
195
{
196
    int    x1, y1;
197
    long score1 =0;
198
    int    col,outx=0,outy=0;
199
    //int    i = (int)arg;
200
    int over1=0;
201
    char  strk[30];
202
 
203
	x1 =  XMIN+20;
204
	y1 =  (YMIN+YMAX)/2;
205
    dx1=1;
206
    dy1=0;
207
    assockey1(); //       CALL FN to ASSOCIATE KEYS PLR1
208
    col = 12;             /* RED COLOUR SNAKE           */
209
 
210
	while (1)
211
	{
212
		x1 += dx1;
213
		y1 += dy1;
214
                   //CHECK IF BEYOND BORDER
215
		outx = (x1 >= XMAX-D) || (x1 <= XMIN+D);
216
		outy = (y1 >= YMAX-D) || (y1 <= YMIN+D);
217
 
218
                  //CHECK IF STONE OR ANOTHER SNAKE
219
        if ((scr[x1+D*dx1][y1+D*dy1]) ==0)
220
         {      scr[x1][y1]=1; // bcos the snake radius is 3;
221
               scr[x1+dy1][y1+dx1] =1;
222
               scr[x1-dy1][y1-dx1] =1;
223
         }
224
        else         //STONE OR SNAKE HIT
225
         { over1=1;  //SET ERR FLAG=1
226
           sprintf(strk,"PLR 1 HIT :PID = %d",pid1);
227
         }
228
 
229
        if (outx || outy) // WALL CRASH
230
         {
231
			sprintf(strk,"PLR 1 WALL CRASH %d ",pid1);
232
            over1=1;
233
		}
234
         if (over1 ==1) //CHECK IF HIT OR CRASH DECLARE OTHER AS WINNER
235
           {grx_text(strk, 120,70,0,69);
236
           grx_text(" WINNER !!! ",340+80,70,0,67);
237
           endgame();
238
           break;
239
           }
240
        score1=score1+10;
241
          // CHECK IF BACKGROUND COLOUR OR FRUIT
242
        if (grx_getpixel(x1+D*dx1,y1+D*dy1)!= 80)
243
          score1+=100;          // BONUS = 1000
244
        sprintf(strk,"%ld",score1);
245
        grx_text(strk,120,60,0,15);//PRINT SCORE
246
		draw_sn(x1, y1, col);
247
      	task_endcycle();
248
 
249
        }
250
  return(0);
251
}
252
 
253
    //    TASK SNAKE2 -- PLAYER 2
254
TASK   sn2(void *arg)
255
{
256
    int     x2, y2,col;
257
    long int   score2=0;
258
    int     outx=0, outy=0;
259
    //int    i = (int)arg;
260
    int over2=0;
261
    char strk[30];
262
 
263
    assockey2();
264
	x2 = XMAX-20;
265
	y2 = (YMIN+YMAX)/2;
266
    dx2=-1;
267
    dy2=0;
268
	col =10;         /* BLUE colore SNAKE2   */
269
 
270
	while (1)
271
	{
272
		x2 += dx2; //SET NEW POS
273
		y2 += dy2;
274
           //      //CHECK IF BEYOND BORDER
275
		outx = (x2 >= XMAX-D) || (x2 <= XMIN+D);
276
		outy = (y2 >= YMAX-D) || (y2 <= YMIN+D);
277
           //CHECK IF STONE OR ANOTHER SNAKE
278
         if ((scr[x2+D*dx2][y2+D*dy2]) ==0)
279
         {      scr[x2][y2]=1; // bcos the snake radius is 3;
280
               scr[x2+dy2][y2+dx2] =1;
281
               scr[x2-dy2][y2-dx2] =1;
282
         }
283
        else    //STONE OR SNAKE HIT
284
         {
285
            over2=1;    //SET ERR FLAG
286
            sprintf(strk," HIT :PID = %d",pid2);
287
            grx_text(strk,340+80,70,0,67);
288
 
289
		 }
290
		if (outx || outy) // WALL CRASH
291
         {
292
            over2=1;
293
            sprintf(strk," WALL CRASH PID= %d",pid2);
294
 
295
		 }
296
        if(over2==1)      //DECLARE OTHER AS WINNER
297
         { grx_text(strk,340+80,70,0,67);
298
           grx_text(" WINNER !!! ",120,70,0,69);
299
           endgame();
300
           break;
301
         }
302
        score2=score2+10;
303
        if (grx_getpixel(x2+D*dx2,y2+D*dy2)!= 80)
304
          score2+=100;
305
 
306
        sprintf(strk,"%ld",score2);
307
        grx_text(strk,340+80,60,0,15);//
308
    	draw_sn(x2, y2, col);
309
        sprintf(strk,"%d",scr[x2][y2]);
310
    	task_endcycle();
311
      }
312
   return(0);
313
}
314
/****************************************************************/
315
 
316
 void endgame()
317
 {  group_kill(SNGROUP);// KILL ALL SNAKES AND FRUIT TASK
318
    grx_clear(1);
319
    grx_text("THANK U FOR PLAYING SNAKES GAME ",200,250,14,1);
320
    grx_text("PRESS ESC KEY ",250,300,14,1);
321
 }
322
 
323
                /* FN CALLED WHEN SYSTEM EXITS  */
324
 void byebye(void *arg)
325
 {
326
    grx_close();
327
    kern_printf("\nCiao ! Bye Bye!\n");
328
 }
329
       // FN TO DRAW STONES
330
 void stone(int xmin,int ymin,int xmax,int ymax,int col)
331
 {  int i,j;
332
    grx_box(xmin,ymin,xmax,ymax,col);
333
    grx_rect(xmin,ymin,xmax,ymax,0);
334
    for(i=xmin;i<=xmax;i++)
335
     for(j=ymin;j<=ymax;j++)
336
      {scr[i][j]=1; // col
337
      }
338
 }
339
 
340
void setplarea()
341
{   int i,j;
342
    char col[2];
343
    // SET SCR ARRAY WHICH REPRESENTS BG TO ZERO ALL
344
    for(i=0;i<=XMAX-1;i++)
345
     for(j=0;j<=YMAX-1;j++)
346
         scr[i][j]=0;
347
 
348
     /* GRAPHICS FOR THE  PLAY AREA */
349
    grx_box(0,0,640,480,15); // FULL SCREEN
350
    grx_rect(XMIN-D, YMIN-1, XMAX+1, YMAX+1,1); // BOUNDARY
351
    grx_box(XMIN,YMIN,XMAX,YMAX,80);           //PLAY AREA
352
 
353
    // DRAW STONES
354
 
355
       stone(120,150,140,160,4);
356
       stone(220,150,230,170,4);
357
       stone(340,150,360,160,4);
358
       stone(500,150,510,170,4);
359
 
360
       stone(100,240,110,260,4);
361
       stone(300,250,320,260,4);
362
       stone(550,250,560,270,4);
363
       stone(350,270,370,280,4);
364
 
365
       stone(50, 410,70,420,4);
366
       stone(250,400,260,420,4);
367
       stone(370,400,390,410,4);
368
       stone(490,400,500,420,4);
369
       stone(150,400,170,410,4);
370
 
371
       stone(60,300,80,310,4);
372
       stone(530,200,550,210,4);
373
       stone(510,300,520,320,4);
374
 
375
 
376
             // CREATE BACKGROUND
377
    grx_text("  SIMULATION OF SNAKES GAME  ", XMIN+200,10,9,15);
378
    grx_text(" 1 . SPACE : START GAME SnakeS" , XMIN, 20,4,15);
379
    grx_text(" 2 . ESC   : Exit to DOS    ", 380, 20,2,15);
380
              // PLAYER 1 STATISTICS
381
    grx_box(XMIN,50,320,80,69);
382
    grx_rect(XMIN-2,50-2,320,80,0);
383
    grx_text(" PLAYER 1     ", XMIN, 50, 0, 69);
384
    grx_text(" SCORE   : "   , XMIN, 60, 0, 69);
385
    grx_text(" STATUS  : "   , XMIN, 70, 0, 69);
386
 
387
    grx_text("UP    - s",80,460, 0, 69);
388
    grx_text("DOWN  - x",80,470, 0, 69);
389
    grx_text("LEFT  - z",200,460, 0, 69);
390
    grx_text("RIGHT - c",200,470, 0, 69);
391
 
392
              // PLAYER 2 STATISTICS
393
    grx_box(340,50,600,80,67);
394
    grx_rect(340-2,50-2,600,80,0);
395
    grx_text(" PLAYER 2     " , 340, 50, 1, 67);
396
    grx_text(" SCORE   : "     , 340, 60, 1, 67);
397
    grx_text(" STATUS  : "     , 340, 70, 1, 67);
398
    grx_text("UP    - k",380,460, 1, 67);
399
    grx_text("DOWN  - ,",380,470, 1, 67);
400
    grx_text("LEFT  - m",500,460, 1, 67);
401
    grx_text("RIGHT - .",500,470, 1, 67);
402
 
403
             // DESIGN
404
    for(i=0,j=0;i<=60;i++)
405
    {
406
        j=j+10;
407
        sprintf(col,"C%d",i);
408
        grx_text(col,j,30,i, 0);
409
    }
410
}
411
 
412
void initscr()
413
{   int i,j,col;
414
    grx_clear(15);
415
    for(i=0,col=0;i<640;i=i+10)
416
      for(j=0;j<480;j=j+10)
417
    {
418
      //  sprintf(col,"C%d",col++%255);
419
        grx_text("",i,j,(col++)%255, 0);
420
    }
421
 
422
    grx_text("THE HUNGRY SNAKE  ",250,100,9,15);
423
    sleep(1);
424
          // DISPLAY MODE SELECTION MENU SCREEN
425
 
426
    grx_clear(8);
427
    grx_text("THE HUNGRY SNAKE  ",250,100,14,8);
428
    grx_text("SELECT THE MODE OF PLAY ",200,150,10,8);
429
    grx_text("1. SINGLE PLAYER MODE ",200,200,12,8);
430
    grx_text("2. DOUBLE PLAYER MODE ",200,250,80,8);
431
    grx_text("3. EXIT ",200,300,80,8);
432
 
433
}
434
 
435
int main(int argc, char **argv)
436
{
437
 
438
    HARD_TASK_MODEL m;
439
    SOFT_TASK_MODEL f;
440
    char c;
441
    int  ntask = 1;        /* NO OF TASKS      */
442
 
443
    hard_task_default_model(m);
444
    hard_task_def_ctrl_jet (m);
445
    hard_task_def_arg      (m, (void *)ntask);
446
    hard_task_def_wcet     (m, SN_WCET);
447
    hard_task_def_mit      (m, SN_T);
448
    hard_task_def_group    (m, SNGROUP);
449
    hard_task_def_unjoinable(m);
450
    hard_task_def_usemath  (m);//fl pt arith
451
                  // SOFT TASK FOR FRUIT/FRUIT
452
    soft_task_default_model(f);
453
    soft_task_def_level(f,1);
454
    soft_task_def_arg(f, (void *)4);
455
    soft_task_def_group(f,SNGROUP);
456
    soft_task_def_met(f,FRUIT_WCET);
457
    soft_task_def_period(f,FRUIT_T);
458
    soft_task_def_usemath(f);
459
    soft_task_def_unjoinable(f);
460
 
461
    set_exchandler_grx();       /*SET EXCEPN HANDLER */
462
 
463
    /* Set the closing function */
464
    sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT);
465
 
466
    /* graphic card Initialization */
467
 
468
    if (grx_init() < 1)
469
      {
470
       cprintf("GRAPHICS INIT ERROR ,ABORTING ");
471
       sys_abort(1);
472
      }
473
    grx_cardinfo(); // TO SEE THE V CARD DETAILS IN TEXT MODE
474
    grx_modeinfo();
475
 
476
      //sleep(2);
477
 
478
    if (grx_open(640, 480, 8) < 0)
479
     {
480
        kern_printf("GRX Err CANT OPEN IN REQ MODE\n");
481
     	sys_abort(1);
482
     }
483
    kern_printf("Video card ok!\n");
484
 
485
REP:initscr(); // call FN TO DISPLAY MENU
486
 
487
    c= keyb_getchar();  // CHOOSE GAME MODE
488
 
489
    switch(c)
490
      {
491
      case '1':
492
           grx_text("1. SINGLE PLAYER MODE ",200,350,8,0);
493
           pid1 = task_create("SNAKE1", sn1, &m, NULL); //PLR1
494
           break;
495
 
496
      case '2':
497
           pid1 = task_create("SNAKE1", sn1, &m, NULL); //PLR1
498
           pid2 = task_create("SNAKE2",sn2,&m,NULL);  //PLR2
499
           break;
500
      case '3':
501
           sys_end();
502
           return 0;
503
      case ESC:
504
           grx_clear(0);
505
           grx_close();
506
           sys_end();
507
           return 0;
508
      default :
509
           grx_text("WRONG KEY PRESSED ",200,400,69,7);
510
            goto REP;
511
 
512
      }
513
 
514
     setplarea(); // GRAPHICS FOR PLAY AREA
515
 
516
     /* The program waits a space to start THE SNAKE GAME */
517
    c = keyb_getch(NON_BLOCK);
518
    do{
519
     if ((c == ' '))// && (ntask < 2)) // 2 PLAYERS
520
	    {
521
                    //CHECK FOR CREATION ERRORS
522
        if (pid1 == NIL)
523
         {
524
	      grx_close();
525
	      perror("CANT CREATE PID1 PRESS ESC");
526
	      sys_abort(1);
527
	     }
528
        if (pid2 == NIL)
529
         {
530
	      grx_close();
531
	      perror("CANT CREATE PID2 PRESS ESC");
532
	      //sys_abort(1);// I HAVE COMMENTED THIS BCOS IT DOESNT SHOW MSG
533
                         // IF PID = NIL
534
	     }
535
        if (pid3 == NIL)
536
         {
537
	      grx_close();
538
	      perror("CANT CREATE PID3 PRESS ESC ");
539
	      //sys_abort(1);
540
	     }           //ACTIVATE TASKS ;
541
        //CREATE TASK
542
        pid3 = task_create("FRUIT",FRUIT,&f,NULL); //FRUIT TASK
543
        group_activate(SNGROUP);
544
	    ntask++;
545
        }
546
     c=keyb_getch(NON_BLOCK);
547
    } while (c != ESC); //EXIT If ESC PRESSED
548
    goto REP;
549
    sys_end();
550
    return 0;
551
}
552
 
553
/*------------------END--OVER-----------------------------------*/