File ImageMagick-memory-corruption-in-MVG-paths.patch of Package ImageMagick.30356

diff --git a/MagickCore/draw.c b/MagickCore/draw.c
index a44d4ff38..cdd5efb1a 100644
--- a/MagickCore/draw.c
+++ b/MagickCore/draw.c
@@ -2583,6 +2583,13 @@ MagickExport MagickBooleanType DrawImage(Image *image,const DrawInfo *draw_info,
       case 'c':
       case 'C':
       {
+        if (LocaleCompare("class",keyword) == 0)
+          {
+            /*
+              Class primitive.
+            */
+            break;
+          }
         if (LocaleCompare("clip-path",keyword) == 0)
           {
             char
@@ -3036,6 +3043,8 @@ MagickExport MagickBooleanType DrawImage(Image *image,const DrawInfo *draw_info,
         if (LocaleCompare("pop",keyword) == 0)
           {
             GetNextToken(q,&q,extent,token);
+            if (LocaleCompare("class",token) == 0)
+              break;
             if (LocaleCompare("clip-path",token) == 0)
               break;
             if (LocaleCompare("defs",token) == 0)
@@ -3084,6 +3093,13 @@ MagickExport MagickBooleanType DrawImage(Image *image,const DrawInfo *draw_info,
         if (LocaleCompare("push",keyword) == 0)
           {
             GetNextToken(q,&q,extent,token);
+            if (LocaleCompare("class",token) == 0)
+              {
+                /*
+                  Class context.
+                */
+                break;
+              }
             if (LocaleCompare("clip-path",token) == 0)
               {
                 char
@@ -3403,8 +3419,8 @@ MagickExport MagickBooleanType DrawImage(Image *image,const DrawInfo *draw_info,
         if (LocaleCompare("stroke-antialias",keyword) == 0)
           {
             GetNextToken(q,&q,extent,token);
-            graphic_context[n]->stroke_antialias=
-              StringToLong(token) != 0 ? MagickTrue : MagickFalse;
+            graphic_context[n]->stroke_antialias=StringToLong(token) != 0 ?
+              MagickTrue : MagickFalse;
             break;
           }
         if (LocaleCompare("stroke-dasharray",keyword) == 0)
@@ -6104,9 +6120,6 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
       break;
     last_attribute=attribute;
     attribute=(int) (*p++);
-    if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
-        (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
-      q=(*mvg_info->primitive_info)+mvg_info->offset;
     switch (attribute)
     {
       case 'a':
@@ -6232,6 +6245,9 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
           if (token == next_token)
             ThrowPointExpectedException(token,exception);
           point.x=(double) (attribute == (int) 'H' ? x: point.x+x);
+          if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
+              (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
+            q=(*mvg_info->primitive_info)+mvg_info->offset;
           TracePoint(q,point);
           mvg_info->offset+=q->coordinates;
           q+=q->coordinates;
@@ -6264,6 +6280,9 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
             ThrowPointExpectedException(token,exception);
           point.x=(double) (attribute == (int) 'L' ? x : point.x+x);
           point.y=(double) (attribute == (int) 'L' ? y : point.y+y);
+          if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
+              (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
+            q=(*mvg_info->primitive_info)+mvg_info->offset;
           TracePoint(q,point);
           mvg_info->offset+=q->coordinates;
           q+=q->coordinates;
@@ -6280,11 +6299,13 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
         /*
           Move to.
         */
-        if (q != primitive_info)
+        if (mvg_info->offset != subpath_offset)
           {
+            primitive_info=(*mvg_info->primitive_info)+subpath_offset;
             primitive_info->coordinates=(size_t) (q-primitive_info);
             number_coordinates+=primitive_info->coordinates;
             primitive_info=q;
+            subpath_offset=mvg_info->offset;
           }
         i=0;
         do
@@ -6306,6 +6327,9 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
           if (i == 0)
             start=point;
           i++;
+          if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
+              (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
+            q=(*mvg_info->primitive_info)+mvg_info->offset;
           TracePoint(q,point);
           mvg_info->offset+=q->coordinates;
           q+=q->coordinates;
@@ -6476,6 +6500,9 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
           if (token == next_token)
             ThrowPointExpectedException(token,exception);
           point.y=(double) (attribute == (int) 'V' ? y : point.y+y);
+          if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
+              (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
+            q=(*mvg_info->primitive_info)+mvg_info->offset;
           TracePoint(q,point);
           mvg_info->offset+=q->coordinates;
           q+=q->coordinates;
@@ -6493,6 +6520,9 @@ static size_t TracePath(MVGInfo *mvg_info,const char *path,
           Close path.
         */
         point=start;
+        if (((size_t) (mvg_info->offset+4096) > *mvg_info->extent) &&
+            (CheckPrimitiveExtent(mvg_info,4096) != MagickFalse))
+          q=(*mvg_info->primitive_info)+mvg_info->offset;
         TracePoint(q,point);
         mvg_info->offset+=q->coordinates;
         q+=q->coordinates;
diff --git a/coders/svg.c b/coders/svg.c
index 8ef0cdb9b..538823793 100644
--- a/coders/svg.c
+++ b/coders/svg.c
@@ -1139,11 +1139,8 @@ static void SVGStartElement(void *context,const xmlChar *name,
     case 'S':
     case 's':
     {
-      if (LocaleCompare((const char *) name,"symbol") == 0)
-        {
-          (void) FormatLocaleFile(svg_info->file,"push symbol\n");
-          break;
-        }
+      if (LocaleCompare((char *) name,"style") == 0)
+        break;
       if (LocaleCompare((const char *) name,"svg") == 0)
         {
           svg_info->svgDepth++;
@@ -1157,6 +1154,11 @@ static void SVGStartElement(void *context,const xmlChar *name,
           (void) FormatLocaleFile(svg_info->file,"fill-rule nonzero\n");
           break;
         }
+      if (LocaleCompare((const char *) name,"symbol") == 0)
+        {
+          (void) FormatLocaleFile(svg_info->file,"push symbol\n");
+          break;
+        }
       break;
     }
     case 'T':
@@ -2552,9 +2554,11 @@ static void SVGEndElement(void *context,const xmlChar *name)
             svg_info->stop_color,svg_info->offset);
           break;
         }
-      if (LocaleCompare((const char *) name,"symbol") == 0)
+      if (LocaleCompare((char *) name,"style") == 0)
         {
-          (void) FormatLocaleFile(svg_info->file,"pop symbol\n");
+          /*
+            Find style definitions in svg_info->text.
+          */
           break;
         }
       if (LocaleCompare((const char *) name,"svg") == 0)
@@ -2563,6 +2567,11 @@ static void SVGEndElement(void *context,const xmlChar *name)
           svg_info->svgDepth--;
           break;
         }
+      if (LocaleCompare((const char *) name,"symbol") == 0)
+        {
+          (void) FormatLocaleFile(svg_info->file,"pop symbol\n");
+          break;
+        }
       break;
     }
     case 'T':

openSUSE Build Service is sponsored by