42#include "magick/studio.h"
43#include "magick/cache.h"
44#include "magick/cache-private.h"
45#include "magick/configure.h"
46#include "magick/exception.h"
47#include "magick/exception-private.h"
48#include "magick/hashmap.h"
49#include "magick/log.h"
50#include "magick/image.h"
51#include "magick/image-private.h"
52#include "magick/memory_.h"
53#include "magick/nt-base-private.h"
54#include "magick/option.h"
55#include "magick/policy.h"
56#include "magick/random_.h"
57#include "magick/registry.h"
58#include "magick/resource_.h"
59#include "magick/semaphore.h"
60#include "magick/signature-private.h"
61#include "magick/string_.h"
62#include "magick/string-private.h"
63#include "magick/splay-tree.h"
64#include "magick/thread-private.h"
65#include "magick/token.h"
66#include "magick/timer-private.h"
67#include "magick/utility.h"
68#include "magick/utility-private.h"
73#define MagickPathTemplate "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
74#define NumberOfResourceTypes \
75 (sizeof(resource_semaphore)/sizeof(*resource_semaphore))
118 MagickULLConstant(0),
119 MagickULLConstant(0),
120 MagickULLConstant(0),
121 MagickULLConstant(0),
122 MagickULLConstant(0),
123 MagickULLConstant(0),
124 MagickULLConstant(0),
125 MagickULLConstant(0),
126 MagickULLConstant(0),
127 MagickULLConstant(0),
128 MagickULLConstant(0),
129 (MagickSizeType) (MAGICK_SSIZE_MAX/
sizeof(
PixelPacket)/5),
130 (MagickSizeType) (MAGICK_SSIZE_MAX/
sizeof(
PixelPacket)/5),
131 MagickResourceInfinity,
132 MagickULLConstant(3072)*1024*1024,
133 MagickULLConstant(1536)*1024*1024,
134 MagickULLConstant(3072)*1024*1024,
135 MagickResourceInfinity,
136 MagickULLConstant(768),
137 MagickULLConstant(1),
138 MagickULLConstant(0),
139 (MagickSizeType) MAGICK_SSIZE_MAX
143 *resource_semaphore[] = {
188MagickExport MagickBooleanType AcquireMagickResource(
const ResourceType type,
189 const MagickSizeType size)
192 resource_current[MaxTextExtent] =
"",
193 resource_limit[MaxTextExtent] =
"",
194 resource_request[MaxTextExtent] =
"";
206 request=(MagickOffsetType) size;
210 logging=(GetLogEventMask() & ResourceEvent) != 0 ? MagickTrue : MagickFalse;
220 ActivateSemaphoreInfo(&resource_semaphore[type]);
221 LockSemaphoreInfo(resource_semaphore[type]);
230 resource_info.area=(MagickOffsetType) size;
231 limit=resource_info.area_limit;
232 if ((limit == MagickResourceInfinity) || (size < limit))
234 if (logging != MagickFalse)
236 (void) FormatMagickSize(size,MagickFalse,resource_request);
237 (void) FormatMagickSize(size,MagickFalse,resource_current);
238 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
244 limit=resource_info.disk_limit;
245 if (((MagickSizeType) resource_info.disk+request) >
246 (MagickSizeType) resource_info.disk)
248 resource_info.disk+=request;
249 if ((limit == MagickResourceInfinity) ||
250 (resource_info.disk < (MagickOffsetType) limit))
253 resource_info.disk-=request;
255 if (logging != MagickFalse)
257 (void) FormatMagickSize(size,MagickTrue,resource_request);
258 (void) FormatMagickSize((MagickSizeType) resource_info.disk,
259 MagickTrue,resource_current);
260 (void) FormatMagickSize(limit,MagickTrue,resource_limit);
266 limit=resource_info.file_limit;
267 if (((MagickSizeType) resource_info.file+request) >
268 (MagickSizeType) resource_info.file)
270 resource_info.file+=request;
271 if ((limit == MagickResourceInfinity) ||
272 (resource_info.file < (MagickOffsetType) limit))
275 if (logging != MagickFalse)
277 (void) FormatMagickSize(size,MagickFalse,resource_request);
278 (void) FormatMagickSize((MagickSizeType) resource_info.file,
279 MagickFalse,resource_current);
280 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
286 resource_info.height=(MagickOffsetType) size;
287 limit=resource_info.height_limit;
288 if ((limit == MagickResourceInfinity) || (size < limit))
290 if (logging != MagickFalse)
292 (void) FormatMagickSize(size,MagickFalse,resource_request);
293 (void) FormatMagickSize(size,MagickFalse,resource_current);
294 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
298 case ListLengthResource:
300 resource_info.list_length=(MagickOffsetType) size;
301 limit=resource_info.list_length_limit;
302 if ((limit == MagickResourceInfinity) || (size < limit))
304 if (logging != MagickFalse)
306 (void) FormatMagickSize(size,MagickFalse,resource_request);
307 (void) FormatMagickSize(size,MagickFalse,resource_current);
308 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
314 limit=resource_info.map_limit;
315 if (((MagickSizeType) resource_info.map+request) >
316 (MagickSizeType) resource_info.map)
318 resource_info.map+=request;
319 if ((limit == MagickResourceInfinity) ||
320 (resource_info.map < (MagickOffsetType) limit))
323 resource_info.map-=request;
325 if (logging != MagickFalse)
327 (void) FormatMagickSize(size,MagickTrue,resource_request);
328 (void) FormatMagickSize((MagickSizeType) resource_info.map,
329 MagickTrue,resource_current);
330 (void) FormatMagickSize(limit,MagickTrue,resource_limit);
336 limit=resource_info.memory_limit;
337 if (((MagickSizeType) resource_info.memory+request) >
338 (MagickSizeType) resource_info.memory)
340 resource_info.memory+=request;
341 if ((limit == MagickResourceInfinity) ||
342 (resource_info.memory < (MagickOffsetType) limit))
345 resource_info.memory-=request;
347 if (logging != MagickFalse)
349 (void) FormatMagickSize(size,MagickTrue,resource_request);
350 (void) FormatMagickSize((MagickSizeType) resource_info.memory,
351 MagickTrue,resource_current);
352 (void) FormatMagickSize(limit,MagickTrue,resource_limit);
358 limit=resource_info.thread_limit;
359 if ((limit == MagickResourceInfinity) ||
360 (resource_info.thread < (MagickOffsetType) limit))
362 if (logging != MagickFalse)
364 (void) FormatMagickSize(size,MagickFalse,resource_request);
365 (void) FormatMagickSize((MagickSizeType) resource_info.thread,
366 MagickFalse,resource_current);
367 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
371 case ThrottleResource:
373 limit=resource_info.throttle_limit;
374 if ((limit == MagickResourceInfinity) ||
375 (resource_info.throttle < (MagickOffsetType) limit))
377 if (logging != MagickFalse)
379 (void) FormatMagickSize(size,MagickFalse,resource_request);
380 (void) FormatMagickSize((MagickSizeType) resource_info.throttle,
381 MagickFalse,resource_current);
382 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
388 limit=resource_info.time_limit;
389 if (((MagickSizeType) resource_info.time+request) >
390 (MagickSizeType) resource_info.time)
392 resource_info.time+=request;
393 if ((limit == MagickResourceInfinity) ||
394 ((MagickSizeType) resource_info.time < limit))
397 resource_info.time-=request;
399 if (logging != MagickFalse)
401 (void) FormatMagickSize(size,MagickFalse,resource_request);
402 (void) FormatMagickSize((MagickSizeType) resource_info.time,
403 MagickFalse,resource_current);
404 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
410 resource_info.width=(MagickOffsetType) size;
411 limit=resource_info.width_limit;
412 if ((limit == MagickResourceInfinity) || (size < limit))
414 if (logging != MagickFalse)
416 (void) FormatMagickSize(size,MagickFalse,resource_request);
417 (void) FormatMagickSize(size,MagickFalse,resource_current);
418 (void) FormatMagickSize(limit,MagickFalse,resource_limit);
433 UnlockSemaphoreInfo(resource_semaphore[type]);
438 if (logging != MagickFalse)
440 (void) LogMagickEvent(ResourceEvent,GetMagickModule(),
"%s: %s/%s/%s",
441 CommandOptionToMnemonic(MagickResourceOptions,(ssize_t) type),
442 resource_request,resource_current,resource_limit);
467MagickExport
void AsynchronousResourceComponentTerminus(
void)
477 ResetSplayTreeIterator(temporary_resources);
478 path=(
const char *) GetNextKeyInSplayTree(temporary_resources);
479 while (path != (
const char *) NULL)
481 (void) ShredFile(path);
482 (void) remove_utf8(path);
483 path=(
const char *) GetNextKeyInSplayTree(temporary_resources);
512static void *DestroyTemporaryResources(
void *temporary_resource)
514 (void) ShredFile((
char *) temporary_resource);
515 (void) remove_utf8((
char *) temporary_resource);
516 temporary_resource=DestroyString((
char *) temporary_resource);
517 return((
void *) NULL);
520MagickExport MagickBooleanType GetPathTemplate(
char *path)
535 (void) FormatLocaleString(path,MaxTextExtent,
"magick-" MagickPathTemplate);
536 exception=AcquireExceptionInfo();
537 directory=(
char *) GetImageRegistry(StringRegistryType,
"temporary-path",
539 exception=DestroyExceptionInfo(exception);
540 if (directory == (
char *) NULL)
541 directory=GetEnvironmentValue(
"MAGICK_TEMPORARY_PATH");
542 if (directory == (
char *) NULL)
543 directory=GetEnvironmentValue(
"MAGICK_TMPDIR");
544 if (directory == (
char *) NULL)
545 directory=GetEnvironmentValue(
"TMPDIR");
546#if defined(MAGICKCORE_WINDOWS_SUPPORT) || defined(__OS2__) || defined(__CYGWIN__)
547 if (directory == (
char *) NULL)
548 directory=GetEnvironmentValue(
"TMP");
549 if (directory == (
char *) NULL)
550 directory=GetEnvironmentValue(
"TEMP");
553 if (directory == (
char *) NULL)
554 directory=GetEnvironmentValue(
"MTMPDIR");
557 if (directory == (
char *) NULL)
558 directory=ConstantString(P_tmpdir);
560 if (directory == (
char *) NULL)
562 value=GetPolicyValue(
"resource:temporary-path");
563 if (value != (
char *) NULL)
565 (void) CloneString(&directory,value);
566 value=DestroyString(value);
568 if (strlen(directory) > (MaxTextExtent-25))
570 directory=DestroyString(directory);
573 status=GetPathAttributes(directory,&attributes);
574 if ((status == MagickFalse) || !S_ISDIR(attributes.st_mode))
576 directory=DestroyString(directory);
579 if (directory[strlen(directory)-1] == *DirectorySeparator)
580 (void) FormatLocaleString(path,MaxTextExtent,
"%smagick-" MagickPathTemplate,
583 (
void) FormatLocaleString(path,MaxTextExtent,
"%s%smagick-"
584 MagickPathTemplate,directory,DirectorySeparator);
585 directory=DestroyString(directory);
586#if defined(MAGICKCORE_WINDOWS_SUPPORT)
595 for (p=(path[1] == *DirectorySeparator ? path+2 : path); *p !=
'\0'; p++)
596 if (*p == *DirectorySeparator)
603MagickExport
int AcquireUniqueFileResource(
char *path)
605#if !defined(O_NOFOLLOW)
609# define TMP_MAX 238328
623 portable_filename[65] =
624 "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_-";
632 assert(path != (
char *) NULL);
633 if ((GetLogEventMask() & ResourceEvent) != 0)
634 (void) LogMagickEvent(ResourceEvent,GetMagickModule(),
"...");
637 if (resource_semaphore[FileResource] == (
SemaphoreInfo *) NULL)
638 ActivateSemaphoreInfo(&resource_semaphore[FileResource]);
639 LockSemaphoreInfo(resource_semaphore[FileResource]);
641 random_info=AcquireRandomInfo();
642 UnlockSemaphoreInfo(resource_semaphore[FileResource]);
645 for (i=0; i < (ssize_t) TMP_MAX; i++)
653 (void) GetPathTemplate(path);
654 key=GetRandomKey(random_info,strlen(MagickPathTemplate)-6);
655 p=path+strlen(path)-strlen(MagickPathTemplate);
656 datum=GetStringInfoDatum(key);
657 for (j=0; j < (ssize_t) GetStringInfoLength(key); j++)
659 c=(int) (datum[j] & 0x3f);
660 *p++=portable_filename[c];
662 key=DestroyStringInfo(key);
663#if defined(MAGICKCORE_HAVE_MKSTEMP)
667#if defined(MAGICKCORE_HAVE_FCHMOD)
668 (void) fchmod(file,0600);
671 setmode(file,O_BINARY);
676 key=GetRandomKey(random_info,strlen(MagickPathTemplate));
677 p=path+strlen(path)-strlen(MagickPathTemplate);
678 datum=GetStringInfoDatum(key);
679 for (j=0; j < (ssize_t) GetStringInfoLength(key); j++)
681 c=(int) (datum[j] & 0x3f);
682 *p++=portable_filename[c];
684 key=DestroyStringInfo(key);
685 file=open_utf8(path,O_RDWR | O_CREAT | O_EXCL | O_BINARY | O_NOFOLLOW,
687 if ((file >= 0) || (errno != EEXIST))
690 if ((GetLogEventMask() & ResourceEvent) != 0)
691 (void) LogMagickEvent(ResourceEvent,GetMagickModule(),
"Acquire %s",path);
694 if (resource_semaphore[FileResource] == (
SemaphoreInfo *) NULL)
695 ActivateSemaphoreInfo(&resource_semaphore[FileResource]);
696 LockSemaphoreInfo(resource_semaphore[FileResource]);
698 temporary_resources=NewSplayTree(CompareSplayTreeString,
699 DestroyTemporaryResources,(
void *(*)(
void *)) NULL);
700 UnlockSemaphoreInfo(resource_semaphore[FileResource]);
701 (void) AddValueToSplayTree(temporary_resources,ConstantString(path),
702 (
const void *) NULL);
728MagickExport MagickSizeType GetMagickResource(
const ResourceType type)
743 ActivateSemaphoreInfo(&resource_semaphore[type]);
744 LockSemaphoreInfo(resource_semaphore[type]);
753 resource=(MagickSizeType) resource_info.area;
758 resource=(MagickSizeType) resource_info.disk;
763 resource=(MagickSizeType) resource_info.file;
768 resource=(MagickSizeType) resource_info.height;
771 case ListLengthResource:
773 resource=(MagickSizeType) resource_info.list_length;
778 resource=(MagickSizeType) resource_info.map;
783 resource=(MagickSizeType) resource_info.memory;
788 resource=(MagickSizeType) resource_info.thread;
791 case ThrottleResource:
793 resource=(MagickSizeType) resource_info.throttle;
798 resource=(MagickSizeType) resource_info.time;
803 resource=(MagickSizeType) resource_info.width;
817 UnlockSemaphoreInfo(resource_semaphore[type]);
847MagickExport MagickSizeType GetMagickResourceLimit(
const ResourceType type)
854 ActivateSemaphoreInfo(&resource_semaphore[type]);
855 LockSemaphoreInfo(resource_semaphore[type]);
860 resource=resource_info.area_limit;
865 resource=resource_info.disk_limit;
870 resource=resource_info.file_limit;
875 resource=resource_info.height_limit;
878 case ListLengthResource:
880 resource=resource_info.list_length_limit;
885 resource=resource_info.memory_limit;
890 resource=resource_info.map_limit;
895 resource=resource_info.thread_limit;
898 case ThrottleResource:
900 resource=resource_info.throttle_limit;
905 resource=resource_info.time_limit;
910 resource=resource_info.width_limit;
916 UnlockSemaphoreInfo(resource_semaphore[type]);
946static ssize_t FormatPixelSize(
const MagickSizeType size,
947 const MagickBooleanType bi,
char *format)
966 "",
"Ki",
"Mi",
"Gi",
"Ti",
"Pi",
"Ei",
"Zi",
"Yi",
"Ri",
"Qi", (
char *) NULL
968 *traditional_units[] =
970 "",
"K",
"M",
"G",
"T",
"P",
"E",
"Z",
"Y",
"R",
"Q", (
char *) NULL
974 units=traditional_units;
975 if (bi != MagickFalse)
980#if defined(_MSC_VER) && (_MSC_VER == 1200)
981 length=(double) ((MagickOffsetType) size);
983 length=(double) size;
985 for (i=0; (length >= bytes) && (units[i+1] != (
const char *) NULL); i++)
988 for (j=2; j < 12; j++)
990 count=FormatLocaleString(format,MaxTextExtent,
"%.*g%sP",(
int) (i+j),length,
992 if (strchr(format,
'+') == (
char *) NULL)
998MagickExport MagickBooleanType ListMagickResourceInfo(FILE *file,
1002 area_limit[MaxTextExtent],
1003 disk_limit[MaxTextExtent],
1004 height_limit[MaxTextExtent],
1005 list_length_limit[MaxTextExtent],
1006 map_limit[MaxTextExtent],
1007 memory_limit[MaxTextExtent],
1008 time_limit[MaxTextExtent],
1009 width_limit[MaxTextExtent];
1011 magick_unreferenced(exception);
1013 if (file == (
const FILE *) NULL)
1015 if (resource_semaphore[FileResource] == (
SemaphoreInfo *) NULL)
1016 ActivateSemaphoreInfo(&resource_semaphore[FileResource]);
1017 LockSemaphoreInfo(resource_semaphore[FileResource]);
1018 (void) FormatPixelSize(resource_info.width_limit,MagickFalse,width_limit);
1019 (void) FormatPixelSize(resource_info.height_limit,MagickFalse,height_limit);
1020 (void) FormatPixelSize(resource_info.area_limit,MagickFalse,area_limit);
1021 (void) CopyMagickString(list_length_limit,
"unlimited",MaxTextExtent);
1022 if (resource_info.list_length_limit != MagickResourceInfinity)
1023 (void) FormatMagickSize(resource_info.list_length_limit,MagickTrue,
1025 (void) FormatMagickSize(resource_info.memory_limit,MagickTrue,memory_limit);
1026 (void) FormatMagickSize(resource_info.map_limit,MagickTrue,map_limit);
1027 (void) CopyMagickString(disk_limit,
"unlimited",MaxTextExtent);
1028 if (resource_info.disk_limit != MagickResourceInfinity)
1029 (void) FormatMagickSize(resource_info.disk_limit,MagickTrue,disk_limit);
1030 (void) CopyMagickString(time_limit,
"unlimited",MaxTextExtent);
1031 if (resource_info.time_limit != MagickResourceInfinity)
1032 (void) FormatLocaleString(time_limit,MaxTextExtent,
"%.20g",(
double)
1033 ((MagickOffsetType) resource_info.time_limit));
1034 (void) FormatLocaleFile(file,
"Resource limits:\n");
1035 (void) FormatLocaleFile(file,
" Width: %s\n",width_limit);
1036 (void) FormatLocaleFile(file,
" Height: %s\n",height_limit);
1037 (void) FormatLocaleFile(file,
" List length: %s\n",list_length_limit);
1038 (void) FormatLocaleFile(file,
" Area: %s\n",area_limit);
1039 (void) FormatLocaleFile(file,
" Memory: %s\n",memory_limit);
1040 (void) FormatLocaleFile(file,
" Map: %s\n",map_limit);
1041 (void) FormatLocaleFile(file,
" Disk: %s\n",disk_limit);
1042 (void) FormatLocaleFile(file,
" File: %.20g\n",(
double) ((MagickOffsetType)
1043 resource_info.file_limit));
1044 (void) FormatLocaleFile(file,
" Thread: %.20g\n",(
double) ((MagickOffsetType)
1045 resource_info.thread_limit));
1046 (void) FormatLocaleFile(file,
" Throttle: %.20g\n",(
double)
1047 ((MagickOffsetType) resource_info.throttle_limit));
1048 (void) FormatLocaleFile(file,
" Time: %s\n",time_limit);
1049 (void) fflush(file);
1050 UnlockSemaphoreInfo(resource_semaphore[FileResource]);
1079MagickExport
void RelinquishMagickResource(
const ResourceType type,
1080 const MagickSizeType size)
1083 resource_current[MaxTextExtent],
1084 resource_limit[MaxTextExtent],
1085 resource_request[MaxTextExtent];
1090 logging=(GetLogEventMask() & ResourceEvent) != 0 ? MagickTrue : MagickFalse;
1091 if (logging != MagickFalse)
1092 (void) FormatMagickSize(size,MagickFalse,resource_request);
1098 case MemoryResource:
1102 ActivateSemaphoreInfo(&resource_semaphore[type]);
1103 LockSemaphoreInfo(resource_semaphore[type]);
1112 resource_info.area=(MagickOffsetType) size;
1113 if (logging != MagickFalse)
1115 (void) FormatMagickSize((MagickSizeType) resource_info.area,
1116 MagickFalse,resource_current);
1117 (void) FormatMagickSize(resource_info.area_limit,MagickFalse,
1124 resource_info.disk-=size;
1125 assert(resource_info.disk >= 0);
1126 if (logging != MagickFalse)
1128 (void) FormatMagickSize((MagickSizeType) resource_info.disk,
1129 MagickTrue,resource_current);
1130 (void) FormatMagickSize(resource_info.disk_limit,MagickTrue,
1137 resource_info.file-=size;
1138 assert(resource_info.file >= 0);
1139 if (logging != MagickFalse)
1141 (void) FormatMagickSize((MagickSizeType) resource_info.file,
1142 MagickFalse,resource_current);
1143 (void) FormatMagickSize((MagickSizeType) resource_info.file_limit,
1144 MagickFalse,resource_limit);
1148 case HeightResource:
1150 resource_info.height=(MagickOffsetType) size;
1151 if (logging != MagickFalse)
1153 (void) FormatMagickSize((MagickSizeType) resource_info.height,
1154 MagickFalse,resource_current);
1155 (void) FormatMagickSize(resource_info.height_limit,MagickFalse,
1160 case ListLengthResource:
1162 resource_info.list_length=(MagickOffsetType) size;
1163 if (logging != MagickFalse)
1165 (void) FormatMagickSize((MagickSizeType) resource_info.list_length,
1166 MagickFalse,resource_current);
1167 (void) FormatMagickSize(resource_info.list_length_limit,MagickFalse,
1174 resource_info.map-=size;
1175 assert(resource_info.map >= 0);
1176 if (logging != MagickFalse)
1178 (void) FormatMagickSize((MagickSizeType) resource_info.map,
1179 MagickTrue,resource_current);
1180 (void) FormatMagickSize(resource_info.map_limit,MagickTrue,
1185 case MemoryResource:
1187 resource_info.memory-=size;
1188 assert(resource_info.memory >= 0);
1189 if (logging != MagickFalse)
1191 (void) FormatMagickSize((MagickSizeType) resource_info.memory,
1192 MagickTrue,resource_current);
1193 (void) FormatMagickSize(resource_info.memory_limit,MagickTrue,
1198 case ThreadResource:
1200 if (logging != MagickFalse)
1202 (void) FormatMagickSize((MagickSizeType) resource_info.thread,
1203 MagickFalse,resource_current);
1204 (void) FormatMagickSize((MagickSizeType) resource_info.thread_limit,
1205 MagickFalse,resource_limit);
1209 case ThrottleResource:
1211 if (logging != MagickFalse)
1213 (void) FormatMagickSize((MagickSizeType) resource_info.throttle,
1214 MagickFalse,resource_current);
1215 (void) FormatMagickSize((MagickSizeType) resource_info.throttle_limit,
1216 MagickFalse,resource_limit);
1222 resource_info.time-=size;
1223 assert(resource_info.time >= 0);
1224 if (logging != MagickFalse)
1225 if (logging != MagickFalse)
1227 (void) FormatMagickSize((MagickSizeType) resource_info.time,
1228 MagickFalse,resource_current);
1229 (void) FormatMagickSize((MagickSizeType) resource_info.time_limit,
1230 MagickFalse,resource_limit);
1236 resource_info.width=(MagickOffsetType) size;
1237 if (logging != MagickFalse)
1239 (void) FormatMagickSize((MagickSizeType) resource_info.width,
1240 MagickFalse,resource_current);
1241 (void) FormatMagickSize(resource_info.width_limit,MagickFalse,
1254 case MemoryResource:
1257 UnlockSemaphoreInfo(resource_semaphore[type]);
1262 if (logging != MagickFalse)
1264 (void) LogMagickEvent(ResourceEvent,GetMagickModule(),
"%s: %s/%s/%s",
1265 CommandOptionToMnemonic(MagickResourceOptions,(ssize_t) type),
1266 resource_request,resource_current,resource_limit);
1292MagickExport MagickBooleanType RelinquishUniqueFileResource(
const char *path)
1295 cache_path[MaxTextExtent];
1300 assert(path != (
const char *) NULL);
1302 if ((GetLogEventMask() & ResourceEvent) != 0)
1303 (void) LogMagickEvent(ResourceEvent,GetMagickModule(),
"Relinquish %s",path);
1304 if (resource_semaphore[FileResource] == (
SemaphoreInfo *) NULL)
1305 ActivateSemaphoreInfo(&resource_semaphore[FileResource]);
1306 LockSemaphoreInfo(resource_semaphore[FileResource]);
1308 status=DeleteNodeFromSplayTree(temporary_resources, (
const void *) path);
1309 UnlockSemaphoreInfo(resource_semaphore[FileResource]);
1310 (void) CopyMagickString(cache_path,path,MaxTextExtent);
1311 AppendImageFormat(
"cache",cache_path);
1312 if (access_utf8(cache_path,F_OK) == 0)
1314 status=ShredFile(cache_path);
1315 status|=remove_utf8(cache_path);
1317 if (status == MagickFalse)
1319 status=ShredFile(path);
1320 status|=remove_utf8(path);
1322 return(status == 0 ? MagickFalse : MagickTrue);
1343MagickExport MagickBooleanType ResourceComponentGenesis(
void)
1362 for (i=0; i < (ssize_t) NumberOfResourceTypes; i++)
1364 ActivateSemaphoreInfo(&resource_semaphore[i]);
1365 (void) SetMagickResourceLimit(WidthResource,resource_info.width_limit);
1366 limit=GetEnvironmentValue(
"MAGICK_WIDTH_LIMIT");
1367 if (limit != (
char *) NULL)
1369 (void) SetMagickResourceLimit(WidthResource,StringToSizeType(limit,
1371 limit=DestroyString(limit);
1373 (void) SetMagickResourceLimit(HeightResource,resource_info.height_limit);
1374 limit=GetEnvironmentValue(
"MAGICK_HEIGHT_LIMIT");
1375 if (limit != (
char *) NULL)
1377 (void) SetMagickResourceLimit(HeightResource,StringToSizeType(limit,
1379 limit=DestroyString(limit);
1381 pagesize=GetMagickPageSize();
1383#if defined(MAGICKCORE_HAVE_SYSCONF) && defined(_SC_PHYS_PAGES)
1384 pages=(ssize_t) sysconf(_SC_PHYS_PAGES);
1385#if defined(MAGICKCORE_WINDOWS_SUPPORT)
1389 memory=(MagickSizeType) pages*pagesize;
1390 if ((pagesize <= 0) || (pages <= 0))
1391 memory=2048UL*1024UL*1024UL;
1392#if defined(MAGICKCORE_PixelCacheThreshold)
1393 memory=StringToMagickSizeType(MAGICKCORE_PixelCacheThreshold,100.0);
1395 (void) SetMagickResourceLimit(AreaResource,4*memory);
1396 limit=GetEnvironmentValue(
"MAGICK_AREA_LIMIT");
1397 if (limit != (
char *) NULL)
1399 (void) SetMagickResourceLimit(AreaResource,StringToSizeType(limit,100.0));
1400 limit=DestroyString(limit);
1402 (void) SetMagickResourceLimit(MemoryResource,memory);
1403 limit=GetEnvironmentValue(
"MAGICK_MEMORY_LIMIT");
1404 if (limit != (
char *) NULL)
1406 (void) SetMagickResourceLimit(MemoryResource,
1407 StringToSizeType(limit,100.0));
1408 limit=DestroyString(limit);
1410 (void) SetMagickResourceLimit(MapResource,2*memory);
1411 limit=GetEnvironmentValue(
"MAGICK_MAP_LIMIT");
1412 if (limit != (
char *) NULL)
1414 (void) SetMagickResourceLimit(MapResource,StringToSizeType(limit,100.0));
1415 limit=DestroyString(limit);
1417 (void) SetMagickResourceLimit(DiskResource,MagickResourceInfinity);
1418 limit=GetEnvironmentValue(
"MAGICK_DISK_LIMIT");
1419 if (limit != (
char *) NULL)
1421 (void) SetMagickResourceLimit(DiskResource,StringToSizeType(limit,100.0));
1422 limit=DestroyString(limit);
1425#if defined(MAGICKCORE_HAVE_SYSCONF) && defined(_SC_OPEN_MAX)
1426 files=(ssize_t) sysconf(_SC_OPEN_MAX);
1428#if defined(MAGICKCORE_HAVE_GETRLIMIT) && defined(RLIMIT_NOFILE)
1434 if (getrlimit(RLIMIT_NOFILE,&resources) != -1)
1435 files=(ssize_t) resources.rlim_cur;
1438#if defined(MAGICKCORE_HAVE_GETDTABLESIZE) && defined(MAGICKCORE_POSIX_SUPPORT)
1440 files=(ssize_t) getdtablesize();
1444 (void) SetMagickResourceLimit(FileResource,MagickMax((
size_t)
1446 limit=GetEnvironmentValue(
"MAGICK_FILE_LIMIT");
1447 if (limit != (
char *) NULL)
1449 (void) SetMagickResourceLimit(FileResource,StringToSizeType(limit,100.0));
1450 limit=DestroyString(limit);
1452 (void) SetMagickResourceLimit(ThreadResource,GetOpenMPMaximumThreads());
1453 limit=GetEnvironmentValue(
"MAGICK_THREAD_LIMIT");
1454 if (limit != (
char *) NULL)
1456 (void) SetMagickResourceLimit(ThreadResource,StringToSizeType(limit,
1458 limit=DestroyString(limit);
1460 (void) SetMagickResourceLimit(ThrottleResource,0);
1461 limit=GetEnvironmentValue(
"MAGICK_THROTTLE_LIMIT");
1462 if (limit != (
char *) NULL)
1464 (void) SetMagickResourceLimit(ThrottleResource,StringToSizeType(limit,
1466 limit=DestroyString(limit);
1468 (void) SetMagickResourceLimit(TimeResource,MagickResourceInfinity);
1469 limit=GetEnvironmentValue(
"MAGICK_TIME_LIMIT");
1470 if (limit != (
char *) NULL)
1472 (void) SetMagickResourceLimit(TimeResource,StringToSizeType(limit,100.0));
1473 limit=DestroyString(limit);
1475 (void) SetMagickResourceLimit(ListLengthResource,MagickResourceInfinity);
1476 limit=GetEnvironmentValue(
"MAGICK_LIST_LENGTH_LIMIT");
1477 if (limit != (
char *) NULL)
1479 (void) SetMagickResourceLimit(ListLengthResource,
1480 StringToSizeType(limit,100.0));
1481 limit=DestroyString(limit);
1504MagickExport
void ResourceComponentTerminus(
void)
1509 for (i=0; i < (ssize_t) NumberOfResourceTypes; i++)
1511 ActivateSemaphoreInfo(&resource_semaphore[i]);
1512 LockSemaphoreInfo(resource_semaphore[FileResource]);
1514 temporary_resources=DestroySplayTree(temporary_resources);
1516 random_info=DestroyRandomInfo(random_info);
1517 UnlockSemaphoreInfo(resource_semaphore[FileResource]);
1518 for (i=0; i < (ssize_t) NumberOfResourceTypes; i++)
1519 DestroySemaphoreInfo(&resource_semaphore[i]);
1548MagickExport MagickBooleanType SetMagickResourceLimit(
const ResourceType type,
1549 const MagickSizeType limit)
1559 ActivateSemaphoreInfo(&resource_semaphore[type]);
1560 LockSemaphoreInfo(resource_semaphore[type]);
1561 value=(
char *) NULL;
1566 value=GetPolicyValue(
"resource:area");
1567 if (value == (
char *) NULL)
1568 resource_info.area_limit=limit;
1570 resource_info.area_limit=MagickMin(limit,StringToSizeType(value,100.0));
1575 value=GetPolicyValue(
"resource:disk");
1576 if (value == (
char *) NULL)
1577 resource_info.disk_limit=limit;
1579 resource_info.disk_limit=MagickMin(limit,StringToSizeType(value,100.0));
1584 value=GetPolicyValue(
"resource:file");
1585 if (value == (
char *) NULL)
1586 resource_info.file_limit=limit;
1588 resource_info.file_limit=MagickMin(limit,StringToSizeType(value,100.0));
1591 case HeightResource:
1593 value=GetPolicyValue(
"resource:height");
1594 if (value == (
char *) NULL)
1595 resource_info.height_limit=limit;
1597 resource_info.height_limit=MagickMin(limit,StringToSizeType(value,
1599 resource_info.height_limit=MagickMin(resource_info.height_limit,
1600 (MagickSizeType) MAGICK_SSIZE_MAX);
1603 case ListLengthResource:
1605 value=GetPolicyValue(
"resource:list-length");
1606 if (value == (
char *) NULL)
1607 resource_info.list_length_limit=limit;
1609 resource_info.list_length_limit=MagickMin(limit,
1610 StringToSizeType(value,100.0));
1615 value=GetPolicyValue(
"resource:map");
1616 if (value == (
char *) NULL)
1617 resource_info.map_limit=limit;
1619 resource_info.map_limit=MagickMin(limit,StringToSizeType(value,100.0));
1622 case MemoryResource:
1624 value=GetPolicyValue(
"resource:memory");
1625 if (value == (
char *) NULL)
1626 resource_info.memory_limit=limit;
1628 resource_info.memory_limit=MagickMin(limit,StringToSizeType(value,
1632 case ThreadResource:
1634 value=GetPolicyValue(
"resource:thread");
1635 if (value == (
char *) NULL)
1636 resource_info.thread_limit=limit;
1638 resource_info.thread_limit=MagickMin(limit,StringToSizeType(value,
1640 if (resource_info.thread_limit > GetOpenMPMaximumThreads())
1641 resource_info.thread_limit=GetOpenMPMaximumThreads();
1643 if (resource_info.thread_limit == 0)
1644 resource_info.thread_limit=1;
1647 case ThrottleResource:
1649 value=GetPolicyValue(
"resource:throttle");
1650 if (value == (
char *) NULL)
1651 resource_info.throttle_limit=limit;
1653 resource_info.throttle_limit=MagickMax(limit,StringToSizeType(value,
1659 value=GetPolicyValue(
"resource:time");
1660 if (value == (
char *) NULL)
1661 resource_info.time_limit=limit;
1663 resource_info.time_limit=MagickMin(limit,StringToSizeType(value,100.0));
1664 resource_info.time_limit=MagickMin(resource_info.time_limit,
1665 (MagickSizeType) MAGICK_SSIZE_MAX);
1670 value=GetPolicyValue(
"resource:width");
1671 if (value == (
char *) NULL)
1672 resource_info.width_limit=limit;
1674 resource_info.width_limit=MagickMin(limit,StringToSizeType(value,
1676 resource_info.width_limit=MagickMin(resource_info.width_limit,
1677 (MagickSizeType) MAGICK_SSIZE_MAX);
1686 if (value != (
char *) NULL)
1687 value=DestroyString(value);
1688 UnlockSemaphoreInfo(resource_semaphore[type]);