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

Last change on this file since 458 was 458, checked in by djay, 6 years ago

Fix some issue in background execution on windows platform (basic array and xlink). Fix issue #89.

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