image/codecs/bmp/
decoder.rs

1use std::cmp::{self, Ordering};
2use std::io::{self, Cursor, Read, Seek, SeekFrom};
3use std::iter::{repeat, Rev};
4use std::marker::PhantomData;
5use std::slice::ChunksMut;
6use std::{error, fmt, mem};
7
8use byteorder::{LittleEndian, ReadBytesExt};
9
10use crate::color::ColorType;
11use crate::error::{
12    DecodingError, ImageError, ImageResult, UnsupportedError, UnsupportedErrorKind,
13};
14use crate::image::{self, ImageDecoder, ImageDecoderRect, ImageFormat, Progress};
15
16const BITMAPCOREHEADER_SIZE: u32 = 12;
17const BITMAPINFOHEADER_SIZE: u32 = 40;
18const BITMAPV2HEADER_SIZE: u32 = 52;
19const BITMAPV3HEADER_SIZE: u32 = 56;
20const BITMAPV4HEADER_SIZE: u32 = 108;
21const BITMAPV5HEADER_SIZE: u32 = 124;
22
23static LOOKUP_TABLE_3_BIT_TO_8_BIT: [u8; 8] = [0, 36, 73, 109, 146, 182, 219, 255];
24static LOOKUP_TABLE_4_BIT_TO_8_BIT: [u8; 16] = [
25    0, 17, 34, 51, 68, 85, 102, 119, 136, 153, 170, 187, 204, 221, 238, 255,
26];
27static LOOKUP_TABLE_5_BIT_TO_8_BIT: [u8; 32] = [
28    0, 8, 16, 25, 33, 41, 49, 58, 66, 74, 82, 90, 99, 107, 115, 123, 132, 140, 148, 156, 165, 173,
29    181, 189, 197, 206, 214, 222, 230, 239, 247, 255,
30];
31static LOOKUP_TABLE_6_BIT_TO_8_BIT: [u8; 64] = [
32    0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 45, 49, 53, 57, 61, 65, 69, 73, 77, 81, 85, 89, 93,
33    97, 101, 105, 109, 113, 117, 121, 125, 130, 134, 138, 142, 146, 150, 154, 158, 162, 166, 170,
34    174, 178, 182, 186, 190, 194, 198, 202, 206, 210, 215, 219, 223, 227, 231, 235, 239, 243, 247,
35    251, 255,
36];
37
38static R5_G5_B5_COLOR_MASK: Bitfields = Bitfields {
39    r: Bitfield { len: 5, shift: 10 },
40    g: Bitfield { len: 5, shift: 5 },
41    b: Bitfield { len: 5, shift: 0 },
42    a: Bitfield { len: 0, shift: 0 },
43};
44const R8_G8_B8_COLOR_MASK: Bitfields = Bitfields {
45    r: Bitfield { len: 8, shift: 24 },
46    g: Bitfield { len: 8, shift: 16 },
47    b: Bitfield { len: 8, shift: 8 },
48    a: Bitfield { len: 0, shift: 0 },
49};
50const R8_G8_B8_A8_COLOR_MASK: Bitfields = Bitfields {
51    r: Bitfield { len: 8, shift: 16 },
52    g: Bitfield { len: 8, shift: 8 },
53    b: Bitfield { len: 8, shift: 0 },
54    a: Bitfield { len: 8, shift: 24 },
55};
56
57const RLE_ESCAPE: u8 = 0;
58const RLE_ESCAPE_EOL: u8 = 0;
59const RLE_ESCAPE_EOF: u8 = 1;
60const RLE_ESCAPE_DELTA: u8 = 2;
61
62/// The maximum width/height the decoder will process.
63const MAX_WIDTH_HEIGHT: i32 = 0xFFFF;
64
65#[derive(PartialEq, Copy, Clone)]
66enum ImageType {
67    Palette,
68    RGB16,
69    RGB24,
70    RGB32,
71    RGBA32,
72    RLE8,
73    RLE4,
74    Bitfields16,
75    Bitfields32,
76}
77
78#[derive(PartialEq)]
79enum BMPHeaderType {
80    Core,
81    Info,
82    V2,
83    V3,
84    V4,
85    V5,
86}
87
88#[derive(PartialEq)]
89enum FormatFullBytes {
90    RGB24,
91    RGB32,
92    RGBA32,
93    Format888,
94}
95
96enum Chunker<'a> {
97    FromTop(ChunksMut<'a, u8>),
98    FromBottom(Rev<ChunksMut<'a, u8>>),
99}
100
101pub(crate) struct RowIterator<'a> {
102    chunks: Chunker<'a>,
103}
104
105impl<'a> Iterator for RowIterator<'a> {
106    type Item = &'a mut [u8];
107
108    #[inline(always)]
109    fn next(&mut self) -> Option<&'a mut [u8]> {
110        match self.chunks {
111            Chunker::FromTop(ref mut chunks) => chunks.next(),
112            Chunker::FromBottom(ref mut chunks) => chunks.next(),
113        }
114    }
115}
116
117/// All errors that can occur when attempting to parse a BMP
118#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq, PartialOrd, Ord)]
119enum DecoderError {
120    // Failed to decompress RLE data.
121    CorruptRleData,
122
123    /// The bitfield mask interleaves set and unset bits
124    BitfieldMaskNonContiguous,
125    /// Bitfield mask invalid (e.g. too long for specified type)
126    BitfieldMaskInvalid,
127    /// Bitfield (of the specified width – 16- or 32-bit) mask not present
128    BitfieldMaskMissing(u32),
129    /// Bitfield (of the specified width – 16- or 32-bit) masks not present
130    BitfieldMasksMissing(u32),
131
132    /// BMP's "BM" signature wrong or missing
133    BmpSignatureInvalid,
134    /// More than the exactly one allowed plane specified by the format
135    MoreThanOnePlane,
136    /// Invalid amount of bits per channel for the specified image type
137    InvalidChannelWidth(ChannelWidthError, u16),
138
139    /// The width is negative
140    NegativeWidth(i32),
141    /// One of the dimensions is larger than a soft limit
142    ImageTooLarge(i32, i32),
143    /// The height is `i32::min_value()`
144    ///
145    /// General negative heights specify top-down DIBs
146    InvalidHeight,
147
148    /// Specified image type is invalid for top-down BMPs (i.e. is compressed)
149    ImageTypeInvalidForTopDown(u32),
150    /// Image type not currently recognized by the decoder
151    ImageTypeUnknown(u32),
152
153    /// Bitmap header smaller than the core header
154    HeaderTooSmall(u32),
155
156    /// The palette is bigger than allowed by the bit count of the BMP
157    PaletteSizeExceeded {
158        colors_used: u32,
159        bit_count: u16,
160    },
161}
162
163impl fmt::Display for DecoderError {
164    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
165        match self {
166            DecoderError::CorruptRleData => f.write_str("Corrupt RLE data"),
167            DecoderError::BitfieldMaskNonContiguous => f.write_str("Non-contiguous bitfield mask"),
168            DecoderError::BitfieldMaskInvalid => f.write_str("Invalid bitfield mask"),
169            DecoderError::BitfieldMaskMissing(bb) => {
170                f.write_fmt(format_args!("Missing {}-bit bitfield mask", bb))
171            }
172            DecoderError::BitfieldMasksMissing(bb) => {
173                f.write_fmt(format_args!("Missing {}-bit bitfield masks", bb))
174            }
175            DecoderError::BmpSignatureInvalid => f.write_str("BMP signature not found"),
176            DecoderError::MoreThanOnePlane => f.write_str("More than one plane"),
177            DecoderError::InvalidChannelWidth(tp, n) => {
178                f.write_fmt(format_args!("Invalid channel bit count for {}: {}", tp, n))
179            }
180            DecoderError::NegativeWidth(w) => f.write_fmt(format_args!("Negative width ({})", w)),
181            DecoderError::ImageTooLarge(w, h) => f.write_fmt(format_args!(
182                "Image too large (one of ({}, {}) > soft limit of {})",
183                w, h, MAX_WIDTH_HEIGHT
184            )),
185            DecoderError::InvalidHeight => f.write_str("Invalid height"),
186            DecoderError::ImageTypeInvalidForTopDown(tp) => f.write_fmt(format_args!(
187                "Invalid image type {} for top-down image.",
188                tp
189            )),
190            DecoderError::ImageTypeUnknown(tp) => {
191                f.write_fmt(format_args!("Unknown image compression type {}", tp))
192            }
193            DecoderError::HeaderTooSmall(s) => {
194                f.write_fmt(format_args!("Bitmap header too small ({} bytes)", s))
195            }
196            DecoderError::PaletteSizeExceeded {
197                colors_used,
198                bit_count,
199            } => f.write_fmt(format_args!(
200                "Palette size {} exceeds maximum size for BMP with bit count of {}",
201                colors_used, bit_count
202            )),
203        }
204    }
205}
206
207impl From<DecoderError> for ImageError {
208    fn from(e: DecoderError) -> ImageError {
209        ImageError::Decoding(DecodingError::new(ImageFormat::Bmp.into(), e))
210    }
211}
212
213impl error::Error for DecoderError {}
214
215/// Distinct image types whose saved channel width can be invalid
216#[derive(Debug, Copy, Clone, Hash, PartialEq, Eq, PartialOrd, Ord)]
217enum ChannelWidthError {
218    /// RGB
219    Rgb,
220    /// 8-bit run length encoding
221    Rle8,
222    /// 4-bit run length encoding
223    Rle4,
224    /// Bitfields (16- or 32-bit)
225    Bitfields,
226}
227
228impl fmt::Display for ChannelWidthError {
229    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
230        f.write_str(match self {
231            ChannelWidthError::Rgb => "RGB",
232            ChannelWidthError::Rle8 => "RLE8",
233            ChannelWidthError::Rle4 => "RLE4",
234            ChannelWidthError::Bitfields => "bitfields",
235        })
236    }
237}
238
239/// Convenience function to check if the combination of width, length and number of
240/// channels would result in a buffer that would overflow.
241fn check_for_overflow(width: i32, length: i32, channels: usize) -> ImageResult<()> {
242    num_bytes(width, length, channels)
243        .map(|_| ())
244        .ok_or_else(|| {
245            ImageError::Unsupported(UnsupportedError::from_format_and_kind(
246                ImageFormat::Bmp.into(),
247                UnsupportedErrorKind::GenericFeature(format!(
248                    "Image dimensions ({}x{} w/{} channels) are too large",
249                    width, length, channels
250                )),
251            ))
252        })
253}
254
255/// Calculate how many many bytes a buffer holding a decoded image with these properties would
256/// require. Returns `None` if the buffer size would overflow or if one of the sizes are negative.
257fn num_bytes(width: i32, length: i32, channels: usize) -> Option<usize> {
258    if width <= 0 || length <= 0 {
259        None
260    } else {
261        match channels.checked_mul(width as usize) {
262            Some(n) => n.checked_mul(length as usize),
263            None => None,
264        }
265    }
266}
267
268/// Call the provided function on each row of the provided buffer, returning Err if the provided
269/// function returns an error, extends the buffer if it's not large enough.
270fn with_rows<F>(
271    buffer: &mut [u8],
272    width: i32,
273    height: i32,
274    channels: usize,
275    top_down: bool,
276    mut func: F,
277) -> io::Result<()>
278where
279    F: FnMut(&mut [u8]) -> io::Result<()>,
280{
281    // An overflow should already have been checked for when this is called,
282    // though we check anyhow, as it somehow seems to increase performance slightly.
283    let row_width = channels.checked_mul(width as usize).unwrap();
284    let full_image_size = row_width.checked_mul(height as usize).unwrap();
285    assert_eq!(buffer.len(), full_image_size);
286
287    if !top_down {
288        for row in buffer.chunks_mut(row_width).rev() {
289            func(row)?;
290        }
291    } else {
292        for row in buffer.chunks_mut(row_width) {
293            func(row)?;
294        }
295    }
296    Ok(())
297}
298
299fn set_8bit_pixel_run<'a, T: Iterator<Item = &'a u8>>(
300    pixel_iter: &mut ChunksMut<u8>,
301    palette: &[[u8; 3]],
302    indices: T,
303    n_pixels: usize,
304) -> bool {
305    for idx in indices.take(n_pixels) {
306        if let Some(pixel) = pixel_iter.next() {
307            let rgb = palette[*idx as usize];
308            pixel[0] = rgb[0];
309            pixel[1] = rgb[1];
310            pixel[2] = rgb[2];
311        } else {
312            return false;
313        }
314    }
315    true
316}
317
318fn set_4bit_pixel_run<'a, T: Iterator<Item = &'a u8>>(
319    pixel_iter: &mut ChunksMut<u8>,
320    palette: &[[u8; 3]],
321    indices: T,
322    mut n_pixels: usize,
323) -> bool {
324    for idx in indices {
325        macro_rules! set_pixel {
326            ($i:expr) => {
327                if n_pixels == 0 {
328                    break;
329                }
330                if let Some(pixel) = pixel_iter.next() {
331                    let rgb = palette[$i as usize];
332                    pixel[0] = rgb[0];
333                    pixel[1] = rgb[1];
334                    pixel[2] = rgb[2];
335                } else {
336                    return false;
337                }
338                n_pixels -= 1;
339            };
340        }
341        set_pixel!(idx >> 4);
342        set_pixel!(idx & 0xf);
343    }
344    true
345}
346
347#[rustfmt::skip]
348fn set_2bit_pixel_run<'a, T: Iterator<Item = &'a u8>>(
349    pixel_iter: &mut ChunksMut<u8>,
350    palette: &[[u8; 3]],
351    indices: T,
352    mut n_pixels: usize,
353) -> bool {
354    for idx in indices {
355        macro_rules! set_pixel {
356            ($i:expr) => {
357                if n_pixels == 0 {
358                    break;
359                }
360                if let Some(pixel) = pixel_iter.next() {
361                    let rgb = palette[$i as usize];
362                    pixel[0] = rgb[0];
363                    pixel[1] = rgb[1];
364                    pixel[2] = rgb[2];
365                } else {
366                    return false;
367                }
368                n_pixels -= 1;
369            };
370        }
371        set_pixel!((idx >> 6) & 0x3u8);
372        set_pixel!((idx >> 4) & 0x3u8);
373        set_pixel!((idx >> 2) & 0x3u8);
374        set_pixel!( idx       & 0x3u8);
375    }
376    true
377}
378
379fn set_1bit_pixel_run<'a, T: Iterator<Item = &'a u8>>(
380    pixel_iter: &mut ChunksMut<u8>,
381    palette: &[[u8; 3]],
382    indices: T,
383) {
384    for idx in indices {
385        let mut bit = 0x80;
386        loop {
387            if let Some(pixel) = pixel_iter.next() {
388                let rgb = palette[((idx & bit) != 0) as usize];
389                pixel[0] = rgb[0];
390                pixel[1] = rgb[1];
391                pixel[2] = rgb[2];
392            } else {
393                return;
394            }
395
396            bit >>= 1;
397            if bit == 0 {
398                break;
399            }
400        }
401    }
402}
403
404#[derive(PartialEq, Eq)]
405struct Bitfield {
406    shift: u32,
407    len: u32,
408}
409
410impl Bitfield {
411    fn from_mask(mask: u32, max_len: u32) -> ImageResult<Bitfield> {
412        if mask == 0 {
413            return Ok(Bitfield { shift: 0, len: 0 });
414        }
415        let mut shift = mask.trailing_zeros();
416        let mut len = (!(mask >> shift)).trailing_zeros();
417        if len != mask.count_ones() {
418            return Err(DecoderError::BitfieldMaskNonContiguous.into());
419        }
420        if len + shift > max_len {
421            return Err(DecoderError::BitfieldMaskInvalid.into());
422        }
423        if len > 8 {
424            shift += len - 8;
425            len = 8;
426        }
427        Ok(Bitfield { shift, len })
428    }
429
430    fn read(&self, data: u32) -> u8 {
431        let data = data >> self.shift;
432        match self.len {
433            1 => ((data & 0b1) * 0xff) as u8,
434            2 => ((data & 0b11) * 0x55) as u8,
435            3 => LOOKUP_TABLE_3_BIT_TO_8_BIT[(data & 0b00_0111) as usize],
436            4 => LOOKUP_TABLE_4_BIT_TO_8_BIT[(data & 0b00_1111) as usize],
437            5 => LOOKUP_TABLE_5_BIT_TO_8_BIT[(data & 0b01_1111) as usize],
438            6 => LOOKUP_TABLE_6_BIT_TO_8_BIT[(data & 0b11_1111) as usize],
439            7 => ((data & 0x7f) << 1 | (data & 0x7f) >> 6) as u8,
440            8 => (data & 0xff) as u8,
441            _ => panic!(),
442        }
443    }
444}
445
446#[derive(PartialEq, Eq)]
447struct Bitfields {
448    r: Bitfield,
449    g: Bitfield,
450    b: Bitfield,
451    a: Bitfield,
452}
453
454impl Bitfields {
455    fn from_mask(
456        r_mask: u32,
457        g_mask: u32,
458        b_mask: u32,
459        a_mask: u32,
460        max_len: u32,
461    ) -> ImageResult<Bitfields> {
462        let bitfields = Bitfields {
463            r: Bitfield::from_mask(r_mask, max_len)?,
464            g: Bitfield::from_mask(g_mask, max_len)?,
465            b: Bitfield::from_mask(b_mask, max_len)?,
466            a: Bitfield::from_mask(a_mask, max_len)?,
467        };
468        if bitfields.r.len == 0 || bitfields.g.len == 0 || bitfields.b.len == 0 {
469            return Err(DecoderError::BitfieldMaskMissing(max_len).into());
470        }
471        Ok(bitfields)
472    }
473}
474
475/// A bmp decoder
476pub struct BmpDecoder<R> {
477    reader: R,
478
479    bmp_header_type: BMPHeaderType,
480    indexed_color: bool,
481
482    width: i32,
483    height: i32,
484    data_offset: u64,
485    top_down: bool,
486    no_file_header: bool,
487    add_alpha_channel: bool,
488    has_loaded_metadata: bool,
489    image_type: ImageType,
490
491    bit_count: u16,
492    colors_used: u32,
493    palette: Option<Vec<[u8; 3]>>,
494    bitfields: Option<Bitfields>,
495}
496
497enum RLEInsn {
498    EndOfFile,
499    EndOfRow,
500    Delta(u8, u8),
501    Absolute(u8, Vec<u8>),
502    PixelRun(u8, u8),
503}
504
505impl<R: Read + Seek> BmpDecoder<R> {
506    fn new_decoder(reader: R) -> BmpDecoder<R> {
507        BmpDecoder {
508            reader,
509
510            bmp_header_type: BMPHeaderType::Info,
511            indexed_color: false,
512
513            width: 0,
514            height: 0,
515            data_offset: 0,
516            top_down: false,
517            no_file_header: false,
518            add_alpha_channel: false,
519            has_loaded_metadata: false,
520            image_type: ImageType::Palette,
521
522            bit_count: 0,
523            colors_used: 0,
524            palette: None,
525            bitfields: None,
526        }
527    }
528
529    /// Create a new decoder that decodes from the stream ```r```
530    pub fn new(reader: R) -> ImageResult<BmpDecoder<R>> {
531        let mut decoder = Self::new_decoder(reader);
532        decoder.read_metadata()?;
533        Ok(decoder)
534    }
535
536    /// Create a new decoder that decodes from the stream ```r``` without first
537    /// reading a BITMAPFILEHEADER. This is useful for decoding the CF_DIB format
538    /// directly from the Windows clipboard.
539    pub fn new_without_file_header(reader: R) -> ImageResult<BmpDecoder<R>> {
540        let mut decoder = Self::new_decoder(reader);
541        decoder.no_file_header = true;
542        decoder.read_metadata()?;
543        Ok(decoder)
544    }
545
546    #[cfg(feature = "ico")]
547    pub(crate) fn new_with_ico_format(reader: R) -> ImageResult<BmpDecoder<R>> {
548        let mut decoder = Self::new_decoder(reader);
549        decoder.read_metadata_in_ico_format()?;
550        Ok(decoder)
551    }
552
553    /// If true, the palette in BMP does not apply to the image even if it is found.
554    /// In other words, the output image is the indexed color.
555    pub fn set_indexed_color(&mut self, indexed_color: bool) {
556        self.indexed_color = indexed_color;
557    }
558
559    #[cfg(feature = "ico")]
560    pub(crate) fn reader(&mut self) -> &mut R {
561        &mut self.reader
562    }
563
564    fn read_file_header(&mut self) -> ImageResult<()> {
565        if self.no_file_header {
566            return Ok(());
567        }
568        let mut signature = [0; 2];
569        self.reader.read_exact(&mut signature)?;
570
571        if signature != b"BM"[..] {
572            return Err(DecoderError::BmpSignatureInvalid.into());
573        }
574
575        // The next 8 bytes represent file size, followed the 4 reserved bytes
576        // We're not interesting these values
577        self.reader.read_u32::<LittleEndian>()?;
578        self.reader.read_u32::<LittleEndian>()?;
579
580        self.data_offset = u64::from(self.reader.read_u32::<LittleEndian>()?);
581
582        Ok(())
583    }
584
585    /// Read BITMAPCOREHEADER https://msdn.microsoft.com/en-us/library/vs/alm/dd183372(v=vs.85).aspx
586    ///
587    /// returns Err if any of the values are invalid.
588    fn read_bitmap_core_header(&mut self) -> ImageResult<()> {
589        // As height/width values in BMP files with core headers are only 16 bits long,
590        // they won't be larger than `MAX_WIDTH_HEIGHT`.
591        self.width = i32::from(self.reader.read_u16::<LittleEndian>()?);
592        self.height = i32::from(self.reader.read_u16::<LittleEndian>()?);
593
594        check_for_overflow(self.width, self.height, self.num_channels())?;
595
596        // Number of planes (format specifies that this should be 1).
597        if self.reader.read_u16::<LittleEndian>()? != 1 {
598            return Err(DecoderError::MoreThanOnePlane.into());
599        }
600
601        self.bit_count = self.reader.read_u16::<LittleEndian>()?;
602        self.image_type = match self.bit_count {
603            1 | 4 | 8 => ImageType::Palette,
604            24 => ImageType::RGB24,
605            _ => {
606                return Err(DecoderError::InvalidChannelWidth(
607                    ChannelWidthError::Rgb,
608                    self.bit_count,
609                )
610                .into())
611            }
612        };
613
614        Ok(())
615    }
616
617    /// Read BITMAPINFOHEADER https://msdn.microsoft.com/en-us/library/vs/alm/dd183376(v=vs.85).aspx
618    /// or BITMAPV{2|3|4|5}HEADER.
619    ///
620    /// returns Err if any of the values are invalid.
621    fn read_bitmap_info_header(&mut self) -> ImageResult<()> {
622        self.width = self.reader.read_i32::<LittleEndian>()?;
623        self.height = self.reader.read_i32::<LittleEndian>()?;
624
625        // Width can not be negative
626        if self.width < 0 {
627            return Err(DecoderError::NegativeWidth(self.width).into());
628        } else if self.width > MAX_WIDTH_HEIGHT || self.height > MAX_WIDTH_HEIGHT {
629            // Limit very large image sizes to avoid OOM issues. Images with these sizes are
630            // unlikely to be valid anyhow.
631            return Err(DecoderError::ImageTooLarge(self.width, self.height).into());
632        }
633
634        if self.height == i32::min_value() {
635            return Err(DecoderError::InvalidHeight.into());
636        }
637
638        // A negative height indicates a top-down DIB.
639        if self.height < 0 {
640            self.height *= -1;
641            self.top_down = true;
642        }
643
644        check_for_overflow(self.width, self.height, self.num_channels())?;
645
646        // Number of planes (format specifies that this should be 1).
647        if self.reader.read_u16::<LittleEndian>()? != 1 {
648            return Err(DecoderError::MoreThanOnePlane.into());
649        }
650
651        self.bit_count = self.reader.read_u16::<LittleEndian>()?;
652        let image_type_u32 = self.reader.read_u32::<LittleEndian>()?;
653
654        // Top-down dibs can not be compressed.
655        if self.top_down && image_type_u32 != 0 && image_type_u32 != 3 {
656            return Err(DecoderError::ImageTypeInvalidForTopDown(image_type_u32).into());
657        }
658        self.image_type = match image_type_u32 {
659            0 => match self.bit_count {
660                1 | 2 | 4 | 8 => ImageType::Palette,
661                16 => ImageType::RGB16,
662                24 => ImageType::RGB24,
663                32 if self.add_alpha_channel => ImageType::RGBA32,
664                32 => ImageType::RGB32,
665                _ => {
666                    return Err(DecoderError::InvalidChannelWidth(
667                        ChannelWidthError::Rgb,
668                        self.bit_count,
669                    )
670                    .into())
671                }
672            },
673            1 => match self.bit_count {
674                8 => ImageType::RLE8,
675                _ => {
676                    return Err(DecoderError::InvalidChannelWidth(
677                        ChannelWidthError::Rle8,
678                        self.bit_count,
679                    )
680                    .into())
681                }
682            },
683            2 => match self.bit_count {
684                4 => ImageType::RLE4,
685                _ => {
686                    return Err(DecoderError::InvalidChannelWidth(
687                        ChannelWidthError::Rle4,
688                        self.bit_count,
689                    )
690                    .into())
691                }
692            },
693            3 => match self.bit_count {
694                16 => ImageType::Bitfields16,
695                32 => ImageType::Bitfields32,
696                _ => {
697                    return Err(DecoderError::InvalidChannelWidth(
698                        ChannelWidthError::Bitfields,
699                        self.bit_count,
700                    )
701                    .into())
702                }
703            },
704            4 => {
705                // JPEG compression is not implemented yet.
706                return Err(ImageError::Unsupported(
707                    UnsupportedError::from_format_and_kind(
708                        ImageFormat::Bmp.into(),
709                        UnsupportedErrorKind::GenericFeature("JPEG compression".to_owned()),
710                    ),
711                ));
712            }
713            5 => {
714                // PNG compression is not implemented yet.
715                return Err(ImageError::Unsupported(
716                    UnsupportedError::from_format_and_kind(
717                        ImageFormat::Bmp.into(),
718                        UnsupportedErrorKind::GenericFeature("PNG compression".to_owned()),
719                    ),
720                ));
721            }
722            11..=13 => {
723                // CMYK types are not implemented yet.
724                return Err(ImageError::Unsupported(
725                    UnsupportedError::from_format_and_kind(
726                        ImageFormat::Bmp.into(),
727                        UnsupportedErrorKind::GenericFeature("CMYK format".to_owned()),
728                    ),
729                ));
730            }
731            _ => {
732                // Unknown compression type.
733                return Err(DecoderError::ImageTypeUnknown(image_type_u32).into());
734            }
735        };
736
737        // The next 12 bytes represent data array size in bytes,
738        // followed the horizontal and vertical printing resolutions
739        // We will calculate the pixel array size using width & height of image
740        // We're not interesting the horz or vert printing resolutions
741        self.reader.read_u32::<LittleEndian>()?;
742        self.reader.read_u32::<LittleEndian>()?;
743        self.reader.read_u32::<LittleEndian>()?;
744
745        self.colors_used = self.reader.read_u32::<LittleEndian>()?;
746
747        // The next 4 bytes represent number of "important" colors
748        // We're not interested in this value, so we'll skip it
749        self.reader.read_u32::<LittleEndian>()?;
750
751        Ok(())
752    }
753
754    fn read_bitmasks(&mut self) -> ImageResult<()> {
755        let r_mask = self.reader.read_u32::<LittleEndian>()?;
756        let g_mask = self.reader.read_u32::<LittleEndian>()?;
757        let b_mask = self.reader.read_u32::<LittleEndian>()?;
758
759        let a_mask = match self.bmp_header_type {
760            BMPHeaderType::V3 | BMPHeaderType::V4 | BMPHeaderType::V5 => {
761                self.reader.read_u32::<LittleEndian>()?
762            }
763            _ => 0,
764        };
765
766        self.bitfields = match self.image_type {
767            ImageType::Bitfields16 => {
768                Some(Bitfields::from_mask(r_mask, g_mask, b_mask, a_mask, 16)?)
769            }
770            ImageType::Bitfields32 => {
771                Some(Bitfields::from_mask(r_mask, g_mask, b_mask, a_mask, 32)?)
772            }
773            _ => None,
774        };
775
776        if self.bitfields.is_some() && a_mask != 0 {
777            self.add_alpha_channel = true;
778        }
779
780        Ok(())
781    }
782
783    fn read_metadata(&mut self) -> ImageResult<()> {
784        if !self.has_loaded_metadata {
785            self.read_file_header()?;
786            let bmp_header_offset = self.reader.stream_position()?;
787            let bmp_header_size = self.reader.read_u32::<LittleEndian>()?;
788            let bmp_header_end = bmp_header_offset + u64::from(bmp_header_size);
789
790            self.bmp_header_type = match bmp_header_size {
791                BITMAPCOREHEADER_SIZE => BMPHeaderType::Core,
792                BITMAPINFOHEADER_SIZE => BMPHeaderType::Info,
793                BITMAPV2HEADER_SIZE => BMPHeaderType::V2,
794                BITMAPV3HEADER_SIZE => BMPHeaderType::V3,
795                BITMAPV4HEADER_SIZE => BMPHeaderType::V4,
796                BITMAPV5HEADER_SIZE => BMPHeaderType::V5,
797                _ if bmp_header_size < BITMAPCOREHEADER_SIZE => {
798                    // Size of any valid header types won't be smaller than core header type.
799                    return Err(DecoderError::HeaderTooSmall(bmp_header_size).into());
800                }
801                _ => {
802                    return Err(ImageError::Unsupported(
803                        UnsupportedError::from_format_and_kind(
804                            ImageFormat::Bmp.into(),
805                            UnsupportedErrorKind::GenericFeature(format!(
806                                "Unknown bitmap header type (size={})",
807                                bmp_header_size
808                            )),
809                        ),
810                    ))
811                }
812            };
813
814            match self.bmp_header_type {
815                BMPHeaderType::Core => {
816                    self.read_bitmap_core_header()?;
817                }
818                BMPHeaderType::Info
819                | BMPHeaderType::V2
820                | BMPHeaderType::V3
821                | BMPHeaderType::V4
822                | BMPHeaderType::V5 => {
823                    self.read_bitmap_info_header()?;
824                }
825            };
826
827            match self.image_type {
828                ImageType::Bitfields16 | ImageType::Bitfields32 => self.read_bitmasks()?,
829                _ => {}
830            };
831
832            self.reader.seek(SeekFrom::Start(bmp_header_end))?;
833
834            match self.image_type {
835                ImageType::Palette | ImageType::RLE4 | ImageType::RLE8 => self.read_palette()?,
836                _ => {}
837            };
838
839            if self.no_file_header {
840                // Use the offset of the end of metadata instead of reading a BMP file header.
841                self.data_offset = self.reader.stream_position()?;
842            }
843
844            self.has_loaded_metadata = true;
845        }
846        Ok(())
847    }
848
849    #[cfg(feature = "ico")]
850    #[doc(hidden)]
851    pub fn read_metadata_in_ico_format(&mut self) -> ImageResult<()> {
852        self.no_file_header = true;
853        self.add_alpha_channel = true;
854        self.read_metadata()?;
855
856        // The height field in an ICO file is doubled to account for the AND mask
857        // (whether or not an AND mask is actually present).
858        self.height /= 2;
859        Ok(())
860    }
861
862    fn get_palette_size(&mut self) -> ImageResult<usize> {
863        match self.colors_used {
864            0 => Ok(1 << self.bit_count),
865            _ => {
866                if self.colors_used > 1 << self.bit_count {
867                    return Err(DecoderError::PaletteSizeExceeded {
868                        colors_used: self.colors_used,
869                        bit_count: self.bit_count,
870                    }
871                    .into());
872                }
873                Ok(self.colors_used as usize)
874            }
875        }
876    }
877
878    fn bytes_per_color(&self) -> usize {
879        match self.bmp_header_type {
880            BMPHeaderType::Core => 3,
881            _ => 4,
882        }
883    }
884
885    fn read_palette(&mut self) -> ImageResult<()> {
886        const MAX_PALETTE_SIZE: usize = 256; // Palette indices are u8.
887
888        let bytes_per_color = self.bytes_per_color();
889        let palette_size = self.get_palette_size()?;
890        let max_length = MAX_PALETTE_SIZE * bytes_per_color;
891
892        let length = palette_size * bytes_per_color;
893        let mut buf = Vec::with_capacity(max_length);
894
895        // Resize and read the palette entries to the buffer.
896        // We limit the buffer to at most 256 colours to avoid any oom issues as
897        // 8-bit images can't reference more than 256 indexes anyhow.
898        buf.resize(cmp::min(length, max_length), 0);
899        self.reader.by_ref().read_exact(&mut buf)?;
900
901        // Allocate 256 entries even if palette_size is smaller, to prevent corrupt files from
902        // causing an out-of-bounds array access.
903        match length.cmp(&max_length) {
904            Ordering::Greater => {
905                self.reader
906                    .seek(SeekFrom::Current((length - max_length) as i64))?;
907            }
908            Ordering::Less => buf.resize(max_length, 0),
909            Ordering::Equal => (),
910        }
911
912        let p: Vec<[u8; 3]> = (0..MAX_PALETTE_SIZE)
913            .map(|i| {
914                let b = buf[bytes_per_color * i];
915                let g = buf[bytes_per_color * i + 1];
916                let r = buf[bytes_per_color * i + 2];
917                [r, g, b]
918            })
919            .collect();
920
921        self.palette = Some(p);
922
923        Ok(())
924    }
925
926    /// Get the palette that is embedded in the BMP image, if any.
927    pub fn get_palette(&self) -> Option<&[[u8; 3]]> {
928        self.palette.as_ref().map(|vec| &vec[..])
929    }
930
931    fn num_channels(&self) -> usize {
932        if self.indexed_color {
933            1
934        } else if self.add_alpha_channel {
935            4
936        } else {
937            3
938        }
939    }
940
941    fn rows<'a>(&self, pixel_data: &'a mut [u8]) -> RowIterator<'a> {
942        let stride = self.width as usize * self.num_channels();
943        if self.top_down {
944            RowIterator {
945                chunks: Chunker::FromTop(pixel_data.chunks_mut(stride)),
946            }
947        } else {
948            RowIterator {
949                chunks: Chunker::FromBottom(pixel_data.chunks_mut(stride).rev()),
950            }
951        }
952    }
953
954    fn read_palettized_pixel_data(&mut self, buf: &mut [u8]) -> ImageResult<()> {
955        let num_channels = self.num_channels();
956        let row_byte_length = ((i32::from(self.bit_count) * self.width + 31) / 32 * 4) as usize;
957        let mut indices = vec![0; row_byte_length];
958        let palette = self.palette.as_ref().unwrap();
959        let bit_count = self.bit_count;
960        let reader = &mut self.reader;
961        let width = self.width as usize;
962        let skip_palette = self.indexed_color;
963
964        reader.seek(SeekFrom::Start(self.data_offset))?;
965
966        if num_channels == 4 {
967            buf.chunks_exact_mut(4).for_each(|c| c[3] = 0xFF);
968        }
969
970        with_rows(
971            buf,
972            self.width,
973            self.height,
974            num_channels,
975            self.top_down,
976            |row| {
977                reader.read_exact(&mut indices)?;
978                if skip_palette {
979                    row.clone_from_slice(&indices[0..width]);
980                } else {
981                    let mut pixel_iter = row.chunks_mut(num_channels);
982                    match bit_count {
983                        1 => {
984                            set_1bit_pixel_run(&mut pixel_iter, palette, indices.iter());
985                        }
986                        2 => {
987                            set_2bit_pixel_run(&mut pixel_iter, palette, indices.iter(), width);
988                        }
989                        4 => {
990                            set_4bit_pixel_run(&mut pixel_iter, palette, indices.iter(), width);
991                        }
992                        8 => {
993                            set_8bit_pixel_run(&mut pixel_iter, palette, indices.iter(), width);
994                        }
995                        _ => panic!(),
996                    };
997                }
998                Ok(())
999            },
1000        )?;
1001
1002        Ok(())
1003    }
1004
1005    fn read_16_bit_pixel_data(
1006        &mut self,
1007        buf: &mut [u8],
1008        bitfields: Option<&Bitfields>,
1009    ) -> ImageResult<()> {
1010        let num_channels = self.num_channels();
1011        let row_padding_len = self.width as usize % 2 * 2;
1012        let row_padding = &mut [0; 2][..row_padding_len];
1013        let bitfields = match bitfields {
1014            Some(b) => b,
1015            None => self.bitfields.as_ref().unwrap(),
1016        };
1017        let reader = &mut self.reader;
1018
1019        reader.seek(SeekFrom::Start(self.data_offset))?;
1020
1021        with_rows(
1022            buf,
1023            self.width,
1024            self.height,
1025            num_channels,
1026            self.top_down,
1027            |row| {
1028                for pixel in row.chunks_mut(num_channels) {
1029                    let data = u32::from(reader.read_u16::<LittleEndian>()?);
1030
1031                    pixel[0] = bitfields.r.read(data);
1032                    pixel[1] = bitfields.g.read(data);
1033                    pixel[2] = bitfields.b.read(data);
1034                    if num_channels == 4 {
1035                        if bitfields.a.len != 0 {
1036                            pixel[3] = bitfields.a.read(data);
1037                        } else {
1038                            pixel[3] = 0xFF;
1039                        }
1040                    }
1041                }
1042                reader.read_exact(row_padding)
1043            },
1044        )?;
1045
1046        Ok(())
1047    }
1048
1049    /// Read image data from a reader in 32-bit formats that use bitfields.
1050    fn read_32_bit_pixel_data(&mut self, buf: &mut [u8]) -> ImageResult<()> {
1051        let num_channels = self.num_channels();
1052
1053        let bitfields = self.bitfields.as_ref().unwrap();
1054
1055        let reader = &mut self.reader;
1056        reader.seek(SeekFrom::Start(self.data_offset))?;
1057
1058        with_rows(
1059            buf,
1060            self.width,
1061            self.height,
1062            num_channels,
1063            self.top_down,
1064            |row| {
1065                for pixel in row.chunks_mut(num_channels) {
1066                    let data = reader.read_u32::<LittleEndian>()?;
1067
1068                    pixel[0] = bitfields.r.read(data);
1069                    pixel[1] = bitfields.g.read(data);
1070                    pixel[2] = bitfields.b.read(data);
1071                    if num_channels == 4 {
1072                        if bitfields.a.len != 0 {
1073                            pixel[3] = bitfields.a.read(data);
1074                        } else {
1075                            pixel[3] = 0xff;
1076                        }
1077                    }
1078                }
1079                Ok(())
1080            },
1081        )?;
1082
1083        Ok(())
1084    }
1085
1086    /// Read image data from a reader where the colours are stored as 8-bit values (24 or 32-bit).
1087    fn read_full_byte_pixel_data(
1088        &mut self,
1089        buf: &mut [u8],
1090        format: &FormatFullBytes,
1091    ) -> ImageResult<()> {
1092        let num_channels = self.num_channels();
1093        let row_padding_len = match *format {
1094            FormatFullBytes::RGB24 => (4 - (self.width as usize * 3) % 4) % 4,
1095            _ => 0,
1096        };
1097        let row_padding = &mut [0; 4][..row_padding_len];
1098
1099        self.reader.seek(SeekFrom::Start(self.data_offset))?;
1100
1101        let reader = &mut self.reader;
1102
1103        with_rows(
1104            buf,
1105            self.width,
1106            self.height,
1107            num_channels,
1108            self.top_down,
1109            |row| {
1110                for pixel in row.chunks_mut(num_channels) {
1111                    if *format == FormatFullBytes::Format888 {
1112                        reader.read_u8()?;
1113                    }
1114
1115                    // Read the colour values (b, g, r).
1116                    // Reading 3 bytes and reversing them is significantly faster than reading one
1117                    // at a time.
1118                    reader.read_exact(&mut pixel[0..3])?;
1119                    pixel[0..3].reverse();
1120
1121                    if *format == FormatFullBytes::RGB32 {
1122                        reader.read_u8()?;
1123                    }
1124
1125                    // Read the alpha channel if present
1126                    if *format == FormatFullBytes::RGBA32 {
1127                        reader.read_exact(&mut pixel[3..4])?;
1128                    } else if num_channels == 4 {
1129                        pixel[3] = 0xFF;
1130                    }
1131                }
1132                reader.read_exact(row_padding)
1133            },
1134        )?;
1135
1136        Ok(())
1137    }
1138
1139    fn read_rle_data(&mut self, buf: &mut [u8], image_type: ImageType) -> ImageResult<()> {
1140        // Seek to the start of the actual image data.
1141        self.reader.seek(SeekFrom::Start(self.data_offset))?;
1142
1143        let num_channels = self.num_channels();
1144        let p = self.palette.as_ref().unwrap();
1145
1146        // Handling deltas in the RLE scheme means that we need to manually
1147        // iterate through rows and pixels.  Even if we didn't have to handle
1148        // deltas, we have to ensure that a single runlength doesn't straddle
1149        // two rows.
1150        let mut row_iter = self.rows(buf);
1151
1152        while let Some(row) = row_iter.next() {
1153            let mut pixel_iter = row.chunks_mut(num_channels);
1154
1155            let mut x = 0;
1156            loop {
1157                let instruction = {
1158                    let control_byte = self.reader.read_u8()?;
1159                    match control_byte {
1160                        RLE_ESCAPE => {
1161                            let op = self.reader.read_u8()?;
1162
1163                            match op {
1164                                RLE_ESCAPE_EOL => RLEInsn::EndOfRow,
1165                                RLE_ESCAPE_EOF => RLEInsn::EndOfFile,
1166                                RLE_ESCAPE_DELTA => {
1167                                    let xdelta = self.reader.read_u8()?;
1168                                    let ydelta = self.reader.read_u8()?;
1169                                    RLEInsn::Delta(xdelta, ydelta)
1170                                }
1171                                _ => {
1172                                    let mut length = op as usize;
1173                                    if self.image_type == ImageType::RLE4 {
1174                                        length = (length + 1) / 2;
1175                                    }
1176                                    length += length & 1;
1177                                    let mut buffer = vec![0; length];
1178                                    self.reader.read_exact(&mut buffer)?;
1179                                    RLEInsn::Absolute(op, buffer)
1180                                }
1181                            }
1182                        }
1183                        _ => {
1184                            let palette_index = self.reader.read_u8()?;
1185                            RLEInsn::PixelRun(control_byte, palette_index)
1186                        }
1187                    }
1188                };
1189
1190                match instruction {
1191                    RLEInsn::EndOfFile => {
1192                        pixel_iter.for_each(|p| p.fill(0));
1193                        row_iter.for_each(|r| r.fill(0));
1194                        return Ok(());
1195                    }
1196                    RLEInsn::EndOfRow => {
1197                        pixel_iter.for_each(|p| p.fill(0));
1198                        break;
1199                    }
1200                    RLEInsn::Delta(x_delta, y_delta) => {
1201                        // The msdn site on bitmap compression doesn't specify
1202                        // what happens to the values skipped when encountering
1203                        // a delta code, however IE and the windows image
1204                        // preview seems to replace them with black pixels,
1205                        // so we stick to that.
1206
1207                        if y_delta > 0 {
1208                            // Zero out the remainder of the current row.
1209                            pixel_iter.for_each(|p| p.fill(0));
1210
1211                            // If any full rows are skipped, zero them out.
1212                            for _ in 1..y_delta {
1213                                let row = row_iter.next().ok_or(DecoderError::CorruptRleData)?;
1214                                row.fill(0);
1215                            }
1216
1217                            // Set the pixel iterator to the start of the next row.
1218                            pixel_iter = row_iter
1219                                .next()
1220                                .ok_or(DecoderError::CorruptRleData)?
1221                                .chunks_mut(num_channels);
1222
1223                            // Zero out the pixels up to the current point in the row.
1224                            for _ in 0..x {
1225                                pixel_iter
1226                                    .next()
1227                                    .ok_or(DecoderError::CorruptRleData)?
1228                                    .fill(0);
1229                            }
1230                        }
1231
1232                        for _ in 0..x_delta {
1233                            let pixel = pixel_iter.next().ok_or(DecoderError::CorruptRleData)?;
1234                            pixel.fill(0);
1235                        }
1236                        x += x_delta as usize;
1237                    }
1238                    RLEInsn::Absolute(length, indices) => {
1239                        // Absolute mode cannot span rows, so if we run
1240                        // out of pixels to process, we should stop
1241                        // processing the image.
1242                        match image_type {
1243                            ImageType::RLE8 => {
1244                                if !set_8bit_pixel_run(
1245                                    &mut pixel_iter,
1246                                    p,
1247                                    indices.iter(),
1248                                    length as usize,
1249                                ) {
1250                                    return Err(DecoderError::CorruptRleData.into());
1251                                }
1252                            }
1253                            ImageType::RLE4 => {
1254                                if !set_4bit_pixel_run(
1255                                    &mut pixel_iter,
1256                                    p,
1257                                    indices.iter(),
1258                                    length as usize,
1259                                ) {
1260                                    return Err(DecoderError::CorruptRleData.into());
1261                                }
1262                            }
1263                            _ => unreachable!(),
1264                        }
1265                        x += length as usize;
1266                    }
1267                    RLEInsn::PixelRun(n_pixels, palette_index) => {
1268                        // A pixel run isn't allowed to span rows, but we
1269                        // simply continue on to the next row if we run
1270                        // out of pixels to set.
1271                        match image_type {
1272                            ImageType::RLE8 => {
1273                                if !set_8bit_pixel_run(
1274                                    &mut pixel_iter,
1275                                    p,
1276                                    repeat(&palette_index),
1277                                    n_pixels as usize,
1278                                ) {
1279                                    return Err(DecoderError::CorruptRleData.into());
1280                                }
1281                            }
1282                            ImageType::RLE4 => {
1283                                if !set_4bit_pixel_run(
1284                                    &mut pixel_iter,
1285                                    p,
1286                                    repeat(&palette_index),
1287                                    n_pixels as usize,
1288                                ) {
1289                                    return Err(DecoderError::CorruptRleData.into());
1290                                }
1291                            }
1292                            _ => unreachable!(),
1293                        }
1294                        x += n_pixels as usize;
1295                    }
1296                }
1297            }
1298        }
1299
1300        Ok(())
1301    }
1302
1303    /// Read the actual data of the image. This function is deliberately not public because it
1304    /// cannot be called multiple times without seeking back the underlying reader in between.
1305    pub(crate) fn read_image_data(&mut self, buf: &mut [u8]) -> ImageResult<()> {
1306        match self.image_type {
1307            ImageType::Palette => self.read_palettized_pixel_data(buf),
1308            ImageType::RGB16 => self.read_16_bit_pixel_data(buf, Some(&R5_G5_B5_COLOR_MASK)),
1309            ImageType::RGB24 => self.read_full_byte_pixel_data(buf, &FormatFullBytes::RGB24),
1310            ImageType::RGB32 => self.read_full_byte_pixel_data(buf, &FormatFullBytes::RGB32),
1311            ImageType::RGBA32 => self.read_full_byte_pixel_data(buf, &FormatFullBytes::RGBA32),
1312            ImageType::RLE8 => self.read_rle_data(buf, ImageType::RLE8),
1313            ImageType::RLE4 => self.read_rle_data(buf, ImageType::RLE4),
1314            ImageType::Bitfields16 => match self.bitfields {
1315                Some(_) => self.read_16_bit_pixel_data(buf, None),
1316                None => Err(DecoderError::BitfieldMasksMissing(16).into()),
1317            },
1318            ImageType::Bitfields32 => match self.bitfields {
1319                Some(R8_G8_B8_COLOR_MASK) => {
1320                    self.read_full_byte_pixel_data(buf, &FormatFullBytes::Format888)
1321                }
1322                Some(R8_G8_B8_A8_COLOR_MASK) => {
1323                    self.read_full_byte_pixel_data(buf, &FormatFullBytes::RGBA32)
1324                }
1325                Some(_) => self.read_32_bit_pixel_data(buf),
1326                None => Err(DecoderError::BitfieldMasksMissing(32).into()),
1327            },
1328        }
1329    }
1330}
1331
1332/// Wrapper struct around a `Cursor<Vec<u8>>`
1333pub struct BmpReader<R>(Cursor<Vec<u8>>, PhantomData<R>);
1334impl<R> Read for BmpReader<R> {
1335    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
1336        self.0.read(buf)
1337    }
1338    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<usize> {
1339        if self.0.position() == 0 && buf.is_empty() {
1340            mem::swap(buf, self.0.get_mut());
1341            Ok(buf.len())
1342        } else {
1343            self.0.read_to_end(buf)
1344        }
1345    }
1346}
1347
1348impl<'a, R: 'a + Read + Seek> ImageDecoder<'a> for BmpDecoder<R> {
1349    type Reader = BmpReader<R>;
1350
1351    fn dimensions(&self) -> (u32, u32) {
1352        (self.width as u32, self.height as u32)
1353    }
1354
1355    fn color_type(&self) -> ColorType {
1356        if self.indexed_color {
1357            ColorType::L8
1358        } else if self.add_alpha_channel {
1359            ColorType::Rgba8
1360        } else {
1361            ColorType::Rgb8
1362        }
1363    }
1364
1365    fn into_reader(self) -> ImageResult<Self::Reader> {
1366        Ok(BmpReader(
1367            Cursor::new(image::decoder_to_vec(self)?),
1368            PhantomData,
1369        ))
1370    }
1371
1372    fn read_image(mut self, buf: &mut [u8]) -> ImageResult<()> {
1373        assert_eq!(u64::try_from(buf.len()), Ok(self.total_bytes()));
1374        self.read_image_data(buf)
1375    }
1376}
1377
1378impl<'a, R: 'a + Read + Seek> ImageDecoderRect<'a> for BmpDecoder<R> {
1379    fn read_rect_with_progress<F: Fn(Progress)>(
1380        &mut self,
1381        x: u32,
1382        y: u32,
1383        width: u32,
1384        height: u32,
1385        buf: &mut [u8],
1386        progress_callback: F,
1387    ) -> ImageResult<()> {
1388        let start = self.reader.stream_position()?;
1389        image::load_rect(
1390            x,
1391            y,
1392            width,
1393            height,
1394            buf,
1395            progress_callback,
1396            self,
1397            |_, _| Ok(()),
1398            |s, buf| s.read_image_data(buf),
1399        )?;
1400        self.reader.seek(SeekFrom::Start(start))?;
1401        Ok(())
1402    }
1403}
1404
1405#[cfg(test)]
1406mod test {
1407    use super::*;
1408
1409    #[test]
1410    fn test_bitfield_len() {
1411        for len in 1..9 {
1412            let bitfield = Bitfield { shift: 0, len };
1413            for i in 0..(1 << len) {
1414                let read = bitfield.read(i);
1415                let calc = (i as f64 / ((1 << len) - 1) as f64 * 255f64).round() as u8;
1416                if read != calc {
1417                    println!("len:{} i:{} read:{} calc:{}", len, i, read, calc);
1418                }
1419                assert_eq!(read, calc);
1420            }
1421        }
1422    }
1423
1424    #[test]
1425    fn read_rect() {
1426        let f = std::fs::File::open("tests/images/bmp/images/Core_8_Bit.bmp").unwrap();
1427        let mut decoder = super::BmpDecoder::new(f).unwrap();
1428
1429        let mut buf: Vec<u8> = vec![0; 8 * 8 * 3];
1430        decoder.read_rect(0, 0, 8, 8, &mut buf).unwrap();
1431    }
1432
1433    #[test]
1434    fn read_rle_too_short() {
1435        let data = vec![
1436            0x42, 0x4d, 0x04, 0xee, 0xfe, 0xff, 0xff, 0x10, 0xff, 0x00, 0x04, 0x00, 0x00, 0x00,
1437            0x7c, 0x00, 0x00, 0x00, 0x0c, 0x41, 0x00, 0x00, 0x07, 0x10, 0x00, 0x00, 0x01, 0x00,
1438            0x04, 0x00, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x00, 0x00,
1439            0x00, 0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x21,
1440            0xff, 0x00, 0x66, 0x61, 0x72, 0x62, 0x66, 0x65, 0x6c, 0x64, 0x00, 0x00, 0x00, 0x00,
1441            0x00, 0x00, 0x00, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1442            0xff, 0xd8, 0xff, 0x00, 0x00, 0x19, 0x51, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
1443            0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0xfa, 0xff, 0x00, 0x00, 0x00,
1444            0x00, 0x01, 0x00, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00,
1445            0x00, 0x00, 0x00, 0x2d, 0x31, 0x31, 0x35, 0x36, 0x00, 0xff, 0x00, 0x00, 0x52, 0x3a,
1446            0x37, 0x30, 0x7e, 0x71, 0x63, 0x91, 0x5a, 0x04, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00,
1447            0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00,
1448            0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x2d, 0x35, 0x37, 0x00, 0xff, 0x00, 0x00, 0x52,
1449            0x3a, 0x37, 0x30, 0x7e, 0x71, 0x63, 0x91, 0x5a, 0x04, 0x05, 0x3c, 0x00, 0x00, 0x11,
1450            0x00, 0x5d, 0x7a, 0x82, 0xb7, 0xca, 0x2d, 0x31, 0xff, 0xff, 0xc7, 0x95, 0x33, 0x2e,
1451            0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x7c, 0x00,
1452            0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x20, 0x66, 0x00, 0x4d,
1453            0x4d, 0x00, 0x2a, 0x00,
1454        ];
1455
1456        let decoder = BmpDecoder::new(Cursor::new(&data)).unwrap();
1457        let mut buf = vec![0; usize::try_from(decoder.total_bytes()).unwrap()];
1458        assert!(decoder.read_image(&mut buf).is_ok());
1459    }
1460
1461    #[test]
1462    fn test_no_header() {
1463        let tests = [
1464            "Info_R8_G8_B8.bmp",
1465            "Info_A8_R8_G8_B8.bmp",
1466            "Info_8_Bit.bmp",
1467            "Info_4_Bit.bmp",
1468            "Info_1_Bit.bmp",
1469        ];
1470
1471        for name in &tests {
1472            let path = format!("tests/images/bmp/images/{name}");
1473            let ref_img = crate::open(&path).unwrap();
1474            let mut data = std::fs::read(&path).unwrap();
1475            // skip the BITMAPFILEHEADER
1476            let slice = &mut data[14..];
1477            let decoder = BmpDecoder::new_without_file_header(Cursor::new(slice)).unwrap();
1478            let no_hdr_img = crate::DynamicImage::from_decoder(decoder).unwrap();
1479            assert_eq!(ref_img, no_hdr_img);
1480        }
1481    }
1482}