IMG_xcf.c: Avoid infinite loop in read_xcf_header()
authorThomas Bernard <miniupnp@free.fr>
Fri, 30 Nov 2018 11:04:15 +0100
changeset 6312346808be360
parent 630 acc936055688
child 632 6536f264b1eb
IMG_xcf.c: Avoid infinite loop in read_xcf_header()
IMG_xcf.c
     1.1 --- a/IMG_xcf.c	Mon Nov 12 16:51:25 2018 -0800
     1.2 +++ b/IMG_xcf.c	Fri Nov 30 11:04:15 2018 +0100
     1.3 @@ -249,13 +249,13 @@
     1.4      |  ((v & 0xFF000000));
     1.5  }
     1.6  
     1.7 -static void xcf_read_property (SDL_RWops * src, xcf_prop * prop) {
     1.8 +static int xcf_read_property (SDL_RWops * src, xcf_prop * prop) {
     1.9    Uint32 len;
    1.10    prop->id = SDL_ReadBE32 (src);
    1.11    prop->length = SDL_ReadBE32 (src);
    1.12  
    1.13  #if DEBUG
    1.14 -  printf ("%.8X: %s: %d\n", SDL_RWtell (src), prop->id < 25 ? prop_names [prop->id] : "unknown", prop->length);
    1.15 +  printf ("%.8X: %s(%u): %u\n", SDL_RWtell (src), prop->id < 25 ? prop_names [prop->id] : "unknown", prop->id, prop->length);
    1.16  #endif
    1.17  
    1.18    switch (prop->id) {
    1.19 @@ -286,8 +286,10 @@
    1.20      break;
    1.21    default:
    1.22      //    SDL_RWread (src, &prop->data, prop->length, 1);
    1.23 -    SDL_RWseek (src, prop->length, RW_SEEK_CUR);
    1.24 +    if (SDL_RWseek (src, prop->length, RW_SEEK_CUR) < 0)
    1.25 +      return 0;  // ERROR
    1.26    }
    1.27 +  return 1;  // OK
    1.28  }
    1.29  
    1.30  static void free_xcf_header (xcf_header * h) {
    1.31 @@ -310,6 +312,10 @@
    1.32    h->width       = SDL_ReadBE32 (src);
    1.33    h->height      = SDL_ReadBE32 (src);
    1.34    h->image_type  = SDL_ReadBE32 (src);
    1.35 +#ifdef DEBUG
    1.36 +  printf ("XCF signature : %.14s\n", h->sign);
    1.37 +  printf (" (%u,%u) type=%u\n", h->width, h->height, h->image_type);
    1.38 +#endif
    1.39  
    1.40    h->properties = NULL;
    1.41    h->layer_file_offsets = NULL;
    1.42 @@ -319,7 +325,10 @@
    1.43  
    1.44    // Just read, don't save
    1.45    do {
    1.46 -    xcf_read_property (src, &prop);
    1.47 +    if (!xcf_read_property (src, &prop)) {
    1.48 +      free_xcf_header (h);
    1.49 +      return NULL;
    1.50 +    }
    1.51      if (prop.id == PROP_COMPRESSION)
    1.52        h->compr = (xcf_compr_type)prop.data.compression;
    1.53      else if (prop.id == PROP_COLORMAP) {
    1.54 @@ -363,7 +372,10 @@
    1.55    l->name = read_string (src);
    1.56  
    1.57    do {
    1.58 -    xcf_read_property (src, &prop);
    1.59 +    if (!xcf_read_property (src, &prop)) {
    1.60 +      free_xcf_layer (l);
    1.61 +      return NULL;
    1.62 +    }
    1.63      if (prop.id == PROP_OFFSETS) {
    1.64        l->offset_x = prop.data.offset.x;
    1.65        l->offset_y = prop.data.offset.y;
    1.66 @@ -395,7 +407,10 @@
    1.67  
    1.68    l->selection = 0;
    1.69    do {
    1.70 -    xcf_read_property (src, &prop);
    1.71 +    if (!xcf_read_property (src, &prop)) {
    1.72 +      free_xcf_channel (l);
    1.73 +      return NULL;
    1.74 +    }
    1.75      switch (prop.id) {
    1.76      case PROP_OPACITY:
    1.77        l->opacity = prop.data.opacity << 24;