Skip to content

Commit 942d71f

Browse files
committed
Add LAYER.CONNECTIONOPTIONS keyword to specify open options to GDAL and OGR drivers
Credits: funded by French Ministry of Defense.
1 parent 84e0ce8 commit 942d71f

18 files changed

+1712
-1429
lines changed

mapfile.c

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3890,6 +3890,8 @@ int initLayer(layerObj *layer, mapObj *map)
38903890

38913891
layer->compositer = NULL;
38923892

3893+
initHashTable(&(layer->connectionoptions));
3894+
38933895
return(0);
38943896
}
38953897

@@ -4021,6 +4023,8 @@ int freeLayer(layerObj *layer)
40214023
msFree(layer->sortBy.properties[i].item);
40224024
msFree(layer->sortBy.properties);
40234025

4026+
if(&(layer->connectionoptions)) msFreeHashItems(&layer->connectionoptions);
4027+
40244028
return MS_SUCCESS;
40254029
}
40264030

@@ -4557,6 +4561,11 @@ int loadLayer(layerObj *layer, mapObj *map)
45574561
case(OFFSITE):
45584562
if(loadColor(&(layer->offsite), NULL) != MS_SUCCESS) return(-1);
45594563
break;
4564+
4565+
case(CONNECTIONOPTIONS):
4566+
if(loadHashTable(&(layer->connectionoptions)) != MS_SUCCESS) return(-1);
4567+
break;
4568+
45604569
case(OPACITY):
45614570
case(TRANSPARENCY): /* keyword supported for mapfile backwards compatability */
45624571
{
@@ -4890,6 +4899,7 @@ static void writeLayer(FILE *stream, int indent, layerObj *layer)
48904899
writeLayerCompositer(stream, indent, layer->compositer);
48914900
writeString(stream, indent, "CONNECTION", NULL, layer->connection);
48924901
writeKeyword(stream, indent, "CONNECTIONTYPE", layer->connectiontype, 10, MS_OGR, "OGR", MS_POSTGIS, "POSTGIS", MS_WMS, "WMS", MS_ORACLESPATIAL, "ORACLESPATIAL", MS_WFS, "WFS", MS_PLUGIN, "PLUGIN", MS_UNION, "UNION", MS_UVRASTER, "UVRASTER", MS_CONTOUR, "CONTOUR", MS_KERNELDENSITY, "KERNELDENSITY");
4902+
writeHashTableInline(stream, indent, "CONNECTIONOPTIONS", &(layer->connectionoptions));
48934903
writeString(stream, indent, "DATA", NULL, layer->data);
48944904
writeNumber(stream, indent, "DEBUG", 0, layer->debug); /* is this right? see loadLayer() */
48954905
writeString(stream, indent, "ENCODING", NULL, layer->encoding);

mapfile.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -329,5 +329,6 @@ enum MS_TOKEN_SOURCES {MS_FILE_TOKENS=0, MS_STRING_TOKENS, MS_URL_TOKENS};
329329
/* rfc59 bindvals objects */
330330
#define BINDVALS 2000
331331

332+
#define CONNECTIONOPTIONS 2001
332333

333334
#endif /* MAPFILE_H */

mapgdal.c

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -566,6 +566,26 @@ int msInitDefaultGDALOutputFormat( outputFormatObj *format )
566566
return MS_SUCCESS;
567567
}
568568

569+
char** msGetStringListFromHashTable(hashTableObj* table)
570+
{
571+
struct hashObj *tp = NULL;
572+
int i;
573+
char** papszRet = NULL;
574+
575+
if(!table) return NULL;
576+
if(msHashIsEmpty(table)) return NULL;
577+
578+
for (i=0; i<MS_HASHSIZE; ++i) {
579+
if (table->items[i] != NULL) {
580+
for (tp=table->items[i]; tp!=NULL; tp=tp->next) {
581+
papszRet = CSLSetNameValue(papszRet, tp->key, tp->data);
582+
}
583+
}
584+
}
585+
return papszRet;
586+
}
587+
588+
569589
#else
570590

