Skip to content

Commit 39f2318

Browse files
committed
🚧 on-chain component serialization
1 parent 322546c commit 39f2318

File tree

11 files changed

+79
-12
lines changed

11 files changed

+79
-12
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

clients/typescript/src/index.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { Keypair, PublicKey } from "@solana/web3.js";
1+
import { PublicKey } from "@solana/web3.js";
22
import BN from "bn.js";
33
import { PROGRAM_ID as WORLD_PROGRAM_ID } from "./generated";
44
import { World as WORLD_PROGRAM_IDL } from "./generated/types";

crates/bolt-cli/src/templates/component/mod.rs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,13 +38,15 @@ pub fn component_type(idl: &Idl, component_id: &str) -> Result<String> {
3838
Some(ty) => ty,
3939
None => return Err(anyhow::anyhow!("Component type not found in IDL")),
4040
};
41+
42+
let component_name = component_account.name.to_upper_camel_case();
43+
println!("Component name: {}", component_name);
4144
let component_code = component_to_rust_code(type_def, component_id);
4245
let types_code = component_types_to_rust_code(&idl.types, &component_account.name);
4346
Ok(format!(
4447
r#"use bolt_lang::*;
4548
4649
#[component_deserialize]
47-
#[derive(Clone, Copy)]
4850
{}
4951
5052
{}

crates/bolt-lang/attribute/component-deserialize/src/lib.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,13 @@ pub fn component_deserialize(_attr: TokenStream, item: TokenStream) -> TokenStre
6363

6464
#[automatically_derived]
6565
impl bolt_lang::AccountSerialize for #name {
66-
fn try_serialize<W>(&self, _writer: &mut W) -> Result<()> {
66+
fn try_serialize<W: std::io::Write>(&self, writer: &mut W) -> Result<()> {
67+
if writer.write_all(Self::DISCRIMINATOR).is_err() {
68+
return Err(bolt_lang::AccountDidNotSerializeErrorCode.into());
69+
}
70+
if bolt_lang::AnchorSerialize::serialize(self, writer).is_err() {
71+
return Err(bolt_lang::AccountDidNotSerializeErrorCode.into());
72+
}
6773
Ok(())
6874
}
6975
}

crates/bolt-lang/src/account.rs

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -43,11 +43,16 @@ impl<'info, T: anchor_lang::ToAccountMetas, const P0: u128, const P1: u128> anch
4343
}
4444
}
4545

46-
impl<'info, T: anchor_lang::AccountsExit<'info>, const P0: u128, const P1: u128> anchor_lang::AccountsExit<'info>
46+
impl<'info, T: anchor_lang::ToAccountInfos<'info> + anchor_lang::ToAccountInfo<'info> + anchor_lang::AccountSerialize + anchor_lang::AccountsExit<'info>, const P0: u128, const P1: u128> anchor_lang::AccountsExit<'info>
4747
for BoltAccount<T, P0, P1>
4848
{
49-
fn exit(&self, program_id: &Pubkey) -> Result<()> {
50-
self.0.exit(program_id)
49+
fn exit(&self, _program_id: &Pubkey) -> Result<()> {
50+
let info = self.0.to_account_info();
51+
let mut data = info.try_borrow_mut_data()?;
52+
let dst: &mut [u8] = &mut data;
53+
let mut writer = crate::bpf_writer::BpfWriter::new(dst);
54+
self.0.try_serialize(&mut writer)?;
55+
Ok(())
5156
}
5257
}
5358

crates/bolt-lang/src/bpf_writer.rs

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
/// Implementation from Anchor.
2+
3+
use solana_program::program_memory::sol_memcpy;
4+
use std::cmp;
5+
use std::io::{self, Write};
6+
7+
#[derive(Debug, Default)]
8+
pub struct BpfWriter<T> {
9+
inner: T,
10+
pub pos: u64,
11+
}
12+
13+
impl<T> BpfWriter<T> {
14+
pub fn new(inner: T) -> Self {
15+
Self { inner, pos: 0 }
16+
}
17+
}
18+
19+
impl Write for BpfWriter<&mut [u8]> {
20+
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
21+
if self.pos >= self.inner.len() as u64 {
22+
return Ok(0);
23+
}
24+
25+
let amt = cmp::min(
26+
self.inner.len().saturating_sub(self.pos as usize),
27+
buf.len(),
28+
);
29+
sol_memcpy(&mut self.inner[(self.pos as usize)..], buf, amt);
30+
self.pos += amt as u64;
31+
Ok(amt)
32+
}
33+
34+
fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
35+
if self.write(buf)? == buf.len() {
36+
Ok(())
37+
} else {
38+
Err(io::Error::new(
39+
io::ErrorKind::WriteZero,
40+
"failed to write whole buffer",
41+
))
42+
}
43+
}
44+
45+
fn flush(&mut self) -> io::Result<()> {
46+
Ok(())
47+
}
48+
}

crates/bolt-lang/src/lib.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,14 @@ pub mod prelude;
22

33
pub use anchor_lang;
44
pub use anchor_lang::error::ErrorCode::AccountDidNotDeserialize as AccountDidNotDeserializeErrorCode;
5+
pub use anchor_lang::error::ErrorCode::AccountDidNotSerialize as AccountDidNotSerializeErrorCode;
56
pub use anchor_lang::prelude::*;
67
pub use anchor_lang::{
78
AccountDeserialize, AccountSerialize, AnchorDeserialize, AnchorSerialize, Bumps, Result,
89
};
910

1011
pub mod instructions;
12+
pub mod bpf_writer;
1113
pub use instructions::*;
1214

1315
pub mod cpi;

crates/types/Cargo.toml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[package]
22
name = "bolt-types"
3-
version.workspace = true
3+
version = "0.2.4"
44
description = "Autogenerate types for the bolt language"
55
edition = "2021"
66

@@ -9,4 +9,5 @@ crate-type = ["cdylib", "lib"]
99
name = "bolt_types"
1010

1111
[dependencies]
12-
bolt-lang.workspace = true
12+
bolt-lang.workspace = true
13+
anchor-lang.workspace = true

crates/types/src/component_Fn1JzzEdyb55fsyduWS94mYHizGhJZuhvjX6DVvrmGbQ.rs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,5 +6,3 @@ pub struct ComponentFn1JzzEdyb55fsyduWS94mYHizGhJZuhvjX6DVvrmGbQ {
66
pub y: i64,
77
pub z: i64,
88
}
9-
10-
pub use ComponentFn1JzzEdyb55fsyduWS94mYHizGhJZuhvjX6DVvrmGbQ as Position;

examples/system-simple-movement/Cargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,4 +26,4 @@ custom-panic = []
2626
[dependencies]
2727
serde.workspace = true
2828
bolt-lang.workspace = true
29-
bolt-types = { version = "0.2.3", path = "../../crates/types" }
29+
bolt-types = { version = "0.2.4", path = "../../crates/types" }

0 commit comments

Comments
 (0)