Jeff Tsen 1 year ago
parent
commit
84c72fa8c4
6 changed files with 227 additions and 37 deletions
  1. 14 0
      Makefile
  2. 50 0
      boardGenerator.c
  3. BIN
      demo_server
  4. 123 32
      game_server.c
  5. 5 2
      game_server.h
  6. 35 3
      players.c

+ 14 - 0
Makefile

@@ -0,0 +1,14 @@
+PORT = 7418
+CFLAGS+= =DPORT=\$(PORT)
+all: boggle_server
+
+game_server.o: game_server.h
+	gcc -g -Wall -Werror -std=gnu99 -c game_server.c
+boardGenerator.o: game_server.h
+	gcc -g -Wall -Werror -std=gnu99 -c boardGenerator.c
+players.o: game_server.h
+	gcc -g -Wall -Werror -std=gnu99 -c players.c
+boggle_server: game_server.o boardGenerator.o players.o
+	gcc -g -Wall -Werror -std=gnu99 -o boggle_server game_server.o boardGenerator.o players.o
+clean:
+	rm game_server.o boardGenerator.o players.o boggle_server

+ 50 - 0
boardGenerator.c

@@ -0,0 +1,50 @@
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+#include "game_server.h"
+
+char* boardGenerator(){
+        char* diceList[] = {
+                "RIFOBX","IFEHEY","DENOWS","UTOKND",
+                "HMSRAO","LUPETS","ACITOA","YLGKUE",
+                "QBMJOA","EHISPN","VETIGN","BALIYT",
+                "EZAVND","RALESC","UWILRG","PACEMD"
+        };
+
+        char* boardValues;
+        boardValues = malloc(16);
+
+        int dieSelected[16];
+        for(int i = 0; i < 16; i++){
+                dieSelected[i] = 0;
+        }
+
+        srand(time(0));
+        int dieChoice;
+        int dieSide;
+        int boardValueCounter = 0;
+        while(boardValueCounter < 16){
+                dieChoice = rand() % 16;
+                if(dieSelected[dieChoice]==1){
+                         continue;
+                 }
+         dieSide = rand() % 6;
+         dieSelected[dieChoice] = 1;
+         boardValues[boardValueCounter] = diceList[dieChoice][dieSide];
+         boardValueCounter++;
+        }
+        return boardValues;
+}
+
+void boardCreator(char* boardValues){
+        printf("---------\n");
+        printf("|%c|%c|%c|%c|\n",boardValues[0],boardValues[1],boardValues[2],boardValues[3]);
+        printf("|-------|\n");
+        printf("|%c|%c|%c|%c|\n",boardValues[4],boardValues[5],boardValues[6],boardValues[7]);
+        printf("|-------|\n");
+        printf("|%c|%c|%c|%c|\n",boardValues[8],boardValues[9],boardValues[10],boardValues[11]);
+        printf("|-------|\n");
+        printf("|%c|%c|%c|%c|\n",boardValues[12],boardValues[13],boardValues[14],boardValues[15]);
+        printf("---------\n");
+}
+

BIN
demo_server


+ 123 - 32
game_server.c

@@ -6,6 +6,7 @@ Player *player_list = NULL;
 Client *client_list = NULL;
 
 short port = -1;