571591
void msGDALInitialize( void ) {}

maplexer.c

Lines changed: 1434 additions & 1420 deletions
Large diffs are not rendered by default.

maplexer.l

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -353,6 +353,7 @@ char path[MS_MAXPATHLEN];
353353
<INITIAL,URL_STRING>offset { MS_LEXER_RETURN_TOKEN(OFFSET); }
354354
<INITIAL>offsite { MS_LEXER_RETURN_TOKEN(OFFSITE); }
355355
<INITIAL,URL_STRING>opacity { MS_LEXER_RETURN_TOKEN(OPACITY); }
356+
<INITIAL>connectionoptions { MS_LEXER_RETURN_TOKEN(CONNECTIONOPTIONS); }
356357
<INITIAL,URL_STRING>outlinecolor { MS_LEXER_RETURN_TOKEN(OUTLINECOLOR); }
357358
<INITIAL,URL_STRING>outlinewidth { MS_LEXER_RETURN_TOKEN(OUTLINEWIDTH); }
358359
<INITIAL>outputformat { MS_LEXER_RETURN_TOKEN(OUTPUTFORMAT); }

mapogr.cpp

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838

3939
#if defined(USE_OGR) || defined(USE_GDAL)
4040
# include "gdal_version.h"
41+
# include "gdal.h"
4142
# include "cpl_conv.h"
4243
# include "cpl_string.h"
4344
# include "ogr_srs_api.h"
@@ -1191,7 +1192,13 @@ msOGRFileOpen(layerObj *layer, const char *connection )
11911192
msDebug("OGROPen(%s)\n", pszDSSelectedName);
11921193

11931194
ACQUIRE_OGR_LOCK;
1194-
hDS = OGROpen( pszDSSelectedName, MS_FALSE, NULL );
1195+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
1196+
hDS = (OGRDataSourceH) GDALOpenEx(pszDSSelectedName,
1197+
GDAL_OF_VECTOR,
1198+
NULL,
1199+
(const char* const*)connectionoptions,
1200+
NULL);
1201+
CSLDestroy(connectionoptions);
11951202
RELEASE_OGR_LOCK;
11961203

