Torna indietro   Hardware Upgrade Forum > Software > Programmazione

Google Pixel 10 è compatto e ha uno zoom 5x a 899€: basta per essere un best-buy?
Google Pixel 10 è compatto e ha uno zoom 5x a 899€: basta per essere un best-buy?
Google Pixel 10 è uno smartphone che unisce una fotocamera molto più versatile rispetto al passato grazie allo zoom ottico 5x, il supporto magnetico Pixelsnap e il nuovo chip Tensor G5. Il dispositivo porta Android 16 e funzionalità AI avanzate come Camera Coach, mantenendo il design caratteristico della serie Pixel con miglioramenti nelle prestazioni e nell'autonomia. In Italia, però, mancano diverse feature peculiari basate sull'AI.
Prova GeForce NOW upgrade Blackwell: il cloud gaming cambia per sempre
Prova GeForce NOW upgrade Blackwell: il cloud gaming cambia per sempre
L'abbonamento Ultimate di GeForce NOW ora comprende la nuova architettura Blackwell RTX con GPU RTX 5080 che garantisce prestazioni tre volte superiori alla precedente generazione. Non si tratta solo di velocità, ma di un'esperienza di gioco migliorata con nuove tecnologie di streaming e un catalogo giochi raddoppiato grazie alla funzione Install-to-Play
Ecovacs Deebot X11 Omnicyclone: niente più sacchetto per lo sporco
Ecovacs Deebot X11 Omnicyclone: niente più sacchetto per lo sporco
Deebot X11 Omnicyclone implementa tutte le ultime tecnologie Ecovacs per l'aspirazione dei pavimenti di casa e il loro lavaggio, con una novità: nella base di ricarica non c'è più il sacchetto di raccolta dello sporco, sostituito da un aspirapolvere ciclonico che accumula tutto in un contenitore rigido
Tutti gli articoli Tutte le news

Vai al Forum
Rispondi
 
Strumenti
Old 26-02-2010, 20:10   #1
ginter87
Member
 
Iscritto dal: Apr 2008
Messaggi: 62
[C] Client/Server - Il mio server si rifiuta di accettare piu client, ne vuole uno

Uff!
Il mio elaborato riguarda una videointerrogazione in rete dove il server è il professore mentre i clients sono gli studenti.

Il mio problema è che io vorrei che il prof invii inizialmente la prima domanda a tutti gli studenti, poi uno di loro risponde, entra in sez critica, gli altri aspettano lui risponde e quando ha terminato si passa alla domanda successiva.

Ciò non avviene O_O

Il mio server prende e accetta il primo ... gli manda le domande aspettando le risposte, fa tutti i controlli di correttezza, assegnamento punteggio poi chiude e finisce mentre invece dovrebbe partecipare anche l'altro client.

Ho provato ad aprire 3 terminali, dove uno è il server e gli altri due sono i client e non so se magari questo "errore" è dovuto all'esecuzione in locale oppure no ...

vi metto il codice ... ditemi, sigh io ho esame l'8 marzo ... sigh
grazie anticipatamente

CODICE SERVER
Codice:
#include <stdio.h> // per I/O

#include <stdlib.h> // per exit, malloc, atoi...

#include <unistd.h> // per exec, getpid...

#include <pthread.h> // thread

#include <semaphore.h> //semafori posix

#include <sys/types.h> // standard posix
#include <netinet/in.h> //

#include <sys/socket.h> // socket

#include <signal.h> // segnali

#include <string.h>
#include <pthread.h>
#include <sys/types.h>
#include <semaphore.h>
#include <sys/types.h>

#include <semaphore.h>

#include <fcntl.h>

#define totpost 3 //numero studenti

#define MAX 3 //numero domande
#define LEN 1024 //caratteri per riga: 1023+0 del messaggio
#define PORT  16000 //porta dove il server accetta le connessioni

#define semaforo "sem_mutex"

#define MACS 2


char domande[MAX][LEN]; //tabella caricata con domande e risposte
char risposte[MAX][2]; //tabella caricata con le risposte corrette

void *caricamento(void *arg); //funzione svolta dal thread1
char risp[2];
sem_t *mutex; 
int sd, i, j, k;
int punteggi[MAX][MACS], punteggio;
int tab[totpost][2];
struct sockaddr_in server_addr;    // struttura dati di configurazione

