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-2011 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 "MagickCore/studio.h"
44 #include "MagickCore/annotate-private.h"
45 #include "MagickCore/blob.h"
46 #include "MagickCore/blob-private.h"
47 #include "MagickCore/cache.h"
48 #include "MagickCore/cache-private.h"
49 #include "MagickCore/coder-private.h"
50 #include "MagickCore/client.h"
51 #include "MagickCore/color-private.h"
52 #include "MagickCore/configure-private.h"
53 #include "MagickCore/constitute-private.h"
54 #include "MagickCore/delegate-private.h"
55 #include "MagickCore/draw.h"
56 #include "MagickCore/exception.h"
57 #include "MagickCore/exception-private.h"
58 #include "MagickCore/locale-private.h"
59 #include "MagickCore/log-private.h"
60 #include "MagickCore/magic-private.h"
61 #include "MagickCore/magick.h"
62 #include "MagickCore/magick-private.h"
63 #include "MagickCore/memory_.h"
64 #include "MagickCore/mime-private.h"
65 #include "MagickCore/module.h"
66 #include "MagickCore/module-private.h"
67 #if defined(MAGICKCORE_WINDOWS_SUPPORT)
68 # include "MagickCore/nt-feature.h"
70 #include "MagickCore/random-private.h"
71 #include "MagickCore/registry.h"
72 #include "MagickCore/registry-private.h"
73 #include "MagickCore/resource_.h"
74 #include "MagickCore/resource-private.h"
75 #include "MagickCore/policy.h"
76 #include "MagickCore/policy-private.h"
77 #include "MagickCore/semaphore.h"
78 #include "MagickCore/semaphore-private.h"
79 #include "MagickCore/signature-private.h"
80 #include "MagickCore/splay-tree.h"
81 #include "MagickCore/string_.h"
82 #include "MagickCore/string-private.h"
83 #include "MagickCore/thread_.h"
84 #include "MagickCore/thread-private.h"
85 #include "MagickCore/type-private.h"
86 #include "MagickCore/token.h"
87 #include "MagickCore/utility.h"
88 #include "MagickCore/utility-private.h"
89 #include "MagickCore/xwindow-private.h"
94 #if !defined(MAGICKCORE_RETSIGTYPE)
95 # define MAGICKCORE_RETSIGTYPE void
98 # define SIG_DFL ((SignalHandler *) 0)
100 #if !defined(SIG_ERR)
101 # define SIG_ERR ((SignalHandler *) -1)
108 Typedef declarations.
110 typedef MAGICKCORE_RETSIGTYPE
117 *magick_semaphore = (SemaphoreInfo *) NULL;
120 *signal_handlers[SIGMAX] = { (SignalHandler *) NULL };
123 *magick_list = (SplayTreeInfo *) NULL;
125 static volatile MagickBooleanType
126 instantiate_magick = MagickFalse,
127 instantiate_magickcore = MagickFalse;
130 Forward declarations.
132 static MagickBooleanType
133 InitializeMagickList(ExceptionInfo *);
136 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
140 + G e t I m a g e D e c o d e r %
144 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
146 % GetImageDecoder() returns the image decoder.
148 % The format of the GetImageDecoder method is:
150 % DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
152 % A description of each parameter follows:
154 % o magick_info: The magick info.
157 MagickExport DecodeImageHandler *GetImageDecoder(const MagickInfo *magick_info)
159 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
160 assert(magick_info != (MagickInfo *) NULL);
161 assert(magick_info->signature == MagickSignature);
162 return(magick_info->decoder);
166 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
170 + G e t I m a g e E n c o d e r %
174 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
176 % GetImageEncoder() returns the image encoder.
178 % The format of the GetImageEncoder method is:
180 % EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
182 % A description of each parameter follows:
184 % o magick_info: The magick info.
187 MagickExport EncodeImageHandler *GetImageEncoder(const MagickInfo *magick_info)
189 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
190 assert(magick_info != (MagickInfo *) NULL);
191 assert(magick_info->signature == MagickSignature);
192 return(magick_info->encoder);
196 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
200 + G e t I m a g e M a g i c k %
204 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
206 % GetImageMagick() searches for an image format that matches the specified
207 % magick string. If one is found, MagickTrue is returned otherwise
210 % The format of the GetImageMagick method is:
212 % MagickBooleanType GetImageMagick(const unsigned char *magick,
213 % const size_t length,char *format)
215 % A description of each parameter follows:
217 % o magick: the image format we are searching for.
219 % o length: the length of the binary string.
221 % o format: the image format as determined by the magick bytes.
224 MagickExport MagickBooleanType GetImageMagick(const unsigned char *magick,
225 const size_t length,char *format)
233 register const MagickInfo
236 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
237 assert(magick != (const unsigned char *) NULL);
238 exception=AcquireExceptionInfo();
239 p=GetMagickInfo("*",exception);
240 exception=DestroyExceptionInfo(exception);
241 if (p == (const MagickInfo *) NULL)
244 LockSemaphoreInfo(magick_semaphore);
245 ResetSplayTreeIterator(magick_list);
246 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
247 while (p != (const MagickInfo *) NULL)
249 if ((p->magick != (IsImageFormatHandler *) NULL) &&
250 (p->magick(magick,length) != 0))
253 (void) CopyMagickString(format,p->name,MaxTextExtent);
256 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
258 UnlockSemaphoreInfo(magick_semaphore);
263 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
267 + G e t M a g i c k A d j o i n %
271 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
273 % GetMagickAdjoin() returns MagickTrue if the magick adjoin is MagickTrue.
275 % The format of the GetMagickAdjoin method is:
277 % MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
279 % A description of each parameter follows:
281 % o magick_info: The magick info.
284 MagickExport MagickBooleanType GetMagickAdjoin(const MagickInfo *magick_info)
286 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
287 assert(magick_info != (MagickInfo *) NULL);
288 assert(magick_info->signature == MagickSignature);
289 return(magick_info->adjoin);
293 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
297 + G e t M a g i c k B l o b S u p p o r t %
301 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
303 % GetMagickBlobSupport() returns MagickTrue if the magick supports blobs.
305 % The format of the GetMagickBlobSupport method is:
307 % MagickBooleanType GetMagickBlobSupport(const MagickInfo *magick_info)
309 % A description of each parameter follows:
311 % o magick_info: The magick info.
314 MagickExport MagickBooleanType GetMagickBlobSupport(
315 const MagickInfo *magick_info)
317 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
318 assert(magick_info != (MagickInfo *) NULL);
319 assert(magick_info->signature == MagickSignature);
320 return(magick_info->blob_support);
324 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
328 + G e t M a g i c k D e s c r i p t i o n %
332 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
334 % GetMagickDescription() returns the magick description.
336 % The format of the GetMagickDescription method is:
338 % const char *GetMagickDescription(const MagickInfo *magick_info)
340 % A description of each parameter follows:
342 % o magick_info: The magick info.
345 MagickExport const char *GetMagickDescription(const MagickInfo *magick_info)
347 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
348 assert(magick_info != (MagickInfo *) NULL);
349 assert(magick_info->signature == MagickSignature);
350 return(magick_info->description);
354 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
358 + G e t M a g i c k E n d i a n S u p p o r t %
362 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
364 % GetMagickEndianSupport() returns the MagickTrue if the coder respects
365 % endianness other than MSBEndian.
367 % The format of the GetMagickEndianSupport method is:
369 % MagickBooleanType GetMagickEndianSupport(const MagickInfo *magick_info)
371 % A description of each parameter follows:
373 % o magick_info: The magick info.
376 MagickExport MagickBooleanType GetMagickEndianSupport(
377 const MagickInfo *magick_info)
379 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
380 assert(magick_info != (MagickInfo *) NULL);
381 assert(magick_info->signature == MagickSignature);
382 return(magick_info->endian_support);
386 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
390 + G e t M a g i c k I n f o %
394 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
396 % GetMagickInfo() returns a pointer MagickInfo structure that matches
397 % the specified name. If name is NULL, the head of the image format list
400 % The format of the GetMagickInfo method is:
402 % const MagickInfo *GetMagickInfo(const char *name,Exception *exception)
404 % A description of each parameter follows:
406 % o name: the image format we are looking for.
408 % o exception: return any errors or warnings in this structure.
411 MagickExport const MagickInfo *GetMagickInfo(const char *name,
412 ExceptionInfo *exception)
414 register const MagickInfo
417 assert(exception != (ExceptionInfo *) NULL);
418 if ((magick_list == (SplayTreeInfo *) NULL) ||
419 (instantiate_magick == MagickFalse))
420 if (InitializeMagickList(exception) == MagickFalse)
421 return((const MagickInfo *) NULL);
422 if ((name == (const char *) NULL) || (LocaleCompare(name,"*") == 0))
424 #if defined(MAGICKCORE_MODULES_SUPPORT)
425 if (LocaleCompare(name,"*") == 0)
426 (void) OpenModules(exception);
428 LockSemaphoreInfo(magick_semaphore);
429 ResetSplayTreeIterator(magick_list);
430 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
431 UnlockSemaphoreInfo(magick_semaphore);
437 LockSemaphoreInfo(magick_semaphore);
438 ResetSplayTreeIterator(magick_list);
439 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
440 while (p != (const MagickInfo *) NULL)
442 if (LocaleCompare(p->name,name) == 0)
444 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
446 #if defined(MAGICKCORE_MODULES_SUPPORT)
447 if (p == (const MagickInfo *) NULL)
450 (void) OpenModule(name,exception);
451 ResetSplayTreeIterator(magick_list);
452 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
453 while (p != (const MagickInfo *) NULL)
455 if (LocaleCompare(p->name,name) == 0)
457 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
461 UnlockSemaphoreInfo(magick_semaphore);
466 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
470 + G e t M a g i c k I n f o L i s t %
474 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
476 % GetMagickInfoList() returns any image formats that match the specified
479 % The format of the GetMagickInfoList function is:
481 % const MagickInfo **GetMagickInfoList(const char *pattern,
482 % size_t *number_formats,ExceptionInfo *exception)
484 % A description of each parameter follows:
486 % o pattern: Specifies a pointer to a text string containing a pattern.
488 % o number_formats: This integer returns the number of formats in the list.
490 % o exception: return any errors or warnings in this structure.
494 #if defined(__cplusplus) || defined(c_plusplus)
498 static int MagickInfoCompare(const void *x,const void *y)
504 p=(const MagickInfo **) x,
505 q=(const MagickInfo **) y;
506 return(LocaleCompare((*p)->name,(*q)->name));
509 #if defined(__cplusplus) || defined(c_plusplus)
513 MagickExport const MagickInfo **GetMagickInfoList(const char *pattern,
514 size_t *number_formats,ExceptionInfo *exception)
519 register const MagickInfo
526 Allocate magick list.
528 assert(pattern != (char *) NULL);
529 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
530 assert(number_formats != (size_t *) NULL);
532 p=GetMagickInfo("*",exception);
533 if (p == (const MagickInfo *) NULL)
534 return((const MagickInfo **) NULL);
535 formats=(const MagickInfo **) AcquireQuantumMemory((size_t)
536 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
537 if (formats == (const MagickInfo **) NULL)
538 return((const MagickInfo **) NULL);
540 Generate magick list.
542 LockSemaphoreInfo(magick_semaphore);
543 ResetSplayTreeIterator(magick_list);
544 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
545 for (i=0; p != (const MagickInfo *) NULL; )
547 if ((p->stealth == MagickFalse) &&
548 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
550 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
552 UnlockSemaphoreInfo(magick_semaphore);
553 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickInfoCompare);
554 formats[i]=(MagickInfo *) NULL;
555 *number_formats=(size_t) i;
560 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
564 + G e t M a g i c k L i s t %
568 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
570 % GetMagickList() returns any image formats that match the specified pattern.
572 % The format of the GetMagickList function is:
574 % char **GetMagickList(const char *pattern,size_t *number_formats,
575 % ExceptionInfo *exception)
577 % A description of each parameter follows:
579 % o pattern: Specifies a pointer to a text string containing a pattern.
581 % o number_formats: This integer returns the number of formats in the list.
583 % o exception: return any errors or warnings in this structure.
587 #if defined(__cplusplus) || defined(c_plusplus)
591 static int MagickCompare(const void *x,const void *y)
599 return(LocaleCompare(*p,*q));
602 #if defined(__cplusplus) || defined(c_plusplus)
606 MagickExport char **GetMagickList(const char *pattern,
607 size_t *number_formats,ExceptionInfo *exception)
612 register const MagickInfo
619 Allocate magick list.
621 assert(pattern != (char *) NULL);
622 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
623 assert(number_formats != (size_t *) NULL);
625 p=GetMagickInfo("*",exception);
626 if (p == (const MagickInfo *) NULL)
627 return((char **) NULL);
628 formats=(char **) AcquireQuantumMemory((size_t)
629 GetNumberOfNodesInSplayTree(magick_list)+1UL,sizeof(*formats));
630 if (formats == (char **) NULL)
631 return((char **) NULL);
632 LockSemaphoreInfo(magick_semaphore);
633 ResetSplayTreeIterator(magick_list);
634 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
635 for (i=0; p != (const MagickInfo *) NULL; )
637 if ((p->stealth == MagickFalse) &&
638 (GlobExpression(p->name,pattern,MagickFalse) != MagickFalse))
639 formats[i++]=ConstantString(p->name);
640 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
642 UnlockSemaphoreInfo(magick_semaphore);
643 qsort((void *) formats,(size_t) i,sizeof(*formats),MagickCompare);
644 formats[i]=(char *) NULL;
645 *number_formats=(size_t) i;
650 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
654 % G e t M a g i c k P r e c i s i o n %
658 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
660 % GetMagickPrecision() returns the maximum number of significant digits to be
663 % The format of the GetMagickPrecision method is:
665 % int GetMagickPrecision(void)
668 MagickExport int GetMagickPrecision(void)
670 #define MagickPrecision 6
672 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
673 if (SetMagickPrecision(0) == 0)
678 (void) SetMagickPrecision(MagickPrecision);
679 limit=GetEnvironmentValue("MAGICK_PRECISION");
680 if (limit == (char *) NULL)
681 limit=GetPolicyValue("precision");
682 if (limit != (char *) NULL)
684 (void) SetMagickPrecision(StringToInteger(limit));
685 limit=DestroyString(limit);
688 return(SetMagickPrecision(0));
692 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
696 + G e t M a g i c k R a w S u p p o r t %
700 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
702 % GetMagickRawSupport() returns the MagickTrue if the coder is a raw format.
704 % The format of the GetMagickRawSupport method is:
706 % MagickBooleanType GetMagickRawSupport(const MagickInfo *magick_info)
708 % A description of each parameter follows:
710 % o magick_info: The magick info.
713 MagickExport MagickBooleanType GetMagickRawSupport(
714 const MagickInfo *magick_info)
716 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
717 assert(magick_info != (MagickInfo *) NULL);
718 assert(magick_info->signature == MagickSignature);
719 return(magick_info->raw);
723 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
727 + G e t M a g i c k S e e k a b l e S t r e a m %
731 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
733 % GetMagickSeekableStream() returns MagickTrue if the magick supports a
736 % The format of the GetMagickSeekableStream method is:
738 % MagickBooleanType GetMagickSeekableStream(const MagickInfo *magick_info)
740 % A description of each parameter follows:
742 % o magick_info: The magick info.
745 MagickExport MagickBooleanType GetMagickSeekableStream(
746 const MagickInfo *magick_info)
748 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
749 assert(magick_info != (MagickInfo *) NULL);
750 assert(magick_info->signature == MagickSignature);
751 return(magick_info->seekable_stream);
755 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
759 + G e t M a g i c k T h r e a d S u p p o r t %
763 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
765 % GetMagickThreadSupport() returns MagickTrue if the magick supports threads.
767 % The format of the GetMagickThreadSupport method is:
769 % MagickStatusType GetMagickThreadSupport(const MagickInfo *magick_info)
771 % A description of each parameter follows:
773 % o magick_info: The magick info.
776 MagickExport MagickStatusType GetMagickThreadSupport(
777 const MagickInfo *magick_info)
779 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
780 assert(magick_info != (MagickInfo *) NULL);
781 assert(magick_info->signature == MagickSignature);
782 return(magick_info->thread_support);
786 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
790 + I n i t i a l i z e M a g i c k L i s t %
794 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
796 % InitializeMagickList() initializes the magick list.
798 % The format of the InitializeMagickList() method is:
800 % InitializeMagickList(Exceptioninfo *exception)
802 % A description of each parameter follows.
804 % o exception: return any errors or warnings in this structure.
808 static void *DestroyMagickNode(void *magick_info)
813 p=(MagickInfo *) magick_info;
814 if (p->name != (char *) NULL)
815 p->name=DestroyString(p->name);
816 if (p->description != (char *) NULL)
817 p->description=DestroyString(p->description);
818 if (p->version != (char *) NULL)
819 p->version=DestroyString(p->version);
820 if (p->note != (char *) NULL)
821 p->note=DestroyString(p->note);
822 if (p->module != (char *) NULL)
823 p->module=DestroyString(p->module);
824 return(RelinquishMagickMemory(p));
827 static MagickBooleanType InitializeMagickList(ExceptionInfo *exception)
830 if ((magick_list == (SplayTreeInfo *) NULL) &&
831 (instantiate_magick == MagickFalse))
833 if (magick_semaphore == (SemaphoreInfo *) NULL)
834 AcquireSemaphoreInfo(&magick_semaphore);
835 LockSemaphoreInfo(magick_semaphore);
836 if ((magick_list == (SplayTreeInfo *) NULL) &&
837 (instantiate_magick == MagickFalse))
845 magick_list=NewSplayTree(CompareSplayTreeString,
846 (void *(*)(void *)) NULL,DestroyMagickNode);
847 if (magick_list == (SplayTreeInfo *) NULL)
848 ThrowFatalException(ResourceLimitFatalError,
849 "MemoryAllocationFailed");
850 magick_info=SetMagickInfo("ephemeral");
851 magick_info->stealth=MagickTrue;
852 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
853 if (status == MagickFalse)
854 ThrowFatalException(ResourceLimitFatalError,
855 "MemoryAllocationFailed");
856 magick_info=SetMagickInfo("clipmask");
857 magick_info->stealth=MagickTrue;
858 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
859 if (status == MagickFalse)
864 message=GetExceptionMessage(errno);
865 ThrowFatalException(ResourceLimitFatalError,
866 "MemoryAllocationFailed");
867 message=DestroyString(message);
869 #if defined(MAGICKCORE_MODULES_SUPPORT)
870 (void) GetModuleInfo((char *) NULL,exception);
872 #if !defined(MAGICKCORE_BUILD_MODULES)
873 RegisterStaticModules();
875 instantiate_magick=MagickTrue;
877 UnlockSemaphoreInfo(magick_semaphore);
879 return(magick_list != (SplayTreeInfo *) NULL ? MagickTrue : MagickFalse);
883 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
887 + I s M a g i c k C o n f l i c t %
891 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
893 % IsMagickConflict() returns MagickTrue if the image format conflicts with a
894 % logical drive (.e.g. X:).
896 % The format of the IsMagickConflict method is:
898 % MagickBooleanType IsMagickConflict(const char *magick)
900 % A description of each parameter follows:
902 % o magick: Specifies the image format.
905 MagickPrivate MagickBooleanType IsMagickConflict(const char *magick)
907 assert(magick != (char *) NULL);
908 #if defined(macintosh)
909 return(MACIsMagickConflict(magick));
911 return(VMSIsMagickConflict(magick));
912 #elif defined(MAGICKCORE_WINDOWS_SUPPORT)
913 return(NTIsMagickConflict(magick));
920 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
924 + L i s t M a g i c k I n f o %
928 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
930 % ListMagickInfo() lists the image formats to a file.
932 % The format of the ListMagickInfo method is:
934 % MagickBooleanType ListMagickInfo(FILE *file,ExceptionInfo *exception)
936 % A description of each parameter follows.
938 % o file: A file handle.
940 % o exception: return any errors or warnings in this structure.
943 MagickExport MagickBooleanType ListMagickInfo(FILE *file,
944 ExceptionInfo *exception)
958 if (file == (FILE *) NULL)
960 magick_info=GetMagickInfoList("*",&number_formats,exception);
961 if (magick_info == (const MagickInfo **) NULL)
963 ClearMagickException(exception);
964 #if !defined(MAGICKCORE_MODULES_SUPPORT)
965 (void) FormatLocaleFile(file," Format Mode Description\n");
967 (void) FormatLocaleFile(file," Format Module Mode Description\n");
969 (void) FormatLocaleFile(file,
970 "--------------------------------------------------------"
971 "-----------------------\n");
972 for (i=0; i < (ssize_t) number_formats; i++)
974 if (magick_info[i]->stealth != MagickFalse)
976 (void) FormatLocaleFile(file,"%9s%c ",
977 magick_info[i]->name != (char *) NULL ? magick_info[i]->name : "",
978 magick_info[i]->blob_support != MagickFalse ? '*' : ' ');
979 #if defined(MAGICKCORE_MODULES_SUPPORT)
982 module[MaxTextExtent];
985 if (magick_info[i]->module != (char *) NULL)
986 (void) CopyMagickString(module,magick_info[i]->module,MaxTextExtent);
987 (void) ConcatenateMagickString(module," ",MaxTextExtent);
989 (void) FormatLocaleFile(file,"%9s ",module);
992 (void) FormatLocaleFile(file,"%c%c%c ",magick_info[i]->decoder ? 'r' : '-',
993 magick_info[i]->encoder ? 'w' : '-',magick_info[i]->encoder != NULL &&
994 magick_info[i]->adjoin != MagickFalse ? '+' : '-');
995 if (magick_info[i]->description != (char *) NULL)
996 (void) FormatLocaleFile(file," %s",magick_info[i]->description);
997 if (magick_info[i]->version != (char *) NULL)
998 (void) FormatLocaleFile(file," (%s)",magick_info[i]->version);
999 (void) FormatLocaleFile(file,"\n");
1000 if (magick_info[i]->note != (char *) NULL)
1005 text=StringToList(magick_info[i]->note);
1006 if (text != (char **) NULL)
1008 for (j=0; text[j] != (char *) NULL; j++)
1010 (void) FormatLocaleFile(file," %s\n",text[j]);
1011 text[j]=DestroyString(text[j]);
1013 text=(char **) RelinquishMagickMemory(text);
1017 (void) FormatLocaleFile(file,"\n* native blob support\n");
1018 (void) FormatLocaleFile(file,"r read support\n");
1019 (void) FormatLocaleFile(file,"w write support\n");
1020 (void) FormatLocaleFile(file,"+ support for multiple images\n");
1021 (void) fflush(file);
1022 magick_info=(const MagickInfo **) RelinquishMagickMemory((void *)
1028 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1032 % I s M a g i c k I n s t a n t i a t e d %
1036 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1038 % IsMagickInstantiated() returns MagickTrue if the ImageMagick environment
1039 % is currently instantiated: MagickCoreGenesis() has been called but
1040 % MagickDestroy() has not.
1042 % The format of the IsMagickInstantiated method is:
1044 % MagickBooleanType IsMagickInstantiated(void)
1047 MagickExport MagickBooleanType IsMagickInstantiated(void)
1049 return(instantiate_magick);
1053 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1057 + M a g i c k C o m p o n e n t G e n e s i s %
1061 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1063 % MagickComponentGenesis() instantiates the magick component.
1065 % The format of the MagickComponentGenesis method is:
1067 % MagickBooleanType MagickComponentGenesis(void)
1070 MagickPrivate MagickBooleanType MagickComponentGenesis(void)
1072 AcquireSemaphoreInfo(&magick_semaphore);
1077 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1081 + M a g i c k C o m p o n e n t T e r m i n u s %
1085 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1087 % MagickComponentTerminus() destroys the magick component.
1089 % The format of the MagickComponentTerminus method is:
1091 % void MagickComponentTerminus(void)
1094 MagickPrivate void MagickComponentTerminus(void)
1096 if (magick_semaphore == (SemaphoreInfo *) NULL)
1097 AcquireSemaphoreInfo(&magick_semaphore);
1098 LockSemaphoreInfo(magick_semaphore);
1099 if (magick_list != (SplayTreeInfo *) NULL)
1100 magick_list=DestroySplayTree(magick_list);
1101 instantiate_magick=MagickFalse;
1102 UnlockSemaphoreInfo(magick_semaphore);
1103 DestroySemaphoreInfo(&magick_semaphore);
1107 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1111 % M a g i c k C o r e G e n e s i s %
1115 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1117 % MagickCoreGenesis() initializes the MagickCore environment.
1119 % The format of the MagickCoreGenesis function is:
1121 % MagickCoreGenesis(const char *path,
1122 % const MagickBooleanType establish_signal_handlers)
1124 % A description of each parameter follows:
1126 % o path: the execution path of the current ImageMagick client.
1128 % o establish_signal_handlers: set to MagickTrue to use MagickCore's own
1129 % signal handlers for common signals.
1133 static SignalHandler *SetMagickSignalHandler(int signal_number,
1134 SignalHandler *handler)
1136 #if defined(MAGICKCORE_HAVE_SIGACTION) && defined(MAGICKCORE_HAVE_SIGEMPTYSET)
1148 sigaddset(&mask,signal_number);
1149 sigprocmask(SIG_BLOCK,&mask,NULL);
1150 action.sa_mask=mask;
1151 action.sa_handler=handler;
1153 #if defined(SA_INTERRUPT)
1154 action.sa_flags|=SA_INTERRUPT;
1156 status=sigaction(signal_number,&action,&previous_action);
1159 sigprocmask(SIG_UNBLOCK,&mask,NULL);
1160 return(previous_action.sa_handler);
1162 return(signal(signal_number,handler));
1166 static void MagickSignalHandler(int signal_number)
1168 #if !defined(MAGICKCORE_HAVE_SIGACTION)
1169 (void) signal(signal_number,SIG_IGN);
1171 AsynchronousResourceComponentTerminus();
1172 instantiate_magick=MagickFalse;
1173 (void) SetMagickSignalHandler(signal_number,signal_handlers[signal_number]);
1174 #if defined(MAGICKCORE_HAVE_RAISE)
1175 if (signal_handlers[signal_number] != MagickSignalHandler)
1176 raise(signal_number);
1178 #if defined(SIGQUIT)
1179 if (signal_number == SIGQUIT)
1182 #if defined(SIGABRT)
1183 if (signal_number == SIGABRT)
1187 if (signal_number == SIGFPE)
1190 #if defined(SIGXCPU)
1191 if (signal_number == SIGXCPU)
1194 #if defined(SIGXFSZ)
1195 if (signal_number == SIGXFSZ)
1198 #if defined(SIGSEGV)
1199 if (signal_number == SIGSEGV)
1202 #if !defined(MAGICKCORE_HAVE__EXIT)
1203 exit(signal_number);
1206 if (signal_number == SIGHUP)
1207 exit(signal_number);
1209 #if defined(SIGINT) && !defined(MAGICKCORE_WINDOWS_SUPPORT)
1210 if (signal_number == SIGINT)
1211 exit(signal_number);
1213 #if defined(SIGTERM)
1214 if (signal_number == SIGTERM)
1215 exit(signal_number);
1217 _exit(signal_number); /* do not invoke registered atexit() methods */
1221 static SignalHandler *RegisterMagickSignalHandler(int signal_number)
1226 handler=SetMagickSignalHandler(signal_number,MagickSignalHandler);
1227 if (handler == SIG_ERR)
1229 if (handler != SIG_DFL)
1230 handler=SetMagickSignalHandler(signal_number,handler);
1232 (void) LogMagickEvent(ConfigureEvent,GetMagickModule(),
1233 "Register handler for signal: %d",signal_number);
1237 MagickExport void MagickCoreGenesis(const char *path,
1238 const MagickBooleanType establish_signal_handlers)
1242 execution_path[MaxTextExtent],
1243 filename[MaxTextExtent];
1246 Initialize the Magick environment.
1249 if (instantiate_magickcore != MagickFalse)
1251 UnlockMagickMutex();
1254 (void) SemaphoreComponentGenesis();
1255 (void) LogComponentGenesis();
1256 (void) LocaleComponentGenesis();
1257 (void) RandomComponentGenesis();
1258 events=GetEnvironmentValue("MAGICK_DEBUG");
1259 if (events != (char *) NULL)
1261 (void) SetLogEventMask(events);
1262 events=DestroyString(events);
1264 #if defined(MAGICKCORE_WINDOWS_SUPPORT)
1265 #if defined(_DEBUG) && !defined(__BORLANDC__) && !defined(__MINGW32__)
1266 if (IsEventLogging() != MagickFalse)
1271 debug=_CrtSetDbgFlag(_CRTDBG_REPORT_FLAG);
1272 debug|=_CRTDBG_CHECK_ALWAYS_DF |_CRTDBG_DELAY_FREE_MEM_DF |
1273 _CRTDBG_LEAK_CHECK_DF;
1276 debug=_CrtSetDbgFlag(debug);
1277 _ASSERTE(_CrtCheckMemory());
1283 Set client name and execution path.
1285 (void) GetExecutionPath(execution_path,MaxTextExtent);
1286 if ((path != (const char *) NULL) && (*path != '\0'))
1287 (void) CopyMagickString(execution_path,path,MaxTextExtent);
1288 GetPathComponent(execution_path,TailPath,filename);
1289 (void) SetClientName(filename);
1290 GetPathComponent(execution_path,HeadPath,execution_path);
1291 (void) SetClientPath(execution_path);
1292 if (establish_signal_handlers != MagickFalse)
1295 Set signal handlers.
1297 #if defined(SIGABRT)
1298 if (signal_handlers[SIGABRT] == (SignalHandler *) NULL)
1299 signal_handlers[SIGABRT]=RegisterMagickSignalHandler(SIGABRT);
1301 #if defined(SIGSEGV)
1302 if (signal_handlers[SIGSEGV] == (SignalHandler *) NULL)
1303 signal_handlers[SIGSEGV]=RegisterMagickSignalHandler(SIGSEGV);
1306 if (signal_handlers[SIGFPE] == (SignalHandler *) NULL)
1307 signal_handlers[SIGFPE]=RegisterMagickSignalHandler(SIGFPE);
1310 if (signal_handlers[SIGHUP] == (SignalHandler *) NULL)
1311 signal_handlers[SIGHUP]=RegisterMagickSignalHandler(SIGHUP);
1313 #if defined(SIGINT) && !defined(MAGICKCORE_WINDOWS_SUPPORT)
1314 if (signal_handlers[SIGINT] == (SignalHandler *) NULL)
1315 signal_handlers[SIGINT]=RegisterMagickSignalHandler(SIGINT);
1317 #if defined(SIGQUIT)
1318 if (signal_handlers[SIGQUIT] == (SignalHandler *) NULL)
1319 signal_handlers[SIGQUIT]=RegisterMagickSignalHandler(SIGQUIT);
1321 #if defined(SIGTERM)
1322 if (signal_handlers[SIGTERM] == (SignalHandler *) NULL)
1323 signal_handlers[SIGTERM]=RegisterMagickSignalHandler(SIGTERM);
1325 #if defined(SIGXCPU)
1326 if (signal_handlers[SIGXCPU] == (SignalHandler *) NULL)
1327 signal_handlers[SIGXCPU]=RegisterMagickSignalHandler(SIGXCPU);
1329 #if defined(SIGXFSZ)
1330 if (signal_handlers[SIGXFSZ] == (SignalHandler *) NULL)
1331 signal_handlers[SIGXFSZ]=RegisterMagickSignalHandler(SIGXFSZ);
1335 Instantiate magick resources.
1337 (void) ConfigureComponentGenesis();
1338 (void) PolicyComponentGenesis();
1339 (void) CacheComponentGenesis();
1340 (void) RegistryComponentGenesis();
1341 (void) ResourceComponentGenesis();
1342 (void) CoderComponentGenesis();
1343 (void) MagickComponentGenesis();
1344 #if defined(MAGICKCORE_MODULES_SUPPORT)
1345 (void) ModuleComponentGenesis();
1347 (void) DelegateComponentGenesis();
1348 (void) MagicComponentGenesis();
1349 (void) ColorComponentGenesis();
1350 (void) TypeComponentGenesis();
1351 (void) MimeComponentGenesis();
1352 (void) ConstituteComponentGenesis();
1353 (void) AnnotateComponentGenesis();
1354 #if defined(MAGICKCORE_X11_DELEGATE)
1355 (void) XComponentGenesis();
1357 instantiate_magickcore=MagickTrue;
1358 UnlockMagickMutex();
1362 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1366 % M a g i c k C o r e T e r m i n u s %
1370 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1372 % MagickCoreTerminus() destroys the MagickCore environment.
1374 % The format of the MagickCoreTerminus function is:
1376 % MagickCoreTerminus(void)
1379 MagickExport void MagickCoreTerminus(void)
1382 if (instantiate_magickcore == MagickFalse)
1384 UnlockMagickMutex();
1387 #if defined(MAGICKCORE_X11_DELEGATE)
1388 XComponentTerminus();
1390 AnnotateComponentTerminus();
1391 ConstituteComponentTerminus();
1392 MimeComponentTerminus();
1393 TypeComponentTerminus();
1394 ColorComponentTerminus();
1395 #if defined(MAGICKCORE_WINDOWS_SUPPORT)
1396 NTGhostscriptUnLoadDLL();
1398 MagicComponentTerminus();
1399 DelegateComponentTerminus();
1400 MagickComponentTerminus();
1401 #if !defined(MAGICKCORE_BUILD_MODULES)
1402 UnregisterStaticModules();
1404 #if defined(MAGICKCORE_MODULES_SUPPORT)
1405 ModuleComponentTerminus();
1407 CoderComponentTerminus();
1408 ResourceComponentTerminus();
1409 RegistryComponentTerminus();
1410 CacheComponentTerminus();
1411 PolicyComponentTerminus();
1412 ConfigureComponentTerminus();
1413 RandomComponentTerminus();
1414 LocaleComponentTerminus();
1415 LogComponentTerminus();
1416 SemaphoreComponentTerminus();
1417 instantiate_magickcore=MagickFalse;
1418 UnlockMagickMutex();
1422 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1426 + R e g i s t e r M a g i c k I n f o %
1430 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1432 % RegisterMagickInfo() adds attributes for a particular image format to the
1433 % list of supported formats. The attributes include the image format name,
1434 % a method to read and/or write the format, whether the format supports the
1435 % saving of more than one frame to the same file or blob, whether the format
1436 % supports native in-memory I/O, and a brief description of the format.
1438 % The format of the RegisterMagickInfo method is:
1440 % MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1442 % A description of each parameter follows:
1444 % o magick_info: the magick info.
1447 MagickExport MagickInfo *RegisterMagickInfo(MagickInfo *magick_info)
1453 Delete any existing name.
1455 assert(magick_info != (MagickInfo *) NULL);
1456 assert(magick_info->signature == MagickSignature);
1457 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",magick_info->name);
1458 if (magick_list == (SplayTreeInfo *) NULL)
1459 return((MagickInfo *) NULL);
1460 status=AddValueToSplayTree(magick_list,magick_info->name,magick_info);
1461 if (status == MagickFalse)
1462 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1463 return(magick_info);
1467 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1471 + S e t M a g i c k I n f o %
1475 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1477 % SetMagickInfo() allocates a MagickInfo structure and initializes the members
1478 % to default values.
1480 % The format of the SetMagickInfo method is:
1482 % MagickInfo *SetMagickInfo(const char *name)
1484 % A description of each parameter follows:
1486 % o magick_info: Method SetMagickInfo returns the allocated and initialized
1487 % MagickInfo structure.
1489 % o name: a character string that represents the image format associated
1490 % with the MagickInfo structure.
1493 MagickExport MagickInfo *SetMagickInfo(const char *name)
1498 assert(name != (const char *) NULL);
1499 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",name);
1500 magick_info=(MagickInfo *) AcquireMagickMemory(sizeof(*magick_info));
1501 if (magick_info == (MagickInfo *) NULL)
1502 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
1503 (void) ResetMagickMemory(magick_info,0,sizeof(*magick_info));
1504 magick_info->name=ConstantString(name);
1505 magick_info->adjoin=MagickTrue;
1506 magick_info->blob_support=MagickTrue;
1507 magick_info->thread_support=(MagickStatusType) (DecoderThreadSupport |
1508 EncoderThreadSupport);
1509 magick_info->signature=MagickSignature;
1510 return(magick_info);
1514 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1518 % S e t M a g i c k P r e c i s i o n %
1522 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1524 % SetMagickPrecision() sets the maximum number of significant digits to be
1525 % printed and returns it.
1527 % The format of the SetMagickPrecision method is:
1529 % int SetMagickPrecision(const int precision)
1531 % A description of each parameter follows:
1533 % o precision: set the maximum number of significant digits to be printed.
1536 MagickExport int SetMagickPrecision(const int precision)
1539 magick_precision = 0;
1541 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
1543 magick_precision=precision;
1544 return(magick_precision);
1548 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1552 + U n r e g i s t e r M a g i c k I n f o %
1556 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
1558 % UnregisterMagickInfo() removes a name from the magick info list. It returns
1559 % MagickFalse if the name does not exist in the list otherwise MagickTrue.
1561 % The format of the UnregisterMagickInfo method is:
1563 % MagickBooleanType UnregisterMagickInfo(const char *name)
1565 % A description of each parameter follows:
1567 % o name: a character string that represents the image format we are
1571 MagickExport MagickBooleanType UnregisterMagickInfo(const char *name)
1573 register const MagickInfo
1579 assert(name != (const char *) NULL);
1580 if (magick_list == (SplayTreeInfo *) NULL)
1581 return(MagickFalse);
1582 if (GetNumberOfNodesInSplayTree(magick_list) == 0)
1583 return(MagickFalse);
1584 LockSemaphoreInfo(magick_semaphore);
1585 ResetSplayTreeIterator(magick_list);
1586 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1587 while (p != (const MagickInfo *) NULL)
1589 if (LocaleCompare(p->name,name) == 0)
1591 p=(const MagickInfo *) GetNextValueInSplayTree(magick_list);
1593 status=DeleteNodeByValueFromSplayTree(magick_list,p);
1594 UnlockSemaphoreInfo(magick_semaphore);