Commit d72e8680d for imagemagick.org
commit d72e8680d6c87208a8711a4c18ba7dc20939d41e
Author: Cristy <urban-warrior@imagemagick.org>
Date: Sat Feb 14 19:41:30 2026 -0500
base recursion detection based on thread id
diff --git a/coders/coders-private.h b/coders/coders-private.h
index ffdcd002a..f4639b49b 100644
--- a/coders/coders-private.h
+++ b/coders/coders-private.h
@@ -20,6 +20,7 @@
#include "MagickCore/colorspace-private.h"
#include "MagickCore/property.h"
#include "MagickCore/string_.h"
+#include "MagickCore/thread-private.h"
#define MagickCoderHeader(coder,offset,magic) \
{ coder, offset, (const unsigned char *) (magic), sizeof(magic)-1, MagickFalse },
@@ -35,6 +36,13 @@ extern ModuleExport size_t \
extern ModuleExport void \
Unregister ## coder ## Image(void);
+static inline void DecorateFilenameWithThreadId(const char *filename,
+ char *thread_filename)
+{
+ (void) FormatLocaleString(thread_filename,MagickPathExtent,"%.20g|%s",
+ (double) GetMagickThreadId(),filename);
+}
+
static inline ImageType IdentifyImageCoderType(const Image *image,
ExceptionInfo *exception)
{
diff --git a/coders/msl.c b/coders/msl.c
index 265bce499..ddd9dd4ef 100644
--- a/coders/msl.c
+++ b/coders/msl.c
@@ -89,10 +89,12 @@
#include "MagickCore/static.h"
#include "MagickCore/string_.h"
#include "MagickCore/string-private.h"
+#include "MagickCore/thread-private.h"
#include "MagickCore/transform.h"
#include "MagickCore/threshold.h"
#include "MagickCore/utility.h"
#include "MagickCore/visual-effects.h"
+#include "coders/coders-private.h"
#if defined(MAGICKCORE_XML_DELEGATE)
# include <libxml/xmlmemory.h>
# include <libxml/parserInternals.h>
@@ -4311,12 +4313,6 @@ static void MSLStartElement(void *context,const xmlChar *tag,
/*
Query font metrics.
*/
- if ((n < 1) || (msl_info->image[n] == (Image *) NULL))
- {
- ThrowMSLException(OptionError,"NoImagesDefined",
- (const char *) tag);
- break;
- }
draw_info=CloneDrawInfo(msl_info->image_info[n],
msl_info->draw_info[n]);
angle=0.0;
@@ -4790,25 +4786,28 @@ static void MSLStartElement(void *context,const xmlChar *tag,
{
if (LocaleCompare(keyword,"filename") == 0)
{
+ char
+ thread_filename[MagickPathExtent];
+
Image
*next = (Image *) NULL;
if (value == (char *) NULL)
break;
- if (GetValueFromSplayTree(msl_tree,value) != (const char *) NULL)
+ DecorateFilenameWithThreadId(value,thread_filename);
+ if (GetValueFromSplayTree(msl_tree,thread_filename) != (const char *) NULL)
{
(void) ThrowMagickException(msl_info->exception,
GetMagickModule(),DrawError,
"VectorGraphicsNestedTooDeeply","`%s'",value);
break;
}
- (void) AddValueToSplayTree(msl_tree,ConstantString(value),
- (void *) 1);
+ (void) AddValueToSplayTree(msl_tree,ConstantString(
+ thread_filename),(void *) 1);
*msl_info->image_info[n]->magick='\0';
(void) CopyMagickString(msl_info->image_info[n]->filename,
value,MagickPathExtent);
next=ReadImage(msl_info->image_info[n],exception);
- (void) DeleteNodeFromSplayTree(msl_tree,value);
CatchException(exception);
if (next == (Image *) NULL)
continue;
@@ -7177,7 +7176,18 @@ static void MSLEndElement(void *context,const xmlChar *tag)
case 'i':
{
if (LocaleCompare((const char *) tag, "image") == 0)
- MSLPopImage(msl_info);
+ {
+ if (msl_info->image_info[msl_info->n] != (ImageInfo *) NULL)
+ {
+ char
+ thread_filename[MagickPathExtent];
+
+ DecorateFilenameWithThreadId(
+ msl_info->image_info[msl_info->n]->filename,thread_filename);
+ (void) DeleteNodeFromSplayTree(msl_tree,thread_filename);
+ }
+ MSLPopImage(msl_info);
+ }
break;
}
case 'L':
diff --git a/coders/svg.c b/coders/svg.c
index bf540357d..e3d3a4c41 100644
--- a/coders/svg.c
+++ b/coders/svg.c
@@ -75,6 +75,7 @@
#include "MagickCore/static.h"
#include "MagickCore/string_.h"
#include "MagickCore/string-private.h"
+#include "MagickCore/thread-private.h"
#include "MagickCore/token.h"
#include "MagickCore/utility.h"
#include "coders/coders-private.h"
@@ -2660,7 +2661,8 @@ static void SVGEndElement(void *context,const xmlChar *name)
if (LocaleCompare((const char *) name,"image") == 0)
{
char
- *text;
+ *text,
+ thread_filename[MagickPathExtent];
Image
*image;
@@ -2674,14 +2676,15 @@ static void SVGEndElement(void *context,const xmlChar *name)
(void) FormatLocaleFile(svg_info->file,"pop graphic-context\n");
break;
}
- if (GetValueFromSplayTree(svg_tree,svg_info->url) != (const char *) NULL)
+ DecorateFilenameWithThreadId(svg_info->url,thread_filename);
+ if (GetValueFromSplayTree(svg_tree,thread_filename) != (const char *) NULL)
{
image_info=DestroyImageInfo(image_info);
(void) ThrowMagickException(svg_info->exception,GetMagickModule(),
DrawError,"VectorGraphicsNestedTooDeeply","`%s'",svg_info->url);
break;
}
- (void) AddValueToSplayTree(svg_tree,ConstantString(svg_info->url),
+ (void) AddValueToSplayTree(svg_tree,ConstantString(thread_filename),
(void *) 1);
(void) CopyMagickString(image_info->filename,svg_info->url,
MagickPathExtent);
@@ -2689,7 +2692,7 @@ static void SVGEndElement(void *context,const xmlChar *name)
image_info=DestroyImageInfo(image_info);
if (image != (Image *) NULL)
image=DestroyImage(image);
- (void) DeleteNodeFromSplayTree(svg_tree,svg_info->url);
+ (void) DeleteNodeFromSplayTree(svg_tree,thread_filename);
text=EscapeString(svg_info->url,'\"');
(void) FormatLocaleFile(svg_info->file,
"image Over %g,%g %g,%g \"%s\"\n",svg_info->bounds.x,