struct sockaddr_in client_addr;

socklen_t client_len;



int main(int argc, char *argv[])

{

  	system("clear"); //system chiama il comando UNIX "clear"
    	printf("Server avviato con pid = %d\n", getpid());

	int i;
//THREAD
	int res, pid;
	pthread_t thread1; //primo thread per il caricamento
	void *thread_result;
	res=pthread_create(&thread1, NULL, caricamento,NULL);
	if (res!=0) 
	{	perror("\n****ERRORE CREAZIONE THREAD***\n");
		exit(1);
	}
	res=pthread_join(thread1, &thread_result); //come la wait
	printf("thread1 terminato con stato: %d\n", (int*)thread_result);
//FINE THREAD


//inizializzo il vettore punteggi
for(j=0;j<2;j++)	
	for(i=0;i<totpost;i++)
	{
		punteggi[i][j]=0;
		punteggi[i][j]=0;
	}
//fine

	
//VISUALIZZAZIONE DOMANDE PER CONFERMA CARICAMENTO
	printf("\n\n******ELENCO DOMANDE******\n");
	for(k=0;k<MAX;k++)
		printf("Domanda numero %d:\t%s\nRisposta Corretta:\t%s\n\n",k+1,domande[k],risposte[k]);

//SOCKET	
 	 int client_sd[totpost];
// preparazione dei dati relativi al bind

  	server_addr.sin_family = AF_INET; //dominio

  	server_addr.sin_port = htons(PORT); //host to network

  	server_addr.sin_addr.s_addr = INADDR_ANY; //associa al server l'indirizzo della macchina

  	client_len = sizeof(struct sockaddr_in);

  	

//SOCKET
  	int sd=socket(AF_INET, SOCK_STREAM, 0);//restituisce l'identificativo del socket
	if(sd<0) 
		{	
 		perror("creazione socket errata!!\n");
		exit(-1);
	 	}
//BIND
  	printf("Effettuo la bind del socket con la porta ds\n", PORT);

  	if (bind(sd, (const struct sockaddr *) &server_addr, client_len) < 0)

    		{

      		perror("Durante il bind\n");

      		exit(1);

    		}

//LISTEN

  	printf("Mi metto in attesa di connessioni sulla porta %d\n", PORT);

  	if (listen(sd, 2) < 0)		

    		{

      		perror("Durante il listen");

      		exit(1);

    		}



  	printf("Entro nel ciclo for in cui accetto connessioni\n");


// itero il tutto cn un ciclo for ke crea un sd dedicato per ogni client accettato

	for(i=0;i<totpost;i++)
		{
//ACCEPT: accetta le commessioni che gli arrivano	
		
		client_sd[i] = accept(sd, (struct sockaddr *) &client_addr, &client_len);
		if (client_sd[i] < 0)
			{
			perror("Durante l'accept\n");
			exit(1);
			}
//FORK: creazione figli
                pid = fork();
	

		if (pid == 0) //FIGLIO
      			{
			printf("sono il servente: %d\n",getpid()); //figlio ke s collega con il client
	  		printf("Connessione con client accettata sul socket %d\n", client_sd[i]);

			break;
			}
		if(pid < 0) //ERRORE
			{
			printf("\n\n ERRORE FORK\n\n");
			exit(1);
			}
	        if(pid >0) //PADRE
			{ 
			sleep(2); //ASPETTA LA TERMINAZIONE DEI FIGLI ... MANCU PER METTERE NA WAIT
			}

//CARICAMENTO TABELLE CON IDENTIFICATIVI ... pero' ci son pobbbbbemi
		tab[i][0]=pid;
		tab[i][1]=client_sd[i];


		}



// crea/preleva un semaforo con valore iniziale a 1 (per noi un mutex)



	mutex = sem_open(semaforo, O_CREAT, 0777, 1);

	if (mutex == 0)

  	{

    	perror("sem_open");

    	exit(1);

 	}

  	else
	{
      	for(k=0;k<MAX;k++) //conta le domande da inviare
		{
		printf(" \nInvio la %d domanda ... ", k+1);
		for(i=0;i<totpost;i++)	
			{
			if(send(client_sd[i],domande[k],strlen(domande[k]),0)>0)
				{
				printf(" \n*********** DOMANDA %d inviata ************ ", k+1);	
				printf("\nAttendo una risposta dagli studenti per circa 10 secondi\n");
				sleep(10);
				//ricevo la prima risposta quindi semaforo rosso per tutti gli altri
				
				printf("\n");

				printf("Attendo l'acquisizione del mutex\n");

				if (sem_wait(mutex) < 0)

					{

					perror("Su sem_wait");

					exit(1);

					}

				printf("Mutex acquisito correttamente\n");

				printf("Effettuo tutte le operazioni\n");
				res=recv(client_sd[i], risp, 2, 0);
				if(res>0)
					{
					printf("\nRisposta ricevuta: \t %s\n",risp);
					sleep(3);
					printf("\n Effettuo il controllo di correttezza sulla risposta\n\n");
					if(strcmp(risposte[k],risp)==0)
						{
						printf("\nLa risposta corretta è stata data dallo studente con ID %d\n",client_sd[i]); 
						punteggi[i][j]=client_sd[i];
						punteggi[i][j+1]++;
						}
										
					}
				sleep(1);
				printf("Rilascio il mutex e dormo 1 secondo\n");

      				if (sem_post(mutex) < 0)

					{

	  				perror("Su sem_post");

	  				exit(1);

					}			
				}
			} 

		}	
	}

for(i=0;i<totpost;i++)
	printf("\nEcco i vari punteggi:\n\nID Studente:  %d\t Punteggio:  %d\n",client_sd[i],punteggi[i][j+1]);


close(sd);


	printf("\n");
	printf("\n\t\t ********************* ");
	printf("\n\t\t *                   * ");
	printf("\n\t\t *   TERMINATO!!!!!  * ");
	printf("\n\t\t *                   * ");
	printf("\n\t\t ********************* ");
	printf("\n\n");
	system("killall -q server");


}  //FINE MAIN


