/**************************************************************************/ /* */ /* P2 - MI amb sockets TCP/IP - Part II */ /* Fitxer lumi.c que implementa la capa d'aplicació de LUMI, sobre la */ /* de transport UDP (fent crides a la interfície de la capa UDP */ /* -sockets-). */ /* */ /* Autors: Marc Cané Salamià, Enric Rodríguez Galán */ /* */ /**************************************************************************/ /* Inclusió de llibreries, p.e. #include o #include "meu.h" */ /* (si les funcions externes es cridessin entre elles, faria falta fer */ /* un #include "MIp2-lumi.h") */ #include #include #include #include #include #include #include #include #include #include #include #include #include "MIp2-lumi.h" /* Definició de constants, p.e., #define MAX_LINIA 150 */ #define RETRANSMISSIONS 10 #define TIMEOUT 100 /* Declaració de funcions internes que es fan servir en aquest fitxer */ /* (les seves definicions es troben més avall) per així fer-les conegudes */ /* des d'aqui fins al final de fitxer. */ /* Com a mínim heu de fer les següents funcions internes: */ int UDP_CreaSock(const char *IPloc, int portUDPloc); int UDP_EnviaA(int Sck, const char *IPrem, int portUDPrem, const char *SeqBytes, int LongSeqBytes); int UDP_RepDe(int Sck, char *IPrem, int *portUDPrem, char *SeqBytes, int LongSeqBytes); int UDP_TancaSock(int Sck); int UDP_TrobaAdrSockLoc(int Sck, char *IPloc, int *portUDPloc); int UDP_DemanaConnexio(int Sck, const char *IPrem, int portUDPrem); int UDP_Envia(int Sck, const char *SeqBytes, int LongSeqBytes); int UDP_Rep(int Sck, char *SeqBytes, int LongSeqBytes); int UDP_TrobaAdrSockRem(int Sck, char *IPrem, int *portUDPrem); ///int HaArribatAlgunaCosaEnTemps(const int *LlistaSck, int LongLlistaSck, int Temps); ///int ResolDNSaIP(const char *NomDNS, char *IP); int Log_CreaFitx(const char *NomFitxLog); int Log_Escriu(int FitxLog, const char *MissLog); int Log_TancaFitx(int FitxLog); int LUMI_DescodificarSockTCPMissatgeC(const char * Missatge, char * IP, int * portTCP, char * adreca); /* Definicio de funcions EXTERNES, és a dir, d'aquelles que en altres */ /* fitxers externs es faran servir. */ /* En termes de capes de l'aplicació, aquest conjunt de funcions externes */ /* formen la interfície de la capa LUMI. */ /* Les funcions externes les heu de dissenyar vosaltres... */ /* Definicio de funcions INTERNES, és a dir, d'aquelles que es faran */ /* servir només en aquest mateix fitxer. */ /* Crea un socket UDP a l’@IP “IPloc” i #port UDP “portUDPloc” */ /* (si “IPloc” és “0.0.0.0” i/o “portUDPloc” és 0 es fa/farà una */ /* assignació implícita de l’@IP i/o del #port UDP, respectivament). */ /* "IPloc" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud màxima de 16 chars (incloent '\0') */ /* Retorna -1 si hi ha error; l’identificador del socket creat si tot */ /* va bé. */ int UDP_CreaSock(const char *IPloc, int portUDPloc) { int sockdesc; if ((sockdesc = socket(AF_INET,SOCK_DGRAM,0)) == -1){ LUMI_MostraError("Error creació socket"); return -1; } else{ struct sockaddr_in adr; adr.sin_family = AF_INET; adr.sin_addr.s_addr = inet_addr(IPloc); adr.sin_port = htons(portUDPloc); int i; for(i=0;i<8;i++){adr.sin_zero[i]='0';} if (bind(sockdesc,(struct sockaddr*)&adr,sizeof(adr))==-1){ LUMI_MostraError("Error bind"); return -1; } } return sockdesc; } /* Envia a través del socket UDP d’identificador “Sck” la seqüència de */ /* bytes escrita a “SeqBytes” (de longitud “LongSeqBytes” bytes) cap al */ /* socket remot que té @IP “IPrem” i #port UDP “portUDPrem”. */ /* "IPrem" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud màxima de 16 chars (incloent '\0') */ /* "SeqBytes" és un vector de chars qualsevol (recordeu que en C, un */ /* char és un enter de 8 bits) d'una longitud >= LongSeqBytes bytes */ /* Retorna -1 si hi ha error; el nombre de bytes enviats si tot va bé. */ int UDP_EnviaA(int Sck, const char *IPrem, int portUDPrem, const char *SeqBytes, int LongSeqBytes) { struct sockaddr_in adrrem; adrrem.sin_family=AF_INET; adrrem.sin_port=htons(portUDPrem); adrrem.sin_addr.s_addr= inet_addr(IPrem); int i; for(i=0;i<8;i++){adrrem.sin_zero[i]='\0';} int bytes_llegits; if((bytes_llegits=sendto(Sck,SeqBytes,LongSeqBytes,0,(struct sockaddr*)&adrrem,sizeof(adrrem)))==-1) { perror("Error en sendto"); close(Sck); return(-1); } return bytes_llegits; } /* Rep a través del socket UDP d’identificador “Sck” una seqüència de */ /* bytes que prové d'un socket remot i l’escriu a “SeqBytes*” (que té */ /* una longitud de “LongSeqBytes” bytes). */ /* Omple "IPrem*" i "portUDPrem*" amb respectivament, l'@IP i el #port */ /* UDP del socket remot. */ /* "IPrem*" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud màxima de 16 chars (incloent '\0') */ /* "SeqBytes*" és un vector de chars qualsevol (recordeu que en C, un */ /* char és un enter de 8 bits) d'una longitud <= LongSeqBytes bytes */ /* Retorna -1 si hi ha error; el nombre de bytes rebuts si tot va bé. */ int UDP_RepDe(int Sck, char *IPrem, int *portUDPrem, char *SeqBytes, int LongSeqBytes) { struct sockaddr_in adrrem; socklen_t ladrrem = sizeof(adrrem); int bytes_llegits; if((bytes_llegits=recvfrom(Sck,SeqBytes,LongSeqBytes,0,(struct sockaddr*)&adrrem,&ladrrem))==-1) { perror("Error recvfrom\n"); close(Sck); return -1; } strcpy(IPrem, inet_ntoa(adrrem.sin_addr)); *portUDPrem = ntohs(adrrem.sin_port); return bytes_llegits; } /* S’allibera (s’esborra) el socket UDP d’identificador “Sck”. */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé. */ int UDP_TancaSock(int Sck) { return close(Sck); } /* Donat el socket UDP d’identificador “Sck”, troba l’adreça d’aquest */ /* socket, omplint “IPloc*” i “portUDPloc*” amb respectivament, la seva */ /* @IP i #port UDP. */ /* "IPloc*" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud màxima de 16 chars (incloent '\0') */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé. */ int UDP_TrobaAdrSockLoc(int Sck, char *IPloc, int *portUDPloc) { struct sockaddr_in sin; socklen_t slen; slen = sizeof(sin); if(getsockname(Sck, (struct sockaddr *)&sin, &slen)){ LUMI_MostraError("Error al trobar la direccio local"); return -1; } *portUDPloc = ntohs(sin.sin_port); strcpy(IPloc, inet_ntoa(sin.sin_addr)); return 1; } /* El socket UDP d’identificador “Sck” es connecta al socket UDP d’@IP */ /* “IPrem” i #port UDP “portUDPrem” (si tot va bé es diu que el socket */ /* “Sck” passa a l’estat “connectat” o establert – established –). */ /* Recordeu que a UDP no hi ha connexions com a TCP, i que això només */ /* vol dir que es guarda localment l’adreça “remota” i així no cal */ /* especificar-la cada cop per enviar i rebre. Llavors quan un socket */ /* UDP està “connectat” es pot fer servir UDP_Envia() i UDP_Rep() (a més */ /* de les anteriors UDP_EnviaA() i UDP_RepDe()) i UDP_TrobaAdrSockRem()). */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé. */ int UDP_DemanaConnexio(int Sck, const char *IPrem, int portUDPrem) { struct sockaddr_in adr; adr.sin_family = AF_INET; adr.sin_addr.s_addr = inet_addr(IPrem); adr.sin_port = htons(portUDPrem); int i; for(i=0;i<8;i++){adr.sin_zero[i]='0';} if((connect(Sck,(struct sockaddr*)&adr,sizeof(adr)))==-1){ char buff[100]; snprintf(buff, sizeof(buff), "Error: no s'ha pogut connectar amb %s", IPrem); LUMI_MostraError(buff); return -1; } return 0; } /* Envia a través del socket UDP “connectat” d’identificador “Sck” la */ /* seqüència de bytes escrita a “SeqBytes” (de longitud “LongSeqBytes” */ /* bytes) cap al socket UDP remot amb qui està connectat. */ /* "SeqBytes" és un vector de chars qualsevol (recordeu que en C, un */ /* char és un enter de 8 bits) d'una longitud >= LongSeqBytes bytes. */ /* Retorna -1 si hi ha error; el nombre de bytes enviats si tot va bé. */ int UDP_Envia(int Sck, const char *SeqBytes, int LongSeqBytes) { return send(Sck,SeqBytes,LongSeqBytes,0); } /* Rep a través del socket UDP “connectat” d’identificador “Sck” una */ /* seqüència de bytes que prové del socket remot amb qui està connectat, */ /* i l’escriu a “SeqBytes*” (que té una longitud de “LongSeqBytes” bytes).*/ /* "SeqBytes*" és un vector de chars qualsevol (recordeu que en C, un */ /* char és un enter de 8 bits) d'una longitud <= LongSeqBytes bytes. */ /* Retorna -1 si hi ha error; el nombre de bytes rebuts si tot va bé. */ int UDP_Rep(int Sck, char *SeqBytes, int LongSeqBytes) { return recv(Sck,SeqBytes,LongSeqBytes,0); } /* Donat el socket UDP “connectat” d’identificador “Sck”, troba l’adreça */ /* del socket remot amb qui està connectat, omplint “IPrem*” i */ /* “portUDPrem*” amb respectivament, la seva @IP i #port UDP. */ /* "IPrem*" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud màxima de 16 chars (incloent '\0'). */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé. */ int UDP_TrobaAdrSockRem(int Sck, char *IPrem, int *portUDPrem) { struct sockaddr_in adr; socklen_t long_adr = sizeof(adr); int res; if ( (res = getpeername(Sck, (struct sockaddr*)&adr, &long_adr)) == -1) { LUMI_MostraError("Error al trobar la direccio remota"); return -1; } strcpy(IPrem,inet_ntoa(adr.sin_addr)); *portUDPrem = ntohs(adr.sin_port); return res; } /* Examina simultàniament durant "Temps" (en [ms] els sockets (poden ser */ /* TCP, UDP i stdin) amb identificadors en la llista “LlistaSck” (de */ /* longitud “LongLlistaSck” sockets) per saber si hi ha arribat alguna */ /* cosa per ser llegida. Si Temps és -1, s'espera indefinidament fins que */ /* arribi alguna cosa. */ /* "LlistaSck" és un vector d'enters d'una longitud >= LongLlistaSck */ /* Retorna -1 si hi ha error; retorna -2 si passa "Temps" sense que */ /* arribi res; si arriba alguna cosa per algun dels sockets, retorna */ /* l’identificador d’aquest socket. */ int HaArribatAlgunaCosaEnTemps(const int *LlistaSck, int LongLlistaSck, int Temps) { struct timeval timeout; timeout.tv_sec = Temps/1000; timeout.tv_usec = (Temps%1000)*1000; //estructura per definir un timeout al select fd_set set; FD_ZERO(&set); int i = 0; while (i 0){ int res; if ((res = select(smax,&set,NULL,NULL,&timeout)) == -1){ LUMI_MostraError("Error a la espera d'arribar alguna cosa"); return -1; } if(res == 0) return 0; } else if (select(smax,&set,NULL,NULL,NULL) == -1){ LUMI_MostraError("Error a la espera d'arribar alguna cosa"); return -1; } int ifd=0; while( ifd < LongLlistaSck && !FD_ISSET(LlistaSck[ifd],&set) ) ifd++; return LlistaSck[ifd]; } /* Donat el nom DNS "NomDNS" obté la corresponent @IP i l'escriu a "IP*" */ /* "NomDNS" és un "string" de C (vector de chars imprimibles acabat en */ /* '\0') d'una longitud qualsevol, i "IP*" és un "string" de C (vector de */ /* chars imprimibles acabat en '\0') d'una longitud màxima de 16 chars */ /* (incloent '\0'). */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé */ int ResolDNSaIP(const char *NomDNS, char *IP) { struct addrinfo hints, *infoptr; memset(&hints, 0, sizeof(struct addrinfo)); hints.ai_family = AF_INET; // AF_INET perquè només volem adreces IPv4 int result = getaddrinfo(NomDNS, NULL, &hints, &infoptr); if (result != 0) { fprintf(stderr, "Error a getaddrinfo\n%s\n",gai_strerror(result)); return(-1); } struct addrinfo *p; char host[256]; p = infoptr; result = getnameinfo(p->ai_addr, p->ai_addrlen, host, sizeof(host), NULL, 0, NI_NUMERICHOST); if (result != 0) { fprintf(stderr, "Error a getnameinfo\n"); return(-1); } strcpy(IP, host); freeaddrinfo(infoptr); return 0; } /* Crea un fitxer de "log" de nom "NomFitxLog". */ /* "NomFitxLog" és un "string" de C (vector de chars imprimibles acabat */ /* en '\0') d'una longitud qualsevol. */ /* Retorna -1 si hi ha error; l'identificador del fitxer creat si tot va */ /* bé. */ int Log_CreaFitx(const char *NomFitxLog) { int filedesc = open(NomFitxLog, O_APPEND|O_CREAT, 0666); if (filedesc < 0){ LUMI_MostraError("Error al crear el fitxer Log"); return -1; } return filedesc; } /* Escriu al fitxer de "log" d'identificador "FitxLog" el missatge de */ /* "log" "MissLog". */ /* "MissLog" és un "string" de C (vector de chars imprimibles acabat */ /* en '\0') d'una longitud qualsevol. */ /* Retorna -1 si hi ha error; el nombre de caràcters del missatge de */ /* "log" (sense el '\0') si tot va bé */ int Log_Escriu(int FitxLog, const char *MissLog) { int lMiss = strlen(MissLog); char buff[lMiss]; strcpy(buff,MissLog); //buff[lMiss-1] = '\n'; /*int res = write(FitxLog,MissLog,strlen(MissLog)-1); if (res < 0) return res;*/ return write(FitxLog,buff,sizeof(buff)); } /* Tanca el fitxer de "log" d'identificador "FitxLog". */ /* Retorna -1 si hi ha error; un valor positiu qualsevol si tot va bé. */ int Log_TancaFitx(int FitxLog) { return close(FitxLog); } void LUMI_MostraError(const char *text) { fprintf(stderr, "%s\n", text); } /* Si ho creieu convenient, feu altres funcions... */ int LUMI_InicialitzarNode(const char * fitxer_log){ //printf("%s\n",fitxer_log); LUMI_Fitxer_Log = Log_CreaFitx(fitxer_log); //el nom del fitxer ha de portar el nom del domini return UDP_CreaSock("0.0.0.0",UDP_PORT); } int LUMI_InicialitzarAgent(const char * IP, int portUDP, int * fitxer_log, const char * adrLUMI, char * IPnode){ int res = UDP_CreaSock(IP,portUDP); if (res < 0 ) return res; char nickname[MAX_USER_NICK], domini[MAX_LEN_DOMINI]; LUMI_DescodificarAdreca(adrLUMI, nickname, domini); //printf("nick: %s, domini: %s",nickname,domini); if (ResolDNSaIP(domini, IPnode) < 0) return -1; if (UDP_DemanaConnexio(res, IPnode, UDP_PORT) < 0) return -1; char nom_fitxer[MAX_NOM_FITXER]; LUMI_ResolNomFitxerLog('A', nom_fitxer, adrLUMI); if ( (*fitxer_log = Log_CreaFitx(nom_fitxer)) < 0 ) return -2; return res; } int LUMI_ResolNomFitxerLog(char tipus, char * fitxer_log, const char * buffer){ if (tipus == 'A' ) strcpy(fitxer_log, NOM_FITXER_AGENT); else if (tipus == 'N') strcpy(fitxer_log, NOM_FITXER_NODE); else return 1; strcat(fitxer_log, buffer); strcat(fitxer_log, EXT_FITXER_LOG); return 0; } int LUMI_EnviaFiable(int Sck, const char * Missatge, char * resposta, int timeout){ int intents = 0, enviat = 0, res, retorn; int llist[] = {Sck}; while(!enviat && intents 0 ){ //Si hem rebut algo, comprovem si es una A (resposta) char buff[MAX_MISSATGE_PLUMI]; int longitud = UDP_Rep(Sck, buff, sizeof(buff)); buff[longitud]='\0'; if(LUMI_ComprovarFormat(buff) != 0) return -6; if (buff[0] == 'A'){ switch(buff[1]){ case 'K': retorn = 0; break; case 'I': retorn = -2; break; case 'N': retorn = -3; break; case 'C': retorn = -7; break; default: retorn = -4; break; } enviat = 1; //Si es una resposta, vol dir que el destinatari ha rebut be el paquet } else if (buff[0]== 'C') {retorn = 1; enviat = 1;} if (resposta != NULL) strcpy(resposta, buff); }//else printf("%s. Intent %i\n", "TIMEOUT EXPIRED", intents);//LUMI_MostraError("TIMEOUT EXPIRED\n"); intents++; } if (enviat == 0){ /*Log_Escriu(LUMI_Fitxer_Log,"Ha fallat l'enviament del seguent missatge: \n\t"); Log_Escriu(LUMI_Fitxer_Log,Missatge); Log_Escriu(LUMI_Fitxer_Log,"\n\n");*/ return -5; } else{ /*Log_Escriu(LUMI_Fitxer_Log,"S'ha enviat correctament el seguent missatge: \n\t"); Log_Escriu(LUMI_Fitxer_Log,Missatge); Log_Escriu(LUMI_Fitxer_Log,"\n\n");*/ return retorn; } } int LUMI_EnviaLiniaA(int Sck, const char * IP, int portUDPrem, const char * buffer){ return UDP_EnviaA(Sck, IP, portUDPrem, buffer, strlen(buffer)); } int LUMI_EnviaPeticioRegistre(int Sck, char * adrLUMI){ char buffer[MAX_MISSATGE_PLUMI+1]; sprintf(buffer,"R%s",adrLUMI); return LUMI_EnviaFiable(Sck, buffer, NULL, TIMEOUT); } int LUMI_EnviaPeticioDesregistre(int Sck){ return LUMI_EnviaFiable(Sck, "D", NULL, TIMEOUT); } int LUMI_EnviaResposta(int Sck, char tipus, const char * adrLUMI, const char * IP, int portUDPrem){ char buffer[MAX_MISSATGE_PLUMI+1]; if(adrLUMI==NULL) sprintf(buffer,"A%c",tipus); else sprintf(buffer,"A%c%s",tipus, adrLUMI); if(portUDPrem==0) return UDP_Envia(Sck, buffer, strlen(buffer)); else return UDP_EnviaA(Sck, IP, portUDPrem, buffer, strlen(buffer)); } int LUMI_EnviaPeticioLocalitzacio(int Sck, const char * adrLUMIloc, const char * adrLUMIrem, char * IPlocalitzat, int * portTCP){ char buffer[MAX_MISSATGE_PLUMI+1]; sprintf(buffer,"L%s#%s", adrLUMIrem, adrLUMIloc); char resposta[MAX_MISSATGE_PLUMI+1]; int res = LUMI_EnviaFiable(Sck, buffer, resposta, TIMEOUT*2); //printf("%s\n", resposta); if (res <= 0) return res; else if (res == 1){ LUMI_DescodificarSockTCPMissatgeC(resposta,IPlocalitzat,portTCP, NULL); return res; } } int LUMI_EnviaPeticioServeiLocalitzacio(int Sck, const char * adrLUMI, const char * IP, int portUDPrem){ char buffer[MAX_MISSATGE_PLUMI+1]; sprintf(buffer,"S%s",adrLUMI); return UDP_EnviaA(Sck, IP, portUDPrem, buffer, strlen(buffer)); } int LUMI_EnviaRespostaServeiLocalitzacio(int Sck, const char * adrLUMI, const char * IP, int portTCPrem){ char buffer[MAX_MISSATGE_PLUMI+1]; sprintf(buffer,"C%s#%i#%s",IP, portTCPrem, adrLUMI); //printf("%s\n", buffer); return UDP_Envia(Sck, buffer, strlen(buffer)); } int LUMI_DescodificarAdreca(const char * adr, char * nickname, char * domini){ int i=0; while (adr[i]!='@') i++; if (domini != NULL) strcpy(domini, adr+i+1); if (nickname != NULL){ strncpy(nickname, adr, i); nickname[i]='\0'; } return 0; } int LUMI_DescodificarMissatge(char tipus, const char * Missatge, char * adreca, char * domini, char * nom_usuari){ if (tipus == 'R'){ strcpy(adreca,Missatge+1); LUMI_DescodificarAdreca(adreca, nom_usuari, domini); } else if (tipus == 'L'){ char buffer[MAX_USER_NICK+MAX_LEN_DOMINI+2]; int i=1; while (Missatge[i]!='#') i++; strncpy(buffer, Missatge+1, i-1); buffer[i-1]='\0'; LUMI_DescodificarAdreca(buffer,nom_usuari,domini); strcpy(adreca, Missatge+i+1); } else if (tipus == 'A'){ int longitud = strlen(Missatge); if (longitud > 2) { strcpy(adreca,Missatge+2); LUMI_DescodificarAdreca(adreca, nom_usuari, domini); } } else if (tipus == 'S'){ strcpy(adreca,Missatge+1); LUMI_DescodificarAdreca(adreca, nom_usuari, domini); } else if(tipus == 'C'){ int i, j=1; for(i = 1; i < 3; i++){ //ens saltem els dos primers # i ens posicionem sobre el tercer while (Missatge[j]!='#') j++; j++; } strcpy(adreca,Missatge+j); //printf("%s\n", adreca); LUMI_DescodificarAdreca(adreca, nom_usuari, domini); } else if (tipus == 'D') return 0; else return -1; return 0; } int LUMI_DescodificarSockTCPMissatgeC(const char * Missatge, char * IP, int * portTCP, char * adreca){ int i=1, j; char buffer[6]; while (Missatge[i]!='#') i++; strncpy(IP,Missatge+1,i-1); //aixo esta mal IP[i-1]='\0'; j=i+1; while (Missatge[j]!='#') j++; strncpy(buffer,Missatge+i+1,j-i-1); *portTCP=atoi(buffer); if (adreca != NULL) strcpy(adreca, Missatge+j+1); return 0; } int comprovarIP(const char * IP){ //aka "la fàbrica de bugs" int i=0, mida=strlen(IP), punts=0, old=-1, temp; char buff[16]; char c; while(i='0')) return 2; i++; } i=0; while(i255) return 1; old=i; i++; punts++; } if (punts != 4 || IP[mida-1]=='.') return -1; return 0; } int validarAdreca(const char * adreca, int longAdr){ int i = 0; while( i < longAdr && adreca[i]!='#' && adreca[i]!='@') i++; if(i == longAdr || adreca[i]=='#') return 1; else return 0; } int LUMI_ComprovarFormat(const char * buffer){ int mida=strlen(buffer), i=1, j; char tipus = buffer[0]; switch(tipus){ case 'R': case 'S': if (mida == 1) return 1; else{ if (validarAdreca(buffer+1,mida-1) == 1) return 1; } break; case 'D': if (mida > 1) return 1; break; case 'L': if(mida == 1) return 1; while (buffer[i]!='@' && buffer[i]!='#' && i2){ while (buffer[i]!='@' && i IP_LENGTH || i-1 <7 ) return 1; /*C222.222.222.222# 01234567891111111 0123456*/ char ip[IP_LENGTH]; strncpy(ip, buffer+1, i-1); ip[i-1] = '\0'; //if(comprovarIP(ip) == 1) return 1; //millor que no estigues implementada j= i+1; while (buffer[j]!='#' && j MAX_PORT) return 1; //comprobem que el port es un nuumero compres entre 0 i 65535 if(validarAdreca(buffer+j+1,mida-j) == 1) return 1; break; default: return 1; break; } return 0; } int LUMI_RepLiniaDe(int Sck, char * IPrem, int * portUDP, char * buffer, int mida_buffer){ int res; if (IPrem != NULL && portUDP != NULL) res = UDP_RepDe(Sck, IPrem, portUDP, buffer, mida_buffer); else res = UDP_Rep(Sck,buffer,mida_buffer); if (res <= 0) return res; buffer[res]='\0'; if(LUMI_ComprovarFormat(buffer) == 1){ LUMI_EnviaResposta(Sck,'I', NULL, IPrem, *portUDP); return -2; } return res; } int LUMI_EscriureFitxerLog(int fitxer, const char * linia){ return 0; } int LUMI_Desconnecta(int Sck){ close(Sck); }