source: admin/Services/ogAdmServer/sources/ogAdmServer.cpp @ 9a2cda1e

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 9a2cda1e was d08ec1cc, checked in by alonso <alonso@…>, 16 years ago

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

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