/*THREAD CONTROLLO MAX E MIN PUNTEGGI
void *punteggi(void *args)
{
  int i, j, temp;
 
  for (i = (array_size - 1); i >= 0; i--)
  {
    for (j = 1; j <= i; j++)
    {
      if (numbers[j-1] > numbers[j])
      {
        temp = numbers[j-1];
        numbers[j-1] = numbers[j];
        numbers[j] = temp;
      }
    }
  } da modificare ma è l'algoritmo bubble sort per ordinare in modo crescente o decrescente il vettore punteggio per decretare il "vincitore"
}*/








//THREAD CARICAMENTO DOMANDE

void *caricamento(void *args) 
{
char s[1024];
char r[2];

int k;
int risp;
printf("\n\n******** CARICAMENTO DOMANDE START ******** ");
for(k=0; k<MAX; k++)
{
		printf("\nInserisci la %d domanda e le 4 risposte\t \n", k+1);
		gets(s);
		if(strlen(s)==0)
		{
			printf("\nERRORE: STRINGA VUOTA!! REINSERIRE DATI NELLA DOMANDA");
			k--;
		}
		else if(strlen(s)>LEN)
		{
			printf("\nERRORE: STRINGA GRANDE!! REINSERIRE DATI NELLA DOMANDA");
			k--;
		}
	else
		strcpy(domande[k], s);

		printf("\nInserisci la %d risposta corretta\n", k+1);
		gets(r);
		if(strlen(r)==0)
		{
			printf("\nERRORE: STRINGA VUOTA NELLA RISPOSTA !! REINSERIRE DATI.");
			k--;
		}
		else if(strlen(r)>1)
		{
			printf("\nERRORE: troppi caratteri, inserire una sola lettera nella risposta");
			k--;
		}
	else
		strcpy(risposte[k], r);
	


}

sleep(3);
pthread_exit(EXIT_SUCCESS);
}

//FINE THREAD CARICAMENTO DOMANDE

CODICE CLIENT
Codice:
#include <sys/types.h>

#include <sys/socket.h>

#include <netinet/in.h>

#include <netdb.h>

#include <stdio.h>

#include <stdlib.h>

#include <string.h>

#include <sys/types.h>




#define LEN 1024

#define PORT  16000
#define MAX 3




int sd, res, ress, i, j;
char risp[2], punt[2];




struct sockaddr_in server_addr;

struct hostent *hostinfo;

socklen_t len;



int main(int argc, char *argv[])

