dgif_lib.c 38 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096
  1. /******************************************************************************
  2. * "Gif-Lib" - Yet another gif library.
  3. *
  4. * Written by: Gershon Elber IBM PC Ver 1.1, Aug. 1990
  5. ******************************************************************************
  6. * The kernel of the GIF Decoding process can be found here.
  7. ******************************************************************************
  8. * History:
  9. * 16 Jun 89 - Version 1.0 by Gershon Elber.
  10. * 3 Sep 90 - Version 1.1 by Gershon Elber (Support for Gif89, Unique names).
  11. *****************************************************************************/
  12. #ifdef HAVE_CONFIG_H
  13. #include <config.h>
  14. #endif
  15. #include <stdlib.h>
  16. #if defined (__MSDOS__) && !defined(__DJGPP__) && !defined(__GNUC__)
  17. #include <io.h>
  18. #include <alloc.h>
  19. #include <sys\stat.h>
  20. #else
  21. #include <sys/types.h>
  22. #include <sys/stat.h>
  23. #endif /* __MSDOS__ */
  24. #ifdef __MACOSX__
  25. #define HAVE_FCNTL_H
  26. #define HAVE_UNISTD_H
  27. #endif
  28. #ifdef HAVE_IO_H
  29. #include <io.h>
  30. #endif
  31. #ifdef HAVE_FCNTL_H
  32. #include <fcntl.h>
  33. #endif /* HAVE_FCNTL_H */
  34. #ifdef HAVE_UNISTD_H
  35. #include <unistd.h>
  36. #endif /* HAVE_UNISTD_H */
  37. #include <stdio.h>
  38. #include <string.h>
  39. #include "gif_lib.h"
  40. #include "gif_lib_private.h"
  41. #define COMMENT_EXT_FUNC_CODE 0xfe /* Extension function code for
  42. comment. */
  43. /* avoid extra function call in case we use fread (TVT) */
  44. #define READ(_gif,_buf,_len) \
  45. (((GifFilePrivateType*)_gif->Private)->Read ? \
  46. ((GifFilePrivateType*)_gif->Private)->Read(_gif,_buf,_len) : \
  47. fread(_buf,1,_len,((GifFilePrivateType*)_gif->Private)->File))
  48. static int DGifGetWord(GifFileType *GifFile, GifWord *Word);
  49. static int DGifSetupDecompress(GifFileType *GifFile);
  50. static int DGifDecompressLine(GifFileType *GifFile, GifPixelType *Line,
  51. int LineLen);
  52. static int DGifGetPrefixChar(GifPrefixType *Prefix, int Code, int ClearCode);
  53. static int DGifDecompressInput(GifFileType *GifFile, int *Code);
  54. static int DGifBufferedInput(GifFileType *GifFile, GifByteType *Buf,
  55. GifByteType *NextByte);
  56. #ifndef _GBA_NO_FILEIO
  57. /******************************************************************************
  58. * Open a new gif file for read, given by its name.
  59. * Returns GifFileType pointer dynamically allocated which serves as the gif
  60. * info record. _GifError is cleared if succesfull.
  61. *****************************************************************************/
  62. GifFileType *
  63. DGifOpenFileName(const char *FileName) {
  64. int FileHandle;
  65. GifFileType *GifFile;
  66. if ((FileHandle = open(FileName, O_RDONLY
  67. #if defined(__MSDOS__) || defined(_OPEN_BINARY)
  68. | O_BINARY
  69. #endif /* __MSDOS__ || _OPEN_BINARY */
  70. )) == -1) {
  71. _GifError = D_GIF_ERR_OPEN_FAILED;
  72. return NULL;
  73. }
  74. GifFile = DGifOpenFileHandle(FileHandle);
  75. if (GifFile == (GifFileType *)NULL)
  76. close(FileHandle);
  77. return GifFile;
  78. }
  79. /******************************************************************************
  80. * Update a new gif file, given its file handle.
  81. * Returns GifFileType pointer dynamically allocated which serves as the gif
  82. * info record. _GifError is cleared if succesfull.
  83. *****************************************************************************/
  84. GifFileType *
  85. DGifOpenFileHandle(int FileHandle) {
  86. unsigned char Buf[GIF_STAMP_LEN + 1];
  87. GifFileType *GifFile;
  88. GifFilePrivateType *Private;
  89. FILE *f;
  90. GifFile = (GifFileType *)malloc(sizeof(GifFileType));
  91. if (GifFile == NULL) {
  92. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  93. return NULL;
  94. }
  95. memset(GifFile, '\0', sizeof(GifFileType));
  96. Private = (GifFilePrivateType *)malloc(sizeof(GifFilePrivateType));
  97. if (Private == NULL) {
  98. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  99. free((char *)GifFile);
  100. return NULL;
  101. }
  102. #ifdef __MSDOS__
  103. setmode(FileHandle, O_BINARY); /* Make sure it is in binary mode. */
  104. #endif /* __MSDOS__ */
  105. f = fdopen(FileHandle, "rb"); /* Make it into a stream: */
  106. #ifdef __MSDOS__
  107. setvbuf(f, NULL, _IOFBF, GIF_FILE_BUFFER_SIZE); /* And inc. stream
  108. buffer. */
  109. #endif /* __MSDOS__ */
  110. GifFile->Private = (VoidPtr)Private;
  111. Private->FileHandle = FileHandle;
  112. Private->File = f;
  113. Private->FileState = FILE_STATE_READ;
  114. Private->Read = 0; /* don't use alternate input method (TVT) */
  115. GifFile->UserData = 0; /* TVT */
  116. /* Lets see if this is a GIF file: */
  117. if (READ(GifFile, Buf, GIF_STAMP_LEN) != GIF_STAMP_LEN) {
  118. _GifError = D_GIF_ERR_READ_FAILED;
  119. fclose(f);
  120. free((char *)Private);
  121. free((char *)GifFile);
  122. return NULL;
  123. }
  124. /* The GIF Version number is ignored at this time. Maybe we should do
  125. * something more useful with it. */
  126. Buf[GIF_STAMP_LEN] = 0;
  127. if (strncmp(GIF_STAMP, Buf, GIF_VERSION_POS) != 0) {
  128. _GifError = D_GIF_ERR_NOT_GIF_FILE;
  129. fclose(f);
  130. free((char *)Private);
  131. free((char *)GifFile);
  132. return NULL;
  133. }
  134. if (DGifGetScreenDesc(GifFile) == GIF_ERROR) {
  135. fclose(f);
  136. free((char *)Private);
  137. free((char *)GifFile);
  138. return NULL;
  139. }
  140. _GifError = 0;
  141. return GifFile;
  142. }
  143. #endif /* _GBA_NO_FILEIO */
  144. /******************************************************************************
  145. * GifFileType constructor with user supplied input function (TVT)
  146. *****************************************************************************/
  147. GifFileType *
  148. DGifOpen(void *userData,
  149. InputFunc readFunc) {
  150. unsigned char Buf[GIF_STAMP_LEN + 1];
  151. GifFileType *GifFile;
  152. GifFilePrivateType *Private;
  153. GifFile = (GifFileType *)malloc(sizeof(GifFileType));
  154. if (GifFile == NULL) {
  155. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  156. return NULL;
  157. }
  158. memset(GifFile, '\0', sizeof(GifFileType));
  159. Private = (GifFilePrivateType *)malloc(sizeof(GifFilePrivateType));
  160. if (!Private) {
  161. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  162. free((char *)GifFile);
  163. return NULL;
  164. }
  165. GifFile->Private = (VoidPtr)Private;
  166. Private->FileHandle = 0;
  167. Private->File = 0;
  168. Private->FileState = FILE_STATE_READ;
  169. Private->Read = readFunc; /* TVT */
  170. GifFile->UserData = userData; /* TVT */
  171. /* Lets see if this is a GIF file: */
  172. if (READ(GifFile, Buf, GIF_STAMP_LEN) != GIF_STAMP_LEN) {
  173. _GifError = D_GIF_ERR_READ_FAILED;
  174. free((char *)Private);
  175. free((char *)GifFile);
  176. return NULL;
  177. }
  178. /* The GIF Version number is ignored at this time. Maybe we should do
  179. * something more useful with it. */
  180. Buf[GIF_STAMP_LEN] = 0;
  181. if (strncmp(GIF_STAMP, Buf, GIF_VERSION_POS) != 0) {
  182. _GifError = D_GIF_ERR_NOT_GIF_FILE;
  183. free((char *)Private);
  184. free((char *)GifFile);
  185. return NULL;
  186. }
  187. if (DGifGetScreenDesc(GifFile) == GIF_ERROR) {
  188. free((char *)Private);
  189. free((char *)GifFile);
  190. return NULL;
  191. }
  192. _GifError = 0;
  193. return GifFile;
  194. }
  195. /******************************************************************************
  196. * This routine should be called before any other DGif calls. Note that
  197. * this routine is called automatically from DGif file open routines.
  198. *****************************************************************************/
  199. int
  200. DGifGetScreenDesc(GifFileType * GifFile) {
  201. int i, BitsPerPixel;
  202. GifByteType Buf[3];
  203. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  204. if (!IS_READABLE(Private)) {
  205. /* This file was NOT open for reading: */
  206. _GifError = D_GIF_ERR_NOT_READABLE;
  207. return GIF_ERROR;
  208. }
  209. /* Put the screen descriptor into the file: */
  210. if (DGifGetWord(GifFile, &GifFile->SWidth) == GIF_ERROR ||
  211. DGifGetWord(GifFile, &GifFile->SHeight) == GIF_ERROR)
  212. return GIF_ERROR;
  213. if (READ(GifFile, Buf, 3) != 3) {
  214. _GifError = D_GIF_ERR_READ_FAILED;
  215. return GIF_ERROR;
  216. }
  217. GifFile->SColorResolution = (((Buf[0] & 0x70) + 1) >> 4) + 1;
  218. BitsPerPixel = (Buf[0] & 0x07) + 1;
  219. GifFile->SBackGroundColor = Buf[1];
  220. if (Buf[0] & 0x80) { /* Do we have global color map? */
  221. GifFile->SColorMap = MakeMapObject(1 << BitsPerPixel, NULL);
  222. if (GifFile->SColorMap == NULL) {
  223. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  224. return GIF_ERROR;
  225. }
  226. /* Get the global color map: */
  227. for (i = 0; i < GifFile->SColorMap->ColorCount; i++) {
  228. if (READ(GifFile, Buf, 3) != 3) {
  229. FreeMapObject(GifFile->SColorMap);
  230. GifFile->SColorMap = NULL;
  231. _GifError = D_GIF_ERR_READ_FAILED;
  232. return GIF_ERROR;
  233. }
  234. GifFile->SColorMap->Colors[i].Red = Buf[0];
  235. GifFile->SColorMap->Colors[i].Green = Buf[1];
  236. GifFile->SColorMap->Colors[i].Blue = Buf[2];
  237. }
  238. } else {
  239. GifFile->SColorMap = NULL;
  240. }
  241. return GIF_OK;
  242. }
  243. /******************************************************************************
  244. * This routine should be called before any attempt to read an image.
  245. *****************************************************************************/
  246. int
  247. DGifGetRecordType(GifFileType * GifFile,
  248. GifRecordType * Type) {
  249. GifByteType Buf;
  250. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  251. if (!IS_READABLE(Private)) {
  252. /* This file was NOT open for reading: */
  253. _GifError = D_GIF_ERR_NOT_READABLE;
  254. return GIF_ERROR;
  255. }
  256. if (READ(GifFile, &Buf, 1) != 1) {
  257. _GifError = D_GIF_ERR_READ_FAILED;
  258. return GIF_ERROR;
  259. }
  260. switch (Buf) {
  261. case ',':
  262. *Type = IMAGE_DESC_RECORD_TYPE;
  263. break;
  264. case '!':
  265. *Type = EXTENSION_RECORD_TYPE;
  266. break;
  267. case ';':
  268. *Type = TERMINATE_RECORD_TYPE;
  269. break;
  270. default:
  271. *Type = UNDEFINED_RECORD_TYPE;
  272. _GifError = D_GIF_ERR_WRONG_RECORD;
  273. return GIF_ERROR;
  274. }
  275. return GIF_OK;
  276. }
  277. /******************************************************************************
  278. * This routine should be called before any attempt to read an image.
  279. * Note it is assumed the Image desc. header (',') has been read.
  280. *****************************************************************************/
  281. int
  282. DGifGetImageDesc(GifFileType * GifFile) {
  283. int i, BitsPerPixel;
  284. GifByteType Buf[3];
  285. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  286. SavedImage *sp;
  287. if (!IS_READABLE(Private)) {
  288. /* This file was NOT open for reading: */
  289. _GifError = D_GIF_ERR_NOT_READABLE;
  290. return GIF_ERROR;
  291. }
  292. if (DGifGetWord(GifFile, &GifFile->Image.Left) == GIF_ERROR ||
  293. DGifGetWord(GifFile, &GifFile->Image.Top) == GIF_ERROR ||
  294. DGifGetWord(GifFile, &GifFile->Image.Width) == GIF_ERROR ||
  295. DGifGetWord(GifFile, &GifFile->Image.Height) == GIF_ERROR)
  296. return GIF_ERROR;
  297. if (READ(GifFile, Buf, 1) != 1) {
  298. _GifError = D_GIF_ERR_READ_FAILED;
  299. return GIF_ERROR;
  300. }
  301. BitsPerPixel = (Buf[0] & 0x07) + 1;
  302. GifFile->Image.Interlace = (Buf[0] & 0x40);
  303. if (Buf[0] & 0x80) { /* Does this image have local color map? */
  304. /*** FIXME: Why do we check both of these in order to do this?
  305. * Why do we have both Image and SavedImages? */
  306. if (GifFile->Image.ColorMap && GifFile->SavedImages == NULL)
  307. FreeMapObject(GifFile->Image.ColorMap);
  308. GifFile->Image.ColorMap = MakeMapObject(1 << BitsPerPixel, NULL);
  309. if (GifFile->Image.ColorMap == NULL) {
  310. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  311. return GIF_ERROR;
  312. }
  313. /* Get the image local color map: */
  314. for (i = 0; i < GifFile->Image.ColorMap->ColorCount; i++) {
  315. if (READ(GifFile, Buf, 3) != 3) {
  316. FreeMapObject(GifFile->Image.ColorMap);
  317. _GifError = D_GIF_ERR_READ_FAILED;
  318. GifFile->Image.ColorMap = NULL;
  319. return GIF_ERROR;
  320. }
  321. GifFile->Image.ColorMap->Colors[i].Red = Buf[0];
  322. GifFile->Image.ColorMap->Colors[i].Green = Buf[1];
  323. GifFile->Image.ColorMap->Colors[i].Blue = Buf[2];
  324. }
  325. } else if (GifFile->Image.ColorMap) {
  326. FreeMapObject(GifFile->Image.ColorMap);
  327. GifFile->Image.ColorMap = NULL;
  328. }
  329. if (GifFile->SavedImages) {
  330. if ((GifFile->SavedImages = (SavedImage *)realloc(GifFile->SavedImages,
  331. sizeof(SavedImage) *
  332. (GifFile->ImageCount + 1))) == NULL) {
  333. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  334. return GIF_ERROR;
  335. }
  336. } else {
  337. if ((GifFile->SavedImages =
  338. (SavedImage *) malloc(sizeof(SavedImage))) == NULL) {
  339. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  340. return GIF_ERROR;
  341. }
  342. }
  343. sp = &GifFile->SavedImages[GifFile->ImageCount];
  344. memcpy(&sp->ImageDesc, &GifFile->Image, sizeof(GifImageDesc));
  345. if (GifFile->Image.ColorMap != NULL) {
  346. sp->ImageDesc.ColorMap = MakeMapObject(
  347. GifFile->Image.ColorMap->ColorCount,
  348. GifFile->Image.ColorMap->Colors);
  349. if (sp->ImageDesc.ColorMap == NULL) {
  350. _GifError = D_GIF_ERR_NOT_ENOUGH_MEM;
  351. return GIF_ERROR;
  352. }
  353. }
  354. sp->RasterBits = (unsigned char *)NULL;
  355. sp->ExtensionBlockCount = 0;
  356. sp->ExtensionBlocks = (ExtensionBlock *) NULL;
  357. GifFile->ImageCount++;
  358. Private->PixelCount = (long)GifFile->Image.Width *
  359. (long)GifFile->Image.Height;
  360. DGifSetupDecompress(GifFile); /* Reset decompress algorithm parameters. */
  361. return GIF_OK;
  362. }
  363. /******************************************************************************
  364. * Get one full scanned line (Line) of length LineLen from GIF file.
  365. *****************************************************************************/
  366. int
  367. DGifGetLine(GifFileType * GifFile,
  368. GifPixelType * Line,
  369. int LineLen) {
  370. GifByteType *Dummy;
  371. GifFilePrivateType *Private = (GifFilePrivateType *) GifFile->Private;
  372. if (!IS_READABLE(Private)) {
  373. /* This file was NOT open for reading: */
  374. _GifError = D_GIF_ERR_NOT_READABLE;
  375. return GIF_ERROR;
  376. }
  377. if (!LineLen)
  378. LineLen = GifFile->Image.Width;
  379. #if defined(__MSDOS__) || defined(__GNUC__)
  380. if ((Private->PixelCount -= LineLen) > 0xffff0000UL) {
  381. #else
  382. if ((Private->PixelCount -= LineLen) > 0xffff0000) {
  383. #endif /* __MSDOS__ */
  384. _GifError = D_GIF_ERR_DATA_TOO_BIG;
  385. return GIF_ERROR;
  386. }
  387. if (DGifDecompressLine(GifFile, Line, LineLen) == GIF_OK) {
  388. if (Private->PixelCount == 0) {
  389. /* We probably would not be called any more, so lets clean
  390. * everything before we return: need to flush out all rest of
  391. * image until empty block (size 0) detected. We use GetCodeNext. */
  392. do
  393. if (DGifGetCodeNext(GifFile, &Dummy) == GIF_ERROR)
  394. return GIF_ERROR;
  395. while (Dummy != NULL) ;
  396. }
  397. return GIF_OK;
  398. } else
  399. return GIF_ERROR;
  400. }
  401. /******************************************************************************
  402. * Put one pixel (Pixel) into GIF file.
  403. *****************************************************************************/
  404. int
  405. DGifGetPixel(GifFileType * GifFile,
  406. GifPixelType Pixel) {
  407. GifByteType *Dummy;
  408. GifFilePrivateType *Private = (GifFilePrivateType *) GifFile->Private;
  409. if (!IS_READABLE(Private)) {
  410. /* This file was NOT open for reading: */
  411. _GifError = D_GIF_ERR_NOT_READABLE;
  412. return GIF_ERROR;
  413. }
  414. #if defined(__MSDOS__) || defined(__GNUC__)
  415. if (--Private->PixelCount > 0xffff0000UL)
  416. #else
  417. if (--Private->PixelCount > 0xffff0000)
  418. #endif /* __MSDOS__ */
  419. {
  420. _GifError = D_GIF_ERR_DATA_TOO_BIG;
  421. return GIF_ERROR;
  422. }
  423. if (DGifDecompressLine(GifFile, &Pixel, 1) == GIF_OK) {
  424. if (Private->PixelCount == 0) {
  425. /* We probably would not be called any more, so lets clean
  426. * everything before we return: need to flush out all rest of
  427. * image until empty block (size 0) detected. We use GetCodeNext. */
  428. do
  429. if (DGifGetCodeNext(GifFile, &Dummy) == GIF_ERROR)
  430. return GIF_ERROR;
  431. while (Dummy != NULL) ;
  432. }
  433. return GIF_OK;
  434. } else
  435. return GIF_ERROR;
  436. }
  437. /******************************************************************************
  438. * Get an extension block (see GIF manual) from gif file. This routine only
  439. * returns the first data block, and DGifGetExtensionNext should be called
  440. * after this one until NULL extension is returned.
  441. * The Extension should NOT be freed by the user (not dynamically allocated).
  442. * Note it is assumed the Extension desc. header ('!') has been read.
  443. *****************************************************************************/
  444. int
  445. DGifGetExtension(GifFileType * GifFile,
  446. int *ExtCode,
  447. GifByteType ** Extension) {
  448. GifByteType Buf;
  449. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  450. if (!IS_READABLE(Private)) {
  451. /* This file was NOT open for reading: */
  452. _GifError = D_GIF_ERR_NOT_READABLE;
  453. return GIF_ERROR;
  454. }
  455. if (READ(GifFile, &Buf, 1) != 1) {
  456. _GifError = D_GIF_ERR_READ_FAILED;
  457. return GIF_ERROR;
  458. }
  459. *ExtCode = Buf;
  460. return DGifGetExtensionNext(GifFile, Extension);
  461. }
  462. /******************************************************************************
  463. * Get a following extension block (see GIF manual) from gif file. This
  464. * routine should be called until NULL Extension is returned.
  465. * The Extension should NOT be freed by the user (not dynamically allocated).
  466. *****************************************************************************/
  467. int
  468. DGifGetExtensionNext(GifFileType * GifFile,
  469. GifByteType ** Extension) {
  470. GifByteType Buf;
  471. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  472. if (READ(GifFile, &Buf, 1) != 1) {
  473. _GifError = D_GIF_ERR_READ_FAILED;
  474. return GIF_ERROR;
  475. }
  476. if (Buf > 0) {
  477. *Extension = Private->Buf; /* Use private unused buffer. */
  478. (*Extension)[0] = Buf; /* Pascal strings notation (pos. 0 is len.). */
  479. if (READ(GifFile, &((*Extension)[1]), Buf) != Buf) {
  480. _GifError = D_GIF_ERR_READ_FAILED;
  481. return GIF_ERROR;
  482. }
  483. } else
  484. *Extension = NULL;
  485. return GIF_OK;
  486. }
  487. /******************************************************************************
  488. * This routine should be called last, to close the GIF file.
  489. *****************************************************************************/
  490. int
  491. DGifCloseFile(GifFileType * GifFile) {
  492. GifFilePrivateType *Private;
  493. FILE *File;
  494. if (GifFile == NULL)
  495. return GIF_ERROR;
  496. Private = (GifFilePrivateType *) GifFile->Private;
  497. if (!IS_READABLE(Private)) {
  498. /* This file was NOT open for reading: */
  499. _GifError = D_GIF_ERR_NOT_READABLE;
  500. return GIF_ERROR;
  501. }
  502. File = Private->File;
  503. if (GifFile->Image.ColorMap) {
  504. FreeMapObject(GifFile->Image.ColorMap);
  505. GifFile->Image.ColorMap = NULL;
  506. }
  507. if (GifFile->SColorMap) {
  508. FreeMapObject(GifFile->SColorMap);
  509. GifFile->SColorMap = NULL;
  510. }
  511. if (Private) {
  512. free((char *)Private);
  513. Private = NULL;
  514. }
  515. if (GifFile->SavedImages) {
  516. FreeSavedImages(GifFile);
  517. GifFile->SavedImages = NULL;
  518. }
  519. free(GifFile);
  520. if (File && (fclose(File) != 0)) {
  521. _GifError = D_GIF_ERR_CLOSE_FAILED;
  522. return GIF_ERROR;
  523. }
  524. return GIF_OK;
  525. }
  526. /******************************************************************************
  527. * Get 2 bytes (word) from the given file:
  528. *****************************************************************************/
  529. static int
  530. DGifGetWord(GifFileType * GifFile,
  531. GifWord *Word) {
  532. unsigned char c[2];
  533. if (READ(GifFile, c, 2) != 2) {
  534. _GifError = D_GIF_ERR_READ_FAILED;
  535. return GIF_ERROR;
  536. }
  537. *Word = (((unsigned int)c[1]) << 8) + c[0];
  538. return GIF_OK;
  539. }
  540. /******************************************************************************
  541. * Get the image code in compressed form. This routine can be called if the
  542. * information needed to be piped out as is. Obviously this is much faster
  543. * than decoding and encoding again. This routine should be followed by calls
  544. * to DGifGetCodeNext, until NULL block is returned.
  545. * The block should NOT be freed by the user (not dynamically allocated).
  546. *****************************************************************************/
  547. int
  548. DGifGetCode(GifFileType * GifFile,
  549. int *CodeSize,
  550. GifByteType ** CodeBlock) {
  551. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  552. if (!IS_READABLE(Private)) {
  553. /* This file was NOT open for reading: */
  554. _GifError = D_GIF_ERR_NOT_READABLE;
  555. return GIF_ERROR;
  556. }
  557. *CodeSize = Private->BitsPerPixel;
  558. return DGifGetCodeNext(GifFile, CodeBlock);
  559. }
  560. /******************************************************************************
  561. * Continue to get the image code in compressed form. This routine should be
  562. * called until NULL block is returned.
  563. * The block should NOT be freed by the user (not dynamically allocated).
  564. *****************************************************************************/
  565. int
  566. DGifGetCodeNext(GifFileType * GifFile,
  567. GifByteType ** CodeBlock) {
  568. GifByteType Buf;
  569. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  570. if (READ(GifFile, &Buf, 1) != 1) {
  571. _GifError = D_GIF_ERR_READ_FAILED;
  572. return GIF_ERROR;
  573. }
  574. if (Buf > 0) {
  575. *CodeBlock = Private->Buf; /* Use private unused buffer. */
  576. (*CodeBlock)[0] = Buf; /* Pascal strings notation (pos. 0 is len.). */
  577. if (READ(GifFile, &((*CodeBlock)[1]), Buf) != Buf) {
  578. _GifError = D_GIF_ERR_READ_FAILED;
  579. return GIF_ERROR;
  580. }
  581. } else {
  582. *CodeBlock = NULL;
  583. Private->Buf[0] = 0; /* Make sure the buffer is empty! */
  584. Private->PixelCount = 0; /* And local info. indicate image read. */
  585. }
  586. return GIF_OK;
  587. }
  588. /******************************************************************************
  589. * Setup the LZ decompression for this image:
  590. *****************************************************************************/
  591. static int
  592. DGifSetupDecompress(GifFileType * GifFile) {
  593. int i, BitsPerPixel;
  594. GifByteType CodeSize;
  595. GifPrefixType *Prefix;
  596. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  597. READ(GifFile, &CodeSize, 1); /* Read Code size from file. */
  598. BitsPerPixel = CodeSize;
  599. Private->Buf[0] = 0; /* Input Buffer empty. */
  600. Private->BitsPerPixel = BitsPerPixel;
  601. Private->ClearCode = (1 << BitsPerPixel);
  602. Private->EOFCode = Private->ClearCode + 1;
  603. Private->RunningCode = Private->EOFCode + 1;
  604. Private->RunningBits = BitsPerPixel + 1; /* Number of bits per code. */
  605. Private->MaxCode1 = 1 << Private->RunningBits; /* Max. code + 1. */
  606. Private->StackPtr = 0; /* No pixels on the pixel stack. */
  607. Private->LastCode = NO_SUCH_CODE;
  608. Private->CrntShiftState = 0; /* No information in CrntShiftDWord. */
  609. Private->CrntShiftDWord = 0;
  610. Prefix = Private->Prefix;
  611. for (i = 0; i <= LZ_MAX_CODE; i++)
  612. Prefix[i] = NO_SUCH_CODE;
  613. return GIF_OK;
  614. }
  615. /******************************************************************************
  616. * The LZ decompression routine:
  617. * This version decompress the given gif file into Line of length LineLen.
  618. * This routine can be called few times (one per scan line, for example), in
  619. * order the complete the whole image.
  620. *****************************************************************************/
  621. static int
  622. DGifDecompressLine(GifFileType * GifFile,
  623. GifPixelType * Line,
  624. int LineLen) {
  625. int i = 0;
  626. int j, CrntCode, EOFCode, ClearCode, CrntPrefix, LastCode, StackPtr;
  627. GifByteType *Stack, *Suffix;
  628. GifPrefixType *Prefix;
  629. GifFilePrivateType *Private = (GifFilePrivateType *) GifFile->Private;
  630. StackPtr = Private->StackPtr;
  631. Prefix = Private->Prefix;
  632. Suffix = Private->Suffix;
  633. Stack = Private->Stack;
  634. EOFCode = Private->EOFCode;
  635. ClearCode = Private->ClearCode;
  636. LastCode = Private->LastCode;
  637. if (StackPtr != 0) {
  638. /* Let pop the stack off before continueing to read the gif file: */
  639. while (StackPtr != 0 && i < LineLen)
  640. Line[i++] = Stack[--StackPtr];
  641. }
  642. while (i < LineLen) { /* Decode LineLen items. */
  643. if (DGifDecompressInput(GifFile, &CrntCode) == GIF_ERROR)
  644. return GIF_ERROR;
  645. if (CrntCode == EOFCode) {
  646. /* Note however that usually we will not be here as we will stop
  647. * decoding as soon as we got all the pixel, or EOF code will
  648. * not be read at all, and DGifGetLine/Pixel clean everything. */
  649. if (i != LineLen - 1 || Private->PixelCount != 0) {
  650. _GifError = D_GIF_ERR_EOF_TOO_SOON;
  651. return GIF_ERROR;
  652. }
  653. i++;
  654. } else if (CrntCode == ClearCode) {
  655. /* We need to start over again: */
  656. for (j = 0; j <= LZ_MAX_CODE; j++)
  657. Prefix[j] = NO_SUCH_CODE;
  658. Private->RunningCode = Private->EOFCode + 1;
  659. Private->RunningBits = Private->BitsPerPixel + 1;
  660. Private->MaxCode1 = 1 << Private->RunningBits;
  661. LastCode = Private->LastCode = NO_SUCH_CODE;
  662. } else {
  663. /* Its regular code - if in pixel range simply add it to output
  664. * stream, otherwise trace to codes linked list until the prefix
  665. * is in pixel range: */
  666. if (CrntCode < ClearCode) {
  667. /* This is simple - its pixel scalar, so add it to output: */
  668. Line[i++] = CrntCode;
  669. } else {
  670. /* Its a code to needed to be traced: trace the linked list
  671. * until the prefix is a pixel, while pushing the suffix
  672. * pixels on our stack. If we done, pop the stack in reverse
  673. * (thats what stack is good for!) order to output. */
  674. if (Prefix[CrntCode] == NO_SUCH_CODE) {
  675. /* Only allowed if CrntCode is exactly the running code:
  676. * In that case CrntCode = XXXCode, CrntCode or the
  677. * prefix code is last code and the suffix char is
  678. * exactly the prefix of last code! */
  679. if (CrntCode == Private->RunningCode - 2) {
  680. CrntPrefix = LastCode;
  681. Suffix[Private->RunningCode - 2] =
  682. Stack[StackPtr++] = DGifGetPrefixChar(Prefix,
  683. LastCode,
  684. ClearCode);
  685. } else {
  686. _GifError = D_GIF_ERR_IMAGE_DEFECT;
  687. return GIF_ERROR;
  688. }
  689. } else
  690. CrntPrefix = CrntCode;
  691. /* Now (if image is O.K.) we should not get an NO_SUCH_CODE
  692. * During the trace. As we might loop forever, in case of
  693. * defective image, we count the number of loops we trace
  694. * and stop if we got LZ_MAX_CODE. obviously we can not
  695. * loop more than that. */
  696. j = 0;
  697. while (j++ <= LZ_MAX_CODE &&
  698. CrntPrefix > ClearCode && CrntPrefix <= LZ_MAX_CODE) {
  699. Stack[StackPtr++] = Suffix[CrntPrefix];
  700. CrntPrefix = Prefix[CrntPrefix];
  701. }
  702. if (j >= LZ_MAX_CODE || CrntPrefix > LZ_MAX_CODE) {
  703. _GifError = D_GIF_ERR_IMAGE_DEFECT;
  704. return GIF_ERROR;
  705. }
  706. /* Push the last character on stack: */
  707. Stack[StackPtr++] = CrntPrefix;
  708. /* Now lets pop all the stack into output: */
  709. while (StackPtr != 0 && i < LineLen)
  710. Line[i++] = Stack[--StackPtr];
  711. }
  712. if (LastCode != NO_SUCH_CODE) {
  713. Prefix[Private->RunningCode - 2] = LastCode;
  714. if (CrntCode == Private->RunningCode - 2) {
  715. /* Only allowed if CrntCode is exactly the running code:
  716. * In that case CrntCode = XXXCode, CrntCode or the
  717. * prefix code is last code and the suffix char is
  718. * exactly the prefix of last code! */
  719. Suffix[Private->RunningCode - 2] =
  720. DGifGetPrefixChar(Prefix, LastCode, ClearCode);
  721. } else {
  722. Suffix[Private->RunningCode - 2] =
  723. DGifGetPrefixChar(Prefix, CrntCode, ClearCode);
  724. }
  725. }
  726. LastCode = CrntCode;
  727. }
  728. }
  729. Private->LastCode = LastCode;
  730. Private->StackPtr = StackPtr;
  731. return GIF_OK;
  732. }
  733. /******************************************************************************
  734. * Routine to trace the Prefixes linked list until we get a prefix which is
  735. * not code, but a pixel value (less than ClearCode). Returns that pixel value.
  736. * If image is defective, we might loop here forever, so we limit the loops to
  737. * the maximum possible if image O.k. - LZ_MAX_CODE times.
  738. *****************************************************************************/
  739. static int
  740. DGifGetPrefixChar(GifPrefixType *Prefix,
  741. int Code,
  742. int ClearCode) {
  743. int i = 0;
  744. while (Code > ClearCode && i++ <= LZ_MAX_CODE)
  745. Code = Prefix[Code];
  746. return Code;
  747. }
  748. /******************************************************************************
  749. * Interface for accessing the LZ codes directly. Set Code to the real code
  750. * (12bits), or to -1 if EOF code is returned.
  751. *****************************************************************************/
  752. int
  753. DGifGetLZCodes(GifFileType * GifFile,
  754. int *Code) {
  755. GifByteType *CodeBlock;
  756. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  757. if (!IS_READABLE(Private)) {
  758. /* This file was NOT open for reading: */
  759. _GifError = D_GIF_ERR_NOT_READABLE;
  760. return GIF_ERROR;
  761. }
  762. if (DGifDecompressInput(GifFile, Code) == GIF_ERROR)
  763. return GIF_ERROR;
  764. if (*Code == Private->EOFCode) {
  765. /* Skip rest of codes (hopefully only NULL terminating block): */
  766. do {
  767. if (DGifGetCodeNext(GifFile, &CodeBlock) == GIF_ERROR)
  768. return GIF_ERROR;
  769. } while (CodeBlock != NULL) ;
  770. *Code = -1;
  771. } else if (*Code == Private->ClearCode) {
  772. /* We need to start over again: */
  773. Private->RunningCode = Private->EOFCode + 1;
  774. Private->RunningBits = Private->BitsPerPixel + 1;
  775. Private->MaxCode1 = 1 << Private->RunningBits;
  776. }
  777. return GIF_OK;
  778. }
  779. /******************************************************************************
  780. * The LZ decompression input routine:
  781. * This routine is responsable for the decompression of the bit stream from
  782. * 8 bits (bytes) packets, into the real codes.
  783. * Returns GIF_OK if read succesfully.
  784. *****************************************************************************/
  785. static int
  786. DGifDecompressInput(GifFileType * GifFile,
  787. int *Code) {
  788. GifFilePrivateType *Private = (GifFilePrivateType *)GifFile->Private;
  789. GifByteType NextByte;
  790. static unsigned short CodeMasks[] = {
  791. 0x0000, 0x0001, 0x0003, 0x0007,
  792. 0x000f, 0x001f, 0x003f, 0x007f,
  793. 0x00ff, 0x01ff, 0x03ff, 0x07ff,
  794. 0x0fff
  795. };
  796. /* The image can't contain more than LZ_BITS per code. */
  797. if (Private->RunningBits > LZ_BITS) {
  798. _GifError = D_GIF_ERR_IMAGE_DEFECT;
  799. return GIF_ERROR;
  800. }
  801. while (Private->CrntShiftState < Private->RunningBits) {
  802. /* Needs to get more bytes from input stream for next code: */
  803. if (DGifBufferedInput(GifFile, Private->Buf, &NextByte) == GIF_ERROR) {
  804. return GIF_ERROR;
  805. }
  806. Private->CrntShiftDWord |=
  807. ((unsigned long)NextByte) << Private->CrntShiftState;
  808. Private->CrntShiftState += 8;
  809. }
  810. *Code = Private->CrntShiftDWord & CodeMasks[Private->RunningBits];
  811. Private->CrntShiftDWord >>= Private->RunningBits;
  812. Private->CrntShiftState -= Private->RunningBits;
  813. /* If code cannot fit into RunningBits bits, must raise its size. Note
  814. * however that codes above 4095 are used for special signaling.
  815. * If we're using LZ_BITS bits already and we're at the max code, just
  816. * keep using the table as it is, don't increment Private->RunningCode.
  817. */
  818. if (Private->RunningCode < LZ_MAX_CODE + 2 &&
  819. ++Private->RunningCode > Private->MaxCode1 &&
  820. Private->RunningBits < LZ_BITS) {
  821. Private->MaxCode1 <<= 1;
  822. Private->RunningBits++;
  823. }
  824. return GIF_OK;
  825. }
  826. /******************************************************************************
  827. * This routines read one gif data block at a time and buffers it internally
  828. * so that the decompression routine could access it.
  829. * The routine returns the next byte from its internal buffer (or read next
  830. * block in if buffer empty) and returns GIF_OK if succesful.
  831. *****************************************************************************/
  832. static int
  833. DGifBufferedInput(GifFileType * GifFile,
  834. GifByteType * Buf,
  835. GifByteType * NextByte) {
  836. if (Buf[0] == 0) {
  837. /* Needs to read the next buffer - this one is empty: */
  838. if (READ(GifFile, Buf, 1) != 1) {
  839. _GifError = D_GIF_ERR_READ_FAILED;
  840. return GIF_ERROR;
  841. }
  842. /* There shouldn't be any empty data blocks here as the LZW spec
  843. * says the LZW termination code should come first. Therefore we
  844. * shouldn't be inside this routine at that point.
  845. */
  846. if (Buf[0] == 0) {
  847. _GifError = D_GIF_ERR_IMAGE_DEFECT;
  848. return GIF_ERROR;
  849. }
  850. if (READ(GifFile, &Buf[1], Buf[0]) != Buf[0]) {
  851. _GifError = D_GIF_ERR_READ_FAILED;
  852. return GIF_ERROR;
  853. }
  854. *NextByte = Buf[1];
  855. Buf[1] = 2; /* We use now the second place as last char read! */
  856. Buf[0]--;
  857. } else {
  858. *NextByte = Buf[Buf[1]++];
  859. Buf[0]--;
  860. }
  861. return GIF_OK;
  862. }
  863. #ifndef _GBA_NO_FILEIO
  864. /******************************************************************************
  865. * This routine reads an entire GIF into core, hanging all its state info off
  866. * the GifFileType pointer. Call DGifOpenFileName() or DGifOpenFileHandle()
  867. * first to initialize I/O. Its inverse is EGifSpew().
  868. ******************************************************************************/
  869. int
  870. DGifSlurp(GifFileType * GifFile) {
  871. int ImageSize;
  872. GifRecordType RecordType;
  873. SavedImage *sp;
  874. GifByteType *ExtData;
  875. SavedImage temp_save;
  876. temp_save.ExtensionBlocks = NULL;
  877. temp_save.ExtensionBlockCount = 0;
  878. do {
  879. if (DGifGetRecordType(GifFile, &RecordType) == GIF_ERROR)
  880. return (GIF_ERROR);
  881. switch (RecordType) {
  882. case IMAGE_DESC_RECORD_TYPE:
  883. if (DGifGetImageDesc(GifFile) == GIF_ERROR)
  884. return (GIF_ERROR);
  885. sp = &GifFile->SavedImages[GifFile->ImageCount - 1];
  886. ImageSize = sp->ImageDesc.Width * sp->ImageDesc.Height;
  887. sp->RasterBits = (unsigned char *)malloc(ImageSize *
  888. sizeof(GifPixelType));
  889. if (sp->RasterBits == NULL) {
  890. return GIF_ERROR;
  891. }
  892. if (DGifGetLine(GifFile, sp->RasterBits, ImageSize) ==
  893. GIF_ERROR)
  894. return (GIF_ERROR);
  895. if (temp_save.ExtensionBlocks) {
  896. sp->ExtensionBlocks = temp_save.ExtensionBlocks;
  897. sp->ExtensionBlockCount = temp_save.ExtensionBlockCount;
  898. temp_save.ExtensionBlocks = NULL;
  899. temp_save.ExtensionBlockCount = 0;
  900. /* FIXME: The following is wrong. It is left in only for
  901. * backwards compatibility. Someday it should go away. Use
  902. * the sp->ExtensionBlocks->Function variable instead. */
  903. sp->Function = sp->ExtensionBlocks[0].Function;
  904. }
  905. break;
  906. case EXTENSION_RECORD_TYPE:
  907. if (DGifGetExtension(GifFile, &temp_save.Function, &ExtData) ==
  908. GIF_ERROR)
  909. return (GIF_ERROR);
  910. while (ExtData != NULL) {
  911. /* Create an extension block with our data */
  912. if (AddExtensionBlock(&temp_save, ExtData[0], &ExtData[1])
  913. == GIF_ERROR)
  914. return (GIF_ERROR);
  915. if (DGifGetExtensionNext(GifFile, &ExtData) == GIF_ERROR)
  916. return (GIF_ERROR);
  917. temp_save.Function = 0;
  918. }
  919. break;
  920. case TERMINATE_RECORD_TYPE:
  921. break;
  922. default: /* Should be trapped by DGifGetRecordType */
  923. break;
  924. }
  925. } while (RecordType != TERMINATE_RECORD_TYPE);
  926. /* Just in case the Gif has an extension block without an associated
  927. * image... (Should we save this into a savefile structure with no image
  928. * instead? Have to check if the present writing code can handle that as
  929. * well.... */
  930. if (temp_save.ExtensionBlocks)
  931. FreeExtension(&temp_save);
  932. return (GIF_OK);
  933. }
  934. #endif /* _GBA_NO_FILEIO */