source: admin/Services/ogAdmServer/sources/ogAdmServer.cpp @ e77c9f9

918-git-images-111dconfigfileconfigure-oglivegit-imageslgromero-new-oglivemainmaint-cronmount-efivarfsmultivmmultivm-ogboot-installerogClonningEngineogboot-installer-jenkinsoglive-ipv6test-python-scriptsticket-301ticket-50ticket-50-oldticket-577ticket-585ticket-611ticket-612ticket-693ticket-700ubu24tplunification2use-local-agent-oglivevarios-instalacionwebconsole3
Last change on this file since e77c9f9 was e77c9f9, checked in by alonso <alonso@…>, 15 years ago

git-svn-id: https://opengnsys.es/svn/trunk@788 a21b9725-9963-47de-94b9-378ad31fedc9

  • Property mode set to 100644
File size: 141.4 KB
Line 
1// ****************************************************************************************************************************************************
2// Aplicación HIDRA
3// Copyright 2003-2005 JosnManuel Alonso. Todos los derechos reservados.
4// Fichero: hidra.cpp
5//      Descripción:
6//              Este proyecto implementa el servicio hidra en un ordenador con plataforma windows NT. Este fichero aporta las funciones de
7//              envn de comandos y recepcin de respuestas
8// ****************************************************************************************************************************************************
9#include "ogAdmServer.h"
10#include "encriptacion.c"
11// ________________________________________________________________________________________________________
12// Función: RegistraLog
13//
14//              Descripción:
15//                      Esta funcin registra los evento de errores en un fichero log
16//              Parametros:
17//                      - msg : Mensage de error
18//                      - swerrno: Switch que indica que recupere literal de error del sistema
19// ________________________________________________________________________________________________________
20void RegistraLog(const char *msg,int swerrno)
21{
22        struct tm * timeinfo;
23        timeinfo = TomaHora();
24
25        FLog=fopen(szPathFileLog,"at");
26        if(swerrno)
27                fprintf (FLog,"%02d/%02d/%d %02d:%02d ***%s:%s\n",timeinfo->tm_mday,timeinfo->tm_mon+1,timeinfo->tm_year+1900,timeinfo->tm_hour,timeinfo->tm_min,msg,strerror(errno));
28        else
29                fprintf (FLog,"%02d/%02d/%d %02d:%02d ***%s\n",timeinfo->tm_mday,timeinfo->tm_mon+1,timeinfo->tm_year+1900,timeinfo->tm_hour,timeinfo->tm_min,msg);
30        fclose(FLog);
31}
32
33// ________________________________________________________________________________________________________
34// Función: TomaHora
35//
36//              Descripción:
37//                      Esta funcin toma la hora actual  del sistema y devuelve una estructura conlos datos
38//              Parametros:
39//                      - msg : Mensage de error
40//                      - swerrno: Switch que indica que recupere literal de error del sistema
41// ________________________________________________________________________________________________________
42struct tm * TomaHora()
43{
44        time_t rawtime;
45        time ( &rawtime );
46        return(gmtime(&rawtime));
47}
48//________________________________________________________________________________________________________
49//
50// Función: TomaConfiguracion
51//
52//              Descripción:
53//              Esta función lee el fichero de configuración del programa hidralinuxcli  y toma los parametros
54//              Parametros:
55//                              - pathfilecfg : Ruta al fichero de configuración
56//________________________________________________________________________________________________________
57int TomaConfiguracion(char* pathfilecfg)
58{
59        long lSize;
60        char * buffer,*lineas[100],*dualparametro[2];
61        char ch[2];
62        int i,numlin,resul;
63
64        if(pathfilecfg==NULL) return(FALSE); // Nombre del fichero en blanco
65
66        Fconfig = fopen ( pathfilecfg , "rb" );
67        if (Fconfig==NULL)      return(FALSE);
68        fseek (Fconfig , 0 , SEEK_END);  // Obtiene tamaño del fichero.
69        lSize = ftell (Fconfig);
70        rewind (Fconfig);
71        buffer = (char*) malloc (lSize);  // Toma memoria para el buffer de lectura.
72        if (buffer == NULL)             return(FALSE);
73        fread (buffer,1,lSize,Fconfig);         // Lee contenido del fichero
74        fclose(Fconfig);
75
76        //inicializar
77        IPlocal[0]=(char)NULL;
78        servidorhidra[0]=(char)NULL;
79        Puerto[0]=(char)NULL;
80        usuario[0]=(char)NULL;
81        pasguor[0]=(char)NULL;
82        datasource[0]=(char)NULL;
83        catalog[0]=(char)NULL;
84       
85       
86        strcpy(ch,"\n");// caracter delimitador ( salto de linea)
87        numlin=split_parametros(lineas,buffer,ch);
88        for (i=0;i<numlin;i++){
89                strcpy(ch,"=");// caracter delimitador
90                split_parametros(dualparametro,lineas[i],ch); // Toma primer nombre del parametros
91
92                resul=strcmp(dualparametro[0],"IPhidra");
93                if(resul==0) strcpy(IPlocal,dualparametro[1]);
94
95                resul=strcmp(dualparametro[0],"IPhidra");
96                if(resul==0) strcpy(servidorhidra,dualparametro[1]);
97
98                resul=strcmp(dualparametro[0],"Puerto");
99                if(resul==0) strcpy(Puerto,dualparametro[1]);
100               
101                resul=strcmp(dualparametro[0],"AulaUp");
102                if(resul==0) strcpy(AulaUp,dualparametro[1]);
103       
104                resul=strcmp(dualparametro[0],"Usuario");
105                if(resul==0) strcpy(usuario,dualparametro[1]);
106
107                resul=strcmp(dualparametro[0],"PassWord");
108                if(resul==0) strcpy(pasguor,dualparametro[1]);
109
110                resul=strcmp(dualparametro[0],"DataSource");
111                if(resul==0) strcpy(datasource,dualparametro[1]);
112
113                resul=strcmp(dualparametro[0],"Catalog");
114                if(resul==0) strcpy(catalog,dualparametro[1]);
115        }
116        if(IPlocal[0]==(char)NULL){
117                RegistraLog("IPlocal, NO se ha definido este parámetro",false);
118                return(FALSE);
119        }
120        if(servidorhidra[0]==(char)NULL){
121                RegistraLog("IPhidra, NO se ha definido este parámetro",false);
122                return(FALSE);
123        }
124        if(Puerto[0]==(char)NULL){
125                RegistraLog("Puerto, NO se ha definido este parámetro",false);
126                return(FALSE);
127        }
128        puerto=atoi(Puerto);
129       
130        if(AulaUp[0]==(char)NULL){
131                RegistraLog("AulaUp, NO se ha definido este parámetro",false);
132                return(FALSE);
133        }       
134        aulaup=atoi(AulaUp);
135                       
136        if(usuario[0]==(char)NULL){
137                RegistraLog("Usuario, NO se ha definido este parámetro",false);
138                return(FALSE);
139        }       
140        if(pasguor[0]==(char)NULL){
141                RegistraLog("PassWord, NO se ha definido este parámetro",false);
142                return(FALSE);
143        }       
144        if(datasource[0]==(char)NULL){
145                RegistraLog("DataSource, NO se ha definido este parámetro",false);
146                return(FALSE);
147        }       
148        if(catalog[0]==(char)NULL){
149                RegistraLog("Catalog, NO se ha definido este parámetro",false);
150                return(FALSE);
151        }       
152        return(TRUE);
153}
154// ________________________________________________________________________________________________________
155// Función: GestionaConexion
156//
157//              Descripción:
158//                      Esta hebra es la encargada de comunicarse con los clientes  a travn del socket enviado como parnetro.
159//              Parametros:
160//                      - lpParam : Socket usado
161// ________________________________________________________________________________________________________
162void * GestionaConexion(void* s)
163{
164        SOCKET socket_c=*(SOCKET*)s;
165        TRAMA trama;           
166       
167        if (recibe_trama(socket_c,&trama)){
168                if (strncmp(trama.identificador,"JMMLCAMDJ",9)==0) // Es una trama hidra
169                        gestiona_comando(socket_c,trama);
170        }
171        return(s);
172}
173// ________________________________________________________________________________________________________
174// Función: gestiona_comando
175//
176//              Descripción:
177//                      Analiza el comando enviado por el servidor web y lo reenvia al cliente rembo o lo ejecuta n mismo
178//              Parametros:
179//                      - s : Socket usado
180//                      - trama : La trama con los parametrso del comando
181// ________________________________________________________________________________________________________
182void gestiona_comando(SOCKET s,TRAMA trama)
183{
184        int i,resul,idaccion,numipes,cont,estado_cliente;
185        char *parametros,*nombrefuncion;
186        char *iph,*ids,*coletilla;
187        char pids[20],ipes[MAXLON_PARAMETROSIPH];
188
189        parametros=&trama.parametros[0];
190       
191        if (trama.ejecutor=='1'){       // Debe ejecutar el servidor
192                INTROaFINCAD(parametros);
193                nombrefuncion=toma_parametro("nfn",parametros);
194                resul=strcmp(nombrefuncion,"InclusionCliente");
195                if(resul==0){
196                        if(!InclusionCliente(s,parametros))
197                                respuesta_cortesia(s);
198                        return;
199                }
200
201                resul=strcmp(nombrefuncion,"inclusion_cliWINLNX");
202                if(resul==0){
203                        inclusion_cliWINLNX(s,parametros);
204                        return;
205                }
206               
207                resul=strcmp(nombrefuncion,"inclusion_REPO");
208                if(resul==0){
209                        inclusion_REPO(s,parametros);
210                        return;
211                }               
212
213                resul=strcmp(nombrefuncion,"ComandosPendientes");
214                if(resul==0){
215                        if(!ComandosPendientes(s,parametros))
216                                respuesta_cortesia(s);
217                        return;
218                }
219
220                resul=strcmp(nombrefuncion,"RecuperaItem");
221                if(resul==0){
222                        if(!RecuperaItem(s,parametros))
223                                respuesta_cortesia(s);
224                        return;
225                }
226
227                resul=strcmp(nombrefuncion,"EjecutarItem");
228                if(resul==0){
229                        if(!EjecutarItem(s,parametros))
230                                respuesta_cortesia(s);
231                        return;
232                }
233                resul=strcmp(nombrefuncion,"DisponibilidadComandos");
234                if(resul==0){
235                        DisponibilidadComandos(s,parametros);
236                        respuesta_cortesia(s);
237                        return;
238                }
239                resul=strcmp(nombrefuncion,"Sondeo");
240                if(resul==0){
241                        Sondeo(s,parametros);
242                        return;
243                }
244                resul=strcmp(nombrefuncion,"Arrancar");
245                if(resul==0){
246                        Arrancar(parametros);
247                        return;
248                }
249
250                resul=strcmp(nombrefuncion,"Actualizar");
251                if(resul==0){
252                        Actualizar(parametros);
253                        return;
254                }
255
256                resul=strcmp(nombrefuncion,"Conmutar");
257                if(resul==0){
258                        Conmutar(parametros);
259                        return;
260                }
261                resul=strcmp(nombrefuncion,"Purgar");
262                if(resul==0){
263                        PurgarTablaSockets(parametros);
264                        return;
265                }
266       
267                resul=strcmp(nombrefuncion,"RESPUESTA_Arrancar");
268                if(resul==0){
269                        RESPUESTA_Arrancar(s,parametros);
270                        respuesta_cortesia(s);
271                        return;
272                }
273
274                resul=strcmp(nombrefuncion,"RESPUESTA_Apagar");
275                if(resul==0){
276                        RESPUESTA_Apagar(s,parametros);
277                        respuesta_cortesia(s);
278                        return;
279                }
280
281                resul=strcmp(nombrefuncion,"RESPUESTA_IniciarSesion");
282                if(resul==0){
283                        RESPUESTA_IniciarSesion(s,parametros);
284                        respuesta_cortesia(s);
285                        return;
286                }
287
288                resul=strcmp(nombrefuncion,"RESPUESTA_Reiniciar");
289                if(resul==0){
290                        RESPUESTA_Reiniciar(s,parametros);
291                        respuesta_cortesia(s);
292                        return;
293                }
294               
295                resul=strcmp(nombrefuncion,"RESPUESTA_IniciarSesion");
296                if(resul==0){
297                        RESPUESTA_Reiniciar(s,parametros);
298                        respuesta_cortesia(s);
299                        return;
300                }               
301                resul=strcmp(nombrefuncion,"RESPUESTA_ExecShell");
302                if(resul==0){
303                        RESPUESTA_ExecShell(s,parametros);
304                        respuesta_cortesia(s);
305                        return;
306                }
307                resul=strcmp(nombrefuncion,"RESPUESTA_CrearPerfilSoftware");
308                if(resul==0){
309                        RESPUESTA_CrearPerfilSoftware(s,parametros);
310                        respuesta_cortesia(s);
311                        return;
312                }
313
314                resul=strcmp(nombrefuncion,"RESPUESTA_CrearSoftwareIncremental");
315                if(resul==0){
316                        RESPUESTA_CrearSoftwareIncremental(s,parametros);
317                        respuesta_cortesia(s);
318                        return;
319                }
320                resul=strcmp(nombrefuncion,"RESPUESTA_RestaurarImagen");
321                if(resul==0){
322                        RESPUESTA_RestaurarImagen(s,parametros);
323                        respuesta_cortesia(s);
324                        return;
325                }
326                resul=strcmp(nombrefuncion,"RESPUESTA_ParticionaryFormatear");
327                if(resul==0){
328                        RESPUESTA_ParticionaryFormatear(s,parametros);
329                        respuesta_cortesia(s);
330                        return;
331                }
332                resul=strcmp(nombrefuncion,"RESPUESTA_Configurar");
333                if(resul==0){
334                        RESPUESTA_Configurar(s,parametros);
335                        respuesta_cortesia(s);
336                        return;
337                }
338                resul=strcmp(nombrefuncion,"RESPUESTA_TomaConfiguracion");
339                if(resul==0){
340                        RESPUESTA_TomaConfiguracion(s,parametros);
341                        respuesta_cortesia(s);
342                        return;
343                }
344                resul=strcmp(nombrefuncion,"RESPUESTA_TomaHardware");
345                if(resul==0){
346                        RESPUESTA_TomaHardware(s,parametros);
347                        respuesta_cortesia(s);
348                        return;
349                }       
350                resul=strcmp(nombrefuncion,"RESPUESTA_TomaSoftware");
351                if(resul==0){
352                        RESPUESTA_TomaSoftware(s,parametros);
353                        respuesta_cortesia(s);
354                        return;
355                }               
356        }
357        else{   // Debe ejecutar elcliente rembo
358                coletilla=corte_iph(parametros); // toma el puntero al comienzo del parametros iph
359                INTROaFINCAD(coletilla);
360                iph=toma_parametro("iph",coletilla); // Toma ipes
361                ids=toma_parametro("ids",coletilla); // Toma identificador de la accion
362                coletilla[0]='\0';// Corta la trama en la ip
363                strcpy(ipes,iph); // Copia la cadena de ipes
364                if(ids!=NULL){
365                        idaccion=atoi(ids);
366                        sprintf(pids,"ids=%d\r",idaccion);
367                        strcat(parametros,pids); // Le ande el identificador de la accion
368                }
369                numipes=cuenta_ipes(ipes); // Numero de ipes a los que enviar las tramas
370                cont=0;
371                DesmarcaServidoresRembo();
372                for (i=0;i<MAXIMOS_SOCKETS;i++){
373                        if (strncmp(tbsockets[i].ip,"\0",1)!=0){ // Si es un cliente activo
374                                if (IgualIP(ipes,tbsockets[i].ip)){ // Si existe la IP en la cadena
375                                        estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_REMBO);
376                                        if(estado_cliente==0){ // Cliente Rembo ...
377                                                strcpy(tbsockets[i].estado,CLIENTE_OCUPADO);
378                                                MarcaServidoresRembo(tbsockets[i].ipsrvrmb,tbsockets[i].ip);
379                                        }
380                                        else{
381                                                estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_OCUPADO);
382                                                if(estado_cliente!=0){ // Cliente Windows(Windows98,Windows2000,windows XP...) y Linux
383                                                        strcpy(tbsockets[i].estado,CLIENTE_OCUPADO);
384                                                        manda_comando(tbsockets[i].sock,parametros);
385                                                }
386                                        }
387                                        cont++; // Contador de envios de tramas a  ordenadores
388                                        if(cont==numipes) break;
389                                }
390                        }
391                }
392                EnviaServidoresRembo(parametros);
393        }
394}
395// ________________________________________________________________________________________________________
396// Función: manda_comando
397//
398//              Descripción:
399//                      Esta funcin envia un comando por la red (TCP) desde el servidor hidra al servidor rembo que controla al cliente que lo ejecutarn
400//              Parametros:
401//                      - sock : El socket del cliente
402//                      - parametros: El contenido del comando
403// ________________________________________________________________________________________________________
404int manda_comando(SOCKET sock,char* parametros)
405{
406        TRAMA trama;           
407        int resul;
408
409        trama.arroba='@';
410        strncpy(trama.identificador,"JMMLCAMDJ",9);
411        trama.ejecutor='0';
412        strcpy(trama.parametros,parametros);
413        resul=manda_trama(sock,&trama);
414        return(resul);
415}
416// ________________________________________________________________________________________________________
417// Función: manda_trama
418//
419//              Descripción:
420//                      Esta funcin envia una trama por la red (TCP)
421//              Parametros:
422//                      - sock : El socket del host al que se dirige la trama
423//                      - trama: El contenido de la trama
424// ________________________________________________________________________________________________________
425int manda_trama(SOCKET sock,TRAMA* trama)
426{
427        int nLeft,idx,ret;
428        Encriptar((char*)trama);
429        nLeft = strlen((char*)trama);
430        idx = 0;
431        while(nLeft > 0){
432                ret = send(sock,(char*)&trama[idx], nLeft, 0);
433               
434                if (ret == 0){
435                        break;
436                }
437                else
438                        if (ret == SOCKET_ERROR){
439                                RegistraLog("***send() fallo en hebra cliente",true);
440                                return(FALSE);
441                        }
442                nLeft -= ret;
443                idx += ret;
444        }
445        return(TRUE);
446}
447// ________________________________________________________________________________________________________
448// Función: recibe_trama
449//
450//              Descripción:
451//                      Esta funcin recibe una trama por la red (TCP)
452//              Parametros:
453//                      - sock : El socket del cliente
454//                      - trama: El buffer para recibir la trama
455// ________________________________________________________________________________________________________
456int recibe_trama(SOCKET sock,TRAMA* trama)
457{
458        int ret;
459
460        while(1){ // Bucle para recibir datos del cliente
461                ret = recv(sock,(char*)trama,LONGITUD_TRAMA,0);
462                if (ret == 0) // Conexin cerrada por parte del cliente (Graceful close)
463                        break;
464                else{
465                        if (ret == SOCKET_ERROR){
466                                RegistraLog("***recv() fallo en recepcion trama",true);
467                                return (FALSE);
468                        }
469                        else // Datos recibidos
470                                break;
471                }
472        }
473        Desencriptar((char*)trama);
474        trama->parametros[ret-11]=(char)NULL; // Coloca caracter fin de cadena en trama
475        return(TRUE);
476}
477// ________________________________________________________________________________________________________
478// Función: hay_hueco
479//
480//              Descripción:
481//                      Esta funcin devuelve true o false dependiendo de que haya hueco en la tabla de sockets para un nuevo cliente.
482//                      Parametros:
483//                              - idx:   Primer indice libre que se podrn utilizar
484// ________________________________________________________________________________________________________
485int hay_hueco(int *idx)
486{
487        int i;
488
489        for (i=0;i<MAXIMOS_SOCKETS;i++){
490                if (strncmp(tbsockets[i].ip,"\0",1)==0){ // Hay un hueco
491                        *idx=i;
492                        return(TRUE);
493                }
494        }
495        return(FALSE);
496}
497// ________________________________________________________________________________________________________
498// Función: cliente_existente
499//
500//               Descripción:
501//                      Esta funcin devuelve true o false dependiendo de si el cliente estnya registrado en  la tabla de sockets
502//              Parametros:
503//                              - ip : La ip del cliente a buscar
504//                              - idx:   Indice que ocuparn el cliente, de estar ya registrado
505// ________________________________________________________________________________________________________
506BOOLEAN cliente_existente(char *ip,int* idx)
507{
508        int i;
509        for (i=0;i<MAXIMOS_SOCKETS;i++){
510                if (strcmp(ip,tbsockets[i].ip)==0){ // Si existe la IP ...
511                        *idx=i;
512                        return(TRUE);
513                }
514        }
515        return(FALSE);
516}
517// ________________________________________________________________________________________________________
518// Función: hay_huecoservidorrembo
519//
520//              Descripción:
521//                      Esta funcin devuelve true o false dependiendo de que haya hueco en la tabla de sockets para un nuevo servidor rembo.
522//              Parametros:
523//                      - idx:   Primer indice libre que se podrn utilizar
524// ________________________________________________________________________________________________________
525int hay_huecoservidorrembo(int *idx)
526{
527        int i;
528        for (i=0;i<MAXIMOS_SRVRMB;i++){
529                if (strncmp(tbsocketsSRVRMB[i].ip,"\0",1)==0){ // Hay un hueco
530                        *idx=i;
531                        return(TRUE);
532                }
533        }
534        return(FALSE);
535}
536// ________________________________________________________________________________________________________
537// Función: servidorrembo_existente
538//
539//              Descripción:
540//                      Esta funcin devuelve true o false dependiendo de si el servidor estnya registrado en  la tabla de sockets
541//              Parametros:
542//                              - ip : La ip delcliente a buscar
543//                              - idx   Indice que ocuparn el servidor, de existir
544// ________________________________________________________________________________________________________
545BOOLEAN servidorrembo_existente(char *ip,int* idx)
546{
547        int i;
548        for (i=0;i<MAXIMOS_SRVRMB;i++){
549                if (strcmp(ip,tbsocketsSRVRMB[i].ip)==0){ // Si existe la IP ...
550                        *idx=i;
551                        return(TRUE);
552                }
553        }
554        return(FALSE);
555}
556// ________________________________________________________________________________________________________
557// Función: INTROaFINCAD
558//
559//              Descripción:
560//                      Cambia INTROS por caracteres fin de cadena ('\0') en una cadena
561//              Parametros:
562//                              - parametros : La cadena a explorar
563// ________________________________________________________________________________________________________
564void INTROaFINCAD(char* parametros)
565{
566        int lon,i;
567        lon=strlen(parametros);
568        for(i=0;i<lon;i++){
569                if(parametros[i]=='\r') parametros[i]='\0';
570        }
571}
572// ________________________________________________________________________________________________________
573// Funciónn: FINCADaINTRO
574//
575//              Descripciónn?:
576//                      Cambia caracteres fin de cadena ('\0') por INTROS en una cadena
577//              Parametros:
578//                              - parametros : La cadena a explorar
579// ________________________________________________________________________________________________________
580void FINCADaINTRO(char* a,char *b)
581{
582        char *i;
583        for(i=a;i<b;i++){ // Cambia los NULOS por INTROS
584                if(*i=='\0') *i='\r';
585        }
586}
587// ________________________________________________________________________________________________________
588// Función: cuenta_ipes
589//
590//              Descripción:
591//                      Cuenta las comas (caracter de separacion) de las cadenas de ipes
592//              Parámetros:
593//                      - parametros : La cadena a explorar
594// ________________________________________________________________________________________________________
595int cuenta_ipes(char* iph)
596{
597        int lon,i,cont=1;
598        lon=strlen(iph);
599        for(i=0;i<lon;i++){
600                if(iph[i]==';') cont++;
601        }
602        return(cont);
603}
604// ________________________________________________________________________________________________________
605// Función: toma_parametro
606//
607//              Descripción:
608//                      Esta funcin devuelve el valor de un parametro incluido en la trama.
609//                      El formato del protocolo es: "nombre_parametro=valor_parametro"
610//              Parámetros:
611//                      - nombre_parametro: Es el nombre del parnetro a recuperar
612//                      - parametros: Es la matriz que contiene todos los parnetros
613// ________________________________________________________________________________________________________
614char * toma_parametro(const char* nombre_parametro,char *parametros)
615{
616        int i=0;
617        char* pos;
618
619        for(i=0;i<LONGITUD_PARAMETROS-4;i++){
620                if(parametros[i]==nombre_parametro[0]){
621                        if(parametros[i+1]==nombre_parametro[1]){
622                                if(parametros[i+2]==nombre_parametro[2]){
623                                        if(parametros[i+3]=='='){
624                                                pos=&parametros[i+4];
625                                                return(pos);
626                                        }
627                                }
628                        }
629                }
630        }
631        return(NULL);
632}
633// ________________________________________________________________________________________________________
634// Función: split_parametros
635//
636//              Descripción:
637//                      Esta funcin trocea una cadena segn un carnter delimitador, Devuelve el nmero de trozos
638//              Parámetros:
639//                      - trozos: Array de punteros a cadenas
640//                      - cadena: Cadena a trocear
641//                      - ch: Carnter delimitador
642// ________________________________________________________________________________________________________
643int split_parametros(char **trozos,char *cadena, char * ch){
644        int w=0;
645        char* token;
646
647        token= strtok(cadena,ch); // Trocea segn delimitador
648        while( token != NULL ){
649                trozos[w++]=token;
650                token=strtok(NULL,ch); // Siguiente token
651        }
652        trozos[w++]=token;
653        return(w-1); // Devuelve el numero de trozos
654}
655// ________________________________________________________________________________________________________
656// Función: corte_iph
657//
658//              Descripción:
659//                      Esta funcin devuelve el valor del parametro iph incluido en la trama que debe ser el ltimo parnetro de la trama.
660//        Parámetros:
661//                      - parametros: Parámetros de la trama
662// ________________________________________________________________________________________________________
663char* corte_iph(char *parametros)
664{
665        int i=0;
666        char nombre_parametro[5];
667
668        strcpy(nombre_parametro,"iph=");
669        for(i=0;i<LONGITUD_PARAMETROS-4;i++){
670                if(parametros[i]==nombre_parametro[0]){
671                        if(parametros[i+1]==nombre_parametro[1]){
672                                if(parametros[i+2]==nombre_parametro[2]){
673                                        if(parametros[i+3]=='='){
674                                                return(&parametros[i]); //Devuelve la posicion de comienzo de la iph
675                                        }
676                                }
677                        }
678                }
679        }
680        return(NULL);
681}
682
683// ________________________________________________________________________________________________________
684// Función: escaparComillas
685//
686//       Descripción:
687//              Escapa las comillas simples de una cadena
688//        Parámetros:
689//              - s: Cadena de caracteres
690//      Devuelve:
691//              La cadena con las comillas escapadas "\'"
692// ________________________________________________________________________________________________________
693char* escaparComillas(char *cadena){
694
695        int lon,i,con=0;
696        char *cadenaescapada;
697       
698        lon=strlen(cadena);
699        for(i=0;i<lon;i++){ // Cuenta las comillas
700                if(cadena[i]==COMILLAS_SIMPES) con++;
701        }
702        if(con>0){ // Existen comillas
703                cadenaescapada = (char*) malloc (lon+con);  // Toma memoria para la cadena escapada.
704                if (cadenaescapada == NULL) return(NULL);
705                int ptr=0;
706                for(i=0;i<lon;i++){
707                        if(cadena[i]==COMILLAS_SIMPES)
708                                cadenaescapada[ptr++]=BARRA_INVERTIDA;
709                        cadenaescapada[ptr++]=cadena[i];
710                }
711        }
712        else
713                cadenaescapada=cadena;
714
715        return(cadenaescapada);
716}
717// ________________________________________________________________________________________________________
718// Función: respuesta_cortesia
719//
720//       Descripción:
721//              Envn respuesta de cortesn al cliente rembo
722//        Parámetros:
723//                      - s: Socket usado por el cliente para comunicarse con el servidor HIDRA
724// ________________________________________________________________________________________________________
725int respuesta_cortesia(SOCKET s)
726{
727        char nwparametros[100];
728
729        nwparametros[0]='\0';
730        strcat(nwparametros,"nfn=Cortesia");
731        strcat(nwparametros,"\r");
732        return(manda_comando(s,nwparametros));
733}
734// ________________________________________________________________________________________________________
735// Función: NoComandosPendientes
736//
737//              Descripción:
738//                      Envn respuesta de cortesn al cliente rembo
739//        Parámetros:
740//                      - s: Socket usado por el cliente para comunicarse con el servidor HIDRA
741// ________________________________________________________________________________________________________
742int NoComandosPendientes(SOCKET s)
743{
744        char nwparametros[100];
745
746        nwparametros[0]='\0';
747        strcat(nwparametros,"nfn=NoComandosPtes");
748        strcat(nwparametros,"\r");
749        return(manda_comando(s,nwparametros));
750}
751// ________________________________________________________________________________________________________
752// Función: InclusionCliente
753//
754//              Descripción:
755//                      Esta funcin incorpora el socket de un nuevo cliente a la tabla de sockets y le devuelve alguna de sus propiedades: nombre,
756//                      dentificador, perfil hardware , mens...
757//              Parámetros:
758//                      - s: Socket del cliente
759//                      - parametros: Parámetros de la trama recibida
760// ________________________________________________________________________________________________________
761int InclusionCliente(SOCKET s,char *parametros)
762{
763        char ErrStr[200],sqlstr[1000];
764        Database db;
765        Table tbl;
766
767        char *iph,*cfg,*mac,*nau,*nor,*ipr,*ipd;
768        int i,lon,glon,idx,resul,puertorepo;
769        char nwparametros[LONGITUD_PARAMETROS];
770        char ipservidordhcp[16],ipservidorrembo[16],nombreordenador[100];
771        int idordenador,idaula,idconfiguracion,idparticion,idperfilhard,idmenu,cache;
772
773        // Toma parnetros
774        iph=toma_parametro("iph",parametros); // Toma ip
775        mac=toma_parametro("mac",parametros); // Toma mac
776        cfg=toma_parametro("cfg",parametros); // Toma configuracion
777        nau=toma_parametro("nau",parametros); // Toma nombre del grupo em el           fichero config de rembo
778        nor=toma_parametro("nor",parametros); // Toma nombre del ordenador en el  fichero config de rembo
779        ipd=toma_parametro("ipd",parametros); // Toma ip del servidor dhcpd
780        ipr=toma_parametro("ipr",parametros); // Toma ip del servidor rembo
781
782        // Toma las propiedades del ordenador
783        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
784                RegistraLog("Error de conexión con la base de datos",false);
785                db.GetErrorErrStr(ErrStr);
786                return(false);
787        }
788        // Recupera los datos del ordenador
789        sprintf(sqlstr,"SELECT ordenadores.idordenador,ordenadores.idaula,ordenadores.nombreordenador, ordenadores.idperfilhard, ordenadores.idconfiguracion,ordenadores.idparticion,servidoresrembo.ip AS ipservidorrembo,servidoresrembo.puertorepo, ordenadores.idmenu,ordenadores.cache FROM ordenadores INNER JOIN  servidoresrembo ON ordenadores.idservidorrembo = servidoresrembo.idservidorrembo  WHERE ordenadores.ip = '%s'",iph);
790
791        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
792                RegistraLog("Error al ejecutar la consulta",false);
793                db.GetErrorErrStr(ErrStr);
794                return(false);
795        }
796        if(tbl.ISEOF()){ // Si No existe registro
797                RegistraLog("Cliente No encontrado, se rechaza la petición",false);
798                if(aulaup==AUTOINCORPORACION_OFF) // No estnactivada la incorporacin automnica
799                        return(false);
800                if(!cuestion_nuevoordenador(db,tbl,&idordenador,nau,nor,iph,mac,cfg,ipd,ipr)) // Ha habido algn error en la incorporacin automnica
801                        return(false);
802                // Valores por defecto del nuevo ordenador
803                strcpy(nombreordenador,nor);
804                idperfilhard=0;
805                strcpy(ipservidordhcp,ipd);
806                strcpy(ipservidorrembo,ipr);
807                idmenu=0;
808        }
809        else{
810         //     sprintf(msglog,"Petición de Inclusión del CLiente:%s",iph);
811        //      RegistraLog(msglog,false);
812
813                if(!tbl.Get("idordenador",idordenador)){ // Toma dato
814                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
815                                return(false);
816                }
817                if(!tbl.Get("nombreordenador",nombreordenador)){ // Toma dato
818                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
819                                return(false);
820                }       
821                if(!tbl.Get("idaula",idaula)){ // Toma dato
822                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
823                                return(false);
824                }
825
826                if(!tbl.Get("idconfiguracion",idconfiguracion)){ // Toma dato
827                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
828                                return(false);
829                }
830                if(!tbl.Get("idparticion",idparticion)){ // Toma dato
831                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
832                                return(false);
833                }
834                if(!tbl.Get("idperfilhard",idperfilhard)){ // Toma dato
835                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
836                                return(false);
837                }
838                /*
839                if(!tbl.Get("ipservidordhcp",ipservidordhcp)){ // Toma dato
840                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
841                                return(false);
842                }
843
844                lon=strlen(ipservidordhcp);
845                for (i=0;i<lon;i++){
846                        if(ipservidordhcp[i]==' ') {
847                                ipservidordhcp[i]='\0';
848                                break;
849                        }
850                }
851                */
852                if(!tbl.Get("ipservidorrembo",ipservidorrembo)){ // Toma dato
853                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
854                                return(false);
855                }
856                lon=strlen(ipservidorrembo);
857                for (i=0;i<lon;i++){
858                        if(ipservidorrembo[i]==' ') {
859                                ipservidorrembo[i]='\0';
860                                break;
861                        }
862                }
863                if(!tbl.Get("puertorepo",puertorepo)){ // Toma dato
864                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
865                                return(false);
866                }               
867               
868                if(!tbl.Get("idmenu",idmenu)){ // Toma dato
869                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
870                                return(false);
871                }
872                if(!tbl.Get("cache",cache)){ // Toma dato
873                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
874                                return(false);
875                }                                       
876                resul=actualiza_configuracion(db,tbl,cfg,idconfiguracion,idparticion,iph); // Actualiza la configuracin del ordenador
877                if(!resul){
878                        pthread_mutex_unlock(&guardia);
879                        return(false);
880                }
881        }
882        // Incluyendo al cliente en la tabla de sokets
883        if (cliente_existente(iph,&i)){ // Si ya existe la IP ...
884                idx=i;
885                //close(tbsockets[idx].sock);
886        }
887        else{
888                if (hay_hueco(&i)){ // Busca hueco para el nuevo cliente
889                        idx=i;
890                        strcpy(tbsockets[idx].ip,iph);// Copia IP
891                }
892                else
893                        return(false); // No hay huecos
894        }
895        strcpy(tbsockets[idx].estado,CLIENTE_INICIANDO); // Actualiza el estado del cliente
896        tbsockets[idx].sock=s; // Guarda el socket
897        //strcpy(tbsockets[idx].ipsrvdhcp,ipservidordhcp);// Guarda IP servidor dhcp
898        strcpy(tbsockets[idx].ipsrvrmb,ipservidorrembo);// Guarda IP servidor rembo
899
900        inclusion_srvRMB(ipservidorrembo,puertorepo); // Actualiza tabla de servidores rembo
901
902        // Prepara la trama
903        lon=sprintf(nwparametros,"nfn=RESPUESTA_InclusionCliente\r");
904        lon+=sprintf(nwparametros+lon,"ido=%d\r",idordenador);
905        lon+=sprintf(nwparametros+lon,"npc=%s\r",nombreordenador);
906        lon+=sprintf(nwparametros+lon,"ida=%d\r",idaula);
907        lon+=sprintf(nwparametros+lon,"hrd=%s\r",servidorhidra);
908        lon+=sprintf(nwparametros+lon,"prt=%d\r",puerto);
909        lon+=sprintf(nwparametros+lon,"ifh=%d\r",idperfilhard);
910        lon+=sprintf(nwparametros+lon,"che=%d\r",cache);
911        lon+=sprintf(nwparametros+lon,"ipr=%s\r",ipservidorrembo);
912        lon+=sprintf(nwparametros+lon,"rep=%d\r",puertorepo);
913        glon=lon;
914        if(!Toma_menu(db,tbl,nwparametros,idmenu,lon)) nwparametros[glon]=(char)NULL;
915        db.Close();
916        return(manda_comando(s,nwparametros));
917}
918// ________________________________________________________________________________________________________
919// Función: Toma menu
920//
921//              Descripción:
922//                      Esta funcin toma los parametros del menu inicial del cliente rembo y se los envn en el proceso de inclusin
923//              Parámetros:
924//                      - nwparametros: Cadena con los parnetros a enviar al cliente
925//                      - idmenu: Identificador del men
926//                      - lon : Longitud inicial de la cadena de parnetros
927// ________________________________________________________________________________________________________
928int Toma_menu(Database db, Table tbl,char* nwparametros,int idmenu,int lon)
929{
930        Table littbl;
931
932        char sqlstr[1000],ErrStr[200],titulo[250],descripitem[250],urlimg[250];
933        int idaccionmenu,idtipoaccion,coorx,coory,idurlimg;
934        int modalidad,resolucion,tipoaccion,tipoitem;
935        char htmlmenupub[250],htmlmenupri[250];
936
937        sprintf(sqlstr,"SELECT menus.resolucion,menus.titulo,menus.coorx,menus.coory,menus.modalidad,menus.scoorx,menus.scoory,menus.smodalidad,menus.htmlmenupub,menus.htmlmenupri,acciones_menus.tipoaccion,acciones_menus.idaccionmenu,acciones_menus.idtipoaccion,acciones_menus.tipoitem,acciones_menus.descripitem,acciones_menus.idurlimg FROM acciones_menus INNER JOIN menus ON acciones_menus.idmenu = menus.idmenu WHERE menus.idmenu=%d order by acciones_menus.orden",idmenu);
938               
939        if(!db.Execute(sqlstr,tbl)){ // Error al leer
940                db.GetErrorErrStr(ErrStr);
941                return(false);
942        }
943        if (tbl.ISEOF()) return(true);
944       
945        if(!tbl.Get("titulo",titulo)){ // Toma dato
946                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
947                return(false);
948        }
949        if(!tbl.Get("coorx",coorx)){ // Toma dato
950                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
951                return(false);
952        }
953        if(!tbl.Get("coory",coory)){ // Toma dato
954                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
955                return(false);
956        }
957        if(!tbl.Get("modalidad",modalidad)){ // Toma dato
958                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
959                return(false);
960        }
961        lon+=sprintf(nwparametros+lon,"cmn=%s&%d&%d&%d&",titulo,coorx,coory,modalidad); // Cabecera de menu
962
963        if(!tbl.Get("scoorx",coorx)){ // Toma dato
964                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
965                return(false);
966        }
967        if(!tbl.Get("scoory",coory)){ // Toma dato
968                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
969                return(false);
970        }
971        if(!tbl.Get("smodalidad",modalidad)){ // Toma dato
972                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
973                return(false);
974        }
975        lon+=sprintf(nwparametros+lon,"%d&%d&%d",coorx,coory,modalidad); // Cabecera de menu
976
977        if(!tbl.Get("resolucion",resolucion)){ // Toma dato
978                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
979                return(false);
980        }
981        lon+=sprintf(nwparametros+lon,"&%d\r",resolucion); // Resolucion de la pantalla
982
983        if(!tbl.Get("htmlmenupub",htmlmenupub)){ // Toma dato
984                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
985                return(false);
986        }
987        if(!tbl.Get("htmlmenupri",htmlmenupri)){ // Toma dato
988                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
989                return(false);
990        }
991        lon+=sprintf(nwparametros+lon,"htm=%s;%s\r",htmlmenupub,htmlmenupri); // Html de menu
992
993        lon+=sprintf(nwparametros+lon,"mnu=");
994        while(!tbl.ISEOF()){ // Recorre acciones del menu
995                if(!tbl.Get("tipoaccion",tipoaccion)){ // Toma dato
996                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
997                        return(false);
998                }
999                if(!tbl.Get("tipoitem",tipoitem)){ // Toma dato
1000                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1001                        return(false);
1002                }
1003                if(!tbl.Get("idtipoaccion",idtipoaccion)){ // Toma dato
1004                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1005                        return(false);
1006                }
1007                if(!tbl.Get("idaccionmenu",idaccionmenu)){ // Toma dato
1008                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1009                        return(false);
1010                }
1011                if(!tbl.Get("descripitem",descripitem)){ // Toma dato
1012                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1013                        return(false);
1014                }
1015                if(!tbl.Get("idurlimg",idurlimg)){ // Toma dato
1016                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1017                        return(false);
1018                }
1019       
1020                sprintf(sqlstr,"SELECT urlicono FROM iconos WHERE idicono=%d",idurlimg);
1021                if(!db.Execute(sqlstr,littbl)){ // Error al leer
1022                        db.GetErrorErrStr(ErrStr);
1023                        return(false);
1024                }
1025                if (!littbl.ISEOF()){
1026                        if(!littbl.Get("urlicono",urlimg)){ // Toma dato
1027                                littbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1028                                return(false);
1029                        }
1030                }
1031                else
1032                        sprintf(urlimg,"itemdefault.pcx");
1033
1034                lon+=sprintf(nwparametros+lon,"%d&%s&%s&%d&%d\?",idaccionmenu,urlimg,descripitem,tipoitem,tipoaccion);
1035                tbl.MoveNext();
1036        }
1037        nwparametros[lon-1]='\r';
1038        nwparametros[lon]=(char)NULL;
1039        return(true);
1040}
1041// ________________________________________________________________________________________________________
1042// Función:RecuperaItem
1043//
1044//              Descripción:
1045//                      Esta funcin busca en la base de datos, los parametros de un items de un menu
1046//              Parámetros:
1047//                      - s: Socket del cliente
1048//                      - parametros: Parámetros de la trama recibida
1049// ________________________________________________________________________________________________________
1050int RecuperaItem(SOCKET s,char *parametros)
1051{
1052        char ErrStr[200],sqlstr[1000];
1053        Database db;
1054        Table tbl;
1055        char *ida;
1056        int idtipoaccion,tipoaccion;
1057
1058        // Toma parnetros
1059        ida=toma_parametro("ida",parametros); // Toma identificador de la acción
1060
1061        //  Abre conexin con la base de datos
1062        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
1063                db.GetErrorErrStr(ErrStr);
1064                return(false);
1065        }
1066        sprintf(sqlstr,"SELECT tipoaccion,idtipoaccion FROM acciones_menus  WHERE idaccionmenu=%s",ida);
1067        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1068                db.GetErrorErrStr(ErrStr);
1069                return(false);
1070        }
1071        if (tbl.ISEOF()) return(false);
1072       
1073        if(!tbl.Get("tipoaccion",tipoaccion)){ // Toma tipo de acción
1074                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1075                return(false);
1076        }
1077        if(!tbl.Get("idtipoaccion",idtipoaccion)){ // Toma identificador del tipo de acción
1078                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1079                return(false);
1080        }
1081        switch(tipoaccion){
1082                case EJECUCION_PROCEDIMIENTO :
1083                        sprintf(sqlstr,"SELECT  procedimientos_comandos.parametros FROM procedimientos_comandos  WHERE procedimientos_comandos.idprocedimiento=%d",idtipoaccion);
1084                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1085                                db.GetErrorErrStr(ErrStr);
1086                                return(false);
1087                        }
1088                        if(tbl.ISEOF()) // No existe procedimiento
1089                                return(false);
1090
1091                        while(!tbl.ISEOF()){
1092                                if(!tbl.Get("parametros",parametros)){ // Toma dato
1093                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1094                                        return(false);
1095                                }
1096                                tbl.MoveNext();
1097                        }
1098                        break;
1099                case EJECUCION_TAREA :
1100                        //Las tareas no se recuperan como fichero de items;
1101                        break;
1102                case EJECUCION_TRABAJO :
1103                        //Los t rabajos no se recuperan como fichero de items;
1104                        break;
1105        }
1106        db.Close();
1107        return(manda_comando(s,parametros));
1108}
1109
1110// ________________________________________________________________________________________________________
1111// Función: actualiza_configuracion
1112//
1113//              Descripción:
1114//                      Esta funcin actualiza la base de datos con la configuracion de sistemas operativos y particiones de un ordenador
1115//              Parámetros:
1116//                      - db: Objeto base de datos (ya operativo)
1117//                      - tbl: Objeto tabla
1118//                      - cfg: cadena con una configuracin
1119//                      - idcfgo: Identificador de la configuracin actual del ordenador
1120//                      - ipho: Identificador de la configuracin actual de las particiones del ordenador
1121//                      - ipho: Ipe del ordenador
1122// ________________________________________________________________________________________________________
1123int actualiza_hardware(Database db, Table tbl,char* hrd,char* ip,char*ido)
1124{
1125        int idtipohardware;
1126        int i,lon=0,idcentro,widcentro;
1127        char *tbHardware[MAXHARDWARE];
1128        int tbidhardware[MAXHARDWARE];
1129        char *dualHardware[2];
1130        char ch[2]; // Carnter delimitador
1131        char sqlstr[1000],ErrStr[200],descripcion[250],nombreordenador[250];
1132
1133
1134        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1135        // ACCESO atnico A TRAVEZ DE OBJETO MUTEX a este trozo de cnigo
1136        pthread_mutex_lock(&guardia);
1137       
1138        // Toma Centro
1139        sprintf(sqlstr,"SELECT aulas.idcentro,ordenadores.nombreordenador FROM aulas INNER JOIN ordenadores ON aulas.idaula=ordenadores.idaula WHERE ordenadores.idordenador=%s",ido);
1140        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1141                db.GetErrorErrStr(ErrStr);
1142                pthread_mutex_unlock(&guardia);
1143                return(false);
1144        }               
1145        if(!tbl.Get("idcentro",widcentro)){ // Toma dato
1146                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1147                pthread_mutex_unlock(&guardia);
1148                return(false);
1149        }                       
1150        idcentro=widcentro+0; // Bug Mysql
1151
1152        if(!tbl.Get("nombreordenador",nombreordenador)){ // Toma dato
1153                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1154                pthread_mutex_unlock(&guardia);
1155                return(false);
1156        }                       
1157       
1158        if(lon>MAXHARDWARE) lon=MAXHARDWARE;
1159
1160        // Lee archivo de inventario hardware
1161        FILE *Finv;
1162        char *buffer;
1163        long lSize;
1164        Finv = fopen ( hrd , "rb" ); // EL parametro sft contiene el path del archivo de inventario
1165        if (Finv==NULL) return(false);
1166        fseek (Finv , 0 , SEEK_END);  // Obtiene tamaño del fichero.
1167        lSize = ftell (Finv);
1168        rewind (Finv);
1169        buffer = (char*) malloc (lSize);  // Toma memoria para el buffer de lectura.
1170        if (buffer == NULL) return(false);
1171        fread (buffer,1,lSize,Finv);    // Lee contenido del fichero
1172        fclose(Finv);
1173        buffer=escaparComillas(buffer);
1174               
1175        // Trocea la cadena de configuración
1176        strcpy(ch,"\n");// caracter delimitador
1177        lon=split_parametros(tbHardware,buffer,ch);
1178       
1179        // Trocea las cadenas de parametros de particin
1180        for (i=0;i<lon;i++){
1181                strcpy(ch,"=");// caracter delimitador "="
1182                split_parametros(dualHardware,tbHardware[i],ch); // Nmero de particin
1183                sprintf(sqlstr,"SELECT idtipohardware,descripcion FROM tipohardwares WHERE nemonico='%s'",dualHardware[0]);
1184                if(!db.Execute(sqlstr,tbl)){ // Error al leer
1185                        db.GetErrorErrStr(ErrStr);
1186                        pthread_mutex_unlock(&guardia);
1187                        return(false);
1188                }               
1189                if(tbl.ISEOF()){ //  Tipo de Hardware NO existente
1190                        sprintf(msglog,"Existe un tipo de hardware que no está registrado (nemónico:%s). Se rechaza proceso de inventario",dualHardware[0]);
1191                        RegistraLog(msglog,false);
1192                        pthread_mutex_unlock(&guardia);
1193                        return(false);
1194                }
1195                else{  //  Tipo de Hardware Existe
1196                        if(!tbl.Get("idtipohardware",idtipohardware)){ // Toma dato
1197                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1198                                pthread_mutex_unlock(&guardia);
1199                                return(false);
1200                        }
1201                        if(!tbl.Get("descripcion",descripcion)){ // Toma dato
1202                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1203                                pthread_mutex_unlock(&guardia);
1204                                return(false);
1205                        }
1206
1207                        sprintf(sqlstr,"SELECT idhardware FROM hardwares WHERE idtipohardware=%d AND descripcion='%s'",idtipohardware,dualHardware[1]);
1208                       
1209                        // EJecuta consulta
1210                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1211                                db.GetErrorErrStr(ErrStr);
1212                                pthread_mutex_unlock(&guardia);
1213                                return(false);
1214                        }       
1215
1216                        if(tbl.ISEOF()){ //  Hardware NO existente
1217                                sprintf(sqlstr,"INSERT hardwares (idtipohardware,descripcion,idcentro,grupoid) VALUES(%d,'%s',%d,0)",idtipohardware,dualHardware[1],idcentro);
1218                                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1219                                        db.GetErrorErrStr(ErrStr);
1220                                        pthread_mutex_unlock(&guardia);
1221                                        return(false);
1222                                }               
1223                                // Recupera el identificador del hardware       
1224                                sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1225                                if(!db.Execute(sqlstr,tbl)){ // Error al leer
1226                                        db.GetErrorErrStr(ErrStr);
1227                                        pthread_mutex_unlock(&guardia);
1228                                        return(false);
1229                                }
1230                                if(!tbl.ISEOF()){ // Si existe registro
1231                                        if(!tbl.Get("identificador",tbidhardware[i])){
1232                                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1233                                                        pthread_mutex_unlock(&guardia);
1234                                                        return(false);
1235                                        }
1236                                }                                       
1237                        }
1238                        else{
1239                                if(!tbl.Get("idhardware",tbidhardware[i])){ // Toma dato
1240                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1241                                        pthread_mutex_unlock(&guardia);
1242                                        return(false);
1243                                }                                                       
1244                        }
1245                }       // Fin for
1246        }
1247         // Comprueba existencia de perfil hardware y actualización de éste para el ordenador
1248        if(!CuestionPerfilHardware(db, tbl,idcentro,ido,tbidhardware,i,nombreordenador)){
1249                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1250                pthread_mutex_unlock(&guardia);
1251                return(false);
1252        }       
1253        pthread_mutex_unlock(&guardia);
1254        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////         
1255        return(true);
1256}
1257// ________________________________________________________________________________________________________
1258// Función: CuestionPerfilHardware
1259//________________________________________________________________________________________________________/
1260int CuestionPerfilHardware(Database db, Table tbl,int idcentro,char* ido,int *tbidhardware,int i,char *nombreordenador){
1261        char sqlstr[1000],ErrStr[200];
1262        int tbidhardwareperfil[MAXHARDWARE];
1263        int j=0;
1264        int idperfilhard;
1265        // Busca perfil hard del ordenador
1266        sprintf(sqlstr,"SELECT perfileshard_hardwares.idhardware FROM ordenadores INNER JOIN perfileshard ON ordenadores.idperfilhard = perfileshard.idperfilhard       INNER JOIN perfileshard_hardwares ON perfileshard_hardwares.idperfilhard = perfileshard.idperfilhard WHERE ordenadores.idordenador =%s",ido);
1267        // EJecuta consulta
1268        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1269                db.GetErrorErrStr(ErrStr);
1270                return(false);
1271        }               
1272        while(!tbl.ISEOF()){ // Recorre acciones del menu
1273                if(!tbl.Get("idhardware",tbidhardwareperfil[j++])){ // Toma dato
1274                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1275                        return(false);
1276                }               
1277                tbl.MoveNext();
1278        }
1279        // Comprueba si el perfil del ordenador contiene todo el hardware enviado
1280        int k,q,sw=false;
1281        for(k=0;k<i;k++){ // Elemento hardware
1282                for(q=0;q<j;q++){
1283                        if(tbidhardware[k]==tbidhardwareperfil[q]){
1284                                sw=true;
1285                                break;
1286                        }
1287                }
1288                if(!sw) break;                 
1289        }
1290        // La variable sw contiene false si se ha encontrado algún hardware que no está en el perfil hardware del ordenador
1291        if(sw) return(true); // Todo el hardware está en el perfil actual
1292       
1293        // Crea perfil nuevo con todo el hardware inventariado
1294        sprintf(sqlstr,"INSERT perfileshard  (descripcion,idcentro,grupoid) VALUES('Perfil Hardware (%s)',%d,0)",nombreordenador,idcentro);
1295        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1296                db.GetErrorErrStr(ErrStr);
1297                return(false);
1298        }               
1299        // Recupera el identificador del hardware       
1300        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1301        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1302                db.GetErrorErrStr(ErrStr);
1303                return(false);
1304        }
1305        if(!tbl.ISEOF()){ // Si existe registro
1306                if(!tbl.Get("identificador",idperfilhard)){
1307                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1308                        return(false);
1309                }
1310        }       
1311        for(k=0;k<i;k++){ // relaciona elementos hardwares con el nuevo perfil hardware
1312                sprintf(sqlstr,"INSERT perfileshard_hardwares  (idperfilhard,idhardware) VALUES(%d,%d)",idperfilhard,tbidhardware[k]);
1313                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1314                        db.GetErrorErrStr(ErrStr);
1315                        return(false);
1316                }               
1317        }                               
1318        sprintf(sqlstr,"UPDATE  ordenadores SET idperfilhard=%d WHERE idordenador=%s",idperfilhard,ido);
1319        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1320                db.GetErrorErrStr(ErrStr);
1321                return(false);
1322        }                       
1323        return(true);
1324}
1325// ________________________________________________________________________________________________________
1326// Función: actualiza_configuracion
1327//
1328//              Descripción:
1329//                      Esta funcin actualiza la base de datos con la configuracion de sistemas operativos y particiones de un ordenador
1330//              Parámetros:
1331//                      - db: Objeto base de datos (ya operativo)
1332//                      - tbl: Objeto tabla
1333//                      - cfg: cadena con una configuracin
1334//                      - idcfgo: Identificador de la configuracin actual del ordenador
1335//                      - ipho: Identificador de la configuracin actual de las particiones del ordenador
1336//                      - ipho: Ipe del ordenador
1337// ________________________________________________________________________________________________________
1338int actualiza_software(Database db, Table tbl,char* sft,char* par,char* tfs,char* ip,char*ido)
1339{
1340        int i,lon=0,idcentro,auxint,idtiposo;
1341        char *tbSoftware[MAXSOFTWARE];
1342        int tbidsoftware[MAXSOFTWARE];
1343        char ch[2],descripso[50]; // Caracter delimitador y nombre del estandar sistema operativo
1344        char sqlstr[1000],ErrStr[200],nombreordenador[250];
1345
1346        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1347        // ACCESO atnico A TRAVEZ DE OBJETO MUTEX a este trozo de cnigo
1348        pthread_mutex_lock(&guardia);
1349       
1350        // Toma Centro
1351        sprintf(sqlstr,"SELECT aulas.idcentro,ordenadores.nombreordenador FROM aulas INNER JOIN ordenadores ON aulas.idaula=ordenadores.idaula WHERE ordenadores.idordenador=%s",ido);
1352        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1353                db.GetErrorErrStr(ErrStr);
1354                pthread_mutex_unlock(&guardia);
1355                return(false);
1356        }               
1357        if(!tbl.Get("idcentro",auxint)){ // Toma dato
1358                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1359                pthread_mutex_unlock(&guardia);
1360                return(false);
1361        }                       
1362        idcentro=auxint+0; // Bug Mysql
1363
1364        if(!tbl.Get("nombreordenador",nombreordenador)){ // Toma dato
1365                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1366                pthread_mutex_unlock(&guardia);
1367                return(false);
1368        }                       
1369       
1370        if(lon>MAXSOFTWARE) lon=MAXSOFTWARE;
1371                // Trocea la cadena de configuracin
1372        strcpy(ch,"\n");// caracter delimitador
1373
1374
1375// Lee archivo de inventario software
1376        FILE *Finv;
1377        char *buffer;
1378        long lSize;
1379        Finv = fopen ( sft , "rb" ); // EL parametro sft contiene el path del archivo de inventario
1380        if (Finv==NULL) return(false);
1381        fseek (Finv , 0 , SEEK_END);  // Obtiene tamaño del fichero.
1382        lSize = ftell (Finv);
1383        rewind (Finv);
1384        buffer = (char*) malloc (lSize);  // Toma memoria para el buffer de lectura.
1385        if (buffer == NULL) return(false);
1386        fread (buffer,1,lSize,Finv);    // Lee contenido del fichero
1387        fclose(Finv);
1388        buffer=escaparComillas(buffer);
1389// trocea las lineas
1390        lon=split_parametros(tbSoftware,buffer,ch);
1391
1392        // Incorpora el sistema Operativo de la partición
1393        sprintf(sqlstr,"SELECT idtiposo,descripcion FROM tiposos WHERE tipopar ='%s'",tfs);
1394        // Ejecuta consulta
1395        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1396                db.GetErrorErrStr(ErrStr);
1397                pthread_mutex_unlock(&guardia);
1398                return(false);
1399        }       
1400        if(tbl.ISEOF()){ //  Software NO existente
1401                pthread_mutex_unlock(&guardia);
1402                return(false);
1403        }       
1404        else{
1405                if(!tbl.Get("idtiposo",auxint)){
1406                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1407                        pthread_mutex_unlock(&guardia);
1408                        return(false);
1409                }
1410                idtiposo=auxint+0; // Bug Mysql
1411                if(!tbl.Get("descripcion",descripso)){
1412                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1413                        pthread_mutex_unlock(&guardia);
1414                        return(false);
1415                }       
1416                tbSoftware[lon++]=descripso;
1417        }       
1418        // Trocea las cadenas de parametros de particin
1419        for (i=0;i<lon;i++){
1420                        sprintf(sqlstr,"SELECT idsoftware FROM softwares WHERE descripcion ='%s'",tbSoftware[i]);
1421                       
1422                        // EJecuta consulta
1423                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1424                                db.GetErrorErrStr(ErrStr);
1425                                pthread_mutex_unlock(&guardia);
1426                                return(false);
1427                        }       
1428                        if(tbl.ISEOF()){ //  Software NO existente
1429                                if((lon-i)>1) // No es el último elemento que es el S.O. el idtiposoftware es 2 (Aplicaciones)
1430                                        sprintf(sqlstr,"INSERT softwares (idtiposoftware,descripcion,idcentro,grupoid) VALUES(2,'%s',%d,0)",tbSoftware[i],idcentro);
1431                                else // Es el último elemento que es el S.O. el idtiposoftware es 1 (Sistemas operativos)
1432                                        sprintf(sqlstr,"INSERT softwares (idtiposoftware,idtiposo,descripcion,idcentro,grupoid) VALUES(1,%d,'%s',%d,0)",idtiposo,tbSoftware[i],idcentro);
1433                               
1434                                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1435                                        db.GetErrorErrStr(ErrStr);
1436                                        pthread_mutex_unlock(&guardia);
1437                                        return(false);
1438                                }               
1439                                // Recupera el identificador del software       
1440                                sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1441                                if(!db.Execute(sqlstr,tbl)){ // Error al leer
1442                                        db.GetErrorErrStr(ErrStr);
1443                                        pthread_mutex_unlock(&guardia);
1444                                        return(false);
1445                                }
1446                                if(!tbl.ISEOF()){ // Si existe registro
1447                                        if(!tbl.Get("identificador",tbidsoftware[i])){
1448                                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1449                                                        pthread_mutex_unlock(&guardia);
1450                                                        return(false);
1451                                        }
1452                                }                                       
1453                        }
1454                        else{
1455                                if(!tbl.Get("idsoftware",tbidsoftware[i])){ // Toma dato
1456                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1457                                        pthread_mutex_unlock(&guardia);
1458                                        return(false);
1459                                }                                                       
1460                }       // Fin for
1461        }
1462         // Comprueba existencia de perfil software y actualización de éste para el ordenador
1463        if(!CuestionPerfilSoftware(db, tbl,idcentro,ido,tbidsoftware,i,nombreordenador,par)){
1464                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1465                pthread_mutex_unlock(&guardia);
1466                return(false);
1467        }       
1468        pthread_mutex_unlock(&guardia);
1469        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////         
1470        return(true);
1471}
1472// ________________________________________________________________________________________________________
1473// Función: CuestionPerfilSoftware
1474//________________________________________________________________________________________________________/
1475int CuestionPerfilSoftware(Database db, Table tbl,int idcentro,char* ido,int *tbidsoftware,int i,char *nombreordenador,char *particion){
1476        char sqlstr[1000],ErrStr[200];
1477        int tbidsoftwareperfil[MAXSOFTWARE];
1478        int j=0;
1479        int idperfilsoft;
1480        // Busca perfil soft del ordenador
1481        sprintf(sqlstr,"SELECT perfilessoft_softwares.idsoftware FROM ordenador_perfilsoft INNER JOIN perfilessoft ON ordenador_perfilsoft.idperfilsoft = perfilessoft.idperfilsoft INNER JOIN perfilessoft_softwares ON perfilessoft_softwares.idperfilsoft=perfilessoft.idperfilsoft WHERE ordenador_perfilsoft.idordenador =%s",ido);
1482        // EJecuta consulta
1483        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1484                db.GetErrorErrStr(ErrStr);
1485                return(false);
1486        }               
1487        while(!tbl.ISEOF()){ // Recorre software del perfils
1488                if(!tbl.Get("idsoftware",tbidsoftwareperfil[j++])){ // Toma dato
1489                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1490                        return(false);
1491                }               
1492                tbl.MoveNext();
1493        }
1494        // Comprueba si el perfil del ordenador contiene todo el software enviado
1495        int k,q,sw=false;
1496        if(i==j){ // Si son el mismo número de componenetes software ...
1497                for(k=0;k<i;k++){ // Elemento software
1498                        for(q=0;q<j;q++){
1499                                if(tbidsoftware[k]==tbidsoftwareperfil[q]){
1500                                        sw=true;
1501                                        break;
1502                                }
1503                        }
1504                        if(!sw) break;                 
1505                }
1506        }
1507       
1508        // La variable sw contiene false si se ha encontrado algún software que no está en el perfil software del ordenador
1509        if(sw) return(true); // Todo el software está en el perfil actual
1510       
1511        // Crea perfil nuevo con todo el software inventariado
1512        sprintf(sqlstr,"INSERT perfilessoft  (descripcion,idcentro,grupoid) VALUES('Perfil Software (%s, Part:%s) ',%d,0)",nombreordenador,particion,idcentro);
1513        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1514                db.GetErrorErrStr(ErrStr);
1515                return(false);
1516        }               
1517        // Recupera el identificador del software       
1518        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1519        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1520                db.GetErrorErrStr(ErrStr);
1521                return(false);
1522        }
1523        if(!tbl.ISEOF()){ // Si existe registro
1524                if(!tbl.Get("identificador",idperfilsoft)){
1525                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1526                        return(false);
1527                }
1528        }       
1529        for(k=0;k<i;k++){ // relaciona elementos softwares con el nuevo perfil software
1530                sprintf(sqlstr,"INSERT perfilessoft_softwares  (idperfilsoft,idsoftware) VALUES(%d,%d)",idperfilsoft,tbidsoftware[k]);
1531                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1532                        db.GetErrorErrStr(ErrStr);
1533                        return(false);
1534                }               
1535        }
1536        // Busca si existe un perfil software para ese ordenador y esa partición       
1537        sprintf(sqlstr,"SELECT idperfilsoft FROM ordenador_perfilsoft WHERE idordenador =%s AND particion=%s",ido,particion);
1538        // Ejecuta consulta
1539        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1540                db.GetErrorErrStr(ErrStr);
1541                return(false);
1542        }               
1543        if(!tbl.ISEOF()){ // existe un perfilsoft que se cambia al nuevo
1544                sprintf(sqlstr,"UPDATE  ordenador_perfilsoft SET idperfilsoft=%d WHERE idordenador=%s AND particion=%s",idperfilsoft,ido,particion);
1545                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1546                        db.GetErrorErrStr(ErrStr);
1547                        return(false);
1548                }                       
1549        }
1550        else{
1551                sprintf(sqlstr,"INSERT INTO ordenador_perfilsoft (idordenador,particion,idperfilsoft) VALUE (%s,%s,%d)",ido,particion,idperfilsoft);
1552                if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1553                        db.GetErrorErrStr(ErrStr);
1554                        return(false);
1555                }                       
1556               
1557        }
1558        return(true);
1559}
1560// ________________________________________________________________________________________________________
1561// Función: actualiza_configuracion
1562//
1563//              Descripción:
1564//                      Esta funcin actualiza la base de datos con la configuracion de sistemas operativos y particiones de un ordenador
1565//              Parámetros:
1566//                      - db: Objeto base de datos (ya operativo)
1567//                      - tbl: Objeto tabla
1568//                      - cfg: cadena con una configuracin
1569//                      - idcfgo: Identificador de la configuracin actual del ordenador
1570//                      - ipho: Identificador de la configuracin actual de las particiones del ordenador
1571//                      - ipho: Ipe del ordenador
1572// ________________________________________________________________________________________________________
1573int actualiza_configuracion(Database db, Table tbl,char* cfg,int idcfgo,int idprto,char* ipho)
1574{
1575        char sqlstr[1000],ErrStr[200]; 
1576        int idconfiguracion,idparticion,lon;
1577        char * part;
1578
1579
1580        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1581        // ACCESO atnico A TRAVEZ DE OBJETO MUTEX a este trozo de cnigo
1582        pthread_mutex_lock(&guardia);
1583        sprintf(sqlstr,"SELECT idconfiguracion FROM configuraciones WHERE configuracion LIKE '%s'",cfg);
1584        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1585                db.GetErrorErrStr(ErrStr);
1586                                pthread_mutex_unlock(&guardia);
1587                return(false);
1588        }
1589        if(!tbl.ISEOF()){ // Configuracin ya existente
1590                if(!tbl.Get("idconfiguracion",idconfiguracion)){ // Toma dato
1591                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1592                                                pthread_mutex_unlock(&guardia);
1593                                return(false);
1594                }
1595        }
1596        else{ // Nueva configuracin
1597                        sprintf(sqlstr,"INSERT configuraciones (configuracion) VALUES('%s')",cfg);
1598                        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1599                                db.GetErrorErrStr(ErrStr);
1600                                pthread_mutex_unlock(&guardia);
1601                                return(false);
1602                        }
1603                        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1604                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1605                                db.GetErrorErrStr(ErrStr);
1606                                pthread_mutex_unlock(&guardia);
1607                                return(false);
1608                        }
1609                        if(!tbl.ISEOF()){ // Si existe registro
1610                                if(!tbl.Get("identificador",idconfiguracion)){
1611                                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1612                                                pthread_mutex_unlock(&guardia);
1613                                                return(false);
1614                                }
1615                        }
1616        }
1617        // Genera cadena de particiones
1618        lon=strlen(cfg);
1619        part=(char*)malloc(lon);
1620        TomaParticiones(cfg,part,lon);
1621        sprintf(sqlstr,"SELECT idparticion FROM particiones WHERE particion LIKE '%s'",part);
1622        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1623                db.GetErrorErrStr(ErrStr);
1624                pthread_mutex_unlock(&guardia);
1625                return(false);
1626        }
1627        if(!tbl.ISEOF()){ // Configuracin ya existente
1628                if(!tbl.Get("idparticion",idparticion)){ // Toma dato
1629                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1630                                                pthread_mutex_unlock(&guardia);
1631                                return(false);
1632                }
1633        }
1634        else{ // Nueva particion
1635                        sprintf(sqlstr,"INSERT particiones (particion) VALUES('%s')",part);
1636                        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
1637                                db.GetErrorErrStr(ErrStr);
1638                                                pthread_mutex_unlock(&guardia);
1639                                return(false);
1640                        }
1641                        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
1642                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1643                                db.GetErrorErrStr(ErrStr);
1644                                                pthread_mutex_unlock(&guardia);
1645                                return(false);
1646                        }
1647                        if(!tbl.ISEOF()){ // Si existe registro
1648                                if(!tbl.Get("identificador",idparticion)){
1649                                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1650                                                                pthread_mutex_unlock(&guardia);
1651                                                return(false);
1652                                }
1653                        }
1654        }                       
1655        if(idconfiguracion!=idcfgo ||  idparticion!=idprto){ // Si el odenador tiene una configuracin distinta ...
1656                sprintf(sqlstr,"Update ordenadores set idconfiguracion=%d, idparticion=%d WHERE ip='%s'",idconfiguracion,idparticion,ipho);
1657                if(!db.Execute(sqlstr,tbl)){ // Error al actualizar
1658                        db.GetErrorErrStr(ErrStr);
1659                                        pthread_mutex_unlock(&guardia);
1660                        return(false);
1661                }
1662        }
1663                        pthread_mutex_unlock(&guardia);
1664        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
1665        return(true);
1666}
1667// ________________________________________________________________________________________________________
1668// Función: TomaParticiones
1669//
1670//              Descripción:
1671//                      Esta funcin compone basndose en la cadena de configuracin que devuelve el ordenador, una cadena de particiones con
1672//                      los valores "n0=PPPP;n1=PPPP..."  con las duplas:el nmero de particin y el tipo, separados por coma
1673//              Parámetros:
1674//                      - cfg: Cadena de configuracin
1675//                      - parts: Cadena devuelta con el formato anterior descrito
1676//                      - lonprt: Longitud mnmima para las cadenas
1677// ________________________________________________________________________________________________________
1678void TomaParticiones(char* cfg, char* parts,int lonprt)
1679{
1680        int i;
1681        int lon=0;
1682        char *tbParticiones[10]; // Para albergar hasta 10 particiones ( Normalmente Mnimo 8);
1683        char *tbParticion[8]; // Para albergar hasta 8 parnetros de particin;
1684        char *tbIgualdad[2]; // Para albergar hasta 8 parnetros de particin;
1685        char ch[2]; // Carnter delimitador
1686        char *apun;
1687        int p;
1688        // Toma memoria para cada elemento de particin
1689        for(i=0;i<10;i++)
1690                tbParticiones[i]=(char*)malloc(lonprt);
1691
1692        // Toma memoria para cada parametro de particin
1693        for(i=0;i<8;i++)
1694                tbParticion[i]=(char*)malloc(lonprt);
1695
1696        // Toma memoria para cada igualdad
1697        for(i=0;i<2;i++)
1698                tbIgualdad[i]=(char*)malloc(20); 
1699
1700        // Trocea la cadena de configuracin
1701        strcpy(ch,"\t");// caracter delimitador (tabulador)
1702        lonprt=split_parametros(tbParticiones,cfg,ch);
1703        // Trocea las cadenas de parametros de particin
1704        for (p=0;p<lonprt;p++){
1705                strcpy(ch,"\n");// caracter delimitador (salto de linea)
1706                split_parametros(tbParticion,tbParticiones[p],ch);
1707                strcpy(ch,"=");// caracter delimitador "="
1708                split_parametros(tbIgualdad,tbParticion[4],ch); // Nmero de particin
1709                lon+=sprintf(parts+lon,"%s=",tbIgualdad[1]);
1710                split_parametros(tbIgualdad,tbParticion[2],ch); // Tipo de particion
1711                apun=tbIgualdad[1];
1712                //if(apun[0]=='H') apun++; // Si es oculta ...
1713                lon+=sprintf(parts+lon,"%s;",apun);
1714        }
1715        lon+=sprintf(parts+lon,"@prt");
1716}
1717// ________________________________________________________________________________________________________
1718// Función: ComandosPendientes
1719//
1720//              Descripción:
1721//                      Esta funcin busca en la base de datos,comandos pendientes de ejecutar por un  ordenador  concreto
1722//              Parámetros:
1723//                      - s: Socket del cliente
1724//                      - parametros: Parámetros de la trama recibida
1725// ________________________________________________________________________________________________________
1726int ComandosPendientes(SOCKET s,char *parametros)
1727{
1728        char *iph,*ido,*coletilla;
1729        int ids;
1730        char pids[20],ipe[16],idord[16];
1731
1732        iph=toma_parametro("iph",parametros); // Toma ip
1733        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
1734        strcpy(ipe,iph);
1735        strcpy(idord,ido);
1736
1737        if(busca_comandos(ipe,idord,parametros,&ids)){
1738                Coloca_estado(ipe,CLIENTE_OCUPADO,s);
1739                //Manda el comando pendiente
1740                coletilla=corte_iph(parametros);
1741                coletilla[0]='\0';// Corta la trama en la ip
1742                sprintf(pids,"ids=%d\r",ids);
1743                strcat(parametros,pids); // Le ande el identificador de la accion
1744                return(manda_comando(s,parametros));
1745        }
1746        NoComandosPendientes(s);  // Indica al cliente rembo que ya no hay mn comandos pendientes
1747        return(true);
1748}
1749// ________________________________________________________________________________________________________
1750// Función: EjecutarItem
1751//
1752//              Descripción:
1753//                      Esta funcin ejecuta un item de un men concreto solicitado por algn cliente rembo
1754//              Parámetros:
1755//                      - s: Socket del cliente
1756//                      - parametros: Parámetros de la trama recibida
1757// ________________________________________________________________________________________________________
1758int EjecutarItem(SOCKET s,char *parametros)
1759{
1760        char sqlstr[1000],ErrStr[200];
1761        Database db;
1762        Table tbl,tbln;
1763        int idtipoaccion,lon,cont_comandos=0,i,puertorepo;
1764        char tipoaccion,*iph,*idt,ipe[16];
1765        char *tbComandosparametros[100];
1766
1767        iph=toma_parametro("iph",parametros); // Toma ip
1768        idt=toma_parametro("idt",parametros); // Toma idemtificador del item
1769        strcpy(ipe,iph);
1770
1771        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
1772                db.GetErrorErrStr(ErrStr);
1773                return(false);
1774        }
1775        sprintf(sqlstr,"SELECT acciones_menus.tipoaccion, acciones_menus.idtipoaccion FROM acciones_menus WHERE acciones_menus.idaccionmenu=%s",idt);
1776        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1777                db.GetErrorErrStr(ErrStr);
1778                return(false);
1779        }
1780        if(tbl.ISEOF()){
1781                return(false);  // No hay comandos pendientes
1782        }
1783
1784        if(!tbl.Get("tipoaccion",tipoaccion)){ // Toma dato
1785                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1786                return(false);
1787        }
1788
1789        if(!tbl.Get("idtipoaccion",idtipoaccion)){ // Toma dato
1790                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1791                return(false);
1792        }
1793       
1794        switch(tipoaccion){
1795                case EJECUCION_PROCEDIMIENTO :
1796                        sprintf(sqlstr,"SELECT  procedimientos_comandos.parametros  FROM  procedimientos_comandos  WHERE procedimientos_comandos.idprocedimiento=%d",idtipoaccion);
1797                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
1798                                db.GetErrorErrStr(ErrStr);
1799                                return(false);
1800                        }
1801                        if(tbl.ISEOF()) // No existe procedimiento
1802                                return(false);
1803
1804                        while(!tbl.ISEOF()){
1805                                if(!tbl.Get("parametros",parametros)){ // Toma dato
1806                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
1807                                        return(false);
1808                                }
1809                                lon=strlen(parametros);
1810                                tbComandosparametros[cont_comandos]=(char*)malloc(lon);
1811                                if(tbComandosparametros[cont_comandos]==NULL)
1812                                        return(false); // No hay memoria bastante
1813                                strcpy(tbComandosparametros[cont_comandos++],parametros);
1814                                tbl.MoveNext();
1815                        }
1816                        strcpy(parametros,tbComandosparametros[0]);
1817                        strcat(parametros,"iph=");
1818                        strcat(parametros,ipe);
1819                        strcat(parametros,"\r");
1820                        for(i=1;i<cont_comandos;i++){
1821                                strcat(parametros,"\n");
1822                                strcat(parametros,tbComandosparametros[i]);
1823                                strcat(parametros,"iph=");
1824                                strcat(parametros,ipe);
1825                                strcat(parametros,"\r");
1826                        }
1827                        if(TomaIPServidorRembo(ipe,&puertorepo))
1828                                return(manda_trama_servidorrembo(ipe,parametros,puertorepo));
1829                        break;
1830                case EJECUCION_TAREA :
1831                        EjecutarTarea(idtipoaccion,0,0,0,db,parametros);
1832                        break;
1833                case EJECUCION_TRABAJO :
1834                        EjecutarTrabajo(idtipoaccion,db,parametros); // Es una programacin de un trabajo
1835                        break;
1836        }
1837        db.Close();
1838        return(true);
1839}
1840// ________________________________________________________________________________________________________
1841// Función: DisponibilidadComandos
1842//
1843//              Descripción:
1844//                      Esta funcin habilita a un clinte rembo para recibir o no, comandos iteractivos
1845//              Parámetros:
1846//                      - s: Socket del cliente
1847//                      - parametros: Parmetros de la trama recibida
1848// ________________________________________________________________________________________________________
1849int DisponibilidadComandos(SOCKET s,char *parametros)
1850{
1851        char *iph,*swd;
1852        int resul=0,i;
1853
1854        iph=toma_parametro("iph",parametros); // Toma ip
1855        swd=toma_parametro("swd",parametros); // Toma switch de diponibilidad
1856
1857        if(strcmp(swd,"1")==0) // Cliente disponible
1858                resul=Coloca_estado(iph,CLIENTE_REMBO,s);
1859        else{
1860                if (cliente_existente(iph,&i)) // Si ya existe la IP ...
1861                        resul=borra_entrada(i); // Cliente apagado
1862        }
1863        return(resul);
1864}
1865// ________________________________________________________________________________________________________
1866// Función: Coloca_estado
1867//
1868//              Descripción:
1869//                      Esta funcin coloca el estado de un ordenador en la tabla de sockets
1870//              Parámetros:
1871//                      - iph: Ip del ordenador
1872//                      - e: Nuevo estado
1873//                      - s: Socket usado por el cliente para comunicarse con el servidor HIDRA
1874// ________________________________________________________________________________________________________
1875int Coloca_estado(char *iph,const char *e,SOCKET s)
1876{
1877        int i;
1878        for (i=0;i<MAXIMOS_SOCKETS;i++){
1879                if (strncmp(tbsockets[i].ip,"\0",1)!=0){         // Si es un cliente activo
1880                        if (IgualIP(iph,tbsockets[i].ip)){      // Si existe la IP en la cadena
1881                                strcpy(tbsockets[i].estado,e);  // Cambia el estado
1882                                tbsockets[i].sock=s;            // Guarda el socket
1883                                return(true);
1884                        }
1885                }
1886        }
1887        return(false);
1888}
1889// ________________________________________________________________________________________________________
1890// Función: IgualIP
1891//
1892//               Descripción:
1893//                      Comprueba si una cadena con una ipe estnincluidad en otra que  contienen varias direcciones ipes separas por punto y coma
1894//              Parámetros:
1895//                      - cadenaiph: Cadena de IPes
1896//                      - ipcliente: Cadena de la ip a buscar
1897// ________________________________________________________________________________________________________
1898BOOLEAN IgualIP(char *cadenaiph,char *ipcliente)
1899{
1900        char *posa,*posb;
1901        int lon;
1902
1903        posa=strstr(cadenaiph,ipcliente);
1904        if(posa==NULL) return(FALSE); // No existe la IP en la cadena
1905        posb=posa; // Iguala direcciones
1906        while(TRUE){
1907                posb++;
1908                if(*posb==';') break;
1909                if(*posb=='\0') break;
1910                if(*posb=='\r') break;
1911        }
1912        lon=strlen(ipcliente);
1913        if((posb-posa)==lon) return(TRUE); // IP encontrada !!!!
1914               
1915        return(FALSE);
1916}
1917// ________________________________________________________________________________________________________
1918// Función: inclusion_srvRMB
1919//
1920//              Descripción:
1921//                      Esta funcin incorpora el socket de un nuevo servidor rembo a la tabla de sockets
1922//              Parámetros:
1923//                      - s: Socket del servidor rembo
1924//                      - parametros: Parámetros de la trama recibida
1925// ________________________________________________________________________________________________________
1926int inclusion_srvRMB(char *iphsrvrmb,int puertorepo)
1927{
1928        int i,idx;
1929       
1930        // Incluyendo al cliente en la tabla de sokets
1931        if (servidorrembo_existente(iphsrvrmb,&i)){ // Si ya existe la IP ...
1932                idx=i;
1933        }
1934        else{
1935                if (hay_huecoservidorrembo(&i)){ // Busca hueco para el nuevo cliente
1936                        idx=i;
1937                        strcpy(tbsocketsSRVRMB[idx].ip,iphsrvrmb);// Copia IP
1938                        tbsocketsSRVRMB[idx].puertorepo=puertorepo;
1939                }
1940                else
1941                        return(false); // No hay huecos
1942        }
1943        return(true);
1944}
1945// ________________________________________________________________________________________________________
1946// Función: inclusion_cliWINLNX
1947//
1948//               Descripción:
1949//                      Esta funcin incorpora el socket de un nuevo cliente rembo a la tabla de sockets
1950//              Parámetros:
1951//                      - s: Socket del servidor rembo
1952//                      - parametros: Parámetros de la trama recibida
1953// ________________________________________________________________________________________________________
1954int inclusion_cliWINLNX(SOCKET s,char *parametros)
1955{
1956        char *iph,*tso;
1957        int i,idx;
1958
1959        // Toma parnetros
1960        iph=toma_parametro("iph",parametros); // Toma ip
1961        tso=toma_parametro("tso",parametros); // Toma ip
1962        // Incluyendo al cliente en la tabla de sokets
1963        if (cliente_existente(iph,&i)){ // Si ya existe la IP ...
1964                idx=i;
1965                close(tbsockets[idx].sock);
1966        }
1967        else{
1968                if (hay_hueco(&i)){ // Busca hueco para el nuevo cliente
1969                        idx=i;
1970                        strcpy(tbsockets[idx].ip,iph);// Copia IP
1971                }
1972                else
1973                        return(false); // No hay huecos
1974        }
1975        tbsockets[idx].sock=s; // Guarda el socket
1976        strcpy(tbsockets[idx].estado,tso);
1977        return(true);
1978}
1979// ________________________________________________________________________________________________________
1980// Función: inclusion_REPO
1981//
1982//               Descripción:
1983//                      Esta funcin incorpora el socket de un nuevo repositorio hidra
1984// ________________________________________________________________________________________________________
1985int inclusion_REPO(SOCKET s,char *parametros)
1986{
1987        char ErrStr[200],sqlstr[1000];
1988        Database db;
1989        Table tbl;
1990       
1991        char *iph;
1992        char PathHidra[250],PathPXE[250]; // path al directorio base de Hidra
1993        int puertorepo,lon;
1994       
1995
1996        // Toma parnetros
1997        iph=toma_parametro("iph",parametros); // Toma ip
1998       
1999        // Toma las propiedades del ordenador
2000        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2001                db.GetErrorErrStr(ErrStr);
2002                return(false);
2003        }
2004        // Recupera los datos del ordenador
2005        sprintf(sqlstr,"SELECT puertorepo,pathrembod,pathpxe FROM servidoresrembo WHERE ip = '%s'",iph);
2006       
2007        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2008                db.GetErrorErrStr(ErrStr);
2009                return(false);
2010        }
2011        if(tbl.ISEOF()){ // Si No existe registro
2012                RegistraLog("No existe el Repositorio, se rechaza la petición",false);
2013                return(false);
2014        }
2015        if(!tbl.Get("puertorepo",puertorepo)){ // Toma dato
2016                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
2017                return(false);
2018        }
2019        if(!tbl.Get("pathrembod",PathHidra)){ // Toma dato
2020                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
2021                return(false);
2022        }
2023        if(!tbl.Get("pathpxe",PathPXE)){ // Toma dato
2024                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
2025                return(false);
2026        }       
2027        inclusion_srvRMB(iph,puertorepo); // Actualiza tabla de servidores rembo
2028        TRAMA *trama=(TRAMA*)malloc(LONGITUD_TRAMA);
2029        if(!trama)
2030                return(false);
2031        // Envia la trama
2032       
2033        trama->arroba='@';
2034        strncpy(trama->identificador,"JMMLCAMDJ",9);
2035        trama->ejecutor='1';
2036        lon=sprintf(trama->parametros,"nfn=RESPUESTA_inclusionREPO\r");
2037        lon+=sprintf(trama->parametros+lon,"prp=%d\r",puertorepo);
2038        lon+=sprintf(trama->parametros+lon,"pth=%s\r",PathHidra);
2039        lon+=sprintf(trama->parametros+lon,"ptx=%s\r",PathPXE);
2040        lon+=sprintf(trama->parametros+lon,"usu=%s\r",usuario);
2041        lon+=sprintf(trama->parametros+lon,"pwd=%s\r",pasguor);
2042        lon+=sprintf(trama->parametros+lon,"dat=%s\r",datasource);
2043        lon+=sprintf(trama->parametros+lon,"cat=%s\r",catalog);
2044        return(manda_trama(s,trama));
2045}
2046// ________________________________________________________________________________________________________
2047// Función: Sondeo
2048//
2049//              Descripción:
2050//                      Esta funcin recupera el estado de los ordenadores solicitados
2051//              Parámetros:
2052//                      - s: Socket del servidor web que envn el comando
2053//                      - parametros: Parámetros de la trama enviada por nte
2054// ________________________________________________________________________________________________________
2055int Sondeo(SOCKET s,char *parametros)
2056{
2057        char *iph;
2058        char nwparametros[LONGITUD_PARAMETROS];
2059        int j;
2060
2061        iph=toma_parametro("iph",parametros); // Toma ip
2062    nwparametros[0]='\0';
2063        strcat(nwparametros,"tso="); // Compone retorno tso ( sistemas operativos de los clientes )
2064    for (j=0;j<MAXIMOS_SOCKETS;j++){
2065                if (strncmp(tbsockets[j].ip,"\0",1)!=0){ // Si es un cliente activo
2066                        if (IgualIP(iph,tbsockets[j].ip)){ // Si existe la IP en la cadena
2067                                 strcat( nwparametros, tbsockets[j].ip); // Compone retorno
2068                                 strcat( nwparametros,"/");                     // "ip=sistemaoperatico;"
2069                                 strcat( nwparametros, tbsockets[j].estado);
2070                                 strcat( nwparametros,";");
2071                        }
2072                }
2073        }
2074        return(manda_comando(s,nwparametros));
2075}
2076// ________________________________________________________________________________________________________
2077// Función: Actualizar
2078//
2079//              Descripción:
2080//                      Esta funcin actualiza la vista de ordenadores
2081//              Parámetros:
2082//                      - parametros: parametros del comando
2083// ________________________________________________________________________________________________________
2084int Actualizar(char *parametros)
2085{
2086        TRAMA *trama=(TRAMA*)malloc(LONGITUD_TRAMA);
2087        if(!trama)return(false);
2088        int i,estado_cliente,lon;
2089        char *iph,*rmb;
2090
2091        iph=toma_parametro("iph",parametros); // Toma ip
2092        rmb=toma_parametro("rmb",parametros); // Toma ipe del servidor rembo
2093        for (i=0;i<MAXIMOS_SOCKETS;i++){
2094                if (strncmp(tbsockets[i].ip,"\0",1)!=0){ // Si es un cliente activo
2095                        if (IgualIP(iph,tbsockets[i].ip)){ // Si existe la IP en la cadena
2096                                estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_OCUPADO);
2097                                if(estado_cliente!=0){ // Cliente NO OCUPADO ...
2098                                        estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_INICIANDO);
2099                                        if(estado_cliente!=0){ // Cliente NO INICIANDO ...
2100                                                estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_REMBO);
2101                                                if(estado_cliente!=0){ // Cliente windows o linux ...
2102                                                        lon=sprintf(trama->parametros,"nfn=Actualizar\r");
2103                                                        manda_comando(tbsockets[i].sock,(char*)trama->parametros);
2104                                                }
2105                                                borra_entrada(i);
2106                                        }
2107                                }
2108                        }
2109                }
2110        }
2111        int j;
2112        for (j=0;j<MAXIMOS_SRVRMB;j++){
2113                if (strcmp(rmb,tbsocketsSRVRMB[j].ip)==0){ // Si existe la IP ...
2114                        FINCADaINTRO(parametros,iph);
2115                        return(manda_trama_servidorrembo(rmb,parametros,tbsocketsSRVRMB[j].puertorepo));
2116                }
2117        }
2118        return(false);
2119}
2120// ________________________________________________________________________________________________________
2121// Función: FicheroOperador
2122//
2123//              Descripción:
2124//                      Esta funcin envia al servidor datos de un operador para crear fichero de login
2125//              Parámetros:
2126//                      - parametros: parametros del comando
2127// ________________________________________________________________________________________________________
2128int FicheroOperador(char *parametros)
2129{
2130        TRAMA trama;           
2131        SOCKET s;
2132        char *rmb,*amb,*usu,*psw,*ida;
2133        int resul,lon;
2134
2135        rmb=toma_parametro("rmb",parametros); // Toma ipe del servidor rembo
2136
2137        // Abre conexion con el servidor rembo y envia trama
2138        s=AbreConexion(rmb,puerto+1);
2139        if(!s){
2140                RegistraLog("Fallo al conectar con el servidor rembo para envio de tramas",true);
2141                return(FALSE);
2142        }
2143
2144        amb=toma_parametro("amb",parametros); // Toma tipo de operacion
2145        usu=toma_parametro("usu",parametros); // Toma usuario
2146        psw=toma_parametro("psw",parametros); // Toma passwrod
2147        ida=toma_parametro("ida",parametros); // Toma identificador del aula
2148
2149        // Envia la trama
2150        trama.arroba='@';
2151        strncpy(trama.identificador,"JMMLCAMDJ",9);
2152        trama.ejecutor='1';
2153        lon=sprintf(trama.parametros,"nfn=FicheroOperador\r");
2154        lon+=sprintf(trama.parametros+lon,"amb=%s\r",amb);
2155        lon+=sprintf(trama.parametros+lon,"usu=%s\r",usu);
2156        lon+=sprintf(trama.parametros+lon,"psw=%s\r",psw);
2157        lon+=sprintf(trama.parametros+lon,"ida=%s\r",ida);
2158        resul=(manda_trama(s,&trama));
2159        if(!resul)
2160                RegistraLog("Fallo en el envio de trama al servidor rembo",true);
2161        return(resul);
2162}
2163// ________________________________________________________________________________________________________
2164// Función: Conmutar
2165//
2166//              Descripción:
2167//                      Esta funcin conmuta un cliente rembo del modo NO administrado al modo admnistrado
2168//              Parámetros:
2169//                      - parametros: parametros del comando
2170// ________________________________________________________________________________________________________
2171int Conmutar(char *parametros)
2172{
2173        TRAMA trama;           
2174        SOCKET s;
2175        int i,estado_cliente,lon,resul;
2176        char *iph,*rmb;
2177
2178        iph=toma_parametro("iph",parametros); // Toma ip
2179        rmb=toma_parametro("rmb",parametros); // Toma ipe del servidor rembo
2180        for (i=0;i<MAXIMOS_SOCKETS;i++){
2181                if (strncmp(tbsockets[i].ip,"\0",1)!=0){ // Si es un cliente activo
2182                        if (IgualIP(iph,tbsockets[i].ip)){ // Si existe la IP en la cadena
2183                                estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_OCUPADO);
2184                                if(estado_cliente!=0){ // Cliente NO OCUPADO ...
2185                                        estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_INICIANDO);
2186                                        if(estado_cliente!=0){ // Cliente NO INICIANDO ...
2187                                                estado_cliente=strcmp(tbsockets[i].estado,CLIENTE_REMBO);
2188                                                if(estado_cliente!=0){ // Cliente windows o linux ...
2189                                                        lon=sprintf(trama.parametros,"nfn=Conmutar\r");
2190                                                        manda_comando(tbsockets[i].sock,trama.parametros);
2191                                                }
2192                                        }
2193                                }
2194                        }
2195                }
2196        }
2197
2198        // Abre conexion con el servidor rembo y envia trama
2199        s=AbreConexion(rmb,puerto+1);
2200        if(!s){
2201                RegistraLog("Fallo al conectar con el servidor rembo para envio de tramas",true);
2202                resul=FALSE;
2203        }
2204        else{
2205                // Envia la trama
2206                trama.arroba='@';
2207                strncpy(trama.identificador,"JMMLCAMDJ",9);
2208                trama.ejecutor='2';
2209                lon=sprintf(trama.parametros,"nfn=Conmutar\r");
2210                lon+=sprintf(trama.parametros+lon,"iph=%s\r",iph);
2211                resul=(manda_trama(s,&trama));
2212                if(!resul){
2213                        RegistraLog("Fallo en el envio de trama al servidor rembo",true);
2214                }
2215        }
2216        return(resul);
2217}
2218// ________________________________________________________________________________________________________
2219// Función: PurgarTablaSockets
2220//
2221//              Descripción:
2222//                      Borra ordenadores de la tabla de sockets
2223//              Parámetros:
2224//                      - parametros: parametros del comando
2225// ________________________________________________________________________________________________________
2226void PurgarTablaSockets(char *parametros)
2227{
2228        int i;
2229        char *iph;
2230
2231        iph=toma_parametro("iph",parametros); // Toma ip
2232    for (i=0;i<MAXIMOS_SOCKETS;i++){
2233                if (strncmp(tbsockets[i].ip,"\0",1)!=0){ // Si es un cliente activo
2234                        if (IgualIP(iph,tbsockets[i].ip)){ // Si existe la IP en la cadena
2235                                borra_entrada(i);
2236                        }
2237                }
2238        }
2239}
2240// _____________________________________________________________________________________________________________
2241// Función: Arrancar
2242//
2243//              Descripción:
2244//                      Esta función arranca los ordenadores solicitados. PAra ello le envía el comando arrancar al servidor rembo que lo controla y
2245//                      es éste el que le envía la trama de wake-up
2246//              Parámetros:
2247//                      - mac: Dirección mac del cliente rembo
2248//                      - iph: Dirección ip del cliente rembo
2249//                      - rmb: ip del servidor rembo
2250// _____________________________________________________________________________________________________________
2251int Arrancar(char *parametros)
2252{
2253        TRAMA *trama=(TRAMA*)malloc(LONGITUD_TRAMA);
2254        if(!trama)return(false);
2255        char *iph,*rmb,*mac;
2256        int j;
2257
2258        rmb=toma_parametro("rmb",parametros);
2259        mac=toma_parametro("mac",parametros);
2260        iph=toma_parametro("iph",parametros);
2261
2262        for (j=0;j<MAXIMOS_SRVRMB;j++){
2263                if (strcmp(rmb,tbsocketsSRVRMB[j].ip)==0){ // Si existe la IP ...
2264                        FINCADaINTRO(parametros,iph);
2265                        return(manda_trama_servidorrembo(rmb,parametros,tbsocketsSRVRMB[j].puertorepo));
2266                }
2267        }
2268        return(false);
2269}
2270// ________________________________________________________________________________________________________
2271// Función: RESPUESTA_Arrancar
2272//
2273//              Descripción:
2274//                      Responde al comando Apagar
2275//              Parámetros:
2276//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2277//                      - parametros: parametros del comando
2278// ________________________________________________________________________________________________________
2279int RESPUESTA_Arrancar(SOCKET s,char *parametros)
2280{
2281        char ErrStr[200];
2282        Database db;
2283        Table tbl;
2284       
2285        char *res,*der,*iph,*ido,*ids;
2286
2287        res=toma_parametro("res",parametros); // Toma resultado
2288        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2289        iph=toma_parametro("iph",parametros); // Toma ip
2290        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2291        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2292
2293        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2294                db.GetErrorErrStr(ErrStr);
2295                return(false);
2296        }
2297        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2298                return(false); // Error al registrar notificacion
2299        }
2300        db.Close();
2301        return(true);
2302}
2303// ________________________________________________________________________________________________________
2304// Función: RESPUESTA_Apagar
2305//
2306//              Descripción:
2307//                      Responde al comando Apagar
2308//              Parámetros:
2309//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2310//                      - parametros: parametros del comando
2311// ________________________________________________________________________________________________________
2312int RESPUESTA_Apagar(SOCKET s,char *parametros)
2313{
2314        char ErrStr[200];
2315        Database db;
2316        Table tbl;
2317        int i;
2318        char *res,*der,*iph,*ido,*ids;
2319
2320        res=toma_parametro("res",parametros); // Toma resultado
2321        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2322        iph=toma_parametro("iph",parametros); // Toma ip
2323        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2324        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2325
2326        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2327                db.GetErrorErrStr(ErrStr);
2328                return(false);
2329        }
2330        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2331                return(false); // Error al registrar notificacion
2332        }
2333
2334        if(strcmp(res,ACCION_FALLIDA)==0) return(TRUE); // Error en la ejecucin de la acción en el cliente rembo
2335
2336        if (cliente_existente(iph,&i)) // Si ya existe la IP ...
2337                borra_entrada(i);
2338        db.Close();
2339        return(true);
2340}
2341// ________________________________________________________________________________________________________
2342// Función: RESPUESTA_Reiniciar
2343//
2344//              Descripción:
2345//                      Responde al comando Reiniciar
2346//              Parámetros:
2347//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2348//                      - parametros: parametros del comando
2349// ________________________________________________________________________________________________________
2350int RESPUESTA_Reiniciar(SOCKET s,char *parametros)
2351{
2352        int i;
2353        char ErrStr[200];
2354        Database db;
2355        Table tbl;
2356       
2357        char *res,*der,*iph,*ido,*ids;
2358
2359        res=toma_parametro("res",parametros); // Toma resultado
2360        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2361        iph=toma_parametro("iph",parametros); // Toma ip
2362        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2363        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2364
2365        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2366                db.GetErrorErrStr(ErrStr);
2367                return(false);
2368        }
2369        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2370                return(false); // Error al registrar notificacion
2371        }
2372        if(strcmp(res,ACCION_FALLIDA)==0) return(TRUE); // Error en la ejecucin de la acción en el cliente rembo
2373
2374        if (cliente_existente(iph,&i)) // Si ya existe la IP ...
2375                borra_entrada(i);
2376        db.Close();
2377        return(true);
2378}
2379// ________________________________________________________________________________________________________
2380// Función: RESPUESTA_Apagar
2381//
2382//              Descripción:
2383//                      Responde al comando Apagar
2384//              Parámetros:
2385//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2386//                      - parametros: parametros del comando
2387// ________________________________________________________________________________________________________
2388int RESPUESTA_IniciarSesion(SOCKET s,char *parametros)
2389{
2390        char ErrStr[200];
2391        Database db;
2392        Table tbl;
2393        int i;
2394        char *res,*der,*iph,*ido,*ids;
2395
2396        res=toma_parametro("res",parametros); // Toma resultado
2397        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2398        iph=toma_parametro("iph",parametros); // Toma ip
2399        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2400        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2401
2402        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2403                db.GetErrorErrStr(ErrStr);
2404                return(false);
2405        }
2406        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2407                return(false); // Error al registrar notificacion
2408        }
2409
2410        if(strcmp(res,ACCION_FALLIDA)==0) return(TRUE); // Error en la ejecucin de la acción en el cliente rembo
2411
2412        if (cliente_existente(iph,&i)) // Si ya existe la IP ...
2413                borra_entrada(i);
2414        db.Close();
2415        return(true);
2416}
2417// ________________________________________________________________________________________________________
2418//
2419// Función: borra_entrada
2420//
2421//              Descripción:
2422//                       Borra la entrada de un ordenador en la tabla de socket
2423//              Parámetros:
2424//                      - i: Indice dentro de la tabla
2425// ________________________________________________________________________________________________________
2426int borra_entrada(int i)
2427{
2428        tbsockets[i].ip[0]=(char)NULL;
2429        tbsockets[i].estado[0]=(char)NULL;
2430        if(!tbsockets[i].sock)
2431                        close(tbsockets[i].sock);
2432        tbsockets[i].sock=INVALID_SOCKET;
2433        //tbsockets[i].ipsrvdhcp[0]=(char)NULL;
2434        tbsockets[i].ipsrvrmb[0]=(char)NULL;
2435
2436        return(true);
2437}
2438// ________________________________________________________________________________________________________
2439// Función: RESPUESTA_ExecShell
2440//
2441//              Descripción:
2442//                      Responde al comando Ejecutar script
2443//              Parámetros:
2444//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2445//                      - parametros: parametros del comando
2446// ________________________________________________________________________________________________________
2447int RESPUESTA_ExecShell(SOCKET s,char *parametros)
2448{
2449        char ErrStr[200];
2450        Database db;
2451        Table tbl;
2452       
2453        char *res,*der,*ids,*iph,*ido,*cfg;
2454
2455        res=toma_parametro("res",parametros); // Toma resultado
2456        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2457        ids=toma_parametro("ids",parametros); // Toma idperfilsoft
2458        iph=toma_parametro("iph",parametros); // Toma ip
2459        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2460        cfg=toma_parametro("cfg",parametros); // Toma configuracin
2461       
2462        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2463                db.GetErrorErrStr(ErrStr);
2464                return(false);
2465        }
2466        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2467                return(false); // Error al registrar notificacion
2468        }
2469
2470        if(strcmp(res,ACCION_FALLIDA)!=0) { // Ha habido algn error en la ejecucin de la acción del cliente rembo
2471                if(!actualiza_configuracion(db,tbl,cfg,0,0,iph)) // El ordenador ha cambiado de configuracin
2472                        return(false);
2473        }
2474        db.Close();
2475        return(true);
2476}
2477// ________________________________________________________________________________________________________
2478// Función: RespuestaEstandar
2479//
2480//              Descripción:
2481//                      Esta funcin actualiza la base de datos con el resultado de la ejecucin de un comando con seguimiento
2482//              Parámetros:
2483//                      - res: resultado de la ejecucin del comando
2484//                      - der: Descripción del error si hubiese habido
2485//                      - ids: identificador de la acción notificada
2486//                      - ido: Identificador del ordenador que notifica
2487//                      - db: Objeto base de datos (operativo)
2488//                      - tbl: Objeto tabla
2489// ________________________________________________________________________________________________________
2490int RespuestaEstandar(char *res,char *der,char *ids,char* ido,Database db,Table tbl)
2491{
2492        char ErrStr[200],sqlstr[1000];
2493        char parametros[LONGITUD_PARAMETROS];
2494        char fechareg[100];
2495        int i,resul;
2496        int idaccion,accionid,idnotificador;
2497        char *iph;
2498    struct tm* st;
2499
2500        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2501        // ACCESO atnico A TRAVEZ DE OBJETO MUTEX a este trozo de cnigo
2502        pthread_mutex_lock(&guardia);
2503
2504        sprintf(sqlstr,"Select * from acciones WHERE idaccion=%s",ids);
2505        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2506                db.GetErrorErrStr(ErrStr);
2507                                pthread_mutex_unlock(&guardia);
2508                return(false);
2509        }
2510        if(tbl.ISEOF()){ // No existe registro de acciones
2511                                pthread_mutex_unlock(&guardia);
2512                return(true);
2513        }
2514        if(!tbl.Get("parametros",parametros)){ // Toma parametros de la acción
2515                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
2516                                        pthread_mutex_unlock(&guardia);
2517                        return(false);
2518        }
2519        char resultado[2]; // comprueba si ya ha fallado la acción
2520        if(!tbl.Get("resultado",resultado)){ // Toma resultado actual de la acción
2521                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
2522                                        pthread_mutex_unlock(&guardia);
2523                        return(false);
2524        }
2525        if(!tbl.Get("idaccion",idaccion)){ // Toma el identificador de la acción para tener el dato en formato "int"
2526                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
2527                                        pthread_mutex_unlock(&guardia);
2528                        return(false);
2529        }
2530        if(!tbl.Get("accionid",accionid)){ // Toma la accion padre
2531                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
2532                                        pthread_mutex_unlock(&guardia);
2533                        return(false);
2534        }
2535        if(!tbl.Get("idnotificador",idnotificador)){ // Toma el identificador del notificador
2536                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
2537                                        pthread_mutex_unlock(&guardia);
2538                        return(false);
2539        }
2540       
2541    st=TomaHora();
2542        sprintf(fechareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
2543
2544        // Graba notificacin
2545        sprintf(sqlstr,"INSERT INTO notificaciones (accionid,idnotificador,fechahorareg,resultado,descrinotificacion) VALUES (%s,%s,'%s','%s','%s')",ids,ido,fechareg,res,der);
2546        if(!db.Execute(sqlstr)){ // Error al insertar
2547                db.GetErrorErrStr(ErrStr);
2548                                pthread_mutex_unlock(&guardia);
2549                return(false);
2550        }
2551 
2552        if(strcmp(res,ACCION_FALLIDA)==0 && strcmp(resultado,ACCION_SINERRORES)==0){ // Accion fallida en el cliente rembo
2553                sprintf(sqlstr,"Update acciones set resultado='%s' WHERE idaccion=%s",ACCION_CONERRORES,ids);
2554                strcpy(resultado,ACCION_CONERRORES);
2555                if(!db.Execute(sqlstr)){ // Error al actualizar
2556                        db.GetErrorErrStr(ErrStr);
2557                                        pthread_mutex_unlock(&guardia);
2558                        return(false);
2559                }
2560        }
2561        // Comprueba si la acción se ejecutncorrectamente para el ambito sumando notificaciones
2562        INTROaFINCAD(parametros);
2563        iph=toma_parametro("iph",parametros); // Toma cadenaip
2564        int tbnumipes=0,totalipes=1,lon;
2565
2566        lon=strlen(iph);
2567        for (i=0;i<lon;i++){
2568                if(iph[i]==';')
2569                        totalipes++; // ip detectada
2570        }
2571       
2572        sprintf(sqlstr,"SELECT COUNT(*) AS tbnumipes FROM notificaciones WHERE accionid=%s",ids);
2573        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
2574                                pthread_mutex_unlock(&guardia);
2575                db.GetErrorErrStr(ErrStr);
2576                                pthread_mutex_unlock(&guardia);
2577                return(false);
2578        }
2579               
2580        if(!tbl.Get("tbnumipes",tbnumipes)){ // Recupera el numero de ordenadores que ya han notificado
2581                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo
2582                                        pthread_mutex_unlock(&guardia);
2583                        return(false);
2584        }
2585        if(tbnumipes!=totalipes){
2586                                pthread_mutex_unlock(&guardia);
2587                return(true); // No es el ultimo ordenador en notificar
2588        }
2589
2590    st=TomaHora();
2591        sprintf(fechareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
2592
2593        // Actualizacion despues de que todos los ordenadores han notificado
2594        if(strcmp(resultado,ACCION_SINERRORES)==0){ // Accion finalizada con exito
2595                sprintf(sqlstr,"Update acciones set estado='%s',resultado='%s',fechahorafin='%s' WHERE idaccion=%s",ACCION_FINALIZADA,ACCION_EXITOSA,fechareg,ids);
2596                if(!db.Execute(sqlstr,tbl)){ // Error al actualizar
2597                        db.GetErrorErrStr(ErrStr);
2598                                        pthread_mutex_unlock(&guardia);
2599                        return(false);
2600                }
2601        }
2602        if(strcmp(resultado,ACCION_CONERRORES)==0){ // Accion finalizada con errores
2603                sprintf(sqlstr,"Update acciones set estado='%s',resultado='%s',fechahorafin='%s' WHERE idaccion=%s",ACCION_FINALIZADA,ACCION_FALLIDA,fechareg,ids);
2604                if(!db.Execute(sqlstr,tbl)){ // Error al actualizar
2605                        db.GetErrorErrStr(ErrStr);
2606                                        pthread_mutex_unlock(&guardia);
2607                        return(false);
2608                }
2609        }
2610        resul=true;
2611        if(accionid>0){ // Existe accion padre que hay que actualizar
2612                resul=InsertaNotificaciones(idaccion,idnotificador,accionid,resultado,db);
2613                if(resul)
2614                        resul=comprueba_resultados(accionid,db);
2615        }
2616                        pthread_mutex_unlock(&guardia);
2617        //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
2618        return(resul);
2619}
2620// ________________________________________________________________________________________________________
2621// Función: RESPUESTA_CrearPerfilSoftware
2622//
2623//              Descripción:
2624//                      Responde al comando Crear Perfil Software
2625//              Parámetros:
2626//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2627//                      - parametros: parametros del comando
2628// ________________________________________________________________________________________________________
2629int RESPUESTA_CrearPerfilSoftware(SOCKET s,char *parametros)
2630{
2631        char ErrStr[200],sqlstr[1000];
2632        char *res,*der,*ids,*ifh,*ifs,*iph,*ido;
2633        Database db;
2634        Table tbl;
2635       
2636        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2637                db.GetErrorErrStr(ErrStr);
2638                return(false);
2639        }
2640
2641        res=toma_parametro("res",parametros); // Toma resultado
2642        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2643        ids=toma_parametro("ids",parametros); // Toma idperfilsoft
2644        iph=toma_parametro("iph",parametros); // Toma ip
2645        ido=toma_parametro("ido",parametros); // Toma dentificador del ordenador
2646        ifh=toma_parametro("ifh",parametros); // Toma idperfilhard
2647        ifs=toma_parametro("ifs",parametros); // Toma idperfilsoft
2648
2649        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2650                return(false); // Error al registrar notificacion
2651        }
2652
2653        if(strcmp(res,ACCION_FALLIDA)==0) { // Ha habido algn error en la ejecucin de la acción en el cliente rembo
2654                db.Close();
2655                return(false);
2656        }
2657
2658        sprintf(sqlstr,"Select * from perfileshard_perfilessoft WHERE idperfilhard=%s AND idperfilsoft=%s",ifh,ifs);
2659        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2660                db.GetErrorErrStr(ErrStr);
2661                return(false);
2662        }
2663        if(!tbl.ISEOF()){ // Si ya existe el registro ... no hace falta insertarlo
2664                db.Close();
2665                return(false); 
2666        }
2667        sprintf(sqlstr,"INSERT INTO perfileshard_perfilessoft (idperfilhard,idperfilsoft) VALUES(%s,%s)",ifh,ifs);
2668        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
2669                db.GetErrorErrStr(ErrStr);
2670                return(false);
2671        }
2672        db.Close();
2673        return(true);
2674}
2675// ________________________________________________________________________________________________________
2676// Función: RESPUESTA_CrearSoftwareIncremental
2677//
2678//              Descripción:
2679//                      Esta funcin responde a un comando de creacin de un software incremental. Ademn actualiza  la base de datos insertando
2680//                      en su caso la nueva combinacin de perfil software con incremental.
2681//              Parámetros:
2682//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2683//                      - parametros: parametros del comando
2684// ________________________________________________________________________________________________________
2685int RESPUESTA_CrearSoftwareIncremental(SOCKET s,char *parametros)
2686{
2687        char ErrStr[200],sqlstr[1000];
2688        char *res,*der,*ids,*ifh,*ifs,*icr,*iph,*ido;
2689        int idphardidpsoft;
2690        Database db;
2691        Table tbl;
2692       
2693        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2694                db.GetErrorErrStr(ErrStr);
2695                return(false);
2696        }
2697
2698        res=toma_parametro("res",parametros); // Toma resultado
2699        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2700        ids=toma_parametro("ids",parametros); // Toma idperfilsoft
2701        iph=toma_parametro("iph",parametros); // Toma ip
2702        ido=toma_parametro("ido",parametros); // Toma dentificador del ordenador
2703        ifh=toma_parametro("ifh",parametros); // Toma idperfilhard
2704        ifs=toma_parametro("ifs",parametros); // Toma idperfilsoft
2705        icr=toma_parametro("icr",parametros); // Toma idsoftincremental
2706
2707        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2708                return(false); // Error al registrar notificacion
2709        }
2710
2711        if(strcmp(res,ACCION_FALLIDA)==0) { // Ha habido algn error en la ejecucin de la acción en el cliente rembo
2712                db.Close();
2713                return(false);
2714        }
2715
2716        sprintf(sqlstr,"Select idphardidpsoft from perfileshard_perfilessoft WHERE idperfilhard=%s AND idperfilsoft=%s",ifh,ifs);
2717        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2718                db.GetErrorErrStr(ErrStr);
2719                return(false);
2720        }
2721
2722        if(tbl.ISEOF()){ // Si no existe el registro ...
2723                db.Close();
2724                return(false); 
2725        }
2726
2727        if(!tbl.Get("idphardidpsoft",idphardidpsoft)){ // Recupera el identificador de la combinacin de perfiles
2728                tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo
2729                return(false);
2730        }
2731
2732        sprintf(sqlstr,"Select * from phard_psoft_softincremental WHERE idphardidpsoft=%d AND idsoftincremental=%s",idphardidpsoft,icr);
2733        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2734                db.GetErrorErrStr(ErrStr);
2735                return(false);
2736        }
2737
2738        if(!tbl.ISEOF()){ // Si ya existe el registro ...
2739                db.Close();
2740                return(false); 
2741        }
2742
2743        sprintf(sqlstr,"INSERT INTO phard_psoft_softincremental (idphardidpsoft,idsoftincremental) VALUES(%d,%s)",idphardidpsoft,icr);
2744        if(!db.Execute(sqlstr,tbl)){ // Error al insertar
2745                db.GetErrorErrStr(ErrStr);
2746                return(false);
2747        }
2748        db.Close();     
2749        return(true);
2750}
2751// ________________________________________________________________________________________________________
2752// Función: RESPUESTA_RestaurarImagen
2753//
2754//              Descripción:
2755//                      Esta funcin responde a un comando de restauracin de una imagen. Ademn actualiza  la base de datos.
2756//              Parámetros:
2757//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2758//                      - parametros: parametros del comando
2759// ________________________________________________________________________________________________________
2760int RESPUESTA_RestaurarImagen(SOCKET s,char *parametros)
2761{
2762        char ErrStr[200],gido[20];
2763        char *res,*der,*ids,*iph,*ido,*idi,*par,*cfg;
2764        Database db;
2765        Table tbl;
2766
2767        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2768                db.GetErrorErrStr(ErrStr);
2769                return(false);
2770        }
2771
2772        INTROaFINCAD(parametros);
2773
2774        res=toma_parametro("res",parametros); // Toma resultado
2775        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2776        ids=toma_parametro("ids",parametros); // Toma identificador de la accion
2777        iph=toma_parametro("iph",parametros); // Toma ip
2778        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2779        cfg=toma_parametro("cfg",parametros); // Toma configuracin
2780        par=toma_parametro("par",parametros); // particion
2781        idi=toma_parametro("idi",parametros); // identificador de la imagen
2782
2783        strcpy(gido,ido); // Guarda el identificador del ordenador
2784
2785        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2786                return(false); // Error al registrar notificacion
2787        }
2788        if(strcmp(res,ACCION_FALLIDA)==0) { // Ha habido algn error en la ejecucin de la acción del cliente rembo
2789                db.Close();
2790                return(false);
2791        }
2792
2793        if(!actualiza_configuracion(db,tbl,cfg,0,0,iph))        return(false); // Erro al actualiza la configuracin
2794        if(!Actualiza_ordenador_imagen(par,idi,gido,db)) return(false);
2795        db.Close();
2796        return(true);   
2797}
2798// ________________________________________________________________________________________________________
2799// Función: Actualiza_ordenador_imagen
2800//
2801//              Descripción:
2802//                      Esta funcin actualiza la tabla ordenador_imagen
2803//              Parámetros:
2804//                      - par: particion
2805//                      - idi: identificador de la imagen ( 0 ninguna )
2806//                      - ido: identificador del ordenador
2807//                      - db: Conexin ADO operativa
2808// ________________________________________________________________________________________________________
2809int Actualiza_ordenador_imagen(char *par,const char *idi,char *ido,Database db)
2810{
2811        char ErrStr[200],sqlstr[1000];
2812        Table tbl;
2813        int idimagen,idimagenres;
2814
2815        idimagenres=atoi(idi);
2816        if(idimagenres==0){ // Se ha formateado la particin y se ha borrado la imagen por tanto
2817                sprintf(sqlstr,"DELETE FROM ordenador_imagen WHERE idordenador=%s AND particion=%s",ido,par);
2818                if(!db.Execute(sqlstr)){ // Error al insertar
2819                        db.GetErrorErrStr(ErrStr);
2820                        return(false);
2821                }
2822                return(true);
2823        }
2824
2825        sprintf(sqlstr,"SELECT idimagen FROM ordenador_imagen INNER JOIN ordenadores ON ordenador_imagen.idordenador = ordenadores.idordenador WHERE ordenadores.idordenador = %s AND ordenador_imagen.particion = %s",ido,par);
2826        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
2827                db.GetErrorErrStr(ErrStr);
2828                return(false);
2829        }
2830        if(!tbl.ISEOF()){ // Existe registro
2831                if(!tbl.Get("idimagen",idimagen)){
2832                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
2833                        return(false);
2834                }
2835                else{
2836                        if (idimagenres!=idimagen){
2837                                sprintf(sqlstr,"Update ordenador_imagen set idimagen=%s WHERE idordenador=%s AND particion=%s",idi,ido,par);
2838                                if(!db.Execute(sqlstr)){ // Error al actualizar
2839                                        db.GetErrorErrStr(ErrStr);
2840                                        return(false);
2841                                }
2842                        }
2843                }
2844        }
2845        else{ // No existe el registro
2846                        sprintf(sqlstr,"INSERT INTO ordenador_imagen (idordenador,particion,idimagen) VALUES(%s,%s,%s)",ido,par,idi);
2847                        if(!db.Execute(sqlstr)){ // Error al insertar
2848                                db.GetErrorErrStr(ErrStr);
2849                                return(false);
2850                        }
2851        }
2852        return(true);
2853}
2854// ________________________________________________________________________________________________________
2855// Función: RESPUESTA_ParticionaryFormatear
2856//
2857//              Descripción:
2858//                      Esta funcin responde a un comando de particionar y formatear.  Ademn actualiza  la base de datos.
2859//              Parámetros:
2860//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2861//                      - parametros: parametros del comando
2862// ________________________________________________________________________________________________________
2863int RESPUESTA_ParticionaryFormatear(SOCKET s,char *parametros)
2864{
2865        char sqlstr[1000],ErrStr[200],gido[20];
2866        Database db;
2867        Table tbl;
2868        char *res,*der,*ids,*iph,*ido,*cfg;
2869
2870        res=toma_parametro("res",parametros); // Toma resultado
2871        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2872        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2873        iph=toma_parametro("iph",parametros); // Toma ip
2874        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2875        cfg=toma_parametro("cfg",parametros); // Toma configuracin
2876       
2877        strcpy(gido,ido); // Guarda el identificador del ordenador
2878
2879        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2880                db.GetErrorErrStr(ErrStr);
2881                return(false);
2882        }
2883        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2884                return(false); // Error al registrar notificacion
2885        }
2886        if(strcmp(res,ACCION_FALLIDA)==0){
2887                db.Close();
2888                 return(true); // Ha habido algn error en la ejecucin de la acción del cliente rembo
2889        }
2890        if(!actualiza_configuracion(db,tbl,cfg,0,0,iph))        return(false); // Erro al actualiza la configuracin
2891
2892        // Elimina informacin sobre imagenes en este ordenador, al haber sido formateado
2893        sprintf(sqlstr,"DELETE FROM ordenador_imagen WHERE idordenador=%s",gido);
2894        if(!db.Execute(sqlstr)){ // Error al insertar
2895                db.GetErrorErrStr(ErrStr);
2896                return(false);
2897        }
2898        db.Close();
2899        return(true);
2900}
2901// ________________________________________________________________________________________________________
2902// Función: RESPUESTA_Configurar
2903//
2904//              Descripción:
2905//                      Esta funcin responde a un comando de Configurar.  Ademn actualiza  la base de datos.
2906//              Parámetros:
2907//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2908//                      - parametros: parametros del comando
2909// ________________________________________________________________________________________________________
2910int RESPUESTA_Configurar(SOCKET s,char *parametros)
2911{
2912        char ErrStr[200],gids[20],gido[20];
2913        Database db;
2914        Table tbl;
2915        int lon,resul,i;
2916        char *res,*der,*ids,*iph,*ido,*cfg,*hdc;
2917
2918        res=toma_parametro("res",parametros); // Toma resultado
2919        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2920        ids=toma_parametro("ids",parametros); // Toma idperfilsoft
2921        iph=toma_parametro("iph",parametros); // Toma ip
2922        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2923        cfg=toma_parametro("cfg",parametros); // Toma configuracin
2924        hdc=toma_parametro("hdc",parametros); // Toma participaciones a formatear
2925
2926        strcpy(gids,ids); // Guarda el identificador de la acción
2927        strcpy(gido,ido); // Guarda el identificador del ordenador
2928
2929        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2930                db.GetErrorErrStr(ErrStr);
2931                return(false);
2932        }
2933        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2934                return(false); // Error al registrar notificacion
2935        }
2936
2937        if(strcmp(res,ACCION_FALLIDA)==0){
2938                db.Close();
2939                 return(true); // Ha habido algn error en la ejecucin de la acción del cliente rembo
2940        }
2941        if(!actualiza_configuracion(db,tbl,cfg,0,0,iph))        return(false); // Erro al actualiza la configuracin
2942       
2943        lon=strlen(hdc);
2944        for(i=0;i<lon;i++){
2945                if(hdc[i]==';') hdc[i]='\0';
2946        }
2947        for(i=0;i<lon;i++){
2948                if(*hdc!='\0'){
2949                        resul=Actualiza_ordenador_imagen(hdc,"0",gido,db);
2950                        if(!resul){
2951                                db.Close();
2952                                 return(false);
2953                        }
2954                }
2955                hdc++;
2956        }
2957        db.Close();
2958        return(true);
2959}
2960// ________________________________________________________________________________________________________
2961// Función: RESPUESTA_TomaConfiguracion
2962//
2963//              Descripción:
2964//                      Esta funcin responde a un comando de Toma Comfiguracin.  Ademn actualiza  la base de datos.
2965//              Parámetros:
2966//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
2967//                      - parametros: parametros del comando
2968// ________________________________________________________________________________________________________
2969int RESPUESTA_TomaConfiguracion(SOCKET s,char *parametros)
2970{
2971        char ErrStr[200];
2972        Database db;
2973        Table tbl;
2974       
2975        char *res,*der,*ids,*iph,*ido,*cfg;
2976
2977        res=toma_parametro("res",parametros); // Toma resultado
2978        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
2979        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
2980        iph=toma_parametro("iph",parametros); // Toma ip
2981        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
2982        cfg=toma_parametro("cfg",parametros); // Toma configuracin
2983       
2984        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
2985                db.GetErrorErrStr(ErrStr);
2986                return(false);
2987        }
2988        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
2989                return(false); // Error al registrar notificacion
2990        }
2991        if(strcmp(res,ACCION_FALLIDA)!=0) { // Ha habido algn error en la ejecucin de la acción del cliente rembo
2992                if(!actualiza_configuracion(db,tbl,cfg,0,0,iph)) // El ordenador ha cambiado de configuracin
2993                        return(false);
2994        }
2995        db.Close();
2996        return(true);
2997}
2998// ________________________________________________________________________________________________________
2999// Función: RESPUESTA_TomaHardware
3000//
3001//              Descripción:
3002//                      Esta funcin responde a un comando de Toma HArdware.  Ademn actualiza  la base de datos.
3003//              Parámetros:
3004//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
3005//                      - parametros: parametros del comando
3006// ________________________________________________________________________________________________________
3007int RESPUESTA_TomaHardware(SOCKET s,char *parametros)
3008{
3009        char ErrStr[200];
3010        Database db;
3011        Table tbl;
3012       
3013        char *res,*der,*ids,*iph,*ido,*hrd;
3014
3015        res=toma_parametro("res",parametros); // Toma resultado
3016        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
3017        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
3018        iph=toma_parametro("iph",parametros); // Toma ip
3019        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
3020       
3021        hrd=toma_parametro("hrd",parametros); // Toma configuracin
3022       
3023        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
3024                db.GetErrorErrStr(ErrStr);
3025                return(false);
3026        }
3027        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
3028                return(false); // Error al registrar notificacion
3029        }
3030        if(strcmp(res,ACCION_FALLIDA)!=0) { // Ha habido algn error en la ejecucin de la acción del cliente rembo
3031                if(!actualiza_hardware(db,tbl,hrd,iph,ido)) // El ordenador ha cambiado de configuracin
3032                        return(false);
3033        }
3034        db.Close();
3035        return(true);
3036}
3037// ________________________________________________________________________________________________________
3038// Función: RESPUESTA_TomaSoftware
3039//
3040//              Descripción:
3041//                      Esta funcin responde a un comando de Inventario Software.  Además actualiza  la base de datos.
3042//              Parámetros:
3043//                      - s: Socket que el cliente rembo usa para comunicarse con el servidor HIDRA
3044//                      - parametros: parametros del comando
3045// ________________________________________________________________________________________________________
3046int RESPUESTA_TomaSoftware(SOCKET s,char *parametros)
3047{
3048        char ErrStr[200];
3049        Database db;
3050        Table tbl;
3051       
3052        char *res,*der,*ids,*iph,*ido,*sft,*par,*tfs;
3053
3054        res=toma_parametro("res",parametros); // Toma resultado
3055        der=toma_parametro("der",parametros); // Toma descripcin del error ( si hubiera habido)
3056        ids=toma_parametro("ids",parametros); // Toma identificador de la acción
3057        iph=toma_parametro("iph",parametros); // Toma ip
3058        ido=toma_parametro("ido",parametros); // Toma identificador del ordenador
3059       
3060        sft=toma_parametro("sft",parametros); // Toma software
3061        par=toma_parametro("par",parametros); // Toma partición
3062        tfs=toma_parametro("tfs",parametros); // Toma tipo partición
3063       
3064        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
3065                db.GetErrorErrStr(ErrStr);
3066                return(false);
3067        }
3068        if(!RespuestaEstandar(res,der,ids,ido,db,tbl)){
3069                return(false); // Error al registrar notificacion
3070        }
3071        if(strcmp(res,ACCION_FALLIDA)!=0) { // Ha habido algn error en la ejecucin de la acción del cliente rembo
3072                if(!actualiza_software(db,tbl,sft,par,tfs,iph,ido)) // El ordenador ha cambiado de configuracin
3073                        return(false);
3074        }
3075        db.Close();
3076        return(true);
3077}
3078// ________________________________________________________________________________________________________
3079// Función: busca_comandos
3080//
3081//              Descripción:
3082//                      Esta funcin busca en la base de datos,comandos pendientes de ejecutar   para el ordenador cocreto
3083//              Parámetros:
3084//                      - iph: Direccin IP del ordenador
3085//                      - ido: Identificador del ordenador
3086//                      - parametros: parametros de la acción buscada
3087//                      - ids: Identificador de la acción
3088// ________________________________________________________________________________________________________
3089int busca_comandos(char* iph,char *ido,char *parametros,int *ids)
3090{
3091        char sqlstr[1000],ErrStr[200];
3092        Database db;
3093        Table tbl,tbln;
3094
3095        if(!db.Open(usuario,pasguor,datasource,catalog)){ // error de conexion
3096                db.GetErrorErrStr(ErrStr);
3097                return(false);
3098        }
3099        sprintf(sqlstr,"SELECT idaccion,resultado,estado,parametros FROM acciones WHERE tipoaccion=%d AND estado = '%s' AND (resultado='%s' OR resultado='%s') AND parametros LIKE '%c%s%c' ORDER BY idaccion",EJECUCION_COMANDO,ACCION_INICIADA,ACCION_SINERRORES,ACCION_CONERRORES,37,iph,37);
3100        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3101                db.GetErrorErrStr(ErrStr);
3102                return(false);
3103        }
3104        if(tbl.ISEOF()){
3105                db.Close();
3106                return(false);  // No hay comandos pendientes
3107        }
3108
3109        while(!tbl.ISEOF()){ // Busca entre todas las acciones de diversos ambitos
3110
3111                if(!tbl.Get("parametros",parametros)){ // Toma parametros
3112                                tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo parametros
3113                                return(false);
3114                }
3115
3116                if(IgualIP(parametros,iph)){ // Si existe la IP en la cadena
3117                        if(!tbl.Get("idaccion",*ids)){ // Toma identificador de la acción
3118                                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3119                                return(false);
3120                        }
3121
3122                        // Comprueba que aunque el resultado es ACCION_INICIADA, este ordenador an no ha notificado
3123                        sprintf(sqlstr,"SELECT idnotificador FROM notificaciones WHERE accionid=%d AND idnotificador=%s",*ids,ido);
3124                        if(!db.Execute(sqlstr,tbln)){ // Error al leer
3125                                db.GetErrorErrStr(ErrStr);
3126                                return(false);
3127                        }
3128                        if(tbln.ISEOF()){
3129                                db.Close();                             
3130                                return(true);  // No ha notificado este ordenador
3131                        }
3132                }
3133                tbl.MoveNext();
3134        }
3135        db.Close();
3136        return(false);  // No hay mn acciones
3137}
3138// ________________________________________________________________________________________________________
3139int InsertaNotificaciones(int idaccion,int idnotificador, int accionid, char *resultado,Database db){
3140       
3141    struct tm* st;
3142        char ErrStr[200],sqlstr[1000];
3143        char fechahorareg[100];
3144        char descrinotificacion[100];
3145
3146
3147    st=TomaHora();
3148        sprintf(fechahorareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
3149
3150        strcpy(descrinotificacion," ");
3151
3152        if(strcmp(resultado,ACCION_CONERRORES)==0) {
3153                strcpy(descrinotificacion,"Ha ocurrido algn error en la ejecucin de esta tarea.");
3154                strcpy(resultado,ACCION_FALLIDA);
3155        }
3156        if(strcmp(resultado,ACCION_SINERRORES)==0)
3157                strcpy(resultado,ACCION_EXITOSA);
3158       
3159        sprintf(sqlstr,"INSERT INTO notificaciones (accionid,idnotificador,fechahorareg,resultado,descrinotificacion,idaccion) VALUES (%d,%d,'%s','%s','%s',%d)",accionid,idnotificador,fechahorareg,resultado,descrinotificacion,idaccion);
3160        if(!db.Execute(sqlstr)){ // Error al insertar
3161                db.GetErrorErrStr(ErrStr);
3162                return(false);
3163        }
3164        return(true);
3165}
3166// ________________________________________________________________________________________________________
3167int comprueba_resultados(int idaccion,Database db){
3168
3169        char ErrStr[200],sqlstr[1000];
3170        int numfallidas;
3171        char finalaccion[2];
3172        Table tbl;
3173
3174        sprintf(sqlstr,"SELECT COUNT(*) as numfallidas FROM notificaciones WHERE resultado='%s' AND accionid=%d",ACCION_FALLIDA,idaccion);
3175        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
3176                db.GetErrorErrStr(ErrStr);
3177                return(false);
3178        }
3179        if(tbl.ISEOF()) return(false); // No existe registro de acciones
3180               
3181        if(!tbl.Get("numfallidas",numfallidas)){ // Toma dato
3182                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3183                        return(false);
3184        }
3185
3186        if(numfallidas>0)
3187                strcpy(finalaccion,ACCION_CONERRORES);
3188        else
3189                strcpy(finalaccion,ACCION_SINERRORES);
3190
3191        sprintf(sqlstr,"UPDATE acciones SET resultado='%s' WHERE idaccion=%d",finalaccion,idaccion);
3192        if(!db.Execute(sqlstr,tbl)){ // Error al actualizar
3193                db.GetErrorErrStr(ErrStr);
3194                return(false);
3195        }
3196        // Comprueba si ha finalizado esta acción e inserta su notificador correspondiente
3197        return(comprueba_finalizada(idaccion,finalaccion,db));
3198}
3199// ________________________________________________________________________________________________________
3200int comprueba_finalizada(int idaccion,char *resultado,Database db){
3201
3202        char ErrStr[200],sqlstr[1000];
3203        int numnotificaciones,tipoaccion,idnotificador;
3204        char parametros[LONGITUD_PARAMETROS],*cadenanot;
3205        char fechareg[100];
3206        int accionid,cont,i,resul,lon;
3207        Table tbl;
3208    struct tm* st;
3209
3210        sprintf(sqlstr,"SELECT COUNT(*) as numnotificaciones FROM notificaciones WHERE accionid=%d",idaccion);
3211        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
3212                db.GetErrorErrStr(ErrStr);
3213                return(false);
3214        }
3215        if(tbl.ISEOF()) return(false); // No existe registro de acciones
3216
3217        if(!tbl.Get("numnotificaciones",numnotificaciones)){ // Toma dato
3218                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3219                        return(false);
3220        }
3221
3222        sprintf(sqlstr,"SELECT tipoaccion,parametros,idnotificador,accionid FROM acciones WHERE idaccion=%d",idaccion);
3223        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
3224                db.GetErrorErrStr(ErrStr);
3225                return(false);
3226        }
3227        if(tbl.ISEOF()) return(true); // No existe registro de acciones
3228               
3229        if(!tbl.Get("tipoaccion",tipoaccion)){ // Toma dato
3230                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
3231                        return(false);
3232        }
3233        if(!tbl.Get("parametros",parametros)){ // Toma dato
3234                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
3235                        return(false);
3236        }
3237        if(!tbl.Get("idnotificador",idnotificador)){ // Toma dato
3238                        tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
3239                        return(false);
3240        }
3241        if(!tbl.Get("accionid",accionid)){ // Toma dato
3242                                tbl.GetErrorErrStr(ErrStr); // error al recuperar el campo resultado
3243                                return(false);
3244        }
3245
3246        INTROaFINCAD(parametros);
3247        switch(tipoaccion){
3248                case EJECUCION_COMANDO :
3249                        cadenanot=toma_parametro("iph",parametros); // Toma cadenaip
3250                        break;
3251                case EJECUCION_TAREA :
3252                        cadenanot=toma_parametro("cmd",parametros); // Toma comandos
3253                        break;
3254                case EJECUCION_TRABAJO :
3255                        cadenanot=toma_parametro("tsk",parametros); // Toma tareas
3256                        break;
3257                default:
3258                        return(false);
3259        }
3260        cont=1;
3261        lon=strlen(cadenanot);
3262        for (i=0;i<lon;i++){
3263                if(cadenanot[i]==';') cont++;
3264        }
3265        resul=true;
3266        if(numnotificaciones==cont){
3267                st=TomaHora();
3268                sprintf(fechareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
3269
3270                if(strcmp(resultado,ACCION_CONERRORES)==0)
3271                        sprintf(sqlstr,"UPDATE acciones SET resultado='%s',estado='%s',fechahorafin='%s' WHERE idaccion=%d",ACCION_FALLIDA,ACCION_FINALIZADA,fechareg,idaccion);
3272                else
3273                        sprintf(sqlstr,"UPDATE acciones SET resultado='%s',estado='%s',fechahorafin='%s' WHERE idaccion=%d",ACCION_EXITOSA,ACCION_FINALIZADA,fechareg,idaccion);
3274
3275                if(!db.Execute(sqlstr)){ // Error al actualizar
3276                        db.GetErrorErrStr(ErrStr);
3277                        return(false);
3278                }
3279
3280                if(accionid>0){ // Esto no se ejecutarnsi la tarea tiene un trabajo padre
3281                        resul=InsertaNotificaciones(idaccion,idnotificador,accionid,resultado,db);
3282                        if(resul)
3283                                return(comprueba_resultados(accionid,db));
3284                }
3285        }
3286        return(resul);
3287}
3288// ________________________________________________________________________________________________________
3289// Función: EnviaServidoresRembo
3290//
3291//              Descripción:
3292//                      Esta funcin envia una  trama a un servidor rembo para que sus clientes ejecuten un comando
3293//              Parámetros:
3294//                      - parametros: parametros del comando
3295// ________________________________________________________________________________________________________
3296void EnviaServidoresRembo(char * parametros)
3297{
3298        int i,lon;
3299        for (i=0;i<MAXIMOS_SRVRMB;i++){
3300                if (tbsocketsSRVRMB[i].swenv==1){ // El switch de envio estna uno hay que enviar al servidor trama ...
3301                        strcat(parametros,"iph=");
3302                        strcat(parametros,tbsocketsSRVRMB[i].ipes);
3303                        lon=strlen(parametros);
3304                        parametros[lon-1]='\r'; // Quita la coma final
3305                        manda_trama_servidorrembo(tbsocketsSRVRMB[i].ip,parametros,tbsocketsSRVRMB[i].puertorepo);
3306                }
3307        }
3308}
3309// ________________________________________________________________________________________________________
3310// Función: manda_comando_servidorrembo
3311//
3312//              Descripción:
3313//                      Esta funcin envia una  trama a un servidor rembo para que sus clientes ejecuten un comando
3314//              Parámetros:
3315//                      - ip_srvrbm: Direccin IP del servidor REMBO
3316//                      - parametros: parametros del comando
3317// ________________________________________________________________________________________________________
3318int manda_trama_servidorrembo(char* ip_srvrbm,char *parametros,int puertorepo)
3319{       int ret;
3320        TRAMA *trama=(TRAMA*)malloc(LONGITUD_TRAMA);
3321        if(!trama)
3322                return(false);
3323        strcpy(trama->parametros,parametros);
3324        SOCKET udpsock;
3325        udpsock=UDPConnect(IPlocal);
3326        if (udpsock == INVALID_SOCKET) return(false);
3327        ret=envia_comandos(udpsock,trama,ip_srvrbm,puertorepo);
3328        close(udpsock);
3329        return(ret);
3330}
3331//_______________________________________________________________________________________________________________
3332//
3333// Crea un socket en un puerto determinado para la conversacin UDP con el repositorio
3334//
3335//_______________________________________________________________________________________________________________
3336SOCKET UDPConnect(char *ips)
3337{
3338        SOCKET socket_c; // Socket para hebras (UDP)
3339    struct sockaddr_in cliente;
3340        int puerto;
3341
3342        socket_c = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); // Crea socket para UDP
3343
3344        if (socket_c == SOCKET_ERROR)
3345                return (INVALID_SOCKET);
3346
3347        cliente.sin_addr.s_addr = inet_addr(ips); // selecciona interface
3348        cliente.sin_family = AF_INET;
3349        puerto=PUERTOMINUSER;
3350        while(puerto<PUERTOMAXUSER){ // Busca puerto libre
3351                cliente.sin_port = htons(puerto); // Puerto asignado
3352                if (bind(socket_c,(struct sockaddr *)&cliente,sizeof(cliente)) == SOCKET_ERROR)
3353                        puerto++;
3354                else
3355                        break;
3356        }
3357        if(puerto>=PUERTOMAXUSER){ // No hay puertos libres
3358                return(INVALID_SOCKET);
3359        }
3360        return(socket_c);
3361}
3362//________________________________________________________________________________________________________
3363// Función: envia_comandos
3364//
3365//              Descripción:
3366//                      Enva trama UDP
3367// ________________________________________________________________________________________________________
3368int envia_comandos(SOCKET s,TRAMA* trama, char* ipsrv,int puerto)
3369{
3370        int ret,lon;
3371        struct sockaddr_in addrRepo;
3372         
3373        trama->arroba='@';                                                                              // cabecera de la trama
3374        strcpy(trama->identificador,"JMMLCAMDJ");       // identificador de la trama
3375        trama->ejecutor='1';                                                                            // ejecutor de la trama 1=el servidor hidra  2=el cliente hidra
3376       
3377        addrRepo.sin_family = AF_INET;
3378    addrRepo.sin_port = htons((short)puerto);
3379    addrRepo.sin_addr.s_addr = inet_addr(ipsrv); //  Direccin IP repositorio
3380    Encriptar((char*)trama);
3381        lon=strlen((char*)trama);
3382        ret = sendto(s,(char *)trama,lon,0,(struct sockaddr *)&addrRepo, sizeof(addrRepo));
3383    if (ret == SOCKET_ERROR){
3384        RegistraLog("***send() fallo en envío al repositorio",true);
3385                return(FALSE);
3386    }
3387        return true;
3388}
3389// ________________________________________________________________________________________________________
3390// Función: DesmarcaServidoresRembo
3391//
3392//       Descripción:
3393//              Esta funcin desmarca la tabla completa de servidores rembo para iniciar la cuesation de envio
3394// ________________________________________________________________________________________________________
3395void DesmarcaServidoresRembo(void)
3396{
3397        int i;
3398        for (i=0;i<MAXIMOS_SRVRMB;i++){
3399                tbsocketsSRVRMB[i].swenv=0;
3400                tbsocketsSRVRMB[i].ipes[0]=(char)NULL;
3401        }
3402}
3403// ________________________________________________________________________________________________________
3404// Función: MarcaServidoresRembo
3405//
3406//              Descripción:
3407//                      Esta funcin marca la tabla de servidores Rembo y coloca la ip del cliente en el buffer
3408//              Parámetros:
3409//                      - ipsrvrmb: ip del servidor rembo
3410//                      - ipclrmb: ip del cliente rembo
3411// ________________________________________________________________________________________________________
3412void MarcaServidoresRembo(char* ipsrvrmb,char*ipclrmb)
3413{
3414        int i,resul;
3415        for (i=0;i<MAXIMOS_SRVRMB;i++){
3416                resul=strcmp(tbsocketsSRVRMB[i].ip,ipsrvrmb);
3417                if(resul==0) {// servidor rembo encontrado
3418                        strcat(tbsocketsSRVRMB[i].ipes,ipclrmb);
3419                        strcat(tbsocketsSRVRMB[i].ipes,";");
3420                        tbsocketsSRVRMB[i].swenv=1;
3421                        return;
3422                }
3423        }
3424}
3425// ________________________________________________________________________________________________________
3426// Función: TomaIPServidorRembo
3427//
3428//              Descripción:
3429//                      Esta funcin devuelve true o false dependiendo si el Servidor REMBO estnen la tabla  de servidores.
3430//              Parámetros:
3431//                      - ip : La ip del servidor a buscar
3432// ________________________________________________________________________________________________________
3433BOOLEAN TomaIPServidorRembo(char *ip,int *p)
3434{
3435        int i,j;
3436        for (i=0;i<MAXIMOS_SOCKETS;i++){
3437                if (strcmp(ip,tbsockets[i].ip)==0){ // Si existe la IP ...
3438                        strcpy(ip,tbsockets[i].ipsrvrmb);
3439                        for (j=0;j<MAXIMOS_SRVRMB;j++){
3440                                if (strcmp(ip,tbsocketsSRVRMB[j].ip)==0){ // Si existe la IP ...
3441                                        *p=tbsocketsSRVRMB[j].puertorepo;
3442                                        return(TRUE);
3443                                }
3444                        }
3445                }
3446        }                       
3447        return(FALSE);
3448}
3449// ________________________________________________________________________________________________________
3450// Función: AbreConexion
3451//
3452//              Descripción:
3453//                      Crea un socket y lo conecta a una interface de red. Devuelve el socket
3454//              Parámetros:
3455//                      - ips : La direccin IP con la que se comunicarnel socket
3456//                      - port : Puerto para la  comunicacin
3457// ________________________________________________________________________________________________________
3458SOCKET AbreConexion(char *ips,int port)
3459{
3460    struct sockaddr_in server;
3461        SOCKET s;
3462
3463        // Crea el socket y se intenta conectar
3464        s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
3465        if (s == SOCKET_ERROR){
3466                RegistraLog("Error en la creacin del socket. Modulo: AbreConexion()",true);
3467                return INVALID_SOCKET;
3468        }
3469
3470        server.sin_family = AF_INET;
3471        server.sin_port = htons((short)port);
3472        server.sin_addr.s_addr = inet_addr(ips);
3473
3474        if (connect(s, (struct sockaddr *)&server, sizeof(server)) == SOCKET_ERROR){
3475                RegistraLog("connect() fallo",true);
3476                return INVALID_SOCKET;
3477        }
3478        return(s);
3479       
3480}
3481// ________________________________________________________________________________________________________
3482// Función: EjecutarTarea
3483//
3484//              Descripción:
3485//                      Registra una acción (Tarea) y la envn para su ejecucin
3486//              Parámetros:
3487//                      - idtarea : Identificador de la tarea
3488//                      - accionid: identificador del trabajo padre (si existe)
3489//                      - idnotificador:  identificador del trabajo_tarea incluido en trabajo padre (si existe)
3490//                      - idcentro: Centro propietario del trabjo padre (si existe este trabajo)
3491//                      - Database: una conexion ADO operativa
3492//                      - parametros: parnetros de la acción
3493// ________________________________________________________________________________________________________
3494int EjecutarTarea(int idtarea,int accionid,int idnotificador,int idcentro,Database db,char* parametros )
3495{
3496        char sqlstr[1000],ErrStr[200],ambito;
3497        Table tbl;
3498        int cont_comandos=0,lon;
3499        int  idcomando,idambito,idtareacomando,accionidcmd;
3500        char wambitarea[20],ambitarea[4000];
3501        char wparamtarea[20],paramtarea[1000],pids[20];
3502        int  tblon[100],tbComandosidcomando[100],tbComandosambito[100],tbComandosidnotificador[100],tbComandosidambito[100];
3503        char *tbComandosparametros[100];
3504
3505        ambitarea[0]=(char)NULL; // Inicializacin
3506        strcpy(paramtarea,"cmd="); // Inicializacin
3507        if(idcentro==0){
3508                // recupera el identificador del Centro propietario de la tarea
3509                sprintf(sqlstr,"SELECT idcentro FROM tareas WHERE idtarea=%d",idtarea);
3510                if(!db.Execute(sqlstr,tbl)){ // Error al leer
3511                        db.GetErrorErrStr(ErrStr);
3512                        return(false);
3513                }
3514                if(tbl.ISEOF()) return(true);
3515                if(!tbl.Get("idcentro",idcentro)){ // Toma dato
3516                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3517                        return(false);
3518                }
3519        }
3520        // Recupera los comandos que forman parte de la tarea
3521        sprintf(sqlstr,"SELECT * FROM tareas_comandos WHERE idtarea=%d ORDER by orden",idtarea);
3522        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3523                db.GetErrorErrStr(ErrStr);
3524                return(false);
3525        }
3526        if(tbl.ISEOF()) return(true);
3527               
3528        // Recorre tareas-comandos
3529        while(!tbl.ISEOF()){
3530                if(!tbl.Get("idcomando",idcomando)){ // Toma dato
3531                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3532                        return(false);
3533                }
3534                tbComandosidcomando[cont_comandos]=idcomando;
3535
3536                if(!tbl.Get("ambito",ambito)){ // Toma dato
3537                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3538                        return(false);
3539                }
3540                tbComandosambito[cont_comandos]=ambito;
3541
3542                if(!tbl.Get("idambito",idambito)){ // Toma dato
3543                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3544                        return(false);
3545                }
3546                tbComandosidambito[cont_comandos]=idambito;
3547
3548
3549                if(!tbl.Get("parametros",parametros)){ // Toma dato
3550                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3551                        return(false);
3552                }
3553
3554                lon=strlen(parametros);
3555                tblon[cont_comandos]=lon;
3556                tbComandosparametros[cont_comandos]=(char*)malloc(lon+20);
3557                if(tbComandosparametros[cont_comandos]==NULL)
3558                        return(false); // No hay memoria bastante
3559
3560                strcpy(tbComandosparametros[cont_comandos],parametros);
3561               
3562                if(!tbl.Get("idtareacomando",idtareacomando)){ // Toma dato
3563                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3564                        return(false);
3565                }
3566                tbComandosidnotificador[cont_comandos]=idtareacomando;
3567
3568                sprintf(wambitarea,"%d:%d;",ambito,idambito);
3569                strcat(ambitarea,wambitarea);
3570
3571                sprintf(wparamtarea,"%d;",idtareacomando);
3572                strcat(paramtarea,wparamtarea);
3573
3574                cont_comandos++;
3575                tbl.MoveNext();
3576        }
3577        lon=strlen(ambitarea);
3578        ambitarea[lon-1]=(char)NULL; // Quita la coma final
3579
3580        lon=strlen(paramtarea);
3581        paramtarea[lon-1]=(char)NULL; // Quita la coma final
3582
3583        char _fechahorareg[100];
3584    struct tm* st;
3585    st=TomaHora();
3586        sprintf(_fechahorareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
3587
3588        sprintf(sqlstr,"INSERT INTO acciones (tipoaccion,idtipoaccion,cateaccion,ambito,idambito,ambitskwrk,fechahorareg,estado,resultado,idcentro,parametros,accionid,idnotificador) VALUES (%d,%d,%d,0,0,'%s','%s','%s','%s',%d,'%s',%d,%d)",EJECUCION_TAREA,idtarea,PROCESOS,ambitarea,_fechahorareg,ACCION_INICIADA,ACCION_SINERRORES,idcentro,paramtarea,accionid,idnotificador);
3589        if(!db.Execute(sqlstr)){ // Error al insertar
3590                db.GetErrorErrStr(ErrStr);
3591                return(false);
3592        }
3593        accionid=0;
3594        // Toma identificador dela acción
3595        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
3596        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3597                db.GetErrorErrStr(ErrStr);
3598                return(false);
3599        }
3600        if(!tbl.ISEOF()){ // Si existe registro
3601                if(!tbl.Get("identificador",accionid)){
3602                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3603                        return(false);
3604                }
3605        }
3606        int i;
3607        // Insertar acciones:comandos
3608        for (i=0;i<cont_comandos;i++){
3609            st=TomaHora();
3610                sprintf(_fechahorareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
3611                sprintf(sqlstr,"INSERT INTO acciones (tipoaccion,idtipoaccion,cateaccion,ambito,idambito,fechahorareg,estado,resultado,idcentro,parametros,accionid,idnotificador) VALUES (%d,%d,%d,%d,%d,'%s','%s','%s',%d,'%s',%d,%d)",EJECUCION_COMANDO,tbComandosidcomando[i],PROCESOS,tbComandosambito[i],tbComandosidambito[i],_fechahorareg,ACCION_EXITOSA,ACCION_SINERRORES,idcentro,tbComandosparametros[i],accionid,tbComandosidnotificador[i]);     
3612                if(!db.Execute(sqlstr)){ // Error al insertar
3613                        db.GetErrorErrStr(ErrStr);
3614                         free(tbComandosparametros[i]);
3615                        return(false);
3616                }
3617                // Toma identificador dela acción
3618                sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
3619                if(!db.Execute(sqlstr,tbl)){ // Error al leer
3620                        db.GetErrorErrStr(ErrStr);
3621                        return(false);
3622                }
3623                if(!tbl.ISEOF()){ // Si existe registro
3624                        if(!tbl.Get("identificador",accionidcmd)){
3625                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3626                        return(false);
3627                        }
3628                }
3629                sprintf(pids,"ids=%d\r",accionidcmd);
3630                strcat((char*)tbComandosparametros[i],pids); // Le ande el identificador de la accion
3631                envia_tarea(tbComandosparametros[i]);
3632                free(tbComandosparametros[i]);
3633        }
3634        return(true);
3635}
3636// ________________________________________________________________________________________________________
3637// Función: manda peticin de inclusion
3638//
3639//              Descripción:
3640//                      Esta funcin envia una tarea  por la red.
3641//              Parámetros:
3642//                      - parametros: El contenido de la tarea
3643// ________________________________________________________________________________________________________
3644void envia_tarea(char* parametros)
3645{
3646        TRAMA trama;   
3647
3648        trama.arroba='@';
3649        strncpy(trama.identificador,"JMMLCAMDJ",9);
3650        trama.ejecutor=parametros[0];
3651        strcpy(trama.parametros,(char*)&parametros[1]);
3652        gestiona_comando(INVALID_SOCKET,trama);
3653}
3654// ________________________________________________________________________________________________________
3655// Función: EjecutarTrabajo
3656//
3657//              Descripción:
3658//                      Registra una acción (Trabajo y la envn para su ejecucin
3659//              Parámetros:
3660//                      - idtrabajo : Identificador del trabajo
3661//                      - Database: una conexion ADO operativa
3662//                      - parametros: parnetros de la acción
3663// ________________________________________________________________________________________________________
3664int EjecutarTrabajo(int idtrabajo,Database db,char*parametros )
3665{
3666        char sqlstr[1000],ErrStr[200];
3667        Table tbl;
3668        int cont_tareas=0,lon;
3669        int  idtarea,idtrabajotarea,idcentro;
3670        char wambitrabajo[500],ambitrabajo[4000];
3671        char wparamtrabajo[20],paramtrabajo[1000];
3672        int  tbTareasidtarea[100],tbTareasidnotificador[100];
3673        char ambitskwrk[500];
3674
3675        ambitrabajo[0]=(char)NULL; // Inicializacin
3676        strcpy(paramtrabajo,"tsk="); // Inicializacin
3677
3678        // recupera el identificador del Centro propietario de la tarea
3679        sprintf(sqlstr,"SELECT idcentro FROM trabajos WHERE idtrabajo=%d",idtrabajo);
3680        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3681                db.GetErrorErrStr(ErrStr);
3682                return(false);
3683        }
3684        if(tbl.ISEOF()) return(true);
3685        if(!tbl.Get("idcentro",idcentro)){ // Toma dato
3686                tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3687                return(false);
3688        }
3689        // Recupera las tareas que forman parte del trabajo
3690        sprintf(sqlstr,"SELECT * FROM trabajos_tareas WHERE idtrabajo=%d ORDER by orden",idtrabajo);
3691        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3692                db.GetErrorErrStr(ErrStr);
3693                return(false);
3694        }
3695        if(tbl.ISEOF()) return(true);
3696        // Recorre trabajos-tareas
3697        while(!tbl.ISEOF()){   
3698                if(!tbl.Get("idtrabajotarea",idtrabajotarea)){ // Toma dato
3699                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3700                        return(false);
3701                }
3702                tbTareasidnotificador[cont_tareas]=idtrabajotarea;
3703
3704                if(!tbl.Get("idtarea",idtarea)){ // Toma dato
3705                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3706                        return(false);
3707                }
3708                tbTareasidtarea[cont_tareas]=idtarea;
3709
3710                if(!tbl.Get("parametros",parametros)){ // Toma dato
3711                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3712                        return(false);
3713                }
3714               
3715                if(!tbl.Get("ambitskwrk",ambitskwrk)){ // Toma dato
3716                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3717                        return(false);
3718                }
3719                sprintf(wambitrabajo,"%s;",ambitskwrk);
3720                strcat(ambitrabajo,wambitrabajo);
3721
3722                sprintf(wparamtrabajo,"%d;",idtrabajotarea);
3723                strcat(paramtrabajo,wparamtrabajo);
3724
3725                cont_tareas++;
3726                tbl.MoveNext();
3727        }
3728        lon=strlen(ambitrabajo);
3729        ambitrabajo[lon-1]=(char)NULL; // Quita la coma final
3730
3731        lon=strlen(paramtrabajo);
3732        paramtrabajo[lon-1]=(char)NULL; // Quita la coma final
3733
3734        char _fechahorareg[100];
3735    struct tm* st;
3736    st=TomaHora();
3737        sprintf(_fechahorareg,"%d/%d/%d %d:%d:%d",st->tm_year+1900,st->tm_mon+1,st->tm_mday,st->tm_hour,st->tm_min,st->tm_sec);
3738
3739        sprintf(sqlstr,"INSERT INTO acciones (tipoaccion,idtipoaccion,cateaccion,ambito,idambito,ambitskwrk,fechahorareg,estado,resultado,idcentro,parametros,accionid,idnotificador) VALUES (%d,%d,%d,0,0,'%s','%s','%s','%s',%d,'%s',0,0)",EJECUCION_TRABAJO,idtrabajo,PROCESOS,ambitrabajo,_fechahorareg,ACCION_INICIADA,ACCION_SINERRORES,idcentro,paramtrabajo);
3740        if(!db.Execute(sqlstr)){ // Error al insertar
3741                db.GetErrorErrStr(ErrStr);
3742                return(false);
3743        }
3744        int accionid=0;
3745        // Toma identificador dela acción
3746        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
3747        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3748                db.GetErrorErrStr(ErrStr);
3749                return(false);
3750        }
3751        if(!tbl.ISEOF()){ // Si existe registro
3752                if(!tbl.Get("identificador",accionid)){
3753                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3754                        return(false);
3755                }
3756        }
3757        int i;
3758        // Insertar acciones:tareas
3759        for (i=0;i<cont_tareas;i++){
3760                if(!EjecutarTarea(tbTareasidtarea[i],accionid,tbTareasidnotificador[i],idcentro,db,parametros)){
3761                        return(false);
3762                }
3763        }
3764        return(true);
3765}
3766// ________________________________________________________________________________________________________
3767// Función: cuestion_nuevoordenador
3768//
3769//       Descripción:
3770//              Esta funcin da de alta un ordenador  y un aula si el sistema estnconfigurado para ello
3771//              Parámetros:
3772//                      - db: Objeto base de datos (ya operativo)
3773//                      - tbl: Objeto tabla
3774//                      - ido: identificador del ordenador que se darnde alta automnicamente( se devuelve)
3775//                      - nau: Nombre del grupo donde estnel ordenador( rembo.conf)
3776//                      - nor: Nombre del ordenador dado por rembo(dhcpd)
3777//                      - iph: IP del ordenador
3778//                      - mac: MAC del ordenador
3779//                      - cfg: configuracin
3780//                      - ipd: ip del servidor dhcp
3781//                      - ipr: ip del servidor rembo
3782// ________________________________________________________________________________________________________
3783int cuestion_nuevoordenador(Database db,Table tbl,int*ido,char *nau,char *nor,char *iph,char *mac,char*cfg,char*ipd,char*ipr)
3784{
3785        char sqlstr[1000],ErrStr[200];
3786        int ida,isd,isr;
3787
3788        // Recupera los datos del aula
3789        sprintf(sqlstr,"SELECT idaula FROM aulas  WHERE nombreaula= '%s'",nau);
3790
3791        if(!db.Execute(sqlstr,tbl)){ // Error al consultar
3792                db.GetErrorErrStr(ErrStr);
3793                return(false);
3794        }
3795        if(tbl.ISEOF()){ // Si NO existe el aula
3796                sprintf(sqlstr,"SELECT idaula FROM aulas  WHERE nombreaula= '%s'","Default");
3797                if(!db.Execute(sqlstr,tbl)){ // Error al consultar
3798                        db.GetErrorErrStr(ErrStr);
3799                        return(false);
3800                }
3801                if(tbl.ISEOF()){ // Inserta el aula por defecto
3802                        sprintf(sqlstr,"INSERT INTO aulas (nombreaula) VALUES ('Default')");
3803                        if(!db.Execute(sqlstr)){ // Error al insertar
3804                                db.GetErrorErrStr(ErrStr);
3805                                return(false);
3806                        }
3807                        ida=0;
3808                        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
3809                        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3810                                db.GetErrorErrStr(ErrStr);
3811                                return(false);
3812                        }
3813                        if(!tbl.ISEOF()){ // Si existe registro
3814                                if(!tbl.Get("identificador",ida)){
3815                                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3816                                        return(false);
3817                                }
3818                        }                               
3819                }
3820        }
3821        else{
3822                if(!tbl.Get("idaula",ida)){ // Toma dato
3823                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3824                        return(false);
3825                }
3826        }
3827        if(!Toma_idservidorres(db,tbl,ipd,ipr,&isd,&isr)) return(false);
3828        if(!alta_ordenador(db,tbl,ido,nor,iph,mac,ida,isd,isr)) return(false); // Alta del ordenador
3829        if(!actualiza_configuracion(db,tbl,cfg,0,0,iph)){ // Actualiza la configuracin del ordenador
3830                return(false);
3831        }
3832        return(true);
3833}
3834// ________________________________________________________________________________________________________
3835// Función: alta_ordenador
3836//
3837//              Descripción:
3838//                      Esta funcin da de alta un ordenador
3839//              Parámetros:
3840//                      - db: Objeto base de datos (ya operativo)
3841//                      - tbl: Objeto tabla
3842//                      - mac: MAC del ordenador
3843//                      - ida: Identificador del aula
3844//                      - isd: Identificador del servidor dhcp
3845//                      - isr: Identificador del servidor rembo
3846// ________________________________________________________________________________________________________
3847int alta_ordenador(Database db,Table tbl,int* ido,char *nor,char *iph,char*mac,int ida,int isd,int isr)
3848{
3849        char sqlstr[1000],ErrStr[200],strmac[20];
3850        int idordenador,lon,i,p;
3851
3852        // Prepara mac
3853        lon=strlen(mac);
3854        p=0;
3855        for (i=0;i<lon;i++){
3856                if(mac[i]!=' ') // Si no es espacio
3857                        strmac[p++]=mac[i];
3858        }
3859        strmac[p]=(char)NULL;
3860
3861        sprintf(sqlstr,"INSERT INTO ordenadores(nombreordenador,ip,mac,idperfilhard,idservidordhcp,idservidorrembo,idmenu,idaula,grupoid,idconfiguracion) VALUES ('%s','%s','%s',0,%d,%d,0,%d,0,0)",nor,iph,strmac,isd,isr,ida);
3862        if(!db.Execute(sqlstr)){ // Error al insertar
3863                db.GetErrorErrStr(ErrStr);
3864                return(false);
3865        }
3866        idordenador=0;
3867        // Toma identificador dela acción
3868        sprintf(sqlstr,"SELECT LAST_INSERT_ID() as identificador");
3869        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3870                db.GetErrorErrStr(ErrStr);
3871                return(false);
3872        }
3873        if(!tbl.ISEOF()){ // Si existe registro
3874                if(!tbl.Get("identificador",idordenador)){
3875                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3876                        return(false);
3877                }
3878        }
3879        *ido=idordenador;
3880        return(true);
3881}
3882// ________________________________________________________________________________________________________
3883// Función: Toma_idservidorres
3884//
3885//              Descripción:
3886//                      Esta funcin devuelve los identificadores de los servidores rembo y dhcp de un determinado ordenador
3887//              Parámetros:
3888//                              db: Objeto base de datos (ya operativo)
3889//                              tbl: Objeto tabla
3890//                              ipd: ip del servidor dhcp
3891//                              ipr: ip del servidor rembo
3892//                              isd: identificador del servidor dhcp
3893//                              isr: identificador del servidor rembo
3894// ________________________________________________________________________________________________________
3895int Toma_idservidorres(Database db,Table tbl,char*ipd,char*ipr,int*isd,int*isr)
3896{
3897        char sqlstr[1000],ErrStr[200];
3898        int identificador_dhcp=0;
3899        int identificador_rembo;
3900       
3901        /* Servidor dhcp
3902        sprintf(sqlstr,"SELECT idservidordhcp FROM servidoresdhcp where ip='%s'",ipd);
3903        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3904                db.GetErrorErrStr(ErrStr);
3905                return(false);
3906        }
3907        if(!tbl.ISEOF()){ // Si existe registro
3908                if(!tbl.Get("idservidordhcp",identificador_dhcp)){
3909                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3910                        return(false);
3911                }
3912        }
3913        */
3914        // Servidor rembo
3915        sprintf(sqlstr,"SELECT idservidorrembo FROM servidoresrembo where ip='%s'",ipr);
3916        if(!db.Execute(sqlstr,tbl)){ // Error al leer
3917                db.GetErrorErrStr(ErrStr);
3918                return(false);
3919        }
3920        if(!tbl.ISEOF()){ // Si existe registro
3921                if(!tbl.Get("idservidorrembo",identificador_rembo)){
3922                        tbl.GetErrorErrStr(ErrStr); // error al acceder al registro
3923                        return(false);
3924                }
3925        }
3926        *isd=identificador_dhcp;
3927        *isr=identificador_rembo;
3928        return(true);
3929}
3930//************************************************************************************************************************************************
3931// PROGRAMA PRINCIPAL ( SERVICIO)
3932//***************************************************************************************************************************************************
3933  int main (int argc, char *argv[])
3934{
3935    SOCKET      socket_s; // Socket donde escucha el servidor
3936    SOCKET      socket_c; // Socket de los clientes que se conectan
3937    int         i;// Tamao de la estructura de direccionamiento IP del cliente
3938    socklen_t   iAddrSize;
3939    struct      sockaddr_in local,cliente;
3940        //pthread_t hThread;
3941        //void *resul
3942        // Validación de parámetros
3943       
3944        strcpy(szPathFileCfg,"ogAdmServer.cfg");
3945        strcpy(szPathFileLog,"ogAdmServer.log");       
3946       
3947    for(i = 1; (i+1) < argc; i+=2){
3948        if (argv[i][0] == '-'){
3949            switch (tolower(argv[i][1])){
3950                case 'f':
3951                    if (argv[i+1]!=NULL)
3952                        strcpy(szPathFileCfg, argv[i+1]);
3953                    else{
3954                        RegistraLog("Fallo en los parámetros: Debe especificar el fichero de configuración del servicio",false);
3955                        exit(EXIT_FAILURE);
3956                        }
3957                    break;
3958                case 'l':
3959                    if (argv[i+1]!=NULL)
3960                        strcpy(szPathFileLog, argv[i+1]);
3961                    else{
3962                        RegistraLog("Fallo en los parámetros: Debe especificar el fichero de log para el servicio",false);
3963                        exit(EXIT_FAILURE);
3964                        }
3965                    break;
3966                default:
3967                        RegistraLog("Fallo de sintaxis en los parámetros: Debe especificar -f nombre_del_fichero_de_configuración_del_servicio",false);
3968                        exit(EXIT_FAILURE);
3969                    break;
3970            }
3971        }
3972    }
3973        if (szPathFileCfg==NULL){
3974                printf ("***Error. No se ha especificado fichero de configuración\n");
3975                exit(EXIT_FAILURE);
3976        }
3977        if(!TomaConfiguracion(szPathFileCfg)){ // Toma parametros de configuracion
3978                RegistraLog("El fichero de configuración contiene un error de sintaxis",false);
3979                exit(EXIT_FAILURE);
3980        }
3981        pthread_mutex_init(&guardia,NULL); // Creación del mutex para control de hebras
3982
3983        for (i=0;i<MAXIMOS_SOCKETS;i++){
3984                tbsockets[i].ip[0]='\0'; // Inicializa IP
3985                tbsockets[i].sock=INVALID_SOCKET; // Inicializa Socket
3986        }
3987        RegistraLog("***Inicio de sesion***",false);
3988
3989        socket_s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); // Crea socket
3990        if (socket_s == SOCKET_ERROR){
3991                RegistraLog("***socket() fallo:",true);
3992        }
3993        local.sin_addr.s_addr = htonl(INADDR_ANY); // selecciona interface
3994        local.sin_family = AF_INET;     
3995        local.sin_port = htons(puerto); // Puerto
3996
3997        if (bind(socket_s,(struct sockaddr *)&local, // Enlaza socket
3998                sizeof(local)) == SOCKET_ERROR){
3999                RegistraLog("***bind() fallo:",true);
4000        }
4001
4002        listen(socket_s,250); // Pone a escuchar al socket
4003        iAddrSize = sizeof(cliente);
4004
4005        while (true) {  // Bucle para escuchar peticiones de clientes
4006                socket_c = accept(socket_s, (struct sockaddr *)&cliente,&iAddrSize);   
4007                if (socket_c == INVALID_SOCKET){
4008                        RegistraLog("***accept() fallo:",true);
4009                    break;
4010                }
4011                //resul=pthread_create(&hThread,NULL,GestionaConexion,(void*)&socket_c);
4012                GestionaConexion(&socket_c);
4013                /*if(resul!=0){2
4014                        RegistraLog("***Fallo al crear la hebra cliente",false);
4015                    break;
4016        }
4017        */
4018                //pthread_detach(hThread);
4019                close(socket_c); // Cierra la conexion con el servidor hidra
4020        }
4021        close(socket_s);
4022        exit(EXIT_SUCCESS);
4023}
Note: See TracBrowser for help on using the repository browser.