{

  if (argc < 2)

    {

      printf("Utilizzo: ./%s <indirizzo>\nHai dimenticato di inserire l'indirizzo!!! \n", argv[0]);

      exit(1);

    }  
system("clear");


//SOCKET

  printf("Creo il socket\n");

  sd = socket(PF_INET, SOCK_STREAM, 0);

  if (sd < 0)

    {

      perror("Durante la creazione del socket\n");

      exit(1);

    }



  // prepara i dati per la connessione con il server

  server_addr.sin_family = AF_INET;

  server_addr.sin_port = htons(PORT);

  server_addr.sin_addr.s_addr = INADDR_ANY;



  hostinfo = gethostbyname(argv[1]);

    

  if (hostinfo == NULL)

    {

      printf("Non è stato possibile risolvere il nome del server\n");

      exit(1);

    }

  else

    server_addr.sin_addr = *((struct in_addr *) hostinfo->h_addr);



//CONNECT
  printf("Apro la connessione\n");

  if (connect(sd, (struct sockaddr *) &server_addr, sizeof(struct sockaddr_in)) < 0)

    {

      perror("Durante la connect");

      exit(1);

    }

//semaforo verde
printf(" ***************Ricevo la prima domanda e la visualizzo a schermo****************");
char buffer[MAX][LEN];
for(i=0;i<=MAX;i++)
{
	res=recv(sd, buffer[i], LEN+1,0);
	if(res>0)
		{
		printf("\nLa  domanda a cui devi rispondere è:  %s  \n Inserisci il carattere corrispondente alla tua risposta\n", buffer[i]);
		gets(risp);
		sleep(3);
		res=send(sd, risp, strlen(risp), 0);
		if (res>0)
			printf("\n La Risposta Inviata Correttamente è: \t %s\n",risp);
   	      }
}

exit(0);
}
ginter87 è offline   Rispondi citando il messaggio o parte di esso
 Rispondi


Google Pixel 10 è compatto e ha uno zoom 5x a 899€: basta per essere un best-buy? Google Pixel 10 è compatto e ha uno zoom ...
Prova GeForce NOW upgrade Blackwell: il cloud gaming cambia per sempre Prova GeForce NOW upgrade Blackwell: il cloud ga...
Ecovacs Deebot X11 Omnicyclone: niente più sacchetto per lo sporco Ecovacs Deebot X11 Omnicyclone: niente più...
Narwal Flow: con il mocio orizzontale lava i pavimenti al meglio Narwal Flow: con il mocio orizzontale lava i pav...
Panasonic 55Z95BEG cala gli assi: pannello Tandem e audio senza compromessi Panasonic 55Z95BEG cala gli assi: pannello Tande...
Iliad: si consolida la partnership tecno...
Il SoC a 2 nm di Samsung non sfigura nel...
Prezzo shock per i Galaxy Buds FE + nuov...
Il nuovo SoC di Qualcomm vuole stupire: ...
Offerta lampo per pulire l'auto: aspirap...
I robotaxi di Amazon entrano in azione: ...
ECOVACS DEEBOT T50 PRO OMNI Gen2 domina ...
iPhone 17 Pro su Amazon: tutti i colori,...
Disney Plus da 2,99 euro al mese per 3 m...
Nuovo test di accensione dei motori per ...
Novità dalle analisi dell'asteroi...
La PS6 sarà più potente del previsto: ec...
Sony svela Xperia 10 VII: è il nu...
Amazon Weekend da urlo: iPhone 16 a prez...
Spotify diffida ReVanced: chiesta la rim...
Chromium
GPU-Z
OCCT
LibreOffice Portable
Opera One Portable
Opera One 106
CCleaner Portable
CCleaner Standard
Cpu-Z
Driver NVIDIA GeForce 546.65 WHQL
SmartFTP
Trillian
Google Chrome Portable
Google Chrome 120
VirtualBox
Tutti gli articoli Tutte le news Tutti i download

Strumenti

Regole
Non Puoi aprire nuove discussioni
Non Puoi rispondere ai messaggi
Non Puoi allegare file
Non Puoi modificare i tuoi messaggi

Il codice vB è On
Le Faccine sono On
Il codice [IMG] è On
Il codice HTML è Off
Vai al Forum


Tutti gli orari sono GMT +1. Ora sono le: 21:05.


Powered by vBulletin® Version 3.6.4
Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
Served by www3v