[mapserver] 01/09: New upstream version 7.0.7

Bas Couwenberg sebastic at debian.org
Wed Nov 15 20:45:59 UTC 2017


This is an automated email from the git hooks/post-receive script.

sebastic pushed a commit to branch master
in repository mapserver.

commit a6d472c5e1a35b675a302204a2e3f8e0f532614d
Author: Bas Couwenberg <sebastic at xs4all.nl>
Date:   Wed Nov 15 20:58:55 2017 +0100

    New upstream version 7.0.7
---
 CMakeLists.txt                  |   2 +-
 mapcairo.c                      |   1 +
 mapcopy.c                       |   1 +
 mapdraw.c                       | 159 +++++++++++++++++++++++++++++++++-------
 mapfile.c                       |  20 +++++
 maphttp.c                       |   5 --
 mapimageio.c                    |  15 ++--
 maplayer.c                      |  12 ++-
 mapogcsld.c                     |   2 +-
 mapogcsos.c                     |   3 +-
 mapogroutput.c                  |  13 +++-
 maporaclespatial.c              |  10 +--
 mapproject.c                    |  79 +++++++++++++++-----
 mapproject.h                    |   2 +
 maprasterquery.c                |   2 +-
 mapregex.c                      |   2 +-
 maprendering.c                  |   5 +-
 mapresample.c                   |  49 +++++++++----
 mapscript/csharp/CMakeLists.txt |   6 +-
 mapserver.h                     |  10 +++
 maputil.c                       |   8 ++
 mapuvraster.c                   |  59 +++++++++++++--
 mapwcs11.c                      |  20 +++--
 mapwcs20.c                      |  36 +++++----
 mapwfslayer.c                   |   2 +-
 25 files changed, 408 insertions(+), 115 deletions(-)

diff --git a/CMakeLists.txt b/CMakeLists.txt
index d8373ae..3422ca8 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -17,7 +17,7 @@ include(CheckCSourceCompiles)
 
 set (MapServer_VERSION_MAJOR 7)
 set (MapServer_VERSION_MINOR 0)
-set (MapServer_VERSION_REVISION 6)
+set (MapServer_VERSION_REVISION 7)
 set (MapServer_VERSION_SUFFIX "")
 
 set(TARGET_VERSION_MAJOR ${MapServer_VERSION_MAJOR})
diff --git a/mapcairo.c b/mapcairo.c
index 600530b..1595abc 100644
--- a/mapcairo.c
+++ b/mapcairo.c
@@ -907,6 +907,7 @@ void freeSVGCache(symbolObj *s) {
         free(cache->pixmap_buffer);
       }
       msFree(s->renderer_cache);
+      s->renderer_cache = NULL;
 #endif
 }
 
diff --git a/mapcopy.c b/mapcopy.c
index 0d50943..406d91a 100644
--- a/mapcopy.c
+++ b/mapcopy.c
@@ -500,6 +500,7 @@ int msCopyStyle(styleObj *dst, styleObj *src)
   MS_COPYSTELEM(offsetx);
   MS_COPYSTELEM(offsety);
   MS_COPYSTELEM(angle);
+  MS_COPYSTELEM(autoangle);
   MS_COPYSTELEM(minvalue);
   MS_COPYSTELEM(maxvalue);
   MS_COPYSTELEM(opacity);
diff --git a/mapdraw.c b/mapdraw.c
index 9fdacda..a064a53 100644
--- a/mapdraw.c
+++ b/mapdraw.c
@@ -220,7 +220,8 @@ imageObj *msDrawMap(mapObj *map, int querymap)
 #if defined(USE_WMS_LYR) || defined(USE_WFS_LYR)
   enum MS_CONNECTION_TYPE lastconnectiontype;
   httpRequestObj *pasOWSReqInfo=NULL;
-  int numOWSLayers=0, numOWSRequests=0;
+  int numOWSLayers=0;
+  int numOWSRequests=0;
   wmsParamsObj sLastWMSParams;
 #endif
 
@@ -256,30 +257,43 @@ imageObj *msDrawMap(mapObj *map, int querymap)
    */
   numOWSLayers=0;
   for(i=0; i<map->numlayers; i++) {
-    if(map->layerorder[i] != -1 &&
-        msLayerIsVisible(map, GET_LAYER(map,map->layerorder[i])))
+      if(map->layerorder[i] == -1 )
+        continue;
+
+      lp = GET_LAYER(map,map->layerorder[i]);
+      if( lp->connectiontype != MS_WMS &&
+          lp->connectiontype != MS_WFS ) {
+        continue;
+      }
       numOWSLayers++;
   }
 
