Path: blob/main/crates/environ/src/fact/transcode.rs
1692 views
use crate::MemoryIndex;1use crate::component::Transcode;2use crate::fact::core_types::CoreTypes;3use crate::prelude::*;4use wasm_encoder::{EntityType, ValType};56#[derive(Copy, Clone, Hash, Eq, PartialEq)]7pub struct Transcoder {8pub from_memory: MemoryIndex,9pub from_memory64: bool,10pub to_memory: MemoryIndex,11pub to_memory64: bool,12pub op: Transcode,13}1415impl Transcoder {16pub fn name(&self) -> String {17format!(18"{} (mem{} => mem{})",19self.op.desc(),20self.from_memory.as_u32(),21self.to_memory.as_u32(),22)23}2425pub fn ty(&self, types: &mut CoreTypes) -> EntityType {26let from_ptr = if self.from_memory64 {27ValType::I6428} else {29ValType::I3230};31let to_ptr = if self.to_memory64 {32ValType::I6433} else {34ValType::I3235};3637let ty = match self.op {38// These direct transcodings take the source pointer, the source39// code units, and the destination pointer.40//41// The memories being copied between are part of each intrinsic and42// the destination code units are the same as the source.43// Note that the pointers are dynamically guaranteed to be aligned44// and in-bounds for the code units length as defined by the string45// encoding.46Transcode::Copy(_) | Transcode::Latin1ToUtf16 => {47types.function(&[from_ptr, from_ptr, to_ptr], &[])48}4950// Transcoding from utf8 to utf16 takes the from ptr/len as well as51// a destination. The destination is valid for len*2 bytes. The52// return value is how many code units were written to the53// destination.54Transcode::Utf8ToUtf16 => types.function(&[from_ptr, from_ptr, to_ptr], &[to_ptr]),5556// Transcoding to utf8 as a smaller format takes all the parameters57// and returns the amount of space consumed in the src/destination58Transcode::Utf16ToUtf8 | Transcode::Latin1ToUtf8 => {59types.function(&[from_ptr, from_ptr, to_ptr, to_ptr], &[from_ptr, to_ptr])60}6162// The return type is a tagged length which indicates which was63// used64Transcode::Utf16ToCompactProbablyUtf16 => {65types.function(&[from_ptr, from_ptr, to_ptr], &[to_ptr])66}6768// The initial step of transcoding from a fixed format to a compact69// format. Takes the ptr/len of the source the destination70// pointer. The destination length is implicitly the same. Returns71// how many code units were consumed in the source, which is also72// how many bytes were written to the destination.73Transcode::Utf8ToLatin1 | Transcode::Utf16ToLatin1 => {74types.function(&[from_ptr, from_ptr, to_ptr], &[from_ptr, to_ptr])75}7677// The final step of transcoding to a compact format when the fixed78// transcode has failed. This takes the ptr/len of the source that's79// remaining to transcode. Then this takes the destination ptr/len80// as well as the destination bytes written so far with latin1.81// Finally this returns the number of code units written to the82// destination.83Transcode::Utf8ToCompactUtf16 | Transcode::Utf16ToCompactUtf16 => {84types.function(&[from_ptr, from_ptr, to_ptr, to_ptr, to_ptr], &[to_ptr])85}86};87EntityType::Function(ty)88}89}909192