+char *board = NULL;
 
 int main(int argc, char* argv[]) {
     struct client *p;
@@ -18,13 +19,33 @@ int main(int argc, char* argv[]) {
     int listenfd = setup();
     
     //TODO install timer signal handler
+    signal(SIGALRM,timer_handler);
    
 	//start timer
     alarm(TIMER_TICK);
 
 	//TODO: implement select()
     while (1) {
-        
+        fd_set fdlist;
+	int maxfd = listenfd;
+	FD_ZERO(&fdlist);
+	FD_SET(listenfd, &fdlist);
+	for(p = client_list; p; p = p->next){
+		FD_SET(p->fd, &fdlist);
+		if(p->fd > maxfd)
+			maxfd = p->fd;
+	}
+	if(select(maxfd+1, &fdlist,NULL,NULL,NULL)<0){
+		perror("select");
+	}else{
+		for(p=client_list; p; p=p->next)
+			if(FD_ISSET(p->fd,&fdlist))
+				break;
+		if(p)
+			receiveclient(p);
+		if(FD_ISSET(listenfd, &fdlist))
+			new_connection(listenfd);
+	}
     }
     return 0;
 }
@@ -72,11 +93,12 @@ int setup (void) {
 void timer_handler(int sig) {
 	//broadcast current game end to all connected clients
 	Client *curr;
-	for (curr = top; curr!=NULL; curr = curr->next) {
+	for (curr = client_list; curr!=NULL; curr = curr->next) {
             sendclient(curr, "Game over\r\n");
     }
 	
 	//TODO - generate new game board
+	board = boardGenerator();
 	
 	//reset the timer so we get called again in 120 seconds
 	alarm(TIMER_TICK);
@@ -100,19 +122,19 @@ void new_connection (int listenfd)  {
 /* creates a new client struct and 
 TODO - adds it to the list of clients */
 void add_client(int fd, struct in_addr addr){
-    struct client *p = malloc(sizeof(struct client));
-    if (!p) {
-        perror("malloc failure");
-        exit(1);
-    }
-    printf("Adding client %s\n", inet_ntoa(addr));
-    fflush(stdout);
-    p->fd = fd;
-    p->state = NAME; //needs yet to identify new client by name
-    p->inbuf = 0;
-    //TODO - add it to the list of clients
-
-    
+	struct client *p = malloc(sizeof(struct client));
+	if (!p) {
+		perror("malloc failure");
+		exit(1);
+	}
+	printf("Adding client %s\n", inet_ntoa(addr));
+	fflush(stdout);
+	p->fd = fd;
+	p->state = NAME; //needs yet to identify new client by name
+	p->inbuf = 0;
+	//TODO - add it to the list of clients
+	p->next = client_list;
+	client_list = p; 
 	sendclient(p, "What is your player name?\n");
 }
 
@@ -165,7 +187,7 @@ void interpret_message(Client *p) {
     } else if (!strcmp(p->buf, "q")) {
         remove_client(p->fd);
     } else {
-        parse_line(p, &player_list);
+        parse_line(p);
     }
 }
 
@@ -198,12 +220,59 @@ int do_command(struct client * p, int cmd_argc, char **cmd_argv) {
     if (cmd_argc <= 0) {
         return 0;
     } else if (strcmp(cmd_argv[0], "q") == 0 && cmd_argc == 1) {
+	sendclient(p,"Thanks for playing! I hope to see you soon.\r\n");
         return -1;
     } else if (strcmp(cmd_argv[0], "all_players") == 0 && cmd_argc == 1) {
 		//TODO produce list of all players and their stats in nice text format and sendclient
+		Player *temp = player_list;
+		while(temp!=NULL){
+			char string [BUFFER_SIZE-10];
+			sprintf(string, "Name:%s\tMax Score:%d\tTotal Games:%d\tTotal Score:%d\n", temp->name, temp->max_score, temp->total_games, temp->total_score);
+			sendclient(p,string);
+			temp = temp->next;
+		}
         
     } else if (strcmp(cmd_argv[0], "top_3") == 0 && cmd_argc == 1) {
 		//TODO produce list of top 3 players with their total score and sentclient as a text
+		Player* curr = player_list;
+		int all_scores[10] = {-1};
+		int high_score_indices[3] = {-1};
+		int counter = 0, curr_max = -1, curr_max_index, curr_print = 1;
+		while(curr->next!=NULL){
+			all_scores[counter] = curr->max_score;
+			counter++; 
+			curr = curr->next;
+		}
+		all_scores[counter] = curr->max_score;
+		counter++;
+		for(int j = 0; j < counter; j++){
+			for(int i =0;i<10;i++){
+				
+				if(all_scores[i] > curr_max){
+					curr_max = all_scores[i];
+					curr_max_index = i;
+				}
+			}
+			high_score_indices[j] = curr_max_index;
+			all_scores[curr_max_index] = -1;
+			curr_max = -1;
+			curr_max_index = -1;
+		}
+		curr = player_list;
+		for(int k = 0; k < counter; k++){
+			if(high_score_indices[k] == -1){
+				break;
+			}
+			for(int h = 0; h < high_score_indices[k]; h++){
+				curr = curr->next;
+			}
+			char str [1023];
+			sprintf(str, "%d.%s\t%d\n", curr_print, curr->name, curr->max_score);
+			sendclient(p, str);
+			curr_print++;
+			curr = player_list;
+		}
+		
        
     } else if (strcmp(cmd_argv[0], "add_score") == 0 && cmd_argc == 2) {
         char str [BUFFER_SIZE - 10];
@@ -216,7 +285,25 @@ int do_command(struct client * p, int cmd_argc, char **cmd_argv) {
         sprintf (str, "added score %d for player %s\r\n", score, p->name);
         sendclient(p, str);
     } else if (strcmp(cmd_argv[0], "new_game") == 0 && cmd_argc == 1) {
-        //TODO -- transmit current board to be presented as a 2D array of chars
+		//TODO -- transmit current board to be presented as a 2D array of chars
+		Player *temp = find_player(p->name, player_list);
+		temp->total_games++;
+		int counter = 0;
+		board = boardGenerator();
+		char new_board[4][8];
+		for(int i = 0; i<4; i++){
+			for(int j = 0; j < 8; j++){
+				if(j==0||j==2||j==4||j==6){
+					new_board[i][j] = board[counter];
+					counter++;
+				}else if(j==1||j==3||j==5){
+					new_board[i][j] = ' ';
+				}else{
+					new_board[i][j] = '\n';
+				}
+			}
+		}
+		sendclient(p, new_board[0]);
     }else {
         sendclient(p, "Incorrect syntax\r\n");
     }
@@ -224,14 +311,6 @@ int do_command(struct client * p, int cmd_argc, char **cmd_argv) {
 }
 
 
-
-
-
-   
-
-
-
-
 void sendclient(struct client *p, char *msg) {
     write(p->fd, msg, strlen(msg));
 }
@@ -249,10 +328,22 @@ int find_network_newline(char *buf, int inbuf) {
 	return -1;
 }
 
-
-
-
-
-
-
-
+void remove_client(int fd){
+	struct client **p;
+	for(p = &client_list; *p && (*p)->fd != fd; p = &(*p)->next)
+		;
+	if(*p){
+		struct client *t = (*p)->next;
+		fprintf(stderr, "Removing client %s\n", (*p)->name);
+		fflush(stdout);
+		free(*p);
+		if(close(fd) != 0){
+			perror("closing fd on exiting client");
+			exit(1);
+		}
+		*p = t;
+	}else{
+		fprintf(stderr, "Trying to remove fd %d, but I don't know about it\n", fd);
+		fflush(stderr);
+	}
+}

+ 5 - 2
game_server.h

@@ -9,10 +9,11 @@
 #include <sys/select.h>
 #include <signal.h>
 #include <sys/time.h>
+#include <errno.h>
 
 
 #ifndef PORT
-  #define PORT 8888
+  #define PORT 7418
 #endif
 
 
@@ -106,5 +107,7 @@ int parse_line(Client *p);
 int do_command(struct client * p, int cmd_argc, char **cmd_argv);
 
 int find_network_newline(char *buf, int inbuf);
+char* boardGenerator();
+void boardCreator(char* boardValues);
 
-#endif
+#endif

+ 35 - 3
players.c

@@ -8,7 +8,33 @@
  * of players whose head is pointed to by *player_ptr_add.
  */
 int create_player(const char *name, Player **player_ptr_add) {
-   return 0;
+	Player *new_player = malloc(sizeof(Player));
+	Player *temp = *player_ptr_add;
+	if(strlen(name) > MAX_NAME){
+		return 2;
+	}
+	while(temp!=NULL){
+		if(strcmp(name, temp->name) == 1)
+			return 1;
+		temp = temp->next;
+	}
+	strncpy(new_player->name, name, MAX_NAME);
+	new_player->max_score = 0;
+	new_player->total_games = 0;
+	new_player->total_score = 0;
+	new_player->next = NULL;
+	Player *curr = *player_ptr_add;
+	if(*player_ptr_add == NULL){
+		*player_ptr_add = new_player;
+		return 0;
+	}
+	while(curr->next != NULL){
+		curr = curr->next;
+	}
+	curr->next = new_player;
+	temp = new_player;
+	
+	return 0;
 }
 
 //TODO - implement this
@@ -16,8 +42,14 @@ int create_player(const char *name, Player **player_ptr_add) {
  * Return a pointer to the player with this name in
  * the list starting with head. Return NULL if no such player exists. 
  */
-Player *find_player(const char *name, const Player *head) {    
-    return NULL;
+Player *find_player(const char *name, const Player *head) { 
+	Player* temp =(Player *)head;
+	while(temp){
+		if(strcmp(temp->name, name) == 0)
+			return temp;
+		temp = temp->next;
+	}
+	return NULL;
 }