alloc
alloc
を使うためには、グローバル(ヒープ)アロケータを実装しなければなりません。
#![no_main] #![no_std] extern crate alloc; extern crate panic_halt as _; use alloc::string::ToString; use alloc::vec::Vec; use buddy_system_allocator::LockedHeap; #[global_allocator] static HEAP_ALLOCATOR: LockedHeap<32> = LockedHeap::<32>::new(); static mut HEAP: [u8; 65536] = [0; 65536]; pub fn entry() { // SAFETY: `HEAP` is only used here and `entry` is only called once. unsafe { // アロケーターにメモリを割り当てます。 HEAP_ALLOCATOR.lock().init(HEAP.as_mut_ptr() as usize, HEAP.len()); } // これで、ヒープ割り当てを必要とする処理を実行できるようになりました。 let mut v = Vec::new(); v.push("A string".to_string()); }
buddy_system_allocator
はサードパーティのクレートで、単純なバディシステムアロケータです。その他にも利用できるクレートはありますし、自前で実装したり、別のアロケータに自分のコードをフックすることも可能です。- パラメータ定数
LockedHeap
はアロケータの最大オーダを示します。この場合、2**32バイトの領域を確保することが可能です。 - もし依存関係にあるクレートが
alloc
に依存する場合、必ずバイナリファイルあたり一つだけのグローバルなアロケータが存在するようにしなければなりません。通常、これはトップレベルのバイナリを生成するクレートにより制御されます。 extern crate panic_halt as _
という部分は、panic_halt
クレートを確実にリンクし、パニックハンドラを利用可能にするために必要です。- この例で示したコードはビルドできますが、エントリポイントがないので実行することはできません。