gear_core/code/metadata.rs
1// This file is part of Gear.
2
3// Copyright (C) 2021-2025 Gear Technologies Inc.
4// SPDX-License-Identifier: GPL-3.0-or-later WITH Classpath-exception-2.0
5
6// This program is free software: you can redistribute it and/or modify
7// it under the terms of the GNU General Public License as published by
8// the Free Software Foundation, either version 3 of the License, or
9// (at your option) any later version.
10
11// This program is distributed in the hope that it will be useful,
12// but WITHOUT ANY WARRANTY; without even the implied warranty of
13// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14// GNU General Public License for more details.
15
16// You should have received a copy of the GNU General Public License
17// along with this program. If not, see <https://www.gnu.org/licenses/>.
18
19//! Module code metadata
20
21use crate::{
22 message::DispatchKind,
23 pages::{WasmPage, WasmPagesAmount},
24};
25use alloc::collections::BTreeSet;
26use scale_info::{
27 TypeInfo,
28 scale::{Decode, Encode},
29};
30
31/// Status of the instrumentation.
32#[derive(Clone, Copy, Debug, Decode, Encode, TypeInfo, PartialEq, Eq, Hash)]
33pub enum InstrumentationStatus {
34 /// Code is not instrumented yet.
35 NotInstrumented,
36 /// Code is instrumented on weights version.
37 Instrumented {
38 /// Version of the instruction weights used for instrumentation.
39 version: u32,
40 /// Instrumented code length.
41 code_len: u32,
42 },
43 /// Failed to instrument code on weights version.
44 InstrumentationFailed {
45 /// Version of the instruction weights used for instrumentation.
46 version: u32,
47 },
48}
49
50/// Metadata for the code.
51#[derive(Clone, Debug, Decode, Encode, TypeInfo, PartialEq, Eq, Hash)]
52pub struct CodeMetadata {
53 /// Original code length.
54 original_code_len: u32,
55 /// Exports of the wasm module.
56 exports: BTreeSet<DispatchKind>,
57 // Static pages count from memory import.
58 static_pages: WasmPagesAmount,
59 /// Stack end page.
60 stack_end: Option<WasmPage>,
61 /// Instrumentation status, contains version of the instructions in case of instrumentation.
62 instrumentation_status: InstrumentationStatus,
63}
64
65impl CodeMetadata {
66 /// Creates a new instance of the code metadata.
67 pub fn new(
68 original_code_len: u32,
69 exports: BTreeSet<DispatchKind>,
70 static_pages: WasmPagesAmount,
71 stack_end: Option<WasmPage>,
72 instrumentation_status: InstrumentationStatus,
73 ) -> Self {
74 Self {
75 original_code_len,
76 exports,
77 static_pages,
78 stack_end,
79 instrumentation_status,
80 }
81 }
82
83 /// Converts the metadata into the failed instrumentation state.
84 pub fn into_failed_instrumentation(self, instruction_weights_version: u32) -> Self {
85 Self {
86 instrumentation_status: InstrumentationStatus::InstrumentationFailed {
87 version: instruction_weights_version,
88 },
89 ..self
90 }
91 }
92
93 /// Returns the original code length.
94 pub fn original_code_len(&self) -> u32 {
95 self.original_code_len
96 }
97
98 /// Returns the instrumented code length.
99 pub fn instrumented_code_len(&self) -> Option<u32> {
100 match self.instrumentation_status {
101 InstrumentationStatus::NotInstrumented
102 | InstrumentationStatus::InstrumentationFailed { .. } => None,
103 InstrumentationStatus::Instrumented { code_len, .. } => Some(code_len),
104 }
105 }
106
107 /// Returns the code exports.
108 pub fn exports(&self) -> &BTreeSet<DispatchKind> {
109 &self.exports
110 }
111
112 /// Returns the static pages count from memory import.
113 pub fn static_pages(&self) -> WasmPagesAmount {
114 self.static_pages
115 }
116
117 /// Returns the stack end page.
118 pub fn stack_end(&self) -> Option<WasmPage> {
119 self.stack_end
120 }
121
122 /// Returns the instrumentation status.
123 pub fn instrumentation_status(&self) -> InstrumentationStatus {
124 self.instrumentation_status
125 }
126
127 /// Returns the version of the instructions.
128 pub fn instruction_weights_version(&self) -> Option<u32> {
129 match self.instrumentation_status {
130 InstrumentationStatus::NotInstrumented => None,
131 InstrumentationStatus::Instrumented { version, .. } => Some(version),
132 InstrumentationStatus::InstrumentationFailed { version } => Some(version),
133 }
134 }
135}