[Git][debian-gis-team/mapserver][buster-backports] 3 commits: Add upstream patches to fix CVE-2021-32062. (closes: #988208)

Bas Couwenberg gitlab at salsa.debian.org
Sat May 8 07:26:13 BST 2021



Bas Couwenberg pushed to branch buster-backports at Debian GIS Project / mapserver


Commits:
701662af by Bas Couwenberg at 2021-05-08T08:12:37+02:00
Add upstream patches to fix CVE-2021-32062. (closes: #988208)

- - - - -
0bee6abe by Bas Couwenberg at 2021-05-08T08:12:47+02:00
Update symbols file.

- - - - -
ae852a9a by Bas Couwenberg at 2021-05-08T08:13:11+02:00
Set distribution to buster-backports.

- - - - -


5 changed files:

- debian/changelog
- debian/libmapserver2.symbols
- + debian/patches/0001-Address-flaw-in-CGI-mapfile-loading-that-makes-it-po.patch
- + debian/patches/0001-Use-CPLSetConfigOption-CPLGetConfigOption-for-some-C.patch
- debian/patches/series


Changes:

=====================================
debian/changelog
=====================================
@@ -1,3 +1,11 @@
+mapserver (7.6.2-1~bpo10+2) buster-backports; urgency=medium
+
+  * Add upstream patches to fix CVE-2021-32062.
+    (closes: #988208)
+  * Update symbols file.
+
+ -- Bas Couwenberg <sebastic at debian.org>  Sat, 08 May 2021 08:12:56 +0200
+
 mapserver (7.6.2-1~bpo10+1) buster-backports; urgency=medium
 
   * Rebuild for buster-backports.


=====================================
debian/libmapserver2.symbols
=====================================
@@ -945,6 +945,7 @@ libmapserver.so.2 #PACKAGE# #MINVER#
  msCSVJoinPrepare at Base 6.2.1
  msCairoCleanup at Base 6.2.1
  msCalculateScale at Base 6.2.1
+ msCaseEvalRegex at Base 7.6.2
  msCaseReplaceSubstring at Base 6.2.1
  msCheckLabelMinDistance at Base 7.0.0
  msCheckParentPointer at Base 6.2.1
@@ -1418,6 +1419,7 @@ libmapserver.so.2 #PACKAGE# #MINVER#
  msIsGlyphASpace at Base 7.2.0
  msIsLayerQueryable at Base 6.2.1
  msIsOuterRing at Base 6.2.1
+ msIsValidRegex at Base 7.6.2
  msIsXMLTagValid at Base 6.2.1
  msItemInGroups at Base 6.2.1
  msJoinClose at Base 6.2.1


=====================================
debian/patches/0001-Address-flaw-in-CGI-mapfile-loading-that-makes-it-po.patch
=====================================
@@ -0,0 +1,161 @@
+Description: Address flaw in CGI mapfile loading that makes it possible to bypass security controls.
+Author: Even Rouault <even.rouault at spatialys.com>
+Origin: https://github.com/MapServer/MapServer/commit/927ac97cb9ece305306b5ab2b5600d3afe8c1732
+Bug: https://github.com/MapServer/MapServer/issues/6313
+Bug-Debian: https://bugs.debian.org/988208
+
+--- a/mapfile.c
++++ b/mapfile.c
+@@ -97,6 +97,16 @@ int msValidateParameter(const char *valu
+   return(MS_FAILURE);
+ }
+ 
++int msIsValidRegex(const char* e) {
++  ms_regex_t re;
++  if(ms_regcomp(&re, e, MS_REG_EXTENDED|MS_REG_NOSUB) != 0) {
++    msSetError(MS_REGEXERR, "Failed to compile expression (%s).", "msEvalRegex()", e);
++    return(MS_FALSE);
++  }
++  ms_regfree(&re);
++  return MS_TRUE;
++}
++
+ int msEvalRegex(const char *e, const char *s)
+ {
+   ms_regex_t re;
+@@ -107,6 +117,26 @@ int msEvalRegex(const char *e, const cha
+     msSetError(MS_REGEXERR, "Failed to compile expression (%s).", "msEvalRegex()", e);
+     return(MS_FALSE);
+   }
++
++  if(ms_regexec(&re, s, 0, NULL, 0) != 0) { /* no match */
++    ms_regfree(&re);
++    return(MS_FALSE);
++  }
++  ms_regfree(&re);
++
++  return(MS_TRUE);
++}
++
++int msCaseEvalRegex(const char *e, const char *s)
++{
++  ms_regex_t re;
++
++  if(!e || !s) return(MS_FALSE);
++
++  if(ms_regcomp(&re, e, MS_REG_EXTENDED|MS_REG_ICASE|MS_REG_NOSUB) != 0) {
++    msSetError(MS_REGEXERR, "Failed to compile expression (%s).", "msEvalRegex()", e);
++    return(MS_FALSE);
++  }
+ 
+   if(ms_regexec(&re, s, 0, NULL, 0) != 0) { /* no match */
+     ms_regfree(&re);
+--- a/mapserv.c
++++ b/mapserv.c
+@@ -166,7 +166,8 @@ int main(int argc, char *argv[])
+ 
+   /* push high-value ENV vars into the CPL global config - primarily for IIS/FastCGI */
+   const char* const apszEnvVars[] = { 
+-    "CURL_CA_BUNDLE", "MS_MAPFILE", "MS_MAP_NO_PATH", "MS_MAP_PATTERN",
++    "CURL_CA_BUNDLE", "MS_MAPFILE", "MS_MAP_NO_PATH", "MS_MAP_PATTERN", "MS_MAP_ENV_PATTERN",
++    "MS_MAP_BAD_PATTERN", "MS_MAP_ENV_BAD_PATTERN",
+      NULL /* guard */ };
+   for( int i = 0; apszEnvVars[i] != NULL; ++i ) {
+     const char* value = getenv(apszEnvVars[i]);
+--- a/mapserver.h
++++ b/mapserver.h
+@@ -2159,7 +2159,9 @@ void msPopulateTextSymbolForLabelAndStri
+   MS_DLL_EXPORT char *msWriteReferenceMapToString(referenceMapObj *ref);
+   MS_DLL_EXPORT char *msWriteLegendToString(legendObj *legend);
+   MS_DLL_EXPORT char *msWriteClusterToString(clusterObj *cluster);
++  MS_DLL_EXPORT int msIsValidRegex(const char* e);
+   MS_DLL_EXPORT int msEvalRegex(const char *e, const char *s);
++  MS_DLL_EXPORT int msCaseEvalRegex(const char *e, const char *s);
+ #ifdef USE_MSFREE
+   MS_DLL_EXPORT void msFree(void *p);
+ #else
+--- a/mapservutil.c
++++ b/mapservutil.c
+@@ -199,41 +199,67 @@ mapObj *msCGILoadMap(mapservObj *mapserv
+   int i, j;
+   mapObj *map = NULL;
+ 
++  const char *ms_map_bad_pattern_default = "[/\\]{2}|[/\\]?\\.+[/\\]|,";
++  const char *ms_map_env_bad_pattern_default = "^(AUTH_.*|CERT_.*|CONTENT_(LENGTH|TYPE)|DOCUMENT_(ROOT|URI)|GATEWAY_INTERFACE|HTTP.*|QUERY_STRING|PATH_(INFO|TRANSLATED)|REMOTE_.*|REQUEST_(METHOD|URI)|SCRIPT_(FILENAME|NAME)|SERVER_.*)";
++
++  int ms_mapfile_tainted = MS_TRUE;
+   const char *ms_mapfile = CPLGetConfigOption("MS_MAPFILE", NULL);
++
+   const char *ms_map_no_path = CPLGetConfigOption("MS_MAP_NO_PATH", NULL);
+   const char *ms_map_pattern = CPLGetConfigOption("MS_MAP_PATTERN", NULL);
++  const char *ms_map_env_pattern = CPLGetConfigOption("MS_MAP_ENV_PATTERN", NULL);
++
++  const char *ms_map_bad_pattern = CPLGetConfigOption("MS_MAP_BAD_PATTERN", NULL);
++  if(ms_map_bad_pattern == NULL) ms_map_bad_pattern = ms_map_bad_pattern_default;
++
++  const char *ms_map_env_bad_pattern = CPLGetConfigOption("MS_MAP_ENV_BAD_PATTERN", NULL);
++  if(ms_map_env_bad_pattern == NULL) ms_map_env_bad_pattern = ms_map_env_bad_pattern_default;
+ 
+   for(i=0; i<mapserv->request->NumParams; i++) /* find the mapfile parameter first */
+     if(strcasecmp(mapserv->request->ParamNames[i], "map") == 0) break;
+ 
+   if(i == mapserv->request->NumParams) {
+-    if(ms_mapfile != NULL) {
+-      map = msLoadMap(ms_mapfile,NULL);
+-    } else {
++    if(ms_mapfile == NULL) {
+       msSetError(MS_WEBERR, "CGI variable \"map\" is not set.", "msCGILoadMap()"); /* no default, outta here */
+       return NULL;
+     }
++    ms_mapfile_tainted = MS_FALSE;
+   } else {
+-    if(getenv(mapserv->request->ParamValues[i])) /* an environment variable references the actual file to use */
+-      map = msLoadMap(getenv(mapserv->request->ParamValues[i]), NULL);
+-    else {
+-      /* by here we know the request isn't for something in an environment variable */
+-      if(ms_map_no_path != NULL) {
+-        msSetError(MS_WEBERR, "Mapfile not found in environment variables and this server is not configured for full paths.", "msCGILoadMap()");
++    if(getenv(mapserv->request->ParamValues[i])) { /* an environment variable references the actual file to use */
++      /* validate env variable name */
++      if(msIsValidRegex(ms_map_env_bad_pattern) == MS_FALSE || msCaseEvalRegex(ms_map_env_bad_pattern, mapserv->request->ParamValues[i]) == MS_TRUE) {
++        msSetError(MS_WEBERR, "CGI variable \"map\" fails to validate.", "msCGILoadMap()");
+         return NULL;
+       }
+-
+-      if(ms_map_pattern != NULL && msEvalRegex(ms_map_pattern, mapserv->request->ParamValues[i]) != MS_TRUE) {
+-        msSetError(MS_WEBERR, "Parameter 'map' value fails to validate.", "msCGILoadMap()");
++      if(ms_map_env_pattern != NULL && msEvalRegex(ms_map_env_pattern, mapserv->request->ParamValues[i]) != MS_TRUE) {
++        msSetError(MS_WEBERR, "CGI variable \"map\" fails to validate.", "msCGILoadMap()");
++        return NULL;
++      }
++      ms_mapfile = getenv(mapserv->request->ParamValues[i]);
++    } else {
++      /* by now we know the request isn't for something in an environment variable */
++      if(ms_map_no_path != NULL) {
++        msSetError(MS_WEBERR, "CGI variable \"map\" not found in environment and this server is not configured for full paths.", "msCGILoadMap()");
+         return NULL;
+       }
++      ms_mapfile = mapserv->request->ParamValues[i];
++    }
++  }
+ 
+-      /* ok to try to load now */
+-      map = msLoadMap(mapserv->request->ParamValues[i], NULL);
++  /* validate ms_mapfile if tainted */
++  if(ms_mapfile_tainted == MS_TRUE) {
++    if(msIsValidRegex(ms_map_bad_pattern) == MS_FALSE || msEvalRegex(ms_map_bad_pattern, ms_mapfile) == MS_TRUE) {
++      msSetError(MS_WEBERR, "CGI variable \"map\" fails to validate.", "msCGILoadMap()");
++      return NULL;
++    }
++    if(ms_map_pattern != NULL && msEvalRegex(ms_map_pattern, ms_mapfile) != MS_TRUE) {
++      msSetError(MS_WEBERR, "CGI variable \"map\" fails to validate.", "msCGILoadMap()");
++      return NULL;
+     }
+   }
+-  
+ 
++  /* ok to try to load now */
++  map = msLoadMap(ms_mapfile, NULL);
+   if(!map) return NULL;
+ 
+   if(!msLookupHashTable(&(map->web.validation), "immutable")) {


=====================================
debian/patches/0001-Use-CPLSetConfigOption-CPLGetConfigOption-for-some-C.patch
=====================================
@@ -0,0 +1,107 @@
+Description: Use CPLSetConfigOption/CPLGetConfigOption for some CGI/FastCGI-related env vars.
+ Push a few high-value env vars into CPL config and then reference that instead of the env (mostly for IIS/FastCGI).
+Author: Steve Lime <steve.lime at state.mn.us>
+Origin: https://github.com/MapServer/MapServer/commit/b128dace3ec3e61bf063f7285d1279e9f9fd9e28
+Bug: https://github.com/MapServer/MapServer/pull/6304
+
+--- a/maphttp.c
++++ b/maphttp.c
+@@ -39,7 +39,7 @@
+ #include "mapthread.h"
+ #include "mapows.h"
+ 
+-
++#include "cpl_conv.h"
+ 
+ #include <time.h>
+ #ifndef _WIN32
+@@ -471,7 +471,7 @@ int msHTTPExecuteRequests(httpRequestObj
+    * If set then the value is the full path to the ca-bundle.crt file
+    * e.g. CURL_CA_BUNDLE=/usr/local/share/curl/curl-ca-bundle.crt
+    */
+-  pszCurlCABundle = getenv("CURL_CA_BUNDLE");
++  pszCurlCABundle = CPLGetConfigOption("CURL_CA_BUNDLE", NULL);
+ 
+   if (debug) {
+     msDebug("HTTP: Starting to prepare HTTP requests.\n");
+--- a/mapserv.c
++++ b/mapserv.c
+@@ -43,6 +43,8 @@
+ #include "mapio.h"
+ #include "maptime.h"
+ 
++#include "cpl_conv.h"
++
+ #ifndef WIN32
+ #include <signal.h>
+ #endif
+@@ -162,6 +164,15 @@ int main(int argc, char *argv[])
+   if(msGetGlobalDebugLevel() >= MS_DEBUGLEVEL_TUNING)
+     msGettimeofday(&execstarttime, NULL);
+ 
++  /* push high-value ENV vars into the CPL global config - primarily for IIS/FastCGI */
++  const char* const apszEnvVars[] = { 
++    "CURL_CA_BUNDLE", "MS_MAPFILE", "MS_MAP_NO_PATH", "MS_MAP_PATTERN",
++     NULL /* guard */ };
++  for( int i = 0; apszEnvVars[i] != NULL; ++i ) {
++    const char* value = getenv(apszEnvVars[i]);
++    if(value) CPLSetConfigOption(apszEnvVars[i], value);
++  }
++
+   /* -------------------------------------------------------------------- */
+   /*      Process arguments.  In normal use as a cgi-bin there are no     */
+   /*      commandline switches, but we provide a few for test/debug       */
+--- a/mapserv.h
++++ b/mapserv.h
+@@ -41,6 +41,7 @@
+ #include "maptile.h"
+ 
+ #include "cgiutil.h"
++
+ /*
+ ** Defines
+ */
+--- a/mapservutil.c
++++ b/mapservutil.c
+@@ -33,6 +33,8 @@
+ #include "maptime.h"
+ #include "mapows.h"
+ 
++#include "cpl_conv.h"
++
+ /*
+ ** Enumerated types, keep the query modes in sequence and at the end of the enumeration (mode enumeration is in maptemplate.h).
+ */
+@@ -197,12 +199,15 @@ mapObj *msCGILoadMap(mapservObj *mapserv
+   int i, j;
+   mapObj *map = NULL;
+ 
++  const char *ms_mapfile = CPLGetConfigOption("MS_MAPFILE", NULL);
++  const char *ms_map_no_path = CPLGetConfigOption("MS_MAP_NO_PATH", NULL);
++  const char *ms_map_pattern = CPLGetConfigOption("MS_MAP_PATTERN", NULL);
++
+   for(i=0; i<mapserv->request->NumParams; i++) /* find the mapfile parameter first */
+     if(strcasecmp(mapserv->request->ParamNames[i], "map") == 0) break;
+ 
+   if(i == mapserv->request->NumParams) {
+-    char *ms_mapfile = getenv("MS_MAPFILE");
+-    if(ms_mapfile) {
++    if(ms_mapfile != NULL) {
+       map = msLoadMap(ms_mapfile,NULL);
+     } else {
+       msSetError(MS_WEBERR, "CGI variable \"map\" is not set.", "msCGILoadMap()"); /* no default, outta here */
+@@ -213,12 +218,12 @@ mapObj *msCGILoadMap(mapservObj *mapserv
+       map = msLoadMap(getenv(mapserv->request->ParamValues[i]), NULL);
+     else {
+       /* by here we know the request isn't for something in an environment variable */
+-      if(getenv("MS_MAP_NO_PATH")) {
++      if(ms_map_no_path != NULL) {
+         msSetError(MS_WEBERR, "Mapfile not found in environment variables and this server is not configured for full paths.", "msCGILoadMap()");
+         return NULL;
+       }
+ 
+-      if(getenv("MS_MAP_PATTERN") && msEvalRegex(getenv("MS_MAP_PATTERN"), mapserv->request->ParamValues[i]) != MS_TRUE) {
++      if(ms_map_pattern != NULL && msEvalRegex(ms_map_pattern, mapserv->request->ParamValues[i]) != MS_TRUE) {
+         msSetError(MS_WEBERR, "Parameter 'map' value fails to validate.", "msCGILoadMap()");
+         return NULL;
+       }


=====================================
debian/patches/series
=====================================
@@ -1,3 +1,5 @@
 perl-mapscript-install.patch
 java-hardening.patch
 interpreter-path.path
+0001-Use-CPLSetConfigOption-CPLGetConfigOption-for-some-C.patch
+0001-Address-flaw-in-CGI-mapfile-loading-that-makes-it-po.patch



View it on GitLab: https://salsa.debian.org/debian-gis-team/mapserver/-/compare/d00f7a5498b55215a78a63652c471aebc4cfdb16...ae852a9ab25685ec3f52f2d9a96bffa0df5e69b4

-- 
View it on GitLab: https://salsa.debian.org/debian-gis-team/mapserver/-/compare/d00f7a5498b55215a78a63652c471aebc4cfdb16...ae852a9ab25685ec3f52f2d9a96bffa0df5e69b4
You're receiving this email because of your account on salsa.debian.org.


-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://alioth-lists.debian.net/pipermail/pkg-grass-devel/attachments/20210508/2c0ece4f/attachment-0001.htm>


More information about the Pkg-grass-devel mailing list