source: branches/prototype-v0/zoo-project/zoo-kernel/server_internal.c @ 862

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

Add the capability to publish heatmap or any templated mapfile using the epecific msInclude and msLayer keys for an output. For MapServer? published output, define 4096 as the default maxsize and use pixel width or height for raster files. use the correct MapServer? imagemode depending on GDALGetRasterDataType (MS_IMAGEMODE_BYTE for GDT_Byte, MS_IMAGEMODE_INT16 for GDT_Int16 and MS_IMAGEMODE_FLOAT32 for GDT_Float32). Create a text file (.maps) listing every mapfiles created for a MapServer? published output (or inputs) using saveMapNames function. Fixes in ulinet, use uuid for naming temporary files. Add dialect input to the ogr2ogr service. Use the .maps file for removing a file from the DeleteData? service

  • Property svn:keywords set to Id
File size: 36.7 KB
Line 
1/*
2 * Author : Gérald Fenoy
3 *
4 *  Copyright 2008-2015 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#include "server_internal.h"
26#include "service_internal.h"
27#include "response_print.h"
28#include "service_callback.h"
29#include "mimetypes.h"
30#ifndef WIN32
31#include <dlfcn.h>
32#include <uuid/uuid.h>
33#else
34#include <rpc.h>
35#define ERROR_MSG_MAX_LENGTH 1024
36#endif
37#include <signal.h>
38
39// #include <stdlib.h>
40/*
41 * Compare two file path strings to see if they refer to the same file.
42 *
43 * @param path1 the first file path
44 * @param path2 the second file path
45 *
46 * @return 0 if the files are identical
47 */
48#define PATHBUFSIZE 4096
49int zoo_path_compare(char* path1, char* path2) {
50
51  if (path1 == NULL || path2 == NULL) {
52    return -1;
53  }
54
55  char realpath1[PATHBUFSIZE];
56  char realpath2[PATHBUFSIZE];
57
58#ifdef WIN32
59  int res1 = GetFullPathName(path1, PATHBUFSIZE, realpath1, NULL);
60  int res2 = GetFullPathName(path2, PATHBUFSIZE, realpath2, NULL);
61
62  if (res1 == 0 || res2 == 0) {
63    return -1;
64  }
65  else {
66    return strncasecmp(realpath1, realpath2, PATHBUFSIZE);
67  }
68#else
69  char* ptr1 = realpath(path1, realpath1);
70  char* ptr2 = realpath(path2, realpath2);
71
72  if (ptr1 == NULL || ptr2 == NULL) {
73    return -1;
74  }
75  else {
76    return strncmp(realpath1, realpath2, PATHBUFSIZE);
77  }
78#endif
79}
80
81/**
82 * Detect WPS version used (1.0.0 or 2.0.0).
83 *
84 * @param version number as char* (1.0.0 or 2.0.0)
85 * @return 0 in case of version 1.0.0, 1 for 2.0.0, -1 in other case
86 */
87int getVersionId(const char* version){
88  int schemaId=0;
89  for(;schemaId<2;schemaId++){
90    if(strncasecmp(version,schemas[schemaId][0],5)==0)
91      return schemaId;
92  }
93  return -1;
94}
95
96/**
97 * Generate a UUID.
98 * ref: https://www.ietf.org/rfc/rfc4122.txt / 4.2
99 *
100 * @return a new char* containing the UUID, make sure to free the returned
101 *  resource once used.
102 */
103char *get_uuid(){
104  char *res=(char*)malloc(37*sizeof(char));
105#ifdef WIN32
106  UUID uuid;
107  UuidCreate(&uuid);
108  RPC_CSTR rest = NULL;
109  UuidToString(&uuid,&rest);
110#else
111  uuid_t uuid;
112  uuid_generate_time(uuid);
113  char rest[128];
114  uuid_unparse(uuid,rest);
115#endif
116  sprintf(res,"%s",rest);
117#ifdef WIN32
118  RpcStringFree(&rest);
119#endif
120  return res;
121}
122
123/**
124 * Extract the service identifier from the full service identifier
125 * ie:
126 *  - Full service name: OTB.BandMath
127 *  - Service name: BandMath
128 *
129 * @param conf the maps containing the settings of the main.cfg file
130 * @param conf_dir the full path to the ZOO-Kernel directory
131 * @param identifier the full service name (potentialy including a prefix, ie:
132 *  Prefix.MyService)
133 * @param buffer the resulting service identifier (without any prefix)
134 */
135void parseIdentifier(maps* conf,char* conf_dir,char *identifier,char* buffer){
136  setMapInMaps(conf,"lenv","oIdentifier",identifier);
137  char *lid=zStrdup(identifier);
138  char *saveptr1;
139  char *tmps1=strtok_r(lid,".",&saveptr1);
140  int level=0;
141  char key[25];
142  char levels[18];
143  while(tmps1!=NULL){
144    char *test=zStrdup(tmps1);
145    char* tmps2=(char*)malloc((strlen(test)+2)*sizeof(char));
146    sprintf(key,"sprefix_%d",level);
147    sprintf(tmps2,"%s.",test);
148    sprintf(levels,"%d",level);
149    setMapInMaps(conf,"lenv","level",levels);
150    setMapInMaps(conf,"lenv",key,tmps2);
151    free(tmps2);
152    free(test);
153    level++;
154    tmps1=strtok_r(NULL,".",&saveptr1);
155  }
156  int i=0;
157  sprintf(buffer,"%s",conf_dir);
158  for(i=0;i<level;i++){
159    char *tmp0=zStrdup(buffer);
160    sprintf(key,"sprefix_%d",i);
161    map* tmp00=getMapFromMaps(conf,"lenv",key);
162    if(tmp00!=NULL)
163      sprintf(buffer,"%s/%s",tmp0,tmp00->value);
164    free(tmp0);
165    buffer[strlen(buffer)-1]=0;
166    if(i+1<level){ 
167      #ifdef IGNORE_METAPATH
168        map* tmpMap = createMap("metapath", "");
169      #else 
170        map* tmpMap=getMapFromMaps(conf,"lenv","metapath");
171      #endif     
172      if(tmpMap==NULL || strlen(tmpMap->value)==0){
173        char *tmp01=zStrdup(tmp00->value);
174        tmp01[strlen(tmp01)-1]=0;
175        setMapInMaps(conf,"lenv","metapath",tmp01);
176        free(tmp01);
177        tmp01=NULL;
178      }
179      else{
180        if(tmp00!=NULL && tmpMap!=NULL){
181          char *tmp00s=zStrdup(tmp00->value);
182          tmp00s[strlen(tmp00s)-1]=0;
183          char *value=(char*)malloc((strlen(tmp00s)+strlen(tmpMap->value)+2)*sizeof(char));
184          sprintf(value,"%s/%s",tmpMap->value,tmp00s);
185          setMapInMaps(conf,"lenv","metapath",value);
186          free(value);
187          free(tmp00s);
188          value=NULL;
189        }
190      }
191    }else{
192      char *tmp01=zStrdup(tmp00->value);
193      tmp01[strlen(tmp01)-1]=0;
194      setMapInMaps(conf,"lenv","Identifier",tmp01);
195      free(tmp01);
196    }
197  }
198  char *tmp0=zStrdup(buffer);
199  sprintf(buffer,"%s.zcfg",tmp0);
200  free(tmp0);
201  free(lid);
202}
203
204/**
205 * Converts a hex character to its integer value
206 *
207 * @param ch the char to convert
208 * @return the converted char
209 */
210char from_hex(char ch) {
211  return isdigit(ch) ? ch - '0' : tolower(ch) - 'a' + 10;
212}
213
214/**
215 * Converts an integer value to its hec character
216 *
217 * @param code the char to convert
218 * @return the converted char
219 */
220char to_hex(char code) {
221  static char hex[] = "0123456789abcdef";
222  return hex[code & 15];
223}
224
225/**
226 * URLEncode an url
227 *
228 * @param str the url to encode
229 * @return a url-encoded version of str
230 * @warning be sure to free() the returned string after use
231 */
232char *url_encode(char *str) {
233  char *pstr = str, *buf = (char*) malloc(strlen(str) * 3 + 1), *pbuf = buf;
234  while (*pstr) {
235    if (isalnum(*pstr) || *pstr == '-' || *pstr == '_' || *pstr == '.' || *pstr == '~') 
236      *pbuf++ = *pstr;
237    else if (*pstr == ' ') 
238      *pbuf++ = '+';
239    else 
240      *pbuf++ = '%', *pbuf++ = to_hex(*pstr >> 4), *pbuf++ = to_hex(*pstr & 15);
241    pstr++;
242  }
243  *pbuf = '\0';
244  return buf;
245}
246
247/**
248 * Decode an URLEncoded url
249 *
250 * @param str the URLEncoded url to decode
251 * @return a url-decoded version of str
252 * @warning be sure to free() the returned string after use
253 */
254char *url_decode(char *str) {
255  char *pstr = str, *buf = (char*) malloc(strlen(str) + 1), *pbuf = buf;
256  while (*pstr) {
257    if (*pstr == '%') {
258      if (pstr[1] && pstr[2]) {
259        *pbuf++ = from_hex(pstr[1]) << 4 | from_hex(pstr[2]);
260        pstr += 2;
261      }
262    } else if (*pstr == '+') { 
263      *pbuf++ = ' ';
264    } else {
265      *pbuf++ = *pstr;
266    }
267    pstr++;
268  }
269  *pbuf = '\0';
270  return buf;
271}
272
273/**
274 * Verify if a given language is listed in the lang list defined in the [main]
275 * section of the main.cfg file.
276 *
277 * @param conf the map containing the settings from the main.cfg file
278 * @param str the specific language
279 * @return 1 if the specific language is listed, -1 in other case.
280 */
281int isValidLang(maps* conf,const char *str){
282  map *tmpMap=getMapFromMaps(conf,"main","language");
283  char *tmp0=NULL,*tmp=NULL,*tmp1=NULL;
284  if(tmpMap!=NULL)
285    tmp0=zStrdup(tmpMap->value);
286  tmpMap=getMapFromMaps(conf,"main","lang");
287  if(tmpMap!=NULL)
288    tmp=zStrdup(tmpMap->value);
289  if(tmp0!=NULL && tmp!=NULL){
290    tmp1=(char*)malloc((strlen(tmp0)+strlen(tmp)+2)*sizeof(char));
291    sprintf(tmp1,"%s,%s",tmp0,tmp);
292    free(tmp0);
293    free(tmp);
294  }else{
295    if(tmp!=NULL){
296      tmp1=zStrdup(tmp);
297      free(tmp);
298    }else{
299      if(tmp0!=NULL){
300        tmp1=zStrdup(tmp0);
301        free(tmp0);
302      }
303    }
304  }
305  char *pToken,*saveptr;
306  pToken=strtok_r(tmp1,",",&saveptr);
307  int res=-1;
308  while(pToken!=NULL){
309    if(strcasecmp(str,pToken)==0){
310      res=1;
311      break;
312    }
313    pToken=strtok_r(NULL,",",&saveptr);
314  }
315  if(tmp1!=NULL)
316    free(tmp1);
317  return res;
318}
319
320
321/**
322 * Access the value of the encoding key in a maps
323 *
324 * @param m the maps to search for the encoding key
325 * @return the value of the encoding key in a maps if encoding key exists,
326 *  "UTF-8" in other case.
327 */
328char* getEncoding(maps* m){
329  if(m!=NULL){
330    map* tmp=getMap(m->content,"encoding");
331    if(tmp!=NULL){
332      return tmp->value;
333    }
334    else
335      return (char*)"UTF-8";
336  }
337  else
338    return (char*)"UTF-8"; 
339}
340
341/**
342 * Access the value of the version key in a maps
343 *
344 * @param m the maps to search for the version key
345 * @return the value of the version key in a maps if encoding key exists,
346 *  "1.0.0" in other case.
347 */
348char* getVersion(maps* m){
349  if(m!=NULL){
350    map* tmp=getMap(m->content,"version");
351    if(tmp!=NULL){
352      return tmp->value;
353    }
354    else
355      return (char*)"1.0.0";
356  }
357  else
358    return (char*)"1.0.0";
359}
360
361/**
362 * Read a file generated by a service.
363 *
364 * @param m the conf maps
365 * @param content the output item
366 * @param filename the file to read
367 */
368void readGeneratedFile(maps* m,map* content,char* filename){
369  FILE * file=fopen(filename,"rb");
370  if(file==NULL){
371    setMapInMaps(m,"lenv","message","Unable to read produced file. Please try again later");
372    return ;
373  }
374  fseek(file, 0, SEEK_END);
375  long count = ftell(file);
376  rewind(file);
377  struct stat file_status; 
378  stat(filename, &file_status);
379  if(getMap(content,"storage")==NULL){
380    map* tmpMap1=getMap(content,"value");
381    if(tmpMap1==NULL){
382      addToMap(content,"value","");
383      tmpMap1=getMap(content,"value");
384    }
385    free(tmpMap1->value);
386    tmpMap1->value=(char*) malloc((count+1)*sizeof(char));
387    if(tmpMap1->value==NULL){
388      setMapInMaps(m,"lenv","message","Unable to allocate the memory required to read the produced file.");
389    }
390    fread(tmpMap1->value,1,count,file);
391    tmpMap1->value[count]=0;
392  }
393  fclose(file);
394  char rsize[1000];
395  sprintf(rsize,"%ld",count);
396  addToMap(content,"size",rsize);
397}
398
399
400/**
401 * Write a file from value and length
402 *
403 * @param fname the file name
404 * @param val the value
405 * @param length the value length
406 */
407int writeFile(char* fname,char* val,int length){
408  FILE* of=fopen(fname,"wb");
409  if(of==NULL){
410    return -1;
411  }
412  size_t ret=fwrite(val,sizeof(char),length,of);
413  if(ret<length){
414    fprintf(stderr,"Write error occurred!\n");
415    fclose(of);
416    return -1;
417  }
418  fclose(of);
419  return 1;
420}
421
422/**
423 * Dump all values in a maps as files
424 *
425 * @param main_conf the maps containing the settings of the main.cfg file
426 * @param in the maps containing values to dump as files
427 */
428void dumpMapsValuesToFiles(maps** main_conf,maps** in){
429  map* tmpPath=getMapFromMaps(*main_conf,"main","tmpPath");
430  map* tmpUrl=getMapFromMaps(*main_conf,"main","tmpUrl");
431  map* tmpSid=getMapFromMaps(*main_conf,"lenv","usid");
432  maps* inputs=*in;
433  int length=0;
434  while(inputs!=NULL){
435    if(getMap(inputs->content,"mimeType")!=NULL &&
436       getMap(inputs->content,"cache_file")==NULL){
437      map* cMap=inputs->content;
438      if(getMap(cMap,"length")!=NULL){
439        map* tmpLength=getMap(cMap,"length");
440        int len=atoi(tmpLength->value);
441        int k=0;
442        for(k=0;k<len;k++){
443          map* cMimeType=getMapArray(cMap,"mimeType",k);
444          map* cValue=getMapArray(cMap,"value",k);
445          map* cSize=getMapArray(cMap,"size",k);
446          char file_ext[32];
447          getFileExtension(cMimeType != NULL ? cMimeType->value : NULL, file_ext, 32);
448          char* val=(char*)malloc((strlen(tmpPath->value)+strlen(inputs->name)+strlen(tmpSid->value)+strlen(file_ext)+16)*sizeof(char));
449          sprintf(val,"%s/Input_%s_%s_%d.%s",tmpPath->value,inputs->name,tmpSid->value,k,file_ext);
450          length=0;
451          if(cSize!=NULL){
452            length=atoi(cSize->value);
453          }else
454            length=strlen(cValue->value);
455          writeFile(val,cValue->value,length);
456          setMapArray(cMap,"cache_file",k,val);
457          free(val);
458          val=(char*)malloc((strlen(tmpUrl->value)+strlen(inputs->name)+strlen(tmpSid->value)+strlen(file_ext)+16)*sizeof(char));
459          sprintf(val,"%s/Input_%s_%s_%d.%s",tmpUrl->value,inputs->name,tmpSid->value,k,file_ext);
460          setMapArray(cMap,"cache_url",k,val);
461          setMapArray(cMap,"byValue",k,"true");
462          free(val);
463        }
464      }else{
465        int length=0;
466        map* cMimeType=getMap(cMap,"mimeType");
467        map* cValue=getMap(cMap,"value");
468        map* cSize=getMap(cMap,"size");
469        char file_ext[32];
470        getFileExtension(cMimeType != NULL ? cMimeType->value : NULL, file_ext, 32);
471        char *val=(char*)malloc((strlen(tmpPath->value)+strlen(inputs->name)+strlen(tmpSid->value)+strlen(file_ext)+16)*sizeof(char));
472        sprintf(val,"%s/Input_%s_%s_%d.%s",tmpPath->value,inputs->name,tmpSid->value,0,file_ext);
473        if(cSize!=NULL){
474          length=atoi(cSize->value);
475        }else
476          length=strlen(cValue->value);
477        writeFile(val,cValue->value,length);
478        addToMap(cMap,"cache_file",val);
479        free(val);
480        val=(char*)malloc((strlen(tmpUrl->value)+strlen(inputs->name)+strlen(tmpSid->value)+strlen(file_ext)+16)*sizeof(char));
481        sprintf(val,"%s/Input_%s_%s_%d.%s",tmpUrl->value,inputs->name,tmpSid->value,0,file_ext);
482        addToMap(cMap,"cache_url",val);
483        addToMap(cMap,"byValue",val);
484        free(val);
485      }
486    }
487    inputs=inputs->next;
488  }
489}
490
491
492/**
493 * Base64 encoding of a char*
494 *
495 * @param input the value to encode
496 * @param length the value length
497 * @return the buffer containing the base64 value
498 * @warning make sure to free the returned value
499 */
500char *base64(const char *input, int length)
501{
502  BIO *bmem, *b64;
503  BUF_MEM *bptr;
504
505  b64 = BIO_new(BIO_f_base64());
506  BIO_set_flags(b64, BIO_FLAGS_BASE64_NO_NL);
507  bmem = BIO_new(BIO_s_mem());
508  b64 = BIO_push(b64, bmem);
509  BIO_write(b64, input, length);
510  BIO_flush(b64);
511  BIO_get_mem_ptr(b64, &bptr);
512
513  char *buff = (char *)malloc((bptr->length+1)*sizeof(char));
514  memcpy(buff, bptr->data, bptr->length);
515  buff[bptr->length] = 0;
516
517  BIO_free_all(b64);
518
519  return buff;
520}
521
522/**
523 * Base64 decoding of a char*
524 *
525 * @param input the value to decode
526 * @param length the value length
527 * @param red the value length
528 * @return the buffer containing the base64 value
529 * @warning make sure to free the returned value
530 */
531char *base64d(const char *input, int length,int* red)
532{
533  BIO *b64, *bmem;
534
535  char *buffer = (char *)malloc(length);
536  if(buffer){
537    memset(buffer, 0, length);
538    b64 = BIO_new(BIO_f_base64());
539    if(b64){
540      bmem = BIO_new_mem_buf((unsigned char*)input,length);
541      bmem = BIO_push(b64, bmem);
542      *red=BIO_read(bmem, buffer, length);
543      buffer[length-1]=0;
544      BIO_free_all(bmem);
545    }
546  }
547  return buffer;
548}
549
550/**
551 * Read Base64 value and split it value by lines of 64 char.
552 *
553 * @param in the map containing the value to split
554 */
555void readBase64(map **in){
556  char *res = NULL;
557  char *curs = (*in)->value;
558  int i = 0;
559  for (i = 0; i <= strlen ((*in)->value) / 64;
560       i++)
561    {
562      if (res == NULL)
563        res =
564          (char *) malloc (65 * sizeof (char));
565      else
566        res =
567          (char *) realloc (res,
568                            (((i + 1) * 65) +
569                             i) * sizeof (char));
570      int csize = i * 65;
571      strncpy (res + csize, curs, 64);
572      if (i == strlen ((*in)->value) / 64)
573        strcat (res, "\n\0");
574      else
575        {
576          strncpy (res + (((i + 1) * 64) + i),
577                   "\n\0", 2);
578          curs += 64;
579        }
580    }
581  free ((*in)->value);
582  (*in)->value = zStrdup (res);
583  free (res);
584}
585
586
587/**
588 * Add the default values defined in the zcfg to a maps.
589 *
590 * @param out the maps containing the inputs or outputs given in the initial
591 *  HTTP request
592 * @param in the description of all inputs or outputs available for a service
593 * @param m the maps containing the settings of the main.cfg file
594 * @param type 0 for inputs and 1 for outputs
595 * @param err the map to store potential missing mandatory input parameters or
596 *  wrong output names depending on the type.
597 * @return "" if no error was detected, the name of last input or output causing
598 *  an error.
599 */
600char* addDefaultValues(maps** out,elements* in,maps* m,int type,map** err){
601  map *res=*err;
602  elements* tmpInputs=in;
603  elements* tmpInputss=NULL;
604  maps* out1=*out;
605  maps* out1s=NULL;
606  char *result=NULL;
607  int nb=0;
608  int inb=0;
609 loopOnInputs:
610  if(type==1){
611    while(out1!=NULL){
612      if(getElements(in,out1->name)==NULL){
613        if(res==NULL){
614          res=createMap("value",out1->name);
615        }else{
616          setMapArray(res,"value",nb,out1->name);
617        }
618        nb++;
619        result=out1->name;
620      }
621      inb++;
622      out1=out1->next;
623    }
624    if(res!=NULL){
625      fflush(stderr);
626      *err=res;
627      return result;
628    }
629    if(out1==NULL && inb>=1)
630      out1=*out;
631  }
632  while(tmpInputs!=NULL){
633    maps *tmpMaps=getMaps(out1,tmpInputs->name);
634    if(tmpMaps==NULL){
635      maps* tmpMaps2=createMaps(tmpInputs->name);
636      if(type==0){
637        map* tmpMapMinO=getMap(tmpInputs->content,"minOccurs");
638        if(tmpMapMinO!=NULL){
639          if(atoi(tmpMapMinO->value)>=1){
640            freeMaps(&tmpMaps2);
641            free(tmpMaps2);
642            if(res==NULL){
643              res=createMap("value",tmpInputs->name);
644            }else{
645              setMapArray(res,"value",nb,tmpInputs->name);
646            }
647            nb++;
648            result=tmpInputs->name;
649          }
650          else{
651            if(tmpMaps2->content==NULL)
652              tmpMaps2->content=createMap("minOccurs",tmpMapMinO->value);
653            else
654              addToMap(tmpMaps2->content,"minOccurs",tmpMapMinO->value);
655          }
656        }
657        if(res==NULL){
658          map* tmpMaxO0=getMap(tmpInputs->content,"useMapserver");
659          if(tmpMaxO0!=NULL){
660            if(tmpMaps2->content==NULL)
661              tmpMaps2->content=createMap("useMapserver",tmpMaxO0->value);
662            else
663              addToMap(tmpMaps2->content,"useMapserver",tmpMaxO0->value);
664          }
665          map* tmpMaxO=getMap(tmpInputs->content,"maxOccurs");
666          if(tmpMaxO!=NULL){
667            if(tmpMaps2->content==NULL)
668              tmpMaps2->content=createMap("maxOccurs",tmpMaxO->value);
669            else
670              addToMap(tmpMaps2->content,"maxOccurs",tmpMaxO->value);
671          }
672          map* tmpMaxMB=getMap(tmpInputs->content,"maximumMegabytes");
673          if(tmpMaxMB!=NULL){
674            if(tmpMaps2->content==NULL)
675              tmpMaps2->content=createMap("maximumMegabytes",tmpMaxMB->value);
676            else
677              addToMap(tmpMaps2->content,"maximumMegabytes",tmpMaxMB->value);
678          }
679        }
680      }
681     
682      if(res==NULL){
683        iotype* tmpIoType=tmpInputs->defaults;
684        if(tmpIoType!=NULL){
685          map* tmpm=tmpIoType->content;
686          while(tmpm!=NULL){
687            if(tmpMaps2->content==NULL)
688              tmpMaps2->content=createMap(tmpm->name,tmpm->value);
689            else{
690              addToMap(tmpMaps2->content,tmpm->name,tmpm->value);
691            }
692            tmpm=tmpm->next;
693          }
694        }
695        if(tmpMaps2->content==NULL){
696          tmpMaps2->content=createMap("inRequest","false");
697          dumpMaps(tmpMaps2);
698        }
699        else
700          addToMap(tmpMaps2->content,"inRequest","false");
701        if(type==0){
702          map *tmpMap=getMap(tmpMaps2->content,"value");
703          if(tmpMap==NULL)
704            addToMap(tmpMaps2->content,"value","NULL");
705        }
706        elements* tmpElements=getElements(in,tmpMaps2->name);
707        if(tmpElements!=NULL && tmpElements->child!=NULL){
708          char *res=addDefaultValues(&tmpMaps2->child,tmpElements->child,m,type,err);
709          if(strlen(res)>0){
710            return res;
711          }
712        }
713
714        if(out1==NULL){
715          *out=dupMaps(&tmpMaps2);
716          out1=*out;
717        }
718        else
719          addMapsToMaps(&out1,tmpMaps2);
720        freeMap(&tmpMaps2->content);
721        free(tmpMaps2->content);
722        tmpMaps2->content=NULL;
723        freeMaps(&tmpMaps2);
724        free(tmpMaps2);
725        tmpMaps2=NULL;
726      }
727    }
728    else /*toto*/{ 
729      iotype* tmpIoType=NULL;
730      if(tmpMaps->content!=NULL){
731        tmpIoType=getIoTypeFromElement(tmpInputs,tmpInputs->name,
732                                       tmpMaps->content);
733        if(type==0) {
734          /**
735           * In case of an Input maps, then add the minOccurs and maxOccurs to the
736           * content map.
737           */
738          char* keys[4]={
739            "minOccurs",
740            "maxOccurs",
741            "maximumMegabytes",
742            "useMapserver"
743          };
744          int i=0;
745          for(i=0;i<4;i++){
746            map* tmpMap1=getMap(tmpInputs->content,keys[i]);
747            if(tmpMap1!=NULL){
748              addToMap(tmpMaps->content,keys[i],tmpMap1->value);
749            }
750          }
751          /**
752           * Parsing BoundingBoxData, fill the following map and then add it to
753           * the content map of the Input maps:
754           * lowerCorner, upperCorner, srs and dimensions
755           * cf. parseBoundingBox
756           */
757          if(tmpInputs->format!=NULL && strcasecmp(tmpInputs->format,"BoundingBoxData")==0){
758            maps* tmpI=getMaps(*out,tmpInputs->name);
759            if(tmpI!=NULL){
760              map* tmpV=getMap(tmpI->content,"value");
761              if(tmpV!=NULL){
762                char *tmpVS=strdup(tmpV->value);
763                map* tmp=parseBoundingBox(tmpVS);
764                free(tmpVS);
765                map* tmpC=tmp;
766                while(tmpC!=NULL){
767                  addToMap(tmpMaps->content,tmpC->name,tmpC->value);
768                  tmpC=tmpC->next;
769                }
770                freeMap(&tmp);
771                free(tmp);
772              }
773            }
774          }
775        }
776      }else{
777        if(tmpInputs!=NULL){
778          tmpIoType=tmpInputs->defaults;
779        }
780      }
781
782      if(tmpIoType!=NULL){
783        map* tmpContent=tmpIoType->content;
784        map* cval=NULL;
785        int hasPassed=-1;
786        while(tmpContent!=NULL){
787          if((cval=getMap(tmpMaps->content,tmpContent->name))==NULL){
788#ifdef DEBUG
789            fprintf(stderr,"addDefaultValues %s => %s\n",tmpContent->name,tmpContent->value);
790#endif
791            if(tmpMaps->content==NULL)
792              tmpMaps->content=createMap(tmpContent->name,tmpContent->value);
793            else
794              addToMap(tmpMaps->content,tmpContent->name,tmpContent->value);
795           
796            if(hasPassed<0 && type==0 && getMap(tmpMaps->content,"isArray")!=NULL){
797              map* length=getMap(tmpMaps->content,"length");
798              int i;
799              char *tcn=strdup(tmpContent->name);
800              for(i=1;i<atoi(length->value);i++){
801#ifdef DEBUG
802                dumpMap(tmpMaps->content);
803                fprintf(stderr,"addDefaultValues %s_%d => %s\n",tcn,i,tmpContent->value);
804#endif
805                int len=strlen((char*) tcn);
806                char *tmp1=(char *)malloc((len+10)*sizeof(char));
807                sprintf(tmp1,"%s_%d",tcn,i);
808#ifdef DEBUG
809                fprintf(stderr,"addDefaultValues %s => %s\n",tmp1,tmpContent->value);
810#endif
811                addToMap(tmpMaps->content,tmp1,tmpContent->value);
812                free(tmp1);
813                hasPassed=1;
814              }
815              free(tcn);
816            }
817          }
818          tmpContent=tmpContent->next;
819        }
820#ifdef USE_MS
821        /**
822         * check for useMapServer presence
823         */
824        if(tmpIoType!=NULL){
825          map* tmpCheck=getMap(tmpIoType->content,"useMapserver");
826          if(tmpCheck!=NULL && strncasecmp(tmpCheck->value,"true",4)==0){
827            // Get the default value
828            addToMap(tmpMaps->content,"useMapserver","true");
829            tmpIoType=getIoTypeFromElement(tmpInputs,tmpInputs->name,NULL);
830            tmpCheck=getMap(tmpMaps->content,"mimeType");
831            addToMap(tmpMaps->content,"requestedMimeType",tmpCheck->value);
832            map* cursor=tmpIoType->content;
833            while(cursor!=NULL){
834              addToMap(tmpMaps->content,cursor->name,cursor->value);
835              cursor=cursor->next;
836            }
837         
838            cursor=tmpInputs->content;
839            while(cursor!=NULL){
840              if(strcasecmp(cursor->name,"Title")==0 ||
841                 strcasecmp(cursor->name,"Abstract")==0)
842                addToMap(tmpMaps->content,cursor->name,cursor->value);
843              cursor=cursor->next;
844            }
845          }
846        }
847#endif
848      }
849      if(tmpMaps->content==NULL)
850        tmpMaps->content=createMap("inRequest","true");
851      else
852        addToMap(tmpMaps->content,"inRequest","true");
853      elements* tmpElements=getElements(in,tmpMaps->name);
854      if(/*tmpMaps->child!=NULL && */tmpElements!=NULL && tmpElements->child!=NULL){
855        char *res=addDefaultValues(&tmpMaps->child,tmpElements->child,m,type,err);
856        if(strlen(res)>0){
857          return res;
858        }
859      }
860    }
861    if(tmpInputs->child!=NULL){
862      tmpInputss=tmpInputs->next;
863      tmpInputs=tmpInputs->child;
864      if(tmpMaps!=NULL){
865        out1=tmpMaps->child;
866        out1s=tmpMaps;
867      }
868    }
869    tmpInputs=tmpInputs->next;
870  }
871  if(tmpInputss!=NULL){
872    out1=out1s;
873    tmpInputs=tmpInputss;
874    tmpInputss=NULL;
875    out1s=NULL;
876    goto loopOnInputs;
877  }
878  if(res!=NULL){
879    *err=res;
880    return result;
881  }
882  return "";
883}
884
885/**
886 * Access the last error message returned by the OS when trying to dynamically
887 * load a shared library.
888 *
889 * @return the last error message
890 * @warning The character string returned from getLastErrorMessage resides
891 * in a static buffer. The application should not write to this
892 * buffer or attempt to free() it.
893 */ 
894char* getLastErrorMessage() {                                             
895#ifdef WIN32
896  LPVOID lpMsgBuf;
897  DWORD errCode = GetLastError();
898  static char msg[ERROR_MSG_MAX_LENGTH];
899  size_t i;
900 
901  DWORD length = FormatMessage(
902                               FORMAT_MESSAGE_ALLOCATE_BUFFER | 
903                               FORMAT_MESSAGE_FROM_SYSTEM |
904                               FORMAT_MESSAGE_IGNORE_INSERTS,
905                               NULL,
906                               errCode,
907                               MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
908                               (LPTSTR) &lpMsgBuf,
909                               0, NULL );       
910 
911#ifdef UNICODE         
912  wcstombs_s( &i, msg, ERROR_MSG_MAX_LENGTH,
913              (wchar_t*) lpMsgBuf, _TRUNCATE );
914#else
915  strcpy_s( msg, ERROR_MSG_MAX_LENGTH,
916            (char *) lpMsgBuf );               
917#endif 
918  LocalFree(lpMsgBuf);
919
920  return msg;
921#else
922  return dlerror();
923#endif
924}
925
926#include <dirent.h>
927#ifndef RELY_ON_DB
928/**
929 * Read the Result file (.res).
930 *
931 * @param conf the maps containing the setting of the main.cfg file
932 * @param pid the service identifier (usid key from the [lenv] section)
933 */
934void readFinalRes(maps* conf,char* pid,map* statusInfo){
935  map* r_inputs = getMapFromMaps (conf, "main", "tmpPath");
936  char* fbkpid =
937    (char *)
938    malloc ((strlen (r_inputs->value) + strlen (pid) + 7) * sizeof (char));
939  sprintf (fbkpid, "%s/%s.res", r_inputs->value, pid);
940  struct stat file_status;
941  int istat = stat (fbkpid, &file_status);
942  if (istat == 0 && file_status.st_size > 0)
943    {
944      maps *res = (maps *) malloc (MAPS_SIZE);
945      conf_read (fbkpid, res);
946      res->child=NULL;
947      map* status=getMapFromMaps(res,"status","status");
948      addToMap(statusInfo,"Status",status->value);
949      freeMaps(&res);
950      free(res);
951    }
952  else
953    addToMap(statusInfo,"Status","Failed"); 
954  free(fbkpid);
955}
956
957/**
958 * Check if a service is running.
959 *
960 * @param conf the maps containing the setting of the main.cfg file
961 * @param pid the unique service identifier (usid from the lenv section)
962 * @return 1 in case the service is still running, 0 otherwise
963 */
964int isRunning(maps* conf,char* pid){
965  int res=0;
966  map* r_inputs = getMapFromMaps (conf, "main", "tmpPath");
967  char* fbkpid =
968    (char *)
969    malloc ((strlen (r_inputs->value) + strlen (pid) + 7) * sizeof (char));
970  sprintf (fbkpid, "%s/%s.pid", r_inputs->value, pid);
971  FILE* f0 = fopen (fbkpid, "r");
972  if(f0!=NULL){
973    fclose(f0);
974    res=1;
975  }
976  free(fbkpid);
977  return res;
978}
979#else
980#include "sqlapi.h"
981#endif
982
983/**
984 * Run GetStatus requests.
985 *
986 * @param conf the maps containing the setting of the main.cfg file
987 * @param pid the service identifier (usid key from the [lenv] section)
988 * @param req the request (GetStatus / GetResult)
989 */
990void runGetStatus(maps* conf,char* pid,char* req){
991  map* r_inputs = getMapFromMaps (conf, "main", "tmpPath");
992  char *sid=getStatusId(conf,pid);
993  if(sid==NULL){
994    errorException (conf, _("The JobID from the request does not match any of the Jobs running on this server"),
995                    "NoSuchJob", pid);
996  }else{
997    map* statusInfo=createMap("JobID",pid);
998    if(isRunning(conf,pid)>0){
999      if(strncasecmp(req,"GetResult",strlen(req))==0){
1000        errorException (conf, _("The result for the requested JobID has not yet been generated. The service is currently running."),
1001                        "ResultNotReady", pid);
1002        return;
1003      }
1004      else
1005        if(strncasecmp(req,"GetStatus",strlen(req))==0){
1006          addToMap(statusInfo,"Status","Running");
1007          char* tmpStr=_getStatus(conf,pid);
1008          if(tmpStr!=NULL && strncmp(tmpStr,"-1",2)!=0){
1009            char *tmpStr1=strdup(tmpStr);
1010            char *tmpStr0=strdup(strstr(tmpStr,"|")+1);
1011            free(tmpStr);
1012            tmpStr1[strlen(tmpStr1)-strlen(tmpStr0)-1]='\0';
1013            addToMap(statusInfo,"PercentCompleted",tmpStr1);
1014            addToMap(statusInfo,"Message",tmpStr0);
1015            free(tmpStr0);
1016            free(tmpStr1);
1017          }
1018        }
1019    }
1020    else{
1021      if(strncasecmp(req,"GetResult",strlen(req))==0){
1022        char* result=_getStatusFile(conf,pid);
1023        if(result!=NULL){
1024          char *encoding=getEncoding(conf);
1025          printf("Content-Type: text/xml; charset=%s\r\nStatus: 200 OK\r\n\r\n",encoding);
1026          printf("%s",result);
1027          fflush(stdout);
1028          free(sid);
1029          freeMap(&statusInfo);
1030          free(statusInfo);
1031          free(result);
1032          return;
1033        }else{
1034          errorException (conf, _("The result for the requested JobID has not yet been generated. The service ends but it still needs to produce the outputs."),
1035                          "ResultNotReady", pid);
1036          freeMap(&statusInfo);
1037          free(statusInfo);
1038          return;
1039        }
1040      }else
1041        if(strncasecmp(req,"GetStatus",strlen(req))==0){
1042          readFinalRes(conf,pid,statusInfo);
1043          char* tmpStr=_getStatus(conf,pid);
1044          if(tmpStr!=NULL && strncmp(tmpStr,"-1",2)!=0){
1045            char *tmpStr1=strdup(tmpStr);
1046            char *tmpStr0=strdup(strstr(tmpStr,"|")+1);
1047            free(tmpStr);
1048            tmpStr1[strlen(tmpStr1)-strlen(tmpStr0)-1]='\0';
1049            addToMap(statusInfo,"PercentCompleted",tmpStr1);
1050            addToMap(statusInfo,"Message",tmpStr0);
1051            free(tmpStr0);
1052            free(tmpStr1);
1053          }
1054        }
1055    }
1056    free(sid);
1057    printStatusInfo(conf,statusInfo,req);
1058    freeMap(&statusInfo);
1059    free(statusInfo);
1060  }
1061  return;
1062}
1063
1064/**
1065 * Run Dismiss requests.
1066 *
1067 * @param conf the maps containing the setting of the main.cfg file
1068 * @param pid the service identifier (usid key from the [lenv] section)
1069 */
1070void runDismiss(maps* conf,char* pid){
1071  map* r_inputs = getMapFromMaps (conf, "main", "tmpPath");
1072  char *sid=getStatusId(conf,pid);
1073  if(sid==NULL){
1074    errorException (conf, _("The JobID from the request does not match any of the Jobs running on this server"),
1075                    "NoSuchJob", pid);
1076  }else{
1077    // We should send the Dismiss request to the target host if it differs
1078    char* fbkpid =
1079      (char *)
1080      malloc ((strlen (r_inputs->value) + strlen (pid) + 7) * sizeof (char));
1081    sprintf (fbkpid, "%s/%s.pid", r_inputs->value, pid);
1082    FILE* f0 = fopen (fbkpid, "r");
1083    if(f0!=NULL){
1084      long flen;
1085      char *fcontent;
1086      fseek (f0, 0, SEEK_END);
1087      flen = ftell (f0);
1088      fseek (f0, 0, SEEK_SET);
1089      fcontent = (char *) malloc ((flen + 1) * sizeof (char));
1090      fread(fcontent,flen,1,f0);
1091      fcontent[flen]=0;
1092      fclose(f0);
1093#ifndef WIN32
1094      kill(atoi(fcontent),SIGKILL);
1095#else
1096      HANDLE myZooProcess=OpenProcess(PROCESS_ALL_ACCESS,false,atoi(fcontent));
1097      TerminateProcess(myZooProcess,1);
1098      CloseHandle(myZooProcess);
1099#endif
1100      free(fcontent);
1101    }
1102    free(fbkpid);
1103    struct dirent *dp;
1104    DIR *dirp = opendir(r_inputs->value);
1105    char fileName[1024];
1106    int hasFile=-1;
1107    if(dirp!=NULL){
1108      while ((dp = readdir(dirp)) != NULL){
1109#ifdef DEBUG
1110        fprintf(stderr,"File : %s searched : %s\n",dp->d_name,tmp);
1111#endif
1112        if(strstr(dp->d_name,pid)!=0){
1113          sprintf(fileName,"%s/%s",r_inputs->value,dp->d_name);
1114          if(unlink(fileName)!=0){
1115            errorException (conf, 
1116                            _("The job cannot be removed, a file cannot be removed"),
1117                            "NoApplicableCode", NULL);
1118            return;
1119          }
1120        }
1121      }
1122    }
1123#ifdef RELY_ON_DB
1124    removeService(conf,pid);
1125#endif
1126    /* No need to call 7_1 when an execution is dismissed.
1127      fprintf(stderr,"************************* %s %d \n\n",__FILE__,__LINE__);
1128      invokeCallback(conf,NULL,NULL,7,1);
1129      fprintf(stderr,"************************* %s %d \n\n",__FILE__,__LINE__);
1130    */
1131    map* statusInfo=createMap("JobID",pid);
1132    addToMap(statusInfo,"Status","Dismissed");
1133    printStatusInfo(conf,statusInfo,"Dismiss");
1134    free(statusInfo);
1135  }
1136  return;
1137}
1138
1139extern int getServiceFromFile (maps *, const char *, service **);
1140
1141/**
1142 * Parse the service file using getServiceFromFile or use getServiceFromYAML
1143 * if YAML support was activated.
1144 *
1145 * @param conf the conf maps containing the main.cfg settings
1146 * @param file the file name to parse
1147 * @param service the service to update witht the file content
1148 * @param name the service name
1149 * @return true if the file can be parsed or false
1150 * @see getServiceFromFile, getServiceFromYAML
1151 */
1152int readServiceFile (maps * conf, char *file, service ** service, char *name){
1153  int t = getServiceFromFile (conf, file, service);
1154#ifdef YAML
1155  if (t < 0){
1156    t = getServiceFromYAML (conf, file, service, name);
1157  }
1158#endif
1159  return t;
1160}
1161
1162/**
1163 * Create the profile registry.
1164 *
1165 * The profile registry is optional (created only if the registry key is
1166 * available in the [main] section of the main.cfg file) and can be used to
1167 * store the profiles hierarchy. The registry is a directory which should
1168 * contain the following sub-directories:
1169 *  * concept: direcotry containing .html files describing concept
1170 *  * generic: directory containing .zcfg files for wps:GenericProcess
1171 *  * implementation: directory containing .zcfg files for wps:Process
1172 *
1173 * @param m the conf maps containing the main.cfg settings
1174 * @param r the registry to update
1175 * @param reg_dir the resgitry
1176 * @return 0 if the resgitry is null or was correctly updated, -1 on failure
1177 */
1178int createRegistry (maps* m,registry ** r, char *reg_dir)
1179{
1180  char registryKeys[3][15]={
1181    "concept",
1182    "generic",
1183    "implementation"
1184  };
1185  int scount = 0,i=0;
1186  if (reg_dir == NULL)
1187    return 0;
1188  for(i=0;i<3;i++){
1189    char * tmpName =
1190      (char *) malloc ((strlen (reg_dir) + strlen (registryKeys[i]) + 2) *
1191                       sizeof (char));
1192    sprintf (tmpName, "%s/%s", reg_dir, registryKeys[i]);
1193   
1194    DIR *dirp1 = opendir (tmpName);
1195    if(dirp1==NULL){
1196      setMapInMaps(m,"lenv","message",_("Unable to open the registry directory."));
1197      setMapInMaps(m,"lenv","type","InternalError");
1198      return -1;
1199    }
1200    struct dirent *dp1;
1201    while ((dp1 = readdir (dirp1)) != NULL){
1202      char* extn = strstr(dp1->d_name, ".zcfg");
1203      if(dp1->d_name[0] != '.' && extn != NULL && strlen(extn) == 5)
1204        {
1205          int t;
1206          char *tmps1=
1207            (char *) malloc ((strlen (tmpName) + strlen (dp1->d_name) + 2) *
1208                             sizeof (char));
1209          sprintf (tmps1, "%s/%s", tmpName, dp1->d_name);
1210          char *tmpsn = zStrdup (dp1->d_name);
1211          tmpsn[strlen (tmpsn) - 5] = 0;
1212          service* s1 = (service *) malloc (SERVICE_SIZE);
1213          if (s1 == NULL)
1214            {
1215              setMapInMaps(m,"lenv","message",_("Unable to allocate memory."));
1216              setMapInMaps(m,"lenv","type","InternalError");
1217              return -2;
1218            }
1219          t = readServiceFile (m, tmps1, &s1, tmpsn);
1220          free (tmpsn);
1221          if (t < 0)
1222            {
1223              map *tmp00 = getMapFromMaps (m, "lenv", "message");
1224              char tmp01[1024];
1225              if (tmp00 != NULL)
1226                sprintf (tmp01, _("Unable to parse the ZCFG file: %s (%s)"),
1227                         dp1->d_name, tmp00->value);
1228              else
1229                sprintf (tmp01, _("Unable to parse the ZCFG file: %s."),
1230                         dp1->d_name);
1231              setMapInMaps(m,"lenv","message",tmp01);
1232              setMapInMaps(m,"lenv","type","InternalError");
1233              return -1;
1234            }
1235          if(strncasecmp(registryKeys[i],"implementation",14)==0){
1236            inheritance(*r,&s1);
1237          }
1238          addServiceToRegistry(r,registryKeys[i],s1);
1239          freeService (&s1);
1240          free (s1);
1241          scount++;
1242        }
1243    }
1244    (void) closedir (dirp1);
1245  }
1246  return 0;
1247}
1248
1249#ifdef WIN32
1250/**
1251 * Create a KVP request for executing background task.
1252 * TODO: use the XML request in case of input POST request.
1253 *
1254 * @param m the maps containing the parameters from the main.cfg file
1255 * @param length the total length of the KVP parameters
1256 * @param type
1257 */
1258char* getMapsAsKVP(maps* m,int length,int type){
1259  char *dataInputsKVP=(char*) malloc(length*sizeof(char));
1260  char *dataInputsKVPi=NULL;
1261  maps* curs=m;
1262  int i=0;
1263  while(curs!=NULL){
1264    map *inRequest=getMap(curs->content,"inRequest");
1265    map *hasLength=getMap(curs->content,"length");
1266    if((inRequest!=NULL && strncasecmp(inRequest->value,"true",4)==0) ||
1267       inRequest==NULL){
1268      if(i==0)
1269        if(type==0){
1270          sprintf(dataInputsKVP,"%s=",curs->name);
1271          if(hasLength!=NULL){
1272            dataInputsKVPi=(char*)malloc((strlen(curs->name)+2)*sizeof(char));
1273            sprintf(dataInputsKVPi,"%s=",curs->name);
1274          }
1275        }
1276        else
1277          sprintf(dataInputsKVP,"%s",curs->name);
1278      else{
1279        char *temp=zStrdup(dataInputsKVP);
1280        if(type==0)
1281          sprintf(dataInputsKVP,"%s;%s=",temp,curs->name);
1282        else
1283          sprintf(dataInputsKVP,"%s;%s",temp,curs->name);
1284      }
1285      map* icurs=curs->content;
1286      if(type==0){
1287        char *temp=zStrdup(dataInputsKVP);
1288        if(getMap(curs->content,"xlink:href")!=NULL)
1289          sprintf(dataInputsKVP,"%sReference",temp);
1290        else{
1291          if(hasLength!=NULL){
1292            int j;
1293            for(j=0;j<atoi(hasLength->value);j++){
1294              map* tmp0=getMapArray(curs->content,"value",j);
1295              if(j==0)
1296                free(temp);
1297              temp=zStrdup(dataInputsKVP);
1298              if(j==0)
1299                sprintf(dataInputsKVP,"%s%s",temp,tmp0->value);
1300              else
1301                sprintf(dataInputsKVP,"%s;%s%s",temp,dataInputsKVPi,tmp0->value);
1302            }
1303          }
1304          else
1305            sprintf(dataInputsKVP,"%s%s",temp,icurs->value);
1306        }
1307        free(temp);
1308      }
1309      while(icurs!=NULL){
1310        if(strncasecmp(icurs->name,"value",5)!=0 &&
1311           strncasecmp(icurs->name,"mimeType_",9)!=0 &&
1312           strncasecmp(icurs->name,"dataType_",9)!=0 &&
1313           strncasecmp(icurs->name,"size",4)!=0 &&
1314           strncasecmp(icurs->name,"length",4)!=0 &&
1315           strncasecmp(icurs->name,"isArray",7)!=0 &&
1316           strcasecmp(icurs->name,"Reference")!=0 &&
1317           strcasecmp(icurs->name,"minOccurs")!=0 &&
1318           strcasecmp(icurs->name,"maxOccurs")!=0 &&
1319           strncasecmp(icurs->name,"fmimeType",9)!=0 &&
1320           strcasecmp(icurs->name,"inRequest")!=0){
1321          char *itemp=zStrdup(dataInputsKVP);
1322          if(strcasecmp(icurs->name,"xlink:href")!=0)
1323            sprintf(dataInputsKVP,"%s@%s=%s",itemp,icurs->name,icurs->value);
1324          else
1325            sprintf(dataInputsKVP,"%s@%s=%s",itemp,icurs->name,url_encode(icurs->value));
1326          free(itemp);
1327        }
1328        icurs=icurs->next;
1329      }
1330    }
1331    curs=curs->next;
1332    i++;
1333  }
1334  return dataInputsKVP;
1335}
1336#endif
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