Coverage Report

Created: 2024-05-16 12:16

/__w/smoldot/smoldot/repo/lib/src/executor.rs
Line
Count
Source (jump to first uncovered line)
1
// Smoldot
2
// Copyright (C) 2019-2022  Parity Technologies (UK) Ltd.
3
// SPDX-License-Identifier: GPL-3.0-or-later WITH Classpath-exception-2.0
4
5
// This program is free software: you can redistribute it and/or modify
6
// it under the terms of the GNU General Public License as published by
7
// the Free Software Foundation, either version 3 of the License, or
8
// (at your option) any later version.
9
10
// This program is distributed in the hope that it will be useful,
11
// but WITHOUT ANY WARRANTY; without even the implied warranty of
12
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13
// GNU General Public License for more details.
14
15
// You should have received a copy of the GNU General Public License
16
// along with this program.  If not, see <http://www.gnu.org/licenses/>.
17
18
//! WebAssembly runtime code execution.
19
//!
20
//! WebAssembly (often abbreviated *Wasm*) plays a big role in Substrate/Polkadot. The storage of
21
//! each block in the chain has a special key named `:code` which contains the WebAssembly code
22
//! of what we call *the runtime*.
23
//!
24
//! The runtime is a program (in WebAssembly) that decides, amongst other things, whether
25
//! transactions are valid and how to apply them on the storage, and whether blocks themselves are
26
//! valid.
27
//!
28
//! This module contains everything necessary to execute runtime code. The highest-level
29
//! sub-module is [`runtime_call`].
30
31
mod allocator; // TODO: make public after refactoring
32
pub mod host;
33
pub mod runtime_call;
34
pub mod storage_diff;
35
pub mod trie_root_calculator;
36
pub mod vm;
37
38
pub use host::{CoreVersion, CoreVersionError, CoreVersionRef};
39
40
/// Default number of heap pages if the storage doesn't specify otherwise.
41
///
42
/// # Context
43
///
44
/// In order to initialize a [`host::HostVmPrototype`], one needs to pass a certain number of
45
/// heap pages that are available to the runtime.
46
///
47
/// This number is normally found in the storage, at the key `:heappages`. But if it is not
48
/// specified, then the value of this constant must be used.
49
pub const DEFAULT_HEAP_PAGES: vm::HeapPages = vm::HeapPages::new(2048);
50
51
/// Converts a value of the key `:heappages` found in the storage to an actual number of heap
52
/// pages.
53
91
pub fn storage_heap_pages_to_value(
54
91
    storage_value: Option<&[u8]>,
55
91
) -> Result<vm::HeapPages, InvalidHeapPagesError> {
56
91
    if let Some(
storage_value0
) = storage_value {
57
0
        let bytes =
58
0
            <[u8; 8]>::try_from(storage_value).map_err(|_| InvalidHeapPagesError::WrongLen)?;
Unexecuted instantiation: _RNCNvNtCsN16ciHI6Qf_7smoldot8executor27storage_heap_pages_to_value0B5_
Unexecuted instantiation: _RNCNvNtCseuYC0Zibziv_7smoldot8executor27storage_heap_pages_to_value0B5_
59
0
        let num = u64::from_le_bytes(bytes);
60
0
        let num = u32::try_from(num).map_err(|_| InvalidHeapPagesError::TooLarge)?;
Unexecuted instantiation: _RNCNvNtCsN16ciHI6Qf_7smoldot8executor27storage_heap_pages_to_values_0B5_
Unexecuted instantiation: _RNCNvNtCseuYC0Zibziv_7smoldot8executor27storage_heap_pages_to_values_0B5_
61
0
        Ok(vm::HeapPages::from(num))
62
    } else {
63
91
        Ok(DEFAULT_HEAP_PAGES)
64
    }
65
91
}
_RNvNtCsN16ciHI6Qf_7smoldot8executor27storage_heap_pages_to_value
Line
Count
Source
53
5
pub fn storage_heap_pages_to_value(
54
5
    storage_value: Option<&[u8]>,
55
5
) -> Result<vm::HeapPages, InvalidHeapPagesError> {
56
5
    if let Some(
storage_value0
) = storage_value {
57
0
        let bytes =
58
0
            <[u8; 8]>::try_from(storage_value).map_err(|_| InvalidHeapPagesError::WrongLen)?;
59
0
        let num = u64::from_le_bytes(bytes);
60
0
        let num = u32::try_from(num).map_err(|_| InvalidHeapPagesError::TooLarge)?;
61
0
        Ok(vm::HeapPages::from(num))
62
    } else {
63
5
        Ok(DEFAULT_HEAP_PAGES)
64
    }
65
5
}
_RNvNtCseuYC0Zibziv_7smoldot8executor27storage_heap_pages_to_value
Line
Count
Source
53
86
pub fn storage_heap_pages_to_value(
54
86
    storage_value: Option<&[u8]>,
55
86
) -> Result<vm::HeapPages, InvalidHeapPagesError> {
56
86
    if let Some(
storage_value0
) = storage_value {
57
0
        let bytes =
58
0
            <[u8; 8]>::try_from(storage_value).map_err(|_| InvalidHeapPagesError::WrongLen)?;
59
0
        let num = u64::from_le_bytes(bytes);
60
0
        let num = u32::try_from(num).map_err(|_| InvalidHeapPagesError::TooLarge)?;
61
0
        Ok(vm::HeapPages::from(num))
62
    } else {
63
86
        Ok(DEFAULT_HEAP_PAGES)
64
    }
65
86
}
66
67
/// Error potentially returned by [`storage_heap_pages_to_value`].
68
0
#[derive(Debug, derive_more::Display, Clone)]
Unexecuted instantiation: _RNvXs_NtCsN16ciHI6Qf_7smoldot8executorNtB4_21InvalidHeapPagesErrorNtNtCsaYZPK01V26L_4core3fmt7Display3fmt
Unexecuted instantiation: _RNvXs_NtCseuYC0Zibziv_7smoldot8executorNtB4_21InvalidHeapPagesErrorNtNtCsaYZPK01V26L_4core3fmt7Display3fmt
69
pub enum InvalidHeapPagesError {
70
    /// Storage value has the wrong length.
71
    WrongLen,
72
    /// Number of heap pages is too large.
73
    TooLarge,
74
}