2015-12-24 27 views
0

我有一個作爲connectfour遊戲原型的程序,作爲一個家庭作業項目。 到目前爲止這麼好,但我有一個主要問題,我如何限制客戶只有其中的兩個,而且,當我要驗證哪個列選取自哪一個時,我怎樣才能輕鬆識別它們?限制和識別客戶端TCP

#include <sys/types.h> 
#include <sys/socket.h> 
#include <netinet/in.h> 
#include <errno.h> 
#include <unistd.h> 
#include <stdio.h> 
#include <string.h> 
#include <stdlib.h> 
#include <signal.h> 
#include <pthread.h> 

//used port 
#define PORT 6660 
//array limits 
#define WIDTH 7 
#define HEIGTH 6 

//error code for some applications 
extern int errno; 

//static column variables 

static int gameVariables [WIDTH] = {6, 6, 6, 6, 6, 6, 6}; 
static char gameArray[HEIGTH][WIDTH]; 

static void *treat(void *);//function called by every thread 
typedef struct thData 
{ 
    pthread_t idThread; //id Thread 
    int cl;//descriptor returned by accept 
}thData; 

//Thread *threadsPool; //Threads array 

//int sd;//listenning socket descriptor 
//int nthreads; //number of threadsPool 

//pthread_mutex_t mlock = PTHREAD_MUTEX_INITIALIZER; //mutex variable 
static void *treat(void *); 
//void raspunde (void *); 
void connectFour(void *); 

void printArray(char array[HEIGTH][WIDTH]) 
{ 
    int k, j; 
for(k = 0; k < HEIGTH; k++) 
    { 
     for(j=0; j < WIDTH; j++) 
     printf("%c ", array[k][j]); 
     printf("\n"); 
    } 
} 

int main() 
{ 
    //game array inialization 
    int k, j; 
    for(k = 0; k < HEIGTH; k++) 
    for(j = 0; j < WIDTH; j++) 
     gameArray[k][j] = (char) 79; 


    printArray(gameArray); 

    struct sockaddr_in server; //structure used by server 
    //void threadCreate(int); 
    struct sockaddr_in from; 
    int message; 
    int sd; 
    int pid; 
    pthread_t th[100]; 
    int i = 0; 
    /*if(argc < 2) 
    { 
    fprintf(stderr, "Error: first argument is the number of thread\n"); 
    exit(1); 
    } 

    nthreads = atoi(argv[1]); 
    if(nthreads <= 0) 
    { 
    fprintf(stderr,"Error: number of threads invalid\n"); 
    exit(1); 
    } 

    threadsPool = calloc(sizeof(Thread), nthreads); 
*/ 
    //create socket 
    if((sd = socket(AF_INET, SOCK_STREAM, 0)) == -1) 
    { 
    perror("[SERVER] Error at socket\n"); 
    return errno; 
    } 

    //using SO_REUSEADDR 
    int on = 1; 
    setsockopt(sd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)); 

    //preparing data structures 
    bzero(&server, sizeof(server)); 
    bzero(&from, sizeof(from)); 

    server.sin_family = AF_INET; 
    server.sin_addr.s_addr = htonl(INADDR_ANY); 
    server.sin_port = htons(PORT); 

    //bind the socket 
    if(bind(sd, (struct sockaddr *) &server, sizeof(struct sockaddr))== -1) 
    { 
    perror("[SERVER] Error at bind\n"); 
    return errno; 
    } 

    //server listening 
    if(listen(sd, 2) == -1) 
    { 
    perror("[SERVER] Error at listen\n"); 
    return errno; 
    } 

/* printf("Number of threads %d\n", nthreads); 
    fflush(stdout); 

    int i; 
    for(i = 0; i < nthreads; i++) 
    threadCreate(i); 

    //serving concurrent clients using threads 
    for(; ;) 
    { 
    printf("[SERVER] Listening at port : %d", PORT); 
    pause(); 
    }//for 
*/ 
    //serving clients 
    for(; ;) 
    { 
    int client; 
    thData *td; //parameter executed by thread 
    int length = sizeof(from); 

    printf("[SERVER] Waiting at port : %d\n", PORT); 
    fflush(stdout); 
    //accept client 
    if((client = accept (sd, (struct sockaddr *) &from, &length)) < 0) 
    { 
     perror ("[SERVER]Error at accept\n"); 
     continue; 
    } 
    //connection established 
    int idThread; //thread id 
    int cl; 

    td = (struct thData*)malloc(sizeof(struct thData)); 
    td -> idThread = i++; 
    td -> cl = client; 

    pthread_create (&th[i], NULL, &treat, td); 
    } //for 
};//main 

