From f1e1122091976f88b1ec3b85d28aac6eae337dde Mon Sep 17 00:00:00 2001 From: Julien Graeffly Date: Fri, 29 May 2009 15:02:20 +0000 Subject: [PATCH] =?UTF-8?q?Reconstitution=20du=20d=C3=A9p=C3=B4t,=20=C3=A9?= =?UTF-8?q?tape=205=20(et=20derni=C3=A8re)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Le commentaire de révision initial figure ci-dessous. Les différences par rapport à ce commit sont : - Dans code/infrastructure-centred/owlps-client/ : importation des modifs de Julien dans la dernière version du client (Julien avait utilisé comme base une ancienne version). - Dans code/infrastructure-centred/owlps-listener/ : idem. - Dans code/owlps-positioning/ : ° Suppression de client (déplacé dans les archives). ° Makefile : ajout d'une pseudo-cible .PHONY. - code/writeInDb/ : ° Le binaire n'est pas versionné. ° Application de astyle --style=gnu. | r93 | jgraeffly | 2009-05-27 14:51:40 +0200 (mer 27 mai 2009) | 23 lines | Chemins modifiés : | R /code/infrastructure-centred/owlps-aggregator/owlps-aggregator.h | R /code/infrastructure-centred/owlps-aggregator/owlps-aggregatord.c | R /code/infrastructure-centred/owlps-client/owlps-client.c | R /code/infrastructure-centred/owlps-listener/owlps-listener.h | R /code/infrastructure-centred/owlps-listener/owlps-listenerd.c | R /code/libowlps/owlps.h | R /code/owlps-positioning/Makefile | D /code/owlps-positioning/client | A /code/owlps-positioning/libowlps-positioning.cc | A /code/owlps-positioning/libowlps-positioning.hh | R /code/owlps-positioning/owlps-positioning.cc | A /code/owlps-positioning/owlps-positioning.cfg | R /code/owlps-positioning/owlps-positioning.hh | R /code/owlps-positioning/positioning.cc | R /code/owlps-positioning/positioning.hh | R /code/owlps-positioning/server.cc | R /code/owlps-positioning/server.hh | R /code/owlps-positioning/treatment.cc | R /code/owlps-positioning/treatment.hh | A /code/writeInDb | A /code/writeInDb/writeindb | A /code/writeInDb/writeindb.cc | A /code/writeInDb/writeindb.hh | | - Mise à jour du positioner : | Prise en charge de la BdD pour utilisation ainsi que pour la | sauvegarde des résultats | Envoi du résultat au client | Prise en compte du fichier de configuration ainsi que des | lignes de commande avec la library boost | | - Mise à jour de l'aggregator : | Pris en compte de la BdD pour la sauvegarde des requetes de | calibration ou de localisation | Envoi des demandes de localisation uniquement vers le | positioner | Ajout des options utilisables en ligne de commande et dans le | fichier de conf | | - Mise à jour du listener : | Ajout de l'envoi de l'adresse IP du mobile | | - Mise à jour du mobile : | Ajout de la socket de récupération de la réponse du serveur la | réponse est sous forme de 3 float (x, y, z) et non d'un Point. | | - Mise à jour de owlps.h : | Ajout des ports par défaut du positioner ainsi que du mobile. | | - Ajout de writeInDb : | Programme permettant de mettre les données contenu dans un | fichier dans la BdD git-svn-id: https://pif.pu-pm.univ-fcomte.fr/svn/loc@94 785a6c6c-259e-4ff1-8b91-dc31627914f0 --- .../owlps-aggregator/owlps-aggregator.h | 16 +- .../owlps-aggregator/owlps-aggregatord.c | 290 ++++++++- .../owlps-client/owlps-client.c | 11 + .../owlps-listener/owlps-listenerd.c | 1 + libowlps/owlps.h | 15 +- owlps-positioning/Makefile | 18 +- owlps-positioning/client/Client.cc | 443 ------------- owlps-positioning/libowlps-positioning.cc | 99 +++ owlps-positioning/libowlps-positioning.hh | 57 ++ owlps-positioning/owlps-positioning.cc | 58 +- owlps-positioning/owlps-positioning.cfg | 9 + owlps-positioning/owlps-positioning.hh | 3 + owlps-positioning/positioning.cc | 273 +++++--- owlps-positioning/positioning.hh | 29 +- owlps-positioning/server.cc | 243 ++++--- owlps-positioning/server.hh | 49 +- owlps-positioning/treatment.cc | 47 +- owlps-positioning/treatment.hh | 33 +- writeInDb/writeindb.cc | 593 ++++++++++++++++++ writeInDb/writeindb.hh | 54 ++ 20 files changed, 1617 insertions(+), 724 deletions(-) delete mode 100644 owlps-positioning/client/Client.cc create mode 100644 owlps-positioning/libowlps-positioning.cc create mode 100644 owlps-positioning/libowlps-positioning.hh create mode 100644 owlps-positioning/owlps-positioning.cfg create mode 100644 writeInDb/writeindb.cc create mode 100644 writeInDb/writeindb.hh diff --git a/infrastructure-centred/owlps-aggregator/owlps-aggregator.h b/infrastructure-centred/owlps-aggregator/owlps-aggregator.h index dd9df47..78c53fd 100644 --- a/infrastructure-centred/owlps-aggregator/owlps-aggregator.h +++ b/infrastructure-centred/owlps-aggregator/owlps-aggregator.h @@ -5,7 +5,7 @@ #ifndef _RTAPAGGREGATE_H #define _RTAPAGGREGATE_H - +#include #include "../../libowlps/owlps.h" #include @@ -14,12 +14,15 @@ /* Arguments & configuration du programme */ -#define OPTIONS "f:l:o:a:k:c:" // Chaîne pour getopt +#define OPTIONS "f:l:o:a:k:c:i:u:n:p:h:" // Chaîne pour getopt #define DEFAULT_CONFIG_FILE "/usr/local/etc/owlps/owlps-aggregator.conf" #define DEFAULT_AGGREGATE_TIMEOUT 1500 // Timeout d'agrégation (en millisecondes) #define DEFAULT_KEEP_TIMEOUT 3000 // Temps que l'on conserve les données dans la liste (en millisecondes) #define DEFAULT_CHECK_INTERVAL 500000 // Temps entre deux vérifications de la liste (en micro-secondes) - +#define DEFAULT_HOST_DB "127.0.0.1" +#define DEFAULT_DB_NAME "owlps_db" +#define DEFAULT_USER_DB "julien" +#define DEFAULT_PASS_DB "10,mamci" /* Codes d'erreur */ #define ERR_NO_MESSAGE_RECEIVED 1 // Erreur lors de la lecture sur la socket @@ -63,7 +66,12 @@ void free_couple_list(couple_list **couples) ; void print_couple_list(couple_list *couples) ; void print_couple_info(couple_info_list *info) ; void* monitor_couple_list(couple_list **couples) ; +int Db_write_request(couple_message message, BOOL ref) ; +int DbAccessPoint(couple_message message, PGconn *conn); +int DbMobile(couple_message message, PGconn *conn); +int DbRefPoint(couple_message message, PGconn *conn); +int DbRequest(couple_message message, PGconn *conn, int id_mobile, int *id_point, BOOL ref); +int DbPacket(couple_message message, PGconn *conn, int id_ap, int id_request, BOOL ref); void print_usage(char *prog) ; - #endif diff --git a/infrastructure-centred/owlps-aggregator/owlps-aggregatord.c b/infrastructure-centred/owlps-aggregator/owlps-aggregatord.c index c658168..381f600 100644 --- a/infrastructure-centred/owlps-aggregator/owlps-aggregatord.c +++ b/infrastructure-centred/owlps-aggregator/owlps-aggregatord.c @@ -10,6 +10,25 @@ cfg_t *cfg ; // Structure contenant la configuration +char* ip_bytes_to_string(unsigned char *ip_binary) +{ + int taille = 16, i = 0; + for(i = 0; i < 4; i++) + { + if(ip_binary[i] < 0x64) + taille--; + if(ip_binary[i] < 0x10) + taille--; + } + + char *ret = malloc(sizeof(char) * taille) ; + + + sprintf(ret, "%d.%d.%d.%d", ip_binary[0], ip_binary[1], ip_binary[2], ip_binary[3]) ; + ret[taille-1] = '\0' ; + + return ret ; +} int main(int argc, char **argv) { @@ -23,13 +42,21 @@ int main(int argc, char **argv) couple_message message ; // Message lu sur la socket pthread_t thread ; // Thread pour la fonction de surveillance de la liste d'informations agrégées char *ap_mac_string, *mobile_mac_string ; // Pointeurs pour retour de mac_bytes_to_string() + char *mobile_ip_string ; + BOOL ref; cfg_opt_t opts[] = { // Options reconnues par confuse dans le fichier de config CFG_INT("listening_port", AGGREGATE_DEFAULT_PORT, CFGF_NONE), // Port d'écoute + CFG_INT("send_port", POSITIONER_DEFAULT_PORT, CFGF_NONE), // Port de sortie + CFG_STR("ip_positioner", "", CFGF_NONE), // Adresse IP du serveur de géolocalisation CFG_STR("output_file", "", CFGF_NONE), // Fichier de sortie CFG_INT("aggregate_timeout", DEFAULT_AGGREGATE_TIMEOUT, CFGF_NONE), // Timeout d'agrégation (en millisecondes) CFG_INT("keep_timeout", DEFAULT_KEEP_TIMEOUT, CFGF_NONE), // Temps que l'on conserve les données dans la liste (en millisecondes) CFG_INT("check_interval", DEFAULT_CHECK_INTERVAL, CFGF_NONE), // Temps entre deux vérifications de la liste (en micro-secondes) + CFG_STR("host_db", DEFAULT_HOST_DB, CFGF_NONE), + CFG_STR("db_name", DEFAULT_DB_NAME, CFGF_NONE), + CFG_STR("user_db", DEFAULT_USER_DB, CFGF_NONE), + CFG_STR("pass_db", DEFAULT_PASS_DB, CFGF_NONE), CFG_END() } ; char *config_file ; // Nom du fichier de configuration int opt ; // Retour de getopt @@ -84,6 +111,21 @@ int main(int argc, char **argv) case 'c' : cfg_setint(cfg, "check_interval", strtol(optarg, NULL, 0)) ; break ; + case 'i' : + cfg_setstr(cfg, "ip_positioner", optarg) ; + break ; + case 'u' : + cfg_setstr(cfg, "user_db", optarg) ; + break ; + case 'n' : + cfg_setstr(cfg, "db_name", optarg) ; + break ; + case 'p' : + cfg_setstr(cfg, "pass_db", optarg) ; + break ; + case 'h' : + cfg_setstr(cfg, "host_db", optarg) ; + break ; default : print_usage(argv[0]) ; return ERR_BAD_USAGE ; @@ -98,6 +140,13 @@ int main(int argc, char **argv) print_usage(argv[0]) ; return ERR_BAD_USAGE ; } + // ip_positioner // + if (cfg_getstr(cfg, "ip_positioner")[0] == '\0') + { + fprintf(stderr, "Erreur ! Vous devez spécifier l'adresse IP du serveur de géolocalisation.\n") ; + print_usage(argv[0]) ; + return ERR_BAD_USAGE ; + } // aggregate_timeout // if (cfg_getint(cfg, "aggregate_timeout") < 0) { @@ -164,10 +213,12 @@ int main(int argc, char **argv) } ap_mac_string = mac_bytes_to_string(message.ap_mac_addr_bytes) ; mobile_mac_string = mac_bytes_to_string(message.mobile_mac_addr_bytes) ; + mobile_ip_string = ip_bytes_to_string(message.mobile_ip_addr_bytes) ; printf("\n\ *** Message reçu du client ***\n\ \tMAC AP : %s\n\ \tMAC mobile : %s\n\ +\tIP mobile : %s\n\ \tNuméro de séquence (heure de la demande) : %llu\n\ \tHeure d'arrivée de la demande de localisation sur l'AP : %llu\n\ \tSignal : %d dBm\n\ @@ -178,6 +229,7 @@ int main(int argc, char **argv) ", ap_mac_string, mobile_mac_string, + mobile_ip_string, timeval_to_ms(message.request_time), timeval_to_ms(message.start_time), message.antenna_signal_dbm - 0x100, @@ -188,8 +240,12 @@ int main(int argc, char **argv) ) ; free(ap_mac_string) ; free(mobile_mac_string) ; + free(mobile_ip_string) ; + + ref = (message.x_position != 0 && message.y_position != 0 && message.z_position != 0)? TRUE : FALSE; - got_couple_info(&couples, message) ; + Db_write_request(message, ref); + if(!ref) got_couple_info(&couples, message) ; } (void) close(sockfd) ; // Fermeture de la socket @@ -212,6 +268,15 @@ void* monitor_couple_list(couple_list **couples) FILE *fd = NULL ; char *ap_mac_string ; unsigned long sub ; // Résultat de sub_date(). + + struct sockaddr_in serv; + struct sockaddr_in client ; + socklen_t serv_len = sizeof(serv); + request demande; + couple_info info; + int sockfd,i; + + sockfd = create_udp_sending_socket(cfg_getstr(cfg, "ip_positioner"), cfg_getint(cfg, "send_port"), &serv, &client); fd = fopen(cfg_getstr(cfg, "output_file"), "a") ; // Ouverture du fichier de sortie en ajout if (fd == NULL) // Si ouverture échouée, @@ -248,10 +313,29 @@ void* monitor_couple_list(couple_list **couples) #endif // TIMESTAMP fprintf(fd, "%0.2f;%0.2f;%0.2f;%hhd", couple_ptr->x_position, couple_ptr->y_position, couple_ptr->z_position, couple_ptr->direction) ; // Inscription des infos du couple dans le fichier + memcpy(demande.mobile_mac_addr_bytes, couple_ptr -> mobile_mac_addr_bytes, 6); + demande.request_time = couple_ptr->request_time; + demande.nb_couples = 0 ; + couple_info_ptr = couple_ptr->info ; - while (couple_info_ptr != NULL) // On vide la liste des infos + while (couple_info_ptr != NULL) { - // Inscription des infos de l'AP dans le fichier + demande.nb_couples++; + couple_info_ptr = couple_info_ptr->next ; + } + sendto(sockfd, (void *)&demande, sizeof(request), 0, (struct sockaddr *)&serv, serv_len) ; + + + couple_info_ptr = couple_ptr->info ; + while (couple_info_ptr != NULL) // On envoi les couples au serveur et on vide la liste + { + // Envoi des infos de l'AP vers le serveur de géolocalisation + memcpy(info.ap_mac_addr_bytes, couple_info_ptr->ap_mac_addr_bytes, 6); + info.antenna_signal_dbm = couple_info_ptr->antenna_signal_dbm - 0x100; + for(i = 0; i < demande.nb_couples; i++) + sendto(sockfd, (void *)&info, sizeof(couple_info), 0, (struct sockaddr *)&serv, serv_len); + + // Inscription des infos de l'AP dans le fichier ap_mac_string = mac_bytes_to_string(couple_info_ptr->ap_mac_addr_bytes) ; fprintf(fd, ";%s;%d", ap_mac_string, couple_info_ptr->antenna_signal_dbm - 0x100) ; free(ap_mac_string) ; @@ -470,10 +554,208 @@ void print_couple_info(couple_info_list *info) +int Db_write_request(couple_message message, BOOL ref) +{ + char *buf = (char *) malloc(100 * sizeof(char)); + sprintf(buf, "hostaddr = '%s' dbname = '%s' user = '%s' password = '%s'", cfg_getstr(cfg, "host_db"), cfg_getstr(cfg, "db_name"), cfg_getstr(cfg, "user_db"), cfg_getstr(cfg, "pass_db")); + + const char* conninfo = buf; + PGconn *conn; + + int id_ap, id_mobile, id_request, id_point = -1; + + conn = PQconnectdb(conninfo); + + if(PQstatus(conn) != CONNECTION_OK){ + printf("Connection à la base de donnée échouée : %s\n", PQerrorMessage(conn)); + PQfinish(conn); + return 1; + } + + if((id_ap = DbAccessPoint(message, conn)) < 0) return 1; + if((id_mobile = DbMobile(message, conn)) < 0) return 1; + if((id_request = DbRequest(message, conn, id_mobile, &id_point, ref)) < 0) return 1; + DbPacket(message, conn, id_ap, id_request, ref); + + PQfinish(conn); + return 0; +} + + + +int DbAccessPoint(couple_message message, PGconn *conn) +{ + char *buf = (char *) malloc(200 * sizeof(char)); + char *ap_mac_string; + int id_ap; + + PGresult *res; + + /** Recherche de l'AP conserné **/ + ap_mac_string = mac_bytes_to_string(message.ap_mac_addr_bytes) ; + + sprintf(buf, "SELECT id_ap, ap_addr FROM ap WHERE ap_addr = '%s';", ap_mac_string); + + res = PQexec(conn, buf); + if(PQresultStatus(res) != PGRES_TUPLES_OK){ + printf("Commande incorrect : %s\n", PQerrorMessage(conn)); + return -1; + }else{ + id_ap = atoi(PQgetvalue(res, 0, 0)); + } + PQclear(res); + free(buf); + + return id_ap; +} + + + +int DbMobile(couple_message message, PGconn *conn) +{ + char *mobile_mac_string, *mobile_ip_string; + char *buf = (char *) malloc(200 * sizeof(char)); + int id_mobile; + + PGresult *res; + + /** Recherche du mobile conserné **/ + mobile_mac_string = mac_bytes_to_string(message.mobile_mac_addr_bytes); + mobile_ip_string = ip_bytes_to_string(message.mobile_ip_addr_bytes); + + sprintf(buf, "SELECT * FROM mobile WHERE mobile_addr = '%s';", mobile_mac_string); + + res = PQexec(conn, buf); + if(PQresultStatus(res) != PGRES_TUPLES_OK){ + printf("Commande incorrect : %s\n", PQerrorMessage(conn)); + return -1; + }else if(PQntuples(res) == 0){ + PQclear(res); + sprintf(buf, "SELECT * FROM mobile;"); + res = PQexec(conn, buf); + id_mobile = (PQntuples(res) != 0)? atoi(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1 : 1; + + sprintf(buf, "INSERT INTO mobile(id_mobile, mobile_addr, ip_mobile, last_connect) VALUES('%d','%s','%s','%lld');",id_mobile, mobile_mac_string, mobile_ip_string, timeval_to_ms(message.request_time)); + + PQexec(conn, buf); + }else{ + id_mobile = atoi(PQgetvalue(res, 0, 0)); + + sprintf(buf, "UPDATE mobile SET last_connect = %lld, ip_mobile = '%s' WHERE id_mobile = %d;", timeval_to_ms(message.request_time), mobile_ip_string, id_mobile); + + PQexec(conn, buf); + } + PQclear(res); + free(buf); + + return id_mobile; +} + + + +int DbRefPoint(couple_message message, PGconn *conn) +{ + char *buf = (char *) malloc(200 * sizeof(char)); + int id_ref_point; + char d = ' '; + + PGresult *res; + + switch(message.direction){ + case 1: + d = 'N'; + break; + case 2: + d = 'E'; + break; + case 3: + d = 'S'; + break; + case 4: + d = 'W'; + break; + default : + d = ' '; + printf("Erreur : direction inconnue\n"); + } + + strcpy(buf, "SELECT * FROM ref_point;"); + res = PQexec(conn, buf); + id_ref_point = (PQntuples(res) != 0)? atoi(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1: 1; + + sprintf(buf, "INSERT INTO ref_point(id_ref_point, x, y, z, direction) VALUES('%d','%f','%f','%f','%c');", id_ref_point, message.x_position, message.y_position, message.z_position, d); + + PQexec(conn, buf); + + return id_ref_point; +} + + + +int DbRequest(couple_message message, PGconn *conn, int id_mobile, int *id_point, BOOL ref) +{ + char *buf = (char *) malloc(200 * sizeof(char)); + int id_request; + + PGresult *res; + + /** Ajout de la requete si elle n'existe pas **/ + if(ref) sprintf(buf, "SELECT * FROM ref_request WHERE mobile_time = %lld AND id_mobile = %d;", timeval_to_ms(message.request_time), id_mobile); + else sprintf(buf, "SELECT * FROM request WHERE mobile_time = %lld AND id_mobile = %d;", timeval_to_ms(message.request_time), id_mobile); + + res = PQexec(conn, buf); + if(PQresultStatus(res) != PGRES_TUPLES_OK){ + printf("Commande incorrect : %s\n", PQerrorMessage(conn)); + return -1; + }else if(PQntuples(res) == 0){ + PQclear(res); + if(ref) sprintf(buf, "SELECT * FROM ref_request;"); + else sprintf(buf, "SELECT * FROM request;"); + res = PQexec(conn, buf); + id_request = (PQntuples(res) != 0)? atoi(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1: 1; + if(ref){ + if((*id_point = DbRefPoint(message, conn)) < 0) return -1; + sprintf(buf, "INSERT INTO ref_request(id_ref_request, mobile_time, id_mobile, id_ref_point) VALUES('%d','%lld','%d','%d');", id_request, timeval_to_ms(message.request_time), id_mobile, *id_point); + }else sprintf(buf, "INSERT INTO request(id_request, mobile_time, id_mobile) VALUES('%d','%lld','%d');", id_request, timeval_to_ms(message.request_time), id_mobile); + + PQexec(conn, buf); + }else{ + id_request = atoi(PQgetvalue(res, 0, 0)); + if(ref) *id_point = atoi(PQgetvalue(res, 0, 3)); + } + PQclear(res); + free(buf); + + return id_request; +} + + + +int DbPacket(couple_message message, PGconn *conn, int id_ap, int id_request, BOOL ref) +{ + char *buf = (char *) malloc(200 * sizeof(char)); + + /** Ajout du paquet **/ + if(ref) sprintf(buf, "INSERT INTO ref_packet(ap_time, power, id_ap, id_ref_request) VALUES('%lld','%d','%d','%d');", timeval_to_ms(message.start_time), message.antenna_signal_dbm - 0x100, id_ap, id_request); + else sprintf(buf, "INSERT INTO packet(ap_time, power, id_ap, id_request) VALUES('%lld','%d','%d','%d');", timeval_to_ms(message.start_time), message.antenna_signal_dbm - 0x100, id_ap, id_request); + + PQexec(conn, buf); + free(buf); + + return 0; +} + + + /* Affiche le mode d'emploi du programme */ void print_usage(char *prog) { printf("Usage :\n\ -\t%s [-f config_file] [-l listening_port] [-a aggregate_timeout] [-k keep_timeout] [-c check_interval] -o output_file\n\ +\t%s [-f config_file] [-l listening_port] [-a aggregate_timeout] [-k keep_timeout] [-c check_interval] -o output_file -i ip_positionner\n\ +\tOptions BdD: \n\ +\t -h hostaddr\t: Adresse de l'host de la BdD \n\ +\t -n name_db\t: Nom de la BdD \n\ +\t -u user\t: Nom d'utilisateur pour l'acces à la BdD \n\ +\t -p passwd\t: Mot de passe pour l'acces à la BdD \n\ ", prog) ; } diff --git a/infrastructure-centred/owlps-client/owlps-client.c b/infrastructure-centred/owlps-client/owlps-client.c index 90f1b01..941a2f9 100644 --- a/infrastructure-centred/owlps-client/owlps-client.c +++ b/infrastructure-centred/owlps-client/owlps-client.c @@ -65,6 +65,9 @@ int main(int argc, char *argv[]) } options = {"", "", -1, -1, 0, 0, 0, 0} ; int opt ; // Retour de getopt + float x,y,z; // Position reçue en réponse du serveur + + // int delay = (argc == ARGC_NORMAL ? DELAY_NORMAL : DELAY_CALIB) ; /* Parcours des arguments de la ligne de commandes */ @@ -253,5 +256,13 @@ int main(int argc, char *argv[]) (void) close(sockfd) ; + /* Attente de la position du serveur */ + sockfd = create_udp_listening_socket(MOBILE_DEFAULT_PORT); + recvfrom(sockfd, &x, sizeof(float), 0, NULL, NULL); + recvfrom(sockfd, &y, sizeof(float), 0, NULL, NULL); + recvfrom(sockfd, &z, sizeof(float), 0, NULL, NULL); + (void) close(sockfd) ; + printf("Position reçue : (%.4f;%.4f;%.4f)\n", x, y, z); + return 0 ; } diff --git a/infrastructure-centred/owlps-listener/owlps-listenerd.c b/infrastructure-centred/owlps-listener/owlps-listenerd.c index ba133a6..488ec6e 100644 --- a/infrastructure-centred/owlps-listener/owlps-listenerd.c +++ b/infrastructure-centred/owlps-listener/owlps-listenerd.c @@ -231,6 +231,7 @@ void read_packet(u_char *args, const struct pcap_pkthdr *header, const u_char *p { memcpy(couple.ap_mac_addr_bytes, mac, 6); // On copie la MAC de l'AP memcpy(couple.mobile_mac_addr_bytes, &data[rtap_bytes+10], 6); // L'adresse MAC source est 10 octets plus loin que le type de paquet + memcpy(couple.mobile_ip_addr_bytes, &data[rtap_bytes + IEEE80211_HEADER_SIZE + LLC_HEADER_SIZE + 12], 4); // L'adresse IP source est à la position 12 de l'en-tête IP gettimeofday(&couple.start_time, NULL) ; packet_type = data[rtap_bytes + IEEE80211_HEADER_SIZE + LLC_HEADER_SIZE + IP_HEADER_SIZE + UDP_HEADER_SIZE] ; diff --git a/libowlps/owlps.h b/libowlps/owlps.h index 309964f..e6be92d 100644 --- a/libowlps/owlps.h +++ b/libowlps/owlps.h @@ -38,7 +38,8 @@ #define LOC_REQUEST_DEFAULT_PORT 9900 // Port sur lequel est envoyée la requête de localisation depuis le mobile #define AGGREGATE_DEFAULT_PORT 9901 // Port d'échange des données entre AP et serveur d'aggrégation - +#define POSITIONER_DEFAULT_PORT 9902 // Port d'échange des données entre server d'aggrégation et serveur de localisation +#define MOBILE_DEFAULT_PORT 9903 // Port d'envoi de la solution vers le mobile /* Type booléen */ typedef enum {FALSE, TRUE} BOOL ; @@ -53,6 +54,7 @@ typedef struct _couple_message { unsigned char ap_mac_addr_bytes[6] ; // Adresse MAC de l'AP émetteur de l'info en octets unsigned char mobile_mac_addr_bytes[6] ; // Adresse MAC du mobile en octets + unsigned char mobile_ip_addr_bytes[4] ; // Adresse IP du mobile en octets struct timeval request_time ; // Identifiant du paquet = date sur le client struct timeval start_time ; // Heure d'arrivée du paquet sur l'AP unsigned char antenna_signal_dbm ; // Puissance du signal reçu par l'AP du mobile @@ -63,6 +65,17 @@ typedef struct _couple_message DIRECTION direction ; // Orientation de la demande de localisation } couple_message ; +typedef struct _couple_info +{ + unsigned char ap_mac_addr_bytes[6] ; // Adresse MAC de l'AP + unsigned char antenna_signal_dbm ; // Puissance du signal reçu par l'AP +} couple_info ; + +typedef struct _request{ + unsigned char mobile_mac_addr_bytes[6]; //Adresse MAC du mobile + struct timeval request_time; // Date sur le client + int nb_couples; // Nombre couples (MAC AP;Puissance) +} request; /* Types de demandes de localisation */ #define PACKET_TYPE_NORMAL 0 diff --git a/owlps-positioning/Makefile b/owlps-positioning/Makefile index bfd921f..76de63a 100644 --- a/owlps-positioning/Makefile +++ b/owlps-positioning/Makefile @@ -1,38 +1,40 @@ +.PHONY : all clean purge install uninstall astyle + GXX = g++ DEBUG = -g GXXFLAGS = $(DEBUG) -Wall -pedantic LD = g++ LDFLAGS = -lm +LIBS = -lpq -lboost_program_options TARGET = owlps-positioning HEADER = owlps-positioning.hh all : ${TARGET} - @rm -f *~ *.o - % : %.o - $(LD) $(LDFLAGS) -o $@ $^ + $(LD) $(LDFLAGS) -o $@ $^ $(LIBS) %.o : %.cc $(HEADER) $(GXX) $(GXXFLAGS) -c $< -positioning.o : point.hh referencepoint.hh accesspoint.hh area.hh -server.o : server.hh positioning.hh point.hh measurement.hh treatment.hh +libowlps-positioning.o : libowlps-positioning.hh +positioning.o : point.hh referencepoint.hh accesspoint.hh area.hh measurement.hh libowlps-positioning.hh +server.o : server.hh positioning.hh point.hh measurement.hh treatment.hh libowlps-positioning.hh referencepoint.o : referencepoint.hh measurement.hh point.hh accesspoint.o : accesspoint.hh point.hh point.o : point.hh measurement.o : measurement.hh area.o : area.hh point.hh -treatment.o : treatment.hh point.hh measurement.hh referencepoint.hh accesspoint.hh +treatment.o : treatment.hh point.hh measurement.hh referencepoint.hh accesspoint.hh libowlps-positioning.hh owlps-positioning.o : server.hh -${TARGET} : point.o measurement.o accesspoint.o referencepoint.o positioning.o server.o area.o treatment.o +${TARGET} : point.o measurement.o accesspoint.o referencepoint.o positioning.o server.o area.o treatment.o libowlps-positioning.o owlps-positioning.o clean: @rm -fv *~ *.o *.orig purge : clean - @rm -fv owlps-positioningd + @rm -f $(TARGET) install : @echo "La cible d'installation de ${TARGET} sera implémentée prochainement. Vous devez lancer le programme 'guinumo' depuis le répertoire des sources." diff --git a/owlps-positioning/client/Client.cc b/owlps-positioning/client/Client.cc deleted file mode 100644 index 693bdef..0000000 --- a/owlps-positioning/client/Client.cc +++ /dev/null @@ -1,443 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include -#include - -#include -#include - -using namespace std; - -typedef struct _couple_info{ - unsigned char ap_mac_addr_bytes[6]; // Adresse MAC de l'AP - int antenna_signal_dbm; // Puissance du signal reçu par l'AP -} couple_info; - -typedef struct _demande{ - unsigned char ag_mac_addr_bytes[6]; // Adresse MAC de l'Aggregateur émetteur de la demande - int nb_couples; // Nombre couples (MAC AP;Puissance) -} demande; - -char* mac_bytes_to_string(unsigned char *mac_binary) ; -int create_udp_sending_socket(char *server_address, int server_port, struct sockaddr_in *server_description, struct sockaddr_in * client_description) ; -void get_mac_addr(char *eth, unsigned char mac_bytes[6]); -int split(string buffer, vector &envoi_info); -unsigned char convertuchar(char *caractere, int); - -int main(int argc, char **argv){ - - int sockfd, n = 0; - struct sockaddr_in serv; - struct sockaddr_in client; - unsigned char mac[6]; - ifstream fichier(argv[3]); - string cppbuffer; - - vector envoi_info; - demande envoi_demande; - - - if (argc != 4){ - cerr << "usage: Client IPaddress interface fichier" << endl; - exit(1); - } - - sockfd = create_udp_sending_socket(argv[1], 1234, &serv, &client); - - if(sockfd < 0){ - cerr << "Erreur ! Impossible de créer la socket vers le serveur de localisation" << endl; - return 1; - } - get_mac_addr(argv[2], mac) ; - memcpy(envoi_demande.ag_mac_addr_bytes, mac, 6); - - if(fichier){ - getline(fichier, cppbuffer); - envoi_demande.nb_couples = split(cppbuffer, envoi_info); - } - - n = sendto(sockfd, (void *)&envoi_demande, sizeof(envoi_demande), 0, (struct sockaddr *)&serv, (socklen_t) sizeof(serv)) ; - - for(int i = 0; i < envoi_demande.nb_couples; i++) - sendto(sockfd, (void *)&envoi_info.at(i), sizeof(couple_info), 0, (struct sockaddr *)&serv, (socklen_t) sizeof(serv)); - - exit(0); -} - -void get_mac_addr(char *eth, unsigned char mac_bytes[6]) -{ - struct ifreq ifr; - int sockfd ; - - bzero(mac_bytes, sizeof(unsigned char) * 6) ; // RàZ - - sockfd = socket(AF_INET, SOCK_DGRAM, 0) ; - if(sockfd < 0) - perror("Impossible d'ouvrir la socket pour récupérer l'adresse MAC ") ; - - strncpy(ifr.ifr_name, eth, IFNAMSIZ) ; - - if (ioctl(sockfd, SIOCGIFFLAGS, &ifr) < 0) - return ; - - if (ioctl(sockfd, SIOCGIFHWADDR, &ifr) < 0) - return ; - - memcpy(mac_bytes, ifr.ifr_hwaddr.sa_data, 6) ; -} - -int split(string buffer, vector &envoi_info){ - - unsigned char mac[6]; - int valueI; - char c[4]; - couple_info elem; - int i = 0; - int nb = 0; - - while(i < buffer.size()){ - - for(int j = 0; j < 6; j++){ - c[0] = buffer[i++]; - c[1] = buffer[i++]; - c[2] = '\0'; - mac[j] = convertuchar(c, 0); - i++; - } - c[0] = buffer[i++]; - c[1] = buffer[i++]; - c[2] = buffer[i++]; - c[3] = '\0'; - i++; - valueI = atoi(c); - memcpy(elem.ap_mac_addr_bytes, mac, 6); - elem.antenna_signal_dbm = valueI; - envoi_info.resize(nb+1); - envoi_info.at(nb) = elem; - nb++; - } - - return nb; -} - -char* mac_bytes_to_string(unsigned char *mac_binary) -{ - char *ret = (char *)malloc(sizeof(char) * 18) ; - - sprintf(ret, "%02x:%02x:%02x:%02x:%02x:%02x", mac_binary[0], mac_binary[1], mac_binary[2], mac_binary[3], mac_binary[4], mac_binary[5]) ; - ret[17] = '\0' ; - - return ret ; -} - -int create_udp_sending_socket(char *server_address, int server_port, struct sockaddr_in *server_description, struct sockaddr_in * client_description){ - - int sockfd ; // Descripteur de la socket - - /* Ceation de la socket UDP */ - sockfd = socket(AF_INET, SOCK_DGRAM, 0) ; - if (sockfd < 0){ - cerr << "Échec de la création de la socket " << endl; - return sockfd; - } - - /* Remise à zéro et initialisation de la structure du client */ - bzero((char *) client_description, sizeof(*client_description)) ; - client_description->sin_family = AF_INET ; // Socket INET - client_description->sin_addr.s_addr = htonl(INADDR_ANY) ; // Toutes les connexions - - /* Remise à zéro et initialisation de la structure du serveur */ - bzero((char *) server_description, sizeof(*server_description)) ; // RÀZ - server_description->sin_family = AF_INET ; // Socket INET - server_description->sin_addr.s_addr = inet_addr(server_address) ; // Adresse du serveur - server_description->sin_port = htons(server_port) ; // Port d'écoute du serveur - - return sockfd ; // On retourne le descripteur de la socket créée -} - -unsigned char convertuchar(char *caractere, int debut) { - - int i = debut; - - if (caractere[i] == '0' && caractere[i + 1] == '0') return 0x00; - if (caractere[i] == '0' && caractere[i + 1] == '1') return 0x01; - if (caractere[i] == '0' && caractere[i + 1] == '2') return 0x02; - if (caractere[i] == '0' && caractere[i + 1] == '3') return 0x03; - if (caractere[i] == '0' && caractere[i + 1] == '4') return 0x04; - if (caractere[i] == '0' && caractere[i + 1] == '5') return 0x05; - if (caractere[i] == '0' && caractere[i + 1] == '6') return 0x06; - if (caractere[i] == '0' && caractere[i + 1] == '7') return 0x07; - if (caractere[i] == '0' && caractere[i + 1] == '8') return 0x08; - if (caractere[i] == '0' && caractere[i + 1] == '9') return 0x09; - if (caractere[i] == '0' && caractere[i + 1] == 'a') return 0x0a; - if (caractere[i] == '0' && caractere[i + 1] == 'b') return 0x0b; - if (caractere[i] == '0' && caractere[i + 1] == 'c') return 0x0c; - if (caractere[i] == '0' && caractere[i + 1] == 'd') return 0x0d; - if (caractere[i] == '0' && caractere[i + 1] == 'e') return 0x0e; - if (caractere[i] == '0' && caractere[i + 1] == 'f') return 0x0f; - - if (caractere[i] == '1' && caractere[i + 1] == '0') return 0x10; - if (caractere[i] == '1' && caractere[i + 1] == '1') return 0x11; - if (caractere[i] == '1' && caractere[i + 1] == '2') return 0x12; - if (caractere[i] == '1' && caractere[i + 1] == '3') return 0x13; - if (caractere[i] == '1' && caractere[i + 1] == '4') return 0x14; - if (caractere[i] == '1' && caractere[i + 1] == '5') return 0x15; - if (caractere[i] == '1' && caractere[i + 1] == '6') return 0x16; - if (caractere[i] == '1' && caractere[i + 1] == '7') return 0x17; - if (caractere[i] == '1' && caractere[i + 1] == '8') return 0x18; - if (caractere[i] == '1' && caractere[i + 1] == '9') return 0x19; - if (caractere[i] == '1' && caractere[i + 1] == 'a') return 0x1a; - if (caractere[i] == '1' && caractere[i + 1] == 'b') return 0x1b; - if (caractere[i] == '1' && caractere[i + 1] == 'c') return 0x1c; - if (caractere[i] == '1' && caractere[i + 1] == 'd') return 0x1d; - if (caractere[i] == '1' && caractere[i + 1] == 'e') return 0x1e; - if (caractere[i] == '1' && caractere[i + 1] == 'f') return 0x1f; - - if (caractere[i] == '2' && caractere[i + 1] == '0') return 0x20; - if (caractere[i] == '2' && caractere[i + 1] == '1') return 0x21; - if (caractere[i] == '2' && caractere[i + 1] == '2') return 0x22; - if (caractere[i] == '2' && caractere[i + 1] == '3') return 0x23; - if (caractere[i] == '2' && caractere[i + 1] == '4') return 0x24; - if (caractere[i] == '2' && caractere[i + 1] == '5') return 0x25; - if (caractere[i] == '2' && caractere[i + 1] == '6') return 0x26; - if (caractere[i] == '2' && caractere[i + 1] == '7') return 0x27; - if (caractere[i] == '2' && caractere[i + 1] == '8') return 0x28; - if (caractere[i] == '2' && caractere[i + 1] == '9') return 0x29; - if (caractere[i] == '2' && caractere[i + 1] == 'a') return 0x2a; - if (caractere[i] == '2' && caractere[i + 1] == 'b') return 0x2b; - if (caractere[i] == '2' && caractere[i + 1] == 'c') return 0x2c; - if (caractere[i] == '2' && caractere[i + 1] == 'd') return 0x2d; - if (caractere[i] == '2' && caractere[i + 1] == 'e') return 0x2e; - if (caractere[i] == '2' && caractere[i + 1] == 'f') return 0x2f; - - if (caractere[i] == '3' && caractere[i + 1] == '0') return 0x30; - if (caractere[i] == '3' && caractere[i + 1] == '1') return 0x31; - if (caractere[i] == '3' && caractere[i + 1] == '2') return 0x32; - if (caractere[i] == '3' && caractere[i + 1] == '3') return 0x33; - if (caractere[i] == '3' && caractere[i + 1] == '4') return 0x34; - if (caractere[i] == '3' && caractere[i + 1] == '5') return 0x35; - if (caractere[i] == '3' && caractere[i + 1] == '6') return 0x36; - if (caractere[i] == '3' && caractere[i + 1] == '7') return 0x37; - if (caractere[i] == '3' && caractere[i + 1] == '8') return 0x38; - if (caractere[i] == '3' && caractere[i + 1] == '9') return 0x39; - if (caractere[i] == '3' && caractere[i + 1] == 'a') return 0x3a; - if (caractere[i] == '3' && caractere[i + 1] == 'b') return 0x3b; - if (caractere[i] == '3' && caractere[i + 1] == 'c') return 0x3c; - if (caractere[i] == '3' && caractere[i + 1] == 'd') return 0x3d; - if (caractere[i] == '3' && caractere[i + 1] == 'e') return 0x3e; - if (caractere[i] == '3' && caractere[i + 1] == 'f') return 0x3f; - - if (caractere[i] == '4' && caractere[i + 1] == '0') return 0x40; - if (caractere[i] == '4' && caractere[i + 1] == '1') return 0x41; - if (caractere[i] == '4' && caractere[i + 1] == '2') return 0x42; - if (caractere[i] == '4' && caractere[i + 1] == '3') return 0x43; - if (caractere[i] == '4' && caractere[i + 1] == '4') return 0x44; - if (caractere[i] == '4' && caractere[i + 1] == '5') return 0x45; - if (caractere[i] == '4' && caractere[i + 1] == '6') return 0x46; - if (caractere[i] == '4' && caractere[i + 1] == '7') return 0x47; - if (caractere[i] == '4' && caractere[i + 1] == '8') return 0x48; - if (caractere[i] == '4' && caractere[i + 1] == '9') return 0x49; - if (caractere[i] == '4' && caractere[i + 1] == 'a') return 0x4a; - if (caractere[i] == '4' && caractere[i + 1] == 'b') return 0x4b; - if (caractere[i] == '4' && caractere[i + 1] == 'c') return 0x4c; - if (caractere[i] == '4' && caractere[i + 1] == 'd') return 0x4d; - if (caractere[i] == '4' && caractere[i + 1] == 'e') return 0x4e; - if (caractere[i] == '4' && caractere[i + 1] == 'f') return 0x4f; - - if (caractere[i] == '5' && caractere[i + 1] == '0') return 0x50; - if (caractere[i] == '5' && caractere[i + 1] == '1') return 0x51; - if (caractere[i] == '5' && caractere[i + 1] == '2') return 0x52; - if (caractere[i] == '5' && caractere[i + 1] == '3') return 0x53; - if (caractere[i] == '5' && caractere[i + 1] == '4') return 0x54; - if (caractere[i] == '5' && caractere[i + 1] == '5') return 0x55; - if (caractere[i] == '5' && caractere[i + 1] == '6') return 0x56; - if (caractere[i] == '5' && caractere[i + 1] == '7') return 0x57; - if (caractere[i] == '5' && caractere[i + 1] == '8') return 0x58; - if (caractere[i] == '5' && caractere[i + 1] == '9') return 0x59; - if (caractere[i] == '5' && caractere[i + 1] == 'a') return 0x5a; - if (caractere[i] == '5' && caractere[i + 1] == 'b') return 0x5b; - if (caractere[i] == '5' && caractere[i + 1] == 'c') return 0x5c; - if (caractere[i] == '5' && caractere[i + 1] == 'd') return 0x5d; - if (caractere[i] == '5' && caractere[i + 1] == 'e') return 0x5e; - if (caractere[i] == '5' && caractere[i + 1] == 'f') return 0x5f; - - if (caractere[i] == '6' && caractere[i + 1] == '0') return 0x60; - if (caractere[i] == '6' && caractere[i + 1] == '1') return 0x61; - if (caractere[i] == '6' && caractere[i + 1] == '2') return 0x62; - if (caractere[i] == '6' && caractere[i + 1] == '3') return 0x63; - if (caractere[i] == '6' && caractere[i + 1] == '4') return 0x64; - if (caractere[i] == '6' && caractere[i + 1] == '5') return 0x65; - if (caractere[i] == '6' && caractere[i + 1] == '6') return 0x66; - if (caractere[i] == '6' && caractere[i + 1] == '7') return 0x67; - if (caractere[i] == '6' && caractere[i + 1] == '8') return 0x68; - if (caractere[i] == '6' && caractere[i + 1] == '9') return 0x69; - if (caractere[i] == '6' && caractere[i + 1] == 'a') return 0x6a; - if (caractere[i] == '6' && caractere[i + 1] == 'b') return 0x6b; - if (caractere[i] == '6' && caractere[i + 1] == 'c') return 0x6c; - if (caractere[i] == '6' && caractere[i + 1] == 'd') return 0x6d; - if (caractere[i] == '6' && caractere[i + 1] == 'e') return 0x6e; - if (caractere[i] == '6' && caractere[i + 1] == 'f') return 0x6f; - - if (caractere[i] == '7' && caractere[i + 1] == '0') return 0x70; - if (caractere[i] == '7' && caractere[i + 1] == '1') return 0x71; - if (caractere[i] == '7' && caractere[i + 1] == '2') return 0x72; - if (caractere[i] == '7' && caractere[i + 1] == '3') return 0x73; - if (caractere[i] == '7' && caractere[i + 1] == '4') return 0x74; - if (caractere[i] == '7' && caractere[i + 1] == '5') return 0x75; - if (caractere[i] == '7' && caractere[i + 1] == '6') return 0x76; - if (caractere[i] == '7' && caractere[i + 1] == '7') return 0x77; - if (caractere[i] == '7' && caractere[i + 1] == '8') return 0x78; - if (caractere[i] == '7' && caractere[i + 1] == '9') return 0x79; - if (caractere[i] == '7' && caractere[i + 1] == 'a') return 0x7a; - if (caractere[i] == '7' && caractere[i + 1] == 'b') return 0x7b; - if (caractere[i] == '7' && caractere[i + 1] == 'c') return 0x7c; - if (caractere[i] == '7' && caractere[i + 1] == 'd') return 0x7d; - if (caractere[i] == '7' && caractere[i + 1] == 'e') return 0x7e; - if (caractere[i] == '7' && caractere[i + 1] == 'f') return 0x7f; - - if (caractere[i] == '8' && caractere[i + 1] == '0') return 0x80; - if (caractere[i] == '8' && caractere[i + 1] == '1') return 0x81; - if (caractere[i] == '8' && caractere[i + 1] == '2') return 0x82; - if (caractere[i] == '8' && caractere[i + 1] == '3') return 0x83; - if (caractere[i] == '8' && caractere[i + 1] == '4') return 0x84; - if (caractere[i] == '8' && caractere[i + 1] == '5') return 0x85; - if (caractere[i] == '8' && caractere[i + 1] == '6') return 0x86; - if (caractere[i] == '8' && caractere[i + 1] == '7') return 0x87; - if (caractere[i] == '8' && caractere[i + 1] == '8') return 0x88; - if (caractere[i] == '8' && caractere[i + 1] == '9') return 0x89; - if (caractere[i] == '8' && caractere[i + 1] == 'a') return 0x8a; - if (caractere[i] == '8' && caractere[i + 1] == 'b') return 0x8b; - if (caractere[i] == '8' && caractere[i + 1] == 'c') return 0x8c; - if (caractere[i] == '8' && caractere[i + 1] == 'd') return 0x8d; - if (caractere[i] == '8' && caractere[i + 1] == 'e') return 0x8e; - if (caractere[i] == '8' && caractere[i + 1] == 'f') return 0x8f; - - if (caractere[i] == '9' && caractere[i + 1] == '0') return 0x90; - if (caractere[i] == '9' && caractere[i + 1] == '1') return 0x91; - if (caractere[i] == '9' && caractere[i + 1] == '2') return 0x92; - if (caractere[i] == '9' && caractere[i + 1] == '3') return 0x93; - if (caractere[i] == '9' && caractere[i + 1] == '4') return 0x94; - if (caractere[i] == '9' && caractere[i + 1] == '5') return 0x95; - if (caractere[i] == '9' && caractere[i + 1] == '6') return 0x96; - if (caractere[i] == '9' && caractere[i + 1] == '7') return 0x97; - if (caractere[i] == '9' && caractere[i + 1] == '8') return 0x98; - if (caractere[i] == '9' && caractere[i + 1] == '9') return 0x99; - if (caractere[i] == '9' && caractere[i + 1] == 'a') return 0x9a; - if (caractere[i] == '9' && caractere[i + 1] == 'b') return 0x9b; - if (caractere[i] == '9' && caractere[i + 1] == 'c') return 0x9c; - if (caractere[i] == '9' && caractere[i + 1] == 'd') return 0x9d; - if (caractere[i] == '9' && caractere[i + 1] == 'e') return 0x9e; - if (caractere[i] == '9' && caractere[i + 1] == 'f') return 0x9f; - - if (caractere[i] == 'a' && caractere[i + 1] == '0') return 0xa0; - if (caractere[i] == 'a' && caractere[i + 1] == '1') return 0xa1; - if (caractere[i] == 'a' && caractere[i + 1] == '2') return 0xa2; - if (caractere[i] == 'a' && caractere[i + 1] == '3') return 0xa3; - if (caractere[i] == 'a' && caractere[i + 1] == '4') return 0xa4; - if (caractere[i] == 'a' && caractere[i + 1] == '5') return 0xa5; - if (caractere[i] == 'a' && caractere[i + 1] == '6') return 0xa6; - if (caractere[i] == 'a' && caractere[i + 1] == '7') return 0xa7; - if (caractere[i] == 'a' && caractere[i + 1] == '8') return 0xa8; - if (caractere[i] == 'a' && caractere[i + 1] == '9') return 0xa9; - if (caractere[i] == 'a' && caractere[i + 1] == 'a') return 0xaa; - if (caractere[i] == 'a' && caractere[i + 1] == 'b') return 0xab; - if (caractere[i] == 'a' && caractere[i + 1] == 'c') return 0xac; - if (caractere[i] == 'a' && caractere[i + 1] == 'd') return 0xad; - if (caractere[i] == 'a' && caractere[i + 1] == 'e') return 0xae; - if (caractere[i] == 'a' && caractere[i + 1] == 'f') return 0xaf; - - if (caractere[i] == 'b' && caractere[i + 1] == '0') return 0xb0; - if (caractere[i] == 'b' && caractere[i + 1] == '1') return 0xb1; - if (caractere[i] == 'b' && caractere[i + 1] == '2') return 0xb2; - if (caractere[i] == 'b' && caractere[i + 1] == '3') return 0xb3; - if (caractere[i] == 'b' && caractere[i + 1] == '4') return 0xb4; - if (caractere[i] == 'b' && caractere[i + 1] == '5') return 0xb5; - if (caractere[i] == 'b' && caractere[i + 1] == '6') return 0xb6; - if (caractere[i] == 'b' && caractere[i + 1] == '7') return 0xb7; - if (caractere[i] == 'b' && caractere[i + 1] == '8') return 0xb8; - if (caractere[i] == 'b' && caractere[i + 1] == '9') return 0xb9; - if (caractere[i] == 'b' && caractere[i + 1] == 'a') return 0xba; - if (caractere[i] == 'b' && caractere[i + 1] == 'b') return 0xbb; - if (caractere[i] == 'b' && caractere[i + 1] == 'c') return 0xbc; - if (caractere[i] == 'b' && caractere[i + 1] == 'd') return 0xbd; - if (caractere[i] == 'b' && caractere[i + 1] == 'e') return 0xbe; - if (caractere[i] == 'b' && caractere[i + 1] == 'f') return 0xbf; - - if (caractere[i] == 'c' && caractere[i + 1] == '0') return 0xc0; - if (caractere[i] == 'c' && caractere[i + 1] == '1') return 0xc1; - if (caractere[i] == 'c' && caractere[i + 1] == '2') return 0xc2; - if (caractere[i] == 'c' && caractere[i + 1] == '3') return 0xc3; - if (caractere[i] == 'c' && caractere[i + 1] == '4') return 0xc4; - if (caractere[i] == 'c' && caractere[i + 1] == '5') return 0xc5; - if (caractere[i] == 'c' && caractere[i + 1] == '6') return 0xc6; - if (caractere[i] == 'c' && caractere[i + 1] == '7') return 0xc7; - if (caractere[i] == 'c' && caractere[i + 1] == '8') return 0xc8; - if (caractere[i] == 'c' && caractere[i + 1] == '9') return 0xc9; - if (caractere[i] == 'c' && caractere[i + 1] == 'a') return 0xca; - if (caractere[i] == 'c' && caractere[i + 1] == 'b') return 0xcb; - if (caractere[i] == 'c' && caractere[i + 1] == 'c') return 0xcc; - if (caractere[i] == 'c' && caractere[i + 1] == 'd') return 0xcd; - if (caractere[i] == 'c' && caractere[i + 1] == 'e') return 0xce; - if (caractere[i] == 'c' && caractere[i + 1] == 'f') return 0xcf; - - if (caractere[i] == 'd' && caractere[i + 1] == '0') return 0xd0; - if (caractere[i] == 'd' && caractere[i + 1] == '1') return 0xd1; - if (caractere[i] == 'd' && caractere[i + 1] == '2') return 0xd2; - if (caractere[i] == 'd' && caractere[i + 1] == '3') return 0xd3; - if (caractere[i] == 'd' && caractere[i + 1] == '4') return 0xd4; - if (caractere[i] == 'd' && caractere[i + 1] == '5') return 0xd5; - if (caractere[i] == 'd' && caractere[i + 1] == '6') return 0xd6; - if (caractere[i] == 'd' && caractere[i + 1] == '7') return 0xd7; - if (caractere[i] == 'd' && caractere[i + 1] == '8') return 0xd8; - if (caractere[i] == 'd' && caractere[i + 1] == '9') return 0xd9; - if (caractere[i] == 'd' && caractere[i + 1] == 'a') return 0xda; - if (caractere[i] == 'd' && caractere[i + 1] == 'b') return 0xdb; - if (caractere[i] == 'd' && caractere[i + 1] == 'c') return 0xdc; - if (caractere[i] == 'd' && caractere[i + 1] == 'd') return 0xdd; - if (caractere[i] == 'd' && caractere[i + 1] == 'e') return 0xde; - if (caractere[i] == 'd' && caractere[i + 1] == 'f') return 0xdf; - - if (caractere[i] == 'e' && caractere[i + 1] == '0') return 0xe0; - if (caractere[i] == 'e' && caractere[i + 1] == '1') return 0xe1; - if (caractere[i] == 'e' && caractere[i + 1] == '2') return 0xe2; - if (caractere[i] == 'e' && caractere[i + 1] == '3') return 0xe3; - if (caractere[i] == 'e' && caractere[i + 1] == '4') return 0xe4; - if (caractere[i] == 'e' && caractere[i + 1] == '5') return 0xe5; - if (caractere[i] == 'e' && caractere[i + 1] == '6') return 0xe6; - if (caractere[i] == 'e' && caractere[i + 1] == '7') return 0xe7; - if (caractere[i] == 'e' && caractere[i + 1] == '8') return 0xe8; - if (caractere[i] == 'e' && caractere[i + 1] == '9') return 0xe9; - if (caractere[i] == 'e' && caractere[i + 1] == 'a') return 0xea; - if (caractere[i] == 'e' && caractere[i + 1] == 'b') return 0xeb; - if (caractere[i] == 'e' && caractere[i + 1] == 'c') return 0xec; - if (caractere[i] == 'e' && caractere[i + 1] == 'd') return 0xed; - if (caractere[i] == 'e' && caractere[i + 1] == 'e') return 0xee; - if (caractere[i] == 'e' && caractere[i + 1] == 'f') return 0xef; - - if (caractere[i] == 'f' && caractere[i + 1] == '0') return 0xf0; - if (caractere[i] == 'f' && caractere[i + 1] == '1') return 0xf1; - if (caractere[i] == 'f' && caractere[i + 1] == '2') return 0xf2; - if (caractere[i] == 'f' && caractere[i + 1] == '3') return 0xf3; - if (caractere[i] == 'f' && caractere[i + 1] == '4') return 0xf4; - if (caractere[i] == 'f' && caractere[i + 1] == '5') return 0xf5; - if (caractere[i] == 'f' && caractere[i + 1] == '6') return 0xf6; - if (caractere[i] == 'f' && caractere[i + 1] == '7') return 0xf7; - if (caractere[i] == 'f' && caractere[i + 1] == '8') return 0xf8; - if (caractere[i] == 'f' && caractere[i + 1] == '9') return 0xf9; - if (caractere[i] == 'f' && caractere[i + 1] == 'a') return 0xfa; - if (caractere[i] == 'f' && caractere[i + 1] == 'b') return 0xfb; - if (caractere[i] == 'f' && caractere[i + 1] == 'c') return 0xfc; - if (caractere[i] == 'f' && caractere[i + 1] == 'd') return 0xfd; - if (caractere[i] == 'f' && caractere[i + 1] == 'e') return 0xfe; - if (caractere[i] == 'f' && caractere[i + 1] == 'f') return 0xff; - - return 0x00; -} diff --git a/owlps-positioning/libowlps-positioning.cc b/owlps-positioning/libowlps-positioning.cc new file mode 100644 index 0000000..9f22958 --- /dev/null +++ b/owlps-positioning/libowlps-positioning.cc @@ -0,0 +1,99 @@ +#include "libowlps-positioning.hh" + +float round_float(float f, int n) +{ + n = (int) pow((double) 10, (double) n) ; + float f_dec = modff(f, &f) ; + f_dec = floor(f_dec * n) / n ; + + return f + f_dec ; +} + +vector explode(const string &input, const char &sep) +{ + + vector vs; + string tmp; + unsigned int i; + + for (i = 0 ; i < input.size() ; i++) + if (input[i] == sep) + { + vs.push_back(tmp); + tmp.clear(); + } + else + { + tmp.push_back(input[i]); + } + + vs.push_back(tmp); + tmp.clear(); + + return vs; +} + +vector extractReferencePointInfoFromBuffer(const string &buffer_in) +{ + unsigned int i = 0; + string tmp_field; + vector ret; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; // go after the ';' + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (i <= buffer_in.size()) + { + if ((buffer_in[i] == ';' || i == buffer_in.size()) && !tmp_field.empty()) // Si on est sur un séparateur et que la valeur lue n'est pas vide, + { + ret.push_back(tmp_field) ; // on met la valeur lue dans les valeurs de retour. + tmp_field.clear() ; + } + else // Si on n'est pas sur un séparateur, + tmp_field.push_back(buffer_in[i]) ; // on ajoute le caractère courant à la suite de la valeur lue. + + i++ ; + } + + return ret; +} + +unsigned long timeval_to_ms(const struct timeval *tv) +{ + return (tv->tv_sec * 1000) + ((tv->tv_usec + 500) / 1000); +} + + diff --git a/owlps-positioning/libowlps-positioning.hh b/owlps-positioning/libowlps-positioning.hh new file mode 100644 index 0000000..b238ab6 --- /dev/null +++ b/owlps-positioning/libowlps-positioning.hh @@ -0,0 +1,57 @@ +#ifndef _LIBOWLPS_POSITINING_HH_ +#define _LIBOWLPS_POSITINING_HH_ + +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include +#include + +#include + + +#define DEFAULT_AP_FILE "csv/minipc.cfg" +#define DEFAULT_PT_FILE "csv/toutes.csv" +#define DEFAULT_TOPO_FILE "csv/topo.csv" +#define DEFAULT_WAYPOINT_FILE "csv/waypoints.csv" + +#define LIGHT_SPEED 300000000 +#define MINMAX_STEP 0.5 +#define MINMAX_X_START 0.5 +#define MINMAX_Y_START 0.5 +#define MINMAX_Z_START 0 +#define MINMAX_X_STOP 10 +#define MINMAX_Y_STOP 31.5 +#define MINMAX_Z_STOP 6 + +typedef struct _couple_info + { + unsigned char ap_mac_addr_bytes[6]; // Adresse MAC de l'AP + int antenna_signal_dbm; // Puissance du signal reçu par l'AP + } couple_info; + +typedef struct _request + { + unsigned char mobile_mac_addr_bytes[6]; //Adresse MAC du mobile + struct timeval request_time; // Date sur le client + int nb_couples; // Nombre couples (MAC AP;Puissance) + } request; + +using namespace std; + +float round_float(float f, int n); +vector explode(const string &input, const char &sep); +vector extractReferencePointInfoFromBuffer(const string &buffer_in); +unsigned long timeval_to_ms(const struct timeval *tv); + +#endif diff --git a/owlps-positioning/owlps-positioning.cc b/owlps-positioning/owlps-positioning.cc index 893c4ff..c49ddbe 100644 --- a/owlps-positioning/owlps-positioning.cc +++ b/owlps-positioning/owlps-positioning.cc @@ -1,29 +1,49 @@ #include "owlps-positioning.hh" - int main(int argc, char** argv) { - if (argc != 1 && argc != 5) + + po::options_description desc("Options"); + po::options_description conf("Configuration Positioner"); + po::options_description opt("Aide"); + po::variables_map vm; + + ifstream ifs("owlps-positioning.cfg"); + + int port, mport; + + desc.add_options() + ("help", "\t: Affichage de l'aide") + ("input-topo,T", po::value(), "\t: Input file topology") + ("input-waypoint,W", po::value(), "\t: Input file waypoint") + ("input-refpoint,R", po::value(), "\t: Input file reference point") + ("input-ap,A", po::value(), "\t: Input file accesspoint") + ; + + conf.add_options() + ("Server.port", po::value(&port) -> default_value(9902), "\t: Port du serveur") + ("Server.mobile-port", po::value(&mport) -> default_value(9903), "\t: Port d'envoi vers le mobile") + ("BDD.name", po::value(), "\t: Nom de la BdD") + ("BDD.hostaddr", po::value(), "\t: Adresse de l'hôte de la BdD") + ("BDD.user", po::value(), "\t: Nom de l'utilisateur de la BdD") + ("BDD.passwd", po::value(), "\t: Mot de passe de la BdD") + ; + + opt.add(desc).add(conf); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::store(po::parse_config_file(ifs, conf), vm); + po::notify(vm); + + Server server(port, mport); + + if (vm.count("help")) { - cout << "Usage:\towlps-positioningd\n" - << " \towlps-positioningd AP_file Pt_file Topo_file Waypoint_file" << endl; - return 1; + cout << opt << endl; + return 0; } - Server server(1234); - - if (argc == 5) - { - string apfile = argv[1]; - string ptfile = argv[2]; - string topofile = argv[3]; - string wayfile = argv[4]; - if (server.initFile(apfile, ptfile, topofile, wayfile)) - { - cerr << "Erreur lors de l'initialisation de la topology" << endl; - return 1; - } - } + if (server.init(vm)) return 1; server.start(); diff --git a/owlps-positioning/owlps-positioning.cfg b/owlps-positioning/owlps-positioning.cfg new file mode 100644 index 0000000..7098388 --- /dev/null +++ b/owlps-positioning/owlps-positioning.cfg @@ -0,0 +1,9 @@ +[Server] +port = 9902 +mobile-port = 9903 + +[BDD] +name = owlps_db +hostaddr = 127.0.0.1 +user = julien +passwd = 10,mamci diff --git a/owlps-positioning/owlps-positioning.hh b/owlps-positioning/owlps-positioning.hh index 7f2c7f0..dca5fc6 100644 --- a/owlps-positioning/owlps-positioning.hh +++ b/owlps-positioning/owlps-positioning.hh @@ -4,8 +4,11 @@ #include #include +#include + #include "server.hh" using namespace std; +namespace po = boost::program_options; #endif diff --git a/owlps-positioning/positioning.cc b/owlps-positioning/positioning.cc index 3b0dfd3..56df3b6 100644 --- a/owlps-positioning/positioning.cc +++ b/owlps-positioning/positioning.cc @@ -12,96 +12,6 @@ inline T from_string(const string &s) return t; } -inline float round_float(float f, int n) -{ - n = (int) pow((double) 10, (double) n) ; - float f_dec = modff(f, &f) ; - f_dec = floor(f_dec * n) / n ; - - return f + f_dec ; -} - -inline vector explode(const string &input, const char &sep) -{ - vector vs; - string tmp; - unsigned int i; - - for (i = 0 ; i < input.size() ; i++) - if (input[i] == sep) - { - vs.push_back(tmp); - tmp.clear(); - } - else - { - tmp.push_back(input[i]); - } - - vs.push_back(tmp); - tmp.clear(); - - return vs; -} - -inline vector extractReferencePointInfoFromBuffer(const string &buffer_in) -{ - unsigned int i = 0; - string tmp_field; - vector ret; - - while (buffer_in[i] != ';') - { - tmp_field.push_back(buffer_in[i]); - i++; - } - ret.push_back(tmp_field); - tmp_field.clear(); - i++; // go after the ';' - - while (buffer_in[i] != ';') - { - tmp_field.push_back(buffer_in[i]); - i++; - } - ret.push_back(tmp_field); - tmp_field.clear(); - i++; - - while (buffer_in[i] != ';') - { - tmp_field.push_back(buffer_in[i]); - i++; - } - ret.push_back(tmp_field); - tmp_field.clear(); - i++; - - while (buffer_in[i] != ';') - { - tmp_field.push_back(buffer_in[i]); - i++; - } - ret.push_back(tmp_field); - tmp_field.clear(); - i++; - - while (i <= buffer_in.size()) - { - if ((buffer_in[i] == ';' || i == buffer_in.size()) && !tmp_field.empty()) // Si on est sur un séparateur et que la valeur lue n'est pas vide, - { - ret.push_back(tmp_field) ; // on met la valeur lue dans les valeurs de retour. - tmp_field.clear() ; - } - else // Si on n'est pas sur un séparateur, - tmp_field.push_back(buffer_in[i]) ; // on ajoute le caractère courant à la suite de la valeur lue. - - i++ ; - } - - return ret; -} - void Positioning::makeReferencePointListFromFile(const string &filename, const bool uniq_point) { @@ -111,6 +21,7 @@ void Positioning::makeReferencePointListFromFile(const string &filename, const b Point tmp_point; float x, y, z ; // Coordonnées des points. unsigned int pt_idx = 0 ; // Position du point lu dans la liste. + int direction; vector infos ; // Liste des informations lues dans une ligne du fichier. input_file.open(filename.c_str()) ; @@ -137,8 +48,9 @@ void Positioning::makeReferencePointListFromFile(const string &filename, const b tmp_point.setX(x); tmp_point.setY(y); tmp_point.setZ(z); + direction = from_string(infos[3]); - if (!uniq_point || !pointExists(reference_point_list, tmp_point)) // Si on ne veut pas de points unique, ou que le point n'existe pas encore,{ + if (!uniq_point || !pointExists(reference_point_list, tmp_point)) // Si on ne veut pas de points unique, ou que le point n'existe pas encore, { rp.setCoordinates(tmp_point); reference_point_list.push_back(rp); // on le crée. @@ -275,13 +187,179 @@ void Positioning::makeWaypointListFromFile(const string &filename) infos.clear() ; } } - input_file.close() ; // Lecture du fichier terminée + input_file.close(); // Lecture du fichier terminée + makeWaypointMatrix(point_list); +} + +void Positioning::makeReferencePointListFromDb(PGconn *conn, const bool uniq) +{ + + PGresult *res; + Point tmp_point; + ReferencePoint rp; + + ostringstream oss; + string buf; + + buf = "SELECT * FROM ref_point;"; + + res = PQexec(conn, buf.c_str()); + if (PQresultStatus(res) != PGRES_TUPLES_OK) + { + cerr << "Commande incorrecte: " << PQerrorMessage(conn); + } + else + { + int nbRes = PQntuples(res); + for (int i = 0; i < nbRes; i++) + { + tmp_point.setX(from_string(PQgetvalue(res, i, 1))); + tmp_point.setY(from_string(PQgetvalue(res, i, 2))); + tmp_point.setZ(from_string(PQgetvalue(res, i, 3))); + + if (!uniq || !pointExists(reference_point_list, tmp_point)) // Si on ne veut pas de points unique, ou que le point n'existe pas encore, + { + rp.setCoordinates(tmp_point); + reference_point_list.push_back(rp); // on le crée. + } + } + PQclear(res); + + for (unsigned int i = 0; i < reference_point_list.size(); i++) + { + + tmp_point = reference_point_list[i].getCoordinates(); + + oss << "SELECT ap.ap_addr, n.power "; + oss << "FROM ap, ref_packet n, ref_request r, ref_point p "; + oss << "WHERE ap.id_ap = n.id_ap "; + oss << "AND n.id_ref_request = r.id_ref_request "; + oss << "AND r.id_ref_point = p.id_ref_point "; + oss << "AND p.x = " << tmp_point.getX() << " "; + oss << "AND p.y = " << tmp_point.getY() << " "; + oss << "AND p.z = " << tmp_point.getZ() << ";"; + + buf = oss.str(); + oss.str(""); + + res = PQexec(conn, buf.c_str()); + + if (PQresultStatus(res) != PGRES_TUPLES_OK) + { + cerr << "Commande incorrecte: " << PQerrorMessage(conn); + } + else + { + nbRes = PQntuples(res); + for (int j = 0; j < nbRes; j++) + reference_point_list[i].addMeasurement(PQgetvalue(res, j, 0), from_string(PQgetvalue(res, j, 1))); + } + + PQclear(res); + } + } + +} + +void Positioning::makeApListFromDb(PGconn *conn) +{ + + PGresult *res; + AccessPoint tmp_ap; + string buf; + + buf = "SELECT * FROM ap;"; + + res = PQexec(conn, buf.c_str()); + if (PQresultStatus(res) != PGRES_TUPLES_OK) + { + cerr << "Commande incorrecte: " << PQerrorMessage(conn); + } + else + { + int nbRes = PQntuples(res); + for (int i = 0; i < nbRes; i++) + { + tmp_ap.setApAddr(PQgetvalue(res, i, 1)); + tmp_ap.setCoordinates(from_string(PQgetvalue(res, i, 2)), from_string(PQgetvalue(res, i, 3)), from_string(PQgetvalue(res, i, 4))); + tmp_ap.setFriisIndex(from_string(PQgetvalue(res, i, 5))); + tmp_ap.setOutputPower(from_string(PQgetvalue(res, i, 8))); + tmp_ap.setAntennaGain(from_string(PQgetvalue(res, i, 7))); + tmp_ap.setFrequency(from_string(PQgetvalue(res, i, 6))); + access_point_list.push_back(tmp_ap); + } + } + + PQclear(res); +} + +void Positioning::makeTopologyFromDb(PGconn *conn) +{ + + PGresult *res; + string buf; + + buf = "SELECT * FROM area;"; + + res = PQexec(conn, buf.c_str()); + if (PQresultStatus(res) != PGRES_TUPLES_OK) + { + cerr << "Commande incorrecte: " << PQerrorMessage(conn); + } + else + { + int nbRes = PQntuples(res); + for (int i = 0; i < nbRes; i++) + { + if (area_list.find(PQgetvalue(res, i, 1)) != area_list.end()) // Si la pièce existe déjà, + cerr << "Erreur ! Déclaration multiple de la zone « " << PQgetvalue(res, i, 1) << " »." << endl ; // on le signale ; + else + area_list[PQgetvalue(res, i, 1)] = Area(PQgetvalue(res, i, 1), from_string(PQgetvalue(res, i, 2)), from_string(PQgetvalue(res, i, 5)), + from_string(PQgetvalue(res, i, 3)), from_string(PQgetvalue(res, i, 6)), + from_string(PQgetvalue(res, i, 4)), from_string(PQgetvalue(res, i, 7))); + } + } + PQclear(res); +} + +void Positioning::makeWaypointListFromDb(PGconn *conn) +{ + + PGresult *res; + string buf; + set point_list ; + + buf = "SELECT * FROM waypoint;"; + + res = PQexec(conn, buf.c_str()); + if (PQresultStatus(res) != PGRES_TUPLES_OK) + { + cerr << "Commande incorrecte: " << PQerrorMessage(conn); + } + else + { + int nbRes = PQntuples(res); + for (int i = 0; i < nbRes; i++) + { + Point tmp_pt(from_string(PQgetvalue(res, i, 0)), from_string(PQgetvalue(res, i, 1)), from_string(PQgetvalue(res, i, 2))); + if (! point_list.insert(tmp_pt).second) + cerr << "Point " << tmp_pt << " non ajouté ! Peut-être est-il dupliqué ?" << endl ; + } + makeWaypointMatrix(point_list); + } + + PQclear(res); +} + +void Positioning::makeWaypointMatrix(set point_list) +{ unsigned int nb_pts = point_list.size() ; // Nombre de points unsigned int cur_idx = 0 ; // Itérateur sur l'indice de la matrice. waypoint_list.reserve(nb_pts) ; // Vector contenant tous les points (attribut du serveur) waypoint_matrix = new float*[nb_pts] ; // Matrice (carrée) des distances entre les points de passage (attribut du serveur) + for (unsigned int i = 0 ; i < nb_pts ; i++) // Initialisation de la matrice : { waypoint_matrix[i] = new float[nb_pts] ; @@ -325,6 +403,7 @@ void Positioning::makeWaypointListFromFile(const string &filename) } } + map Positioning::inWhichAreas(const Point &p) { @@ -334,7 +413,8 @@ map Positioning::inWhichAreas(const Point &p) if (it->second.containsPoint(p)) areas.insert(make_pair(it->first, it->second)) ; - return areas ; + return areas; + } bool Positioning::inTheSameArea(const Point &p1, const Point &p2) @@ -535,7 +615,6 @@ bool Positioning::checkTopology() } } - for (unsigned int i = 0 ; i < reference_point_list.size() ; i++) { map areas(inWhichAreas((Point)reference_point_list[i])) ; @@ -649,3 +728,9 @@ void Positioning::printAccessPointList() const for (unsigned int i = 0; i < access_point_list.size(); i++) cout << access_point_list[i] << endl; } + +void Positioning::printAreatList() +{ + for (map::iterator it = area_list.begin() ; it != area_list.end() ; it++) + cout << it -> second << endl; +} diff --git a/owlps-positioning/positioning.hh b/owlps-positioning/positioning.hh index 36093d8..5d9af6c 100644 --- a/owlps-positioning/positioning.hh +++ b/owlps-positioning/positioning.hh @@ -1,24 +1,12 @@ #ifndef _POSITIONING_HH_ #define _POSITIONING_HH_ -#include -#include -#include -#include -#include -#include -#include - -#include -#include -#include - -#include "referencepoint.hh" #include "point.hh" +#include "referencepoint.hh" #include "accesspoint.hh" #include "area.hh" - -using namespace std; +#include "measurement.hh" +#include "libowlps-positioning.hh" class Positioning { @@ -41,10 +29,12 @@ class Positioning void makeTopologyFromFile(const string &filename); void makeWaypointListFromFile(const string &filename); - void makeReferencePointListFromDb() {}; - void makeApListFromDb() {}; - void makeTopologyFromDb() {}; - void makeWaypointListFromDb() {}; + void makeReferencePointListFromDb(PGconn*, const bool); + void makeApListFromDb(PGconn*); + void makeTopologyFromDb(PGconn*); + void makeWaypointListFromDb(PGconn*); + + void makeWaypointMatrix(set); map inWhichAreas(const Point &p); bool inTheSameArea(const Point &p1, const Point &p2); @@ -79,6 +69,7 @@ class Positioning void printReferencePointList(); void printPointList(vector &point_list); void printAccessPointList() const; + void printAreatList(); }; #endif diff --git a/owlps-positioning/server.cc b/owlps-positioning/server.cc index 0e9bc75..7fc40eb 100644 --- a/owlps-positioning/server.cc +++ b/owlps-positioning/server.cc @@ -1,20 +1,68 @@ #include "server.hh" -char* mac_bytes_to_string(unsigned char *mac_binary) +template +inline T from_string(const string &s) { - char *ret = (char *)malloc(sizeof(char) * 18) ; - sprintf(ret, "%02x:%02x:%02x:%02x:%02x:%02x", mac_binary[0], mac_binary[1], mac_binary[2], mac_binary[3], mac_binary[4], mac_binary[5]) ; - ret[17] = '\0' ; + T t; + istringstream iss(s); - return ret ; + iss >> t; + + return t; } -Server::Server(int port) +int Server::init(const boost::program_options::variables_map vm) { - listen_port = port; - client_len = sizeof(client); + ostringstream oss; + string buf; + + oss << "hostaddr = '" << vm["BDD.hostaddr"].as() << "' "; + oss << "dbname = '" << vm["BDD.name"].as() << "' "; + oss << "user = '" << vm["BDD.user"].as() << "' "; + oss << "password = '"<< vm["BDD.passwd"].as() << "'"; + buf = oss.str(); + + const char *conninfo = buf.c_str(); + conn = PQconnectdb(conninfo); + + if (PQstatus(conn) != CONNECTION_OK) + { + cout << "Connection à la base de donnée échouée: " << PQerrorMessage(conn) << endl; + return 1; + } + + if (vm.count("input-topo")) pos.makeTopologyFromFile(vm["input-topo"].as()); + else pos.makeTopologyFromDb(conn); + + if (vm.count("input-waypoint")) pos.makeWaypointListFromFile(vm["input-waypoint"].as()); + else pos.makeWaypointListFromDb(conn); + + if (vm.count("input-refpoint")) pos.makeReferencePointListFromFile(vm["input-refpoint"].as(), true); + else pos.makeReferencePointListFromDb(conn, true); + + if (!pos.checkTopology()) + { + cerr << "Erreur lors de la création de la topology" << endl; + return 1; + } + + pos.makeReferencePointDistances(); + + if (vm.count("input-ap")) pos.makeApListFromFile(vm["input-ap"].as()); + else pos.makeApListFromDb(conn); + + return 0; +} + +int Server::start() +{ + + struct sockaddr_in serv_addr; + struct sockaddr_in client; + socklen_t client_len = sizeof(client); + Point solution; /* Création d'une socket UDP */ listen_socket = socket(AF_INET, SOCK_DGRAM, 0) ; @@ -37,28 +85,6 @@ Server::Server(int port) close(listen_socket) ; exit(1); } -} - -int Server::initFile(const string &apfile, const string &ptfile, const string &topofile, const string &wayfile) -{ - calcul.makeTopologyFromFile(topofile.c_str()); - calcul.makeWaypointListFromFile(wayfile.c_str()); - calcul.makeReferencePointListFromFile(ptfile.c_str(), true); - - if (!calcul.checkTopology()) - { - cerr << "Erreur lors de la création de la topology" << endl; - exit(1); - } - - calcul.makeReferencePointDistances(); - calcul.makeApListFromFile(apfile.c_str()); - - return 0; -} - -int Server::start() -{ cout << "Serveur prêt" << endl; @@ -77,77 +103,148 @@ int Server::start() for (int i = 0; i < att_request.nb_couples; i++) recvfrom(listen_socket, &recv_info.at(i), sizeof(couple_info), 0, (struct sockaddr *) &client, &client_len); - treatment(att_request, recv_info); + treatment(); + recv_info.clear(); } } -void Server::treatment(request att_request, vector recv_info) +void Server::treatment() { - Treatment treat(calcul.getAccessPointList(), calcul.getReferencePointList()); Point solution; - makeMeasurementList(recv_info); + int id_request; + char *mac = (char *) malloc(18 * sizeof(char)); + ostringstream oss; + + PGresult *res; + + Treatment treat(pos.getAccessPointList(), pos.getReferencePointList()); + treat.makeMeasurementList(recv_info); + + sprintf(mac, "%02x:%02x:%02x:%02x:%02x:%02x", att_request.mobile_mac_addr_bytes[0],att_request.mobile_mac_addr_bytes[1], + att_request.mobile_mac_addr_bytes[2],att_request.mobile_mac_addr_bytes[3], + att_request.mobile_mac_addr_bytes[4],att_request.mobile_mac_addr_bytes[5]); + + oss << "SELECT r.id_request FROM request r, mobile m "; + oss << "WHERE r.mobile_time = " << timeval_to_ms(&att_request.request_time); + oss << " AND m.id_mobile = r.id_mobile"; + oss << " AND m.mobile_addr = '" << mac << "';"; + + res = PQexec(conn, oss.str().c_str()); + id_request = (PQntuples(res) != 0)? from_string(PQgetvalue(res, PQntuples(res) - 1, 0)): 0; + PQclear(res); /* Interlink Networks */ - solution = treat.interlink(point_list, 0) ; - cout << "Interlink Networks : "<< solution << endl; + solution = treat.interlink(0) ; + createResult(solution, id_request, "Interlink Network"); /* RADAR */ - solution = treat.getkClosestInSs(point_list, 1, NULL)[0] ; - cout << "RADAR : " << solution << endl; + solution = treat.getkClosestInSs(1, NULL)[0] ; + createResult(solution, id_request, "Radar"); /* FBCM */ - solution = treat.fbcm(point_list, 0) ; - cout << "FBCM : " << solution << endl; + solution = treat.fbcm(0) ; + createResult(solution, id_request, "FCBM"); /* 1-NSS + FBCM */ - solution = treat.getkClosestInSs(point_list, 1, NULL)[0] ; - solution = treat.fbcm_friis(point_list, treat.computeFriisFromRefList(solution, point_list), solution.getZ()) ; - cout << "1-NSS + FBCM : " << solution << endl; + solution = treat.getkClosestInSs(1, NULL)[0] ; + solution = treat.fbcm_friis(treat.computeFriisFromRefList(solution), solution.getZ()) ; + createResult(solution, id_request, "1-NSS + FBCM"); /* 2-NSS */ - solution = treat.getkWeightedInSs(point_list, 2, NULL); - cout << "2-NSS : " << solution << endl; + solution = treat.getkWeightedInSs(2, NULL); + createResult(solution, id_request, "2-NSS"); /* 3-NSS */ - solution = treat.getkWeightedInSs(point_list, 3, NULL); - cout << "3-NSS : " << solution << endl; + solution = treat.getkWeightedInSs(3, NULL); + createResult(solution, id_request, "3-NSS"); /* 5-NSS */ - solution = treat.getkWeightedInSs(point_list, 5, NULL); - cout << "5-NSS : " << solution << endl; + solution = treat.getkWeightedInSs(5, NULL); + createResult(solution, id_request, "5-NSS"); - cout << endl ; - - point_list.clear(); + sendToClient(solution, mac); + free(mac); } -void Server::makeMeasurementList(vector recv_info) +void Server::createResult(Point solution, int id_request, string use_algo) { - Measurement m; - bool inserted = false; + int id_result; + string buf; + ostringstream oss; - for (unsigned int i = 0; i < recv_info.size(); i++) - { + struct timeval current; - string mac_a = mac_bytes_to_string(recv_info.at(i).ap_mac_addr_bytes); - int value = recv_info.at(i).antenna_signal_dbm; + PGresult *res; - for (unsigned int j = 0 ; j < point_list.size() ; j++) - if (point_list[j].getMacAddr() == mac_a) - { - point_list[j].addSsValue(value); - inserted = true; - break; - } - if (inserted == false) - { - m.setMacAddr(mac_a); - m.addSsValue(value); - point_list.push_back(m); - } - } + gettimeofday(¤t, NULL); + + buf = "SELECT * FROM result;"; + + res = PQexec(conn, buf.c_str()); + id_result = (PQntuples(res) != 0)? from_string(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1: 1; + + oss << "INSERT INTO result(id_result, x, y, z, calcul_date, using_algo"; + if (id_request != 0) oss << ", id_request"; + oss << ") VALUES('"; + oss << id_result << "','" << solution.getX() << "','" << solution.getY() << "','" << solution.getZ(); + oss << "','" << timeval_to_ms(¤t) << "','" << use_algo; + if (id_request != 0) oss << "','" << id_request; + oss << "');"; + + PQexec(conn, oss.str().c_str()); + PQclear(res); +} + +void Server::sendToClient(Point solution, char *mac) +{ + + int sockfd ; // Descripteur de la socket + struct sockaddr_in serv; + struct sockaddr_in mobile; + socklen_t mobile_len = sizeof(mobile); + ostringstream oss; + float x,y,z; + + PGresult *res; + + oss << "SELECT ip_mobile FROM mobile "; + oss << "WHERE mobile_addr = '" << mac << "';"; + + res = PQexec(conn, oss.str().c_str()); + if (PQntuples(res) != 0) + { + /* Ceation de la socket UDP */ + sockfd = socket(AF_INET, SOCK_DGRAM, 0) ; + if (sockfd < 0) + { + cerr << "Échec de la création de la socket " << endl; + exit(1); + } + + /* Remise à zéro et initialisation de la structure du server */ + bzero((char *) &serv, sizeof(serv)) ; + serv.sin_family = AF_INET ; // Socket INET + serv.sin_addr.s_addr = htonl(INADDR_ANY) ; // Toutes les connexions + + /* Remise à zéro et initialisation de la structure du mobile */ + bzero((char *) &mobile, sizeof(mobile)) ; // RÀZ + mobile.sin_family = AF_INET ; // Socket INET + mobile.sin_addr.s_addr = inet_addr(PQgetvalue(res, 0, 0)) ; + mobile.sin_port = htons(mobile_port) ; + + x = solution.getX(); + y = solution.getY(); + z = solution.getZ(); + + sendto(sockfd, (void *)&x, sizeof(float), 0, (struct sockaddr *)&mobile, mobile_len); + sendto(sockfd, (void *)&y, sizeof(float), 0, (struct sockaddr *)&mobile, mobile_len); + sendto(sockfd, (void *)&z, sizeof(float), 0, (struct sockaddr *)&mobile, mobile_len); + + close(sockfd); + } + PQclear(res); } diff --git a/owlps-positioning/server.hh b/owlps-positioning/server.hh index 920bf00..c34b8c1 100644 --- a/owlps-positioning/server.hh +++ b/owlps-positioning/server.hh @@ -8,31 +8,13 @@ #include #include -#include -#include +#include -#include -#include -#include - -#include "positioning.hh" #include "point.hh" +#include "positioning.hh" #include "measurement.hh" #include "treatment.hh" - -using namespace std; - -typedef struct _couple_info - { - unsigned char ap_mac_addr_bytes[6]; // Adresse MAC de l'AP - int antenna_signal_dbm; // Puissance du signal reçu par l'AP - } couple_info; - -typedef struct _request - { - unsigned char ag_mac_addr_bytes[6]; // Adresse MAC de l'Aggregateur émetteur de la demande - int nb_couples; // Nombre couples (MAC AP;Puissance) - } request; +#include "libowlps-positioning.hh" class Server { @@ -41,26 +23,31 @@ class Server request att_request; vector recv_info; - int listen_socket; int listen_port; - struct sockaddr_in serv_addr; - struct sockaddr_in client; - socklen_t client_len; + int mobile_port; + int listen_socket; - Positioning calcul; - vector point_list; + PGconn *conn; + + Positioning pos; public: - Server(int); + Server(int port, int mport) + { + listen_port = port; + mobile_port = mport; + }; ~Server() { close(listen_socket); + PQfinish(conn); }; - int initFile(const string &, const string &, const string &, const string &); int start(); - void treatment(request, vector); - void makeMeasurementList(vector); + int init(const boost::program_options::variables_map); + void treatment(); + void createResult(Point, int, string); + void sendToClient(Point, char *); }; #endif diff --git a/owlps-positioning/treatment.cc b/owlps-positioning/treatment.cc index 085fb0f..0fd838f 100644 --- a/owlps-positioning/treatment.cc +++ b/owlps-positioning/treatment.cc @@ -40,7 +40,42 @@ unsigned int Treatment::apIndex(const string &ap_addr)const return 0; // Should never happen } -vector Treatment::getkClosestInSs(const vector &m, const unsigned int &k, const Point *point_ignored)const +void Treatment::makeMeasurementList(vector recv_info) +{ + + bool inserted = false; + Measurement measure; + char *ret = (char *)malloc(sizeof(char) * 18) ; + string mac_a; + int value; + + for (unsigned int i = 0; i < recv_info.size(); i++) + { + + sprintf(ret, "%02x:%02x:%02x:%02x:%02x:%02x", recv_info.at(i).ap_mac_addr_bytes[0], recv_info.at(i).ap_mac_addr_bytes[1], recv_info.at(i).ap_mac_addr_bytes[2], recv_info.at(i).ap_mac_addr_bytes[3], recv_info.at(i).ap_mac_addr_bytes[4], recv_info.at(i).ap_mac_addr_bytes[5]) ; + ret[17] = '\0'; + mac_a = ret; + value = recv_info.at(i).antenna_signal_dbm; + + for (unsigned int j = 0 ; j < m.size() ; j++) + if (m[j].getMacAddr() == mac_a) + { + m[j].addSsValue(value); + inserted = true; + break; + } + if (inserted == false) + { + measure.setMacAddr(mac_a); + measure.addSsValue(value); + m.push_back(measure); + } + } + + free(ret); +} + +vector Treatment::getkClosestInSs(const unsigned int &k, const Point *point_ignored)const { unsigned int i, j, min_idx; @@ -112,7 +147,7 @@ vector Treatment::getkClosestInSs(const vector &m, const uns return points_vector; } -Point Treatment::fbcm(const vector &m, const int &client_idx)const +Point Treatment::fbcm(const int &client_idx)const { Point ret(0, 0, 0); @@ -169,7 +204,7 @@ Point Treatment::fbcm(const vector &m, const int &client_idx)const return ret; } -Point Treatment::fbcm_friis( const vector &m, const vector friis_idx_list, const float &z)const +Point Treatment::fbcm_friis(const vector friis_idx_list, const float &z)const { Point ret(0, 0, 0); @@ -224,7 +259,7 @@ Point Treatment::fbcm_friis( const vector &m, const vector f return ret; } -Point Treatment::interlink(const vector &m, const int &client_idx) const +Point Treatment::interlink(const int &client_idx) const { Point ret(0, 0, 0); @@ -276,7 +311,7 @@ Point Treatment::interlink(const vector &m, const int &client_idx) return ret; } -vector Treatment::computeFriisFromRefList(const Point &p, const vector &m) +vector Treatment::computeFriisFromRefList(const Point &p) { vector friis_idx_list; @@ -322,7 +357,7 @@ vector Treatment::computeFriisFromRefList(const Point &p, const vector &m, const unsigned int &k, const Point *point_ignored)const +Point Treatment::getkWeightedInSs(const unsigned int &k, const Point *point_ignored)const { unsigned int i, j; diff --git a/owlps-positioning/treatment.hh b/owlps-positioning/treatment.hh index 333940b..9e300e5 100644 --- a/owlps-positioning/treatment.hh +++ b/owlps-positioning/treatment.hh @@ -1,26 +1,11 @@ #ifndef _TREATMENT_HH_ #define _TREATMENT_HH_ -#include -#include -#include -#include - #include "point.hh" #include "measurement.hh" #include "accesspoint.hh" #include "referencepoint.hh" - -#define LIGHT_SPEED 300000000 -#define MINMAX_STEP 0.5 -#define MINMAX_X_START 0.5 -#define MINMAX_Y_START 0.5 -#define MINMAX_Z_START 0 -#define MINMAX_X_STOP 10 -#define MINMAX_Y_STOP 31.5 -#define MINMAX_Z_STOP 6 - -using namespace std; +#include "libowlps-positioning.hh" class Treatment { @@ -28,6 +13,7 @@ class Treatment private: vector access_point_list; vector reference_point_list; + vector m; public: Treatment(vector access_point, vector reference_point) @@ -38,20 +24,23 @@ class Treatment ~Treatment() { access_point_list.clear(); + m.clear(); + reference_point_list.clear(); }; bool apExists(const string &)const; unsigned int apIndex(const string &)const; + void makeMeasurementList(vector); - vector getkClosestInSs(const vector &m, const unsigned int &k, const Point *point_ignored)const; + vector getkClosestInSs(const unsigned int &k, const Point *point_ignored)const; Point kPointsAverage(const vector &vp)const; - Point fbcm(const vector &m, const int &client_idx)const; - Point fbcm_friis( const vector &m, const vector friis_idx_list, const float &z)const; - Point interlink(const vector &m, const int &client_idx)const; + Point fbcm(const int &client_idx)const; + Point fbcm_friis(const vector friis_idx_list, const float &z)const; + Point interlink(const int &client_idx)const; - vector computeFriisFromRefList(const Point &p, const vector &m); - Point getkWeightedInSs(const vector &m, const unsigned int &k, const Point *point_ignored)const ; + vector computeFriisFromRefList(const Point &p); + Point getkWeightedInSs(const unsigned int &k, const Point *point_ignored)const ; }; #endif diff --git a/writeInDb/writeindb.cc b/writeInDb/writeindb.cc new file mode 100644 index 0000000..b383aea --- /dev/null +++ b/writeInDb/writeindb.cc @@ -0,0 +1,593 @@ +#include "writeindb.hh" + +template +inline T from_string(const string &s) +{ + + T t; + istringstream iss(s); + + iss >> t; + + return t; +} + +inline string stringToLower(string strToConvert) +{ + + for (unsigned int i=0; i < strToConvert.length(); i++) + { + strToConvert[i] = tolower(strToConvert[i]); + } + + return strToConvert; +} + +inline vector explode(const string &input, const char &sep) +{ + vector vs; + string tmp; + unsigned int i; + + for (i = 0 ; i < input.size() ; i++) + if (input[i] == sep) + { + vs.push_back(tmp); + tmp.clear(); + } + else + { + tmp.push_back(input[i]); + } + + vs.push_back(tmp); + tmp.clear(); + + return vs; +} + +inline vector extractReferencePointInfoFromBuffer(const string &buffer_in) +{ + unsigned int i = 0; + string tmp_field; + vector ret; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; // go after the ';' + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (buffer_in[i] != ';') + { + tmp_field.push_back(buffer_in[i]); + i++; + } + ret.push_back(tmp_field); + tmp_field.clear(); + i++; + + while (i <= buffer_in.size()) + { + if ((buffer_in[i] == ';' || i == buffer_in.size()) && !tmp_field.empty()) // Si on est sur un séparateur et que la valeur lue n'est pas vide, + { + ret.push_back(tmp_field) ; // on met la valeur lue dans les valeurs de retour. + tmp_field.clear() ; + } + else // Si on n'est pas sur un séparateur, + tmp_field.push_back(buffer_in[i]) ; // on ajoute le caractère courant à la suite de la valeur lue. + + i++ ; + } + + return ret; +} + +void WriteInDb::makeReferencePointListFromFile(const string &filename, const bool uniq_point) +{ + + ifstream input_file ; // Flux d'entrée du fichier. + string cpp_buffer ; // Buffer au format string. + ReferencePoint rp; + Point tmp_point; + float x, y, z ; // Coordonnées des points. + unsigned int pt_idx = 0 ; // Position du point lu dans la liste. + int direction; + vector infos ; // Liste des informations lues dans une ligne du fichier. + + input_file.open(filename.c_str()) ; + if (input_file.fail()) + { + cerr << "Error opening input file « " << filename << " » !" << endl ; + return ; + } + + while (!input_file.eof()) + { + getline(input_file, cpp_buffer); + + if ((input_file.rdstate() & ifstream::eofbit) == 0) + { + if (cpp_buffer.size() == 0) // Ignorer une ligne vide + continue ; + + infos = extractReferencePointInfoFromBuffer(cpp_buffer); + x = from_string(infos[0]); + y = from_string(infos[1]); + z = from_string(infos[2]); + + tmp_point.setX(x); + tmp_point.setY(y); + tmp_point.setZ(z); + direction = from_string(infos[3]); + + if (!uniq_point || !pointExists(reference_point_list, tmp_point)) // Si on ne veut pas de points unique, ou que le point n'existe pas encore, + { + rp.setCoordinates(tmp_point); + reference_point_list.push_back(rp); // on le crée. + pt_idx = reference_point_list.size() - 1; // Le point que l'on vient d'ajouter est le dernier du vector. + } + else // Le point existe déjà : + { + pt_idx = pointIndex(reference_point_list, tmp_point) ; // On recherche le point auquel on veut ajouter les informations. + } + + for (unsigned int i = 4; i < infos.size(); i++) + { + if (i+1 < infos.size()) + { + reference_point_list[pt_idx].addMeasurement(infos[i], from_string(infos[i+1])); + i++; + } + } + } + } + + input_file.close(); + infos.clear() ; +} + +void WriteInDb::makeApListFromFile(const string &filename) +{ + + ifstream input_file; + string buffer; + vector ap_infos; + AccessPoint tmp_ap; + + input_file.open(filename.c_str()); + if (input_file.fail()) + { + cerr << "Error opening input file « " << filename << " » !" << endl ; + return ; + } + + while (!input_file.eof()) + { + getline(input_file, buffer); + + if ((input_file.rdstate() & ifstream::eofbit) == 0) + { + if (buffer[0] == '\0' || buffer[0] == '#') // ligne vide ou ligne commençant par # + continue; + + ap_infos = explode(buffer, ';'); + tmp_ap.setApAddr(ap_infos[0]); + tmp_ap.setCoordinates(from_string(ap_infos[1]), from_string(ap_infos[2]), from_string(ap_infos[3])); + tmp_ap.setFrequency(from_string(ap_infos[4])); + tmp_ap.setAntennaGain(from_string(ap_infos[5])); + tmp_ap.setOutputPower(from_string(ap_infos[6])); + access_point_list.push_back(tmp_ap); + ap_infos.clear(); + } + } + + input_file.close(); +} + +void WriteInDb::makeTopologyFromFile(const string &filename) +{ + + ifstream input_file; + string buffer; + vector infos; + + input_file.open(filename.c_str()) ; + if (input_file.fail()) + { + cerr << "Error opening input file « " << filename << " » !" << endl ; + return ; + } + + while (!input_file.eof()) + { + getline(input_file, buffer) ; + + if ((input_file.rdstate() & ifstream::eofbit) == 0) + { + /* Traitement basique des commentaires */ + if (buffer[0] == '\0' || buffer[0] == '#') // ligne vide ou ligne commençant par # + continue ; // ignorer cette ligne. + + infos = explode(buffer, ';') ; + if (area_list.find(infos[0]) != area_list.end()) // Si la pièce existe déjà, + cerr << "Erreur ! Déclaration multiple de la zone « " << infos[0] << " »." << endl ; // on le signale ; + else // sinon on l'ajoute : + area_list[infos[0]] = Area(infos[0], from_string(infos[1]), from_string(infos[3]), + from_string(infos[2]), from_string(infos[4]), + from_string(infos[5]), from_string(infos[6])) ; + + infos.clear() ; + } + } + + input_file.close() ; + +} + +void WriteInDb::makeWaypointListFromFile(const string &filename) +{ + + ifstream input_file ; + string buffer; + vector infos ; + + input_file.open(filename.c_str()); + if (input_file.fail()) + { + cerr << "Error opening input file « " << filename << " » !" << endl ; + return ; + } + + while (!input_file.eof()) + { + getline(input_file, buffer); + + if ((input_file.rdstate() & ifstream::eofbit) == 0) + { + if (buffer[0] == '\0' || buffer[0] == '#') // ligne vide ou ligne commençant par # + continue; + + infos = explode(buffer, ';') ; + + Point tmp_pt(from_string(infos[0]), from_string(infos[1]), from_string(infos[2])); + waypoint_list.push_back(tmp_pt); + + infos.clear() ; + } + } + input_file.close(); // Lecture du fichier terminée +} + +void WriteInDb::writeAccessPointToDb(PGconn *conn) +{ + + PGresult *res; + + ostringstream oss; + string buf; + bool exist = false; + string addr_files; + + buf = "SELECT * FROM ap;"; + res = PQexec(conn, buf.c_str()); + + for (unsigned int i = 0; i < access_point_list.size(); i++) + { + addr_files = stringToLower(access_point_list[i].getApAddr()); + if (PQresultStatus(res) == PGRES_TUPLES_OK) + { + int nbRes = PQntuples(res); + for (int j = 0; j < nbRes; j++) + { + if (addr_files == PQgetvalue(res, i, 1)) + exist = true; + } + } + + if (exist) + { + oss << "UPDATE ap SET x = '" << access_point_list[i].getCoordinates().getX() << "','"; + oss << "y = '" << access_point_list[i].getCoordinates().getY() << "','"; + oss << "z = '" << access_point_list[i].getCoordinates().getZ() << "','"; + oss << "friis_index = '" << access_point_list[i].getFriisIndex() << "','"; + oss << "freq = '" << access_point_list[i].getFrequency() << "','"; + oss << "antenna_gain = '" << access_point_list[i].getAntennaGain() << "','"; + oss << "output_power = '" << access_point_list[i].getOutputPower(); + oss << " WHERE ap_addr = '" << addr_files << ";"; + } + else + { + oss << "INSERT INTO ap(ap_addr,x,y,z,friis_index,freq,antenna_gain,output_power) VALUES('"; + oss << addr_files << "','"; + oss << access_point_list[i].getCoordinates().getX() << "','"; + oss << access_point_list[i].getCoordinates().getY() << "','"; + oss << access_point_list[i].getCoordinates().getZ() << "','"; + oss << access_point_list[i].getFriisIndex() << "','"; + oss << access_point_list[i].getFrequency() << "','"; + oss << access_point_list[i].getAntennaGain() << "','"; + oss << access_point_list[i].getOutputPower() << "');"; + } + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + exist = false; + } + PQclear(res); +} + +void WriteInDb::writeWaypointToDb(PGconn *conn) +{ + ostringstream oss; + string buf; + + for (unsigned int i = 0; i < waypoint_list.size(); i++) + { + oss << "INSERT INTO waypoint VALUES('"; + oss << waypoint_list[i].getX() << "','"; + oss << waypoint_list[i].getY() << "','"; + oss << waypoint_list[i].getZ() << "');"; + + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + } +} + +int WriteInDb::writePointToDb(PGconn *conn, Point p) +{ + + ostringstream oss; + string buf; + int id_point = -1; + + PGresult *res; + + oss << "SELECT * FROM ref_point "; + oss << "WHERE x = " << p.getX(); + oss << " AND y = " << p.getY(); + oss << " AND z = " << p.getZ(); + + buf = oss.str(); + oss.str(""); + + res = PQexec(conn, buf.c_str()); + if (PQntuples(res) == 0) + { + PQclear(res); + buf = "SELECT * FROM ref_point;"; + res = PQexec(conn, buf.c_str()); + id_point = (PQntuples(res) != 0)? from_string(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1: 1; + + oss << "INSERT INTO ref_point(id_ref_point,x,y,z,direction) VALUES('"; + oss << id_point << "','"; + oss << p.getX() << "','"; + oss << p.getY() << "','"; + oss << p.getZ() << "','"; + oss << " " << "');"; + + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + } + else + { + id_point = from_string(PQgetvalue(res, 0, 0)); + } + + return id_point; +} + +void WriteInDb::writeReferencePointToDb(PGconn *conn) +{ + + ostringstream oss; + string buf; + PGresult *res; + + struct timeval current_time ; + int id_point, id_ap, id_request; + + vector m_list; + vector ss_list; + + for (unsigned int i = 0; i < reference_point_list.size(); i++) + { + buf = "SELECT * FROM ref_request;"; + res = PQexec(conn, buf.c_str()); + id_request = (PQntuples(res) != 0)? from_string(PQgetvalue(res, PQntuples(res) - 1, 0)) + 1: 1; + + id_point = writePointToDb(conn, reference_point_list[i].getCoordinates()); + oss << "INSERT INTO ref_request(id_ref_request, id_ref_point) VALUES('"; + oss << id_request << "','"; + oss << id_point << "');"; + + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + + m_list = reference_point_list[i].getMeasurementList(); + for (unsigned int j = 0; j < m_list.size(); j++) + { + oss << "SELECT id_ap FROM ap WHERE ap_addr = '"; + oss << stringToLower(m_list[j].getMacAddr()) << "';"; + + buf = oss.str(); + oss.str(""); + + PQclear(res); + res = PQexec(conn, buf.c_str()); + id_ap = from_string(PQgetvalue(res, 0, 0)); + + ss_list = m_list[j].getSsList(); + for (unsigned int k = 0; k < ss_list.size(); k++) + { + oss << "INSERT INTO ref_packet(power, id_ap, id_ref_request) VALUES('"; + oss << ss_list[k] << "','"; + oss << id_ap << "','"; + oss << id_request << "');"; + + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + } + } + } + PQclear(res); +} + +void WriteInDb::writeTopologyToDb(PGconn *conn) +{ + + ostringstream oss; + string buf; + PGresult *res; + + bool exist = false; + + buf = "SELECT * from area;"; + res = PQexec(conn, buf.c_str()); + + for (map::iterator it = area_list.begin() ; it != area_list.end() ; it++) + { + if (PQresultStatus(res) == PGRES_TUPLES_OK) + { + int nbRes = PQntuples(res); + for (int j = 0; j < nbRes; j++) + { + if (it -> second.getName() == PQgetvalue(res, j, 1)) + exist = true; + } + } + + if (!exist) + { + oss << "INSERT INTO area(name_area,x_min,y_min,z_min,x_max,y_max,z_max) VALUES ('"; + oss << it -> second.getName() << "','"; + oss << it -> second.getXmin() << "','"; + oss << it -> second.getYmin() << "','"; + oss << it -> second.getZmin() << "','"; + oss << it -> second.getXmax() << "','"; + oss << it -> second.getYmax() << "','"; + oss << it -> second.getZmax() << "');"; + + buf = oss.str(); + oss.str(""); + + PQexec(conn, buf.c_str()); + } + + exist = false; + } + + PQclear(res); +} + +inline bool WriteInDb::pointExists(const vector &point_list, const Point &p) const + { + return (pointIndex(point_list, p) != -1); + } + +inline int WriteInDb::pointIndex(const vector &point_list, const Point &p) const + { + unsigned int i; + + for (i = 0 ; i < point_list.size() ; i++) + if (p == point_list[i].getCoordinates()) + { + return i; + } + + return -1; + } + +int main(int argc, char **argv) +{ + + WriteInDb w; + + po::options_description desc("Options"); + po::variables_map vm; + + desc.add_options() + ("help", "\t: Affichage de l'aide") + ("input-topo,T", po::value(), "\t: Input file topology") + ("input-waypoint,W", po::value(), "\t: Input file waypoint") + ("input-refpoint,R", po::value(), "\t: Input file reference point") + ("input-ap,A", po::value(), "\t: Input file accesspoint") + ; + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + cout << desc << endl; + return 0; + } + + const char *conninfo = "hostaddr = '127.0.0.1' dbname = 'owlps_db' user = 'julien' password = '10,mamci'"; + PGconn *conn; + + conn = PQconnectdb(conninfo); + + if (PQstatus(conn) != CONNECTION_OK) + { + cout << "Connection à la base de donnée échouée: " << PQerrorMessage(conn) << endl; + PQfinish(conn); + return 1; + } + + if (vm.count("input-ap")) + { + w.makeApListFromFile(vm["input-ap"].as()); + w.writeAccessPointToDb(conn); + } + + if (vm.count("input-topo")) + { + w.makeTopologyFromFile(vm["input-topo"].as()); + w.writeTopologyToDb(conn); + } + + if (vm.count("input-waypoint")) + { + w.makeWaypointListFromFile(vm["input-waypoint"].as()); + w.writeWaypointToDb(conn); + } + + if (vm.count("input-refpoint")) + { + w.makeReferencePointListFromFile(vm["input-refpoint"].as(), true); + w.writeReferencePointToDb(conn); + } + + PQfinish(conn); + return 0; +} diff --git a/writeInDb/writeindb.hh b/writeInDb/writeindb.hh new file mode 100644 index 0000000..f06d19b --- /dev/null +++ b/writeInDb/writeindb.hh @@ -0,0 +1,54 @@ +#ifndef _WRITEINDB_HH_ +#define _WRITEINDB_HH_ + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "../referencepoint.hh" +#include "../point.hh" +#include "../accesspoint.hh" +#include "../area.hh" +#include "../measurement.hh" + +#include +#include + +using namespace std; +namespace po = boost::program_options; + +class WriteInDb + { + + private: + vector reference_point_list; + vector access_point_list; + vector waypoint_list; + map area_list; + + public: + WriteInDb() {}; + ~WriteInDb() {}; + + void makeReferencePointListFromFile(const string &filename, const bool); + void makeApListFromFile(const string &filename); + void makeTopologyFromFile(const string &filename); + void makeWaypointListFromFile(const string &filename); + + void writeAccessPointToDb(PGconn*); + void writeWaypointToDb(PGconn*); + int writePointToDb(PGconn *conn, Point p); + void writeReferencePointToDb(PGconn*); + void writeTopologyToDb(PGconn*); + + bool pointExists(const vector &point_list, const Point &p) const ; + int pointIndex(const vector &point_list, const Point &p) const ; + }; + +#endif