LCOV - code coverage report
Current view: top level - libavcodec - bmp.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 156 216 72.2 %
Date: 2017-12-17 04:34:43 Functions: 1 1 100.0 %

          Line data    Source code
       1             : /*
       2             :  * BMP image format decoder
       3             :  * Copyright (c) 2005 Mans Rullgard
       4             :  *
       5             :  * This file is part of FFmpeg.
       6             :  *
       7             :  * FFmpeg is free software; you can redistribute it and/or
       8             :  * modify it under the terms of the GNU Lesser General Public
       9             :  * License as published by the Free Software Foundation; either
      10             :  * version 2.1 of the License, or (at your option) any later version.
      11             :  *
      12             :  * FFmpeg is distributed in the hope that it will be useful,
      13             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      14             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      15             :  * Lesser General Public License for more details.
      16             :  *
      17             :  * You should have received a copy of the GNU Lesser General Public
      18             :  * License along with FFmpeg; if not, write to the Free Software
      19             :  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
      20             :  */
      21             : 
      22             : #include <inttypes.h>
      23             : 
      24             : #include "avcodec.h"
      25             : #include "bytestream.h"
      26             : #include "bmp.h"
      27             : #include "internal.h"
      28             : #include "msrledec.h"
      29             : 
      30          46 : static int bmp_decode_frame(AVCodecContext *avctx,
      31             :                             void *data, int *got_frame,
      32             :                             AVPacket *avpkt)
      33             : {
      34          46 :     const uint8_t *buf = avpkt->data;
      35          46 :     int buf_size       = avpkt->size;
      36          46 :     AVFrame *p         = data;
      37             :     unsigned int fsize, hsize;
      38             :     int width, height;
      39             :     unsigned int depth;
      40             :     BiCompression comp;
      41             :     unsigned int ihsize;
      42             :     int i, j, n, linesize, ret;
      43          46 :     uint32_t rgb[3] = {0};
      44          46 :     uint32_t alpha = 0;
      45             :     uint8_t *ptr;
      46             :     int dsize;
      47          46 :     const uint8_t *buf0 = buf;
      48             :     GetByteContext gb;
      49             : 
      50          46 :     if (buf_size < 14) {
      51           0 :         av_log(avctx, AV_LOG_ERROR, "buf size too small (%d)\n", buf_size);
      52           0 :         return AVERROR_INVALIDDATA;
      53             :     }
      54             : 
      55          92 :     if (bytestream_get_byte(&buf) != 'B' ||
      56          46 :         bytestream_get_byte(&buf) != 'M') {
      57           0 :         av_log(avctx, AV_LOG_ERROR, "bad magic number\n");
      58           0 :         return AVERROR_INVALIDDATA;
      59             :     }
      60             : 
      61          46 :     fsize = bytestream_get_le32(&buf);
      62          46 :     if (buf_size < fsize) {
      63           0 :         av_log(avctx, AV_LOG_ERROR, "not enough data (%d < %u), trying to decode anyway\n",
      64             :                buf_size, fsize);
      65           0 :         fsize = buf_size;
      66             :     }
      67             : 
      68          46 :     buf += 2; /* reserved1 */
      69          46 :     buf += 2; /* reserved2 */
      70             : 
      71          46 :     hsize  = bytestream_get_le32(&buf); /* header size */
      72          46 :     ihsize = bytestream_get_le32(&buf); /* more header size */
      73          46 :     if (ihsize + 14LL > hsize) {
      74           0 :         av_log(avctx, AV_LOG_ERROR, "invalid header size %u\n", hsize);
      75           0 :         return AVERROR_INVALIDDATA;
      76             :     }
      77             : 
      78             :     /* sometimes file size is set to some headers size, set a real size in that case */
      79          46 :     if (fsize == 14 || fsize == ihsize + 14)
      80           2 :         fsize = buf_size - 2;
      81             : 
      82          46 :     if (fsize <= hsize) {
      83           0 :         av_log(avctx, AV_LOG_ERROR,
      84             :                "Declared file size is less than header size (%u < %u)\n",
      85             :                fsize, hsize);
      86           0 :         return AVERROR_INVALIDDATA;
      87             :     }
      88             : 
      89          46 :     switch (ihsize) {
      90          44 :     case  40: // windib
      91             :     case  56: // windib v3
      92             :     case  64: // OS/2 v2
      93             :     case 108: // windib v4
      94             :     case 124: // windib v5
      95          44 :         width  = bytestream_get_le32(&buf);
      96          44 :         height = bytestream_get_le32(&buf);
      97          44 :         break;
      98           2 :     case  12: // OS/2 v1
      99           2 :         width  = bytestream_get_le16(&buf);
     100           2 :         height = bytestream_get_le16(&buf);
     101           2 :         break;
     102           0 :     default:
     103           0 :         avpriv_report_missing_feature(avctx, "Information header size %u",
     104             :                                       ihsize);
     105           0 :         return AVERROR_PATCHWELCOME;
     106             :     }
     107             : 
     108             :     /* planes */
     109          46 :     if (bytestream_get_le16(&buf) != 1) {
     110           0 :         av_log(avctx, AV_LOG_ERROR, "invalid BMP header\n");
     111           0 :         return AVERROR_INVALIDDATA;
     112             :     }
     113             : 
     114          46 :     depth = bytestream_get_le16(&buf);
     115             : 
     116          46 :     if (ihsize >= 40)
     117          44 :         comp = bytestream_get_le32(&buf);
     118             :     else
     119           2 :         comp = BMP_RGB;
     120             : 
     121          46 :     if (comp != BMP_RGB && comp != BMP_BITFIELDS && comp != BMP_RLE4 &&
     122             :         comp != BMP_RLE8) {
     123           0 :         av_log(avctx, AV_LOG_ERROR, "BMP coding %d not supported\n", comp);
     124           0 :         return AVERROR_INVALIDDATA;
     125             :     }
     126             : 
     127          46 :     if (comp == BMP_BITFIELDS) {
     128           6 :         buf += 20;
     129           6 :         rgb[0] = bytestream_get_le32(&buf);
     130           6 :         rgb[1] = bytestream_get_le32(&buf);
     131           6 :         rgb[2] = bytestream_get_le32(&buf);
     132           6 :         if (ihsize > 40)
     133           0 :         alpha = bytestream_get_le32(&buf);
     134             :     }
     135             : 
     136          46 :     ret = ff_set_dimensions(avctx, width, height > 0 ? height : -(unsigned)height);
     137          46 :     if (ret < 0) {
     138           0 :         av_log(avctx, AV_LOG_ERROR, "Failed to set dimensions %d %d\n", width, height);
     139           0 :         return AVERROR_INVALIDDATA;
     140             :     }
     141             : 
     142          46 :     avctx->pix_fmt = AV_PIX_FMT_NONE;
     143             : 
     144          46 :     switch (depth) {
     145           4 :     case 32:
     146           4 :         if (comp == BMP_BITFIELDS) {
     147           2 :             if (rgb[0] == 0xFF000000 && rgb[1] == 0x00FF0000 && rgb[2] == 0x0000FF00)
     148           0 :                 avctx->pix_fmt = alpha ? AV_PIX_FMT_ABGR : AV_PIX_FMT_0BGR;
     149           2 :             else if (rgb[0] == 0x00FF0000 && rgb[1] == 0x0000FF00 && rgb[2] == 0x000000FF)
     150           2 :                 avctx->pix_fmt = alpha ? AV_PIX_FMT_BGRA : AV_PIX_FMT_BGR0;
     151           0 :             else if (rgb[0] == 0x0000FF00 && rgb[1] == 0x00FF0000 && rgb[2] == 0xFF000000)
     152           0 :                 avctx->pix_fmt = alpha ? AV_PIX_FMT_ARGB : AV_PIX_FMT_0RGB;
     153           0 :             else if (rgb[0] == 0x000000FF && rgb[1] == 0x0000FF00 && rgb[2] == 0x00FF0000)
     154           0 :                 avctx->pix_fmt = alpha ? AV_PIX_FMT_RGBA : AV_PIX_FMT_RGB0;
     155             :             else {
     156           0 :                 av_log(avctx, AV_LOG_ERROR, "Unknown bitfields "
     157             :                        "%0"PRIX32" %0"PRIX32" %0"PRIX32"\n", rgb[0], rgb[1], rgb[2]);
     158           0 :                 return AVERROR(EINVAL);
     159             :             }
     160             :         } else {
     161           2 :             avctx->pix_fmt = AV_PIX_FMT_BGRA;
     162             :         }
     163           4 :         break;
     164          22 :     case 24:
     165          22 :         avctx->pix_fmt = AV_PIX_FMT_BGR24;
     166          22 :         break;
     167           6 :     case 16:
     168           6 :         if (comp == BMP_RGB)
     169           2 :             avctx->pix_fmt = AV_PIX_FMT_RGB555;
     170           4 :         else if (comp == BMP_BITFIELDS) {
     171           4 :             if (rgb[0] == 0xF800 && rgb[1] == 0x07E0 && rgb[2] == 0x001F)
     172           2 :                avctx->pix_fmt = AV_PIX_FMT_RGB565;
     173           2 :             else if (rgb[0] == 0x7C00 && rgb[1] == 0x03E0 && rgb[2] == 0x001F)
     174           2 :                avctx->pix_fmt = AV_PIX_FMT_RGB555;
     175           0 :             else if (rgb[0] == 0x0F00 && rgb[1] == 0x00F0 && rgb[2] == 0x000F)
     176           0 :                avctx->pix_fmt = AV_PIX_FMT_RGB444;
     177             :             else {
     178           0 :                av_log(avctx, AV_LOG_ERROR,
     179             :                       "Unknown bitfields %0"PRIX32" %0"PRIX32" %0"PRIX32"\n",
     180             :                       rgb[0], rgb[1], rgb[2]);
     181           0 :                return AVERROR(EINVAL);
     182             :             }
     183             :         }
     184           6 :         break;
     185           6 :     case 8:
     186           6 :         if (hsize - ihsize - 14 > 0)
     187           6 :             avctx->pix_fmt = AV_PIX_FMT_PAL8;
     188             :         else
     189           0 :             avctx->pix_fmt = AV_PIX_FMT_GRAY8;
     190           6 :         break;
     191           8 :     case 1:
     192             :     case 4:
     193           8 :         if (hsize - ihsize - 14 > 0) {
     194           8 :             avctx->pix_fmt = AV_PIX_FMT_PAL8;
     195             :         } else {
     196           0 :             av_log(avctx, AV_LOG_ERROR, "Unknown palette for %u-colour BMP\n",
     197             :                    1 << depth);
     198           0 :             return AVERROR_INVALIDDATA;
     199             :         }
     200           8 :         break;
     201           0 :     default:
     202           0 :         av_log(avctx, AV_LOG_ERROR, "depth %u not supported\n", depth);
     203           0 :         return AVERROR_INVALIDDATA;
     204             :     }
     205             : 
     206          46 :     if (avctx->pix_fmt == AV_PIX_FMT_NONE) {
     207           0 :         av_log(avctx, AV_LOG_ERROR, "unsupported pixel format\n");
     208           0 :         return AVERROR_INVALIDDATA;
     209             :     }
     210             : 
     211          46 :     if ((ret = ff_get_buffer(avctx, p, 0)) < 0)
     212           0 :         return ret;
     213          46 :     p->pict_type = AV_PICTURE_TYPE_I;
     214          46 :     p->key_frame = 1;
     215             : 
     216          46 :     buf   = buf0 + hsize;
     217          46 :     dsize = buf_size - hsize;
     218             : 
     219             :     /* Line size in file multiple of 4 */
     220          46 :     n = ((avctx->width * depth + 31) / 8) & ~3;
     221             : 
     222          46 :     if (n * avctx->height > dsize && comp != BMP_RLE4 && comp != BMP_RLE8) {
     223           0 :         n = (avctx->width * depth + 7) / 8;
     224           0 :         if (n * avctx->height > dsize) {
     225           0 :             av_log(avctx, AV_LOG_ERROR, "not enough data (%d < %d)\n",
     226           0 :                    dsize, n * avctx->height);
     227           0 :             return AVERROR_INVALIDDATA;
     228             :         }
     229           0 :         av_log(avctx, AV_LOG_ERROR, "data size too small, assuming missing line alignment\n");
     230             :     }
     231             : 
     232             :     // RLE may skip decoding some picture areas, so blank picture before decoding
     233          46 :     if (comp == BMP_RLE4 || comp == BMP_RLE8)
     234           4 :         memset(p->data[0], 0, avctx->height * p->linesize[0]);
     235             : 
     236          46 :     if (height > 0) {
     237          46 :         ptr      = p->data[0] + (avctx->height - 1) * p->linesize[0];
     238          46 :         linesize = -p->linesize[0];
     239             :     } else {
     240           0 :         ptr      = p->data[0];
     241           0 :         linesize = p->linesize[0];
     242             :     }
     243             : 
     244          46 :     if (avctx->pix_fmt == AV_PIX_FMT_PAL8) {
     245          14 :         int colors = 1 << depth;
     246             : 
     247          14 :         memset(p->data[1], 0, 1024);
     248             : 
     249          14 :         if (ihsize >= 36) {
     250             :             int t;
     251          12 :             buf = buf0 + 46;
     252          12 :             t   = bytestream_get_le32(&buf);
     253          12 :             if (t < 0 || t > (1 << depth)) {
     254           0 :                 av_log(avctx, AV_LOG_ERROR,
     255             :                        "Incorrect number of colors - %X for bitdepth %u\n",
     256             :                        t, depth);
     257          12 :             } else if (t) {
     258           2 :                 colors = t;
     259             :             }
     260             :         } else {
     261           2 :             colors = FFMIN(256, (hsize-ihsize-14) / 3);
     262             :         }
     263          14 :         buf = buf0 + 14 + ihsize; //palette location
     264             :         // OS/2 bitmap, 3 bytes per palette entry
     265          14 :         if ((hsize-ihsize-14) < (colors << 2)) {
     266           2 :             if ((hsize-ihsize-14) < colors * 3) {
     267           0 :                 av_log(avctx, AV_LOG_ERROR, "palette doesn't fit in packet\n");
     268           0 :                 return AVERROR_INVALIDDATA;
     269             :             }
     270         514 :             for (i = 0; i < colors; i++)
     271         512 :                 ((uint32_t*)p->data[1])[i] = (0xFFU<<24) | bytestream_get_le24(&buf);
     272             :         } else {
     273        1136 :             for (i = 0; i < colors; i++)
     274        1124 :                 ((uint32_t*)p->data[1])[i] = 0xFFU << 24 | bytestream_get_le32(&buf);
     275             :         }
     276          14 :         buf = buf0 + hsize;
     277             :     }
     278          46 :     if (comp == BMP_RLE4 || comp == BMP_RLE8) {
     279           4 :         if (comp == BMP_RLE8 && height < 0) {
     280           0 :             p->data[0]    +=  p->linesize[0] * (avctx->height - 1);
     281           0 :             p->linesize[0] = -p->linesize[0];
     282             :         }
     283           4 :         bytestream2_init(&gb, buf, dsize);
     284           4 :         ff_msrle_decode(avctx, p, depth, &gb);
     285           8 :         if (height < 0) {
     286           0 :             p->data[0]    +=  p->linesize[0] * (avctx->height - 1);
     287           0 :             p->linesize[0] = -p->linesize[0];
     288             :         }
     289             :     } else {
     290          42 :         switch (depth) {
     291           2 :         case 1:
     292         130 :             for (i = 0; i < avctx->height; i++) {
     293             :                 int j;
     294        2176 :                 for (j = 0; j < n; j++) {
     295        2048 :                     ptr[j*8+0] =  buf[j] >> 7;
     296        2048 :                     ptr[j*8+1] = (buf[j] >> 6) & 1;
     297        2048 :                     ptr[j*8+2] = (buf[j] >> 5) & 1;
     298        2048 :                     ptr[j*8+3] = (buf[j] >> 4) & 1;
     299        2048 :                     ptr[j*8+4] = (buf[j] >> 3) & 1;
     300        2048 :                     ptr[j*8+5] = (buf[j] >> 2) & 1;
     301        2048 :                     ptr[j*8+6] = (buf[j] >> 1) & 1;
     302        2048 :                     ptr[j*8+7] =  buf[j]       & 1;
     303             :                 }
     304         128 :                 buf += n;
     305         128 :                 ptr += linesize;
     306             :             }
     307           2 :             break;
     308          30 :         case 8:
     309             :         case 24:
     310             :         case 32:
     311        5140 :             for (i = 0; i < avctx->height; i++) {
     312        5110 :                 memcpy(ptr, buf, n);
     313        5110 :                 buf += n;
     314        5110 :                 ptr += linesize;
     315             :             }
     316          30 :             break;
     317           4 :         case 4:
     318         176 :             for (i = 0; i < avctx->height; i++) {
     319             :                 int j;
     320       15052 :                 for (j = 0; j < n; j++) {
     321       14880 :                     ptr[j*2+0] = (buf[j] >> 4) & 0xF;
     322       14880 :                     ptr[j*2+1] = buf[j] & 0xF;
     323             :                 }
     324         172 :                 buf += n;
     325         172 :                 ptr += linesize;
     326             :             }
     327           4 :             break;
     328           6 :         case 16:
     329         390 :             for (i = 0; i < avctx->height; i++) {
     330         384 :                 const uint16_t *src = (const uint16_t *) buf;
     331         384 :                 uint16_t *dst       = (uint16_t *) ptr;
     332             : 
     333       49152 :                 for (j = 0; j < avctx->width; j++)
     334       48768 :                     *dst++ = av_le2ne16(*src++);
     335             : 
     336         384 :                 buf += n;
     337         384 :                 ptr += linesize;
     338             :             }
     339           6 :             break;
     340           0 :         default:
     341           0 :             av_log(avctx, AV_LOG_ERROR, "BMP decoder is broken\n");
     342           0 :             return AVERROR_INVALIDDATA;
     343             :         }
     344             :     }
     345          46 :     if (avctx->pix_fmt == AV_PIX_FMT_BGRA) {
     346         130 :         for (i = 0; i < avctx->height; i++) {
     347             :             int j;
     348         128 :             uint8_t *ptr = p->data[0] + p->linesize[0]*i + 3;
     349       16384 :             for (j = 0; j < avctx->width; j++) {
     350       16256 :                 if (ptr[4*j])
     351           0 :                     break;
     352             :             }
     353         128 :             if (j < avctx->width)
     354           0 :                 break;
     355             :         }
     356           2 :         if (i == avctx->height)
     357           2 :             avctx->pix_fmt = p->format = AV_PIX_FMT_BGR0;
     358             :     }
     359             : 
     360          46 :     *got_frame = 1;
     361             : 
     362          46 :     return buf_size;
     363             : }
     364             : 
     365             : AVCodec ff_bmp_decoder = {
     366             :     .name           = "bmp",
     367             :     .long_name      = NULL_IF_CONFIG_SMALL("BMP (Windows and OS/2 bitmap)"),
     368             :     .type           = AVMEDIA_TYPE_VIDEO,
     369             :     .id             = AV_CODEC_ID_BMP,
     370             :     .decode         = bmp_decode_frame,
     371             :     .capabilities   = AV_CODEC_CAP_DR1,
     372             : };

Generated by: LCOV version 1.13