00303 {
00304
Image *image,*palette;
00305
ImageInfo *clone_info;
00306
MagickBooleanType status;
00307
unsigned long EncodedByte;
00308
unsigned char RunCount,RunValue,RunCountMasked;
00309
CUTHeader Header;
00310
CUTPalHeader PalHeader;
00311
long depth;
00312
long i,j;
00313
long ldblk;
00314
unsigned char *BImgBuff=NULL,*ptrB;
00315
PixelPacket *q;
00316
00317
00318
00319
00320
assert(image_info != (
const ImageInfo *) NULL);
00321
assert(image_info->
signature == MagickSignature);
00322
if (image_info->
debug !=
MagickFalse)
00323 (
void)
LogMagickEvent(TraceEvent,
GetMagickModule(),image_info->
filename);
00324
assert(exception != (
ExceptionInfo *) NULL);
00325
assert(exception->
signature == MagickSignature);
00326 image=
AllocateImage(image_info);
00327 status=
OpenBlob(image_info,image,ReadBinaryBlobMode,exception);
00328
if (status ==
MagickFalse)
00329 {
00330
DestroyImageList(image);
00331
return((
Image *) NULL);
00332 }
00333
00334
00335
00336 palette=NULL;
00337 clone_info=NULL;
00338 Header.
Width=
ReadBlobLSBShort(image);
00339 Header.
Height=
ReadBlobLSBShort(image);
00340 Header.
Reserved=
ReadBlobLSBShort(image);
00341
00342
if (Header.
Width==0 || Header.
Height==0 || Header.
Reserved!=0)
00343 CUT_KO:
ThrowReaderException(CorruptImageError,
"ImproperImageHeader");
00344
00345
00346 EncodedByte=
ReadBlobLSBShort(image);
00347 RunCount=(
unsigned char)
ReadBlobByte(image);
00348 RunCountMasked=RunCount & 0x7F;
00349 ldblk=0;
00350
while((
int) RunCountMasked!=0)
00351 {
00352 i=1;
00353
if((
int) RunCount<0x80) i=(
long) RunCountMasked;
00354 (
void)
SeekBlob(image,
TellBlob(image)+i,SEEK_SET);
00355
if(
EOFBlob(image) !=
MagickFalse)
goto CUT_KO;
00356 EncodedByte-=i+1;
00357 ldblk+=(
long) RunCountMasked;
00358
00359 RunCount=(
unsigned char)
ReadBlobByte(image);
00360
if(
EOFBlob(image) !=
MagickFalse)
goto CUT_KO;
00361 RunCountMasked=RunCount & 0x7F;
00362 }
00363
if(EncodedByte!=1)
goto CUT_KO;
00364 i=0;
00365
if(ldblk==(
int) Header.
Width) i=8;
00366
if(2*ldblk==(
int) Header.
Width) i=4;
00367
if(8*ldblk==(
int) Header.
Width) i=1;
00368
if(i==0)
goto CUT_KO;
00369 depth=i;
00370
00371 image->
columns=Header.
Width;
00372 image->
rows=Header.
Height;
00373 image->
depth=8;
00374 image->
colors=1UL << (
unsigned long) i;
00375
00376
00377
00378
if ((clone_info=
CloneImageInfo(image_info)) == NULL)
goto NoPalette;
00379
00380
00381 i=(
long) strlen(clone_info->
filename);
00382 j=i;
00383
while(--i>0)
00384 {
00385
if(clone_info->
filename[i]==
'.')
00386 {
00387
break;
00388 }
00389
if(clone_info->
filename[i]==
'/' || clone_info->
filename[i]==
'\\' ||
00390 clone_info->
filename[i]==
':' )
00391 {
00392 i=j;
00393
break;
00394 }
00395 }
00396
00397 (
void) strcpy(clone_info->
filename+i,
".PAL");
00398
if((clone_info->
file=fopen(clone_info->
filename,
"rb"))==NULL)
00399 {
00400 (
void) strcpy(clone_info->
filename+i,
".pal");
00401
if((clone_info->
file=fopen(clone_info->
filename,
"rb"))==NULL)
00402 {
00403 clone_info->
filename[i]=
'\0';
00404
if((clone_info->
file=fopen(clone_info->
filename,
"rb"))==NULL)
00405 {
00406 clone_info=
DestroyImageInfo(clone_info);
00407 clone_info=NULL;
00408
goto NoPalette;
00409 }
00410 }
00411 }
00412
00413
if( (palette=
AllocateImage(clone_info))==NULL )
goto NoPalette;
00414 status=
OpenBlob(clone_info,palette,ReadBinaryBlobMode,exception);
00415
if (status ==
MagickFalse)
00416 {
00417 ErasePalette:
00418 palette=
DestroyImage(palette);
00419 palette=NULL;
00420
goto NoPalette;
00421 }
00422
00423
00424
if(palette!=NULL)
00425 {
00426 (
void)
ReadBlob(palette,2,(
unsigned char *) PalHeader.
FileId);
00427
if(strncmp(PalHeader.
FileId,
"AH",2) != 0)
goto ErasePalette;
00428 PalHeader.
Version=
ReadBlobLSBShort(palette);
00429 PalHeader.
Size=
ReadBlobLSBShort(palette);
00430 PalHeader.
FileType=(
char)
ReadBlobByte(palette);
00431 PalHeader.
SubType=(
char)
ReadBlobByte(palette);
00432 PalHeader.
BoardID=
ReadBlobLSBShort(palette);
00433 PalHeader.
GraphicsMode=
ReadBlobLSBShort(palette);
00434 PalHeader.
MaxIndex=
ReadBlobLSBShort(palette);
00435 PalHeader.
MaxRed=
ReadBlobLSBShort(palette);
00436 PalHeader.
MaxGreen=
ReadBlobLSBShort(palette);
00437 PalHeader.
MaxBlue=
ReadBlobLSBShort(palette);
00438 (
void)
ReadBlob(palette,20,(
unsigned char *) PalHeader.
PaletteId);
00439
00440
if(PalHeader.
MaxIndex<1)
goto ErasePalette;
00441 image->
colors=PalHeader.
MaxIndex+1;
00442
if (
AllocateImageColormap(image,image->
colors) ==
MagickFalse)
goto NoMemory;
00443
00444
if(PalHeader.
MaxRed==0) PalHeader.
MaxRed=
MaxRGB;
00445
if(PalHeader.
MaxGreen==0) PalHeader.
MaxGreen=
MaxRGB;
00446
if(PalHeader.
MaxBlue==0) PalHeader.
MaxBlue=
MaxRGB;
00447
00448
for(i=0;i<=(
int) PalHeader.
MaxIndex;i++)
00449 {
00450 j=(
long)
TellBlob(palette);
00451
if((j % 512)>512-6)
00452 {
00453 j=((j / 512)+1)*512;
00454 (
void)
SeekBlob(palette,j,SEEK_SET);
00455 }
00456 image->
colormap[i].
red=
ReadBlobLSBShort(palette);
00457
if(
MaxRGB!=(
Quantum) PalHeader.
MaxRed)
00458 {
00459 image->
colormap[i].
red=(
Quantum)
00460 (((
double)image->
colormap[i].
red*
MaxRGB+(PalHeader.
MaxRed>>1))/PalHeader.
MaxRed+0.5);
00461 }
00462 image->
colormap[i].
green=
ReadBlobLSBShort(palette);
00463
if(
MaxRGB!=(
Quantum) PalHeader.
MaxGreen)
00464 {
00465 image->
colormap[i].
green=(
Quantum)
00466 (((
double)image->
colormap[i].
green*
MaxRGB+(PalHeader.
MaxGreen>>1))/PalHeader.
MaxGreen+0.5);
00467 }
00468 image->
colormap[i].
blue=
ReadBlobLSBShort(palette);
00469
if(
MaxRGB!=(
Quantum) PalHeader.
MaxBlue)
00470 {
00471 image->
colormap[i].
blue=(
Quantum)
00472 (((
double)image->
colormap[i].
blue*
MaxRGB+(PalHeader.
MaxBlue>>1))/PalHeader.
MaxBlue+0.5);
00473 }
00474
00475 }
00476 }
00477
00478
00479
00480 NoPalette:
00481
if(palette==NULL)
00482 {
00483
00484 image->
colors=256;
00485
if (
AllocateImageColormap(image,image->
colors) ==
MagickFalse)
00486 {
00487 NoMemory:
00488
ThrowReaderException(ResourceLimitError,
"MemoryAllocationFailed");
00489 }
00490
00491
for (i=0; i < (
long)image->
colors; i++)
00492 {
00493 image->
colormap[i].
red=
ScaleCharToQuantum(i);
00494 image->
colormap[i].
green=
ScaleCharToQuantum(i);
00495 image->
colormap[i].
blue=
ScaleCharToQuantum(i);
00496 }
00497 }
00498
00499
00500
00501 BImgBuff=(
unsigned char *)
AcquireMagickMemory((size_t) ldblk);
00502
if(BImgBuff==NULL)
goto NoMemory;
00503
00504 (
void)
SeekBlob(image,6 ,SEEK_SET);
00505
for(i=0;i<(
int) Header.
Height;i++)
00506 {
00507 EncodedByte=
ReadBlobLSBShort(image);
00508
00509 ptrB=BImgBuff;
00510 j=ldblk;
00511
00512 RunCount=(
unsigned char)
ReadBlobByte(image);
00513 RunCountMasked=RunCount & 0x7F;
00514
00515
while((
int) RunCountMasked!=0)
00516 {
00517
if((
long) RunCountMasked>j)
00518 {
00519 RunCountMasked=(
unsigned char) j;
00520
if(j==0)
00521 {
00522
break;
00523 }
00524 }
00525
00526
if((
int) RunCount>0x80)
00527 {
00528 RunValue=(
unsigned char)
ReadBlobByte(image);
00529 (
void)
ResetMagickMemory(ptrB,(
int) RunValue,(size_t) RunCountMasked);
00530 }
00531
else {
00532 (
void)
ReadBlob(image,(size_t) RunCountMasked,ptrB);
00533 }
00534
00535 ptrB+=(
int) RunCountMasked;
00536 j-=(
int) RunCountMasked;
00537
00538
if (
EOFBlob(image) !=
MagickFalse)
goto Finish;
00539 RunCount=(
unsigned char)
ReadBlobByte(image);
00540 RunCountMasked=RunCount & 0x7F;
00541 }
00542
00543
InsertRow(depth,BImgBuff,i,image);
00544 }
00545
00546
00547
00548
00549
if(palette==NULL)
00550 {
00551
if ((image->
storage_class ==
PseudoClass) &&
00552 (
IsGrayImage(image,&image->
exception) !=
MagickFalse))
00553 {
00554
if(
GetCutColors(image)==2)
00555 {
00556
for (i=0; i < (
long)image->
colors; i++)
00557 {
00558
register Quantum
00559 sample;
00560 sample=
ScaleCharToQuantum(i);
00561
if(image->
colormap[i].
red!=sample)
goto Finish;
00562
if(image->
colormap[i].
green!=sample)
goto Finish;
00563
if(image->
colormap[i].
blue!=sample)
goto Finish;
00564 }
00565
00566 image->
colormap[1].
red=image->
colormap[1].
green=image->
colormap[1].
blue=
MaxRGB;
00567
for (i=0; i < (
long)image->
rows; i++)
00568 {
00569 q=
SetImagePixels(image,0,i,image->
columns,1);
00570
for (j=0; j < (
long)image->
columns; j++)
00571 {
00572
if(q->
red==
ScaleCharToQuantum(1))
00573 {
00574 q->
red=q->
green=q->
blue=
MaxRGB;
00575 }
00576 q++;
00577 }
00578
if (
SyncImagePixels(image) ==
MagickFalse)
goto Finish;
00579 }
00580 }
00581 }
00582 }
00583
00584 Finish:
00585
if (BImgBuff != NULL)
00586 BImgBuff=(
unsigned char *)
RelinquishMagickMemory(BImgBuff);
00587
if (palette != NULL)
00588 palette=
DestroyImage(palette);
00589
if (clone_info != NULL)
00590 clone_info=
DestroyImageInfo(clone_info);
00591
if (
EOFBlob(image) !=
MagickFalse)
00592
ThrowFileException(exception,CorruptImageError,
"UnexpectedEndOfFile",
00593 image->
filename);
00594
CloseBlob(image);
00595
return(
GetFirstImageInList(image));
00596 }