minemod/src/vita/mod.rs
2025-01-20 06:22:36 -04:00

211 lines
5.4 KiB
Rust

use std::fmt::Write;
use std::panic::PanicHookInfo;
use std::thread;
use std::time::Duration;
use vitasdk_sys::sceGxmTerminate;
mod debug_screen;
mod gui;
// pub const CDRAM_ALIGNMENT: u32 = 0x3FFFF;
/// 256 kb
pub const CDRAM_ALIGNMENT:u32 = (256 * 1024) - 1;
/// 4 kb
pub const NOT_CDRAM_ALIGNMENT:u32 = (4 * 1024) - 1;
#[inline]
pub const fn align(data:u32, alignment:u32) -> u32 { (data + alignment) & !alignment }
// these should probably be macros?
#[inline]
pub fn abs(x:i8) -> i8 { if x > 0 { x } else { x * -1 } }
// tracing based logger
fn rainbow_color(t:f32) -> (u32, u32, u32) {
let hue = t * 360.0; // Convert time to hue (0-360 degrees)
let saturation = 1.0; // Maximum saturation
let value = 1.0; // Maximum value (brightness)
// Convert HSV to RGB
let c = value * saturation;
let x = c * (1.0 - (((hue / 60.0) % 2.0) - 1.0).abs());
let m = value - c;
let (r, g, b) = match hue {
0.0..=60.0 => (c, x, 0.0),
60.0..=120.0 => (x, c, 0.0),
120.0..=180.0 => (0.0, c, x),
180.0..=240.0 => (0.0, x, c),
240.0..=300.0 => (x, 0.0, c),
_ => (c, 0.0, x),
};
// Scale RGB values to 8-bit integers
let r = (255.0 * (r + m)) as u32;
let g = (255.0 * (g + m)) as u32;
let b = (255.0 * (b + m)) as u32;
(r, g, b)
}
fn ilerp(min:f32, max:f32, input:f32) -> f32 { (input - min) / (max - min) }
// #[tokio::main]
pub fn main() {
std::panic::set_hook(Box::new(custom_panic_hook));
println!("Panic hook set");
// SCE_GXM_ERROR_INVALID_POINTER
// const thing1: u32 = 0x80024b05;
// const thing2: u32 = 0x80024309;
// unsafe { sceClibPrintf("whar?".as_ptr() as *const i8); }
// text_screen();
// std::thread::sleep(Duration::from_secs(3));
// for _ in 0..3 {
// raw_rainbow();
// }
// std::thread::sleep(Duration::from_secs(3));
// new_text_screen();
// std::thread::sleep(Duration::from_secs(3));
// unsafe {
// cube::cube();
// cube2::cube();
// cube3::cube();
// }
std::thread::sleep(Duration::from_secs(3));
panic!("Test panic!");
// loop {
// std::thread::sleep(Duration::from_secs(10));
// }
unsafe { sceGxmTerminate() };
}
// fn new_text_screen() {
// let mut screen = gui::TextScreen::predef();
// screen.enable();
// // for i in 336..446 {
// // screen.framebuffer.set(i, 0xFF_FF_FF_FF);
// // }
// // screen.set_cursor(4, 0);
// // write!(screen, "\n").ok();
// // screen.update_screen_raw();
// write!(screen, "Goodbye Void!\n").ok();
// screen.update_screen_raw();
// thread::sleep(Duration::from_secs(3));
// write!(screen, "Goodbye Void!\n").ok();
// screen.update_screen_raw();
// thread::sleep(Duration::from_secs(3));
// write!(screen, "Goodbye Void!\n").ok();
// screen.update_screen_raw();
// thread::sleep(Duration::from_secs(3));
// screen.set_cursor(0, 3);
// for _ in 0..25 {
// write!(screen, "Goodbye Void!\n").ok();
// // screen.update_screen_raw();
// }
// thread::sleep(Duration::from_secs(3));
// screen.clear();
// screen.update_screen_raw();
// // screen.set_foreground(255,255,0);
// // for x in 0..24 {
// // for y in 0..24 {
// // mono_screen.set_cursor(24 + x, 24 + y);
// // write!((219 as char).to_string());
// // thread::sleep(Duration::from_millis(16));
// // }
// // }
// // mono_screen.set_cursor(0,1);
// // mono_screen.set_foreground(0,0,0);
// // drop(screen);
// // let mut screen = gui::TextScreen::new();
// // screen.set_display();
// // loop {
// // screen.clear();
// // screen.update_screen_raw();
// // std::thread::sleep(Duration::from_millis(100));
// // }
// }
// fn text_screen() {
// let mut screen = debug::framebuffer::DebugScreen::new();
// writeln!(screen, "crusty").ok();
// // thread::sleep(Duration::from_secs(2));
// writeln!(screen, "newline").ok();
// // thread::sleep(Duration::from_secs(2));
// let random_numbers: Vec<u8> = (0..8).map(|_i| rand::random::<u8>()).collect();
// writeln!(screen, "random numbers: {:?}", random_numbers).ok();
// // writeln!(screen, "I know where you sleep :3").ok();
// }
fn raw_rainbow() {
let mut raw_buffer = gui::framebuffer::Framebuffer::new();
raw_buffer.set_display();
for index_width in 0..raw_buffer.screen_width {
thread::sleep(Duration::from_micros(20));
let (r, g, b) = rainbow_color(ilerp(0.0, raw_buffer.screen_width as f32, index_width as f32));
for index_height in 0..raw_buffer.screen_height {
raw_buffer.set(index_width + (index_height * raw_buffer.screen_width), 0 as u32 | b << 16 | g << 8 | r); // VITA USES ABGR
}
}
}
fn custom_panic_hook(info:&PanicHookInfo<'_>) {
// The current implementation always returns `Some`.
let location = info.location().unwrap();
let msg = match info.payload().downcast_ref::<&'static str>() {
Some(s) => *s,
None => match info.payload().downcast_ref::<String>() {
Some(s) => &s[..],
None => "Box<Any>",
},
};
let name = "unknown";
let mut screen = debug_screen::framebuffer::DebugScreen::new();
println!("thread '{}' panicked at '{}', {}", name, msg, location);
writeln!(screen, "thread '{}' panicked at '{}', {}", name, msg, location).ok();
// Give 2 seconds to see the error in case capturing the stack trace fails
// (capturing the stack trace allocates memory)
thread::sleep(Duration::from_secs(2));
let _ = std::panic::catch_unwind(move || {
// The backtrace is full of "unknown" for some reason
let backtrace = std::backtrace::Backtrace::force_capture();
writeln!(screen, "{}", backtrace).ok();
});
loop {
thread::sleep(Duration::from_secs(60));
}
}