2 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
6 % M M AAA GGGG IIIII CCCC K K %
7 % MM MM A A G I C K K %
8 % M M M AAAAA G GGG I C KKK %
9 % M M A A G G I C K K %
10 % M M A A GGGG IIIII CCCC K K %
13 % Methods to Read or List ImageMagick Image formats %
21 % Copyright 1999-2009 ImageMagick Studio LLC, a non-profit organization %
22 % dedicated to making software imaging solutions freely available. %
24 % You may not use this file except in compliance with the License. You may %
25 % obtain a copy of the License at %
27 % http://www.imagemagick.org/script/license.php %
29 % Unless required by applicable law or agreed to in writing, software %
30 % distributed under the License is distributed on an "AS IS" BASIS, %
31 % WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. %
32 % See the License for the specific language governing permissions and %
33 % limitations under the License. %
35 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
43 #include "magick/studio.h"
44 #include "magick/blob.h"
45 #include "magick/cache.h"
46 #include "magick/coder.h"
47 #include "magick/client.h"
48 #include "magick/coder.h"
49 #include "magick/configure.h"
50 #include "magick/constitute.h"
51 #include "magick/delegate.h"
52 #include "magick/draw.h"
53 #include "magick/exception.h"
54 #include "magick/exception-private.h"
55 #include "magick/locale_.h"
56 #include "magick/log.h"
57 #include "magick/magic.h"
58 #include "magick/magick.h"
59 #include "magick/memory_.h"
60 #include "magick/mime.h"
61 #include "magick/module.h"
62 #if defined(__WINDOWS__)
63 # include "magick/nt-feature.h"
65 #include "magick/random_.h"
66 #include "magick/registry.h"
67 #include "magick/resource_.h"
68 #include "magick/policy.h"
69 #include "magick/semaphore.h"
70 #include "magick/signature-private.h"
71 #include "magick/splay-tree.h"
72 #include "magick/string_.h"
73 #include "magick/thread_.h"
74 #include "magick/thread-private.h"
75 #include "magick/token.h"
76 #include "magick/utility.h"
77 #include "magick/xwindow-private.h"
82 #if !defined(MAGICKCORE_RETSIGTYPE)
83 # define MAGICKCORE_RETSIGTYPE void
86 # define SIG_DFL ((SignalHandler *) 0)
89 # define SIG_ERR ((SignalHandler *) -1)
98 typedef MAGICKCORE_RETSIGTYPE
105 *magick_semaphore = (SemaphoreInfo *) NULL;
108 *signal_handlers[SIGMAX] = { (SignalHandler *) NULL };
111 *magick_list = (SplayTreeInfo *) NULL;
113 static volatile MagickBooleanType
114 instantiate_magick = MagickFalse; /* double-checked locking pattern */
117 Forward declarations.
119 static MagickBooleanType
120 InitializeMagickList(ExceptionInfo *);
123 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
127 + D e s t r o y M a g i c k C o m p o n e n t %
131 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
133 % DestroyMagickComponent() destroys the magick component.
135 % The format of the DestroyMagickComponent method is:
137 % void DestroyMagickComponent(void)
140 MagickExport void DestroyMagickComponent(void)
142 AcquireSemaphoreInfo(&magick_semaphore);
143 if (magick_list != (SplayTreeInfo *) NULL)
144 magick_list=DestroySplayTree(magick_list);
145 instantiate_magick=MagickFalse;
146 RelinquishSemaphoreInfo(magick_semaphore);
147 DestroySemaphoreInfo(&magick_semaphore);
148 #if !defined(MAGICKCORE_BUILD_MODULES)
149 UnregisterStaticModules();
151 #if defined(MAGICKCORE_MODULES_SUPPORT)
157 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
161 + G e t I m a g e D e c o d e r %
165 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
167 % GetImageDecoder() returns the image decoder.
169 % The format of the GetImageDecoder method is:
171 % DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
173 % A description of each parameter follows:
175 % o magick_info: The magick info.
178 MagickExport DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
180 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
181 assert(magick_info != (MagickInfo *) NULL);
182 assert(magick_info->signature == MagickSignature);
183 return(magick_info->decoder);
187 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
191 + G e t I m a g e E n c o d e r %
195 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
197 % GetImageEncoder() returns the image encoder.
199 % The format of the GetImageEncoder method is:
201 % EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
203 % A description of each parameter follows:
205 % o magick_info: The magick info.
208 MagickExport EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
210 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
211 assert(magick_info != (MagickInfo *) NULL);
212 assert(magick_info->signature == MagickSignature);
213 return(magick_info->encoder);
217 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
221 + G e t I m a g e M a g i c k %
225 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
227 % GetImageMagick() searches for an image format that matches the specified
228 % magick string. If one is found, MagickTrue is returned otherwise
231 % The format of the GetImageMagick method is:
233 % MagickBooleanType GetImageMagick(const unsigned char *magick,
234 % const size_t length,char *format)
236 % A description of each parameter follows:
238 % o magick: the image format we are searching for.
240 % o length: the length of the binary string.
242 % o format: the image format as determined by the magick bytes.
245 MagickExport MagickBooleanType GetImageMagick(const unsigned char *magick,
246 const size_t length,char *format)
254 register const MagickInfo
257 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
258 assert(magick != (const unsigned char *) NULL);
259 exception=AcquireExceptionInfo();
260 p=GetMagickInfo("*",exception);
261 exception=DestroyExceptionInfo(exception);
262 if (p == (const MagickInfo *) NULL)
265 AcquireSemaphoreInfo(&magick_semaphore);
266 ResetSplayTreeIterator(magick_list);
267 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
268 while (p != (const MagickInfo *) NULL)
270 if ((p->magick != (IsImageFormatHandler *) NULL) &&
271 (p->magick(magick,length) != 0))
274 (void) CopyMagickString(format,p->name,MaxTextExtent);
277 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
279 RelinquishSemaphoreInfo(magick_semaphore);
284 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
288 + G e t M a g i c k A d j o i n %
292 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
294 % GetMagickAdjoin() returns MagickTrue if the magick adjoin is MagickTrue.
296 % The format of the GetMagickAdjoin method is:
298 % MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
300 % A description of each parameter follows:
302 % o magick_info: The magick info.
305 MagickExport MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
307 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
308 assert(magick_info != (MagickInfo *) NULL);
309 assert(magick_info->signature == MagickSignature);
310 return(magick_info->adjoin);
314 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
318 + G e t M a g i c k B l o b S u p p o r t %
322 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
324 % GetMagickBlobSupport() returns MagickTrue if the magick supports blobs.
326 % The format of the GetMagickBlobSupport method is:
328 % MagickBooleanType GetMagickBlobSupport(const MagickInfo *magick_info)
330 % A description of each parameter follows:
332 % o magick_info: The magick info.
335 MagickExport MagickBooleanType GetMagickBlobSupport(
336 const MagickInfo *magick_info)
338 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
339 assert(magick_info != (MagickInfo *) NULL);
340 assert(magick_info->signature == MagickSignature);
341 return(magick_info->blob_support);
345 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
349 + G e t M a g i c k D e s c r i p t i o n %
353 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
355 % GetMagickDescription() returns the magick description.
357 % The format of the GetMagickDescription method is:
359 % const char *GetMagickDescription(const MagickInfo *magick_info)
361 % A description of each parameter follows:
363 % o magick_info: The magick info.
366 MagickExport const char *GetMagickDescription(const MagickInfo *magick_info)
368 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
369 assert(magick_info != (MagickInfo *) NULL);
370 assert(magick_info->signature == MagickSignature);
371 return(magick_info->description);
375 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
379 + G e t M a g i c k E n d i a n S u p p o r t %
383 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
385 % GetMagickEndianSupport() returns the MagickTrue if the coder respects
386 % endianness other than MSBEndian.
388 % The format of the GetMagickEndianSupport method is:
390 % MagickBooleanType GetMagickEndianSupport(const MagickInfo *magick_info)
392 % A description of each parameter follows:
394 % o magick_info: The magick info.
397 MagickExport MagickBooleanType GetMagickEndianSupport(
398 const MagickInfo *magick_info)
400 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
401 assert(magick_info != (MagickInfo *) NULL);
402 assert(magick_info->signature == MagickSignature);
403 return(magick_info->endian_support);
407 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
411 + G e t M a g i c k I n f o %
415 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
417 % GetMagickInfo() returns a pointer MagickInfo structure that matches
418 % the specified name. If name is NULL, the head of the image format list
421 % The format of the GetMagickInfo method is:
423 % const MagickInfo *GetMagickInfo(const char *name,Exception *exception)
425 % A description of each parameter follows:
427 % o name: the image format we are looking for.
429 % o exception: return any errors or warnings in this structure.
432 MagickExport const MagickInfo *GetMagickInfo(const char *name,
433 ExceptionInfo *exception)
435 register const MagickInfo
438 assert(exception != (ExceptionInfo *) NULL);
439 if ((magick_list == (SplayTreeInfo *) NULL) ||
440 (instantiate_magick == MagickFalse))
441 if (InitializeMagickList(exception) == MagickFalse)
442 return((const MagickInfo *) NULL);
443 if ((name == (const char *) NULL) || (LocaleCompare(name,"*") == 0))
445 #if defined(MAGICKCORE_MODULES_SUPPORT)
446 if (LocaleCompare(name,"*") == 0)
447 (void) OpenModules(exception);
449 AcquireSemaphoreInfo(&magick_semaphore);
450 ResetSplayTreeIterator(magick_list);
451 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
452 RelinquishSemaphoreInfo(magick_semaphore);
458 AcquireSemaphoreInfo(&magick_semaphore);
459 ResetSplayTreeIterator(magick_list);
460 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
461 while (p != (const MagickInfo *) NULL)
463 if (LocaleCompare(p->name,name) == 0)
465 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
467 #if defined(MAGICKCORE_MODULES_SUPPORT)
468 if (p == (const MagickInfo *) NULL)
471 (void) OpenModule(name,exception);
472 ResetSplayTreeIterator(magick_list);
473 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
474 while (p != (const MagickInfo *) NULL)
476 if (LocaleCompare(p->name,name) == 0)
478 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
482 RelinquishSemaphoreInfo(magick_semaphore);
487 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
491 + G e t M a g i c k I n f o L i s t %
495 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
497 % GetMagickInfoList() returns any image formats that match the specified
500 % The format of the GetMagickInfoList function is:
502 % const MagickInfo **GetMagickInfoList(const char *pattern,
503 % unsigned long *number_formats,ExceptionInfo *exception)
505 % A description of each parameter follows:
507 % o pattern: Specifies a pointer to a text string containing a pattern.
509 % o number_formats: This integer returns the number of formats in the list.
511 % o exception: return any errors or warnings in this structure.
515 #if defined(__cplusplus) || defined(c_plusplus)
519 static int MagickInfoCompare(const void *x,const void *y)
525 p=(const MagickInfo **) x,
526 q=(const MagickInfo **) y;
527 return(LocaleCompare((*p)->name,(*q)->name));
530 #if defined(__cplusplus) || defined(c_plusplus)
534 MagickExport const MagickInfo **GetMagickInfoList(const char *pattern,
535 unsigned long *number_formats,ExceptionInfo *exception)
540 register const MagickInfo
547 Allocate magick list.
549 assert(pattern != (char *) NULL);
550 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
551 assert(number_formats != (unsigned long *) NULL);
553 p=GetMagickInfo("*",exception);
554 if (p == (const MagickInfo *) NULL)
555 return((const MagickInfo **) NULL);
556 formats=(const MagickInfo **) AcquireQuantumMemory((size_t)
557 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
558 if (formats == (const MagickInfo **) NULL)
559 return((const MagickInfo **) NULL);
561 Generate magick list.
563 AcquireSemaphoreInfo(&magick_semaphore);
564 ResetSplayTreeIterator(magick_list);
565 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
566 for (i=0; p != (const MagickInfo *) NULL; )
568 if ((p->stealth == MagickFalse) &&
569 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
571 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
573 RelinquishSemaphoreInfo(magick_semaphore);
574 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickInfoCompare);
575 formats[i]=(MagickInfo *) NULL;
576 *number_formats=(unsigned long) i;
581 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
585 + G e t M a g i c k L i s t %
589 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
591 % GetMagickList() returns any image formats that match the specified pattern.
593 % The format of the GetMagickList function is:
595 % char **GetMagickList(const char *pattern,unsigned long *number_formats,
596 % ExceptionInfo *exception)
598 % A description of each parameter follows:
600 % o pattern: Specifies a pointer to a text string containing a pattern.
602 % o number_formats: This integer returns the number of formats in the list.
604 % o exception: return any errors or warnings in this structure.
608 #if defined(__cplusplus) || defined(c_plusplus)
612 static int MagickCompare(const void *x,const void *y)
620 return(LocaleCompare(*p,*q));
623 #if defined(__cplusplus) || defined(c_plusplus)
627 MagickExport char **GetMagickList(const char *pattern,
628 unsigned long *number_formats,ExceptionInfo *exception)
633 register const MagickInfo
640 Allocate magick list.
642 assert(pattern != (char *) NULL);
643 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
644 assert(number_formats != (unsigned long *) NULL);
646 p=GetMagickInfo("*",exception);
647 if (p == (const MagickInfo *) NULL)
648 return((char **) NULL);
649 formats=(char **) AcquireQuantumMemory((size_t)
650 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
651 if (formats == (char **) NULL)
652 return((char **) NULL);
653 AcquireSemaphoreInfo(&magick_semaphore);
654 ResetSplayTreeIterator(magick_list);
655 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
656 for (i=0; p != (const MagickInfo *) NULL; )
658 if ((p->stealth == MagickFalse) &&
659 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
660 formats[i++]=ConstantString(p->name);
661 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
663 RelinquishSemaphoreInfo(magick_semaphore);
664 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickCompare);
665 formats[i]=(char *) NULL;
666 *number_formats=(unsigned long) i;
671 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
675 + G e t M a g i c k E n d i a n S u p p o r t %
679 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
681 % GetMagickRawSupport() returns the MagickTrue if the coder is a raw format.
683 % The format of the GetMagickRawSupport method is:
685 % MagickBooleanType GetMagickRawSupport(const MagickInfo *magick_info)
687 % A description of each parameter follows:
689 % o magick_info: The magick info.
692 MagickExport MagickBooleanType GetMagickRawSupport(
693 const MagickInfo *magick_info)
695 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
696 assert(magick_info != (MagickInfo *) NULL);
697 assert(magick_info->signature == MagickSignature);
698 return(magick_info->raw);
702 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
706 + G e t M a g i c k S e e k a b l e S t r e a m %
710 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
712 % GetMagickSeekableStream() returns MagickTrue if the magick supports a
715 % The format of the GetMagickSeekableStream method is:
717 % MagickBooleanType GetMagickSeekableStream(const MagickInfo *magick_info)
719 % A description of each parameter follows:
721 % o magick_info: The magick info.
724 MagickExport MagickBooleanType GetMagickSeekableStream(
725 const MagickInfo *magick_info)
727 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
728 assert(magick_info != (MagickInfo *) NULL);
729 assert(magick_info->signature == MagickSignature);
730 return(magick_info->seekable_stream);
734 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
738 + G e t M a g i c k T h r e a d S u p p o r t %
742 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
744 % GetMagickThreadSupport() returns MagickTrue if the magick supports threads.
746 % The format of the GetMagickThreadSupport method is:
748 % MagickStatusType GetMagickThreadSupport(const MagickInfo *magick_info)
750 % A description of each parameter follows:
752 % o magick_info: The magick info.
755 MagickExport MagickStatusType GetMagickThreadSupport(
756 const MagickInfo *magick_info)
758 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
759 assert(magick_info != (MagickInfo *) NULL);
760 assert(magick_info->signature == MagickSignature);
761 return(magick_info->thread_support);
765 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
769 + I n i t i a l i z e M a g i c k L i s t %
773 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
775 % InitializeMagickList() initializes the magick list.
777 % The format of the InitializeMagickList() method is:
779 % InitializeMagickList(Exceptioninfo *exception)
781 % A description of each parameter follows.
783 % o exception: return any errors or warnings in this structure.
787 static void *DestroyMagickNode(void *magick_info)
792 p=(MagickInfo *) magick_info;
793 if (p->name != (char *) NULL)
794 p->name=DestroyString(p->name);
795 if (p->description != (char *) NULL)
796 p->description=DestroyString(p->description);
797 if (p->version != (char *) NULL)
798 p->version=DestroyString(p->version);
799 if (p->note != (char *) NULL)
800 p->note=DestroyString(p->note);
801 if (p->module != (char *) NULL)
802 p->module=DestroyString(p->module);
803 return(RelinquishMagickMemory(p));
806 static MagickBooleanType InitializeMagickList(ExceptionInfo *exception)
809 if ((magick_list == (SplayTreeInfo *) NULL) &&
810 (instantiate_magick == MagickFalse))
812 AcquireSemaphoreInfo(&magick_semaphore);
813 if ((magick_list == (SplayTreeInfo *) NULL) &&
814 (instantiate_magick == MagickFalse))
822 magick_list=NewSplayTree(CompareSplayTreeString,
823 (void *(*)(void *)) NULL,DestroyMagickNode);
824 if (magick_list == (SplayTreeInfo *) NULL)
825 ThrowFatalException(ResourceLimitFatalError,
826 "MemoryAllocationFailed");
827 magick_info=SetMagickInfo("ephemeral");
828 magick_info->stealth=MagickTrue;
829 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
830 if (status == MagickFalse)
831 ThrowFatalException(ResourceLimitFatalError,
832 "MemoryAllocationFailed");
833 magick_info=SetMagickInfo("clipmask");
834 magick_info->stealth=MagickTrue;
835 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
836 if (status == MagickFalse)
841 message=GetExceptionMessage(errno);
842 ThrowFatalException(ResourceLimitFatalError,
843 "MemoryAllocationFailed");
844 message=DestroyString(message);
846 #if defined(MAGICKCORE_MODULES_SUPPORT)
847 (void) GetModuleInfo((char *) NULL,exception);
849 #if !defined(MAGICKCORE_BUILD_MODULES)
850 RegisterStaticModules();
852 instantiate_magick=MagickTrue;
854 RelinquishSemaphoreInfo(magick_semaphore);
856 return(magick_list != (SplayTreeInfo *) NULL ? MagickTrue : MagickFalse);
860 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
864 + I n s t a n t i a t e M a g i c k C o m p o n e n t %
868 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
870 % InstantiateMagickComponent() instantiates the magick component.
872 % The format of the InstantiateMagickComponent method is:
874 % MagickBooleanType InstantiateMagickComponent(void)
877 MagickExport MagickBooleanType InstantiateMagickComponent(void)
879 AcquireSemaphoreInfo(&magick_semaphore);
880 RelinquishSemaphoreInfo(magick_semaphore);
885 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
889 + I s M a g i c k C o n f l i c t %
893 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
895 % IsMagickConflict() returns MagickTrue if the image format is not a valid
896 % image format or conflicts with a logical drive (.e.g. X:).
898 % The format of the IsMagickConflict method is:
900 % MagickBooleanType IsMagickConflict(const char *magick)
902 % A description of each parameter follows:
904 % o magick: Specifies the image format.
907 MagickExport MagickBooleanType IsMagickConflict(const char *magick)
918 assert(magick != (char *) NULL);
919 exception=AcquireExceptionInfo();
920 magick_info=GetMagickInfo(magick,exception);
921 delegate_info=GetDelegateInfo(magick,(char *) NULL,exception);
922 if (delegate_info == (const DelegateInfo *) NULL)
923 delegate_info=GetDelegateInfo((char *) NULL,magick,exception);
924 exception=DestroyExceptionInfo(exception);
925 if ((magick_info == (const MagickInfo *) NULL) &&
926 (delegate_info == (const DelegateInfo *) NULL))
928 #if defined(macintosh)
929 return(MACIsMagickConflict(magick));
931 return(VMSIsMagickConflict(magick));
932 #elif defined(__WINDOWS__)
933 return(NTIsMagickConflict(magick));
940 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
944 + L i s t M a g i c k I n f o %
948 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
950 % ListMagickInfo() lists the image formats to a file.
952 % The format of the ListMagickInfo method is:
954 % MagickBooleanType ListMagickInfo(FILE *file,ExceptionInfo *exception)
956 % A description of each parameter follows.
958 % o file: A file handle.
960 % o exception: return any errors or warnings in this structure.
963 MagickExport MagickBooleanType ListMagickInfo(FILE *file,
964 ExceptionInfo *exception)
978 if (file == (FILE *) NULL)
980 magick_info=GetMagickInfoList("*",&number_formats,exception);
981 if (magick_info == (const MagickInfo **) NULL)
983 ClearMagickException(exception);
984 #if !defined(MAGICKCORE_MODULES_SUPPORT)
985 (void) fprintf(file," Format Mode Description\n");
987 (void) fprintf(file," Format Module Mode Description\n");
989 (void) fprintf(file,"--------------------------------------------------------"
990 "-----------------------\n");
991 for (i=0; i < (long) number_formats; i++)
993 if (magick_info[i]->stealth != MagickFalse)
995 (void) fprintf(file,"%9s%c ",magick_info[i]->name != (char *) NULL ?
996 magick_info[i]->name : "",
997 magick_info[i]->blob_support != MagickFalse ? '*' : ' ');
998 #if defined(MAGICKCORE_MODULES_SUPPORT)
1001 module[MaxTextExtent];
1004 if (magick_info[i]->module != (char *) NULL)
1005 (void) CopyMagickString(module,magick_info[i]->module,MaxTextExtent);
1006 (void) ConcatenateMagickString(module," ",MaxTextExtent);
1008 (void) fprintf(file,"%9s ",module);
1011 (void) fprintf(file,"%c%c%c ",magick_info[i]->decoder ? 'r' : '-',
1012 magick_info[i]->encoder ? 'w' : '-',magick_info[i]->encoder != NULL &&
1013 magick_info[i]->adjoin != MagickFalse ? '+' : '-');
1014 if (magick_info[i]->description != (char *) NULL)
1015 (void) fprintf(file," %s",magick_info[i]->description);
1016 if (magick_info[i]->version != (char *) NULL)
1017 (void) fprintf(file," (%s)",magick_info[i]->version);
1018 (void) fprintf(file,"\n");
1019 if (magick_info[i]->note != (char *) NULL)
1024 text=StringToList(magick_info[i]->note);
1025 if (text != (char **) NULL)
1027 for (j=0; text[j] != (char *) NULL; j++)
1029 (void) fprintf(file," %s\n",text[j]);
1030 text[j]=DestroyString(text[j]);
1032 text=(char **) RelinquishMagickMemory(text);
1036 (void) fprintf(file,"\n* native blob support\n");
1037 (void) fprintf(file,"r read support\n");
1038 (void) fprintf(file,"w write support\n");
1039 (void) fprintf(file,"+ support for multiple images\n");
1040 (void) fflush(file);
1041 magick_info=(const MagickInfo **) RelinquishMagickMemory((void *)
1047 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1051 % I s M a g i c k I n s t a n t i a t e d %
1055 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1057 % IsMagickInstantiated() returns MagickTrue if the ImageMagick environment
1058 % is currently instantiated: MagickCoreGenesis() has been called but
1059 % MagickDestroy() has not.
1061 % The format of the IsMagickInstantiated method is:
1063 % MagickBooleanType IsMagickInstantiated(void)
1066 MagickExport MagickBooleanType IsMagickInstantiated(void)
1068 return(instantiate_magick);
1072 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1076 % M a g i c k C o r e G e n e s i s %
1080 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1082 % MagickCoreGenesis() initializes the MagickCore environment.
1084 % The format of the MagickCoreGenesis function is:
1086 % MagickCoreGenesis(const char *path,
1087 % const MagickBooleanType establish_signal_handlers)
1089 % A description of each parameter follows:
1091 % o path: the execution path of the current ImageMagick client.
1093 % o establish_signal_handlers: set to MagickTrue to use MagickCore's own
1094 % signal handlers for common signals.
1098 static SignalHandler *SetMagickSignalHandler(int signal_number,
1099 SignalHandler *handler)
1101 #if defined(MAGICKCORE_HAVE_SIGACTION) && defined(MAGICKCORE_HAVE_SIGEMPTYSET)
1113 sigaddset(&mask,signal_number);
1114 sigprocmask(SIG_BLOCK,&mask,NULL);
1115 action.sa_mask=mask;
1116 action.sa_handler=handler;
1118 #if defined(SA_INTERRUPT)
1119 action.sa_flags|=SA_INTERRUPT;
1121 status=sigaction(signal_number,&action,&previous_action);
1124 sigprocmask(SIG_UNBLOCK,&mask,NULL);
1125 return(previous_action.sa_handler);
1127 return(signal(signal_number,handler));
1131 static void MagickSignalHandler(int signal_number)
1133 #if !defined(MAGICKCORE_HAVE_SIGACTION)
1134 (void) signal(signal_number,SIG_IGN);
1136 AsynchronousDestroyResourceComponent();
1137 instantiate_magick=MagickFalse;
1138 (void) SetMagickSignalHandler(signal_number,signal_handlers[signal_number]);
1139 #if defined(MAGICKCORE_HAVE_RAISE)
1140 if (signal_handlers[signal_number] != MagickSignalHandler)
1141 raise(signal_number);
1143 #if !defined(MAGICKCORE_HAVE__EXIT)
1144 exit(signal_number);
1147 if (signal_number == SIGHUP)
1148 exit(signal_number);
1150 #if defined(SIGINT) && !defined(__WINDOWS__)
1151 if (signal_number == SIGINT)
1152 exit(signal_number);
1154 #if defined(SIGTERM)
1155 if (signal_number == SIGTERM)
1156 exit(signal_number);
1158 _exit(signal_number);
1162 static SignalHandler *RegisterMagickSignalHandler(int signal_number)
1167 handler=SetMagickSignalHandler(signal_number,MagickSignalHandler);
1168 if (handler == SIG_ERR)
1170 if (handler != SIG_DFL)
1171 handler=SetMagickSignalHandler(signal_number,handler);
1173 (void) LogMagickEvent(ConfigureEvent,GetMagickModule(),
1174 "Register handler for signal: %d",signal_number);
1178 MagickExport void MagickCoreGenesis(const char *path,
1179 const MagickBooleanType establish_signal_handlers)
1183 execution_path[MaxTextExtent],
1184 filename[MaxTextExtent];
1193 Initialize the Magick environment.
1195 (void) setlocale(LC_ALL,"");
1196 (void) setlocale(LC_NUMERIC,"C");
1197 (void) InstantiateSemaphoreComponent();
1198 (void) InstantiateLogComponent();
1199 (void) InstantiateLocaleComponent();
1200 (void) InstantiateRandomComponent();
1201 seconds=time((time_t *) NULL);
1202 events=GetEnvironmentValue("MAGICK_DEBUG");
1203 if (events != (char *) NULL)
1205 (void) SetLogEventMask(events);
1206 events=DestroyString(events);
1208 #if defined(__WINDOWS__)
1209 #if defined(_DEBUG) && !defined(__BORLANDC__) && !defined(__MINGW32__)
1210 if (IsEventLogging() != MagickFalse)
1215 debug=_CrtSetDbgFlag(_CRTDBG_REPORT_FLAG);
1216 debug|=_CRTDBG_CHECK_ALWAYS_DF |_CRTDBG_DELAY_FREE_MEM_DF |
1217 _CRTDBG_LEAK_CHECK_DF;
1220 debug=_CrtSetDbgFlag(debug);
1221 _ASSERTE(_CrtCheckMemory());
1227 Set client name and execution path.
1229 (void) GetExecutionPath(execution_path,MaxTextExtent);
1230 if ((path != (const char *) NULL) && (*path != '\0'))
1231 (void) CopyMagickString(execution_path,path,MaxTextExtent);
1232 GetPathComponent(execution_path,TailPath,filename);
1233 (void) SetClientName(filename);
1234 GetPathComponent(execution_path,HeadPath,execution_path);
1235 (void) SetClientPath(execution_path);
1236 if (establish_signal_handlers != MagickFalse)
1239 Set signal handlers.
1241 #if defined(SIGABRT)
1242 if (signal_handlers[SIGABRT] == (SignalHandler *) NULL)
1243 signal_handlers[SIGABRT]=RegisterMagickSignalHandler(SIGABRT);
1246 if (signal_handlers[SIGFPE] == (SignalHandler *) NULL)
1247 signal_handlers[SIGFPE]=RegisterMagickSignalHandler(SIGFPE);
1250 if (signal_handlers[SIGHUP] == (SignalHandler *) NULL)
1251 signal_handlers[SIGHUP]=RegisterMagickSignalHandler(SIGHUP);
1253 #if defined(SIGINT) && !defined(__WINDOWS__)
1254 if (signal_handlers[SIGINT] == (SignalHandler *) NULL)
1255 signal_handlers[SIGINT]=RegisterMagickSignalHandler(SIGINT);
1257 #if defined(SIGQUIT)
1258 if (signal_handlers[SIGQUIT] == (SignalHandler *) NULL)
1259 signal_handlers[SIGQUIT]=RegisterMagickSignalHandler(SIGQUIT);
1261 #if defined(SIGTERM)
1262 if (signal_handlers[SIGTERM] == (SignalHandler *) NULL)
1263 signal_handlers[SIGTERM]=RegisterMagickSignalHandler(SIGTERM);
1265 #if defined(SIGXCPU)
1266 if (signal_handlers[SIGXCPU] == (SignalHandler *) NULL)
1267 signal_handlers[SIGXCPU]=RegisterMagickSignalHandler(SIGXCPU);
1269 #if defined(SIGXFSZ)
1270 if (signal_handlers[SIGXFSZ] == (SignalHandler *) NULL)
1271 signal_handlers[SIGXFSZ]=RegisterMagickSignalHandler(SIGXFSZ);
1275 Initialize magick resources.
1277 (void) InstantiatePolicyComponent();
1278 (void) InstantiateCacheComponent();
1279 (void) InstantiateRegistryComponent();
1280 (void) InstantiateResourcesComponent();
1281 (void) InstantiateCoderComponent();
1282 (void) InstantiateMagickComponent();
1283 (void) InstantiateModuleComponent();
1284 (void) InstantiateDelegateComponent();
1285 (void) InstantiateMagicComponent();
1286 (void) InstantiateColorComponent();
1287 (void) InstantiateTypeComponent();
1288 (void) InstantiateConfigureComponent();
1289 (void) InstantiateMimeComponent();
1290 (void) InstantiateConstituteComponent();
1291 exception=AcquireExceptionInfo();
1292 #if defined(MAGICKCORE_MODULES_SUPPORT)
1293 InitializeModuleList(exception);
1295 exception=DestroyExceptionInfo(exception);
1296 (void) InstantiateLogComponent();
1300 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1304 % M a g i c k C o r e T e r m i n u s %
1308 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1310 % MagickCoreTerminus() destroys the MagickCore environment.
1312 % The format of the DestroyMagick function is:
1314 % MagickCoreTerminus(void)
1317 MagickExport void MagickCoreTerminus(void)
1319 #if defined(MAGICKCORE_X11_DELEGATE)
1320 DestroyXResources();
1322 DestroyConstituteComponent();
1323 DestroyMimeComponent();
1324 DestroyConfigureComponent();
1325 DestroyTypeComponent();
1326 DestroyColorComponent();
1327 #if defined(__WINDOWS__)
1328 NTGhostscriptUnLoadDLL();
1330 DestroyMagicComponent();
1331 DestroyDelegateComponent();
1332 DestroyMagickComponent();
1333 DestroyCoderComponent();
1334 DestroyResourceComponent();
1335 DestroyRegistryComponent();
1336 DestroyCacheFaclity();
1337 DestroyPolicyComponent();
1338 DestroyRandomComponent();
1339 DestroyLocaleComponent();
1340 DestroyLogComponent();
1341 DestroySemaphoreComponent();
1342 instantiate_magick=MagickFalse;
1346 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1350 + R e g i s t e r M a g i c k I n f o %
1354 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1356 % RegisterMagickInfo() adds attributes for a particular image format to the
1357 % list of supported formats. The attributes include the image format name,
1358 % a method to read and/or write the format, whether the format supports the
1359 % saving of more than one frame to the same file or blob, whether the format
1360 % supports native in-memory I/O, and a brief description of the format.
1362 % The format of the RegisterMagickInfo method is:
1364 % MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1366 % A description of each parameter follows:
1368 % o magick_info: the magick info.
1371 MagickExport MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1377 Delete any existing name.
1379 assert(magick_info != (MagickInfo *) NULL);
1380 assert(magick_info->signature == MagickSignature);
1381 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",magick_info->name);
1382 if (magick_list == (SplayTreeInfo *) NULL)
1383 return((MagickInfo *) NULL);
1384 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
1385 if (status == MagickFalse)
1386 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1387 return(magick_info);
1391 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1395 + S e t M a g i c k I n f o %
1399 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1401 % SetMagickInfo() allocates a MagickInfo structure and initializes the members
1402 % to default values.
1404 % The format of the SetMagickInfo method is:
1406 % MagickInfo *SetMagickInfo(const char *name)
1408 % A description of each parameter follows:
1410 % o magick_info: Method SetMagickInfo returns the allocated and initialized
1411 % MagickInfo structure.
1413 % o name: a character string that represents the image format associated
1414 % with the MagickInfo structure.
1417 MagickExport MagickInfo *SetMagickInfo(const char *name)
1422 assert(name != (const char *) NULL);
1423 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",name);
1424 magick_info=(MagickInfo *) AcquireMagickMemory(sizeof(*magick_info));
1425 if (magick_info == (MagickInfo *) NULL)
1426 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1427 (void) ResetMagickMemory(magick_info,0,sizeof(*magick_info));
1428 magick_info->name=ConstantString(name);
1429 magick_info->adjoin=MagickTrue;
1430 magick_info->blob_support=MagickTrue;
1431 magick_info->thread_support=(MagickStatusType) (DecoderThreadSupport |
1432 EncoderThreadSupport);
1433 magick_info->signature=MagickSignature;
1434 return(magick_info);
1438 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1442 + U n r e g i s t e r M a g i c k I n f o %
1446 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1448 % UnregisterMagickInfo() removes a name from the magick info list. It returns
1449 % MagickFalse if the name does not exist in the list otherwise MagickTrue.
1451 % The format of the UnregisterMagickInfo method is:
1453 % MagickBooleanType UnregisterMagickInfo(const char *name)
1455 % A description of each parameter follows:
1457 % o name: a character string that represents the image format we are
1461 MagickExport MagickBooleanType UnregisterMagickInfo(const char *name)
1463 register const MagickInfo
1469 assert(name != (const char *) NULL);
1470 if (magick_list == (SplayTreeInfo *) NULL)
1471 return(MagickFalse);
1472 if (GetNumberOfNodesInSplayTree(magick_list) == 0)
1473 return(MagickFalse);
1474 AcquireSemaphoreInfo(&magick_semaphore);
1475 ResetSplayTreeIterator(magick_list);
1476 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1477 while (p != (const MagickInfo *) NULL)
1479 if (LocaleCompare(p->name,name) == 0)
1481 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1483 status=DeleteNodeByValueFromSplayTree(magick_list,p);
1484 RelinquishSemaphoreInfo(magick_semaphore);