libextractor

GNU libextractor
Log | Files | Refs | Submodules | README | LICENSE

gif_extractor.c (4098B)


      1 /*
      2      This file is part of libextractor.
      3      Copyright (C) 2012 Vidyut Samanta and Christian Grothoff
      4 
      5      libextractor is free software; you can redistribute it and/or modify
      6      it under the terms of the GNU General Public License as published
      7      by the Free Software Foundation; either version 3, or (at your
      8      option) any later version.
      9 
     10      libextractor is distributed in the hope that it will be useful, but
     11      WITHOUT ANY WARRANTY; without even the implied warranty of
     12      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
     13      General Public License for more details.
     14 
     15      You should have received a copy of the GNU General Public License
     16      along with libextractor; see the file COPYING.  If not, write to the
     17      Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
     18      Boston, MA 02110-1301, USA.
     19  */
     20 /**
     21  * @file plugins/gif_extractor.c
     22  * @brief plugin to support GIF files
     23  * @author Christian Grothoff
     24  */
     25 #include "platform.h"
     26 #include "extractor.h"
     27 #include <gif_lib.h>
     28 
     29 
     30 /**
     31  * Callback invoked by libgif to read data.
     32  *
     33  * @param ft the file handle, including our extract context
     34  * @param bt where to write the data
     35  * @param arg number of bytes to read
     36  * @return -1 on error, otherwise number of bytes read
     37  */
     38 static int
     39 gif_READ_func (GifFileType *ft,
     40                GifByteType *bt,
     41                int arg)
     42 {
     43   struct EXTRACTOR_ExtractContext *ec = ft->UserData;
     44   void *data;
     45   ssize_t ret;
     46 
     47   ret = ec->read (ec->cls,
     48                   &data,
     49                   arg);
     50   if (-1 == ret)
     51     return -1;
     52   memcpy (bt, data, ret);
     53   return ret;
     54 }
     55 
     56 
     57 /**
     58  * Main entry method for the 'image/gif' extraction plugin.
     59  *
     60  * @param ec extraction context provided to the plugin
     61  */
     62 void
     63 EXTRACTOR_gif_extract_method (struct EXTRACTOR_ExtractContext *ec);
     64 
     65 void
     66 EXTRACTOR_gif_extract_method (struct EXTRACTOR_ExtractContext *ec)
     67 {
     68   GifFileType *gif_file;
     69   GifRecordType gif_type;
     70   GifByteType *ext;
     71   int et;
     72   char dims[128];
     73 #if defined (GIF_LIB_VERSION) || GIFLIB_MAJOR <= 4
     74   if (NULL == (gif_file = DGifOpen (ec, &gif_READ_func)))
     75     return; /* not a GIF */
     76 #else
     77   int gif_error;
     78 
     79   gif_error = 0;
     80   gif_file = DGifOpen (ec, &gif_READ_func, &gif_error);
     81   if ((gif_file == NULL) || (gif_error != 0))
     82   {
     83     if (gif_file != NULL)
     84 #if GIFLIB_MAJOR < 5 || GIFLIB_MINOR < 1
     85       EGifCloseFile (gif_file);
     86 #else
     87       EGifCloseFile (gif_file, NULL);
     88 #endif
     89     return; /* not a GIF */
     90   }
     91 #endif
     92   if (0 !=
     93       ec->proc (ec->cls,
     94                 "gif",
     95                 EXTRACTOR_METATYPE_MIMETYPE,
     96                 EXTRACTOR_METAFORMAT_UTF8,
     97                 "text/plain",
     98                 "image/gif",
     99                 strlen ("image/gif") + 1))
    100     return;
    101   snprintf (dims,
    102             sizeof (dims),
    103             "%dx%d",
    104             gif_file->SHeight,
    105             gif_file->SWidth);
    106   if (0 !=
    107       ec->proc (ec->cls,
    108                 "gif",
    109                 EXTRACTOR_METATYPE_IMAGE_DIMENSIONS,
    110                 EXTRACTOR_METAFORMAT_UTF8,
    111                 "text/plain",
    112                 dims,
    113                 strlen (dims) + 1))
    114     return;
    115   while (1)
    116   {
    117     if (GIF_OK !=
    118         DGifGetRecordType (gif_file,
    119                            &gif_type))
    120       break;
    121     if (UNDEFINED_RECORD_TYPE == gif_type)
    122       break;
    123     if (EXTENSION_RECORD_TYPE != gif_type)
    124       continue;
    125     if (GIF_OK !=
    126         DGifGetExtension (gif_file, &et, &ext))
    127       continue;
    128     if (NULL == ext)
    129       continue;
    130     if (COMMENT_EXT_FUNC_CODE == et)
    131     {
    132       ec->proc (ec->cls,
    133                 "gif",
    134                 EXTRACTOR_METATYPE_COMMENT,
    135                 EXTRACTOR_METAFORMAT_C_STRING,
    136                 "text/plain",
    137                 (char*) &ext[1],
    138                 (uint8_t) ext[0]);
    139       break;
    140     }
    141     while ( (GIF_ERROR !=
    142              DGifGetExtensionNext (gif_file, &ext)) &&
    143             (NULL != ext) )
    144       ;                   /* keep going */
    145   }
    146 #if defined (GIF_LIB_VERSION) || GIFLIB_MAJOR < 5 || GIFLIB_MINOR < 1
    147   DGifCloseFile (gif_file);
    148 #else
    149   DGifCloseFile (gif_file, NULL);
    150 #endif
    151 }
    152 
    153 
    154 /* end of gif_extractor.c */