00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040 #include "magick/studio.h"
00041 #include "magick/blob.h"
00042 #include "magick/client.h"
00043 #include "magick/configure.h"
00044 #include "magick/exception.h"
00045 #include "magick/exception-private.h"
00046 #include "magick/hashmap.h"
00047 #include "magick/memory_.h"
00048 #include "magick/mime.h"
00049 #include "magick/mime-private.h"
00050 #include "magick/option.h"
00051 #include "magick/semaphore.h"
00052 #include "magick/string_.h"
00053 #include "magick/token.h"
00054 #include "magick/utility.h"
00055 #include "magick/xml-tree.h"
00056
00057
00058
00059
00060 #define MimeFilename "mime.xml"
00061
00062
00063
00064
00065 struct _MimeInfo
00066 {
00067 char
00068 *path,
00069 *type,
00070 *description,
00071 *pattern;
00072
00073 long
00074 priority;
00075
00076 MagickOffsetType
00077 offset;
00078
00079 size_t
00080 extent;
00081
00082 DataType
00083 data_type;
00084
00085 long
00086 mask,
00087 value;
00088
00089 EndianType
00090 endian;
00091
00092 size_t
00093 length;
00094
00095 unsigned char
00096 *magic;
00097
00098 MagickBooleanType
00099 stealth;
00100
00101 unsigned long
00102 signature;
00103 };
00104
00105
00106
00107
00108 static const char
00109 *MimeMap = (char *)
00110 "<?xml version=\"1.0\"?>"
00111 "<mimemap>"
00112 "</mimemap>";
00113
00114 static LinkedListInfo
00115 *mime_list = (LinkedListInfo *) NULL;
00116
00117 static SemaphoreInfo
00118 *mime_semaphore = (SemaphoreInfo *) NULL;
00119
00120 static volatile MagickBooleanType
00121 instantiate_mime = MagickFalse;
00122
00123
00124
00125
00126 static MagickBooleanType
00127 InitializeMimeList(ExceptionInfo *);
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148 static void *DestroyMimeElement(void *mime_info)
00149 {
00150 register MimeInfo
00151 *p;
00152
00153 p=(MimeInfo *) mime_info;
00154 if (p->magic != (unsigned char *) NULL)
00155 p->magic=(unsigned char *) RelinquishMagickMemory(p->magic);
00156 if (p->pattern != (char *) NULL)
00157 p->pattern=DestroyString(p->pattern);
00158 if (p->description != (char *) NULL)
00159 p->description=DestroyString(p->description);
00160 if (p->type != (char *) NULL)
00161 p->type=DestroyString(p->type);
00162 if (p->path != (char *) NULL)
00163 p->path=DestroyString(p->path);
00164 p=(MimeInfo *) RelinquishMagickMemory(p);
00165 return((void *) NULL);
00166 }
00167
00168 MagickExport void DestroyMimeList(void)
00169 {
00170 AcquireSemaphoreInfo(&mime_semaphore);
00171 if (mime_list != (LinkedListInfo *) NULL)
00172 mime_list=DestroyLinkedList(mime_list,DestroyMimeElement);
00173 instantiate_mime=MagickFalse;
00174 RelinquishSemaphoreInfo(mime_semaphore);
00175 DestroySemaphoreInfo(&mime_semaphore);
00176 }
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211 MagickExport const MimeInfo *GetMimeInfo(const char *filename,
00212 const unsigned char *magic,const size_t length,ExceptionInfo *exception)
00213 {
00214 const MimeInfo
00215 *mime_info;
00216
00217 EndianType
00218 endian;
00219
00220 long
00221 value;
00222
00223 register const MimeInfo
00224 *p;
00225
00226 register const unsigned char
00227 *q;
00228
00229 register long
00230 i;
00231
00232 unsigned long
00233 lsb_first;
00234
00235 assert(exception != (ExceptionInfo *) NULL);
00236 if ((mime_list == (LinkedListInfo *) NULL) ||
00237 (instantiate_mime == MagickFalse))
00238 if (InitializeMimeList(exception) == MagickFalse)
00239 return((const MimeInfo *) NULL);
00240 if ((mime_list == (LinkedListInfo *) NULL) ||
00241 (IsLinkedListEmpty(mime_list) != MagickFalse))
00242 return((const MimeInfo *) NULL);
00243 if ((magic == (const unsigned char *) NULL) || (length == 0))
00244 return((const MimeInfo *) GetValueFromLinkedList(mime_list,0));
00245 if (length == 0)
00246 return((const MimeInfo *) NULL);
00247
00248
00249
00250 mime_info=(const MimeInfo *) NULL;
00251 lsb_first=1;
00252 AcquireSemaphoreInfo(&mime_semaphore);
00253 ResetLinkedListIterator(mime_list);
00254 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00255 while (p != (const MimeInfo *) NULL)
00256 {
00257 assert(p->offset >= 0);
00258 if (mime_info != (const MimeInfo *) NULL)
00259 if (p->priority > mime_info->priority)
00260 {
00261 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00262 continue;
00263 }
00264 if ((p->pattern != (char *) NULL) && (filename != (char *) NULL))
00265 {
00266 if (GlobExpression(filename,p->pattern,MagickFalse) != MagickFalse)
00267 mime_info=p;
00268 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00269 continue;
00270 }
00271 switch (p->data_type)
00272 {
00273 case ByteData:
00274 {
00275 if ((size_t) (p->offset+4) > length)
00276 break;
00277 q=magic+p->offset;
00278 value=(*q++);
00279 if (p->mask == 0)
00280 {
00281 if (p->value == value)
00282 mime_info=p;
00283 }
00284 else
00285 {
00286 if ((p->value & p->mask) == value)
00287 mime_info=p;
00288 }
00289 break;
00290 }
00291 case ShortData:
00292 {
00293 if ((size_t) (p->offset+4) > length)
00294 break;
00295 q=magic+p->offset;
00296 endian=p->endian;
00297 if (p->endian == UndefinedEndian)
00298 endian=(*(char *) &lsb_first) == 1 ? LSBEndian : MSBEndian;
00299 if (endian == LSBEndian)
00300 {
00301 value=(*q++);
00302 value|=(*q++) << 8;
00303 }
00304 else
00305 {
00306 value=(*q++) << 8;
00307 value|=(*q++);
00308 }
00309 if (p->mask == 0)
00310 {
00311 if (p->value == value)
00312 mime_info=p;
00313 }
00314 else
00315 {
00316 if ((p->value & p->mask) == value)
00317 mime_info=p;
00318 }
00319 break;
00320 }
00321 case LongData:
00322 {
00323 if ((size_t) (p->offset+4) > length)
00324 break;
00325 q=magic+p->offset;
00326 endian=p->endian;
00327 if (p->endian == UndefinedEndian)
00328 endian=(*(char *) &lsb_first) == 1 ? LSBEndian : MSBEndian;
00329 if (endian == LSBEndian)
00330 {
00331 value=(*q++);
00332 value|=(*q++) << 8;
00333 value|=(*q++) << 16;
00334 value|=(*q++) << 24;
00335 }
00336 else
00337 {
00338 value=(*q++) << 24;
00339 value|=(*q++) << 16;
00340 value|=(*q++) << 8;
00341 value|=(*q++);
00342 }
00343 if (p->mask == 0)
00344 {
00345 if (p->value == value)
00346 mime_info=p;
00347 }
00348 else
00349 {
00350 if ((p->value & p->mask) == value)
00351 mime_info=p;
00352 }
00353 break;
00354 }
00355 case StringData:
00356 default:
00357 {
00358 for (i=0; i <= (long) p->extent; i++)
00359 {
00360 if ((size_t) (p->offset+i+p->length) > length)
00361 break;
00362 if (memcmp(magic+p->offset+i,p->magic,p->length) == 0)
00363 {
00364 mime_info=p;
00365 break;
00366 }
00367 }
00368 break;
00369 }
00370 }
00371 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00372 }
00373 if (p != (const MimeInfo *) NULL)
00374 (void) InsertValueInLinkedList(mime_list,0,
00375 RemoveElementByValueFromLinkedList(mime_list,p));
00376 RelinquishSemaphoreInfo(mime_semaphore);
00377 return(mime_info);
00378 }
00379
00380
00381
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393
00394
00395
00396
00397
00398
00399
00400
00401
00402
00403
00404
00405
00406
00407
00408
00409
00410 #if defined(__cplusplus) || defined(c_plusplus)
00411 extern "C" {
00412 #endif
00413
00414 static int MimeInfoCompare(const void *x,const void *y)
00415 {
00416 const MimeInfo
00417 **p,
00418 **q;
00419
00420 p=(const MimeInfo **) x,
00421 q=(const MimeInfo **) y;
00422 if (strcasecmp((*p)->path,(*q)->path) == 0)
00423 return(strcasecmp((*p)->type,(*q)->type));
00424 return(strcasecmp((*p)->path,(*q)->path));
00425 }
00426
00427 #if defined(__cplusplus) || defined(c_plusplus)
00428 }
00429 #endif
00430
00431 MagickExport const MimeInfo **GetMimeInfoList(const char *pattern,
00432 unsigned long *number_aliases,ExceptionInfo *exception)
00433 {
00434 const MimeInfo
00435 **aliases;
00436
00437 register const MimeInfo
00438 *p;
00439
00440 register long
00441 i;
00442
00443
00444
00445
00446 assert(pattern != (char *) NULL);
00447 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
00448 assert(number_aliases != (unsigned long *) NULL);
00449 *number_aliases=0;
00450 p=GetMimeInfo((char *) NULL,(unsigned char *) "*",0,exception);
00451 if (p == (const MimeInfo *) NULL)
00452 return((const MimeInfo **) NULL);
00453 aliases=(const MimeInfo **) AcquireQuantumMemory((size_t)
00454 GetNumberOfElementsInLinkedList(mime_list)+1UL,sizeof(*aliases));
00455 if (aliases == (const MimeInfo **) NULL)
00456 return((const MimeInfo **) NULL);
00457
00458
00459
00460 AcquireSemaphoreInfo(&mime_semaphore);
00461 ResetLinkedListIterator(mime_list);
00462 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00463 for (i=0; p != (const MimeInfo *) NULL; )
00464 {
00465 if ((p->stealth == MagickFalse) &&
00466 (GlobExpression(p->type,pattern,MagickFalse) != MagickFalse))
00467 aliases[i++]=p;
00468 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00469 }
00470 RelinquishSemaphoreInfo(mime_semaphore);
00471 qsort((void *) aliases,(size_t) i,sizeof(*aliases),MimeInfoCompare);
00472 aliases[i]=(MimeInfo *) NULL;
00473 *number_aliases=(unsigned long) i;
00474 return(aliases);
00475 }
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485
00486
00487
00488
00489
00490
00491
00492
00493
00494
00495
00496
00497
00498
00499
00500
00501
00502
00503
00504
00505
00506
00507 #if defined(__cplusplus) || defined(c_plusplus)
00508 extern "C" {
00509 #endif
00510
00511 static int MimeCompare(const void *x,const void *y)
00512 {
00513 register char
00514 *p,
00515 *q;
00516
00517 p=(char *) x;
00518 q=(char *) y;
00519 return(strcasecmp(p,q));
00520 }
00521
00522 #if defined(__cplusplus) || defined(c_plusplus)
00523 }
00524 #endif
00525
00526 MagickExport char **GetMimeList(const char *pattern,
00527 unsigned long *number_aliases,ExceptionInfo *exception)
00528 {
00529 char
00530 **aliases;
00531
00532 register const MimeInfo
00533 *p;
00534
00535 register long
00536 i;
00537
00538
00539
00540
00541 assert(pattern != (char *) NULL);
00542 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"%s",pattern);
00543 assert(number_aliases != (unsigned long *) NULL);
00544 *number_aliases=0;
00545 p=GetMimeInfo((char *) NULL,(unsigned char *) "*",0,exception);
00546 if (p == (const MimeInfo *) NULL)
00547 return((char **) NULL);
00548 aliases=(char **) AcquireQuantumMemory((size_t)
00549 GetNumberOfElementsInLinkedList(mime_list)+1UL,sizeof(*aliases));
00550 if (aliases == (char **) NULL)
00551 return((char **) NULL);
00552 AcquireSemaphoreInfo(&mime_semaphore);
00553 ResetLinkedListIterator(mime_list);
00554 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00555 for (i=0; p != (const MimeInfo *) NULL; )
00556 {
00557 if ((p->stealth == MagickFalse) &&
00558 (GlobExpression(p->type,pattern,MagickFalse) != MagickFalse))
00559 aliases[i++]=ConstantString(p->type);
00560 p=(const MimeInfo *) GetNextValueInLinkedList(mime_list);
00561 }
00562 RelinquishSemaphoreInfo(mime_semaphore);
00563 qsort((void *) aliases,(size_t) i,sizeof(*aliases),MimeCompare);
00564 aliases[i]=(char *) NULL;
00565 *number_aliases=(unsigned long) i;
00566 return(aliases);
00567 }
00568
00569
00570
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582
00583
00584
00585
00586
00587
00588
00589
00590
00591 MagickExport const char *GetMimeDescription(const MimeInfo *mime_info)
00592 {
00593 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
00594 assert(mime_info != (MimeInfo *) NULL);
00595 assert(mime_info->signature == MagickSignature);
00596 return(mime_info->description);
00597 }
00598
00599
00600
00601
00602
00603
00604
00605
00606
00607
00608
00609
00610
00611
00612
00613
00614
00615
00616
00617
00618
00619
00620
00621 MagickExport const char *GetMimeType(const MimeInfo *mime_info)
00622 {
00623 (void) LogMagickEvent(TraceEvent,GetMagickModule(),"...");
00624 assert(mime_info != (MimeInfo *) NULL);
00625 assert(mime_info->signature == MagickSignature);
00626 return(mime_info->type);
00627 }
00628
00629
00630
00631
00632
00633
00634
00635
00636
00637
00638
00639
00640
00641
00642
00643
00644
00645
00646
00647
00648
00649
00650
00651 static MagickBooleanType InitializeMimeList(ExceptionInfo *exception)
00652 {
00653 if ((mime_list == (LinkedListInfo *) NULL) &&
00654 (instantiate_mime == MagickFalse))
00655 {
00656 AcquireSemaphoreInfo(&mime_semaphore);
00657 if ((mime_list == (LinkedListInfo *) NULL) &&
00658 (instantiate_mime == MagickFalse))
00659 {
00660 (void) LoadMimeLists(MimeFilename,exception);
00661 instantiate_mime=MagickTrue;
00662 }
00663 RelinquishSemaphoreInfo(mime_semaphore);
00664 }
00665 return(mime_list != (LinkedListInfo *) NULL ? MagickTrue : MagickFalse);
00666 }
00667
00668
00669
00670
00671
00672
00673
00674
00675
00676
00677
00678
00679
00680
00681
00682
00683
00684
00685
00686
00687
00688
00689
00690
00691
00692 MagickExport MagickBooleanType ListMimeInfo(FILE *file,ExceptionInfo *exception)
00693 {
00694 const char
00695 *path;
00696
00697 const MimeInfo
00698 **mime_info;
00699
00700 long
00701 j;
00702
00703 register long
00704 i;
00705
00706 unsigned long
00707 number_aliases;
00708
00709 if (file == (const FILE *) NULL)
00710 file=stdout;
00711 mime_info=GetMimeInfoList("*",&number_aliases,exception);
00712 if (mime_info == (const MimeInfo **) NULL)
00713 return(MagickFalse);
00714 j=0;
00715 path=(const char *) NULL;
00716 for (i=0; i < (long) number_aliases; i++)
00717 {
00718 if (mime_info[i]->stealth != MagickFalse)
00719 continue;
00720 if ((path == (const char *) NULL) ||
00721 (strcasecmp(path,mime_info[i]->path) != 0))
00722 {
00723 if (mime_info[i]->path != (char *) NULL)
00724 (void) fprintf(file,"\nPath: %s\n\n",mime_info[i]->path);
00725 (void) fprintf(file,"Type Description\n");
00726 (void) fprintf(file,"-------------------------------------------------"
00727 "------------------------------\n");
00728 }
00729 path=mime_info[i]->path;
00730 (void) fprintf(file,"%s",mime_info[i]->type);
00731 if (strlen(mime_info[i]->type) <= 25)
00732 {
00733 for (j=(long) strlen(mime_info[i]->type); j <= 27; j++)
00734 (void) fprintf(file," ");
00735 }
00736 else
00737 {
00738 (void) fprintf(file,"\n");
00739 for (j=0; j <= 27; j++)
00740 (void) fprintf(file," ");
00741 }
00742 if (mime_info[i]->description != (char *) NULL)
00743 (void) fprintf(file,"%s",mime_info[i]->description);
00744 (void) fprintf(file,"\n");
00745 }
00746 (void) fflush(file);
00747 mime_info=(const MimeInfo **) RelinquishMagickMemory((void *) mime_info);
00748 return(MagickTrue);
00749 }
00750
00751
00752
00753
00754
00755
00756
00757
00758
00759
00760
00761
00762
00763
00764
00765
00766
00767
00768
00769
00770
00771
00772
00773
00774
00775
00776
00777
00778
00779
00780
00781 static MagickBooleanType LoadMimeList(const char *xml,const char *filename,
00782 const unsigned long depth,ExceptionInfo *exception)
00783 {
00784 const char
00785 *attribute;
00786
00787 MimeInfo
00788 *mime_info = (MimeInfo *) NULL;
00789
00790 MagickBooleanType
00791 status;
00792
00793 XMLTreeInfo
00794 *mime,
00795 *mime_map,
00796 *include;
00797
00798
00799
00800
00801 (void) LogMagickEvent(ConfigureEvent,GetMagickModule(),
00802 "Loading mime map \"%s\" ...",filename);
00803 if (xml == (const char *) NULL)
00804 return(MagickFalse);
00805 if (mime_list == (LinkedListInfo *) NULL)
00806 {
00807 mime_list=NewLinkedList(0);
00808 if (mime_list == (LinkedListInfo *) NULL)
00809 {
00810 ThrowFileException(exception,ResourceLimitError,
00811 "MemoryAllocationFailed",filename);
00812 return(MagickFalse);
00813 }
00814 }
00815 mime_map=NewXMLTree(xml,exception);
00816 if (mime_map == (XMLTreeInfo *) NULL)
00817 return(MagickFalse);
00818 status=MagickTrue;
00819 include=GetXMLTreeChild(mime_map,"include");
00820 while (include != (XMLTreeInfo *) NULL)
00821 {
00822
00823
00824
00825 attribute=GetXMLTreeAttribute(include,"file");
00826 if (attribute != (const char *) NULL)
00827 {
00828 if (depth > 200)
00829 (void) ThrowMagickException(exception,GetMagickModule(),
00830 ConfigureError,"IncludeElementNestedTooDeeply","`%s'",filename);
00831 else
00832 {
00833 char
00834 path[MaxTextExtent],
00835 *xml;
00836
00837 GetPathComponent(filename,HeadPath,path);
00838 if (*path != '\0')
00839 (void) ConcatenateMagickString(path,DirectorySeparator,
00840 MaxTextExtent);
00841 (void) ConcatenateMagickString(path,attribute,MaxTextExtent);
00842 xml=FileToString(path,~0,exception);
00843 if (xml != (char *) NULL)
00844 {
00845 status=LoadMimeList(xml,path,depth+1,exception);
00846 xml=DestroyString(xml);
00847 }
00848 }
00849 }
00850 include=GetNextXMLTreeTag(include);
00851 }
00852 mime=GetXMLTreeChild(mime_map,"mime");
00853 while (mime != (XMLTreeInfo *) NULL)
00854 {
00855 const char
00856 *attribute;
00857
00858
00859
00860
00861 mime_info=(MimeInfo *) AcquireMagickMemory(sizeof(*mime_info));
00862 if (mime_info == (MimeInfo *) NULL)
00863 ThrowFatalException(ResourceLimitFatalError,"MemoryAllocationFailed");
00864 (void) ResetMagickMemory(mime_info,0,sizeof(*mime_info));
00865 mime_info->path=ConstantString(filename);
00866 mime_info->signature=MagickSignature;
00867 attribute=GetXMLTreeAttribute(mime,"data-type");
00868 if (attribute != (const char *) NULL)
00869 mime_info->data_type=(DataType) ParseMagickOption(MagickDataTypeOptions,
00870 MagickTrue,attribute);
00871 attribute=GetXMLTreeAttribute(mime,"description");
00872 if (attribute != (const char *) NULL)
00873 mime_info->description=ConstantString(attribute);
00874 attribute=GetXMLTreeAttribute(mime,"endian");
00875 if (attribute != (const char *) NULL)
00876 mime_info->endian=(EndianType) ParseMagickOption(MagickEndianOptions,
00877 MagickTrue,attribute);
00878 attribute=GetXMLTreeAttribute(mime,"magic");
00879 if (attribute != (const char *) NULL)
00880 {
00881 char
00882 *token;
00883
00884 const char
00885 *p;
00886
00887 register unsigned char
00888 *q;
00889
00890 token=AcquireString(attribute);
00891 (void) SubstituteString((char **) &token,"<","<");
00892 (void) SubstituteString((char **) &token,"&","&");
00893 (void) SubstituteString((char **) &token,""","\"");
00894 mime_info->magic=(unsigned char *) AcquireString(token);
00895 q=mime_info->magic;
00896 for (p=token; *p != '\0'; )
00897 {
00898 if (*p == '\\')
00899 {
00900 p++;
00901 if (isdigit((int) ((unsigned char) *p)) != 0)
00902 {
00903 char
00904 *end;
00905
00906 *q++=(unsigned char) strtol(p,&end,8);
00907 p+=(end-p);
00908 mime_info->length++;
00909 continue;
00910 }
00911 switch (*p)
00912 {
00913 case 'b': *q='\b'; break;
00914 case 'f': *q='\f'; break;
00915 case 'n': *q='\n'; break;
00916 case 'r': *q='\r'; break;
00917 case 't': *q='\t'; break;
00918 case 'v': *q='\v'; break;
00919 case 'a': *q='a'; break;
00920 case '?': *q='\?'; break;
00921 default: *q=(unsigned char) (*p); break;
00922 }
00923 p++;
00924 q++;
00925 mime_info->length++;
00926 continue;
00927 }
00928 *q++=(unsigned char) (*p++);
00929 mime_info->length++;
00930 }
00931 token=DestroyString(token);
00932 if (mime_info->data_type != StringData)
00933 mime_info->value=strtol((char *) mime_info->magic,(char **) NULL,0);
00934 }
00935 attribute=GetXMLTreeAttribute(mime,"mask");
00936 if (attribute != (const char *) NULL)
00937 mime_info->mask=strtol(attribute,(char **) NULL,0);
00938 attribute=GetXMLTreeAttribute(mime,"offset");
00939 if (attribute != (const char *) NULL)
00940 {
00941 char
00942 *c;
00943
00944 mime_info->offset=(MagickOffsetType) strtol(attribute,&c,0);
00945 if (*c == ':')
00946 mime_info->extent=(size_t) strtol(c+1,(char **) NULL,0);
00947 }
00948 attribute=GetXMLTreeAttribute(mime,"pattern");
00949 if (attribute != (const char *) NULL)
00950 mime_info->pattern=ConstantString(attribute);
00951 attribute=GetXMLTreeAttribute(mime,"priority");
00952 if (attribute != (const char *) NULL)
00953 mime_info->priority=strtol(attribute,(char **) NULL,0);
00954 attribute=GetXMLTreeAttribute(mime,"stealth");
00955 if (attribute != (const char *) NULL)
00956 mime_info->stealth=IsMagickTrue(attribute);
00957 attribute=GetXMLTreeAttribute(mime,"type");
00958 if (attribute != (const char *) NULL)
00959 mime_info->type=ConstantString(attribute);
00960 status=AppendValueToLinkedList(mime_list,mime_info);
00961 if (status == MagickFalse)
00962 (void) ThrowMagickException(exception,GetMagickModule(),
00963 ResourceLimitError,"MemoryAllocationFailed","`%s'",filename);
00964 mime=GetNextXMLTreeTag(mime);
00965 }
00966 mime_map=DestroyXMLTree(mime_map);
00967 return(status);
00968 }
00969
00970
00971
00972
00973
00974
00975
00976
00977
00978
00979
00980
00981
00982
00983
00984
00985
00986
00987
00988
00989
00990
00991
00992
00993
00994
00995
00996 MagickExport MagickBooleanType LoadMimeLists(const char *filename,
00997 ExceptionInfo *exception)
00998 {
00999 #if defined(MAGICKCORE_EMBEDDABLE_SUPPORT)
01000 return(LoadMimeList(MimeMap,"built-in",0,exception));
01001 #else
01002 const StringInfo
01003 *option;
01004
01005 LinkedListInfo
01006 *options;
01007
01008 MagickStatusType
01009 status;
01010
01011 status=MagickFalse;
01012 options=GetConfigureOptions(filename,exception);
01013 option=(const StringInfo *) GetNextValueInLinkedList(options);
01014 while (option != (const StringInfo *) NULL)
01015 {
01016 status|=LoadMimeList((const char *) GetStringInfoDatum(option),
01017 GetStringInfoPath(option),0,exception);
01018 option=(const StringInfo *) GetNextValueInLinkedList(options);
01019 }
01020 options=DestroyConfigureOptions(options);
01021 if ((mime_list == (LinkedListInfo *) NULL) ||
01022 (IsLinkedListEmpty(mime_list) != MagickFalse))
01023 status|=LoadMimeList(MimeMap,"built-in",0,exception);
01024 else
01025 ClearMagickException(exception);
01026 return(status != 0 ? MagickTrue : MagickFalse);
01027 #endif
01028 }
01029
01030
01031
01032
01033
01034
01035
01036
01037
01038
01039
01040
01041
01042
01043
01044
01045
01046
01047
01048
01049
01050
01051
01052
01053
01054
01055 MagickExport char *MagickToMime(const char *magick)
01056 {
01057 char
01058 filename[MaxTextExtent],
01059 media[MaxTextExtent];
01060
01061 const MimeInfo
01062 *mime_info;