source: trunk/zoo-kernel/zoo_service_loader.c @ 88

Last change on this file since 88 was 88, checked in by djay, 13 years ago

Special thanks to Soeren Gebbert for his proposals. Add the inRequest key to the inputs/outputs maps for specifying if an input/output was present in the request or not (required to remove the PyXB dependency from GRASS Support). Add the automatic base64 decoding for input provided as base64 encoded string, in this case a size key will be added (containing the size of the decoded string which is probably a binary file), base64_value will be added to store the original base64 string for possible acces from service function, value will finally contain the decoded string (this was required for supporting requests coming from the QGIS WPS Client).

File size: 49.8 KB
Line 
1/**
2 * Author : Gérald FENOY
3 *
4 *  Copyright 2008-2011 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
30extern "C" {
31#include <libxml/tree.h>
32#include <libxml/xmlmemory.h>
33#include <libxml/parser.h>
34#include <libxml/xpath.h>
35#include <libxml/xpathInternals.h>
36}
37
38#include "cgic.h"
39#include "ulinet.h"
40
41#include <libintl.h>
42#include <locale.h>
43#include <string.h>
44
45#include "service.h"
46
47#include "service_internal.h"
48
49#ifdef USE_PYTHON
50#include "service_internal_python.h"
51#endif
52
53#ifdef USE_JAVA
54#include "service_internal_java.h"
55#endif
56
57#ifdef USE_PHP
58#include "service_internal_php.h"
59#endif
60
61#ifdef USE_JS
62#include "service_internal_js.h"
63#endif
64
65#ifdef USE_PERL
66#include "service_internal_perl.h"
67#endif
68
69
70
71#include <dirent.h>
72#include <signal.h>
73#include <unistd.h>
74#ifndef WIN32
75#include <dlfcn.h>
76#include <libgen.h>
77#else
78#include <windows.h>
79#include <direct.h>
80#endif
81#include <fcntl.h>
82#include <time.h>
83#include <stdarg.h>
84
85#define _(String) dgettext ("zoo-kernel",String)
86
87
88void *translateChar(char* str,char toReplace,char toReplaceBy){
89  int i=0,len=strlen(str);
90  for(i=0;i<len;i++){
91    if(str[i]==toReplace)
92      str[i]=toReplaceBy;
93  }
94}
95
96xmlXPathObjectPtr extractFromDoc(xmlDocPtr doc,char* search){
97  xmlXPathContextPtr xpathCtx;
98  xmlXPathObjectPtr xpathObj;
99  xpathCtx = xmlXPathNewContext(doc);
100  xpathObj = xmlXPathEvalExpression(BAD_CAST search,xpathCtx);
101  xmlXPathFreeContext(xpathCtx);
102  return xpathObj;
103}
104
105void sig_handler(int sig){
106  char tmp[100];
107  char *ssig;
108  switch(sig){
109  case SIGSEGV:
110    ssig="SIGSEGV";
111    break;
112  case SIGTERM:
113    ssig="SIGTERM";
114    break;
115  case SIGINT:
116    ssig="SIGINT";
117    break;
118  case SIGILL:
119    ssig="SIGILL";
120    break;
121  case SIGFPE:
122    ssig="SIGFPE";
123    break;
124  case SIGABRT:
125    ssig="SIGABRT";
126    break;
127  default:
128    ssig="UNKNOWN";
129    break;
130  }
131  sprintf(tmp,_("ZOO Kernel failed to process your request receiving signal %d = %s"),sig,ssig);
132  errorException(NULL, tmp, "InternalError");
133#ifdef DEBUG
134  fprintf(stderr,"Not this time!\n");
135#endif
136  exit(0);
137}
138
139void *loadServiceAndRun(maps **myMap,service* s1,map* request_inputs,maps **inputs,maps** ioutputs,int* eres){
140  char tmps1[1024];
141  char ntmp[1024];
142  maps *m=*myMap;
143  maps *request_output_real_format=*ioutputs;
144  maps *request_input_real_format=*inputs;
145  /**
146   * Extract serviceType to know what kind of service should be loaded
147   */
148  map* r_inputs=NULL;
149#ifndef WIN32
150  getcwd(ntmp,1024);
151#else
152  _getcwd(ntmp,1024);
153#endif
154  r_inputs=getMap(s1->content,"serviceType");
155#ifdef DEBUG
156  fprintf(stderr,"LOAD A %s SERVICE PROVIDER \n",r_inputs->value);
157  fflush(stderr);
158#endif
159  if(strncasecmp(r_inputs->value,"C",1)==0){
160    r_inputs=getMap(request_inputs,"metapath");
161    if(r_inputs!=NULL)
162      sprintf(tmps1,"%s/%s",ntmp,r_inputs->value);
163    else
164      sprintf(tmps1,"%s/",ntmp);
165    char *altPath=strdup(tmps1);
166    r_inputs=getMap(s1->content,"ServiceProvider");
167    sprintf(tmps1,"%s/%s",altPath,r_inputs->value);
168    free(altPath);
169#ifdef DEBUG
170    fprintf(stderr,"Trying to load %s\n",tmps1);
171#endif
172#ifdef WIN32
173    HINSTANCE so = LoadLibraryEx(tmps1,NULL,LOAD_WITH_ALTERED_SEARCH_PATH);
174#else
175    void* so = dlopen(tmps1, RTLD_LAZY);
176#endif
177#ifdef DEBUG
178#ifdef WIN32
179    DWORD errstr;
180    errstr = GetLastError();
181    fprintf(stderr,"%s loaded (%d) \n",tmps1,errstr);
182#else
183    char *errstr;
184    errstr = dlerror();
185#endif
186#endif
187
188    if( so != NULL ) {
189#ifdef DEBUG
190      fprintf(stderr,"Library loaded %s \n",errstr);
191      fprintf(stderr,"Service Shared Object = %s\n",r_inputs->value);
192#endif
193      r_inputs=getMap(s1->content,"serviceType");
194#ifdef DEBUG
195      dumpMap(r_inputs);
196      fprintf(stderr,"%s\n",r_inputs->value);
197      fflush(stderr);
198#endif
199      if(strncasecmp(r_inputs->value,"C-FORTRAN",9)==0){
200#ifdef WIN32
201        //Strange return value needed here !
202        return 1;
203#endif
204        r_inputs=getMap(request_inputs,"Identifier");
205        char fname[1024];
206        sprintf(fname,"%s_",r_inputs->value);
207#ifdef DEBUG
208        fprintf(stderr,"Try to load function %s\n",fname);
209#endif
210#ifdef WIN32
211        typedef int (CALLBACK* execute_t)(char***,char***,char***);
212        execute_t execute=(execute_t)GetProcAddress(so,fname);
213#else
214        typedef int (*execute_t)(char***,char***,char***);
215        execute_t execute=(execute_t)dlsym(so,fname);
216#endif
217#ifdef DEBUG
218#ifdef WIN32
219        errstr = GetLastError();
220#else
221        errstr = dlerror();
222#endif
223        fprintf(stderr,"Function loaded %s\n",errstr);
224#endif 
225
226        char main_conf[10][30][1024];
227        char inputs[10][30][1024];
228        char outputs[10][30][1024];
229        for(int i=0;i<10;i++){
230          for(int j=0;j<30;j++){
231            memset(main_conf[i][j],0,1024);
232            memset(inputs[i][j],0,1024);
233            memset(outputs[i][j],0,1024);
234          }
235        }
236        mapsToCharXXX(m,(char***)main_conf);
237        mapsToCharXXX(request_input_real_format,(char***)inputs);
238        mapsToCharXXX(request_output_real_format,(char***)outputs);
239        *eres=execute((char***)&main_conf[0],(char***)&inputs[0],(char***)&outputs[0]);
240#ifdef DEBUG
241        fprintf(stderr,"Function run successfully \n");
242#endif
243        charxxxToMaps((char***)&outputs[0],&request_output_real_format);
244      }else{
245#ifdef DEBUG
246#ifdef WIN32
247        errstr = GetLastError();
248        fprintf(stderr,"Function %s failed to load because of %d\n",r_inputs->value,errstr);
249#endif
250#endif
251        r_inputs=getMap(request_inputs,"Identifier");
252#ifdef DEBUG
253        fprintf(stderr,"Try to load function %s\n",r_inputs->value);
254#endif
255        typedef int (*execute_t)(maps**,maps**,maps**);
256#ifdef WIN32
257        execute_t execute=(execute_t)GetProcAddress(so,r_inputs->value); 
258#else
259        execute_t execute=(execute_t)dlsym(so,r_inputs->value);
260#endif
261
262#ifdef DEBUG
263#ifdef WIN32
264        errstr = GetLastError();
265#else
266        errstr = dlerror();
267#endif
268        fprintf(stderr,"Function loaded %s\n",errstr);
269#endif 
270
271#ifdef DEBUG
272        fprintf(stderr,"Now run the function \n");
273        fflush(stderr);
274#endif
275        *eres=execute(&m,&request_input_real_format,&request_output_real_format);
276#ifdef DEBUG
277        fprintf(stderr,"Function loaded and returned %d\n",eres);
278        fflush(stderr);
279#endif
280      }
281      dlclose(so);
282    } else {
283      /**
284       * Unable to load the specified shared library
285       */
286      char tmps[1024];
287#ifdef WIN32
288      DWORD errstr = GetLastError();
289#else
290      char* errstr = dlerror();
291#endif
292      sprintf(tmps,_("C Library can't be loaded %s \n"),errstr);
293      map* tmps1=createMap("text",tmps);
294      printExceptionReportResponse(m,tmps1);
295      *eres=-1;
296    }
297  }
298  else
299#ifdef USE_PYTHON
300    if(strncasecmp(r_inputs->value,"PYTHON",6)==0){
301      *eres=zoo_python_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
302    }
303    else
304#endif
305       
306#ifdef USE_JAVA
307      if(strncasecmp(r_inputs->value,"JAVA",4)==0){
308        *eres=zoo_java_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
309      }
310      else
311#endif
312
313#ifdef USE_PHP
314        if(strncasecmp(r_inputs->value,"PHP",3)==0){
315          *eres=zoo_php_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
316        }
317        else
318#endif
319           
320           
321#ifdef USE_PERL
322          if(strncasecmp(r_inputs->value,"PERL",4)==0){
323            *eres=zoo_perl_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
324          }
325          else
326#endif
327
328#ifdef USE_JS
329            if(strncasecmp(r_inputs->value,"JS",2)==0){
330              *eres=zoo_js_support(&m,request_inputs,s1,&request_input_real_format,&request_output_real_format);
331            }
332            else
333#endif
334              {
335                char tmpv[1024];
336                sprintf(tmpv,_("Programming Language (%s) set in ZCFG file is not currently supported by ZOO Kernel.\n"),r_inputs->value);
337                map* tmps=createMap("text",tmpv);
338                printExceptionReportResponse(m,tmps);
339                *eres=-1;
340              }
341  *myMap=m;
342  *ioutputs=request_output_real_format;
343}
344
345int runRequest(map* request_inputs)
346{
347
348#ifndef USE_GDB
349  (void) signal(SIGSEGV,sig_handler);
350  (void) signal(SIGTERM,sig_handler);
351  (void) signal(SIGINT,sig_handler);
352  (void) signal(SIGILL,sig_handler);
353  (void) signal(SIGFPE,sig_handler);
354  (void) signal(SIGABRT,sig_handler);
355#endif
356
357  map* r_inputs=NULL,*tmps=NULL;
358  maps* m=NULL;
359  int argc=count(request_inputs);
360
361  char* REQUEST=NULL;
362  /**
363   * Parsing service specfic configuration file
364   */
365  m=(maps*)calloc(1,MAPS_SIZE);
366  if(m == NULL){
367    return errorException(m, _("Unable to allocate memory."), "InternalError");
368  }
369  char ntmp[1024];
370#ifndef WIN32
371  getcwd(ntmp,1024);
372#else
373  _getcwd(ntmp,1024);
374#endif
375  r_inputs=getMap(request_inputs,"metapath");
376  if(r_inputs==NULL){
377    if(request_inputs==NULL)
378      request_inputs=createMap("metapath","");
379    else
380      addToMap(request_inputs,"metapath","");
381#ifdef DEBUG
382    fprintf(stderr,"ADD METAPATH\n");
383    dumpMap(request_inputs);
384#endif
385    r_inputs=getMap(request_inputs,"metapath");
386  }
387  char conf_file[10240];
388  snprintf(conf_file,10240,"%s/%s/main.cfg",ntmp,r_inputs->value);
389  conf_read(conf_file,m);
390#ifdef DEBUG
391  fprintf(stderr, "***** BEGIN MAPS\n"); 
392  dumpMaps(m);
393  fprintf(stderr, "***** END MAPS\n");
394#endif
395
396  bindtextdomain ("zoo-kernel","/usr/share/locale/");
397  bindtextdomain ("zoo-services","/usr/share/locale/");
398 
399  if((r_inputs=getMap(request_inputs,"language"))!=NULL){
400    char *tmp=strdup(r_inputs->value);
401    translateChar(tmp,'-','_');
402    setlocale (LC_ALL, tmp);
403    free(tmp);
404    setMapInMaps(m,"main","language",r_inputs->value);
405  }
406  else{
407    setlocale (LC_ALL, "en_US");
408    setMapInMaps(m,"main","language","en-US");
409  }
410  setlocale (LC_NUMERIC, "en_US");
411  bind_textdomain_codeset("zoo-kernel","UTF-8");
412  textdomain("zoo-kernel");
413  bind_textdomain_codeset("zoo-services","UTF-8");
414  textdomain("zoo-services");
415
416
417  /**
418   * Check for minimum inputs
419   */
420  r_inputs=getMap(request_inputs,"Request");
421  if(request_inputs==NULL || r_inputs==NULL){ 
422    errorException(m, _("Parameter <request> was not specified"),"MissingParameterValue");
423    freeMaps(&m);
424    free(m);
425    freeMap(&request_inputs);
426    free(request_inputs);
427    free(REQUEST);
428    return 1;
429  }
430  else{
431    REQUEST=strdup(r_inputs->value);
432    if(strncasecmp(r_inputs->value,"GetCapabilities",15)!=0
433       && strncasecmp(r_inputs->value,"DescribeProcess",15)!=0
434       && strncasecmp(r_inputs->value,"Execute",7)!=0){ 
435      errorException(m, _("Unenderstood <request> value. Please check that it was set to GetCapabilities, DescribeProcess or Execute."), "InvalidParameterValue");
436      freeMaps(&m);
437      free(m);
438      free(REQUEST);
439      return 1;
440    }
441  }
442  r_inputs=NULL;
443  r_inputs=getMap(request_inputs,"Service");
444  if(r_inputs==NULLMAP){
445    errorException(m, _("Parameter <service> was not specified"),"MissingParameterValue");
446    freeMaps(&m);
447    free(m);
448    free(REQUEST);
449    return 1;
450  }
451  if(strncasecmp(REQUEST,"GetCapabilities",15)!=0){
452    r_inputs=getMap(request_inputs,"Version");
453    if(r_inputs==NULL){ 
454      errorException(m, _("Parameter <version> was not specified"),"MissingParameterValue");
455      freeMaps(&m);
456      free(m);
457      free(REQUEST);
458      return 1;
459    }
460  }
461
462  r_inputs=getMap(request_inputs,"serviceprovider");
463  if(r_inputs==NULL){
464    addToMap(request_inputs,"serviceprovider","");
465  }
466
467  map* outputs=NULL;
468  maps* request_output_real_format=NULL;
469  map* tmpm=getMapFromMaps(m,"main","serverAddress");
470  if(tmpm!=NULL)
471    SERVICE_URL=strdup(tmpm->value);
472  else
473    SERVICE_URL=strdup(DEFAULT_SERVICE_URL);
474
475  service* s[100];
476  service* s1;
477  int scount=0;
478
479#ifdef DEBUG
480  dumpMap(r_inputs);
481#endif
482  char conf_dir[1024];
483  int t;
484  char tmps1[1024];
485
486  r_inputs=NULL;
487  r_inputs=getMap(request_inputs,"metapath");
488  if(r_inputs!=NULL)
489    snprintf(conf_dir,1024,"%s/%s",ntmp,r_inputs->value);
490  else
491    snprintf(conf_dir,1024,"%s",ntmp);
492
493  if(strncasecmp(REQUEST,"GetCapabilities",15)==0){
494    int i=0;
495    struct dirent *dp;
496#ifdef DEBUG
497    dumpMap(r_inputs);
498#endif
499    DIR *dirp = opendir(conf_dir);
500    if(dirp==NULL){
501      return errorException(m, _("The specified path doesn't exist."),"InvalidParameterValue");
502    }
503    xmlDocPtr doc = xmlNewDoc(BAD_CAST "1.0");
504    r_inputs=NULL;
505    r_inputs=getMap(request_inputs,"ServiceProvider");
506    xmlNodePtr n;
507    //dumpMap(request_inputs);
508    if(r_inputs!=NULL)
509      n = printGetCapabilitiesHeader(doc,r_inputs->value,m);
510    else
511      n = printGetCapabilitiesHeader(doc,"",m);
512    /**
513     * Strange, here we need to close stdout to ensure that no uneeded
514     * char will be printed (parser issue ?)
515     */
516    int saved_stdout = dup(fileno(stdout));
517    dup2(fileno(stderr),fileno(stdout));
518    while ((dp = readdir(dirp)) != NULL)
519      if(strstr(dp->d_name,".zcfg")!=0){
520        memset(tmps1,0,1024);
521        snprintf(tmps1,1024,"%s/%s",conf_dir,dp->d_name);
522        s1=(service*)calloc(1,SERVICE_SIZE);
523        if(s1 == NULL){ 
524          return errorException(m, _("Unable to allocate memory."),"InternalError");
525        }
526#ifdef DEBUG
527        fprintf(stderr,"#################\n%s\n#################\n",tmps1);
528#endif
529        t=getServiceFromFile(tmps1,&s1);
530#ifdef DEBUG
531        dumpService(s1);
532        fflush(stdout);
533        fflush(stderr);
534#endif
535        printGetCapabilitiesForProcess(m,n,s1);
536        freeService(&s1);
537        free(s1);
538        scount++;
539      }
540    (void)closedir(dirp);
541    fflush(stdout);
542    dup2(saved_stdout,fileno(stdout));
543    printDocument(m,doc,getpid());
544    freeMaps(&m);
545    free(m);
546    free(REQUEST);
547    free(SERVICE_URL);
548    fflush(stdout);
549    return 0;
550  }
551  else{
552    r_inputs=getMap(request_inputs,"Identifier");
553    if(r_inputs==NULL 
554       || strlen(r_inputs->name)==0 || strlen(r_inputs->value)==0){ 
555      errorException(m, _("Mandatory <identifier> was not specified"),"MissingParameterValue");
556      freeMaps(&m);
557      free(m);
558      free(REQUEST);
559      free(SERVICE_URL);
560      return 0;
561    }
562
563    struct dirent *dp;
564    DIR *dirp = opendir(conf_dir);
565    if(dirp==NULL){
566      errorException(m, _("The specified path path doesn't exist."),"InvalidParameterValue");
567      freeMaps(&m);
568      free(m);
569      free(REQUEST);
570      free(SERVICE_URL);
571      return 0;
572    }
573    if(strncasecmp(REQUEST,"DescribeProcess",15)==0){
574      /**
575       * Loop over Identifier list
576       */
577      xmlDocPtr doc = xmlNewDoc(BAD_CAST "1.0");
578      r_inputs=NULL;
579      r_inputs=getMap(request_inputs,"ServiceProvider");
580
581      xmlNodePtr n;
582      if(r_inputs!=NULL)
583        n = printDescribeProcessHeader(doc,r_inputs->value,m);
584      else
585        n = printDescribeProcessHeader(doc,"",m);
586
587      r_inputs=getMap(request_inputs,"Identifier");
588      char *tmps=strtok(r_inputs->value,",");
589     
590      char buff[256];
591      char buff1[1024];
592      int i=0;
593      int j=0;
594      int end=-1;
595      int saved_stdout = dup(fileno(stdout));
596      dup2(fileno(stderr),fileno(stdout));
597      while(tmps){
598        memset(buff,0,256);
599        snprintf(buff,256,"%s.zcfg",tmps);
600        memset(buff1,0,1024);
601#ifdef DEBUG
602        fprintf(stderr,"\n#######%s\n########\n",buff1);
603#endif
604        while ((dp = readdir(dirp)) != NULL)
605          if(strcmp(dp->d_name,buff)==0){
606            memset(buff1,0,1024);
607            snprintf(buff1,1024,"%s/%s",conf_dir,dp->d_name);
608            //s1=(service*)malloc(sizeof(service*));
609            s1=(service*)calloc(1,SERVICE_SIZE);
610            if(s1 == NULL){
611              return errorException(m, _("Unable to allocate memory."),"InternalError");
612            }
613#ifdef DEBUG
614            fprintf(stderr,"#################\n%s\n#################\n",buff1);
615#endif
616            t=getServiceFromFile(buff1,&s1);
617#ifdef DEBUG
618            dumpService(s1);
619#endif
620            printDescribeProcessForProcess(m,n,s1,1);
621            freeService(&s1);
622            free(s1);
623            scount++;
624          }
625        rewinddir(dirp);
626        tmps=strtok(NULL,",");
627      }
628      closedir(dirp);
629      fflush(stdout);
630      dup2(saved_stdout,fileno(stdout));
631      printDocument(m,doc,getpid());
632      freeMaps(&m);
633      free(m);
634      free(REQUEST);
635      free(SERVICE_URL);
636      fflush(stdout);
637      //xmlFree(n);
638#ifndef LINUX_FREE_ISSUE
639      if(s1)
640        free(s1);
641#endif
642      return 0;
643    }
644    else
645      if(strncasecmp(REQUEST,"Execute",strlen(REQUEST))!=0){
646        errorException(m, _("Unenderstood <request> value. Please check that it was set to GetCapabilities, DescribeProcess or Execute."), "InvalidParameterValue");
647#ifdef DEBUG
648        fprintf(stderr,"No request found %s",REQUEST);
649#endif 
650        closedir(dirp);
651        free(s);
652        return 0;
653      }
654    closedir(dirp);
655  }
656 
657  s1=NULL;
658  s1=(service*)calloc(1,SERVICE_SIZE);
659  if(s1 == NULL){
660    freeMaps(&m);
661    free(m);
662    free(REQUEST);
663    free(SERVICE_URL);
664    return errorException(m, _("Unable to allocate memory."),"InternalError");
665  }
666  r_inputs=getMap(request_inputs,"MetaPath");
667  if(r_inputs!=NULL)
668    snprintf(tmps1,1024,"%s/%s",ntmp,r_inputs->value);
669  else
670    snprintf(tmps1,1024,"%s/",ntmp);
671  r_inputs=getMap(request_inputs,"Identifier");
672  char *ttmp=strdup(tmps1);
673  snprintf(tmps1,1024,"%s/%s.zcfg",ttmp,r_inputs->value);
674  free(ttmp);
675#ifdef DEBUG
676  fprintf(stderr,"Trying to load %s\n", tmps1);
677#endif
678  int saved_stdout = dup(fileno(stdout));
679  dup2(fileno(stderr),fileno(stdout));
680  t=getServiceFromFile(tmps1,&s1);
681  fflush(stdout);
682  dup2(saved_stdout,fileno(stdout));
683  if(t<0){
684    char tmpMsg[2048+strlen(r_inputs->value)];
685    sprintf(tmpMsg,_("The value for <indetifier> seems to be wrong (%s). Please, ensure that the process exist using the GetCapabilities request."),r_inputs->value);
686    errorException(m, tmpMsg, "InvalidParameterValue");
687    freeService(&s1);
688    free(s1);
689    freeMaps(&m);
690    free(m);
691    free(REQUEST);
692    free(SERVICE_URL);
693    return 0;
694  }
695  close(saved_stdout);
696
697#ifdef DEBUG
698  dumpService(s1);
699#endif
700  map* inputs=NULL;
701  elements* c_inputs=s1->inputs;
702  int j;
703 
704  /**
705   * Create the input maps data structure
706   */
707  int i=0;
708  HINTERNET hInternet;
709  HINTERNET res;
710  hInternet=InternetOpen(
711#ifndef WIN32
712                         (LPCTSTR)
713#endif
714                         "ZooWPSClient\0",
715                         INTERNET_OPEN_TYPE_PRECONFIG,
716                         NULL,NULL, 0);
717
718#ifndef WIN32
719  if(!CHECK_INET_HANDLE(hInternet))
720    fprintf(stderr,"WARNING : hInternet handle failed to initialize");
721#endif
722  maps* request_input_real_format=NULL;
723  maps* tmpmaps = request_input_real_format;
724  map* postRequest=NULL;
725  postRequest=getMap(request_inputs,"xrequest");
726  if(postRequest==NULLMAP){
727    /**
728     * Parsing outputs provided as KVP
729     */
730    r_inputs=NULL;
731#ifdef DEBUG
732    fprintf(stderr,"OUTPUT Parsing ... \n");
733#endif
734    r_inputs=getMap(request_inputs,"ResponseDocument"); 
735    if(r_inputs==NULL) r_inputs=getMap(request_inputs,"RawDataOutput");
736   
737#ifdef DEBUG
738    fprintf(stderr,"OUTPUT Parsing ... \n");
739#endif
740    if(r_inputs!=NULL){
741#ifdef DEBUG
742      fprintf(stderr,"OUTPUT Parsing start now ... \n");
743#endif
744      char current_output_as_string[10240];
745      char cursor_output[10240];
746      char *cotmp=strdup(r_inputs->value);
747      snprintf(cursor_output,10240,"%s",cotmp);
748      free(cotmp);
749      j=0;
750      map* request_kvp_outputs=NULL;
751       
752      /**
753       * Put each Output into the outputs_as_text array
754       */
755      char * pToken;
756      maps* tmp_output=NULL;
757#ifdef DEBUG
758      fprintf(stderr,"OUTPUT [%s]\n",cursor_output);
759#endif
760      pToken=strtok(cursor_output,";");
761      char** outputs_as_text=(char**)calloc(128,sizeof(char*));
762      if(outputs_as_text == NULL) {
763        return errorException(m, _("Unable to allocate memory"), "InternalError");
764      }
765      i=0;
766      while(pToken!=NULL){
767#ifdef DEBUG
768        fprintf(stderr,"***%s***\n",pToken);
769        fflush(stderr);
770        fprintf(stderr,"***%s***\n",pToken);
771#endif
772        outputs_as_text[i]=(char*)calloc(strlen(pToken)+1,sizeof(char));
773        if(outputs_as_text[i] == NULL) {
774          return errorException(m, _("Unable to allocate memory"), "InternalError");
775        }
776        snprintf(outputs_as_text[i],strlen(pToken)+1,"%s",pToken);
777        pToken = strtok(NULL,";");
778        i++;
779      }
780      for(j=0;j<i;j++){
781        char *tmp=strdup(outputs_as_text[j]);
782        free(outputs_as_text[j]);
783        char *tmpc;
784        tmpc=strtok(tmp,"@");
785        int k=0;
786        while(tmpc!=NULL){
787          if(k==0){
788            if(tmp_output==NULL){
789              tmp_output=(maps*)calloc(1,MAPS_SIZE);
790              if(tmp_output == NULL){
791                return errorException(m, _("Unable to allocate memory."), "InternalError");
792              }
793              tmp_output->name=strdup(tmpc);
794              tmp_output->content=NULL;
795              tmp_output->next=NULL;
796            }
797          }
798          else{
799            char *tmpv=strstr(tmpc,"=");
800            char tmpn[256];
801            memset(tmpn,0,256);
802            strncpy(tmpn,tmpc,(strlen(tmpc)-strlen(tmpv))*sizeof(char));
803            tmpn[strlen(tmpc)-strlen(tmpv)]=0;
804#ifdef DEBUG
805            fprintf(stderr,"OUTPUT DEF [%s]=[%s]\n",tmpn,tmpv+1);
806#endif
807            if(tmp_output->content==NULL){
808              tmp_output->content=createMap(tmpn,tmpv+1);
809              tmp_output->content->next=NULL;
810            }
811            else
812              addToMap(tmp_output->content,tmpn,tmpv+1);
813          }
814          k++;
815#ifdef DEBUG
816          fprintf(stderr,"***%s***\n",tmpc);
817#endif
818          tmpc=strtok(NULL,"@");
819        }
820        if(request_output_real_format==NULL)
821          request_output_real_format=dupMaps(&tmp_output);
822        else
823          addMapsToMaps(&request_output_real_format,tmp_output);
824        freeMaps(&tmp_output);
825        free(tmp_output);
826        tmp_output=NULL;
827#ifdef DEBUG
828        dumpMaps(tmp_output);
829        fflush(stderr);
830#endif
831        //tmp_output=tmp_output->next;
832        free(tmp);
833      }
834      free(outputs_as_text);
835    }
836
837
838    /**
839     * Parsing inputs provided as KVP
840     */
841    r_inputs=getMap(request_inputs,"DataInputs");
842#ifdef DEBUG
843    fprintf(stderr,"DATA INPUTS [%s]\n",r_inputs->value);
844#endif
845    char current_input_as_string[40960];
846    char cursor_input[40960];
847    if(r_inputs!=NULL)
848      snprintf(cursor_input,40960,"%s",r_inputs->value);
849    else{
850      errorException(m, _("Parameter <DataInputs> was not specified"),"MissingParameterValue");
851      freeMaps(&m);
852      free(m);
853      free(REQUEST);
854      free(SERVICE_URL);
855      InternetCloseHandle(hInternet);
856      freeService(&s1);
857      free(s1);
858      return 0;
859    }
860    j=0;
861    map* request_kvp_inputs=NULL;
862 
863    /**
864     * Put each DataInputs into the inputs_as_text array
865     */
866    char * pToken;
867    pToken=strtok(cursor_input,";");
868    char** inputs_as_text=(char**)calloc(100,sizeof(char*));
869    if(inputs_as_text == NULL){
870      return errorException(m, _("Unable to allocate memory."), "InternalError");
871    }
872    i=0;
873    while(pToken!=NULL){
874#ifdef DEBUG
875      fprintf(stderr,"***%s***\n",pToken);
876#endif
877      fflush(stderr);
878#ifdef DEBUG
879      fprintf(stderr,"***%s***\n",pToken);
880#endif
881      inputs_as_text[i]=(char*)calloc(strlen(pToken)+1,sizeof(char));
882      snprintf(inputs_as_text[i],strlen(pToken)+1,"%s",pToken);
883      if(inputs_as_text[i] == NULL){
884        return errorException(m, _("Unable to allocate memory."), "InternalError");
885      }
886      pToken = strtok(NULL,";");
887      i++;
888    }
889
890    for(j=0;j<i;j++){
891      char *tmp=strdup(inputs_as_text[j]);
892      free(inputs_as_text[j]);
893      char *tmpc;
894      tmpc=strtok(tmp,"@");
895      while(tmpc!=NULL){
896#ifdef DEBUG
897        fprintf(stderr,"***\n***%s***\n",tmpc);
898#endif
899        char *tmpv=strstr(tmpc,"=");
900        char tmpn[256];
901        memset(tmpn,0,256);
902        strncpy(tmpn,tmpc,(strlen(tmpc)-strlen(tmpv))*sizeof(char));
903        tmpn[strlen(tmpc)-strlen(tmpv)]=0;
904        int cnt=0;
905#ifdef DEBUG
906        fprintf(stderr,"***\n*** %s = %s ***\n",tmpn,tmpv+1);
907#endif
908        if(tmpmaps==NULL){
909          tmpmaps=(maps*)calloc(1,MAPS_SIZE);
910          if(tmpmaps == NULL){
911            return errorException(m, _("Unable to allocate memory."), "InternalError");
912          }
913          tmpmaps->name=strdup(tmpn);
914          tmpmaps->content=createMap("value",tmpv+1);
915          tmpmaps->next=NULL;
916        }
917        tmpc=strtok(NULL,"@");
918        while(tmpc!=NULL){
919#ifdef DEBUG
920          fprintf(stderr,"*** KVP NON URL-ENCODED \n***%s***\n",tmpc);
921#endif
922          char *tmpv1=strstr(tmpc,"=");
923#ifdef DEBUG
924          fprintf(stderr,"*** VALUE NON URL-ENCODED \n***%s***\n",tmpv1+1);
925#endif
926          char tmpn1[1024];
927          memset(tmpn1,0,1024);
928          strncpy(tmpn1,tmpc,strlen(tmpc)-strlen(tmpv1));
929          tmpn1[strlen(tmpc)-strlen(tmpv1)]=0;
930#ifdef DEBUG
931          fprintf(stderr,"*** NAME NON URL-ENCODED \n***%s***\n",tmpn1);
932          fprintf(stderr,"*** VALUE NON URL-ENCODED \n***%s***\n",tmpv1+1);
933#endif
934          if(strcmp(tmpn1,"xlink:href")!=0)
935            addToMap(tmpmaps->content,tmpn1,tmpv1+1);
936          else{
937#ifdef DEBUG
938            fprintf(stderr,"REQUIRE TO DOWNLOAD A FILE FROM A SERVER : url(%s)\n",tmpv1+1);
939#endif
940#ifndef WIN32
941            if(CHECK_INET_HANDLE(hInternet))
942#endif
943              {
944                res=InternetOpenUrl(hInternet,tmpv1+1,NULL,0,
945                                    INTERNET_FLAG_NO_CACHE_WRITE,0);
946#ifdef DEBUG
947                fprintf(stderr,"(%s) content-length : %d,,res.nDataAlloc %d \n",
948                        tmpv1+1,res.nDataAlloc,res.nDataLen);
949#endif
950                char* tmpContent=(char*)calloc((res.nDataLen+1),sizeof(char));
951                if(tmpContent == NULL){
952                  return errorException(m, _("Unable to allocate memory."), "InternalError");
953                }
954                size_t dwRead;
955                InternetReadFile(res, (LPVOID)tmpContent,res.nDataLen, &dwRead);
956                map* tmpMap=getMap(tmpmaps->content,"value");
957                if(tmpMap!=NULL){
958                  free(tmpMap->value);
959                  tmpMap->value=(char*)malloc((res.nDataLen+1)*sizeof(char));
960                  memmove(tmpMap->value,tmpContent,(res.nDataLen)*sizeof(char));
961                  tmpMap->value[res.nDataLen]=0;
962                  if(strlen(tmpContent)!=res.nDataLen){
963                    char tmp[256];
964                    sprintf(tmp,"%d",res.nDataLen*sizeof(char));
965                    addToMap(tmpmaps->content,"size",tmp);
966                  }
967                }
968                free(tmpContent);
969              }
970            addToMap(tmpmaps->content,tmpn1,tmpv1+1);
971            addToMap(tmpmaps->content,"Reference",tmpv1+1);
972          }
973          tmpc=strtok(NULL,"@");
974        }
975#ifdef DEBUG
976        dumpMaps(tmpmaps);
977        fflush(stderr);
978#endif
979        if(request_input_real_format==NULL)
980          request_input_real_format=dupMaps(&tmpmaps);
981        else
982          addMapsToMaps(&request_input_real_format,tmpmaps);
983        freeMaps(&tmpmaps);
984        free(tmpmaps);
985        tmpmaps=NULL;
986        free(tmp);
987      }
988    }
989    free(inputs_as_text);
990  }
991  else {
992    /**
993     * Parse XML request
994     */ 
995    xmlInitParser();
996#ifdef DEBUG
997    fflush(stderr);
998    fprintf(stderr,"BEFORE %s\n",postRequest->value);
999    fflush(stderr);
1000#endif
1001    xmlDocPtr doc =
1002      xmlParseMemory(postRequest->value,cgiContentLength);
1003#ifdef DEBUG
1004    fprintf(stderr,"AFTER\n");
1005    fflush(stderr);
1006#endif
1007    xmlNodePtr cur = xmlDocGetRootElement(doc);
1008    /**
1009     * Parse every Input in DataInputs node.
1010     */
1011    maps* tempMaps=NULL;
1012    xmlXPathObjectPtr tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='Input']");
1013    xmlNodeSet* tmps=tmpsptr->nodesetval;
1014#ifdef DEBUG
1015    fprintf(stderr,"*****%d*****\n",tmps->nodeNr);
1016#endif
1017    for(int k=0;k<tmps->nodeNr;k++){
1018      maps *tmpmaps=NULL;
1019      xmlNodePtr cur=tmps->nodeTab[k];
1020      if(tmps->nodeTab[k]->type == XML_ELEMENT_NODE) {
1021        /**
1022         * A specific Input node.
1023         */
1024#ifdef DEBUG
1025        fprintf(stderr, "= element 0 node \"%s\"\n", cur->name);
1026#endif
1027        xmlNodePtr cur2=cur->children;
1028        while(cur2!=NULL){
1029          while(cur2!=NULL && cur2->type!=XML_ELEMENT_NODE)
1030            cur2=cur2->next;
1031          if(cur2==NULL)
1032            break;
1033          /**
1034           * Indentifier
1035           */
1036          if(xmlStrncasecmp(cur2->name,BAD_CAST "Identifier",xmlStrlen(cur2->name))==0){
1037            xmlChar *val= xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1038            if(tmpmaps==NULL){
1039              tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1040              if(tmpmaps == NULL){
1041                return errorException(m, _("Unable to allocate memory."), "InternalError");
1042              }
1043              tmpmaps->name=strdup((char*)val);
1044              tmpmaps->content=NULL;
1045              tmpmaps->next=NULL;
1046            }
1047            xmlFree(val);
1048          }
1049          /**
1050           * Title, Asbtract
1051           */
1052          if(xmlStrncasecmp(cur2->name,BAD_CAST "Title",xmlStrlen(cur2->name))==0 ||
1053             xmlStrncasecmp(cur2->name,BAD_CAST "Abstract",xmlStrlen(cur2->name))==0){
1054            xmlChar *val=
1055              xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1056            if(tmpmaps==NULL){
1057              tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1058              if(tmpmaps == NULL){
1059                return errorException(m, _("Unable to allocate memory."), "InternalError");
1060              }
1061              tmpmaps->name="missingIndetifier";
1062              tmpmaps->content=createMap((char*)cur2->name,(char*)val);
1063              tmpmaps->next=NULL;
1064            }
1065            else{
1066              if(tmpmaps->content!=NULL)
1067                addToMap(tmpmaps->content,
1068                         (char*)cur2->name,(char*)val);
1069              else
1070                tmpmaps->content=
1071                  createMap((char*)cur2->name,(char*)val);
1072            }
1073#ifdef DEBUG
1074            dumpMaps(tmpmaps);
1075#endif
1076            xmlFree(val);
1077          }
1078          /**
1079           * InputDataFormChoice (Reference or Data ?)
1080           */
1081          if(xmlStrcasecmp(cur2->name,BAD_CAST "Reference")==0){
1082            /**
1083             * Get every attribute from a Reference node
1084             * mimeType, encoding, schema, href, method
1085             * Header and Body gesture should be added here
1086             */
1087#ifdef DEBUG
1088            fprintf(stderr,"REFERENCE\n");
1089#endif
1090            map* referenceMap=NULL;
1091            char *refs[5];
1092            refs[0]="mimeType";
1093            refs[1]="encoding";
1094            refs[2]="schema";
1095            refs[3]="method";
1096            refs[4]="href";
1097            char*url;
1098            for(int l=0;l<5;l++){
1099#ifdef DEBUG
1100              fprintf(stderr,"*** %s ***",refs[l]);
1101#endif
1102              xmlChar *val=xmlGetProp(cur2,BAD_CAST refs[l]);
1103              if(val!=NULL && xmlStrlen(val)>0){
1104                if(tmpmaps->content!=NULL)
1105                  addToMap(tmpmaps->content,refs[l],(char*)val);
1106                else
1107                  tmpmaps->content=createMap(refs[l],(char*)val);
1108                map* ltmp=getMap(tmpmaps->content,"method");
1109                if(l==4){
1110                  if(!(ltmp!=NULL && strcmp(ltmp->value,"POST")==0)
1111                     && CHECK_INET_HANDLE(hInternet)){
1112                    res=InternetOpenUrl(hInternet,(char*)val,NULL,0,
1113                                        INTERNET_FLAG_NO_CACHE_WRITE,0);
1114                    char* tmpContent=
1115                      (char*)calloc((res.nDataLen+1),sizeof(char));
1116                    if(tmpContent == NULL){
1117                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1118                    }
1119                    size_t dwRead;
1120                    InternetReadFile(res, (LPVOID)tmpContent,
1121                                     res.nDataLen, &dwRead);
1122                    tmpContent[res.nDataLen]=0;
1123                    addToMap(tmpmaps->content,"value",tmpContent);
1124                  }
1125                }
1126              }
1127#ifdef DEBUG
1128              fprintf(stderr,"%s\n",val);
1129#endif
1130              xmlFree(val);
1131            }
1132#ifdef POST_DEBUG
1133            fprintf(stderr,"Parse Header and Body from Reference \n");
1134#endif
1135            xmlNodePtr cur3=cur2->children;
1136            hInternet.header=NULL;
1137            while(cur3){
1138              if(xmlStrcasecmp(cur3->name,BAD_CAST "Header")==0 ){
1139                xmlNodePtr cur4=cur3;
1140                char *tmp=new char[cgiContentLength];
1141                char *ha[2];
1142                ha[0]="key";
1143                ha[1]="value";
1144                int hai;
1145                char *has;
1146                char *key;
1147                for(hai=0;hai<2;hai++){
1148                  xmlChar *val=xmlGetProp(cur3,BAD_CAST ha[hai]);
1149#ifdef POST_DEBUG
1150                  fprintf(stderr,"%s = %s\n",ha[hai],(char*)val);
1151#endif
1152                  if(hai==0){
1153                    key=(char*)calloc((1+strlen((char*)val)),sizeof(char));
1154                    snprintf(key,1+strlen((char*)val),"%s",(char*)val);
1155                  }else{
1156                    has=(char*)calloc((3+strlen((char*)val)+strlen(key)),sizeof(char));
1157                    if(has == NULL){
1158                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1159                    }
1160                    snprintf(has,(3+strlen((char*)val)+strlen(key)),"%s: %s",key,(char*)val);
1161#ifdef POST_DEBUG
1162                    fprintf(stderr,"%s\n",has);
1163#endif
1164                  }
1165                }
1166                hInternet.header=curl_slist_append(hInternet.header, has);
1167                //free(has);
1168              }
1169              else{
1170#ifdef POST_DEBUG
1171                fprintf(stderr,"Try to fetch the body part of the request ...\n");
1172#endif
1173                if(xmlStrcasecmp(cur3->name,BAD_CAST "Body")==0 ){
1174#ifdef POST_DEBUG
1175                  fprintf(stderr,"Body part found !!!\n",(char*)cur3->content);
1176#endif
1177                  char *tmp=new char[cgiContentLength];
1178                  memset(tmp,0,cgiContentLength);
1179                  xmlNodePtr cur4=cur3->children;
1180                  while(cur4!=NULL){
1181                    xmlDocPtr bdoc = xmlNewDoc(BAD_CAST "1.0");
1182                    bdoc->encoding = xmlCharStrdup ("UTF-8");
1183                    xmlDocSetRootElement(bdoc,cur4);
1184                    xmlChar* btmps;
1185                    int bsize;
1186                    xmlDocDumpMemory(bdoc,&btmps,&bsize);
1187#ifdef POST_DEBUG
1188                    fprintf(stderr,"Body part found !!! %s %s\n",tmp,(char*)btmps);
1189#endif
1190                    if(btmps!=NULL)
1191                      sprintf(tmp,"%s",(char*)btmps);
1192                    xmlFreeDoc(bdoc);
1193                    cur4=cur4->next;
1194                  }
1195                  map *btmp=getMap(tmpmaps->content,"href");
1196                  if(btmp!=NULL){
1197#ifdef POST_DEBUG
1198                    fprintf(stderr,"%s %s\n",btmp->value,tmp);
1199                    curl_easy_setopt(hInternet.handle, CURLOPT_VERBOSE, 1);
1200#endif
1201                    res=InternetOpenUrl(hInternet,btmp->value,tmp,strlen(tmp),
1202                                        INTERNET_FLAG_NO_CACHE_WRITE,0);
1203                    char* tmpContent = (char*)calloc((res.nDataLen+1),sizeof(char));
1204                    if(tmpContent == NULL){
1205                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1206                    }
1207                    size_t dwRead;
1208                    InternetReadFile(res, (LPVOID)tmpContent,
1209                                     res.nDataLen, &dwRead);
1210                    tmpContent[res.nDataLen]=0;
1211                    if(hInternet.header!=NULL)
1212                      curl_slist_free_all(hInternet.header);
1213                    addToMap(tmpmaps->content,"value",tmpContent);
1214#ifdef POST_DEBUG
1215                    fprintf(stderr,"DL CONTENT : (%s)\n",tmpContent);
1216#endif
1217                  }
1218                }
1219                else
1220                  if(xmlStrcasecmp(cur3->name,BAD_CAST "BodyReference")==0 ){
1221                    xmlChar *val=xmlGetProp(cur3,BAD_CAST "href");
1222                    HINTERNET bInternet,res1;
1223                    bInternet=InternetOpen(
1224#ifndef WIN32
1225                                           (LPCTSTR)
1226#endif
1227                                           "ZooWPSClient\0",
1228                                           INTERNET_OPEN_TYPE_PRECONFIG,
1229                                           NULL,NULL, 0);
1230                    if(!CHECK_INET_HANDLE(bInternet))
1231                      fprintf(stderr,"WARNING : hInternet handle failed to initialize");
1232#ifdef POST_DEBUG
1233                    curl_easy_setopt(bInternet.handle, CURLOPT_VERBOSE, 1);
1234#endif
1235                    res1=InternetOpenUrl(bInternet,(char*)val,NULL,0,
1236                                         INTERNET_FLAG_NO_CACHE_WRITE,0);
1237                    char* tmp=
1238                      (char*)calloc((res1.nDataLen+1),sizeof(char));
1239                    if(tmp == NULL){
1240                      return errorException(m, _("Unable to allocate memory."), "InternalError");
1241                    }
1242                    size_t bRead;
1243                    InternetReadFile(res1, (LPVOID)tmp,
1244                                     res1.nDataLen, &bRead);
1245                    tmp[res1.nDataLen]=0;
1246                    InternetCloseHandle(bInternet);
1247                    map *btmp=getMap(tmpmaps->content,"href");
1248                    if(btmp!=NULL){
1249#ifdef POST_DEBUG
1250                      fprintf(stderr,"%s %s\n",btmp->value,tmp);
1251                      curl_easy_setopt(hInternet.handle, CURLOPT_VERBOSE, 1);
1252#endif
1253                      res=InternetOpenUrl(hInternet,btmp->value,tmp,
1254                                          strlen(tmp),
1255                                          INTERNET_FLAG_NO_CACHE_WRITE,0);
1256                      char* tmpContent = (char*)calloc((res.nDataLen+1),sizeof(char));
1257                      if(tmpContent == NULL){
1258                        return errorException(m, _("Unable to allocate memory."), "InternalError");
1259                      }
1260                      size_t dwRead;
1261                      InternetReadFile(res, (LPVOID)tmpContent,
1262                                       res.nDataLen, &dwRead);
1263                      tmpContent[res.nDataLen]=0;
1264                      if(hInternet.header!=NULL)
1265                        curl_slist_free_all(hInternet.header);
1266                      addToMap(tmpmaps->content,"value",tmpContent);
1267#ifdef POST_DEBUG
1268                      fprintf(stderr,"DL CONTENT : (%s)\n",tmpContent);
1269#endif
1270                    }
1271                  }
1272              }
1273              cur3=cur3->next;
1274            }
1275#ifdef POST_DEBUG
1276            fprintf(stderr,"Header and Body was parsed from Reference \n");
1277#endif
1278#ifdef DEBUG
1279            dumpMap(tmpmaps->content);
1280            fprintf(stderr, "= element 2 node \"%s\" = (%s)\n", 
1281                    cur2->name,cur2->content);
1282#endif
1283          }
1284          else if(xmlStrcasecmp(cur2->name,BAD_CAST "Data")==0){
1285#ifdef DEBUG
1286            fprintf(stderr,"DATA\n");
1287#endif
1288            xmlNodePtr cur4=cur2->children;
1289            while(cur4!=NULL){
1290              while(cur4!=NULL &&cur4->type!=XML_ELEMENT_NODE)
1291                cur4=cur4->next;
1292              if(cur4==NULL)
1293                break;
1294              if(xmlStrcasecmp(cur4->name, BAD_CAST "LiteralData")==0){
1295                /**
1296                 * Get every attribute from a LiteralData node
1297                 * dataType , uom
1298                 */
1299                char *lits[2];
1300                lits[0]="dataType";
1301                lits[1]="uom";
1302                for(int l=0;l<2;l++){
1303#ifdef DEBUG
1304                  fprintf(stderr,"*** LiteralData %s ***",lits[l]);
1305#endif
1306                  xmlChar *val=xmlGetProp(cur4,BAD_CAST lits[l]);
1307                  if(val!=NULL && strlen((char*)val)>0){
1308                    if(tmpmaps->content!=NULL)
1309                      addToMap(tmpmaps->content,lits[l],(char*)val);
1310                    else
1311                      tmpmaps->content=createMap(lits[l],(char*)val);
1312                  }
1313#ifdef DEBUG
1314                  fprintf(stderr,"%s\n",val);
1315#endif
1316                  xmlFree(val);
1317                }
1318              }
1319              else if(xmlStrcasecmp(cur4->name, BAD_CAST "ComplexData")==0){
1320                /**
1321                 * Get every attribute from a Reference node
1322                 * mimeType, encoding, schema
1323                 */
1324                char *coms[3];
1325                coms[0]="mimeType";
1326                coms[1]="encoding";
1327                coms[2]="schema";
1328                for(int l=0;l<3;l++){
1329#ifdef DEBUG
1330                  fprintf(stderr,"*** ComplexData %s ***",coms[l]);
1331#endif
1332                  xmlChar *val=xmlGetProp(cur4,BAD_CAST coms[l]);
1333                  if(val!=NULL && strlen((char*)val)>0){
1334                    if(tmpmaps->content!=NULL)
1335                      addToMap(tmpmaps->content,coms[l],(char*)val);
1336                    else
1337                      tmpmaps->content=createMap(coms[l],(char*)val);
1338                  }
1339#ifdef DEBUG
1340                  fprintf(stderr,"%s\n",val);
1341#endif
1342                  xmlFree(val);
1343                }
1344              }
1345              xmlChar* mv=xmlNodeListGetString(doc,cur4->xmlChildrenNode,1);
1346              if(mv==NULL){
1347                xmlDocPtr doc1=xmlNewDoc(BAD_CAST "1.0");
1348                int buffersize;
1349                xmlDocSetRootElement(doc1,cur4->xmlChildrenNode);
1350                xmlDocDumpFormatMemoryEnc(doc1, &mv, &buffersize, "utf-8", 1);
1351                char size[1024];
1352                sprintf(size,"%d",buffersize);
1353                addToMap(tmpmaps->content,"size",size);
1354              }
1355              addToMap(tmpmaps->content,"value",(char*)mv);
1356              xmlFree(mv);
1357              cur4=cur4->next;
1358            }
1359          }
1360#ifdef DEBUG
1361          fprintf(stderr,"cur2 next \n");
1362          fflush(stderr);
1363#endif
1364          cur2=cur2->next;
1365        }
1366#ifdef DEBUG
1367        fprintf(stderr,"ADD MAPS TO REQUEST MAPS !\n");
1368        fflush(stderr);
1369#endif
1370        addMapsToMaps(&request_input_real_format,tmpmaps);
1371       
1372#ifdef DEBUG
1373        fprintf(stderr,"******TMPMAPS*****\n");
1374        dumpMaps(tmpmaps);
1375        fprintf(stderr,"******REQUESTMAPS*****\n");
1376        dumpMaps(request_input_real_format);
1377#endif
1378        freeMaps(&tmpmaps);
1379        free(tmpmaps);
1380        tmpmaps=NULL;         
1381      }
1382#ifdef DEBUG
1383      dumpMaps(tmpmaps); 
1384#endif
1385    }
1386#ifdef DEBUG
1387    fprintf(stderr,"Search for response document node\n");
1388#endif
1389    xmlXPathFreeObject(tmpsptr);
1390    //xmlFree(tmps);
1391    tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='ResponseDocument']");
1392    tmps=tmpsptr->nodesetval;
1393#ifdef DEBUG
1394    fprintf(stderr,"*****%d*****\n",tmps->nodeNr);
1395#endif
1396    for(int k=0;k<tmps->nodeNr;k++){
1397      addToMap(request_inputs,"ResponseDocument","");
1398      request_output_real_format;
1399      maps *tmpmaps=NULL;
1400      xmlNodePtr cur=tmps->nodeTab[k];
1401      if(cur->type == XML_ELEMENT_NODE) {
1402        /**
1403         * A specific responseDocument node.
1404         */
1405        if(tmpmaps==NULL){
1406          tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1407          if(tmpmaps == NULL){
1408            return errorException(m, _("Unable to allocate memory."), "InternalError");
1409          }
1410          tmpmaps->name="unknownIdentifier";
1411          tmpmaps->next=NULL;
1412        }
1413        /**
1414         * Get every attribute from a LiteralData node
1415         * storeExecuteResponse, lineage, status
1416         */
1417        char *ress[3];
1418        ress[0]="storeExecuteResponse";
1419        ress[1]="lineage";
1420        ress[2]="status";
1421        xmlChar *val;
1422        for(int l=0;l<3;l++){
1423#ifdef DEBUG
1424          fprintf(stderr,"*** %s ***\t",ress[l]);
1425#endif
1426          val=xmlGetProp(cur,BAD_CAST ress[l]);
1427          if(val!=NULL && strlen((char*)val)>0){
1428            if(tmpmaps->content!=NULL)
1429              addToMap(tmpmaps->content,ress[l],(char*)val);
1430            else
1431              tmpmaps->content=createMap(ress[l],(char*)val);
1432            addToMap(request_inputs,ress[l],(char*)val);
1433          }
1434#ifdef DEBUG
1435          fprintf(stderr,"%s\n",val);
1436#endif
1437          xmlFree(val);
1438        }
1439        xmlNodePtr cur1=cur->children;
1440        while(cur1){
1441          if(xmlStrncasecmp(cur1->name,BAD_CAST "Output",xmlStrlen(cur1->name))==0){
1442            /**
1443             * Get every attribute from a Output node
1444             * mimeType, encoding, schema, uom, asReference
1445             */
1446            char *outs[5];
1447            outs[0]="mimeType";
1448            outs[1]="encoding";
1449            outs[2]="schema";
1450            outs[3]="uom";
1451            outs[4]="asReference";
1452            for(int l=0;l<5;l++){
1453#ifdef DEBUG
1454              fprintf(stderr,"*** %s ***\t",outs[l]);
1455#endif
1456              val=xmlGetProp(cur1,BAD_CAST outs[l]);
1457              if(val!=NULL && strlen((char*)val)>0){
1458                if(tmpmaps->content!=NULL)
1459                  addToMap(tmpmaps->content,outs[l],(char*)val);
1460                else
1461                  tmpmaps->content=createMap(outs[l],(char*)val);
1462              }
1463#ifdef DEBUG
1464              fprintf(stderr,"%s\n",val);
1465#endif
1466              xmlFree(val);
1467            }
1468           
1469            xmlNodePtr cur2=cur1->children;
1470            while(cur2){
1471              /**
1472               * Indentifier
1473               */
1474              if(xmlStrncasecmp(cur2->name,BAD_CAST "Identifier",xmlStrlen(cur2->name))==0){
1475                xmlChar *val=
1476                  xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1477                if(tmpmaps==NULL){
1478                  tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1479                  if(tmpmaps == NULL){
1480                    return errorException(m, _("Unable to allocate memory."), "InternalError");
1481                  }
1482                  tmpmaps->name=strdup((char*)val);
1483                  tmpmaps->content=NULL;
1484                  tmpmaps->next=NULL;
1485                }
1486                else
1487                  tmpmaps->name=strdup((char*)val);;
1488                xmlFree(val);
1489              }
1490              /**
1491               * Title, Asbtract
1492               */
1493              if(xmlStrncasecmp(cur2->name,BAD_CAST "Title",xmlStrlen(cur2->name))==0 ||
1494                 xmlStrncasecmp(cur2->name,BAD_CAST "Abstract",xmlStrlen(cur2->name))==0){
1495                xmlChar *val=
1496                  xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1497                if(tmpmaps==NULL){
1498                  tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1499                  if(tmpmaps == NULL){
1500                    return errorException(m, _("Unable to allocate memory."), "InternalError");
1501                  }
1502                  tmpmaps->name="missingIndetifier";
1503                  tmpmaps->content=createMap((char*)cur2->name,(char*)val);
1504                  tmpmaps->next=NULL;
1505                }
1506                else{
1507                  if(tmpmaps->content!=NULL)
1508                    addToMap(tmpmaps->content,
1509                             (char*)cur2->name,(char*)val);
1510                  else
1511                    tmpmaps->content=
1512                      createMap((char*)cur2->name,(char*)val);
1513                }
1514                xmlFree(val);
1515              }
1516              cur2=cur2->next;
1517            }
1518          }
1519          cur1=cur1->next;
1520        }
1521      }
1522      //xmlFree(cur);
1523      if(request_output_real_format==NULL)
1524        request_output_real_format=tmpmaps;
1525      else
1526        addMapsToMaps(&request_output_real_format,tmpmaps);
1527#ifdef DEBUG
1528      dumpMaps(tmpmaps);
1529#endif
1530    }
1531    xmlXPathFreeObject(tmpsptr);
1532    //xmlFree(tmps);
1533    tmpsptr=extractFromDoc(doc,"/*/*/*[local-name()='RawDataOutput']");
1534    tmps=tmpsptr->nodesetval;
1535#ifdef DEBUG
1536    fprintf(stderr,"*****%d*****\n",tmps->nodeNr);
1537#endif
1538    for(int k=0;k<tmps->nodeNr;k++){
1539      addToMap(request_inputs,"RawDataOutput","");
1540      xmlNodePtr cur1=tmps->nodeTab[k];
1541      xmlChar *val;
1542      /**
1543       * Get every attribute from a Output node
1544       * mimeType, encoding, schema, uom, asReference
1545       */
1546      char *outs[4];
1547      outs[0]="mimeType";
1548      outs[1]="encoding";
1549      outs[2]="schema";
1550      outs[3]="uom";
1551      for(int l=0;l<4;l++){
1552#ifdef DEBUG
1553        fprintf(stderr,"*** %s ***\t",outs[l]);
1554#endif
1555        val=xmlGetProp(cur1,BAD_CAST outs[l]);
1556        if(val!=NULL && strlen((char*)val)>0){
1557          if(tmpmaps==NULL){
1558            tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1559            if(tmpmaps == NULL){
1560              return errorException(m, _("Unable to allocate memory."), "InternalError");
1561            }
1562            tmpmaps->name="unknownIdentifier";
1563            tmpmaps->content=createMap(outs[l],(char*)val);
1564            tmpmaps->next=NULL;
1565          }
1566          else
1567            addToMap(tmpmaps->content,outs[l],(char*)val);
1568        }
1569#ifdef DEBUG
1570        fprintf(stderr,"%s\n",val);
1571#endif
1572        xmlFree(val);
1573      }
1574           
1575      xmlNodePtr cur2=cur1->children;
1576      while(cur2){
1577        /**
1578         * Indentifier
1579         */
1580        if(xmlStrncasecmp(cur2->name,BAD_CAST "Identifier",xmlStrlen(cur2->name))==0){
1581          val=
1582            xmlNodeListGetString(doc,cur2->xmlChildrenNode,1);
1583          if(tmpmaps==NULL){
1584            tmpmaps=(maps*)calloc(1,MAPS_SIZE);
1585            if(tmpmaps == NULL){
1586              return errorException(m, _("Unable to allocate memory."), "InternalError");
1587            }
1588            tmpmaps->name=strdup((char*)val);
1589            tmpmaps->content=NULL;
1590            tmpmaps->next=NULL;
1591          }
1592          else
1593            tmpmaps->name=strdup((char*)val);;
1594          xmlFree(val);
1595        }
1596        cur2=cur2->next;
1597      }
1598      if(request_output_real_format==NULL)
1599        request_output_real_format=tmpmaps;
1600      else
1601        addMapsToMaps(&request_output_real_format,tmpmaps);
1602#ifdef DEBUG
1603      dumpMaps(tmpmaps);
1604#endif
1605    }
1606    xmlXPathFreeObject(tmpsptr);
1607    //xmlFree(tmps);
1608    xmlCleanupParser();
1609  }
1610
1611  //if(CHECK_INET_HANDLE(hInternet))
1612  InternetCloseHandle(hInternet);
1613
1614#ifdef DEBUG
1615  fprintf(stderr,"\n%i\n",i);
1616  dumpMaps(request_input_real_format);
1617  dumpMaps(request_output_real_format);
1618  dumpMap(request_inputs);
1619#endif
1620
1621  /**
1622   * Ensure that each requested arguments are present in the request
1623   * DataInputs and ResponseDocument / RawDataOutput
1624   */ 
1625  char *dfv=addDefaultValues(&request_input_real_format,s1->inputs,m,0);
1626  if(strcmp(dfv,"")!=0){
1627    char tmps[1024];
1628    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);
1629    map* tmpe=createMap("text",tmps);
1630    addToMap(tmpe,"code","MissingParameterValue");
1631    printExceptionReportResponse(m,tmpe);
1632    freeService(&s1);
1633    free(s1);
1634    freeMap(&tmpe);
1635    free(tmpe);
1636    freeMaps(&m);
1637    free(m);
1638    free(REQUEST);
1639    free(SERVICE_URL);
1640    freeMaps(&request_input_real_format);
1641    free(request_input_real_format);
1642    freeMaps(&request_output_real_format);
1643    free(request_output_real_format);
1644    freeMaps(&tmpmaps);
1645    free(tmpmaps);
1646    return 1;
1647  }
1648  addDefaultValues(&request_output_real_format,s1->outputs,m,1);
1649
1650  ensureDecodedBase64(&request_input_real_format);
1651
1652#ifdef DEBUG
1653  fprintf(stderr,"REQUEST_INPUTS\n");
1654  dumpMaps(request_input_real_format);
1655  fprintf(stderr,"REQUEST_OUTPUTS\n");
1656  dumpMaps(request_output_real_format);
1657#endif
1658
1659  maps* curs=getMaps(m,"env");
1660  if(curs!=NULL){
1661    map* mapcs=curs->content;
1662    while(mapcs!=NULLMAP){
1663#ifndef WIN32
1664      setenv(mapcs->name,mapcs->value,1);
1665#else
1666#ifdef DEBUG
1667      fprintf(stderr,"[ZOO: setenv (%s=%s)]\n",mapcs->name,mapcs->value);
1668#endif
1669      if(mapcs->value[strlen(mapcs->value)-2]=='\r'){
1670#ifdef DEBUG
1671        fprintf(stderr,"[ZOO: Env var finish with \r]\n");
1672#endif
1673        mapcs->value[strlen(mapcs->value)-1]=0;
1674      }
1675#ifdef DEBUG
1676      fflush(stderr);
1677      fprintf(stderr,"setting variable... %s\n",
1678#endif
1679              SetEnvironmentVariable(mapcs->name,mapcs->value)
1680#ifdef DEBUG
1681              ? "OK" : "FAILED");
1682#else
1683      ;
1684#endif
1685#ifdef DEBUG
1686      fflush(stderr);
1687#endif
1688#endif
1689#ifdef DEBUG
1690      fprintf(stderr,"[ZOO: setenv (%s=%s)]\n",mapcs->name,mapcs->value);
1691      fflush(stderr);
1692#endif
1693      mapcs=mapcs->next;
1694    }
1695  }
1696 
1697#ifdef DEBUG
1698  dumpMap(request_inputs);
1699#endif
1700
1701  /**
1702   * Need to check if we need to fork to load a status enabled
1703   */
1704  r_inputs=NULL;
1705  map* store=getMap(request_inputs,"storeExecuteResponse");
1706  map* status=getMap(request_inputs,"status");
1707  /**
1708   * 05-007r7 WPS 1.0.0 page 57 :
1709   * 'If status="true" and storeExecuteResponse is "false" then the service
1710   * shall raise an exception.'
1711   */
1712  if(status!=NULL && strcmp(status->value,"true")==0 && 
1713     store!=NULL && strcmp(store->value,"false")==0){
1714    errorException(m, _("Status cannot be set to true with storeExecuteResponse to false. Please, modify your request parameters."), "InvalidParameterValue");
1715    freeService(&s1);
1716    free(s1);
1717    freeMaps(&m);
1718    free(m);
1719   
1720    freeMaps(&request_input_real_format);
1721    free(request_input_real_format);
1722   
1723    freeMaps(&request_output_real_format);
1724    free(request_output_real_format);
1725   
1726    free(REQUEST);
1727    free(SERVICE_URL);
1728    return 1;
1729  }
1730  r_inputs=getMap(request_inputs,"storeExecuteResponse");
1731  int eres=SERVICE_STARTED;
1732  int cpid=getpid();
1733 
1734  maps *_tmpMaps=(maps*)malloc(MAPS_SIZE);
1735  _tmpMaps->name=strdup("lenv");
1736  char tmpBuff[100];
1737  sprintf(tmpBuff,"%i",cpid);
1738  _tmpMaps->content=createMap("sid",tmpBuff);
1739  _tmpMaps->next=NULL;
1740  addToMap(_tmpMaps->content,"status","0");
1741  addMapsToMaps(&m,_tmpMaps);
1742  freeMaps(&_tmpMaps);
1743  free(_tmpMaps);
1744
1745#ifdef DEBUG
1746  dumpMap(request_inputs);
1747#endif
1748
1749  if(status!=NULL)
1750    if(strcasecmp(status->value,"false")==0)
1751      status=NULL;
1752  if(status==NULLMAP){
1753    loadServiceAndRun(&m,s1,request_inputs,&request_input_real_format,&request_output_real_format,&eres);
1754  }
1755  else{
1756    pid_t   pid;
1757#ifdef DEBUG
1758    fprintf(stderr,"\nPID : %d\n",cpid);
1759#endif
1760
1761#ifndef WIN32
1762    pid = fork ();
1763#else
1764    pid = 0;
1765#endif
1766    if (pid > 0) {
1767      /**
1768       * dady :
1769       * set status to SERVICE_ACCEPTED
1770       */
1771#ifdef DEBUG
1772      fprintf(stderr,"father pid continue (origin %d) %d ...\n",cpid,getpid());
1773#endif
1774      eres=SERVICE_ACCEPTED;
1775    }else if (pid == 0) {
1776      /**
1777       * son : have to close the stdout, stdin and stderr to let the parent
1778       * process answer to http client.
1779       */
1780      r_inputs=getMapFromMaps(m,"main","tmpPath");
1781      map* r_inputs1=getMap(s1->content,"ServiceProvider");
1782      char* fbkp=(char*)malloc((strlen(r_inputs->value)+strlen(r_inputs1->value)+100)*sizeof(char));
1783      sprintf(fbkp,"%s/%s_%d.xml",r_inputs->value,r_inputs1->value,cpid);
1784      char* flog=(char*)malloc((strlen(r_inputs->value)+strlen(r_inputs1->value)+100)*sizeof(char));
1785      sprintf(flog,"%s/%s_%d_error.log",r_inputs->value,r_inputs1->value,cpid);
1786#ifdef DEBUG
1787      fprintf(stderr,"RUN IN BACKGROUND MODE \n");
1788      fprintf(stderr,"son pid continue (origin %d) %d ...\n",cpid,getpid());
1789      fprintf(stderr,"\nFILE TO STORE DATA %s\n",r_inputs->value);
1790#endif
1791      freopen(fbkp , "w+", stdout);
1792      fclose(stdin);
1793      freopen(flog,"w+",stderr);
1794      free(fbkp);
1795      free(flog);
1796      /**
1797       * set status to SERVICE_STARTED and flush stdout to ensure full
1798       * content was outputed (the file used to store the ResponseDocument).
1799       * The rewind stdout to restart writing from the bgining of the file,
1800       * this way the data will be updated at the end of the process run.
1801       */
1802      updateStatus(m);
1803      printProcessResponse(m,request_inputs,cpid,
1804                            s1,r_inputs1->value,SERVICE_STARTED,
1805                            request_input_real_format,
1806                            request_output_real_format);
1807      fflush(stdout);
1808      rewind(stdout);
1809
1810      loadServiceAndRun(&m,s1,request_inputs,&request_input_real_format,&request_output_real_format,&eres);
1811
1812    } else {
1813      /**
1814       * error server don't accept the process need to output a valid
1815       * error response here !!!
1816       */
1817      eres=-1;
1818      errorException(m, _("Unable to run the child process properly"), "InternalError");
1819    }
1820       
1821  }
1822
1823#ifdef DEBUG
1824  dumpMaps(request_output_real_format);
1825  fprintf(stderr,"Function loaded and returned %d\n",eres);
1826  fflush(stderr);
1827#endif
1828  if(eres!=-1)
1829    outputResponse(s1,request_input_real_format,
1830                   request_output_real_format,request_inputs,
1831                   cpid,m,eres);
1832
1833  if(((int)getpid())!=cpid){
1834    fclose(stdout);
1835    fclose(stderr);
1836    unhandleStatus(m);
1837  }
1838
1839  freeService(&s1);
1840  free(s1);
1841  freeMaps(&m);
1842  free(m);
1843 
1844  freeMaps(&request_input_real_format);
1845  free(request_input_real_format);
1846 
1847  freeMaps(&request_output_real_format);
1848  free(request_output_real_format);
1849 
1850  free(REQUEST);
1851  free(SERVICE_URL);
1852#ifdef DEBUG
1853  fprintf(stderr,"Processed response \n");
1854  fflush(stdout);
1855  fflush(stderr);
1856#endif
1857
1858  return 0;
1859}
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