コード例 #1
0
int main()
{

    string fileName = "";
    string input = "";

    cout << "Enter filename: \n> ";
    cin >> fileName;

    AccountNode* head = new AccountNode;
    head = loadAccountsFromFile(fileName);
    displayAccounts(head);

    cout << "Enter first name: \n> ";
    cin >> input;

    AccountNode* result = searchAccountListByFirstName(head, input); 

    cout << "Enter last name to find and remove: \n> ";
    cin >> input;

    result = searchAccountListByLastName(head, input); 
    if (result != NULL && deleteAccount(&head, result->account) == 0)
        cout << "Removal of \"" << result->account->firstName << " " << result->account->lastName << "\" was successful." << endl; 
    else
        cout << "Not found." << endl;
result = searchAccountListByLastName(head, "Almighty"); 
if (result != NULL && deleteAccount(&head, result->account) == 0)
        cout << "Removal of \"" << result->account->firstName << " " << result->account->lastName << "\" was successful." << endl; 
    else
        cout << "Not found." << endl;
result = searchAccountListByLastName(head, "Borden"); 
cout << result << endl;
    if (result != NULL && deleteAccount(&head, result->account) == 0)
        cout << "Removal of \"" << result->account->firstName << " " << result->account->lastName << "\" was successful." << endl; 
    else
        cout << "Not found." << endl;
    displayAccounts(head);

    // unless we delete the memory 
    // we're going to have a ton of memory leaks
    return 0;
}
コード例 #2
0
void authentificationThread()
{
	// initialisation de la structure sockaddr_in d'ecoute.

	AccountsList *list = loadAccountsFromFile(ACCOUNTS_FILE); // ajouter la détection de l'existence du fichier.
	if(list == NULL)
	{
		errorMessage("Accounts file is corrupted");
		return;
	}

	struct sockaddr_in server;
	initServerSocketAddress(&server);
	int listen_socket = createServerListenSocket(&server);


	ConnectionList connection_list;
	connection_list.nb_connections = 0;

	// initialisation de la fine d'attente des joueurs à charger sur la map et des joueurs déconnectés.
	PlayersQueue players_queues[2];
	initPlayersQueue(&players_queues[0]);
	initPlayersQueue(&players_queues[1]);

	PlayersQueue *new_players_queue = players_queues;
	PlayersQueue *disconnected_players_queue = &players_queues[1];

	// lancement du thread s'occupant de la gestion du déroulement du jeu.

#ifdef RUN_GAME_MANAGEMENT_THREAD
	runGameManagementThread(players_queues);
#endif
	int _continue, return_value;
	char *login, *password;
	Player *player;
	Connection * current_connection;
	int connection_index, account_index;
	GenericPacket packet;
	Buffer recv_buffer, send_buffer;
	initBuffer(&recv_buffer);
	initBuffer(&send_buffer);

	// utilise pour rendr le thread inactif pendant un certain temps.
	int no_activity = 0;
	struct timespec wait_time = {0, 150000}, sleep_return;

	long last_save_time = getTime();
	char save_needed = FALSE;

	while(1)
	{
		no_activity = TRUE;

		acceptNewConnections(listen_socket, &connection_list);
		/// il reste a traiter les packets éventuels de chaque connexion.
		for(connection_index = 0; connection_index < connection_list.nb_connections; connection_index++)
		{
			current_connection = & connection_list.connections[connection_index];
			_continue = TRUE;
			while(_continue)
			{
				return_value = recvPacket(current_connection, &packet, &recv_buffer);
				if(return_value == 1) // traitement du packet recu.
				{
					no_activity = FALSE;
					if(packet.type == AUTHENTIFICATION_REQUEST)
					{
						if(extractLoginAndPassword(&packet, &recv_buffer, &login, &password) < 0) // si la forme des donnees du paquet est incorrecte, on rejette la demande d'authentification.
							sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION);
						else if(!isCorrectLoginOrPassword(login)) // si le login est syntaxiquement incorrecte, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : login \"%s\" is syntactically false", login);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else if(!isCorrectLoginOrPassword(password)) // si le mot de passe est syntaxiquement incorrecte, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : password \"%s\" is syntactically false", password);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else if((account_index = getAccountPosition(list, login)) < 0) // Si le login ne correspond à aucun compte, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : none account matching with login \"%s\".", login);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else if(list->accounts[account_index].opened) // Si le compte correspondant au login est deja ouvert, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : account \"%s\" is already opened.", login);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else if(list->accounts[account_index].opened) // Si le compte correspondant est deja utilise, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : account \"%s\" is already opened.", password, login);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else if(strcmp(password, list->accounts[account_index].password)) // Si le compte correspondant au login a un mot de passe different de celui recu, on rejette la demande d'authentification.
						{
							debugMessage("Authentication has failed : password \"%s\" is incorrect for account \"%s\".", password, login);
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
							{
								warningMessage("Current connection is lost.");
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
							}
						}
						else // l'authentification a reussi, on supprime donc la connection du service de comptes.
						{
							if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, ACCEPT_AUTHENTIFICATION)) == -2)
								warningMessage("Current connection is lost.");

							if(addPlayerToQueue(new_players_queue, (player = createPlayerForAccount(& list->accounts[account_index], current_connection))) < 0) // Si la file d'attente des noueaux joueurs en attente de chargement sur la map est pleine, on rejette la demande d'authentification.
							{
								destroyPlayer(player);
								debugMessage("Authentication has failed : new players queue is full.");
								if((return_value = sendAuthentificationAnswer(current_connection, &send_buffer, REJECT_AUTHENTIFICATION)) == -2)
								{
									warningMessage("Current connection is lost.");
									removeConnectionFromList(& connection_list, connection_index);
									connection_index--;
									_continue = FALSE;
								}
							}
							else
							{
								removeConnectionFromList(& connection_list, connection_index);
								connection_index--;
								_continue = FALSE;
								list->accounts[account_index].opened = TRUE;
								debugMessage("player %s is authenticated", login);
							}
						}
					}
					else // le type du paquet ne concerne pas le service de comptes, donc on l'ignore.
						warningMessage("packet received is not for account management : type is %d", packet.type);
				}
				else if(return_value == 0) // aucun nouveau paquet recu, donc on traite l'eventuelle connexion suivante.
					_continue = FALSE;
				else if(return_value == -1)
					_continue = FALSE;
				else // la connexion est perdue, donc on la supprime de la liste des connexions et on traite l'eventuelle connexion suivante.
				{
					no_activity = FALSE;
					removeConnectionFromList(& connection_list, connection_index);
					connection_index--;
					_continue = FALSE;
				}
			}
		}

		// on traite l'ensemble des joueurs deconnectes.
		while((player = removePlayerFromQueue(disconnected_players_queue)) != NULL)
		{
			no_activity = FALSE;

			account_index = getAccountPosition(list, player->login); // on recupere l'indice du compte associe au joueur 'player'
			if(account_index >= 0) // si le compte est retrouve, on le met a jour.
			{
				list->accounts[account_index].opened = FALSE;
				list->accounts[account_index].pos_x = player->position.x;
				list->accounts[account_index].pos_y = player->position.y;
				save_needed = TRUE;
			}
			destroyPlayer(player);
		}

		if(save_needed && getTime() - last_save_time > 30000000) // sauvegarde des comptes toutes les 30 secondes.
		{
			saveAccountsFile(ACCOUNTS_FILE, list);
			save_needed = FALSE;
			last_save_time = getTime();
		}

		// si aucune activite (reception de paquet ou demande de connexion) n'a eu lieu, alors on rend le thread inactif pendant un certain temps afin de limiter la consommation des ressouces processeur.
		if(no_activity == TRUE)
			nanosleep(&wait_time, &sleep_return);
	}
}