wadec 0.0.1

A library for decoding WebAssembly modules.
Documentation
use crate::core::indices::MemIdx;
use crate::core::{Data, DataMode};
use crate::decode::helpers::{
    DecodeByteVectorError, DecodeVectorError, ParseExpressionError, decode_byte_vector,
    decode_expr, decode_vector,
};
use crate::decode::indices::DecodeMemIdxError;
use crate::decode::integer::{DecodeU32Error, decode_u32};
use std::io::Read;
use thiserror::Error;

#[derive(Debug, Error)]
pub enum DecodeDataSectionError {
    #[error("failed decoding Data section")]
    DecodeVector(#[from] DecodeVectorError<DecodeDataSegmentError>),
}

pub(crate) fn decode_data_section<R: Read + ?Sized>(
    reader: &mut R,
) -> Result<Vec<Data>, DecodeDataSectionError> {
    Ok(decode_vector(reader, parse_data)?)
}

#[derive(Debug, Error)]
pub enum DecodeDataSegmentError {
    #[error("failed decoding bitfield")]
    DecodeBitfield(DecodeU32Error),

    #[error("invalid bitfield: expected 0 (passive), 1 or 2 (active); got {0}")]
    InvalidBitfield(u32),

    #[error("failed decoding offset expression")]
    DecodeOffsetExpr(ParseExpressionError),

    #[error("failed decoding init byte vector")]
    DecodeInitVector(#[from] DecodeByteVectorError),

    #[error("failed decoding Memory index")]
    DecodeMemIdx(#[from] DecodeMemIdxError),
}

fn parse_data<R: Read + ?Sized>(reader: &mut R) -> Result<Data, DecodeDataSegmentError> {
    let init: Vec<u8>;
    let mode: DataMode;

    (init, mode) = match decode_u32(reader).map_err(DecodeDataSegmentError::DecodeBitfield)? {
        0 => {
            let e = decode_expr(reader).map_err(DecodeDataSegmentError::DecodeOffsetExpr)?;
            (
                decode_byte_vector(reader)?,
                DataMode::Active {
                    memory: MemIdx(0),
                    offset: e,
                },
            )
        }
        1 => (decode_byte_vector(reader)?, DataMode::Passive),
        2 => {
            let x = MemIdx::decode(reader)?;
            let e = decode_expr(reader).map_err(DecodeDataSegmentError::DecodeOffsetExpr)?;

            (
                decode_byte_vector(reader)?,
                DataMode::Active {
                    memory: x,
                    offset: e,
                },
            )
        }
        n => return Err(DecodeDataSegmentError::InvalidBitfield(n)),
    };

    Ok(Data { init, mode })
}