static void *treat(void * arg) 
{ 
    struct thData tdL; 
    tdL= *((struct thData*)arg); 
    printf ("[thread]- %d - Waiting message\n", tdL.idThread); 
    fflush (stdout);  
    pthread_detach(pthread_self()); 
    connectFour((struct thData*)arg); 
    /* am terminat cu acest client, inchidem conexiunea */ 
    close ((int)arg); 
    return(NULL); 

}; 

/* 
void raspunde (void *arg) 
{ 
    int i = 0; 
    char message[50], message2[100]; 
    struct thData tdL; 
    tdL = *((struct thData*) arg); 
    bzero(message, 50); 
    if(read(tdL.cl, message, 50) <= 0) 
    { 
    printf("[thread %d]\n", tdL.idThread); 
    perror("Error at read from client\n"); 
    } 

    printf("[thread %d] Message was received %s\n", tdL.idThread, message); 
    //preparing answer 
    /*bzero(message2, 100); 
    strcat(message2, "Hello, "); 
    strcat(message2, message); 
    printf("[thread %d] Sending back message %s\n", tdL.idThread, message2); 

    //returning message 
    if(write(tdL.cl, message2, 100) <= 0) 
    { 
    printf("[thread %d]\n", tdL.idThread); 
    perror("[thread] Error at write\n"); 
    } 
    else 
    printf("[thread %d] Message was sent with success\n", tdL.idThread); 
}; 
*/ 

void connectFour(void *arg) 
{ 

    int playerPick; 
    char message[50]; 

    struct thData tdL; 
    tdL = *((struct thData*) arg); 
    bzero(message, 2); 

    if(read (tdL.cl, message, 50) <= 0) 
    { 
    printf("[thread %d]\n", tdL.idThread); 
    perror("Error at read from client\n"); 
    } 

    printf ("[thread %d]Column pick received is : %s\n", tdL.idThread, message); 
    playerPick = atoi(message); 

    printf("playerPick is : %d\n", playerPick); 
    fflush(stdout); 
    switch(playerPick) 
    { 
    case 1: 
    if(gameVariables[0] >0 && gameVariables[0] < 7) 
     { 
     --gameVariables[0]; 
     gameArray[gameVariables[0]][0] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 2: 

     if(gameVariables[1] >0 && gameVariables[1] < 7) 
     { 
     --gameVariables[1]; 
     gameArray[gameVariables[1]][1] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 3: 
     if(gameVariables[2] >0 && gameVariables[2] < 7) 
     { 
      --gameVariables[2]; 
      gameArray[gameVariables[2]][2] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 4: 
     if(gameVariables[3] >0 && gameVariables[3] < 7) 
     { 
      --gameVariables[3]; 
      gameArray[gameVariables[3]][3] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 5: 
     if(gameVariables[4] >0 && gameVariables[4] < 7) 
     { 
     --gameVariables[4]; 
     gameArray[gameVariables[4]][4] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 6: 
     if(gameVariables[5] >0 && gameVariables[5] < 7) 
     { 
     --gameVariables[5]; 
     gameArray[gameVariables[5]][5] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 
    case 7: 
     if(gameVariables[6] >0 && gameVariables[6] < 7) 
     { 
     --gameVariables[6]; 
     gameArray[gameVariables[6]][6] = (char) 82; 
     } 
     printArray(gameArray); 
     break; 

    } 
    printf("%d %d %d %d %d %d %d\n", gameVariables[0], gameVariables[1], gameVariables[2], gameVariables[3], gameVariables[4], gameVariables[5], gameVariables[6]); 


} 

;

回答

1

您只需保留一個您在接受連接時檢查的計數器。當客戶端連接時,檢查計數器是否超出限制,然後關閉連接,否則保持連接並增加計數器。當客戶斷開連接時(無論什麼原因)你減少計數器。


即使您立即再次關閉它們,確實接受所有連接也很重要。這是因爲等待accept的套接字隊列不是無限的。一旦你填滿它,沒有更多的客戶將能夠連接。