fn read_avif_meta()

in mp4parse/src/lib.rs [2716:2816]


fn read_avif_meta<T: Read + Offset>(
    src: &mut BMFFBox<T>,
    strictness: ParseStrictness,
    unsupported_features: &mut UnsupportedFeatures,
) -> Result<AvifMeta> {
    let version = read_fullbox_version_no_flags(src)?;

    if version != 0 {
        return Err(Error::Unsupported("unsupported meta version"));
    }

    let mut read_handler_box = false;
    let mut primary_item_id = None;
    let mut item_infos = None;
    let mut iloc_items = None;
    let mut item_references = None;
    let mut item_properties = None;
    let mut item_data_box = None;

    let mut iter = src.box_iter();
    while let Some(mut b) = iter.next_box()? {
        trace!("read_avif_meta parsing {:?} box", b.head.name);

        if !read_handler_box && b.head.name != BoxType::HandlerBox {
            fail_with_status_if(
                strictness != ParseStrictness::Permissive,
                Status::HdlrNotFirst,
            )?;
        }

        match b.head.name {
            BoxType::HandlerBox => {
                if read_handler_box {
                    return Status::HdrlBadQuantity.into();
                }
                let HandlerBox { handler_type } = read_hdlr(&mut b, strictness)?;
                if handler_type != b"pict" {
                    fail_with_status_if(
                        strictness != ParseStrictness::Permissive,
                        Status::HdlrTypeNotPict,
                    )?;
                }
                read_handler_box = true;
            }
            BoxType::ItemInfoBox => {
                if item_infos.is_some() {
                    return Status::IinfBadQuantity.into();
                }
                item_infos = Some(read_iinf(&mut b, strictness, unsupported_features)?);
            }
            BoxType::ItemLocationBox => {
                if iloc_items.is_some() {
                    return Status::IlocBadQuantity.into();
                }
                iloc_items = Some(read_iloc(&mut b)?);
            }
            BoxType::PrimaryItemBox => {
                if primary_item_id.is_some() {
                    return Status::PitmBadQuantity.into();
                }
                primary_item_id = Some(read_pitm(&mut b)?);
            }
            BoxType::ItemReferenceBox => {
                if item_references.is_some() {
                    return Status::IrefBadQuantity.into();
                }
                item_references = Some(read_iref(&mut b)?);
            }
            BoxType::ItemPropertiesBox => {
                if item_properties.is_some() {
                    return Status::IprpBadQuantity.into();
                }
                item_properties = Some(read_iprp(
                    &mut b,
                    MIF1_BRAND,
                    strictness,
                    unsupported_features,
                )?);
            }
            BoxType::ItemDataBox => {
                if item_data_box.is_some() {
                    return Status::IdatBadQuantity.into();
                }
                let data = b.read_into_try_vec()?;
                item_data_box = Some(DataBox::from_idat(data));
            }
            _ => skip_box_content(&mut b)?,
        }

        check_parser_state!(b.content);
    }

    Ok(AvifMeta {
        item_properties: item_properties.unwrap_or_default(),
        item_references: item_references.unwrap_or_default(),
        primary_item_id,
        item_infos: item_infos.unwrap_or_default(),
        iloc_items: iloc_items.unwrap_or_default(),
        item_data_box,
    })
}