1#![no_std]
10#![no_main]
11#![feature(custom_test_frameworks)]
12#![test_runner(test_runner)]
13#![reexport_test_harness_main = "test_main"]
14
15use crate::hil::symmetric_encryption::AES128_BLOCK_SIZE;
16use crate::otbn::OtbnComponent;
17use crate::pinmux_layout::BoardPinmuxLayout;
18use capsules_aes_gcm::aes_gcm;
19use capsules_core::virtualizers::virtual_aes_ccm;
20use capsules_core::virtualizers::virtual_alarm::{MuxAlarm, VirtualMuxAlarm};
21use capsules_system::syscall_filter::tbf_header_filter::TbfHeaderFilterDefaultAllow;
22use earlgrey::chip::EarlGreyDefaultPeripherals;
23use earlgrey::chip_config::EarlGreyConfig;
24use earlgrey::pinmux_config::EarlGreyPinmuxConfig;
25use kernel::capabilities;
26use kernel::component::Component;
27use kernel::debug::PanicResources;
28use kernel::hil;
29use kernel::hil::entropy::Entropy32;
30use kernel::hil::hasher::Hasher;
31use kernel::hil::i2c::I2CMaster;
32use kernel::hil::led::LedHigh;
33use kernel::hil::rng::Rng;
34use kernel::hil::symmetric_encryption::AES128;
35use kernel::platform::{KernelResources, SyscallDriverLookup};
36use kernel::scheduler::priority::PrioritySched;
37use kernel::utilities::registers::interfaces::ReadWriteable;
38use kernel::utilities::single_thread_value::SingleThreadValue;
39use kernel::{create_capability, debug, static_init};
40use lowrisc::flash_ctrl::FlashMPConfig;
41use rv32i::csr;
42
43pub mod io;
44mod otbn;
45pub mod pinmux_layout;
46#[cfg(test)]
47mod tests;
48
49pub enum ChipConfig {}
58
59#[cfg(feature = "fpga_cw310")]
60impl EarlGreyConfig for ChipConfig {
61 const NAME: &'static str = "fpga_cw310";
62
63 const CPU_FREQ: u32 = 24_000_000;
65 const PERIPHERAL_FREQ: u32 = 6_000_000;
66 const AON_TIMER_FREQ: u32 = 250_000;
67 const UART_BAUDRATE: u32 = 115200;
68}
69
70#[cfg(feature = "sim_verilator")]
71impl EarlGreyConfig for ChipConfig {
72 const NAME: &'static str = "sim_verilator";
73
74 const CPU_FREQ: u32 = 500_000;
76 const PERIPHERAL_FREQ: u32 = 125_000;
77 const AON_TIMER_FREQ: u32 = 125_000;
78 const UART_BAUDRATE: u32 = 7200;
79}
80
81pub const EPMP_HANDOVER_CONFIG_CHECK: bool = false;
84
85pub type EPMPDebugConfig = earlgrey::epmp::EPMPDebugEnable;
94
95pub type EarlGreyChip = earlgrey::chip::EarlGrey<
98 'static,
99 { <EPMPDebugConfig as earlgrey::epmp::EPMPDebugConfig>::TOR_USER_REGIONS },
100 EarlGreyDefaultPeripherals<'static, ChipConfig, BoardPinmuxLayout>,
101 ChipConfig,
102 BoardPinmuxLayout,
103 earlgrey::epmp::EarlGreyEPMP<{ EPMP_HANDOVER_CONFIG_CHECK }, EPMPDebugConfig>,
104>;
105
106const NUM_PROCS: usize = 4;
107
108type ChipHw = EarlGreyChip;
109type AlarmHw = earlgrey::timer::RvTimer<'static, ChipConfig>;
110type SchedulerTimerHw =
111 components::virtual_scheduler_timer::VirtualSchedulerTimerComponentType<AlarmHw>;
112type ProcessPrinterInUse = capsules_system::process_printer::ProcessPrinterText;
113
114static PANIC_RESOURCES: SingleThreadValue<PanicResources<ChipHw, ProcessPrinterInUse>> =
116 SingleThreadValue::new(PanicResources::new());
117
118#[cfg(test)]
120static mut PERIPHERALS: Option<&'static EarlGreyDefaultPeripherals<ChipConfig, BoardPinmuxLayout>> =
121 None;
122#[cfg(test)]
124static mut BOARD: Option<&'static kernel::Kernel> = None;
125#[cfg(test)]
127static mut PLATFORM: Option<&'static EarlGrey> = None;
128#[cfg(test)]
130static mut MAIN_CAP: Option<&dyn kernel::capabilities::MainLoopCapability> = None;
131static mut ALARM: Option<
133 &'static MuxAlarm<'static, earlgrey::timer::RvTimer<'static, ChipConfig>>,
134> = None;
135static mut TICKV: Option<
137 &capsules_extra::tickv::TicKVSystem<
138 'static,
139 capsules_core::virtualizers::virtual_flash::FlashUser<
140 'static,
141 lowrisc::flash_ctrl::FlashCtrl<'static>,
142 >,
143 capsules_extra::sip_hash::SipHasher24<'static>,
144 2048,
145 >,
146> = None;
147static mut AES: Option<
149 &aes_gcm::Aes128Gcm<
150 'static,
151 virtual_aes_ccm::VirtualAES128CCM<'static, earlgrey::aes::Aes<'static>>,
152 >,
153> = None;
154static mut SIPHASH: Option<&capsules_extra::sip_hash::SipHasher24<'static>> = None;
156static mut RSA_HARDWARE: Option<&lowrisc::rsa::OtbnRsa<'static>> = None;
158
159#[cfg(test)]
161static mut SHA256SOFT: Option<&capsules_extra::sha256::Sha256Software<'static>> = None;
162
163const FAULT_RESPONSE: capsules_system::process_policies::PanicFaultPolicy =
165 capsules_system::process_policies::PanicFaultPolicy {};
166
167kernel::stack_size! {0x1400}
168
169struct EarlGrey {
172 led: &'static capsules_core::led::LedDriver<
173 'static,
174 LedHigh<'static, earlgrey::gpio::GpioPin<'static, earlgrey::pinmux::PadConfig>>,
175 8,
176 >,
177 gpio: &'static capsules_core::gpio::GPIO<
178 'static,
179 earlgrey::gpio::GpioPin<'static, earlgrey::pinmux::PadConfig>,
180 >,
181 console: &'static capsules_core::console::Console<'static>,
182 alarm: &'static capsules_core::alarm::AlarmDriver<
183 'static,
184 VirtualMuxAlarm<'static, earlgrey::timer::RvTimer<'static, ChipConfig>>,
185 >,
186 hmac: &'static capsules_extra::hmac::HmacDriver<'static, lowrisc::hmac::Hmac<'static>, 32>,
187 lldb: &'static capsules_core::low_level_debug::LowLevelDebug<
188 'static,
189 capsules_core::virtualizers::virtual_uart::UartDevice<'static>,
190 >,
191 i2c_master:
192 &'static capsules_core::i2c_master::I2CMasterDriver<'static, lowrisc::i2c::I2c<'static>>,
193 spi_controller: &'static capsules_core::spi_controller::Spi<
194 'static,
195 capsules_core::virtualizers::virtual_spi::VirtualSpiMasterDevice<
196 'static,
197 lowrisc::spi_host::SpiHost<'static>,
198 >,
199 >,
200 rng: &'static capsules_core::rng::RngDriver<
201 'static,
202 capsules_core::rng::Entropy32ToRandom<'static, lowrisc::csrng::CsRng<'static>>,
203 >,
204 aes: &'static capsules_extra::symmetric_encryption::aes::AesDriver<
205 'static,
206 aes_gcm::Aes128Gcm<
207 'static,
208 virtual_aes_ccm::VirtualAES128CCM<'static, earlgrey::aes::Aes<'static>>,
209 >,
210 >,
211 kv_driver: &'static capsules_extra::kv_driver::KVStoreDriver<
212 'static,
213 capsules_extra::virtualizers::virtual_kv::VirtualKVPermissions<
214 'static,
215 capsules_extra::kv_store_permissions::KVStorePermissions<
216 'static,
217 capsules_extra::tickv_kv_store::TicKVKVStore<
218 'static,
219 capsules_extra::tickv::TicKVSystem<
220 'static,
221 capsules_core::virtualizers::virtual_flash::FlashUser<
222 'static,
223 lowrisc::flash_ctrl::FlashCtrl<'static>,
224 >,
225 capsules_extra::sip_hash::SipHasher24<'static>,
226 2048,
227 >,
228 [u8; 8],
229 >,
230 >,
231 >,
232 >,
233 syscall_filter: &'static TbfHeaderFilterDefaultAllow,
234 scheduler: &'static PrioritySched,
235 scheduler_timer: &'static SchedulerTimerHw,
236 watchdog: &'static lowrisc::aon_timer::AonTimer,
237}
238
239impl SyscallDriverLookup for EarlGrey {
241 fn with_driver<F, R>(&self, driver_num: usize, f: F) -> R
242 where
243 F: FnOnce(Option<&dyn kernel::syscall::SyscallDriver>) -> R,
244 {
245 match driver_num {
246 capsules_core::led::DRIVER_NUM => f(Some(self.led)),
247 capsules_extra::hmac::DRIVER_NUM => f(Some(self.hmac)),
248 capsules_core::gpio::DRIVER_NUM => f(Some(self.gpio)),
249 capsules_core::console::DRIVER_NUM => f(Some(self.console)),
250 capsules_core::alarm::DRIVER_NUM => f(Some(self.alarm)),
251 capsules_core::low_level_debug::DRIVER_NUM => f(Some(self.lldb)),
252 capsules_core::i2c_master::DRIVER_NUM => f(Some(self.i2c_master)),
253 capsules_core::spi_controller::DRIVER_NUM => f(Some(self.spi_controller)),
254 capsules_core::rng::DRIVER_NUM => f(Some(self.rng)),
255 capsules_extra::symmetric_encryption::aes::DRIVER_NUM => f(Some(self.aes)),
256 capsules_extra::kv_driver::DRIVER_NUM => f(Some(self.kv_driver)),
257 _ => f(None),
258 }
259 }
260}
261
262impl KernelResources<EarlGreyChip> for EarlGrey {
263 type SyscallDriverLookup = Self;
264 type SyscallFilter = TbfHeaderFilterDefaultAllow;
265 type ProcessFault = ();
266 type Scheduler = PrioritySched;
267 type SchedulerTimer = SchedulerTimerHw;
268 type WatchDog = lowrisc::aon_timer::AonTimer;
269 type ContextSwitchCallback = ();
270
271 fn syscall_driver_lookup(&self) -> &Self::SyscallDriverLookup {
272 self
273 }
274 fn syscall_filter(&self) -> &Self::SyscallFilter {
275 self.syscall_filter
276 }
277 fn process_fault(&self) -> &Self::ProcessFault {
278 &()
279 }
280 fn scheduler(&self) -> &Self::Scheduler {
281 self.scheduler
282 }
283 fn scheduler_timer(&self) -> &Self::SchedulerTimer {
284 self.scheduler_timer
285 }
286 fn watchdog(&self) -> &Self::WatchDog {
287 self.watchdog
288 }
289 fn context_switch_callback(&self) -> &Self::ContextSwitchCallback {
290 &()
291 }
292}
293
294unsafe fn setup() -> (
295 &'static kernel::Kernel,
296 &'static EarlGrey,
297 &'static EarlGreyChip,
298 &'static EarlGreyDefaultPeripherals<'static, ChipConfig, BoardPinmuxLayout>,
299) {
300 extern "C" {
302 static _sapps: u8;
304 static _eapps: u8;
306 static mut _sappmem: u8;
308 static _eappmem: u8;
310 static _stext: u8;
312 static _etext: u8;
314 static _sflash: u8;
316 static _eflash: u8;
318 static _ssram: u8;
320 static _esram: u8;
322 static _manifest: u8;
324 }
325
326 earlgrey::chip::configure_trap_handler();
328
329 kernel::deferred_call::initialize_deferred_call_state_unsafe::<
331 <ChipHw as kernel::platform::chip::Chip>::ThreadIdProvider,
332 >();
333
334 PANIC_RESOURCES
336 .bind_to_thread_unsafe::<<ChipHw as kernel::platform::chip::Chip>::ThreadIdProvider>();
337
338 let earlgrey_epmp = earlgrey::epmp::EarlGreyEPMP::new_debug(
342 earlgrey::epmp::FlashRegion(
343 rv32i::pmp::NAPOTRegionSpec::from_start_end(
344 core::ptr::addr_of!(_sflash),
345 core::ptr::addr_of!(_eflash),
346 )
347 .unwrap(),
348 ),
349 earlgrey::epmp::RAMRegion(
350 rv32i::pmp::NAPOTRegionSpec::from_start_end(
351 core::ptr::addr_of!(_ssram),
352 core::ptr::addr_of!(_esram),
353 )
354 .unwrap(),
355 ),
356 earlgrey::epmp::MMIORegion(
357 rv32i::pmp::NAPOTRegionSpec::from_start_size(
358 0x40000000 as *const u8, 0x10000000, )
361 .unwrap(),
362 ),
363 earlgrey::epmp::KernelTextRegion(
364 rv32i::pmp::TORRegionSpec::from_start_end(
365 core::ptr::addr_of!(_stext),
366 core::ptr::addr_of!(_etext),
367 )
368 .unwrap(),
369 ),
370 earlgrey::epmp::RVDMRegion(
375 rv32i::pmp::NAPOTRegionSpec::from_start_size(
376 0x00010000 as *const u8, 0x00001000, )
379 .unwrap(),
380 ),
381 )
382 .unwrap();
383
384 BoardPinmuxLayout::setup();
386
387 let process_mgmt_cap = create_capability!(capabilities::ProcessManagementCapability);
389 let memory_allocation_cap = create_capability!(capabilities::MemoryAllocationCapability);
390
391 let processes = components::process_array::ProcessArrayComponent::new()
393 .finalize(components::process_array_component_static!(NUM_PROCS));
394 PANIC_RESOURCES.get().map(|resources| {
395 resources.processes.put(processes.as_slice());
396 });
397
398 let board_kernel = static_init!(kernel::Kernel, kernel::Kernel::new(processes.as_slice()));
400
401 let peripherals = static_init!(
402 EarlGreyDefaultPeripherals<ChipConfig, BoardPinmuxLayout>,
403 EarlGreyDefaultPeripherals::new()
404 );
405 peripherals.init();
406
407 let debug_gpios = static_init!(
409 [&'static dyn kernel::hil::gpio::Pin; 1],
410 [
411 &peripherals.gpio_port[7]
413 ]
414 );
415 kernel::debug::initialize_debug_gpio_unsafe::<
416 <ChipHw as kernel::platform::chip::Chip>::ThreadIdProvider,
417 >();
418 kernel::debug::assign_gpios(debug_gpios);
419
420 let uart_mux =
422 components::console::UartMuxComponent::new(&peripherals.uart0, ChipConfig::UART_BAUDRATE)
423 .finalize(components::uart_mux_component_static!());
424
425 let led = components::led::LedsComponent::new().finalize(components::led_component_static!(
428 LedHigh<'static, earlgrey::gpio::GpioPin<earlgrey::pinmux::PadConfig>>,
429 LedHigh::new(&peripherals.gpio_port[8]),
430 LedHigh::new(&peripherals.gpio_port[9]),
431 LedHigh::new(&peripherals.gpio_port[10]),
432 LedHigh::new(&peripherals.gpio_port[11]),
433 LedHigh::new(&peripherals.gpio_port[12]),
434 LedHigh::new(&peripherals.gpio_port[13]),
435 LedHigh::new(&peripherals.gpio_port[14]),
436 LedHigh::new(&peripherals.gpio_port[15]),
437 ));
438
439 let gpio = components::gpio::GpioComponent::new(
440 board_kernel,
441 capsules_core::gpio::DRIVER_NUM,
442 components::gpio_component_helper!(
443 earlgrey::gpio::GpioPin<earlgrey::pinmux::PadConfig>,
444 0 => &peripherals.gpio_port[0],
445 1 => &peripherals.gpio_port[1],
446 2 => &peripherals.gpio_port[2],
447 3 => &peripherals.gpio_port[3],
448 4 => &peripherals.gpio_port[4],
449 5 => &peripherals.gpio_port[5],
450 6 => &peripherals.gpio_port[6],
451 7 => &peripherals.gpio_port[15]
452 ),
453 )
454 .finalize(components::gpio_component_static!(
455 earlgrey::gpio::GpioPin<earlgrey::pinmux::PadConfig>
456 ));
457
458 let hardware_alarm = static_init!(
459 earlgrey::timer::RvTimer<ChipConfig>,
460 earlgrey::timer::RvTimer::new()
461 );
462 hardware_alarm.setup();
463
464 let mux_alarm = static_init!(
467 MuxAlarm<'static, earlgrey::timer::RvTimer<ChipConfig>>,
468 MuxAlarm::new(hardware_alarm)
469 );
470 hil::time::Alarm::set_alarm_client(hardware_alarm, mux_alarm);
471
472 ALARM = Some(mux_alarm);
473
474 let virtual_alarm_user = static_init!(
476 VirtualMuxAlarm<'static, earlgrey::timer::RvTimer<ChipConfig>>,
477 VirtualMuxAlarm::new(mux_alarm)
478 );
479 virtual_alarm_user.setup();
480
481 let alarm = static_init!(
482 capsules_core::alarm::AlarmDriver<
483 'static,
484 VirtualMuxAlarm<'static, earlgrey::timer::RvTimer<ChipConfig>>,
485 >,
486 capsules_core::alarm::AlarmDriver::new(
487 virtual_alarm_user,
488 board_kernel.create_grant(capsules_core::alarm::DRIVER_NUM, &memory_allocation_cap)
489 )
490 );
491 hil::time::Alarm::set_alarm_client(virtual_alarm_user, alarm);
492
493 let scheduler_timer =
494 components::virtual_scheduler_timer::VirtualSchedulerTimerComponent::new(mux_alarm)
495 .finalize(components::virtual_scheduler_timer_component_static!(
496 AlarmHw
497 ));
498
499 let chip = static_init!(
500 EarlGreyChip,
501 earlgrey::chip::EarlGrey::new(peripherals, hardware_alarm, earlgrey_epmp)
502 );
503 PANIC_RESOURCES.get().map(|resources| {
504 resources.chip.put(chip);
505 });
506
507 chip.enable_plic_interrupts();
509 csr::CSR.mie.modify(
511 csr::mie::mie::msoft::SET + csr::mie::mie::mtimer::CLEAR + csr::mie::mie::mext::SET,
512 );
513 csr::CSR.mstatus.modify(csr::mstatus::mstatus::mie::SET);
514
515 let console = components::console::ConsoleComponent::new(
517 board_kernel,
518 capsules_core::console::DRIVER_NUM,
519 uart_mux,
520 )
521 .finalize(components::console_component_static!());
522 components::debug_writer::DebugWriterComponent::new_unsafe(
524 uart_mux,
525 create_capability!(capabilities::SetDebugWriterCapability),
526 || unsafe {
527 kernel::debug::initialize_debug_writer_wrapper_unsafe::<
528 <ChipHw as kernel::platform::chip::Chip>::ThreadIdProvider,
529 >();
530 },
531 )
532 .finalize(components::debug_writer_component_static!());
533
534 let lldb = components::lldb::LowLevelDebugComponent::new(
535 board_kernel,
536 capsules_core::low_level_debug::DRIVER_NUM,
537 uart_mux,
538 )
539 .finalize(components::low_level_debug_component_static!());
540
541 let hmac = components::hmac::HmacComponent::new(
542 board_kernel,
543 capsules_extra::hmac::DRIVER_NUM,
544 &peripherals.hmac,
545 )
546 .finalize(components::hmac_component_static!(lowrisc::hmac::Hmac, 32));
547
548 let i2c_master_buffer = static_init!(
549 [u8; capsules_core::i2c_master::BUFFER_LENGTH],
550 [0; capsules_core::i2c_master::BUFFER_LENGTH]
551 );
552 let i2c_master = static_init!(
553 capsules_core::i2c_master::I2CMasterDriver<'static, lowrisc::i2c::I2c<'static>>,
554 capsules_core::i2c_master::I2CMasterDriver::new(
555 &peripherals.i2c0,
556 i2c_master_buffer,
557 board_kernel.create_grant(
558 capsules_core::i2c_master::DRIVER_NUM,
559 &memory_allocation_cap
560 )
561 )
562 );
563
564 peripherals.i2c0.set_master_client(i2c_master);
565
566 let mux_spi = components::spi::SpiMuxComponent::new(&peripherals.spi_host0).finalize(
568 components::spi_mux_component_static!(lowrisc::spi_host::SpiHost),
569 );
570
571 let spi_controller = components::spi::SpiSyscallComponent::new(
572 board_kernel,
573 mux_spi,
574 lowrisc::spi_host::CS(0),
575 capsules_core::spi_controller::DRIVER_NUM,
576 )
577 .finalize(components::spi_syscall_component_static!(
578 lowrisc::spi_host::SpiHost
579 ));
580
581 let process_printer = components::process_printer::ProcessPrinterTextComponent::new()
582 .finalize(components::process_printer_text_component_static!());
583 PANIC_RESOURCES.get().map(|resources| {
584 resources.printer.put(process_printer);
585 });
586
587 extern "C" {
599 static _sstorage: u8;
601 static _estorage: u8;
602 }
603
604 let mp_cfg = FlashMPConfig {
607 read_en: true,
608 write_en: false,
609 erase_en: false,
610 scramble_en: false,
611 ecc_en: false,
612 he_en: false,
613 };
614
615 if let Err(e) = peripherals.flash_ctrl.mp_set_region_perms(
617 core::ptr::addr_of!(_manifest) as usize,
618 core::ptr::addr_of!(_etext) as usize,
619 0,
620 &mp_cfg,
621 ) {
622 debug!("Failed to set flash memory protection: {:?}", e);
623 } else {
624 if let Err(e) = peripherals.flash_ctrl.mp_lock_region_cfg(0) {
626 debug!("Failed to lock memory protection config: {:?}", e);
627 }
628 }
629
630 let flash_ctrl_read_buf = static_init!(
632 [u8; lowrisc::flash_ctrl::PAGE_SIZE],
633 [0; lowrisc::flash_ctrl::PAGE_SIZE]
634 );
635 let page_buffer = static_init!(
636 lowrisc::flash_ctrl::LowRiscPage,
637 lowrisc::flash_ctrl::LowRiscPage::default()
638 );
639
640 let mux_flash = components::flash::FlashMuxComponent::new(&peripherals.flash_ctrl).finalize(
641 components::flash_mux_component_static!(lowrisc::flash_ctrl::FlashCtrl),
642 );
643
644 let sip_hash = static_init!(
646 capsules_extra::sip_hash::SipHasher24,
647 capsules_extra::sip_hash::SipHasher24::new()
648 );
649 kernel::deferred_call::DeferredCallClient::register(sip_hash);
650 SIPHASH = Some(sip_hash);
651
652 let tickv = components::tickv::TicKVComponent::new(
654 sip_hash,
655 mux_flash, lowrisc::flash_ctrl::FLASH_PAGES_PER_BANK - 1, lowrisc::flash_ctrl::FLASH_PAGES_PER_BANK * lowrisc::flash_ctrl::PAGE_SIZE,
659 flash_ctrl_read_buf, page_buffer, )
662 .finalize(components::tickv_component_static!(
663 lowrisc::flash_ctrl::FlashCtrl,
664 capsules_extra::sip_hash::SipHasher24,
665 2048
666 ));
667 hil::flash::HasClient::set_client(&peripherals.flash_ctrl, mux_flash);
668 sip_hash.set_client(tickv);
669 TICKV = Some(tickv);
670
671 let kv_store = components::kv::TicKVKVStoreComponent::new(tickv).finalize(
672 components::tickv_kv_store_component_static!(
673 capsules_extra::tickv::TicKVSystem<
674 capsules_core::virtualizers::virtual_flash::FlashUser<
675 lowrisc::flash_ctrl::FlashCtrl,
676 >,
677 capsules_extra::sip_hash::SipHasher24<'static>,
678 2048,
679 >,
680 capsules_extra::tickv::TicKVKeyType,
681 ),
682 );
683
684 let kv_store_permissions = components::kv::KVStorePermissionsComponent::new(kv_store).finalize(
685 components::kv_store_permissions_component_static!(
686 capsules_extra::tickv_kv_store::TicKVKVStore<
687 capsules_extra::tickv::TicKVSystem<
688 capsules_core::virtualizers::virtual_flash::FlashUser<
689 lowrisc::flash_ctrl::FlashCtrl,
690 >,
691 capsules_extra::sip_hash::SipHasher24<'static>,
692 2048,
693 >,
694 capsules_extra::tickv::TicKVKeyType,
695 >
696 ),
697 );
698
699 let mux_kv = components::kv::KVPermissionsMuxComponent::new(kv_store_permissions).finalize(
700 components::kv_permissions_mux_component_static!(
701 capsules_extra::kv_store_permissions::KVStorePermissions<
702 capsules_extra::tickv_kv_store::TicKVKVStore<
703 capsules_extra::tickv::TicKVSystem<
704 capsules_core::virtualizers::virtual_flash::FlashUser<
705 lowrisc::flash_ctrl::FlashCtrl,
706 >,
707 capsules_extra::sip_hash::SipHasher24<'static>,
708 2048,
709 >,
710 capsules_extra::tickv::TicKVKeyType,
711 >,
712 >
713 ),
714 );
715
716 let virtual_kv_driver = components::kv::VirtualKVPermissionsComponent::new(mux_kv).finalize(
717 components::virtual_kv_permissions_component_static!(
718 capsules_extra::kv_store_permissions::KVStorePermissions<
719 capsules_extra::tickv_kv_store::TicKVKVStore<
720 capsules_extra::tickv::TicKVSystem<
721 capsules_core::virtualizers::virtual_flash::FlashUser<
722 lowrisc::flash_ctrl::FlashCtrl,
723 >,
724 capsules_extra::sip_hash::SipHasher24<'static>,
725 2048,
726 >,
727 capsules_extra::tickv::TicKVKeyType,
728 >,
729 >
730 ),
731 );
732
733 let kv_driver = components::kv::KVDriverComponent::new(
734 virtual_kv_driver,
735 board_kernel,
736 capsules_extra::kv_driver::DRIVER_NUM,
737 )
738 .finalize(components::kv_driver_component_static!(
739 capsules_extra::virtualizers::virtual_kv::VirtualKVPermissions<
740 capsules_extra::kv_store_permissions::KVStorePermissions<
741 capsules_extra::tickv_kv_store::TicKVKVStore<
742 capsules_extra::tickv::TicKVSystem<
743 capsules_core::virtualizers::virtual_flash::FlashUser<
744 lowrisc::flash_ctrl::FlashCtrl,
745 >,
746 capsules_extra::sip_hash::SipHasher24<'static>,
747 2048,
748 >,
749 capsules_extra::tickv::TicKVKeyType,
750 >,
751 >,
752 >
753 ));
754
755 let mux_otbn = crate::otbn::AccelMuxComponent::new(&peripherals.otbn)
756 .finalize(otbn_mux_component_static!());
757
758 let otbn = OtbnComponent::new(mux_otbn).finalize(crate::otbn_component_static!());
759
760 let otbn_rsa_internal_buf = static_init!([u8; 512], [0; 512]);
761
762 if let Ok((rsa_imem_start, rsa_imem_length, rsa_dmem_start, rsa_dmem_length)) =
764 crate::otbn::find_app(
765 "otbn-rsa",
766 core::slice::from_raw_parts(
767 core::ptr::addr_of!(_sapps),
768 core::ptr::addr_of!(_eapps) as usize - core::ptr::addr_of!(_sapps) as usize,
769 ),
770 )
771 {
772 let rsa_hardware = static_init!(
773 lowrisc::rsa::OtbnRsa<'static>,
774 lowrisc::rsa::OtbnRsa::new(
775 otbn,
776 lowrisc::rsa::AppAddresses {
777 imem_start: rsa_imem_start,
778 imem_size: rsa_imem_length,
779 dmem_start: rsa_dmem_start,
780 dmem_size: rsa_dmem_length
781 },
782 otbn_rsa_internal_buf,
783 )
784 );
785 peripherals.otbn.set_client(rsa_hardware);
786 RSA_HARDWARE = Some(rsa_hardware);
787 } else {
788 debug!("Unable to find otbn-rsa, disabling RSA support");
789 }
790
791 let entropy_to_random = static_init!(
793 capsules_core::rng::Entropy32ToRandom<'static, lowrisc::csrng::CsRng<'static>>,
794 capsules_core::rng::Entropy32ToRandom::new(&peripherals.rng)
795 );
796 peripherals.rng.set_client(entropy_to_random);
797 let rng = static_init!(
799 capsules_core::rng::RngDriver<
800 'static,
801 capsules_core::rng::Entropy32ToRandom<'static, lowrisc::csrng::CsRng<'static>>,
802 >,
803 capsules_core::rng::RngDriver::new(
804 entropy_to_random,
805 board_kernel.create_grant(capsules_core::rng::DRIVER_NUM, &memory_allocation_cap)
806 )
807 );
808 entropy_to_random.set_client(rng);
809
810 const CRYPT_SIZE: usize = 7 * AES128_BLOCK_SIZE;
811
812 let ccm_mux = static_init!(
813 virtual_aes_ccm::MuxAES128CCM<'static, earlgrey::aes::Aes<'static>>,
814 virtual_aes_ccm::MuxAES128CCM::new(&peripherals.aes)
815 );
816 kernel::deferred_call::DeferredCallClient::register(ccm_mux);
817 peripherals.aes.set_client(ccm_mux);
818
819 let ccm_client = components::aes::AesVirtualComponent::new(ccm_mux).finalize(
820 components::aes_virtual_component_static!(earlgrey::aes::Aes<'static>),
821 );
822
823 let crypt_buf2 = static_init!([u8; CRYPT_SIZE], [0x00; CRYPT_SIZE]);
824 let gcm_client = static_init!(
825 aes_gcm::Aes128Gcm<
826 'static,
827 virtual_aes_ccm::VirtualAES128CCM<'static, earlgrey::aes::Aes<'static>>,
828 >,
829 aes_gcm::Aes128Gcm::new(ccm_client, crypt_buf2)
830 );
831 ccm_client.set_client(gcm_client);
832
833 let aes = components::aes::AesDriverComponent::new(
834 board_kernel,
835 capsules_extra::symmetric_encryption::aes::DRIVER_NUM,
836 gcm_client,
837 )
838 .finalize(components::aes_driver_component_static!(
839 aes_gcm::Aes128Gcm<
840 'static,
841 virtual_aes_ccm::VirtualAES128CCM<'static, earlgrey::aes::Aes<'static>>,
842 >,
843 ));
844
845 AES = Some(gcm_client);
846
847 #[cfg(test)]
848 {
849 use capsules_extra::sha256::Sha256Software;
850
851 let sha_soft = static_init!(Sha256Software<'static>, Sha256Software::new());
852 kernel::deferred_call::DeferredCallClient::register(sha_soft);
853
854 SHA256SOFT = Some(sha_soft);
855 }
856
857 hil::symmetric_encryption::AES128GCM::set_client(gcm_client, aes);
858 hil::symmetric_encryption::AES128::set_client(gcm_client, ccm_client);
859
860 let syscall_filter = static_init!(TbfHeaderFilterDefaultAllow, TbfHeaderFilterDefaultAllow {});
861 let scheduler = components::sched::priority::PriorityComponent::new(board_kernel)
862 .finalize(components::priority_component_static!());
863 let watchdog = &peripherals.watchdog;
864
865 let earlgrey = static_init!(
866 EarlGrey,
867 EarlGrey {
868 led,
869 gpio,
870 console,
871 alarm,
872 hmac,
873 lldb,
874 i2c_master,
875 spi_controller,
876 rng,
877 aes,
878 kv_driver,
879 syscall_filter,
880 scheduler,
881 scheduler_timer,
882 watchdog,
883 }
884 );
885
886 kernel::process::load_processes(
887 board_kernel,
888 chip,
889 core::slice::from_raw_parts(
890 core::ptr::addr_of!(_sapps),
891 core::ptr::addr_of!(_eapps) as usize - core::ptr::addr_of!(_sapps) as usize,
892 ),
893 core::slice::from_raw_parts_mut(
894 core::ptr::addr_of_mut!(_sappmem),
895 core::ptr::addr_of!(_eappmem) as usize - core::ptr::addr_of!(_sappmem) as usize,
896 ),
897 &FAULT_RESPONSE,
898 &process_mgmt_cap,
899 )
900 .unwrap_or_else(|err| {
901 debug!("Error loading processes!");
902 debug!("{:?}", err);
903 });
904 debug!("OpenTitan initialisation complete. Entering main loop");
905
906 (board_kernel, earlgrey, chip, peripherals)
907}
908
909#[no_mangle]
914pub unsafe fn main() {
915 #[cfg(test)]
916 test_main();
917
918 #[cfg(not(test))]
919 {
920 let (board_kernel, earlgrey, chip, _peripherals) = setup();
921
922 let main_loop_cap = create_capability!(capabilities::MainLoopCapability);
923
924 board_kernel.kernel_loop(earlgrey, chip, None::<&kernel::ipc::IPC<0>>, &main_loop_cap);
925 }
926}
927
928#[cfg(test)]
929use kernel::platform::watchdog::WatchDog;
930
931#[cfg(test)]
932fn test_runner(tests: &[&dyn Fn()]) {
933 unsafe {
934 let (board_kernel, earlgrey, _chip, peripherals) = setup();
935
936 BOARD = Some(board_kernel);
937 PLATFORM = Some(&earlgrey);
938 PERIPHERALS = Some(peripherals);
939 MAIN_CAP = Some(&create_capability!(capabilities::MainLoopCapability));
940
941 PLATFORM.map(|p| {
942 p.watchdog().setup();
943 });
944
945 for test in tests {
946 test();
947 }
948 }
949
950 crate::tests::semihost_command_exit_success()
952}