source: trunk/zoo-project/zoo-kernel/zoo_service_loader.c @ 389

Last change on this file since 389 was 388, checked in by djay, 12 years ago

Fix issue in OGR python services, thanks to Farkas to point this issue. Update Java support to handle properly the error messages coming from the JVM. Fix segfault when ZCFG file doesn't exist.

  • Property svn:eol-style set to native
  • Property svn:mime-type set to text/x-csrc
File size: 64.5 KB
Line 
1/**
2 * Author : Gérald FENOY
3 *
4 *  Copyright 2008-2012 GeoLabs SARL. All rights reserved.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
12 *
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22 * THE SOFTWARE.
23 */
24
25#define length(x) (sizeof(x) / sizeof(x[0]))
26
27extern "C" int yylex();
28extern "C" int crlex();
29
30#include "cgic.h"
31
32extern "C" {
33#include <libxml/tree.h>
34#include <libxml/xmlmemory.h>
35#include <libxml/parser.h>
36#include <libxml/xpath.h>
37#include <libxml/xpathInternals.h>
38}
39
40#include "ulinet.h"
41
42#include <libintl.h>
43#include <locale.h>
44#include <string.h>
45
46#include "service.h"
47
48#include "service_internal.h"
49
50#ifdef USE_PYTHON
51#include "service_internal_python.h"
52#endif
53
54#ifdef USE_JAVA
55#include "service_internal_java.h"
56#endif
57
58#ifdef USE_PHP
59#include "service_internal_php.h"
60#endif
61
62#ifdef USE_JS
63#include "service_internal_js.h"
64#endif
65
66#ifdef USE_PERL
67#include "service_internal_perl.h"
68#endif
69
70#include <dirent.h>
71#include <signal.h>
72#include <unistd.h>
73#ifndef WIN32
74#include <dlfcn.h>
75#include <libgen.h>
76#else
77#include <windows.h>
78#include <direct.h>
79#include <sys/types.h>
80#include <sys/stat.h>
81#include <unistd.h>
82#define pid_t int;
83#endif
84#include <fcntl.h>
85#include <time.h>
86#include <stdarg.h>
87
88#ifdef WIN32
89extern "C" {
90  __declspec(dllexport) char *strcasestr(char const *a, char const *b)
91#ifndef USE_MS
92 { 
93  char *x=_strdup(a); 
94  char *y=_strdup(b); 
95 
96  x=_strlwr(x); 
97  y=_strlwr(y); 
98  char *pos = strstr(x, y); 
99  char *ret = pos == NULL ? NULL : (char *)(a + (pos-x)); 
100  free(x); 
101  free(y); 
102  return ret; 
103 };
104#else
105  ;
106#endif
107}
108#endif
109
110#define _(String) dgettext ("zoo-kernel",String)
111#define __(String) dgettext ("zoo-service",String)
112
113
114void translateChar(char* str,char toReplace,char toReplaceBy){
115  int i=0,len=strlen(str);
116  for(i=0;i<len;i++){
117    if(str[i]==toReplace)
118      str[i]=toReplaceBy;
119  }
120}
121
122/**
123 * Create (or append to) an array valued maps
124 * value = "["",""]"
125 */
126int appendMapsToMaps(maps* m,maps* mo,maps* mi,elements* elem){
127  maps* tmpMaps=getMaps(mo,mi->name);
128  map* tmap=getMapType(tmpMaps->content);
129  elements* el=getElements(elem,mi->name);
130  int hasEl=1;
131  if(el==NULL)
132    hasEl=-1;
133  if(tmap==NULL){
134    if(hasEl>0)
135      tmap=getMapType(el->defaults->content);     
136  }
137
138  map* testMap=NULL;
139  if(hasEl>0){
140    testMap=getMap(el->content,"maxOccurs");
141  }else{
142    testMap=createMap("maxOccurs","unbounded");
143  }
144
145  if(testMap!=NULL){
146    if(strncasecmp(testMap->value,"unbounded",9)!=0 && atoi(testMap->value)>1){
147      if(addMapsArrayToMaps(&mo,mi,tmap->name)<0){
148        char emsg[1024];
149        sprintf(emsg,_("You set maximum occurences for <%s> as %i but you tried to use it more than the limit you set. Please correct your ZCFG file or your request."),mi->name,atoi(testMap->value));
150        errorException(m,emsg,"InternalError");
151        return -1;
152      }
153    }else{
154      if(strncasecmp(testMap->value,"unbounded",9)==0){
155        if(hasEl<0){
156          freeMap(&testMap);
157          free(testMap);
158        }
159        if(addMapsArrayToMaps(&mo,mi,tmap->name)<0){
160          char emsg[1024];
161          map* tmpMap=getMap(mi->content,"length");
162          sprintf(emsg,_("ZOO-Kernel was unable to load your data for %s position %s."),mi->name,tmpMap->value);
163          errorException(m,emsg,"InternalError");
164          return -1;
165        }
166      }
167      else{
168        char emsg[1024];
169        sprintf(emsg,_("You set maximum occurences for <%s> to one but you tried to use it more than once. Please correct your ZCFG file or your request."),mi->name);
170        errorException(m,emsg,"InternalError");
171        return -1;
172      }
173    }
174  }
175  return 0;
176}
177
178xmlXPathObjectPtr extractFromDoc(xmlDocPtr doc,const char* search){
179  xmlXPathContextPtr xpathCtx;
180  xmlXPathObjectPtr xpathObj;
181  xpathCtx = xmlXPathNewContext(doc);
182  xpathObj = xmlXPathEvalExpression(BAD_CAST search,xpathCtx);
183  xmlXPathFreeContext(xpathCtx);
184  return xpathObj;
185}
186
187void donothing(int sig){
188  fprintf(stderr,"Signal %d after the ZOO-Kernel returned result !\n",sig);
189  exit(0);
190}
191
192void sig_handler(int sig){
193  char tmp[100];
194  const char *ssig;
195  switch(sig){
196  case SIGSEGV:
197    ssig="SIGSEGV";
198    break;
199  case SIGTERM:
200    ssig="SIGTERM";
201    break;
202  case SIGINT:
203    ssig="SIGINT";
204    break;
205  case SIGILL:
206    ssig="SIGILL";
207    break;
208  case SIGFPE:
209    ssig="SIGFPE";
210    break;
211  case SIGABRT:
212    ssig="SIGABRT";
213    break;
214  default:
215    ssig="UNKNOWN";
216    break;
217  }
218  sprintf(tmp,_("ZOO Kernel failed to process your request receiving signal %d = %s"),sig,ssig);
219  errorException(NULL, tmp, "InternalError");
220#ifdef DEBUG
221  fprintf(stderr,"Not this time!\n");
222#endif
223  exit(0);
224}
225
226void loadServiceAndRun(maps **myMap,service* s1,map* request_inputs,maps **inputs,maps** ioutputs,int* eres){
227  char tmps1[1024];
228  char ntmp[1024];
229  maps *m=*myMap;
230  maps *request_output_real_format=*ioutputs;
231  maps *request_input_real_format=*inputs;
232  /**
233   * Extract serviceType to know what kind of service should be loaded
234   */
235  map* r_inputs=NULL;
236#ifndef WIN32
237  char* pntmp=getcwd(ntmp,1024);
238#else
239  _getcwd(ntmp,1024);
240#endif
241  r_inputs=getMap(s1->content,"serviceType");
242#ifdef DEBUG
243  fprintf(stderr,"LOAD A %s SERVICE PROVIDER \n",r_inputs->value);
244  fflush(stderr);
245#endif
246  if(strlen(r_inputs->value)==1 && strncasecmp(r_inputs->value,"C",1)==0){
247    r_inputs=getMap(request_inputs,"metapath");
248    if(r_inputs!=NULL)
249      sprintf(tmps1,"%s/%s",ntmp,r_inputs->value);
250    else
251      sprintf(tmps1,"%s/",ntmp);
252    char *altPath=strdup(tmps1);
253    r_inputs=getMap(s1->content,"ServiceProvider");
254    sprintf(tmps1,"%s/%s",altPath,r_inputs->value);
255    free(altPath);
256#ifdef DEBUG
257    fprintf(stderr,"Trying to load %s\n",tmps1);
258#endif
259#ifdef WIN32
260    HINSTANCE so = LoadLibraryEx(tmps1,NULL,LOAD_WITH_ALTERED_SEARCH_PATH);
261#else
262    void* so = dlopen(tmps1, RTLD_LAZY);
263#endif
264#ifdef DEBUG
265#ifdef WIN32
266    DWORD errstr;
267    errstr = GetLastError();
268    fprintf(stderr,"%s loaded (%d) \n",tmps1,errstr);
269#else
270    char *errstr;
271    errstr = dlerror();
272#endif
273#endif
274
275    if( so != NULL ) {
276#ifdef DEBUG
277      fprintf(stderr,"Library loaded %s \n",errstr);
278      fprintf(stderr,"Service Shared Object = %s\n",r_inputs->value);
279#endif
280      r_inputs=getMap(s1->content,"serviceType");
281#ifdef DEBUG
282      dumpMap(r_inputs);
283      fprintf(stderr,"%s\n",r_inputs->value);
284      fflush(stderr);
285#endif
286      if(strncasecmp(r_inputs->value,"C-FORTRAN",9)==0){
287        r_inputs=getMap(request_inputs,"Identifier");
288        char fname[1024];
289        sprintf(fname,"%s_",r_inputs->value);
290#ifdef DEBUG
291        fprintf(stderr,"Try to load function %s\n",fname);
292#endif
293#ifdef WIN32
294        typedef int (CALLBACK* execute_t)(char***,char***,char***);
295        execute_t execute=(execute_t)GetProcAddress(so,fname);
296#else
297        typedef int (*execute_t)(char***,char***,char***);
298        execute_t execute=(execute_t)dlsym(so,fname);
299#endif
300#ifdef DEBUG
301#ifdef WIN32
302        errstr = GetLastError();
303#else
304        errstr = dlerror();
305#endif
306        fprintf(stderr,"Function loaded %s\n",errstr);
307#endif 
308
309        char main_conf[10][30][1024];
310        char inputs[10][30][1024];
311        char outputs[10][30][1024];
312        for(int i=0;i<10;i++){
313          for(int j=0;j<30;j++){
314            memset(main_conf[i][j],0,1024);
315            memset(inputs[i][j],0,1024);
316            memset(outputs[i][j],0,1024);
317          }
318        }
319        mapsToCharXXX(m,(char***)main_conf);
320        mapsToCharXXX(request_input_real_format,(char***)inputs);
321        mapsToCharXXX(request_output_real_format,(char***)outputs);
322        *eres=execute((char***)&main_conf[0],(char***)&inputs[0],(char***)&outputs[0]);
323#ifdef DEBUG
324        fprintf(stderr,"Function run successfully \n");
325#endif
326        charxxxToMaps((char***)&outputs[0],&request_output_real_format);
327      }else{
328#ifdef DEBUG
329#ifdef WIN32
330        errstr = GetLastError();
331        fprintf(stderr,"Function %s failed to load because of %d\n",r_inputs->value,errstr);
332#endif
333#endif
334        r_inputs=getMap(request_inputs,"Identifier");
335#ifdef DEBUG
336        fprintf(stderr,"Try to load function %s\n",r_inputs->value);
337#endif
338        typedef int (*execute_t)(maps**,maps**,maps**);
339#ifdef WIN32
340        execute_t execute=(execute_t)GetProcAddress(so,r_inputs->value); 
341#else
342        execute_t execute=(execute_t)dlsym(so,r_inputs->value);
343#endif
344
345#ifdef DEBUG
346#ifdef WIN32
347        errstr = GetLastError();
348#else
349        errstr = dlerror();
350#endif
351        fprintf(stderr,"Function loaded %s\n",errstr);
352#endif 
353
354#ifdef DEBUG
355        fprintf(stderr,"Now run the function \n");
356        fflush(stderr);
357#endif
358        *eres=execute(&m,&request_input_real_format,&request_output_real_format);
359#ifdef DEBUG
360        fprintf(stderr,"Function loaded and returned %d\n",eres);
361        fflush(stderr);
362#endif
363      }
364#ifdef WIN32
365      *ioutputs=dupMaps(&request_output_real_format);
366      FreeLibrary(so);
367#else
368      dlclose(so);
369#endif
370    } else {
371      /**
372       * Unable to load the specified shared library
373       */
374      char tmps[1024];
375#ifdef WIN32
376      DWORD errstr = GetLastError();
377#else
378      char* errstr = dlerror();
379#endif
380      sprintf(tmps,_("C Library can't be loaded %s \n"),errstr);
381      map* tmps1=createMap("text",tmps);
382      printExceptionReportResponse(m,tmps1);
383      *eres=-1;
384    }
385  }
386  else
387#ifdef USE_PYTHON
388    if(strncasecmp(r_inputs->value,"PYTHON",6)==0){
389      *eres=zoo_python_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
390    }
391    else
392#endif
393       
394#ifdef USE_JAVA
395      if(strncasecmp(r_inputs->value,"JAVA",4)==0){
396        *eres=zoo_java_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
397      }
398      else
399#endif
400
401#ifdef USE_PHP
402        if(strncasecmp(r_inputs->value,"PHP",3)==0){
403          *eres=zoo_php_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
404        }
405        else
406#endif
407           
408           
409#ifdef USE_PERL
410          if(strncasecmp(r_inputs->value,"PERL",4)==0){
411            *eres=zoo_perl_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
412          }
413          else
414#endif
415
416#ifdef USE_JS
417            if(strncasecmp(r_inputs->value,"JS",2)==0){
418              *eres=zoo_js_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
419            }
420            else
421#endif
422              {
423                char tmpv[1024];
424                sprintf(tmpv,_("Programming Language (%s) set in ZCFG file is not currently supported by ZOO Kernel.\n"),r_inputs->value);
425                map* tmps=createMap("text",tmpv);
426                printExceptionReportResponse(m,tmps);
427                *eres=-1;
428              }
429  *myMap=m;
430  *ioutputs=request_output_real_format;
431}
432
433
434#ifdef WIN32
435/**
436 * createProcess function: create a new process after setting some env variables
437 */
438void createProcess(maps* m,map* request_inputs,service* s1,char* opts,int cpid, maps* inputs,maps* outputs){
439  STARTUPINFO si;
440  PROCESS_INFORMATION pi;
441  ZeroMemory( &si, sizeof(si) );
442  si.cb = sizeof(si);
443  ZeroMemory( &pi, sizeof(pi) );
444  char *tmp=(char *)malloc((1024+cgiContentLength)*sizeof(char));
445  char *tmpq=(char *)malloc((1024+cgiContentLength)*sizeof(char));
446  map *req=getMap(request_inputs,"request");
447  map *id=getMap(request_inputs,"identifier");
448  map *di=getMap(request_inputs,"DataInputs");
449
450  char *dataInputsKVP=getMapsAsKVP(inputs,cgiContentLength,0);
451  char *dataOutputsKVP=getMapsAsKVP(outputs,cgiContentLength,1);
452#ifdef DEBUG
453  fprintf(stderr,"DATAINPUTSKVP %s\n",dataInputsKVP);
454  fprintf(stderr,"DATAOUTPUTSKVP %s\n",dataOutputsKVP);
455#endif
456  map *sid=getMapFromMaps(m,"lenv","sid");
457  map* r_inputs=getMapFromMaps(m,"main","tmpPath");
458  map* r_inputs1=getMap(request_inputs,"metapath");
459  int hasIn=-1;
460  if(r_inputs1==NULL){
461    r_inputs1=createMap("metapath","");
462    hasIn=1;
463  }
464  map* r_inputs2=getMap(s1->content,"ResponseDocument");
465  if(r_inputs2==NULL)
466    r_inputs2=getMap(s1->content,"RawDataOutput");
467  map *tmpPath=getMapFromMaps(m,"lenv","cwd");
468
469  if(r_inputs2!=NULL){
470    sprintf(tmp,"\"metapath=%s&request=%s&service=WPS&version=1.0.0&Identifier=%s&DataInputs=%s&%s=%s&cgiSid=%s\"",r_inputs1->value,req->value,id->value,dataInputsKVP,r_inputs2->name,r_inputs2->value,sid->value);
471    sprintf(tmpq,"metapath=%s&request=%s&service=WPS&version=1.0.0&Identifier=%s&DataInputs=%s&%s=%s",r_inputs1->value,req->value,id->value,dataInputsKVP,r_inputs2->name,dataOutputsKVP);
472  }
473  else{
474    sprintf(tmp,"\"metapath=%s&request=%s&service=WPS&version=1.0.0&Identifier=%s&DataInputs=%s&cgiSid=%s\"",r_inputs1->value,req->value,id->value,dataInputsKVP,sid->value);
475    sprintf(tmpq,"metapath=%s&request=%s&service=WPS&version=1.0.0&Identifier=%s&DataInputs=%s",r_inputs1->value,req->value,id->value,dataInputsKVP,sid->value);
476  }
477 
478  if(hasIn>0){
479    freeMap(&r_inputs1);
480    free(r_inputs1);
481  }
482  char *tmp1=strdup(tmp);
483  sprintf(tmp,"zoo_loader.cgi %s \"%s\"",tmp1,sid->value);
484 
485  free(dataInputsKVP);
486  free(dataOutputsKVP);
487  //printf("REQUEST IS : %s \n",tmp);
488#ifdef DEBUG
489  fprintf(stderr,"REQUEST IS : %s \n",tmp);
490#endif
491  SetEnvironmentVariable("CGISID",TEXT(sid->value));
492  SetEnvironmentVariable("QUERY_STRING",TEXT(tmpq));
493  char clen[1000];
494  sprintf(clen,"%d",strlen(tmpq));
495  SetEnvironmentVariable("CONTENT_LENGTH",TEXT(clen));
496
497  if( !CreateProcess( NULL,             // No module name (use command line)
498                      TEXT(tmp),        // Command line
499                      NULL,             // Process handle not inheritable
500                      NULL,             // Thread handle not inheritable
501                      FALSE,            // Set handle inheritance to FALSE
502                      CREATE_NO_WINDOW, // Apache won't wait until the end
503                      NULL,             // Use parent's environment block
504                      NULL,             // Use parent's starting directory
505                      &si,              // Pointer to STARTUPINFO struct
506                      &pi )             // Pointer to PROCESS_INFORMATION struct
507      ) 
508    { 
509      //printf("CreateProcess failed (%d).\n",GetLastError() );
510#ifdef DEBUG
511      fprintf( stderr, "CreateProcess failed (%d).\n", GetLastError() );
512#endif
513      return ;
514    }else{
515    //printf("CreateProcess successfull (%d).\n",GetLastError() );
516#ifdef DEBUG
517    fprintf( stderr, "CreateProcess successfull (%d).\n\n\n\n", GetLastError() );
518#endif
519  }
520  CloseHandle( pi.hProcess );
521  CloseHandle( pi.hThread );
522  //printf("CreateProcess finished !\n");
523#ifdef DEBUG
524  fprintf(stderr,"CreateProcess finished !\n");
525#endif
526}
527#endif
528
529int runRequest(map* request_inputs)
530{
531
532#ifndef USE_GDB
533  (void) signal(SIGSEGV,sig_handler);
534  (void) signal(SIGTERM,sig_handler);
535  (void) signal(SIGINT,sig_handler);
536  (void) signal(SIGILL,sig_handler);
537  (void) signal(SIGFPE,sig_handler);
538  (void) signal(SIGABRT,sig_handler);
539#endif
540
541  map* r_inputs=NULL;
542  maps* m=NULL;
543
544  char* REQUEST=NULL;
545  /**
546   * Parsing service specfic configuration file
547   */
548  m=(maps*)malloc(MAPS_SIZE);
549  if(m == NULL){
550    return errorException(m, _("Unable to allocate memory."), "InternalError");
551  }
552  char ntmp[1024];
553#ifndef WIN32
554  char *pntmp=getcwd(ntmp,1024);
555#else
556  _getcwd(ntmp,1024);
557#endif
558  r_inputs=getMapOrFill(request_inputs,"metapath","");
559
560
561  char conf_file[10240];
562  snprintf(conf_file,10240,"%s/%s/main.cfg",ntmp,r_inputs->value);
563  if(conf_read(conf_file,m)==2){
564    errorException(NULL, _("Unable to load the main.cfg file."),"InternalError");
565    free(m);
566    return 1;
567  }
568#ifdef DEBUG
569  fprintf(stderr, "***** BEGIN MAPS\n"); 
570  dumpMaps(m);
571  fprintf(stderr, "***** END MAPS\n");
572#endif
573
574  map *getPath=getMapFromMaps(m,"main","gettextPath");
575  if(getPath!=NULL){
576    bindtextdomain ("zoo-kernel",getPath->value);
577    bindtextdomain ("zoo-services",getPath->value);   
578  }else{
579    bindtextdomain ("zoo-kernel","/usr/share/locale/");
580    bindtextdomain ("zoo-services","/usr/share/locale/");
581  }
582
583
584  /**
585   * Manage our own error log file (usefull to separate standard apache debug
586   * messages from the ZOO-Kernel ones but also for IIS users to avoid wrong
587   * headers messages returned by the CGI due to wrong redirection of stderr)
588   */
589  FILE * fstde=NULL;
590  map* fstdem=getMapFromMaps(m,"main","logPath");
591  if(fstdem!=NULL)
592        fstde = freopen(fstdem->value, "a+", stderr) ;
593
594  r_inputs=getMap(request_inputs,"language");
595  if(r_inputs==NULL)
596    r_inputs=getMapFromMaps(m,"main","language");
597  if(r_inputs!=NULL){
598    char *tmp=strdup(r_inputs->value);
599    setMapInMaps(m,"main","language",tmp);
600    translateChar(tmp,'-','_');
601    setlocale (LC_ALL, tmp);
602#ifdef WIN32
603    char tmp1[12];
604    sprintf(tmp1,"LC_ALL=%s",tmp);
605    putenv(tmp1);
606#endif
607    free(tmp);
608  }
609  else{
610    setlocale (LC_ALL, "en_US");
611#ifdef WIN32
612    char tmp1[12];
613    sprintf(tmp1,"LC_ALL=en_US");
614    putenv(tmp1);
615#endif
616    setMapInMaps(m,"main","language","en-US");
617  }
618  setlocale (LC_NUMERIC, "en_US");
619  bind_textdomain_codeset("zoo-kernel","UTF-8");
620  textdomain("zoo-kernel");
621  bind_textdomain_codeset("zoo-services","UTF-8");
622  textdomain("zoo-services");
623
624  map* lsoap=getMap(request_inputs,"soap");
625  if(lsoap!=NULL && strcasecmp(lsoap->value,"true")==0)
626    setMapInMaps(m,"main","isSoap","true");
627  else
628    setMapInMaps(m,"main","isSoap","false");
629
630
631  /**
632   * Check for minimum inputs
633   */
634  r_inputs=getMap(request_inputs,"Request");
635  if(request_inputs==NULL || r_inputs==NULL){ 
636    errorException(m, _("Parameter <request> was not specified"),"MissingParameterValue");
637    freeMaps(&m);
638    free(m);
639    freeMap(&request_inputs);
640    free(request_inputs);
641    return 1;
642  }
643  else{
644    REQUEST=strdup(r_inputs->value);
645    if(strncasecmp(r_inputs->value,"GetCapabilities",15)!=0
646       && strncasecmp(r_inputs->value,"DescribeProcess",15)!=0
647       && strncasecmp(r_inputs->value,"Execute",7)!=0){ 
648      errorException(m, _("Unenderstood <request> value. Please check that it was set to GetCapabilities, DescribeProcess or Execute."), "InvalidParameterValue");
649      freeMaps(&m);
650      free(m);
651      free(REQUEST);
652      return 1;
653    }
654  }
655  r_inputs=NULL;
656  r_inputs=getMap(request_inputs,"Service");
657  if(r_inputs==NULLMAP){
658    errorException(m, _("Parameter <service> was not specified"),"MissingParameterValue");
659    freeMaps(&m);
660    free(m);
661    free(REQUEST);
662    return 1;
663  }
664  if(strncasecmp(REQUEST,"GetCapabilities",15)!=0){
665    r_inputs=getMap(request_inputs,"Version");
666    if(r_inputs==NULL){ 
667      errorException(m, _("Parameter <version> was not specified"),"MissingParameterValue");
668      freeMaps(&m);
669      free(m);
670      free(REQUEST);
671      return 1;
672    }
673  }
674
675  r_inputs=getMap(request_inputs,"serviceprovider");
676  if(r_inputs==NULL){
677    addToMap(request_inputs,"serviceprovider","");
678  }
679
680  maps* request_output_real_format=NULL;
681  map* tmpm=getMapFromMaps(m,"main","serverAddress");
682  if(tmpm!=NULL)
683    SERVICE_URL=strdup(tmpm->value);
684  else
685    SERVICE_URL=strdup(DEFAULT_SERVICE_URL);
686
687  service* s1;
688  int scount=0;
689#ifdef DEBUG
690  dumpMap(r_inputs);
691#endif
692  char conf_dir[1024];
693  int t;
694  char tmps1[1024];
695
696  r_inputs=NULL;
697  r_inputs=getMap(request_inputs,"metapath");
698  if(r_inputs!=NULL)
699    snprintf(conf_dir,1024,"%s/%s",ntmp,r_inputs->value);
700  else
701    snprintf(conf_dir,1024,"%s",ntmp);
702
703  if(strncasecmp(REQUEST,"GetCapabilities",15)==0){
704    struct dirent *dp;
705#ifdef DEBUG
706    dumpMap(r_inputs);
707#endif
708    DIR *dirp = opendir(conf_dir);
709    if(dirp==NULL){
710      return errorException(m, _("The specified path doesn't exist."),"InvalidParameterValue");
711    }
712    xmlDocPtr doc = xmlNewDoc(BAD_CAST "1.0");
713    r_inputs=NULL;
714    r_inputs=getMap(request_inputs,"ServiceProvider");
715    xmlNodePtr n;
716    if(r_inputs!=NULL)
717      n = printGetCapabilitiesHeader(doc,r_inputs->value,m);
718    else
719      n = printGetCapabilitiesHeader(doc,"",m);
720    /**
721     * Here we need to close stdout to ensure that not supported chars
722     * has been found in the zcfg and then printed on stdout
723     */
724    int saved_stdout = dup(fileno(stdout));
725    dup2(fileno(stderr),fileno(stdout));
726    while ((dp = readdir(dirp)) != NULL)
727      if(strstr(dp->d_name,".zcfg")!=0){
728        memset(tmps1,0,1024);
729        snprintf(tmps1,1024,"%s/%s",conf_dir,dp->d_name);
730        s1=(service*)malloc(SERVICE_SIZE);
731        if(s1 == NULL){ 
732          return errorException(m, _("Unable to allocate memory."),"InternalError");
733        }
734#ifdef DEBUG
735        fprintf(stderr,"#################\n%s\n#################\n",tmps1);
736#endif
737        t=getServiceFromFile(tmps1,&s1);
738#ifdef DEBUG
739        dumpService(s1);
740        fflush(stdout);
741        fflush(stderr);
742#endif
743        printGetCapabilitiesForProcess(m,n,s1);
744        freeService(&s1);
745        free(s1);
746        scount++;
747      }
748    (void)closedir(dirp);
749    fflush(stdout);
750    dup2(saved_stdout,fileno(stdout));
751    printDocument(m,doc,getpid());
752    freeMaps(&m);
753    free(m);
754    free(REQUEST);
755    free(SERVICE_URL);
756    fflush(stdout);
757    return 0;
758  }
759  else{
760    r_inputs=getMap(request_inputs,"Identifier");
761    if(r_inputs==NULL 
762       || strlen(r_inputs->name)==0 || strlen(r_inputs->value)==0){ 
763      errorException(m, _("Mandatory <identifier> was not specified"),"MissingParameterValue");
764      freeMaps(&m);
765      free(m);
766      free(REQUEST);
767      free(SERVICE_URL);
768      return 0;
769    }
770
771    struct dirent *dp;
772    DIR *dirp = opendir(conf_dir);
773    if(dirp==NULL){
774      errorException(m, _("The specified path path doesn't exist."),"InvalidParameterValue");
775      freeMaps(&m);
776      free(m);
777      free(REQUEST);
778      free(SERVICE_URL);
779      return 0;
780    }
781    if(strncasecmp(REQUEST,"DescribeProcess",15)==0){
782      /**
783       * Loop over Identifier list
784       */
785      xmlDocPtr doc = xmlNewDoc(BAD_CAST "1.0");
786      r_inputs=NULL;
787      r_inputs=getMap(request_inputs,"ServiceProvider");
788
789      xmlNodePtr n;
790      if(r_inputs!=NULL)
791        n = printDescribeProcessHeader(doc,r_inputs->value,m);
792      else
793        n = printDescribeProcessHeader(doc,"",m);
794
795      r_inputs=getMap(request_inputs,"Identifier");
796      char *tmps=strtok(r_inputs->value,",");
797     
798      char buff[256];
799      char buff1[1024];
800      int saved_stdout = dup(fileno(stdout));
801      dup2(fileno(stderr),fileno(stdout));
802      while(tmps){
803        memset(buff,0,256);
804        snprintf(buff,256,"%s.zcfg",tmps);
805        memset(buff1,0,1024);
806#ifdef DEBUG
807        printf("\n#######%s\n########\n",buff1);
808#endif
809        while ((dp = readdir(dirp)) != NULL)
810          if((strcasecmp("all.zcfg",buff)==0 && strstr(dp->d_name,".zcfg")>0)
811             || strcasecmp(dp->d_name,buff)==0){
812            memset(buff1,0,1024);
813            snprintf(buff1,1024,"%s/%s",conf_dir,dp->d_name);
814            s1=(service*)malloc(SERVICE_SIZE);
815            if(s1 == NULL){
816              dup2(saved_stdout,fileno(stdout));
817              return errorException(m, _("Unable to allocate memory."),"InternalError");
818            }
819#ifdef DEBUG
820            printf("#################\n%s\n#################\n",buff1);
821#endif
822            t=getServiceFromFile(buff1,&s1);
823#ifdef DEBUG
824            dumpService(s1);
825#endif
826            printDescribeProcessForProcess(m,n,s1,1);
827            freeService(&s1);
828            free(s1);
829            scount++;
830          }
831        rewinddir(dirp);
832        tmps=strtok(NULL,",");
833      }
834      closedir(dirp);
835      fflush(stdout);
836      dup2(saved_stdout,fileno(stdout));
837      printDocument(m,doc,getpid());
838      freeMaps(&m);
839      free(m);
840      free(REQUEST);
841      free(SERVICE_URL);
842      fflush(stdout);
843      return 0;
844    }
845    else
846      if(strncasecmp(REQUEST,"Execute",strlen(REQUEST))!=0){
847        errorException(m, _("Unenderstood <request> value. Please check that it was set to GetCapabilities, DescribeProcess or Execute."), "InvalidParameterValue");
848#ifdef DEBUG
849        fprintf(stderr,"No request found %s",REQUEST);
850#endif 
851        closedir(dirp);
852        freeMaps(&m);
853        free(m);
854        free(REQUEST);
855        free(SERVICE_URL);
856        fflush(stdout);
857        return 0;
858      }
859    closedir(dirp);
860  }
861 
862  s1=NULL;
863  s1=(service*)malloc(SERVICE_SIZE);
864  if(s1 == NULL){
865    freeMaps(&m);
866    free(m);
867    free(REQUEST);
868    free(SERVICE_URL);
869    return errorException(m, _("Unable to allocate memory."),"InternalError");
870  }
871  r_inputs=getMap(request_inputs,"MetaPath");
872  if(r_inputs!=NULL)
873    snprintf(tmps1,1024,"%s/%s",ntmp,r_inputs->value);
874  else
875    snprintf(tmps1,1024,"%s/",ntmp);
876  r_inputs=getMap(request_inputs,"Identifier");
877  char *ttmp=strdup(tmps1);
878  snprintf(tmps1,1024,"%s/%s.zcfg",ttmp,r_inputs->value);
879  free(ttmp);
880#ifdef DEBUG
881  fprintf(stderr,"Trying to load %s\n", tmps1);
882#endif
883  int saved_stdout = dup(fileno(stdout));
884  dup2(fileno(stderr),fileno(stdout));
885  t=getServiceFromFile(tmps1,&s1);
886  fflush(stdout);
887  dup2(saved_stdout,fileno(stdout));
888  if(t<0){
889    char *tmpMsg=(char*)malloc(2048+strlen(r_inputs->value));
890   
891    sprintf(tmpMsg,_("The value for <indetifier> seems to be wrong (%s). Please, ensure that the process exist using the GetCapabilities request."),r_inputs->value);
892    errorException(m, tmpMsg, "InvalidParameterValue");
893    free(tmpMsg);
894    free(s1);
895    freeMaps(&m);
896    free(m);
897    free(REQUEST);
898    free(SERVICE_URL);
899    return 0;
900  }
901  close(saved_stdout);
902
903#ifdef DEBUG
904  dumpService(s1);
905#endif
906  int j;
907 
908
909  /**
910   * Create the input and output maps data structure
911   */
912  int i=0;
913  HINTERNET hInternet;
914  HINTERNET res;
915  hInternet=InternetOpen(
916#ifndef WIN32
917                         (LPCTSTR)
918#endif
919                         "ZooWPSClient\0",
920                         INTERNET_OPEN_TYPE_PRECONFIG,
921                         NULL,NULL, 0);
922
923#ifndef WIN32
924  if(!CHECK_INET_HANDLE(hInternet))
925    fprintf(stderr,"WARNING : hInternet handle failed to initialize");
926#endif
927  maps* request_input_real_format=NULL;
928  maps* tmpmaps = request_input_real_format;
929  map* postRequest=NULL;
930  postRequest=getMap(request_inputs,"xrequest");
931  if(postRequest==NULLMAP){
932    /**
933     * Parsing outputs provided as KVP
934     */
935    r_inputs=NULL;
936#ifdef DEBUG
937    fprintf(stderr,"OUTPUT Parsing ... \n");
938#endif
939    r_inputs=getMap(request_inputs,"ResponseDocument"); 
940    if(r_inputs==NULL) r_inputs=getMap(request_inputs,"RawDataOutput");
941   
942#ifdef DEBUG
943    fprintf(stderr,"OUTPUT Parsing ... \n");
944#endif
945    if(r_inputs!=NULL){
946#ifdef DEBUG
947      fprintf(stderr,"OUTPUT Parsing start now ... \n");
948#endif
949      char cursor_output[10240];
950      char *cotmp=strdup(r_inputs->value);
951      snprintf(cursor_output,10240,"%s",cotmp);
952      free(cotmp);
953      j=0;
954       
955      /**
956       * Put each Output into the outputs_as_text array
957       */
958      char * pToken;
959      maps* tmp_output=NULL;
960#ifdef DEBUG
961      fprintf(stderr,"OUTPUT [%s]\n",cursor_output);
962#endif
963      pToken=strtok(cursor_output,";");
964      char** outputs_as_text=(char**)malloc(128*sizeof(char*));
965      if(outputs_as_text == NULL) {
966        return errorException(m, _("Unable to allocate memory"), "InternalError");
967      }
968      i=0;
969      while(pToken!=NULL){
970#ifdef DEBUG
971        fprintf(stderr,"***%s***\n",pToken);
972        fflush(stderr);
973        fprintf(stderr,"***%s***\n",pToken);
974#endif
975        outputs_as_text[i]=(char*)malloc((strlen(pToken)+1)*sizeof(char));
976        if(outputs_as_text[i] == NULL) {
977          return errorException(m, _("Unable to allocate memory"), "InternalError");
978        }
979        snprintf(outputs_as_text[i],strlen(pToken)+1,"%s",pToken);
980        pToken = strtok(NULL,";");
981        i++;
982      }
983      for(j=0;j<i;j++){
984        char *tmp=strdup(outputs_as_text[j]);
985        free(outputs_as_text[j]);
986        char *tmpc;
987        tmpc=strtok(tmp,"@");
988        int k=0;
989        while(tmpc!=NULL){
990          if(k==0){
991            if(tmp_output==NULL){
992              tmp_output=(maps*)malloc(MAPS_SIZE);
993              if(tmp_output == NULL){
994                return errorException(m, _("Unable to allocate memory."), "InternalError");
995              }
996              tmp_output->name=strdup(tmpc);
997              tmp_output->content=NULL;
998              tmp_output->next=NULL;
999            }
1000          }
1001          else{
1002            char *tmpv=strstr(tmpc,"=");
1003            char tmpn[256];
1004            memset(tmpn,0,256);
1005            strncpy(tmpn,tmpc,(strlen(tmpc)-strlen(tmpv))*sizeof(char));
1006            tmpn[strlen(tmpc)-strlen(tmpv)]=0;
1007#ifdef DEBUG
1008            fprintf(stderr,"OUTPUT DEF [%s]=[%s]\n",tmpn,tmpv+1);
1009#endif
1010            if(tmp_output->content==NULL){
1011              tmp_output->content=createMap(tmpn,tmpv+1);
1012              tmp_output->content->next=NULL;
1013            }
1014            else
1015              addToMap(tmp_output->content,tmpn,tmpv+1);
1016          }
1017          k++;
1018#ifdef DEBUG
1019          fprintf(stderr,"***%s***\n",tmpc);
1020#endif
1021          tmpc=strtok(NULL,"@");
1022        }
1023        if(request_output_real_format==NULL)
1024          request_output_real_format=dupMaps(&tmp_output);
1025        else
1026          addMapsToMaps(&request_output_real_format,tmp_output);
1027        freeMaps(&tmp_output);
1028        free(tmp_output);
1029        tmp_output=NULL;
1030#ifdef DEBUG
1031        dumpMaps(tmp_output);
1032        fflush(stderr);
1033#endif
1034        free(tmp);
1035      }
1036      free(outputs_as_text);
1037    }
1038
1039
1040    /**
1041     * Parsing inputs provided as KVP
1042     */
1043    r_inputs=getMap(request_inputs,"DataInputs");
1044#ifdef DEBUG
1045    fprintf(stderr,"DATA INPUTS [%s]\n",r_inputs->value);
1046#endif
1047    char cursor_input[40960];
1048    if(r_inputs!=NULL)
1049      snprintf(cursor_input,40960,"%s",r_inputs->value);
1050    else{
1051      errorException(m, _("Parameter <DataInputs> was not specified"),"MissingParameterValue");
1052      freeMaps(&m);
1053      free(m);
1054      free(REQUEST);
1055      free(SERVICE_URL);
1056      InternetCloseHandle(hInternet);
1057      freeService(&s1);
1058      free(s1);
1059      return 0;
1060    }
1061    j=0;
1062 
1063    /**
1064     * Put each DataInputs into the inputs_as_text array
1065     */
1066    char *tmp1=strdup(cursor_input);
1067    char * pToken;
1068    pToken=strtok(cursor_input,";");
1069    if(pToken!=NULL && strncasecmp(pToken,tmp1,strlen(tmp1))==0){
1070      char* tmp2=url_decode(tmp1);
1071      snprintf(cursor_input,(strlen(tmp2)+1)*sizeof(char),"%s",tmp2);
1072      free(tmp2);
1073      pToken=strtok(cursor_input,";");
1074    }
1075    free(tmp1);
1076
1077    char** inputs_as_text=(char**)malloc(100*sizeof(char*));
1078    if(inputs_as_text == NULL){
1079      return errorException(m, _("Unable to allocate memory."), "InternalError");
1080    }
1081    i=0;
1082    while(pToken!=NULL){
1083#ifdef DEBUG
1084      fprintf(stderr,"***%s***\n",pToken);
1085#endif
1086      fflush(stderr);
1087#ifdef DEBUG
1088      fprintf(stderr,"***%s***\n",pToken);
1089#endif
1090      inputs_as_text[i]=(char*)malloc((strlen(pToken)+1)*sizeof(char));
1091      snprintf(inputs_as_text[i],strlen(pToken)+1,"%s",pToken);
1092      if(inputs_as_text[i] == NULL){
1093        return errorException(m, _("Unable to allocate memory."), "InternalError");
1094      }
1095      pToken = strtok(NULL,";");
1096      i++;
1097    }
1098
1099    for(j=0;j<i;j++){
1100      char *tmp=strdup(inputs_as_text[j]);
1101      free(inputs_as_text[j]);
1102      char *tmpc;
1103      tmpc=strtok(tmp,"@");
1104      while(tmpc!=NULL){
1105#ifdef DEBUG
1106        fprintf(stderr,"***\n***%s***\n",tmpc);
1107#endif
1108        char *tmpv=strstr(tmpc,"=");
1109        char tmpn[256];
1110        memset(tmpn,0,256);
1111        if(tmpv!=NULL){
1112          strncpy(tmpn,tmpc,(strlen(tmpc)-strlen(tmpv))*sizeof(char));
1113          tmpn[strlen(tmpc)-strlen(tmpv)]=0;
1114        }
1115        else{
1116          strncpy(tmpn,tmpc,strlen(tmpc)*sizeof(char));
1117          tmpn[strlen(tmpc)]=0;
1118        }
1119#ifdef DEBUG
1120        fprintf(stderr,"***\n*** %s = %s ***\n",tmpn,tmpv+1);
1121#endif
1122        if(tmpmaps==NULL){
1123          tmpmaps=(maps*)malloc(MAPS_SIZE);
1124          if(tmpmaps == NULL){
1125            return errorException(m, _("Unable to allocate memory."), "InternalError");
1126          }
1127          tmpmaps->name=strdup(tmpn);
1128          if(tmpv!=NULL){
1129            char *tmpvf=url_decode(tmpv+1);
1130            tmpmaps->content=createMap("value",tmpvf);
1131            free(tmpvf);
1132          }
1133          else
1134            tmpmaps->content=createMap("value","Reference");
1135          tmpmaps->next=NULL;
1136        }
1137        tmpc=strtok(NULL,"@");
1138        while(tmpc!=NULL){
1139#ifdef DEBUG
1140          fprintf(stderr,"*** KVP NON URL-ENCODED \n***%s***\n",tmpc);
1141#endif
1142          char *tmpv1=strstr(tmpc,"=");
1143#ifdef DEBUG
1144          fprintf(stderr,"*** VALUE NON URL-ENCODED \n***%s***\n",tmpv1+1);
1145#endif
1146          char tmpn1[1024];
1147          memset(tmpn1,0,1024);
1148          if(tmpv1!=NULL){
1149            strncpy(tmpn1,tmpc,strlen(tmpc)-strlen(tmpv1));
1150            tmpn1[strlen(tmpc)-strlen(tmpv1)]=0;
1151            addToMap(tmpmaps->content,tmpn1,tmpv1+1);
1152          }
1153          else{
1154            strncpy(tmpn1,tmpc,strlen(tmpc));
1155            tmpn1[strlen(tmpc)]=0;
1156            map* lmap=getLastMap(tmpmaps->content);
1157            char *tmpValue=(char*)malloc((strlen(tmpv)+strlen(tmpc)+1)*sizeof(char));
1158            sprintf(tmpValue,"%s@%s",tmpv+1,tmpc);
1159            free(lmap->value);
1160            lmap->value=strdup(tmpValue);
1161            free(tmpValue);
1162            tmpc=strtok(NULL,"@");
1163            continue;
1164          }
1165#ifdef DEBUG
1166          fprintf(stderr,"*** NAME NON URL-ENCODED \n***%s***\n",tmpn1);
1167          fprintf(stderr,"*** VALUE NON URL-ENCODED \n***%s***\n",tmpv1+1);
1168#endif
1169          if(strcmp(tmpn1,"xlink:href")!=0)
1170            addToMap(tmpmaps->content,tmpn1,tmpv1+1);
1171          else
1172            if(tmpv1!=NULL){
1173              char *tmpx2=url_decode(tmpv1+1);
1174              if(strncasecmp(tmpx2,"http://",7)!=0 &&
1175                 strncasecmp(tmpx2,"ftp://",6)!=0){
1176                char emsg[1024];
1177                sprintf(emsg,_("Unable to find a valid protocol to download the remote file %s"),tmpv1+1);
1178                errorException(m,emsg,"InternalError");
1179                freeMaps(&m);
1180                free(m);
1181                free(REQUEST);
1182                free(SERVICE_URL);
1183                InternetCloseHandle(hInternet);
1184                freeService(&s1);
1185                free(s1);
1186                return 0;
1187              }
1188#ifdef DEBUG
1189              fprintf(stderr,"REQUIRE TO DOWNLOAD A FILE FROM A SERVER : url(%s)\n",tmpv1+1);
1190#endif
1191              addToMap(tmpmaps->content,tmpn1,tmpx2);
1192             
1193#ifndef WIN32
1194              if(CHECK_INET_HANDLE(hInternet))
1195#endif
1196                {
1197                  if(loadRemoteFile(m,tmpmaps->content,hInternet,tmpx2)<0){
1198                    freeMaps(&m);
1199                    free(m);
1200                    free(REQUEST);
1201                    free(SERVICE_URL);
1202                    InternetCloseHandle(hInternet);
1203                    freeService(&s1);
1204                    free(s1);
1205                    return 0;
1206                  }
1207                }
1208              free(tmpx2);
1209              addToMap(tmpmaps->content,"Reference",tmpv1+1);
1210            }
1211          tmpc=strtok(NULL,"@");
1212        }
1213#ifdef DEBUG
1214        dumpMaps(tmpmaps);
1215        fflush(stderr);
1216#endif
1217        if(request_input_real_format==NULL)
1218          request_input_real_format=dupMaps(&tmpmaps);
1219        else{
1220          maps* testPresence=getMaps(request_input_real_format,tmpmaps->name);
1221          if(testPresence!=NULL){
1222            elements* elem=getElements(s1->inputs,tmpmaps->name);
1223            if(elem!=NULL){
1224              if(appendMapsToMaps(m,request_input_real_format,tmpmaps,elem)<0){
1225                freeMaps(&m);
1226                free(m);
1227                free(REQUEST);
1228                free(SERVICE_URL);
1229                InternetCloseHandle(hInternet);
1230                freeService(&s1);
1231                free(s1);
1232                return 0;
1233              }
1234            }
1235          }
1236          else
1237            addMapsToMaps(&request_input_real_format,tmpmaps);
1238        }
1239        freeMaps(&tmpmaps);
1240        free(tmpmaps);
1241        tmpmaps=NULL;
1242        free(tmp);
1243      }
1244    }
1245    free(inputs_as_text);
1246  }
1247  else {
1248    /**
1249     * Parse XML request
1250     */ 
1251    xmlInitParser();
1252#ifdef DEBUG
1253    fflush(stderr);
1254    fprintf(stderr,"BEFORE %s\n",postRequest->value);
1255    fflush(stderr);
1256#endif
1257    xmlDocPtr doc =
1258      xmlParseMemory(postRequest->value,cgiContentLength);
1259#ifdef DEBUG
1260    fprintf(stderr,"AFTER\n");
1261    fflush(stderr);
1262#endif
1263    /**
1264     * Parse every Input in DataInputs node.
1265     */
1266    xmlXPathObjectPtr tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='Input']");
1267    xmlNodeSet* tmps=tmpsptr->nodesetval;
1268#ifdef DEBUG
1269    fprintf(stderr,"*****%d*****\n",tmps->nodeNr);
1270#endif
1271    for(int k=0;k<tmps->nodeNr;k++){
1272      maps *tmpmaps=NULL;
1273      xmlNodePtr cur=tmps->nodeTab[k];
1274      if(tmps->nodeTab[k]->type == XML_ELEMENT_NODE) {
1275        /**
1276         * A specific Input node.
1277         */
1278#ifdef DEBUG
1279        fprintf(stderr, "= element 0 node \"%s\"\n", cur->name);
1280#endif
1281        xmlNodePtr cur2=cur->children;
1282        while(cur2!=NULL){
1283          while(cur2!=NULL && cur2->type!=XML_ELEMENT_NODE)
1284            cur2=cur2->next;
1285          if(cur2==NULL)
1286            break;
1287          /**
1288           * Indentifier
1289           */
1290          if(xmlStrncasecmp(cur2->name,BAD_CAST "Identifier",xmlStrlen(cur2->name))==0){
1291            xmlChar *val= xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1292            if(tmpmaps==NULL){
1293              tmpmaps=(maps*)malloc(MAPS_SIZE);
1294              if(tmpmaps == NULL){
1295                return errorException(m, _("Unable to allocate memory."), "InternalError");
1296              }
1297              tmpmaps->name=strdup((char*)val);
1298              tmpmaps->content=NULL;
1299              tmpmaps->next=NULL;
1300            }
1301            xmlFree(val);
1302          }
1303          /**
1304           * Title, Asbtract
1305           */
1306          if(xmlStrncasecmp(cur2->name,BAD_CAST "Title",xmlStrlen(cur2->name))==0 ||
1307             xmlStrncasecmp(cur2->name,BAD_CAST "Abstract",xmlStrlen(cur2->name))==0){
1308            xmlChar *val=
1309              xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1310            if(tmpmaps==NULL){
1311              tmpmaps=(maps*)malloc(MAPS_SIZE);
1312              if(tmpmaps == NULL){
1313                return errorException(m, _("Unable to allocate memory."), "InternalError");
1314              }
1315              tmpmaps->name=strdup("missingIndetifier");
1316              tmpmaps->content=createMap((char*)cur2->name,(char*)val);
1317              tmpmaps->next=NULL;
1318            }
1319            else{
1320              if(tmpmaps->content!=NULL)
1321                addToMap(tmpmaps->content,
1322                         (char*)cur2->name,(char*)val);
1323              else
1324                tmpmaps->content=
1325                  createMap((char*)cur2->name,(char*)val);
1326            }
1327#ifdef DEBUG
1328            dumpMaps(tmpmaps);
1329#endif
1330            xmlFree(val);
1331          }
1332          /**
1333           * InputDataFormChoice (Reference or Data ?)
1334           */
1335          if(xmlStrcasecmp(cur2->name,BAD_CAST "Reference")==0){
1336            /**
1337             * Get every attribute from a Reference node
1338             * mimeType, encoding, schema, href, method
1339             * Header and Body gesture should be added here
1340             */
1341#ifdef DEBUG
1342            fprintf(stderr,"REFERENCE\n");
1343#endif
1344            const char *refs[5]={"mimeType","encoding","schema","method","href"};
1345            for(int l=0;l<5;l++){
1346#ifdef DEBUG
1347              fprintf(stderr,"*** %s ***",refs[l]);
1348#endif
1349              xmlChar *val=xmlGetProp(cur2,BAD_CAST refs[l]);
1350              if(val!=NULL && xmlStrlen(val)>0){
1351                if(tmpmaps->content!=NULL)
1352                  addToMap(tmpmaps->content,refs[l],(char*)val);
1353                else
1354                  tmpmaps->content=createMap(refs[l],(char*)val);
1355                map* ltmp=getMap(tmpmaps->content,"method");
1356                if(l==4){
1357                  if(!(ltmp!=NULL && strcmp(ltmp->value,"POST")==0)
1358                     && CHECK_INET_HANDLE(hInternet)){
1359                    if(loadRemoteFile(m,tmpmaps->content,hInternet,(char*)val)!=0){
1360                      freeMaps(&m);
1361                      free(m);
1362                      free(REQUEST);
1363                      free(SERVICE_URL);
1364                      InternetCloseHandle(hInternet);
1365                      freeService(&s1);
1366                      free(s1);
1367                      return 0;
1368                    }
1369                  }
1370                }
1371              }
1372#ifdef DEBUG
1373              fprintf(stderr,"%s\n",val);
1374#endif
1375              xmlFree(val);
1376            }
1377#ifdef POST_DEBUG
1378            fprintf(stderr,"Parse Header and Body from Reference \n");
1379#endif
1380            xmlNodePtr cur3=cur2->children;
1381            hInternet.header=NULL;
1382            while(cur3){
1383              while(cur3!=NULL && cur3->type!=XML_ELEMENT_NODE)
1384                cur2=cur3->next;
1385              if(xmlStrcasecmp(cur3->name,BAD_CAST "Header")==0 ){
1386                const char *ha[2];
1387                ha[0]="key";
1388                ha[1]="value";
1389                int hai;
1390                char *has;
1391                char *key;
1392                for(hai=0;hai<2;hai++){
1393                  xmlChar *val=xmlGetProp(cur3,BAD_CAST ha[hai]);
1394#ifdef POST_DEBUG
1395                  fprintf(stderr,"%s = %s\n",ha[hai],(char*)val);
1396#endif
1397                  if(hai==0){
1398                    key=(char*)malloc((1+strlen((char*)val))*sizeof(char));
1399                    snprintf(key,1+strlen((char*)val),"%s",(char*)val);
1400                  }else{
1401                    has=(char*)malloc((3+strlen((char*)val)+strlen(key))*sizeof(char));
1402                    if(has == NULL){
1403                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1404                    }
1405                    snprintf(has,(3+strlen((char*)val)+strlen(key)),"%s: %s",key,(char*)val);
1406#ifdef POST_DEBUG
1407                    fprintf(stderr,"%s\n",has);
1408#endif
1409                  }
1410                }
1411                hInternet.header=curl_slist_append(hInternet.header, has);
1412                free(has);
1413              }
1414              else{
1415#ifdef POST_DEBUG
1416                fprintf(stderr,"Try to fetch the body part of the request ...\n");
1417#endif
1418                if(xmlStrcasecmp(cur3->name,BAD_CAST "Body")==0 ){
1419#ifdef POST_DEBUG
1420                  fprintf(stderr,"Body part found !!!\n",(char*)cur3->content);
1421#endif
1422                  char *tmp=new char[cgiContentLength];
1423                  memset(tmp,0,cgiContentLength);
1424                  xmlNodePtr cur4=cur3->children;
1425                  while(cur4!=NULL){
1426                    while(cur4->type!=XML_ELEMENT_NODE)
1427                      cur4=cur4->next;
1428                    xmlDocPtr bdoc = xmlNewDoc(BAD_CAST "1.0");
1429                    bdoc->encoding = xmlCharStrdup ("UTF-8");
1430                    xmlDocSetRootElement(bdoc,cur4);
1431                    xmlChar* btmps;
1432                    int bsize;
1433                    xmlDocDumpMemory(bdoc,&btmps,&bsize);
1434#ifdef POST_DEBUG
1435                    fprintf(stderr,"Body part found !!! %s %s\n",tmp,(char*)btmps);
1436#endif
1437                    if(btmps!=NULL)
1438                      sprintf(tmp,"%s",(char*)btmps);
1439                    xmlFreeDoc(bdoc);
1440                    cur4=cur4->next;
1441                  }
1442                  map *btmp=getMap(tmpmaps->content,"href");
1443                  if(btmp!=NULL){
1444#ifdef POST_DEBUG
1445                    fprintf(stderr,"%s %s\n",btmp->value,tmp);
1446                    curl_easy_setopt(hInternet.handle, CURLOPT_VERBOSE, 1);
1447#endif
1448                    res=InternetOpenUrl(hInternet,btmp->value,tmp,strlen(tmp),
1449                                        INTERNET_FLAG_NO_CACHE_WRITE,0);
1450                    char* tmpContent = (char*)malloc((res.nDataLen+1)*sizeof(char));
1451                    if(tmpContent == NULL){
1452                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1453                    }
1454                    size_t dwRead;
1455                    InternetReadFile(res, (LPVOID)tmpContent,
1456                                     res.nDataLen, &dwRead);
1457                    tmpContent[res.nDataLen]=0;
1458                    if(hInternet.header!=NULL)
1459                      curl_slist_free_all(hInternet.header);
1460                    addToMap(tmpmaps->content,"value",tmpContent);
1461#ifdef POST_DEBUG
1462                    fprintf(stderr,"DL CONTENT : (%s)\n",tmpContent);
1463#endif
1464                  }
1465                }
1466                else
1467                  if(xmlStrcasecmp(cur3->name,BAD_CAST "BodyReference")==0 ){
1468                    xmlChar *val=xmlGetProp(cur3,BAD_CAST "href");
1469                    HINTERNET bInternet,res1;
1470                    bInternet=InternetOpen(
1471#ifndef WIN32
1472                                           (LPCTSTR)
1473#endif
1474                                           "ZooWPSClient\0",
1475                                           INTERNET_OPEN_TYPE_PRECONFIG,
1476                                           NULL,NULL, 0);
1477                    if(!CHECK_INET_HANDLE(bInternet))
1478                      fprintf(stderr,"WARNING : hInternet handle failed to initialize");
1479#ifdef POST_DEBUG
1480                    curl_easy_setopt(bInternet.handle, CURLOPT_VERBOSE, 1);
1481#endif
1482                    res1=InternetOpenUrl(bInternet,(char*)val,NULL,0,
1483                                         INTERNET_FLAG_NO_CACHE_WRITE,0);
1484                    char* tmp=
1485                      (char*)malloc((res1.nDataLen+1)*sizeof(char));
1486                    if(tmp == NULL){
1487                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1488                    }
1489                    size_t bRead;
1490                    InternetReadFile(res1, (LPVOID)tmp,
1491                                     res1.nDataLen, &bRead);
1492                    tmp[res1.nDataLen]=0;
1493                    InternetCloseHandle(bInternet);
1494                    map *btmp=getMap(tmpmaps->content,"href");
1495                    if(btmp!=NULL){
1496#ifdef POST_DEBUG
1497                      fprintf(stderr,"%s %s\n",btmp->value,tmp);
1498                      curl_easy_setopt(hInternet.handle, CURLOPT_VERBOSE, 1);
1499#endif
1500                      res=InternetOpenUrl(hInternet,btmp->value,tmp,
1501                                          strlen(tmp),
1502                                          INTERNET_FLAG_NO_CACHE_WRITE,0);
1503                      char* tmpContent = (char*)malloc((res.nDataLen+1)*sizeof(char));
1504                      if(tmpContent == NULL){
1505                        return errorException(m, _("Unable to allocate memory."), "InternalError");
1506                      }
1507                      size_t dwRead;
1508                      InternetReadFile(res, (LPVOID)tmpContent,
1509                                       res.nDataLen, &dwRead);
1510                      tmpContent[res.nDataLen]=0;
1511                      if(hInternet.header!=NULL)
1512                        curl_slist_free_all(hInternet.header);
1513                      addToMap(tmpmaps->content,"value",tmpContent);
1514#ifdef POST_DEBUG
1515                      fprintf(stderr,"DL CONTENT : (%s)\n",tmpContent);
1516#endif
1517                    }
1518                  }
1519              }
1520              cur3=cur3->next;
1521            }
1522#ifdef POST_DEBUG
1523            fprintf(stderr,"Header and Body was parsed from Reference \n");
1524#endif
1525#ifdef DEBUG
1526            dumpMap(tmpmaps->content);
1527            fprintf(stderr, "= element 2 node \"%s\" = (%s)\n", 
1528                    cur2->name,cur2->content);
1529#endif
1530          }
1531          else if(xmlStrcasecmp(cur2->name,BAD_CAST "Data")==0){
1532#ifdef DEBUG
1533            fprintf(stderr,"DATA\n");
1534#endif
1535            xmlNodePtr cur4=cur2->children;
1536            while(cur4!=NULL){
1537              while(cur4!=NULL &&cur4->type!=XML_ELEMENT_NODE)
1538                cur4=cur4->next;
1539              if(cur4==NULL)
1540                break;
1541              if(xmlStrcasecmp(cur4->name, BAD_CAST "LiteralData")==0){
1542                /**
1543                 * Get every attribute from a LiteralData node
1544                 * dataType , uom
1545                 */
1546                char *list[2];
1547                list[0]=strdup("dataType");
1548                list[1]=strdup("uom");
1549                for(int l=0;l<2;l++){
1550#ifdef DEBUG
1551                  fprintf(stderr,"*** LiteralData %s ***",list[l]);
1552#endif
1553                  xmlChar *val=xmlGetProp(cur4,BAD_CAST list[l]);
1554                  if(val!=NULL && strlen((char*)val)>0){
1555                    if(tmpmaps->content!=NULL)
1556                      addToMap(tmpmaps->content,list[l],(char*)val);
1557                    else
1558                      tmpmaps->content=createMap(list[l],(char*)val);
1559#ifdef DEBUG
1560                    fprintf(stderr,"%s\n",val);
1561#endif
1562                  }
1563                  xmlFree(val);
1564                  free(list[l]);                 
1565                }
1566              }
1567              else if(xmlStrcasecmp(cur4->name, BAD_CAST "ComplexData")==0){
1568                /**
1569                 * Get every attribute from a Reference node
1570                 * mimeType, encoding, schema
1571                 */
1572                const char *coms[3]={"mimeType","encoding","schema"};
1573                for(int l=0;l<3;l++){
1574#ifdef DEBUG
1575                  fprintf(stderr,"*** ComplexData %s ***\n",coms[l]);
1576#endif
1577                  xmlChar *val=xmlGetProp(cur4,BAD_CAST coms[l]);
1578                  if(val!=NULL && strlen((char*)val)>0){
1579                    if(tmpmaps->content!=NULL)
1580                      addToMap(tmpmaps->content,coms[l],(char*)val);
1581                    else
1582                      tmpmaps->content=createMap(coms[l],(char*)val);
1583#ifdef DEBUG
1584                    fprintf(stderr,"%s\n",val);
1585#endif
1586                  }
1587                  xmlFree(val);
1588                }
1589              }
1590
1591              map* test=getMap(tmpmaps->content,"encoding");
1592              if(test==NULL){
1593                if(tmpmaps->content!=NULL)
1594                  addToMap(tmpmaps->content,"encoding","utf-8");
1595                else
1596                  tmpmaps->content=createMap("encoding","utf-8");
1597                test=getMap(tmpmaps->content,"encoding");
1598              }
1599
1600              if(strcasecmp(test->value,"base64")!=0){
1601                xmlChar* mv=xmlNodeListGetString(doc,cur4->xmlChildrenNode,1);
1602                map* ltmp=getMap(tmpmaps->content,"mimeType");
1603                if(mv==NULL || 
1604                   (xmlStrcasecmp(cur4->name, BAD_CAST "ComplexData")==0 &&
1605                    (ltmp==NULL || strncasecmp(ltmp->value,"text/xml",8)==0) )){
1606                  xmlDocPtr doc1=xmlNewDoc(BAD_CAST "1.0");
1607                  int buffersize;
1608                  xmlNodePtr cur5=cur4->children;
1609                  while(cur5!=NULL &&cur5->type!=XML_ELEMENT_NODE)
1610                    cur5=cur5->next;
1611                  xmlDocSetRootElement(doc1,cur5);
1612                  xmlDocDumpFormatMemoryEnc(doc1, &mv, &buffersize, "utf-8", 1);
1613                  char size[1024];
1614                  sprintf(size,"%d",buffersize);
1615                  addToMap(tmpmaps->content,"size",size);
1616                }
1617                addToMap(tmpmaps->content,"value",(char*)mv);
1618                xmlFree(mv);
1619              }else{
1620                xmlChar* tmp=xmlNodeListGetRawString(doc,cur4->xmlChildrenNode,0);
1621                addToMap(tmpmaps->content,"value",(char*)tmp);
1622                map* tmpv=getMap(tmpmaps->content,"value");
1623                char *res=NULL;
1624                char *curs=tmpv->value;
1625                for(int i=0;i<=strlen(tmpv->value)/64;i++) {
1626                  if(res==NULL)
1627                    res=(char*)malloc(67*sizeof(char));
1628                  else
1629                    res=(char*)realloc(res,(((i+1)*65)+i)*sizeof(char));
1630                  int csize=i*65;
1631                  strncpy(res + csize,curs,64);
1632                  if(i==xmlStrlen(tmp)/64)
1633                    strcat(res,"\n\0");
1634                  else{
1635                    strncpy(res + (((i+1)*64)+i),"\n\0",2);
1636                    curs+=64;
1637                  }
1638                }
1639                free(tmpv->value);
1640                tmpv->value=strdup(res);
1641                free(res);
1642                xmlFree(tmp);
1643              }
1644              cur4=cur4->next;
1645            }
1646          }
1647#ifdef DEBUG
1648          fprintf(stderr,"cur2 next \n");
1649          fflush(stderr);
1650#endif
1651          cur2=cur2->next;
1652        }
1653#ifdef DEBUG
1654        fprintf(stderr,"ADD MAPS TO REQUEST MAPS !\n");
1655        fflush(stderr);
1656#endif
1657
1658        {
1659          maps* testPresence=getMaps(request_input_real_format,tmpmaps->name);
1660          if(testPresence!=NULL){
1661            elements* elem=getElements(s1->inputs,tmpmaps->name);
1662            if(elem!=NULL){
1663              if(appendMapsToMaps(m,request_input_real_format,tmpmaps,elem)<0){
1664                freeMaps(&m);
1665                free(m);
1666                free(REQUEST);
1667                free(SERVICE_URL);
1668                InternetCloseHandle(hInternet);
1669                freeService(&s1);
1670                free(s1);
1671                return 0;
1672              }
1673            }
1674          }
1675          else
1676            addMapsToMaps(&request_input_real_format,tmpmaps);
1677        }
1678       
1679#ifdef DEBUG
1680        fprintf(stderr,"******TMPMAPS*****\n");
1681        dumpMaps(tmpmaps);
1682        fprintf(stderr,"******REQUESTMAPS*****\n");
1683        dumpMaps(request_input_real_format);
1684#endif
1685        freeMaps(&tmpmaps);
1686        free(tmpmaps);
1687        tmpmaps=NULL;         
1688      }
1689#ifdef DEBUG
1690      dumpMaps(tmpmaps); 
1691#endif
1692    }
1693#ifdef DEBUG
1694    fprintf(stderr,"Search for response document node\n");
1695#endif
1696    xmlXPathFreeObject(tmpsptr);
1697   
1698    tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='ResponseDocument']");
1699    bool asRaw=false;
1700    tmps=tmpsptr->nodesetval;
1701    if(tmps->nodeNr==0){
1702      tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='RawDataOutput']");
1703      tmps=tmpsptr->nodesetval;
1704      asRaw=true;
1705    }
1706#ifdef DEBUG
1707    fprintf(stderr,"*****%d*****\n",tmps->nodeNr);
1708#endif
1709    for(int k=0;k<tmps->nodeNr;k++){
1710      if(asRaw==true)
1711        addToMap(request_inputs,"RawDataOutput","");
1712      else
1713        addToMap(request_inputs,"ResponseDocument","");
1714      maps *tmpmaps=NULL;
1715      xmlNodePtr cur=tmps->nodeTab[k];
1716      if(cur->type == XML_ELEMENT_NODE) {
1717        /**
1718         * A specific responseDocument node.
1719         */
1720        if(tmpmaps==NULL){
1721          tmpmaps=(maps*)malloc(MAPS_SIZE);
1722          if(tmpmaps == NULL){
1723            return errorException(m, _("Unable to allocate memory."), "InternalError");
1724          }
1725          tmpmaps->name=strdup("unknownIdentifier");
1726          tmpmaps->content=NULL;
1727          tmpmaps->next=NULL;
1728        }
1729        /**
1730         * Get every attribute: storeExecuteResponse, lineage, status
1731         */
1732        const char *ress[3]={"storeExecuteResponse","lineage","status"};
1733        xmlChar *val;
1734        for(int l=0;l<3;l++){
1735#ifdef DEBUG
1736          fprintf(stderr,"*** %s ***\t",ress[l]);
1737#endif
1738          val=xmlGetProp(cur,BAD_CAST ress[l]);
1739          if(val!=NULL && strlen((char*)val)>0){
1740            if(tmpmaps->content!=NULL)
1741              addToMap(tmpmaps->content,ress[l],(char*)val);
1742            else
1743              tmpmaps->content=createMap(ress[l],(char*)val);
1744            addToMap(request_inputs,ress[l],(char*)val);
1745          }
1746#ifdef DEBUG
1747          fprintf(stderr,"%s\n",val);
1748#endif
1749          xmlFree(val);
1750        }
1751        xmlNodePtr cur1=cur->children;
1752        while(cur1!=NULL && cur1->type != XML_ELEMENT_NODE)
1753          cur1=cur1->next;
1754        while(cur1){
1755          /**
1756           * Indentifier
1757           */
1758          if(xmlStrncasecmp(cur1->name,BAD_CAST "Identifier",xmlStrlen(cur1->name))==0){
1759            xmlChar *val=
1760              xmlNodeListGetString(doc,cur1->xmlChildrenNode,1);
1761            if(tmpmaps==NULL){
1762              tmpmaps=(maps*)malloc(MAPS_SIZE);
1763              if(tmpmaps == NULL){
1764                return errorException(m, _("Unable to allocate memory."), "InternalError");
1765              }
1766              tmpmaps->name=strdup((char*)val);
1767              tmpmaps->content=NULL;
1768              tmpmaps->next=NULL;
1769            }
1770            else{
1771              //free(tmpmaps->name);
1772              tmpmaps->name=strdup((char*)val);
1773            }
1774            xmlFree(val);
1775          }
1776          /**
1777           * Title, Asbtract
1778           */
1779          else if(xmlStrncasecmp(cur1->name,BAD_CAST "Title",xmlStrlen(cur1->name))==0 ||
1780                  xmlStrncasecmp(cur1->name,BAD_CAST "Abstract",xmlStrlen(cur1->name))==0){
1781            xmlChar *val=
1782              xmlNodeListGetString(doc,cur1->xmlChildrenNode,1);
1783            if(tmpmaps==NULL){
1784              tmpmaps=(maps*)malloc(MAPS_SIZE);
1785              if(tmpmaps == NULL){
1786                return errorException(m, _("Unable to allocate memory."), "InternalError");
1787              }
1788              tmpmaps->name=strdup("missingIndetifier");
1789              tmpmaps->content=createMap((char*)cur1->name,(char*)val);
1790              tmpmaps->next=NULL;
1791            }
1792            else{
1793              if(tmpmaps->content!=NULL)
1794                addToMap(tmpmaps->content,(char*)cur1->name,(char*)val);
1795              else
1796                tmpmaps->content=createMap((char*)cur1->name,(char*)val);
1797            }
1798            xmlFree(val);
1799          }
1800          else if(xmlStrncasecmp(cur1->name,BAD_CAST "Output",xmlStrlen(cur1->name))==0){
1801            /**
1802             * Get every attribute from a Output node
1803             * mimeType, encoding, schema, uom, asReference
1804             */
1805            const char *outs[5]={"mimeType","encoding","schema","uom","asReference"};
1806            for(int l=0;l<5;l++){
1807#ifdef DEBUG
1808              fprintf(stderr,"*** %s ***\t",outs[l]);
1809#endif
1810              val=xmlGetProp(cur1,BAD_CAST outs[l]);
1811              if(val!=NULL && strlen((char*)val)>0){
1812                if(tmpmaps->content!=NULL)
1813                  addToMap(tmpmaps->content,outs[l],(char*)val);
1814                else
1815                  tmpmaps->content=createMap(outs[l],(char*)val);
1816              }
1817#ifdef DEBUG
1818              fprintf(stderr,"%s\n",val);
1819#endif
1820              xmlFree(val);
1821            }
1822            xmlNodePtr cur2=cur1->children;
1823            while(cur2!=NULL && cur2->type != XML_ELEMENT_NODE)
1824              cur2=cur2->next;
1825            while(cur2){
1826              /**
1827               * Indentifier
1828               */
1829              if(xmlStrncasecmp(cur2->name,BAD_CAST "Identifier",xmlStrlen(cur2->name))==0){
1830                xmlChar *val=
1831                  xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1832                if(tmpmaps==NULL){
1833                  tmpmaps=(maps*)malloc(MAPS_SIZE);
1834                  if(tmpmaps == NULL){
1835                    return errorException(m, _("Unable to allocate memory."), "InternalError");
1836                  }
1837                  tmpmaps->name=strdup((char*)val);
1838                  tmpmaps->content=NULL;
1839                  tmpmaps->next=NULL;
1840                }
1841                else{
1842                  if(tmpmaps->name!=NULL)
1843                    free(tmpmaps->name);
1844                  tmpmaps->name=strdup((char*)val);;
1845                }
1846                xmlFree(val);
1847              }
1848              /**
1849               * Title, Asbtract
1850               */
1851              else if(xmlStrncasecmp(cur2->name,BAD_CAST "Title",xmlStrlen(cur2->name))==0 ||
1852                      xmlStrncasecmp(cur2->name,BAD_CAST "Abstract",xmlStrlen(cur2->name))==0){
1853                xmlChar *val=
1854                  xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1855                if(tmpmaps==NULL){
1856                  tmpmaps=(maps*)malloc(MAPS_SIZE);
1857                  if(tmpmaps == NULL){
1858                    return errorException(m, _("Unable to allocate memory."), "InternalError");
1859                  }
1860                  tmpmaps->name=strdup("missingIndetifier");
1861                  tmpmaps->content=createMap((char*)cur2->name,(char*)val);
1862                  tmpmaps->next=NULL;
1863                }
1864                else{
1865                  if(tmpmaps->content!=NULL)
1866                    addToMap(tmpmaps->content,
1867                             (char*)cur2->name,(char*)val);
1868                  else
1869                    tmpmaps->content=
1870                      createMap((char*)cur2->name,(char*)val);
1871                }
1872                xmlFree(val);
1873              }
1874              if(request_output_real_format==NULL)
1875                request_output_real_format=dupMaps(&tmpmaps);
1876              else
1877                addMapsToMaps(&request_output_real_format,tmpmaps);
1878              cur2=cur2->next;
1879              while(cur2!=NULL && cur2->type != XML_ELEMENT_NODE)
1880                cur2=cur2->next;
1881            }
1882          }
1883          cur1=cur1->next;
1884          while(cur1!=NULL && cur1->type != XML_ELEMENT_NODE)
1885            cur1=cur1->next;
1886        }
1887      }
1888      if(tmpmaps!=NULL){
1889        freeMaps(&tmpmaps);
1890        free(tmpmaps);
1891        tmpmaps=NULL;
1892      }
1893    }
1894    xmlXPathFreeObject(tmpsptr);
1895    xmlCleanupParser();
1896  }
1897 
1898  //if(CHECK_INET_HANDLE(hInternet))
1899  InternetCloseHandle(hInternet);
1900
1901#ifdef DEBUG
1902  fprintf(stderr,"\n%d\n",__LINE__);
1903  fflush(stderr);
1904  dumpMaps(request_input_real_format);
1905  dumpMaps(request_output_real_format);
1906  dumpMap(request_inputs);
1907  fprintf(stderr,"\n%d\n",__LINE__);
1908  fflush(stderr);
1909#endif
1910
1911  /**
1912   * Ensure that each requested arguments are present in the request
1913   * DataInputs and ResponseDocument / RawDataOutput
1914   */
1915  char *dfv=addDefaultValues(&request_input_real_format,s1->inputs,m,0);
1916  char *dfv1=addDefaultValues(&request_output_real_format,s1->outputs,m,1);
1917  if(strcmp(dfv1,"")!=0 || strcmp(dfv,"")!=0){
1918    char tmps[1024];
1919    if(strcmp(dfv,"")!=0){
1920      snprintf(tmps,1024,_("The <%s> argument was not specified in DataInputs but defined as requested in ZOO ServicesProvider configuration file, please correct your query or the ZOO Configuration file."),dfv);
1921    }
1922    else if(strcmp(dfv1,"")!=0){
1923      snprintf(tmps,1024,_("The <%s> argument was specified as Output identifier but not defined in the ZOO Configuration File. Please, correct your query or the ZOO Configuration File."),dfv1);
1924    }
1925    map* tmpe=createMap("text",tmps);
1926    addToMap(tmpe,"code","MissingParameterValue");
1927    printExceptionReportResponse(m,tmpe);
1928    freeService(&s1);
1929    free(s1);
1930    freeMap(&tmpe);
1931    free(tmpe);
1932    freeMaps(&m);
1933    free(m);
1934    free(REQUEST);
1935    free(SERVICE_URL);
1936    freeMaps(&request_input_real_format);
1937    free(request_input_real_format);
1938    freeMaps(&request_output_real_format);
1939    free(request_output_real_format);
1940    freeMaps(&tmpmaps);
1941    free(tmpmaps);
1942    return 1;
1943  }
1944  maps* tmpReqI=request_input_real_format;
1945  while(tmpReqI!=NULL){
1946    char name[1024];
1947    if(getMap(tmpReqI->content,"isFile")!=NULL){
1948      if (cgiFormFileName(tmpReqI->name, name, sizeof(name)) == cgiFormSuccess) {
1949        int BufferLen=1024;
1950        cgiFilePtr file;
1951        int targetFile;
1952        mode_t mode;
1953        char storageNameOnServer[2048];
1954        char fileNameOnServer[64];
1955        char contentType[1024];
1956        char buffer[1024];
1957        char *tmpStr=NULL;
1958        int size;
1959        int got,t;
1960        map *path=getMapFromMaps(m,"main","tmpPath");
1961        cgiFormFileSize(tmpReqI->name, &size);
1962        cgiFormFileContentType(tmpReqI->name, contentType, sizeof(contentType));
1963        if (cgiFormFileOpen(tmpReqI->name, &file) == cgiFormSuccess) {
1964          t=-1;
1965          while(1){
1966            tmpStr=strstr(name+t+1,"\\");
1967            if(NULL==tmpStr)
1968              tmpStr=strstr(name+t+1,"/");
1969            if(NULL!=tmpStr)
1970              t=(int)(tmpStr-name);
1971            else
1972              break;
1973          }
1974          strcpy(fileNameOnServer,name+t+1);
1975         
1976          sprintf(storageNameOnServer,"%s/%s",path->value,fileNameOnServer);
1977          printf("\n\nName on server %s\n",storageNameOnServer);
1978#ifdef DEBUG
1979          fprintf(stderr,"Name on server %s\n",storageNameOnServer);
1980          fprintf(stderr,"fileNameOnServer: %s\n",fileNameOnServer);
1981#endif
1982          mode=S_IRWXU|S_IRGRP|S_IROTH;
1983          targetFile = open (storageNameOnServer,O_RDWR|O_CREAT|O_TRUNC,S_IRWXU|S_IRGRP|S_IROTH);
1984          if(targetFile<0){
1985#ifdef DEBUG
1986            fprintf(stderr,"could not create the new file,%s\n",fileNameOnServer);         
1987#endif
1988          }else{
1989            while (cgiFormFileRead(file, buffer, BufferLen, &got) ==cgiFormSuccess){
1990              if(got>0)
1991                write(targetFile,buffer,got);
1992            }
1993          }
1994          addToMap(tmpReqI->content,"lref",storageNameOnServer);
1995          cgiFormFileClose(file);
1996          close(targetFile);
1997#ifdef DEBUG
1998          fprintf(stderr,"File \"%s\" has been uploaded",fileNameOnServer);
1999#endif
2000        }
2001      }
2002    }
2003    tmpReqI=tmpReqI->next;
2004  }
2005
2006  ensureDecodedBase64(&request_input_real_format);
2007
2008#ifdef DEBUG
2009  fprintf(stderr,"REQUEST_INPUTS\n");
2010  dumpMaps(request_input_real_format);
2011  fprintf(stderr,"REQUEST_OUTPUTS\n");
2012  dumpMaps(request_output_real_format);
2013#endif
2014
2015  maps* curs=getMaps(m,"env");
2016  if(curs!=NULL){
2017    map* mapcs=curs->content;
2018    while(mapcs!=NULLMAP){
2019#ifndef WIN32
2020      setenv(mapcs->name,mapcs->value,1);
2021#else
2022#ifdef DEBUG
2023      fprintf(stderr,"[ZOO: setenv (%s=%s)]\n",mapcs->name,mapcs->value);
2024#endif
2025      if(mapcs->value[strlen(mapcs->value)-2]=='\r'){
2026#ifdef DEBUG
2027        fprintf(stderr,"[ZOO: Env var finish with \r]\n");
2028#endif
2029        mapcs->value[strlen(mapcs->value)-1]=0;
2030      }
2031#ifdef DEBUG
2032      fflush(stderr);
2033      fprintf(stderr,"setting variable... %s\n",(
2034#endif
2035              SetEnvironmentVariable(mapcs->name,mapcs->value)
2036#ifdef DEBUG
2037              ==0)? "OK" : "FAILED");
2038#else
2039      ;
2040#endif
2041          char* toto=(char*)malloc((strlen(mapcs->name)+strlen(mapcs->value)+2)*sizeof(char));
2042      sprintf(toto,"%s=%s",mapcs->name,mapcs->value);
2043          putenv(toto);
2044#ifdef DEBUG
2045      fflush(stderr);
2046#endif
2047#endif
2048#ifdef DEBUG
2049      fprintf(stderr,"[ZOO: setenv (%s=%s)]\n",mapcs->name,mapcs->value);
2050      fflush(stderr);
2051#endif
2052      mapcs=mapcs->next;
2053    }
2054  }
2055 
2056#ifdef DEBUG
2057  dumpMap(request_inputs);
2058#endif
2059
2060  /**
2061   * Need to check if we need to fork to load a status enabled
2062   */
2063  r_inputs=NULL;
2064  map* store=getMap(request_inputs,"storeExecuteResponse");
2065  map* status=getMap(request_inputs,"status");
2066  /**
2067   * 05-007r7 WPS 1.0.0 page 57 :
2068   * 'If status="true" and storeExecuteResponse is "false" then the service
2069   * shall raise an exception.'
2070   */
2071  if(status!=NULL && strcmp(status->value,"true")==0 && 
2072     store!=NULL && strcmp(store->value,"false")==0){
2073    errorException(m, _("Status cannot be set to true with storeExecuteResponse to false. Please, modify your request parameters."), "InvalidParameterValue");
2074    freeService(&s1);
2075    free(s1);
2076    freeMaps(&m);
2077    free(m);
2078   
2079    freeMaps(&request_input_real_format);
2080    free(request_input_real_format);
2081   
2082    freeMaps(&request_output_real_format);
2083    free(request_output_real_format);
2084   
2085    free(REQUEST);
2086    free(SERVICE_URL);
2087    return 1;
2088  }
2089  r_inputs=getMap(request_inputs,"storeExecuteResponse");
2090  int eres=SERVICE_STARTED;
2091  int cpid=getpid();
2092
2093  maps *_tmpMaps=(maps*)malloc(MAPS_SIZE);
2094  _tmpMaps->name=strdup("lenv");
2095  char tmpBuff[100];
2096  sprintf(tmpBuff,"%i",cpid);
2097  _tmpMaps->content=createMap("sid",tmpBuff);
2098  _tmpMaps->next=NULL;
2099  addToMap(_tmpMaps->content,"status","0");
2100  addToMap(_tmpMaps->content,"cwd",ntmp);
2101  map* ltmp=getMap(request_inputs,"soap");
2102  if(ltmp!=NULL)
2103    addToMap(_tmpMaps->content,"soap",ltmp->value);
2104  else
2105    addToMap(_tmpMaps->content,"soap","false");
2106  if(cgiCookie!=NULL && strlen(cgiCookie)>0){
2107    char *tcook=strdup(cgiCookie);
2108    if(strstr(cgiCookie,";")>0){
2109      char *token,*saveptr;
2110      token=strtok_r(cgiCookie,";",&saveptr);
2111      while(token!=NULL){
2112        if(strcasestr(token,"ID")!=NULL){
2113          if(tcook!=NULL)
2114            free(tcook);
2115          tcook=strdup(token);
2116        }
2117        token=strtok_r(NULL,";",&saveptr);
2118      }
2119    }
2120    addToMap(_tmpMaps->content,"sessid",strstr(tcook,"=")+1);
2121    char session_file_path[1024];
2122    map *tmpPath=getMapFromMaps(m,"main","sessPath");
2123    if(tmpPath==NULL)
2124      tmpPath=getMapFromMaps(m,"main","tmpPath");
2125    char *tmp1=strtok(tcook,";");
2126    if(tmp1!=NULL)
2127      sprintf(session_file_path,"%s/sess_%s.cfg",tmpPath->value,strstr(tmp1,"=")+1);
2128    else
2129      sprintf(session_file_path,"%s/sess_%s.cfg",tmpPath->value,strstr(cgiCookie,"=")+1);
2130    free(tcook);
2131    maps *tmpSess=(maps*)malloc(MAPS_SIZE);
2132    struct stat file_status;
2133    int istat = stat(session_file_path, &file_status);
2134    if(istat==0 && file_status.st_size>0){
2135      conf_read(session_file_path,tmpSess);
2136      addMapsToMaps(&m,tmpSess);
2137      freeMaps(&tmpSess);
2138    }else{
2139      errorException(m, _("Unable to read your session file."), "InternalError");
2140      freeMaps(&tmpSess);
2141      freeService(&s1);
2142      free(s1);
2143      freeMaps(&m);
2144      free(m);
2145      freeMaps(&request_input_real_format);
2146      free(request_input_real_format);
2147      freeMaps(&request_output_real_format);
2148      free(request_output_real_format);
2149      free(REQUEST);
2150      free(SERVICE_URL);
2151      return 1;
2152    }
2153    free(tmpSess);
2154  }
2155  addMapsToMaps(&m,_tmpMaps);
2156  freeMaps(&_tmpMaps);
2157  free(_tmpMaps);
2158
2159#ifdef DEBUG
2160  dumpMap(request_inputs);
2161#endif
2162#ifdef WIN32
2163  char *cgiSidL=NULL;
2164  if(getenv("CGISID")!=NULL)
2165    addToMap(request_inputs,"cgiSid",getenv("CGISID"));
2166  map* test1=getMap(request_inputs,"cgiSid");
2167  if(test1!=NULL){
2168    cgiSid=test1->value;
2169    addToMap(request_inputs,"storeExecuteResponse","true");
2170    addToMap(request_inputs,"status","true");
2171    setMapInMaps(m,"lenv","sid",test1->value);
2172    status=getMap(request_inputs,"status");
2173    printf("cgiSid %s\n",cgiSid);
2174  }
2175#endif
2176  int hrstd=-1;
2177  char *fbkp,*fbkp1;
2178  FILE *f0,*f1;
2179  if(status!=NULL)
2180    if(strcasecmp(status->value,"false")==0)
2181      status=NULLMAP;
2182  if(status==NULLMAP){
2183    loadServiceAndRun(&m,s1,request_inputs,&request_input_real_format,&request_output_real_format,&eres);
2184  }
2185  else{
2186    int   pid;
2187#ifdef DEBUG
2188    fprintf(stderr,"\nPID : %d\n",cpid);
2189#endif
2190
2191#ifndef WIN32
2192    pid = fork ();
2193#else
2194    if(cgiSid==NULL){
2195      createProcess(m,request_inputs,s1,NULL,cpid,request_input_real_format,request_output_real_format);
2196      pid = cpid;
2197    }else{
2198      pid=0;
2199      cpid=atoi(cgiSid);
2200      printf("cgiSid %s\n",cgiSid);
2201    }
2202    //printf("pid cpid %d %d\n",pid,cpid);
2203    //fflush(stderr);
2204#endif
2205    if (pid > 0) {
2206      /**
2207       * dady :
2208       * set status to SERVICE_ACCEPTED
2209       */
2210#ifdef DEBUG
2211      fprintf(stderr,"father pid continue (origin %d) %d ...\n",cpid,getpid());
2212#endif
2213      eres=SERVICE_ACCEPTED;
2214    }else if (pid == 0) {
2215      /**
2216       * son : have to close the stdout, stdin and stderr to let the parent
2217       * process answer to http client.
2218       */
2219      r_inputs=getMapFromMaps(m,"main","tmpPath");
2220      map* r_inputs1=getMap(s1->content,"ServiceProvider");
2221      fbkp=(char*)malloc((strlen(r_inputs->value)+strlen(r_inputs1->value)+1024)*sizeof(char));
2222      sprintf(fbkp,"%s/%s_%d.xml",r_inputs->value,r_inputs1->value,cpid);
2223      char* flog=(char*)malloc((strlen(r_inputs->value)+strlen(r_inputs1->value)+1024)*sizeof(char));
2224      sprintf(flog,"%s/%s_%d_error.log",r_inputs->value,r_inputs1->value,cpid);
2225#ifdef DEBUG
2226      fprintf(stderr,"RUN IN BACKGROUND MODE \n");
2227      fprintf(stderr,"son pid continue (origin %d) %d ...\n",cpid,getpid());
2228      fprintf(stderr,"\nFILE TO STORE DATA %s\n",r_inputs->value);
2229#endif
2230      freopen(flog,"w+",stderr);
2231      f0=freopen(fbkp , "w+", stdout);
2232      fclose(stdin);
2233      free(flog);
2234      /**
2235       * set status to SERVICE_STARTED and flush stdout to ensure full
2236       * content was outputed (the file used to store the ResponseDocument).
2237       * The rewind stdout to restart writing from the bgining of the file,
2238       * this way the data will be updated at the end of the process run.
2239       */
2240      printProcessResponse(m,request_inputs,cpid,
2241                           s1,r_inputs1->value,SERVICE_STARTED,
2242                           request_input_real_format,
2243                           request_output_real_format);
2244#ifndef WIN32
2245      fflush(stdout);
2246      rewind(stdout);
2247#else
2248#endif
2249      fbkp1=(char*)malloc((strlen(r_inputs->value)+strlen(r_inputs1->value)+1024)*sizeof(char));
2250      sprintf(fbkp1,"%s/%s_final_%d.xml",r_inputs->value,r_inputs1->value,cpid);
2251      f1=freopen(fbkp1 , "w+", stdout);
2252      loadServiceAndRun(&m,s1,request_inputs,&request_input_real_format,&request_output_real_format,&eres);
2253    } else {
2254      /**
2255       * error server don't accept the process need to output a valid
2256       * error response here !!!
2257       */
2258      eres=-1;
2259      errorException(m, _("Unable to run the child process properly"), "InternalError");
2260    }
2261  }
2262
2263#ifdef DEBUG
2264  dumpMaps(request_output_real_format);
2265#endif
2266  if(eres!=-1)
2267    outputResponse(s1,request_input_real_format,
2268                   request_output_real_format,request_inputs,
2269                   cpid,m,eres);
2270  fflush(stdout);
2271  /**
2272   * Ensure that if error occurs when freeing memory, no signal will return
2273   * an ExceptionReport document as the result was already returned to the
2274   * client.
2275   */
2276#ifndef USE_GDB
2277  (void) signal(SIGSEGV,donothing);
2278  (void) signal(SIGTERM,donothing);
2279  (void) signal(SIGINT,donothing);
2280  (void) signal(SIGILL,donothing);
2281  (void) signal(SIGFPE,donothing);
2282  (void) signal(SIGABRT,donothing);
2283#endif
2284
2285  if(((int)getpid())!=cpid){
2286    fclose(stdout);
2287    fclose(stderr);
2288    unhandleStatus(m);
2289    /**
2290     * Dump back the final file fbkp1 to fbkp
2291     */
2292    fclose(f0);
2293    fclose(f1);
2294    FILE* f2=fopen(fbkp1,"rb");
2295    FILE* f3=fopen(fbkp,"wb+");
2296    free(fbkp);
2297    free(fbkp1);
2298    fseek(f2,0,SEEK_END);
2299    long flen=ftell(f2);
2300    fseek(f2,0,SEEK_SET);
2301    char *tmps1=(char*)malloc((flen+1)*sizeof(char));
2302    fread(tmps1,flen,1,f2);
2303    fwrite(tmps1,1,flen,f3);
2304    fclose(f2);
2305    fclose(f3);
2306  }
2307
2308  freeService(&s1);
2309  free(s1);
2310  freeMaps(&m);
2311  free(m);
2312 
2313  freeMaps(&request_input_real_format);
2314  free(request_input_real_format);
2315 
2316  freeMaps(&request_output_real_format);
2317  free(request_output_real_format);
2318 
2319  free(REQUEST);
2320  free(SERVICE_URL);
2321#ifdef DEBUG
2322  fprintf(stderr,"Processed response \n");
2323  fflush(stdout);
2324  fflush(stderr);
2325#endif
2326
2327  return 0;
2328}
2329
Note: See TracBrowser for help on using the repository browser.

Search

ZOO Sponsors

http://www.zoo-project.org/trac/chrome/site/img/geolabs-logo.pnghttp://www.zoo-project.org/trac/chrome/site/img/neogeo-logo.png http://www.zoo-project.org/trac/chrome/site/img/apptech-logo.png http://www.zoo-project.org/trac/chrome/site/img/3liz-logo.png http://www.zoo-project.org/trac/chrome/site/img/gateway-logo.png

Become a sponsor !

Knowledge partners

http://www.zoo-project.org/trac/chrome/site/img/ocu-logo.png http://www.zoo-project.org/trac/chrome/site/img/gucas-logo.png http://www.zoo-project.org/trac/chrome/site/img/polimi-logo.png http://www.zoo-project.org/trac/chrome/site/img/fem-logo.png http://www.zoo-project.org/trac/chrome/site/img/supsi-logo.png http://www.zoo-project.org/trac/chrome/site/img/cumtb-logo.png

Become a knowledge partner

Related links

http://zoo-project.org/img/ogclogo.png http://zoo-project.org/img/osgeologo.png