11971204
if( hDS == NULL ) {

mapraster.c

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -661,7 +661,21 @@ void* msDrawRasterLayerLowOpenDataset(mapObj *map, layerObj *layer,
661661
return NULL;
662662

663663
msAcquireLock( TLOCK_GDAL );
664-
return GDALOpenShared( *p_decrypted_path, GA_ReadOnly );
664+
if( !layer->tileindex )
665+
{
666+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
667+
GDALDatasetH hDS = GDALOpenEx( *p_decrypted_path,
668+
GDAL_OF_RASTER | GDAL_OF_SHARED,
669+
NULL,
670+
(const char* const*)connectionoptions,
671+
NULL);
672+
CSLDestroy(connectionoptions);
673+
return hDS;
674+
}
675+
else
676+
{
677+
return GDALOpenShared( *p_decrypted_path, GA_ReadOnly );
678+
}
665679
#endif
666680
}
667681

@@ -683,6 +697,15 @@ void msDrawRasterLayerLowCloseDataset(layerObj *layer, void* hDS)
683697
if( close_connection == NULL && layer->tileindex == NULL )
684698
close_connection = "DEFER";
685699

700+
{
701+
/* Due to how GDAL processes OVERVIEW_LEVEL, datasets returned are */
702+
/* not shared, despite being asked to, so close them for real */
703+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
704+
if( CSLFetchNameValue(connectionoptions, "OVERVIEW_LEVEL") )
705+
close_connection = NULL;
706+
CSLDestroy(connectionoptions);
707+
}
708+
686709
if( close_connection != NULL
687710
&& strcasecmp(close_connection,"DEFER") == 0 ) {
688711
GDALDereferenceDataset( (GDALDatasetH)hDS );

maprasterquery.c

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -788,7 +788,20 @@ int msRasterQueryByRect(mapObj *map, layerObj *layer, rectObj queryRect)
788788
}
789789

790790
msAcquireLock( TLOCK_GDAL );
791-
hDS = GDALOpen(decrypted_path, GA_ReadOnly );
791+
if( !layer->tileindex )
792+
{
793+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
794+
hDS = GDALOpenEx(decrypted_path,
795+
GDAL_OF_RASTER,
796+
NULL,
797+
(const char* const*)connectionoptions,
798+
NULL);
799+
CSLDestroy(connectionoptions);
800+
}
801+
else
802+
{
803+
hDS = GDALOpen(decrypted_path, GA_ReadOnly );
804+
}
792805

793806
if( hDS == NULL ) {
794807
int ignore_missing = msMapIgnoreMissingData( map );
@@ -1378,7 +1391,13 @@ int msRASTERLayerGetExtent(layerObj *layer, rectObj *extent)
13781391

13791392
msAcquireLock( TLOCK_GDAL );
13801393
if( decrypted_path ) {
1381-
hDS = GDALOpen(decrypted_path, GA_ReadOnly );
1394+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
1395+
hDS = GDALOpenEx(decrypted_path,
1396+
GDAL_OF_RASTER,
1397+
NULL,
1398+
(const char* const*)connectionoptions,
1399+
NULL);
1400+
CSLDestroy(connectionoptions);
13821401
msFree( decrypted_path );
13831402
} else
13841403
hDS = NULL;

mapserver.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1797,6 +1797,8 @@ typedef struct labelObj labelObj;
17971797
#endif
17981798

17991799
LayerCompositer *compositer;
1800+
1801+
hashTableObj connectionoptions;
18001802
};
18011803

18021804

@@ -2791,6 +2793,7 @@ void msPopulateTextSymbolForLabelAndString(textSymbolObj *ts, labelObj *l, char
27912793
MS_DLL_EXPORT int msInitDefaultGDALOutputFormat( outputFormatObj *format );
27922794
#ifdef USE_GDAL
27932795
void msCleanVSIDir( const char *pszDir );
2796+
char** msGetStringListFromHashTable(hashTableObj* table);
27942797
#endif
27952798

27962799
/* ==================================================================== */

mapuvraster.c

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -477,8 +477,15 @@ int msUVRASTERLayerWhichShapes(layerObj *layer, rectObj rect, int isQuery)
477477

478478
if( decrypted_path )
479479
{
480+
char** connectionoptions;
480481
GDALAllRegister();
481-
hDS = GDALOpen(decrypted_path, GA_ReadOnly );
482+
connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
483+
hDS = GDALOpenEx(decrypted_path,
484+
GDAL_OF_RASTER,
485+
NULL,
486+
(const char* const*)connectionoptions,
487+
NULL);
488+
CSLDestroy(connectionoptions);
482489
}
483490
if( hDS != NULL )
484491
{
@@ -833,7 +840,13 @@ int msUVRASTERLayerGetExtent(layerObj *layer, rectObj *extent)
833840

834841
msAcquireLock( TLOCK_GDAL );
835842
if( decrypted_path ) {
836-
hDS = GDALOpen(decrypted_path, GA_ReadOnly );
843+
char** connectionoptions = msGetStringListFromHashTable(&(layer->connectionoptions));
844+
hDS = GDALOpenEx(decrypted_path,
845+
GDAL_OF_RASTER,
846+
NULL,
847+
(const char* const*)connectionoptions,
848+
NULL);
849+
CSLDestroy(connectionoptions);
837850
msFree( decrypted_path );
838851
} else
839852
hDS = NULL;

0 commit comments

Comments
 (0)