-
   if (numOWSLayers > 0) {
+
     /* Alloc and init pasOWSReqInfo...
      */
-    pasOWSReqInfo = (httpRequestObj *)malloc((numOWSLayers+1)*sizeof(httpRequestObj));
+    pasOWSReqInfo = (httpRequestObj *)malloc(numOWSLayers*sizeof(httpRequestObj));
     if (pasOWSReqInfo == NULL) {
       msSetError(MS_MEMERR, "Allocation of httpRequestObj failed.", "msDrawMap()");
       return NULL;
     }
-    msHTTPInitRequestObj(pasOWSReqInfo, numOWSLayers+1);
+    msHTTPInitRequestObj(pasOWSReqInfo, numOWSLayers);
     msInitWmsParamsObj(&sLastWMSParams);
 
     /* Pre-download all WMS/WFS layers in parallel before starting to draw map */
     lastconnectiontype = MS_SHAPEFILE;
-    for(i=0; numOWSLayers && i<map->numlayers; i++) {
-      if(map->layerorder[i] == -1 || !msLayerIsVisible(map, GET_LAYER(map,map->layerorder[i])))
+    for(i=0; i<map->numlayers; i++) {
+      if(map->layerorder[i] == -1 )
         continue;
 
       lp = GET_LAYER(map,map->layerorder[i]);
+      if( lp->connectiontype != MS_WMS &&
+          lp->connectiontype != MS_WFS ) {
+        continue;
+      }
+
+      if( !msLayerIsVisible(map, lp) )
+        continue;
 
 #ifdef USE_WMS_LYR
       if(lp->connectiontype == MS_WMS) {
@@ -306,9 +320,7 @@ imageObj *msDrawMap(mapObj *map, int querymap)
       lastconnectiontype = lp->connectiontype;
     }
 
-#ifdef USE_WMS_LYR
     msFreeWmsParamsObj(&sLastWMSParams);
-#endif
   } /* if numOWSLayers > 0 */
 
   if(numOWSRequests && msOWSExecuteRequests(pasOWSReqInfo, numOWSRequests, map, MS_TRUE) == MS_FAILURE) {
@@ -582,17 +594,8 @@ int msLayerIsVisible(mapObj *map, layerObj *layer)
   if(layer->type == MS_LAYER_QUERY || layer->type == MS_LAYER_TILEINDEX) return(MS_FALSE);
   if((layer->status != MS_ON) && (layer->status != MS_DEFAULT)) return(MS_FALSE);
 
-  /* Only return MS_FALSE if it is definitely false. Sometimes it will return MS_UNKNOWN, which we
-  ** consider true, for this use case (it might be visible, try and draw it, see what happens). */
-  if ( msExtentsOverlap(map, layer) == MS_FALSE ) {
-    if( layer->debug >= MS_DEBUGLEVEL_V ) {
-      msDebug("msLayerIsVisible(): Skipping layer (%s) because LAYER.EXTENT does not intersect MAP.EXTENT\n", layer->name);
-    }
-    return(MS_FALSE);
-  }
-
-  if(msEvalContext(map, layer, layer->requires) == MS_FALSE) return(MS_FALSE);
-
+  /* Do comparisons of layer scale vs map scale now, since msExtentsOverlap() */
+  /* can be slow */
   if(map->scaledenom > 0) {
 
     /* layer scale boundaries should be checked first */
@@ -602,13 +605,27 @@ int msLayerIsVisible(mapObj *map, layerObj *layer)
       }
       return(MS_FALSE);
     }
-    if((layer->minscaledenom > 0) && (map->scaledenom <= layer->minscaledenom)) {
+    if(/*(layer->minscaledenom > 0) &&*/ (map->scaledenom <= layer->minscaledenom)) {
       if( layer->debug >= MS_DEBUGLEVEL_V ) {
         msDebug("msLayerIsVisible(): Skipping layer (%s) because LAYER.MINSCALE is too large for this MAP scale\n", layer->name);
       }
       return(MS_FALSE);
     }
-  
+  }
+
+  /* Only return MS_FALSE if it is definitely false. Sometimes it will return MS_UNKNOWN, which we
+  ** consider true, for this use case (it might be visible, try and draw it, see what happens). */
+  if ( msExtentsOverlap(map, layer) == MS_FALSE ) {
+    if( layer->debug >= MS_DEBUGLEVEL_V ) {
+      msDebug("msLayerIsVisible(): Skipping layer (%s) because LAYER.EXTENT does not intersect MAP.EXTENT\n", layer->name);
+    }
+    return(MS_FALSE);
+  }
+
+  if(msEvalContext(map, layer, layer->requires) == MS_FALSE) return(MS_FALSE);
+
+  if(map->scaledenom > 0) {
+
     /* now check class scale boundaries (all layers *must* pass these tests) */
     if(layer->numclasses > 0) {
       for(i=0; i<layer->numclasses; i++) {
@@ -939,8 +956,100 @@ int msDrawVectorLayer(mapObj *map, layerObj *layer, imageObj *image)
   if(layer->transform == MS_TRUE) {
     searchrect = map->extent;
 #ifdef USE_PROJ
-    if((map->projection.numargs > 0) && (layer->projection.numargs > 0))
-      msProjectRect(&map->projection, &layer->projection, &searchrect); /* project the searchrect to source coords */
+    if((map->projection.numargs > 0) && (layer->projection.numargs > 0)) {
+      int bDone = MS_FALSE;
+
+      /* For UVRaster, it is important that the searchrect is not too large */
+      /* to avoid insufficient intermediate raster resolution, which could */
+      /* happen if we use the default code path, given potential reprojection */
+      /* issues when using a map extent that is not in the validity area of */
+      /* the layer projection. */
+      if( layer->connectiontype == MS_UVRASTER &&
+          !layer->projection.gt.need_geotransform &&
+          !(pj_is_latlong(map->projection.proj) &&
+            pj_is_latlong(layer->projection.proj)) ) {
+        rectObj layer_ori_extent;
+
+        if( msLayerGetExtent(layer, &layer_ori_extent) == MS_SUCCESS ) {
+          projectionObj map_proj;
+
+          double map_extent_minx = map->extent.minx;
+          double map_extent_miny = map->extent.miny;
+          double map_extent_maxx = map->extent.maxx;
+          double map_extent_maxy = map->extent.maxy;
+          rectObj layer_extent = layer_ori_extent;
+
+          /* Create a variant of map->projection without geotransform for */
+          /* conveniency */
+          msInitProjection(&map_proj);
+          msCopyProjection(&map_proj, &map->projection);
+          map_proj.gt.need_geotransform = MS_FALSE;
+          if( map->projection.gt.need_geotransform ) {
+            map_extent_minx = map->projection.gt.geotransform[0]
+                + map->projection.gt.geotransform[1] * map->extent.minx
+                + map->projection.gt.geotransform[2] * map->extent.miny;
+            map_extent_miny = map->projection.gt.geotransform[3]
+                + map->projection.gt.geotransform[4] * map->extent.minx
+                + map->projection.gt.geotransform[5] * map->extent.miny;
+            map_extent_maxx = map->projection.gt.geotransform[0]
+                + map->projection.gt.geotransform[1] * map->extent.maxx
+                + map->projection.gt.geotransform[2] * map->extent.maxy;
+            map_extent_maxy = map->projection.gt.geotransform[3]
+                + map->projection.gt.geotransform[4] * map->extent.maxx
+                + map->projection.gt.geotransform[5] * map->extent.maxy;
+          }
+
+          /* Reproject layer extent to map projection */
+          msProjectRect(&layer->projection, &map_proj, &layer_extent);
+
+          if( layer_extent.minx <= map_extent_minx &&
+              layer_extent.miny <= map_extent_miny &&
+              layer_extent.maxx >= map_extent_maxx &&
+              layer_extent.maxy >= map_extent_maxy ) {
+            /* do nothing special if area to map is inside layer extent */
+          }
+          else {
+            if( layer_extent.minx >= map_extent_minx &&
+                layer_extent.maxx <= map_extent_maxx &&
+                layer_extent.miny >= map_extent_miny &&
+                layer_extent.maxy <= map_extent_maxy ) {
+              /* if the area to map is larger than the layer extent, then */
+              /* use full layer extent and add some margin to reflect the */
+              /* proportion of the useful area over the requested bbox */
+              double extra_x =
+                (map_extent_maxx - map_extent_minx) /
+                  (layer_extent.maxx - layer_extent.minx) *
+                  (layer_ori_extent.maxx -  layer_ori_extent.minx);
+              double extra_y =
+                 (map_extent_maxy - map_extent_miny) /
+                  (layer_extent.maxy - layer_extent.miny) *
+                  (layer_ori_extent.maxy -  layer_ori_extent.miny);
+              searchrect.minx = layer_ori_extent.minx - extra_x / 2;
+              searchrect.maxx = layer_ori_extent.maxx + extra_x / 2;
+              searchrect.miny = layer_ori_extent.miny - extra_y / 2;
+              searchrect.maxy = layer_ori_extent.maxy + extra_y / 2;
+            }
+            else
+            {
+              /* otherwise clip the map extent with the reprojected layer */
+              /* extent */
+              searchrect.minx = MAX( map_extent_minx, layer_extent.minx );
+              searchrect.maxx = MIN( map_extent_maxx, layer_extent.maxx );
+              searchrect.miny = MAX( map_extent_miny, layer_extent.miny );
+              searchrect.maxy = MIN( map_extent_maxy, layer_extent.maxy );
+              /* and reproject into the layer projection */
+              msProjectRect(&map_proj, &layer->projection, &searchrect);
+            }
+            bDone = MS_TRUE;
+          }
+
+          msFreeProjection(&map_proj);
+        }
+      }
+
+      if( !bDone )
+        msProjectRect(&map->projection, &layer->projection, &searchrect); /* project the searchrect to source coords */
+    }
 #endif
   } else {
     searchrect.minx = searchrect.miny = 0;
diff --git a/mapfile.c b/mapfile.c
index a8a48bf..10596a1 100644
--- a/mapfile.c
+++ b/mapfile.c
@@ -7140,6 +7140,25 @@ static void applyLayerDefaultSubstitutions(layerObj *layer, hashTableObj *table)
   return;
 }
 
+static void applyHashTableDefaultSubstitutions(hashTableObj *hashTab, hashTableObj *table)
+{
+	int i;
+	const char *default_key = msFirstKeyFromHashTable(table);
+	while (default_key) {
+		if (!strncmp(default_key, "default_", 8)) {
+			size_t buffer_size = (strlen(default_key) - 5);
+			char *to = msLookupHashTable(table, default_key);
+			char *tag = (char *)msSmallMalloc(buffer_size);
+			snprintf(tag, buffer_size, "%%%s%%", &(default_key[8]));
+
+			hashTableSubstituteString(hashTab, tag, to);
+			free(tag);
+		}
+		default_key = msNextKeyFromHashTable(table, default_key);
+	}
+	return;
+}
+
 /*
 ** Loop through layer metadata for keys that have a default_%key% pattern to replace
 ** remaining %key% entries by their default value.
@@ -7165,6 +7184,7 @@ void msApplyDefaultSubstitutions(mapObj *map)
     applyLayerDefaultSubstitutions(layer, &(layer->validation)); /* ...then layer settings... */
     applyLayerDefaultSubstitutions(layer, &(map->web.validation)); /* ...and finally web settings */
   }
+  applyHashTableDefaultSubstitutions(&map->web.metadata, &(map->web.validation));
 }
 
 char *_get_param_value(const char *key, char **names, char **values, int npairs) {
diff --git a/maphttp.c b/maphttp.c
index e7a1801..98329d4 100644
--- a/maphttp.c
+++ b/maphttp.c
@@ -113,11 +113,6 @@ void msHTTPCleanup()
  * Should be called on a new array of httpRequestObj to initialize them
  * for use with msHTTPExecuteRequest(), etc.
  *
- * Note that users of this module should always allocate and init one
- * more instance of httpRequestObj in their array than what they plan to
- * use because the terminate_handler() needs the last entry in the array
- * to have reqObj->request == NULL
- *
  **********************************************************************/
 void msHTTPInitRequestObj(httpRequestObj *pasReqInfo, int numRequests)
 {
diff --git a/mapimageio.c b/mapimageio.c
index 95feda2..df896c5 100644
--- a/mapimageio.c
+++ b/mapimageio.c
@@ -206,11 +206,16 @@ int saveAsJPEG(mapObj *map, rasterBufferObj *rb, streamInfo *info,
     cinfo.optimize_coding = TRUE;
 
   if( arithmetic || optimized ) {
-    if (map == NULL || msGetConfigOption(map, "JPEGMEM") == NULL) {
-      /* If the user doesn't provide a value for JPEGMEM, we want to be sure */
-      /* that at least the image size will be used before creating the temporary file */
-      cinfo.mem->max_memory_to_use =
-        MS_MAX(cinfo.mem->max_memory_to_use, cinfo.input_components * rb->width * rb->height);
+    /* libjpeg turbo 1.5.2 honours max_memory_to_use, but has no backing */
+    /* store implementation, so better not set max_memory_to_use ourselves. */
+    /* See https://github.com/libjpeg-turbo/libjpeg-turbo/issues/162 */
+    if( cinfo.mem->max_memory_to_use > 0 ) {
+      if (map == NULL || msGetConfigOption(map, "JPEGMEM") == NULL) {
+        /* If the user doesn't provide a value for JPEGMEM, we want to be sure */
+        /* that at least the image size will be used before creating the temporary file */
+        cinfo.mem->max_memory_to_use =
+          MS_MAX(cinfo.mem->max_memory_to_use, cinfo.input_components * rb->width * rb->height);
+      }
     }
   }
 
diff --git a/maplayer.c b/maplayer.c
index c0b721d..18bf221 100644
--- a/maplayer.c
+++ b/maplayer.c
@@ -229,7 +229,8 @@ int msLayerOpen(layerObj *layer)
   if(layer->tileindex && layer->connectiontype == MS_SHAPEFILE)
     layer->connectiontype = MS_TILED_SHAPEFILE;
 
-  if(layer->type == MS_LAYER_RASTER && layer->connectiontype != MS_WMS)
+  if(layer->type == MS_LAYER_RASTER && layer->connectiontype != MS_WMS
+      && layer->connectiontype != MS_KERNELDENSITY)
     layer->connectiontype = MS_RASTER;
 
   if ( ! layer->vtable) {
@@ -1564,7 +1565,7 @@ int msLayerApplyPlainFilterToLayer(FilterEncodingNode *psNode, mapObj *map, int
 int msLayerSupportsSorting(layerObj *layer)
 {
   if (layer && (
-         (layer->connectiontype == MS_OGR) || (layer->connectiontype == MS_POSTGIS) || (layer->connectiontype == MS_ORACLESPATIAL)
+    (layer->connectiontype == MS_OGR) || (layer->connectiontype == MS_POSTGIS) || (layer->connectiontype == MS_ORACLESPATIAL) || ((layer->connectiontype == MS_PLUGIN) && (strstr(layer->plugin_library,"msplugin_oracle") != NULL))
                )
      )
     return MS_TRUE;
@@ -1880,7 +1881,8 @@ int msInitializeVirtualTable(layerObj *layer)
   if(layer->tileindex && layer->connectiontype == MS_SHAPEFILE)
     layer->connectiontype = MS_TILED_SHAPEFILE;
 
-  if(layer->type == MS_LAYER_RASTER && layer->connectiontype != MS_WMS)
+  if(layer->type == MS_LAYER_RASTER && layer->connectiontype != MS_WMS
+      && layer->connectiontype != MS_KERNELDENSITY)
     layer->connectiontype = MS_RASTER;
 
   switch(layer->connectiontype) {
@@ -1903,6 +1905,10 @@ int msInitializeVirtualTable(layerObj *layer)
       /* WMS should be treated as a raster layer */
       return(msRASTERLayerInitializeVirtualTable(layer));
       break;
+    case(MS_KERNELDENSITY):
+      /* KERNELDENSITY should be treated as a raster layer */
+      return(msRASTERLayerInitializeVirtualTable(layer));
+      break;
     case(MS_ORACLESPATIAL):
       return(msOracleSpatialLayerInitializeVirtualTable(layer));
       break;
diff --git a/mapogcsld.c b/mapogcsld.c
index 26122e3..00afe03 100644
--- a/mapogcsld.c
+++ b/mapogcsld.c
@@ -329,7 +329,7 @@ int msSLDApplySLD(mapObj *map, char *psSLDXML, int iLayer, char *pszStyleLayerNa
 
           /* opacity for sld raster */
           if (GET_LAYER(map, i)->type == MS_LAYER_RASTER &&
-              pasLayers[i].compositer && pasLayers[j].compositer->opacity != 100)
+              pasLayers[j].compositer && pasLayers[j].compositer->opacity != 100)
             msSetLayerOpacity(GET_LAYER(map, i), pasLayers[j].compositer->opacity);
 
           /* mark as auto-generate SLD */
diff --git a/mapogcsos.c b/mapogcsos.c
index 8563e50..5ee9bab 100644
--- a/mapogcsos.c
+++ b/mapogcsos.c
@@ -1340,6 +1340,8 @@ int msSOSGetCapabilities(mapObj *map, sosParamsObj *sosparams, cgiRequestObj *re
             break;
         }
 
+        lp = (GET_LAYER(map, j));
+
         /*description*/
         value = msOWSLookupMetadata(&(lp->metadata), "S",
                                     "offering_description");
@@ -1349,7 +1351,6 @@ int msSOSGetCapabilities(mapObj *map, sosParamsObj *sosparams, cgiRequestObj *re
           xmlAddSibling(psNode, xmlNewComment(BAD_CAST "WARNING: Optional metadata \"sos_offering_description\" missing for gml:description"));
 
         /*name*/
-        lp = (GET_LAYER(map, j)); /*first layer*/
         value = msOWSLookupMetadata(&(lp->metadata), "S", "offering_name");
         if (value)
           psNode = xmlNewChild(psOfferingNode, psNsGml, BAD_CAST "name", BAD_CAST value);
diff --git a/mapogroutput.c b/mapogroutput.c
index c105fdf..0c1def2 100644
--- a/mapogroutput.c
+++ b/mapogroutput.c
@@ -767,6 +767,7 @@ int msOGRWriteFromQuery( mapObj *map, outputFormatObj *format, int sendheaders )
   /*      Create a subdirectory to handle this request.                   */
   /* -------------------------------------------------------------------- */
   if( !EQUAL(storage,"stream") ) {
+    const char* dir_to_create;
     if (strlen(base_dir) > 0)
       request_dir = msTmpFile(map, NULL, base_dir, "" );
     else
@@ -775,11 +776,19 @@ int msOGRWriteFromQuery( mapObj *map, outputFormatObj *format, int sendheaders )
     if( request_dir[strlen(request_dir)-1] == '.' )
       request_dir[strlen(request_dir)-1] = '\0';
 
-    if( VSIMkdir( request_dir, 0777 ) != 0 ) {
+    dir_to_create = request_dir;
+    /* Workaround issue in GDAL versions released at this time :
+     * GDAL issue fixed per https://trac.osgeo.org/gdal/ticket/6991 */
+    if( EQUAL(storage,"memory") && EQUAL(format->driver+4, "ESRI Shapefile") )
+    {
+        dir_to_create = base_dir;
+    }
+
+    if( VSIMkdir( dir_to_create, 0777 ) != 0 ) {
       msSetError( MS_MISCERR,
                   "Attempt to create directory '%s' failed.",
                   "msOGRWriteFromQuery()",
-                  request_dir );
+                  dir_to_create );
       return MS_FAILURE;
     }
   } else
diff --git a/maporaclespatial.c b/maporaclespatial.c
index 2f44ebc..efbfa1f 100644
--- a/maporaclespatial.c
+++ b/maporaclespatial.c
@@ -1707,7 +1707,7 @@ static int osGetOrdinates(msOracleSpatialDataHandler *dthand, msOracleSpatialHan
   } /* end of not-null-object if */
 
   if (compound_type){
-    if(gtype == 2003)
+    if (gtype == 2003 || gtype == 2007)
       shape->type = MS_SHAPE_POLYGON;
     msFreeShape(&newshape);
   }
@@ -2019,7 +2019,7 @@ int msOracleSpatialLayerWhichShapes( layerObj *layer, rectObj rect, int isQuery)
   /* define SQL query */
   for( i=0; i < layer->numitems; ++i ) {
       
-      snprintf( query_str + strlen(query_str), sizeof(query_str)-strlen(query_str), "%s, ", layer->items[i] );
+      snprintf( query_str + strlen(query_str), sizeof(query_str)-strlen(query_str), "\"%s\", ", layer->items[i] );
   }
 
   /*we add the uniqueid if it was not part of the current item list*/
@@ -3956,7 +3956,7 @@ PluginInitializeVirtualTable(layerVTableObj* vtable, layerObj *layer)
   assert(layer != NULL);
   assert(vtable != NULL);
 
-  layer->vtable->LayerTranslateFilter = msOracleSpatialLayerTranslateFilter;
+  vtable->LayerTranslateFilter = msOracleSpatialLayerTranslateFilter;
 
 
   vtable->LayerInitItemInfo = msOracleSpatialLayerInitItemInfo;
@@ -3975,7 +3975,7 @@ PluginInitializeVirtualTable(layerVTableObj* vtable, layerObj *layer)
   vtable->LayerApplyFilterToLayer = msLayerApplyCondSQLFilterToLayer;
   vtable->LayerSetTimeFilter = msLayerMakeBackticsTimeFilter;
   //vtable->LayerSetTimeFilter = msOracleSpatialLayerSetTimeFilter;
-  vtable->LayerEscapePropertyName = msOracleSpatialEscapePropertyName;
+  //vtable->LayerEscapePropertyName = msOracleSpatialEscapePropertyName;
   /* layer->vtable->LayerGetNumFeatures, use default */
   /* layer->vtable->LayerGetAutoProjection = msOracleSpatialLayerGetAutoProjection; Disabled until tested */
   vtable->LayerEnablePaging = msOracleSpatialEnablePaging;
@@ -4009,7 +4009,7 @@ int msOracleSpatialLayerInitializeVirtualTable(layerObj *layer)
   layer->vtable->LayerApplyFilterToLayer = msLayerApplyCondSQLFilterToLayer;
   layer->vtable->LayerSetTimeFilter = msLayerMakeBackticsTimeFilter;
   //layer->vtable->LayerSetTimeFilter = msOracleSpatialLayerSetTimeFilter;
-  layer->vtable->LayerEscapePropertyName = msOracleSpatialEscapePropertyName;
+  //layer->vtable->LayerEscapePropertyName = msOracleSpatialEscapePropertyName;
   /* layer->vtable->LayerCreateItems, use default */
   /* layer->vtable->LayerGetNumFeatures, use default */
   /* layer->vtable->LayerGetAutoProjection = msOracleSpatialLayerGetAutoProjection; Disabled until tested */
diff --git a/mapproject.c b/mapproject.c
index c90cc54..61c5ddb 100644
--- a/mapproject.c
+++ b/mapproject.c
@@ -930,7 +930,7 @@ msProjectRectAsPolygon(projectionObj *in, projectionObj *out,
   /*      logic.                                                          */
   /* -------------------------------------------------------------------- */
   if( out && pj_is_latlong(out->proj) && in && !pj_is_latlong(in->proj)
-      && rect->maxx - rect->minx > 360.0 ) {
+      && rect->maxx - rect->minx > 360.0 && !out->gt.need_geotransform ) {
     rect->maxx = 180;
     rect->minx = -180;
   }
@@ -943,6 +943,32 @@ msProjectRectAsPolygon(projectionObj *in, projectionObj *out,
 }
 
 /************************************************************************/
+/*                        msProjectHasLonWrap()                         */
+/************************************************************************/
+
+int msProjectHasLonWrap(projectionObj *in, double* pdfLonWrap)
+{
+    int i;
+    if( pdfLonWrap )
+        *pdfLonWrap = 0;
+#if USE_PROJ
+    if( !pj_is_latlong(in->proj) )
+        return MS_FALSE;
+#endif
+    for( i = 0; i < in->numargs; i++ )
+    {
+        if( strncmp(in->args[i], "lon_wrap=",
+                    strlen("lon_wrap=")) == 0 )
+        {
+            if( pdfLonWrap )
+                *pdfLonWrap = atof(in->args[i] + strlen("lon_wrap="));
+            return MS_TRUE;
+        }
+    }
+    return MS_FALSE;
+}
+
+/************************************************************************/
 /*                           msProjectRect()                            */
 /************************************************************************/
 
@@ -953,7 +979,10 @@ int msProjectRect(projectionObj *in, projectionObj *out, rectObj *rect)
 #else
   char *over = "+over";
   int ret;
+  int bFreeInOver = MS_FALSE;
+  int bFreeOutOver = MS_FALSE;
   projectionObj in_over,out_over,*inp,*outp;
+  double dfLonWrap = 0.0;
 
 #if USE_PROJ
   /* Detect projecting from north polar stereographic to longlat */
@@ -988,6 +1017,14 @@ int msProjectRect(projectionObj *in, projectionObj *out, rectObj *rect)
   }
 #endif
 
+  if(in && msProjectHasLonWrap(in, &dfLonWrap) && dfLonWrap == 180.0) {
+    inp = in;
+    outp = out;
+    if( rect->maxx > 180.0 ) {
+      rect->minx = -180.0;
+      rect->maxx = 180.0;
+    }
+  }
   /* 
    * Issue #4892: When projecting a rectangle we do not want proj to wrap resulting
    * coordinates around the dateline, as in practice a requested bounding box of
@@ -997,24 +1034,28 @@ int msProjectRect(projectionObj *in, projectionObj *out, rectObj *rect)
    *  To enforce this, we clone the input projections and add the "+over" proj 
    *  parameter in order to disable dateline wrapping.
    */ 
-  if(out) {
-    msInitProjection(&out_over);
-    msCopyProjectionExtended(&out_over,out,&over,1);
-    outp = &out_over;
-  } else {
-    outp = out;
-  }
-  if(in) {
-    msInitProjection(&in_over);
-    msCopyProjectionExtended(&in_over,in,&over,1);
-    inp = &in_over;
-  } else {
-    inp = in;
+  else {
+    if(out) {
+      bFreeOutOver = MS_TRUE;
+      msInitProjection(&out_over);
+      msCopyProjectionExtended(&out_over,out,&over,1);
+      outp = &out_over;
+    } else {
+      outp = out;
+    }
+    if(in) {
+      bFreeInOver = MS_TRUE;
+      msInitProjection(&in_over);
+      msCopyProjectionExtended(&in_over,in,&over,1);
+      inp = &in_over;
+    } else {
+      inp = in;
+    }
   }
   ret = msProjectRectAsPolygon(inp,outp, rect );
-  if(in)
+  if(bFreeInOver)
     msFreeProjection(&in_over);
-  if(out)
+  if(bFreeOutOver)
     msFreeProjection(&out_over);
   return ret;
 #endif
@@ -1132,7 +1173,11 @@ int msProjectionsDiffer( projectionObj *proj1, projectionObj *proj2 )
     int ret;
 
     ret = msProjectionsDifferInternal(proj1, proj2); 
-    if( ret ) 
+    if( ret &&
+        /* to speed up things, do normalization only if one proj is */
+        /* likely of the form init=epsg:XXX and the other proj=XXX datum=YYY... */
+        ( (proj1->numargs == 1 && proj2->numargs > 1) ||
+          (proj1->numargs > 1 && proj2->numargs == 1) ) )
     {
         projectionObj* p1normalized;
         projectionObj* p2normalized;
diff --git a/mapproject.h b/mapproject.h
index 4204cc4..c296677 100644
--- a/mapproject.h
+++ b/mapproject.h
@@ -108,6 +108,8 @@ extern "C" {
 
   /*utility functions */
   MS_DLL_EXPORT int GetMapserverUnitUsingProj(projectionObj *psProj);
+
+  int msProjectHasLonWrap(projectionObj *in, double* pdfLonWrap);
 #endif
 
 #ifdef __cplusplus
diff --git a/maprasterquery.c b/maprasterquery.c
index b6556be..ccf1528 100644
--- a/maprasterquery.c
+++ b/maprasterquery.c
@@ -193,7 +193,7 @@ static void msRasterLayerInfoInitialize( layerObj *layer )
   /* We need to do this or the layer->layerinfo will be interpreted */
   /* as shapefile access info because the default connectiontype is */
   /* MS_SHAPEFILE. */
-  if (layer->connectiontype != MS_WMS)
+  if (layer->connectiontype != MS_WMS && layer->connectiontype != MS_KERNELDENSITY)
     layer->connectiontype = MS_RASTER;
 
   rlinfo->query_result_hard_max = 1000000;
diff --git a/mapregex.c b/mapregex.c
index 00eac84..6a8a74f 100644
--- a/mapregex.c
+++ b/mapregex.c
@@ -45,7 +45,7 @@
 /*Need to specify this so that mapregex.h doesn't defined constants and
   doesn't #define away our ms_*/
 
-#if defined(_WIN32) && !defined(__CYGWIN__)
+#if defined(_WIN32) && !defined(__CYGWIN__) && _MSC_VER < 1900
 #define off_t  long
 #endif
 
diff --git a/maprendering.c b/maprendering.c
index b32716c..4af4887 100644
--- a/maprendering.c
+++ b/maprendering.c
@@ -1026,6 +1026,7 @@ int msDrawTextSymbol(mapObj *map, imageObj *image, pointObj labelPnt, textSymbol
     int g;
     double ox, oy;
     double cosa,sina;
+    int ret;
     if(ts->rotation != 0) {
       cosa = cos(ts->rotation);
       sina = sin(ts->rotation);
@@ -1048,9 +1049,11 @@ int msDrawTextSymbol(mapObj *map, imageObj *image, pointObj labelPnt, textSymbol
       ts_shadow->textpath->glyphs[g].pnt.y += oy;
     }
 
-    renderer->renderGlyphs(image,ts_shadow->textpath,&ts->label->shadowcolor,NULL,0);
+    ret = renderer->renderGlyphs(image,ts_shadow->textpath,&ts->label->shadowcolor,NULL,0);
     freeTextSymbol(ts_shadow);
     msFree(ts_shadow);
+    if( ret != MS_SUCCESS )
+      return ret;
   }
 
   if(MS_VALID_COLOR(ts->label->color))
diff --git a/mapresample.c b/mapresample.c
index 1179ab4..0bad1b2 100644
--- a/mapresample.c
+++ b/mapresample.c
@@ -1136,18 +1136,8 @@ static int msTransformMapToSource( int nDstXSize, int nDstYSize,
   /* -------------------------------------------------------------------- */
   if( bOutInit && pj_is_latlong(psSrcProj->proj) )
   {
-      int bHasLonWrap = MS_FALSE;
       double dfLonWrap = 0;
-      for( i = 0; i < psSrcProj->numargs; i++ )
-      {
-          if( strncmp(psSrcProj->args[i], "lon_wrap=",
-                      strlen("lon_wrap=")) == 0 )
-          {
-              bHasLonWrap = MS_TRUE;
-              dfLonWrap = atof( psSrcProj->args[i] + strlen("lon_wrap=") );
-              break;
-          }
-      }
+      int bHasLonWrap = msProjectHasLonWrap(psSrcProj, &dfLonWrap);
 
       if( bHasLonWrap )
       {
@@ -1366,14 +1356,47 @@ int msResampleGDALToMap( mapObj *map, layerObj *layer, imageObj *image,
   /* -------------------------------------------------------------------- */
   if( CSLFetchBoolean( layer->processing, "LOAD_WHOLE_IMAGE", FALSE ) )
     bSuccess = FALSE;
-  else
+  else {
     bSuccess =
       msTransformMapToSource( nDstXSize, nDstYSize, adfDstGeoTransform,
                               &(map->projection),
                               nSrcXSize, nSrcYSize,adfInvSrcGeoTransform,
                               &(layer->projection),
                               &sSrcExtent, FALSE );
-
+      if (bSuccess) {
+    /* -------------------------------------------------------------------- */
+    /*      Repeat transformation for a rectangle interior to the output    */
+    /*      requested region.  If the latter results in a more extreme y    */
+    /*      extent, then extend extents in source layer projection to       */
+    /*      southern/northing bounds and entire x extent.                   */
+    /* -------------------------------------------------------------------- */
+      memcpy( &sOrigSrcExtent, &sSrcExtent, sizeof(sSrcExtent) );
+      adfDstGeoTransform[0] = adfDstGeoTransform[0] + adfDstGeoTransform[1];
+      adfDstGeoTransform[3] = adfDstGeoTransform[3] + adfDstGeoTransform[5];
+      bSuccess =
+          msTransformMapToSource( nDstXSize-2, nDstYSize-2, adfDstGeoTransform,
+                                  &(map->projection),
+                                  nSrcXSize, nSrcYSize,adfInvSrcGeoTransform,
+                                  &(layer->projection),
+                                  &sSrcExtent, FALSE );
+      /* Reset this array to its original value! */
+      memcpy( adfDstGeoTransform, map->gt.geotransform, sizeof(double)*6 );
+
+      if (bSuccess) {
+          if (sSrcExtent.maxy > sOrigSrcExtent.maxy || sSrcExtent.miny < sOrigSrcExtent.miny) {
+              msDebug( "msTransformMapToSource(): extending bounds.\n");
+              sOrigSrcExtent.minx = 0;
+              sOrigSrcExtent.maxx = nSrcXSize;
+              if (sSrcExtent.maxy > sOrigSrcExtent.maxy)
+                  sOrigSrcExtent.maxy = nSrcYSize;
+              if (sSrcExtent.miny < sOrigSrcExtent.miny)
+                  sOrigSrcExtent.miny = 0;
+          }
+      }
+      memcpy( &sSrcExtent, &sOrigSrcExtent, sizeof(sOrigSrcExtent) );
+      bSuccess = TRUE;
+    }
+  }
   /* -------------------------------------------------------------------- */
   /*      If the transformation failed, it is likely that we have such    */
   /*      broad extents that the projection transformation failed at      */
diff --git a/mapscript/csharp/CMakeLists.txt b/mapscript/csharp/CMakeLists.txt
index 722ff86..b2792f4 100644
--- a/mapscript/csharp/CMakeLists.txt
+++ b/mapscript/csharp/CMakeLists.txt
@@ -44,8 +44,10 @@ SWIG_LINK_LIBRARIES(csharpmapscript ${MAPSERVER_LIBMAPSERVER})
 ADD_CUSTOM_COMMAND(TARGET csharpmapscript
                       WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}
                       POST_BUILD
-					  COMMAND copy /Y ..\\..\\..\\mapscript\\csharp\\mapscript.snk
-                      COMMAND ${CSHARP_COMPILER} ${PLATFORM_TARGET} /t:library /out:mapscript_csharp.dll ${KEYFILE_SPEC} *.cs ${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\config\\AssemblyInfo.cs
+					  COMMAND set MAPSCRIPT_SNK=${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\mapscript.snk          
+					  COMMAND set MAPSCRIPT_SNK=%MAPSCRIPT_SNK:/=\\%          
+					  COMMAND copy /Y \"%MAPSCRIPT_SNK%\"
+					  COMMAND ${CSHARP_COMPILER} ${PLATFORM_TARGET} /t:library /out:mapscript_csharp.dll ${KEYFILE_SPEC} *.cs ${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\config\\AssemblyInfo.cs
 					  COMMAND ${CSHARP_COMPILER} ${PLATFORM_TARGET} /r:mapscript_csharp.dll /out:shpdump.exe ${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\examples\\shpdump.cs
 					  COMMAND ${CSHARP_COMPILER} ${PLATFORM_TARGET} /r:mapscript_csharp.dll /out:drawmap.exe ${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\examples\\drawmap.cs
 					  COMMAND ${CSHARP_COMPILER} ${PLATFORM_TARGET} /r:mapscript_csharp.dll /out:shapeinfo.exe ${PROJECT_SOURCE_DIR}\\mapscript\\csharp\\examples\\shapeinfo.cs
diff --git a/mapserver.h b/mapserver.h
index 32182fa..df7eeb9 100644
--- a/mapserver.h
+++ b/mapserver.h
@@ -1123,6 +1123,16 @@ extern "C" {
 
     labelLeaderObj *leader;
   };
+  
+#ifdef SWIG
+#ifdef	__cplusplus
+extern "C" {
+#endif
+typedef struct labelObj labelObj;
+#ifdef	__cplusplus
+}
+#endif
+#endif
 
 #ifndef SWIG
   /* lightweight structure containing information to render a labelObj */
diff --git a/maputil.c b/maputil.c
index d6f23d2..9a7da7b 100644
--- a/maputil.c
+++ b/maputil.c
@@ -2260,6 +2260,14 @@ int msExtentsOverlap(mapObj *map, layerObj *layer)
   if( ! (layer->projection.numargs > 0) )
     return msRectOverlap( &(map->extent), &(layer->extent) );
 
+  /* In the case where map and layer projections are identical, and the */
+  /* bounding boxes don't cross the dateline, do simple rectangle comparison */
+  if( map->extent.minx < map->extent.maxx &&
+      layer->extent.minx < layer->extent.maxx &&
+      !msProjectionsDiffer(&(map->projection), &(layer->projection)) ) {
+    return msRectOverlap( &(map->extent), &(layer->extent) );
+  }
+
   /* We need to transform our rectangles for comparison,
   ** so we will work with copies and leave the originals intact. */
   MS_COPYRECT(&map_extent, &(map->extent) );
diff --git a/mapuvraster.c b/mapuvraster.c
index 52d92a5..9d44f00 100644
--- a/mapuvraster.c
+++ b/mapuvraster.c
@@ -345,7 +345,8 @@ int msUVRASTERLayerWhichShapes(layerObj *layer, rectObj rect, int isQuery)
   int width, height, u_src_off, v_src_off, i, x, y;
   char   **alteredProcessing = NULL, *saved_layer_mask;
   char **savedProcessing = NULL;
-
+  int bHasLonWrap = MS_FALSE;
+  double dfLonWrap = 0.0;
   
   if (layer->debug)
     msDebug("Entering msUVRASTERLayerWhichShapes().\n");
@@ -389,10 +390,6 @@ int msUVRASTERLayerWhichShapes(layerObj *layer, rectObj rect, int isQuery)
   map_cellsize = MS_MAX(MS_CELLSIZE(rect.minx, rect.maxx,layer->map->width),
                         MS_CELLSIZE(rect.miny,rect.maxy,layer->map->height));
   map_tmp->cellsize = map_cellsize*spacing;
-  
-  if (layer->debug)
-    msDebug("msUVRASTERLayerWhichShapes(): width: %d, height: %d, cellsize: %g\n",
-            width, height, map_tmp->cellsize);
 
   /* Initialize our dummy map */
   MS_INIT_COLOR(map_tmp->imagecolor, 255,255,255,255);
@@ -419,7 +416,55 @@ int msUVRASTERLayerWhichShapes(layerObj *layer, rectObj rect, int isQuery)
   map_tmp->extent.maxy = map_tmp->extent.miny+((height-1)*map_tmp->cellsize);
   map_tmp->gt.rotation_angle = 0.0;
 
-   msCopyProjection(&map_tmp->projection, &layer->projection);
+  /* Custom msCopyProjection() that removes lon_wrap parameter */
+  {
+#ifdef USE_PROJ
+    int i;
+
+    map_tmp->projection.numargs = 0;
+    map_tmp->projection.gt = layer->projection.gt;
+    map_tmp->projection.automatic = layer->projection.automatic;
+
+    for (i = 0; i < layer->projection.numargs; i++) {
+      if( strncmp(layer->projection.args[i], "lon_wrap=",
+                  strlen("lon_wrap=")) == 0 ) {
+        bHasLonWrap = MS_TRUE;
+        dfLonWrap = atof( layer->projection.args[i] + strlen("lon_wrap=") );
+      }
+      else {
+        map_tmp->projection.args[map_tmp->projection.numargs ++] =
+            msStrdup(layer->projection.args[i]);
+      }
+    }
+    if (map_tmp->projection.numargs != 0) {
+      msProcessProjection(&(map_tmp->projection));
+    }
+#endif
+    map_tmp->projection.wellknownprojection = layer->projection.wellknownprojection;
+  }
+
+  if( bHasLonWrap && dfLonWrap == 180.0) {
+    if( map_tmp->extent.minx >= 180 ) {
+      /* Request on the right half of the shifted raster (= western hemisphere) */
+      map_tmp->extent.minx -= 360;
+      map_tmp->extent.maxx -= 360;
+    }
+    else if( map_tmp->extent.maxx >= 180.0 ) {
+      /* Request spanning on the 2 hemispheres => drawing whole planet */
+      /* Take only into account vertical resolution, as horizontal one */
+      /* will be unreliable (assuming square pixels...) */
+      map_cellsize = MS_CELLSIZE(rect.miny,rect.maxy,layer->map->height);
+      map_tmp->cellsize = map_cellsize*spacing;
+
+      width = 360.0 / map_tmp->cellsize;
+      map_tmp->extent.minx = -180.0+(0.5*map_tmp->cellsize);
+      map_tmp->extent.maxx = 180.0-(0.5*map_tmp->cellsize);
+    }
+  }
+
+  if (layer->debug)
+    msDebug("msUVRASTERLayerWhichShapes(): width: %d, height: %d, cellsize: %g\n",
+            width, height, map_tmp->cellsize);
 
   if (layer->debug == 5)
     msDebug("msUVRASTERLayerWhichShapes(): extent: %g %g %g %g\n",
@@ -653,6 +698,8 @@ int msUVRASTERLayerGetExtent(layerObj *layer, rectObj *extent)
   msTryBuildPath3(szPath, map->mappath, map->shapepath, layer->data);
   decrypted_path = msDecryptStringTokens( map, szPath );
 
+  GDALAllRegister();
+
   msAcquireLock( TLOCK_GDAL );
   if( decrypted_path ) {
     hDS = GDALOpen(decrypted_path, GA_ReadOnly );
diff --git a/mapwcs11.c b/mapwcs11.c
index 8dbe948..8bfd60f 100644
--- a/mapwcs11.c
+++ b/mapwcs11.c
@@ -720,21 +720,29 @@ msWCSDescribeCoverage_CoverageDescription11(
   /* -------------------------------------------------------------------- */
   {
     char format_buf[500];
+    projectionObj proj;
+    double x0 = cm.geotransform[0]+cm.geotransform[1]/2+cm.geotransform[2]/2;
+    double y0 = cm.geotransform[3]+cm.geotransform[4]/2+cm.geotransform[5]/2;
+    double resx = cm.geotransform[1];
+    double resy = cm.geotransform[5];
+
+    msInitProjection( &proj );
+    if( msLoadProjectionString( &proj, cm.srs_urn ) == 0 ) {
+      msAxisNormalizePoints( &proj, 1, &x0, &y0 );
+      msAxisNormalizePoints( &proj, 1, &resx, &resy );
+    }
+    msFreeProjection( &proj );
 
     psGridCRS = xmlNewChild( psSD, NULL, BAD_CAST "GridCRS", NULL );
 
-
     xmlNewChild( psGridCRS, NULL, BAD_CAST "GridBaseCRS", BAD_CAST cm.srs_urn );
     xmlNewChild( psGridCRS, NULL, BAD_CAST "GridType",
                  BAD_CAST "urn:ogc:def:method:WCS:1.1:2dSimpleGrid" );
 
-    sprintf( format_buf, "%.15g %.15g",
-             cm.geotransform[0]+cm.geotransform[1]/2+cm.geotransform[2]/2,
-             cm.geotransform[3]+cm.geotransform[4]/2+cm.geotransform[5]/2);
+    sprintf( format_buf, "%.15g %.15g", x0, y0 );
     xmlNewChild( psGridCRS, NULL, BAD_CAST "GridOrigin", BAD_CAST format_buf );
 
-    sprintf( format_buf, "%.15g %.15g",
-             cm.geotransform[1], cm.geotransform[5] );
+    sprintf( format_buf, "%.15g %.15g", resx, resy );
     xmlNewChild( psGridCRS, NULL, BAD_CAST "GridOffsets", BAD_CAST format_buf );
 
     xmlNewChild( psGridCRS, NULL, BAD_CAST "GridCS",
diff --git a/mapwcs20.c b/mapwcs20.c
index 0b03893..020c0cb 100644
--- a/mapwcs20.c
+++ b/mapwcs20.c
@@ -2009,12 +2009,18 @@ static void msWCSCommon20_CreateDomainSet(layerObj* layer, wcs20coverageMetadata
 {
   xmlNodePtr psDomainSet, psGrid, psLimits, psGridEnvelope, psOrigin,
              psOffsetX, psOffsetY;
-  char low[100], high[100], id[100], point[100], resx[100], resy[100], axisLabels[100];
+  char low[100], high[100], id[100], point[100];
+  char offsetVector1[100], offsetVector2[100], axisLabels[100];
 
   psDomainSet = xmlNewChild( psRoot, psGmlNs, BAD_CAST "domainSet", NULL);
   {
     psGrid = xmlNewChild(psDomainSet, psGmlNs, BAD_CAST "RectifiedGrid", NULL);
     {
+      double x0 = cm->geotransform[0]+cm->geotransform[1]/2+cm->geotransform[2]/2;
+      double y0 = cm->geotransform[3]+cm->geotransform[4]/2+cm->geotransform[5]/2;
+      double resx = cm->geotransform[1];
+      double resy = cm->geotransform[5];
+
       xmlNewProp(psGrid, BAD_CAST "dimension", BAD_CAST "2");
       snprintf(id, sizeof(id), "grid_%s", layer->name);
       xmlNewNsProp(psGrid, psGmlNs, BAD_CAST "id", BAD_CAST id);
@@ -2032,17 +2038,9 @@ static void msWCSCommon20_CreateDomainSet(layerObj* layer, wcs20coverageMetadata
       }
 
       if(projection->proj != NULL && pj_is_latlong(projection->proj)) {
-        if (swapAxes == MS_FALSE) {
-          strlcpy(axisLabels, "long lat", sizeof(axisLabels));
-        } else {
-          strlcpy(axisLabels, "lat long", sizeof(axisLabels));
-        }
+        strlcpy(axisLabels, "long lat", sizeof(axisLabels));
       } else {
-        if (swapAxes == MS_FALSE) {
-          strlcpy(axisLabels, "x y", sizeof(axisLabels));
-        } else {
-          strlcpy(axisLabels, "y x", sizeof(axisLabels));
-        }
+        strlcpy(axisLabels, "x y", sizeof(axisLabels));
       }
 
       xmlNewChild(psGrid, psGmlNs, BAD_CAST "axisLabels", BAD_CAST axisLabels);
@@ -2050,9 +2048,9 @@ static void msWCSCommon20_CreateDomainSet(layerObj* layer, wcs20coverageMetadata
       psOrigin = xmlNewChild(psGrid, psGmlNs, BAD_CAST "origin", NULL);
       {
         if (swapAxes == MS_FALSE) {
-          snprintf(point, sizeof(point), "%f %f", cm->extent.minx, cm->extent.maxy);
+          snprintf(point, sizeof(point), "%f %f", x0, y0);
         } else {
-          snprintf(point, sizeof(point), "%f %f", cm->extent.maxy, cm->extent.minx);
+          snprintf(point, sizeof(point), "%f %f", y0, x0);
         }
         psOrigin = xmlNewChild(psOrigin, psGmlNs, BAD_CAST "Point", NULL);
         snprintf(id, sizeof(id), "grid_origin_%s", layer->name);
@@ -2063,14 +2061,14 @@ static void msWCSCommon20_CreateDomainSet(layerObj* layer, wcs20coverageMetadata
       }
 
       if (swapAxes == MS_FALSE) {
-        snprintf(resx, sizeof(resx), "%f 0", cm->xresolution);
-        snprintf(resy, sizeof(resy), "0 %f", -fabs(cm->yresolution));
+        snprintf(offsetVector1, sizeof(offsetVector1), "%f 0", resx);
+        snprintf(offsetVector2, sizeof(offsetVector2), "0 %f", resy);
       } else {
-        snprintf(resx, sizeof(resx), "0 %f", cm->xresolution);
-        snprintf(resy, sizeof(resy), "%f 0", -fabs(cm->yresolution));
+        snprintf(offsetVector1, sizeof(offsetVector1), "0 %f", resx);
+        snprintf(offsetVector2, sizeof(offsetVector2), "%f 0", resy);
       }
-      psOffsetX = xmlNewChild(psGrid, psGmlNs, BAD_CAST "offsetVector", BAD_CAST resx);
-      psOffsetY = xmlNewChild(psGrid, psGmlNs, BAD_CAST "offsetVector", BAD_CAST resy);
+      psOffsetX = xmlNewChild(psGrid, psGmlNs, BAD_CAST "offsetVector", BAD_CAST offsetVector1);
+      psOffsetY = xmlNewChild(psGrid, psGmlNs, BAD_CAST "offsetVector", BAD_CAST offsetVector2);
 
       xmlNewProp(psOffsetX, BAD_CAST "srsName", BAD_CAST cm->srs_uri);
       xmlNewProp(psOffsetY, BAD_CAST "srsName", BAD_CAST cm->srs_uri);
diff --git a/mapwfslayer.c b/mapwfslayer.c
index fe6560e..4a30955 100644
--- a/mapwfslayer.c
+++ b/mapwfslayer.c
@@ -445,7 +445,7 @@ static char *msBuildWFSLayerGetURL(mapObj *map, layerObj *lp, rectObj *bbox,
 		 } else {
 			 snprintf(pszURL + strlen(pszURL), bufferSize - strlen(pszURL),
 					 "&BBOX=%.15g,%.15g,%.15g,%.15g,%s&SRSNAME=%s",
-					 bbox->minx, bbox->miny, bbox->maxy, bbox->maxy,
+					 bbox->minx, bbox->miny, bbox->maxx, bbox->maxy,
 					 projUrn, projUrn);
 		 }
 	  } else {

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-grass/mapserver.git



More information about the Pkg-grass-devel mailing list