forked from AbleOS/ableos
Merge branch 'master' into fix/rhai-repl
This commit is contained in:
commit
9273d74446
|
@ -2,19 +2,19 @@ use lazy_static::lazy_static;
|
|||
use spin::Mutex;
|
||||
use uart_16550::SerialPort;
|
||||
lazy_static! {
|
||||
pub static ref SERIAL1: Mutex<SerialPort> = {
|
||||
let mut serial_port = unsafe { SerialPort::new(0x3F8) };
|
||||
serial_port.init();
|
||||
Mutex::new(serial_port)
|
||||
};
|
||||
pub static ref SERIAL1: Mutex<SerialPort> = {
|
||||
let mut serial_port = unsafe { SerialPort::new(0x3F8) };
|
||||
serial_port.init();
|
||||
Mutex::new(serial_port)
|
||||
};
|
||||
}
|
||||
#[doc(hidden)]
|
||||
pub fn _print(args: ::core::fmt::Arguments) {
|
||||
use core::fmt::Write;
|
||||
SERIAL1
|
||||
.lock()
|
||||
.write_fmt(args)
|
||||
.expect("Printing to serial failed");
|
||||
use core::fmt::Write;
|
||||
SERIAL1
|
||||
.lock()
|
||||
.write_fmt(args)
|
||||
.expect("Printing to serial failed");
|
||||
}
|
||||
/// Prints to the host through the serial interface.
|
||||
#[macro_export]
|
||||
|
|
|
@ -1,112 +1,112 @@
|
|||
use bootloader::bootinfo::{MemoryMap, MemoryRegionType};
|
||||
use x86_64::{
|
||||
structures::paging::{
|
||||
FrameAllocator, Mapper, OffsetPageTable, Page, PageTable, PhysFrame, Size4KiB,
|
||||
},
|
||||
PhysAddr, VirtAddr,
|
||||
structures::paging::{
|
||||
FrameAllocator, Mapper, OffsetPageTable, Page, PageTable, PhysFrame, Size4KiB,
|
||||
},
|
||||
PhysAddr, VirtAddr,
|
||||
};
|
||||
|
||||
pub unsafe fn init(physical_memory_offset: VirtAddr) -> OffsetPageTable<'static> {
|
||||
let level_4_table = active_level_4_table(physical_memory_offset);
|
||||
OffsetPageTable::new(level_4_table, physical_memory_offset)
|
||||
let level_4_table = active_level_4_table(physical_memory_offset);
|
||||
OffsetPageTable::new(level_4_table, physical_memory_offset)
|
||||
}
|
||||
|
||||
unsafe fn active_level_4_table(physical_memory_offset: VirtAddr) -> &'static mut PageTable {
|
||||
use x86_64::registers::control::Cr3;
|
||||
use x86_64::registers::control::Cr3;
|
||||
|
||||
let (level_4_table_frame, _) = Cr3::read();
|
||||
let (level_4_table_frame, _) = Cr3::read();
|
||||
|
||||
let phys = level_4_table_frame.start_address();
|
||||
let virt = physical_memory_offset + phys.as_u64();
|
||||
let page_table_ptr: *mut PageTable = virt.as_mut_ptr();
|
||||
let phys = level_4_table_frame.start_address();
|
||||
let virt = physical_memory_offset + phys.as_u64();
|
||||
let page_table_ptr: *mut PageTable = virt.as_mut_ptr();
|
||||
|
||||
// THIS IS UNSAFE
|
||||
&mut *page_table_ptr
|
||||
// THIS IS UNSAFE
|
||||
&mut *page_table_ptr
|
||||
}
|
||||
|
||||
fn translate_addr_inner(addr: VirtAddr, physical_memory_offset: VirtAddr) -> Option<PhysAddr> {
|
||||
use x86_64::registers::control::Cr3;
|
||||
use x86_64::structures::paging::page_table::FrameError;
|
||||
use x86_64::registers::control::Cr3;
|
||||
use x86_64::structures::paging::page_table::FrameError;
|
||||
|
||||
let (level_4_table_frame, _) = Cr3::read();
|
||||
let (level_4_table_frame, _) = Cr3::read();
|
||||
|
||||
let table_indexes = [
|
||||
addr.p4_index(),
|
||||
addr.p3_index(),
|
||||
addr.p2_index(),
|
||||
addr.p1_index(),
|
||||
];
|
||||
let mut frame = level_4_table_frame;
|
||||
let table_indexes = [
|
||||
addr.p4_index(),
|
||||
addr.p3_index(),
|
||||
addr.p2_index(),
|
||||
addr.p1_index(),
|
||||
];
|
||||
let mut frame = level_4_table_frame;
|
||||
|
||||
for &index in &table_indexes {
|
||||
// convert the frame into a page table reference
|
||||
let virt = physical_memory_offset + frame.start_address().as_u64();
|
||||
let table_ptr: *const PageTable = virt.as_ptr();
|
||||
let table = unsafe { &*table_ptr };
|
||||
for &index in &table_indexes {
|
||||
// convert the frame into a page table reference
|
||||
let virt = physical_memory_offset + frame.start_address().as_u64();
|
||||
let table_ptr: *const PageTable = virt.as_ptr();
|
||||
let table = unsafe { &*table_ptr };
|
||||
|
||||
let entry = &table[index];
|
||||
frame = match entry.frame() {
|
||||
Ok(frame) => frame,
|
||||
Err(FrameError::FrameNotPresent) => return None,
|
||||
Err(FrameError::HugeFrame) => panic!["huge pages not supported"],
|
||||
};
|
||||
}
|
||||
let entry = &table[index];
|
||||
frame = match entry.frame() {
|
||||
Ok(frame) => frame,
|
||||
Err(FrameError::FrameNotPresent) => return None,
|
||||
Err(FrameError::HugeFrame) => panic!["huge pages not supported"],
|
||||
};
|
||||
}
|
||||
|
||||
Some(frame.start_address() + u64::from(addr.page_offset()))
|
||||
Some(frame.start_address() + u64::from(addr.page_offset()))
|
||||
}
|
||||
|
||||
pub unsafe fn translate_addr(addr: VirtAddr, physical_memory_offset: VirtAddr) -> Option<PhysAddr> {
|
||||
translate_addr_inner(addr, physical_memory_offset)
|
||||
translate_addr_inner(addr, physical_memory_offset)
|
||||
}
|
||||
|
||||
pub fn create_example_mapping(
|
||||
page: Page,
|
||||
mapper: &mut OffsetPageTable,
|
||||
frame_allocator: &mut impl FrameAllocator<Size4KiB>,
|
||||
page: Page,
|
||||
mapper: &mut OffsetPageTable,
|
||||
frame_allocator: &mut impl FrameAllocator<Size4KiB>,
|
||||
) {
|
||||
use x86_64::structures::paging::PageTableFlags as Flags;
|
||||
use x86_64::structures::paging::PageTableFlags as Flags;
|
||||
|
||||
let frame = PhysFrame::containing_address(PhysAddr::new(0xb8000));
|
||||
let flags = Flags::PRESENT | Flags::WRITABLE;
|
||||
let frame = PhysFrame::containing_address(PhysAddr::new(0xb8000));
|
||||
let flags = Flags::PRESENT | Flags::WRITABLE;
|
||||
|
||||
let map_to_result = unsafe { mapper.map_to(page, frame, flags, frame_allocator) };
|
||||
map_to_result.expect("map_to failed").flush();
|
||||
let map_to_result = unsafe { mapper.map_to(page, frame, flags, frame_allocator) };
|
||||
map_to_result.expect("map_to failed").flush();
|
||||
}
|
||||
|
||||
pub struct EmptyFrameAllocator;
|
||||
|
||||
unsafe impl FrameAllocator<Size4KiB> for EmptyFrameAllocator {
|
||||
fn allocate_frame(&mut self) -> Option<PhysFrame<Size4KiB>> {
|
||||
None
|
||||
}
|
||||
fn allocate_frame(&mut self) -> Option<PhysFrame<Size4KiB>> {
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
pub struct BootInfoFrameAllocator {
|
||||
memory_map: &'static MemoryMap,
|
||||
next: usize,
|
||||
memory_map: &'static MemoryMap,
|
||||
next: usize,
|
||||
}
|
||||
|
||||
impl BootInfoFrameAllocator {
|
||||
pub unsafe fn init(memory_map: &'static MemoryMap) -> Self {
|
||||
Self {
|
||||
memory_map,
|
||||
next: 0,
|
||||
}
|
||||
}
|
||||
pub unsafe fn init(memory_map: &'static MemoryMap) -> Self {
|
||||
Self {
|
||||
memory_map,
|
||||
next: 0,
|
||||
}
|
||||
}
|
||||
|
||||
fn usable_frames(&self) -> impl Iterator<Item = PhysFrame> {
|
||||
let regions = self.memory_map.iter();
|
||||
let usable_regions = regions.filter(|r| r.region_type == MemoryRegionType::Usable);
|
||||
let addr_range = usable_regions.map(|r| r.range.start_addr()..r.range.end_addr());
|
||||
let frame_address = addr_range.flat_map(|r| r.step_by(4096));
|
||||
frame_address.map(|addr| PhysFrame::containing_address(PhysAddr::new(addr)))
|
||||
}
|
||||
fn usable_frames(&self) -> impl Iterator<Item = PhysFrame> {
|
||||
let regions = self.memory_map.iter();
|
||||
let usable_regions = regions.filter(|r| r.region_type == MemoryRegionType::Usable);
|
||||
let addr_range = usable_regions.map(|r| r.range.start_addr()..r.range.end_addr());
|
||||
let frame_address = addr_range.flat_map(|r| r.step_by(4096));
|
||||
frame_address.map(|addr| PhysFrame::containing_address(PhysAddr::new(addr)))
|
||||
}
|
||||
}
|
||||
|
||||
unsafe impl FrameAllocator<Size4KiB> for BootInfoFrameAllocator {
|
||||
fn allocate_frame(&mut self) -> Option<PhysFrame<Size4KiB>> {
|
||||
let frame = self.usable_frames().nth(self.next);
|
||||
self.next += 1;
|
||||
frame
|
||||
}
|
||||
fn allocate_frame(&mut self) -> Option<PhysFrame<Size4KiB>> {
|
||||
let frame = self.usable_frames().nth(self.next);
|
||||
self.next += 1;
|
||||
frame
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,34 +1,34 @@
|
|||
// Can be standardized
|
||||
// NOTE: Move this to relib
|
||||
pub struct SemanticVersion {
|
||||
pub major: u8,
|
||||
pub minor: u8,
|
||||
pub patch: u8,
|
||||
pub major: u8,
|
||||
pub minor: u8,
|
||||
pub patch: u8,
|
||||
}
|
||||
impl core::fmt::Display for SemanticVersion {
|
||||
fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
|
||||
write!(f, "v{}.{}.{}", self.major, self.minor, self.patch)
|
||||
}
|
||||
fn fmt(&self, f: &mut core::fmt::Formatter) -> core::fmt::Result {
|
||||
write!(f, "v{}.{}.{}", self.major, self.minor, self.patch)
|
||||
}
|
||||
}
|
||||
// NOTE: Move to somewhere else
|
||||
lazy_static! {
|
||||
pub static ref KINFO: KernelInfo = KernelInfo {
|
||||
kernel_version: SemanticVersion {
|
||||
major: 0,
|
||||
minor: 0,
|
||||
patch: 0,
|
||||
},
|
||||
memory: SystemMemory { used: 0, total: 0 }
|
||||
};
|
||||
pub static ref KINFO: KernelInfo = KernelInfo {
|
||||
kernel_version: SemanticVersion {
|
||||
major: 0,
|
||||
minor: 0,
|
||||
patch: 0,
|
||||
},
|
||||
memory: SystemMemory { used: 0, total: 0 }
|
||||
};
|
||||
}
|
||||
/// simple info you would want to know in a neofetch like program
|
||||
pub struct KernelInfo {
|
||||
// os: String,
|
||||
// host: String,
|
||||
pub kernel_version: SemanticVersion,
|
||||
// cpu: String,
|
||||
// gpu: String,
|
||||
pub memory: SystemMemory,
|
||||
// os: String,
|
||||
// host: String,
|
||||
pub kernel_version: SemanticVersion,
|
||||
// cpu: String,
|
||||
// gpu: String,
|
||||
pub memory: SystemMemory,
|
||||
}
|
||||
use super::systeminfo::SystemMemory;
|
||||
use lazy_static::lazy_static;
|
||||
|
|
|
@ -1,10 +1,10 @@
|
|||
pub trait Server {
|
||||
/// Initialize the server and return a number
|
||||
fn initialize() -> u32;
|
||||
/// kill the server
|
||||
fn kill() -> bool;
|
||||
// put data in the servers outbox
|
||||
fn send();
|
||||
// put data in the servers inbox and notify it
|
||||
fn recieve();
|
||||
/// Initialize the server and return a number
|
||||
fn initialize() -> u32;
|
||||
/// kill the server
|
||||
fn kill() -> bool;
|
||||
// put data in the servers outbox
|
||||
fn send();
|
||||
// put data in the servers inbox and notify it
|
||||
fn recieve();
|
||||
}
|
||||
|
|
|
@ -1,3 +1,3 @@
|
|||
//!
|
||||
pub mod compositor;
|
||||
pub mod window;
|
||||
pub mod compositor;
|
|
@ -1,16 +1,16 @@
|
|||
use crate::{
|
||||
DecodedKey, HandleControl, KeyCode, KeyboardLayout, LayoutEntry, LayoutEntryKind, Modifiers,
|
||||
DecodedKey, HandleControl, KeyCode, KeyboardLayout, LayoutEntry, LayoutEntryKind, Modifiers,
|
||||
};
|
||||
|
||||
// Do not edit this file directly. Instead, create a `Keyboard` and modify that.
|
||||
|
||||
pub struct CustomLayout {
|
||||
mapping: [LayoutEntry; 256],
|
||||
mapping: [LayoutEntry; 256],
|
||||
}
|
||||
impl Default for CustomLayout {
|
||||
fn default() -> Self {
|
||||
Self::new_us104key()
|
||||
}
|
||||
fn default() -> Self {
|
||||
Self::new_us104key()
|
||||
}
|
||||
}
|
||||
#[rustfmt::skip]
|
||||
impl CustomLayout {
|
||||
|
@ -101,76 +101,76 @@ impl CustomLayout {
|
|||
}
|
||||
}
|
||||
impl KeyboardLayout for CustomLayout {
|
||||
fn map_keycode(
|
||||
&self,
|
||||
keycode: KeyCode,
|
||||
modifiers: &Modifiers,
|
||||
handle_ctrl: HandleControl,
|
||||
) -> DecodedKey {
|
||||
let map_to_unicode = handle_ctrl == HandleControl::MapLettersToUnicode;
|
||||
let spot = &self.mapping[keycode as usize];
|
||||
if let Some(k) = if map_to_unicode && modifiers.is_ctrl() {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.raw_unicode,
|
||||
LayoutEntryKind::Numlockable => None,
|
||||
LayoutEntryKind::Capslockable => spot.raw_unicode,
|
||||
}
|
||||
} else if modifiers.alt_gr {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.altgr,
|
||||
LayoutEntryKind::Numlockable => None,
|
||||
LayoutEntryKind::Capslockable => spot.altgr,
|
||||
}
|
||||
} else if modifiers.is_shifted() {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.shifted,
|
||||
LayoutEntryKind::Numlockable => {
|
||||
if modifiers.numlock {
|
||||
spot.locked_shifted
|
||||
} else {
|
||||
spot.shifted
|
||||
}
|
||||
fn map_keycode(
|
||||
&self,
|
||||
keycode: KeyCode,
|
||||
modifiers: &Modifiers,
|
||||
handle_ctrl: HandleControl,
|
||||
) -> DecodedKey {
|
||||
let map_to_unicode = handle_ctrl == HandleControl::MapLettersToUnicode;
|
||||
let spot = &self.mapping[keycode as usize];
|
||||
if let Some(k) = if map_to_unicode && modifiers.is_ctrl() {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.raw_unicode,
|
||||
LayoutEntryKind::Numlockable => None,
|
||||
LayoutEntryKind::Capslockable => spot.raw_unicode,
|
||||
}
|
||||
LayoutEntryKind::Capslockable => {
|
||||
if modifiers.is_caps() {
|
||||
spot.locked_shifted
|
||||
} else {
|
||||
spot.shifted
|
||||
}
|
||||
} else if modifiers.alt_gr {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.altgr,
|
||||
LayoutEntryKind::Numlockable => None,
|
||||
LayoutEntryKind::Capslockable => spot.altgr,
|
||||
}
|
||||
}
|
||||
} else {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.unshifted,
|
||||
LayoutEntryKind::Numlockable => {
|
||||
if modifiers.numlock {
|
||||
spot.locked
|
||||
} else {
|
||||
spot.unshifted
|
||||
}
|
||||
} else if modifiers.is_shifted() {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.shifted,
|
||||
LayoutEntryKind::Numlockable => {
|
||||
if modifiers.numlock {
|
||||
spot.locked_shifted
|
||||
} else {
|
||||
spot.shifted
|
||||
}
|
||||
}
|
||||
LayoutEntryKind::Capslockable => {
|
||||
if modifiers.is_caps() {
|
||||
spot.locked_shifted
|
||||
} else {
|
||||
spot.shifted
|
||||
}
|
||||
}
|
||||
}
|
||||
LayoutEntryKind::Capslockable => {
|
||||
if modifiers.is_caps() {
|
||||
spot.locked
|
||||
} else {
|
||||
spot.unshifted
|
||||
}
|
||||
} else {
|
||||
match spot.kind {
|
||||
LayoutEntryKind::Regular => spot.unshifted,
|
||||
LayoutEntryKind::Numlockable => {
|
||||
if modifiers.numlock {
|
||||
spot.locked
|
||||
} else {
|
||||
spot.unshifted
|
||||
}
|
||||
}
|
||||
LayoutEntryKind::Capslockable => {
|
||||
if modifiers.is_caps() {
|
||||
spot.locked
|
||||
} else {
|
||||
spot.unshifted
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} {
|
||||
k
|
||||
} else {
|
||||
DecodedKey::RawKey(keycode as u8)
|
||||
}
|
||||
}
|
||||
} {
|
||||
k
|
||||
} else {
|
||||
DecodedKey::RawKey(keycode as u8)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Note(elfein) Not super hard to get right, but still- DO NOT TOUCH
|
||||
impl CustomLayout {
|
||||
// See how hard this is to get right?
|
||||
// See the complexity of all the methods?
|
||||
// Yeah- if you don't know what you're doing, ask before you touch!
|
||||
pub fn set(&mut self, pos: KeyCode, entry: LayoutEntry) {
|
||||
self.mapping[pos as usize] = entry;
|
||||
}
|
||||
// See how hard this is to get right?
|
||||
// See the complexity of all the methods?
|
||||
// Yeah- if you don't know what you're doing, ask before you touch!
|
||||
pub fn set(&mut self, pos: KeyCode, entry: LayoutEntry) {
|
||||
self.mapping[pos as usize] = entry;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,253 +1,255 @@
|
|||
use crate::{KeyCode, ScancodeSet, DecodeState, KeyEvent, Error, KeyState, keyboard::EXTENDED_KEY_CODE};
|
||||
use crate::{
|
||||
keyboard::EXTENDED_KEY_CODE, DecodeState, Error, KeyCode, KeyEvent, KeyState, ScancodeSet,
|
||||
};
|
||||
|
||||
pub struct CustomScancodeSet {
|
||||
single_byte: [Option<KeyCode>; 256],
|
||||
extended: [Option<KeyCode>; 256],
|
||||
single_byte: [Option<KeyCode>; 256],
|
||||
extended: [Option<KeyCode>; 256],
|
||||
}
|
||||
impl Default for CustomScancodeSet {
|
||||
fn default() -> Self {
|
||||
Self::scancode_set1()
|
||||
}
|
||||
fn default() -> Self {
|
||||
Self::scancode_set1()
|
||||
}
|
||||
}
|
||||
impl CustomScancodeSet {
|
||||
pub fn scancode_set1() -> Self {
|
||||
let mut scancode_set = Self {
|
||||
single_byte: [None; 256],
|
||||
extended: [None; 256],
|
||||
};
|
||||
scancode_set.single_byte[0x01] = Some(KeyCode::Escape); // 01
|
||||
scancode_set.single_byte[0x02] = Some(KeyCode::Key1); // 02
|
||||
scancode_set.single_byte[0x03] = Some(KeyCode::Key2); // 03
|
||||
scancode_set.single_byte[0x04] = Some(KeyCode::Key3); // 04
|
||||
scancode_set.single_byte[0x05] = Some(KeyCode::Key4); // 05
|
||||
scancode_set.single_byte[0x06] = Some(KeyCode::Key5); // 06
|
||||
scancode_set.single_byte[0x07] = Some(KeyCode::Key6); // 07
|
||||
scancode_set.single_byte[0x08] = Some(KeyCode::Key7); // 08
|
||||
scancode_set.single_byte[0x09] = Some(KeyCode::Key8); // 09
|
||||
scancode_set.single_byte[0x0A] = Some(KeyCode::Key9); // 0A
|
||||
scancode_set.single_byte[0x0B] = Some(KeyCode::Key0); // 0B
|
||||
scancode_set.single_byte[0x0C] = Some(KeyCode::Minus); // 0C
|
||||
scancode_set.single_byte[0x0D] = Some(KeyCode::Equals); // 0D
|
||||
scancode_set.single_byte[0x0E] = Some(KeyCode::Backspace); // 0E
|
||||
scancode_set.single_byte[0x0F] = Some(KeyCode::Tab); // 0F
|
||||
scancode_set.single_byte[0x10] = Some(KeyCode::Q); // 10
|
||||
scancode_set.single_byte[0x11] = Some(KeyCode::W); // 11
|
||||
scancode_set.single_byte[0x12] = Some(KeyCode::E); // 12
|
||||
scancode_set.single_byte[0x13] = Some(KeyCode::R); // 13
|
||||
scancode_set.single_byte[0x14] = Some(KeyCode::T); // 14
|
||||
scancode_set.single_byte[0x15] = Some(KeyCode::Y); // 15
|
||||
scancode_set.single_byte[0x16] = Some(KeyCode::U); // 16
|
||||
scancode_set.single_byte[0x17] = Some(KeyCode::I); // 17
|
||||
scancode_set.single_byte[0x18] = Some(KeyCode::O); // 18
|
||||
scancode_set.single_byte[0x19] = Some(KeyCode::P); // 19
|
||||
scancode_set.single_byte[0x1A] = Some(KeyCode::BracketSquareLeft); // 1A
|
||||
scancode_set.single_byte[0x1B] = Some(KeyCode::BracketSquareRight); // 1B
|
||||
scancode_set.single_byte[0x1C] = Some(KeyCode::Enter); // 1C
|
||||
scancode_set.single_byte[0x1D] = Some(KeyCode::ControlLeft); // 1D
|
||||
scancode_set.single_byte[0x1E] = Some(KeyCode::A); // 1E
|
||||
scancode_set.single_byte[0x1F] = Some(KeyCode::S); // 1F
|
||||
scancode_set.single_byte[0x20] = Some(KeyCode::D); // 20
|
||||
scancode_set.single_byte[0x21] = Some(KeyCode::F); // 21
|
||||
scancode_set.single_byte[0x22] = Some(KeyCode::G); // 22
|
||||
scancode_set.single_byte[0x23] = Some(KeyCode::H); // 23
|
||||
scancode_set.single_byte[0x24] = Some(KeyCode::J); // 24
|
||||
scancode_set.single_byte[0x25] = Some(KeyCode::K); // 25
|
||||
scancode_set.single_byte[0x26] = Some(KeyCode::L); // 26
|
||||
scancode_set.single_byte[0x27] = Some(KeyCode::SemiColon); // 27
|
||||
scancode_set.single_byte[0x28] = Some(KeyCode::Quote); // 28
|
||||
scancode_set.single_byte[0x29] = Some(KeyCode::BackTick); // 29
|
||||
scancode_set.single_byte[0x2A] = Some(KeyCode::ShiftLeft); // 2A
|
||||
scancode_set.single_byte[0x2B] = Some(KeyCode::BackSlash); // 2B
|
||||
scancode_set.single_byte[0x2C] = Some(KeyCode::Z); // 2C
|
||||
scancode_set.single_byte[0x2D] = Some(KeyCode::X); // 2D
|
||||
scancode_set.single_byte[0x2E] = Some(KeyCode::C); // 2E
|
||||
scancode_set.single_byte[0x2F] = Some(KeyCode::V); // 2F
|
||||
scancode_set.single_byte[0x30] = Some(KeyCode::B); // 30
|
||||
scancode_set.single_byte[0x31] = Some(KeyCode::N); // 31
|
||||
scancode_set.single_byte[0x32] = Some(KeyCode::M); // 32
|
||||
scancode_set.single_byte[0x33] = Some(KeyCode::Comma); // 33
|
||||
scancode_set.single_byte[0x34] = Some(KeyCode::Fullstop); // 34
|
||||
scancode_set.single_byte[0x35] = Some(KeyCode::Slash); // 35
|
||||
scancode_set.single_byte[0x36] = Some(KeyCode::ShiftRight); // 36
|
||||
scancode_set.single_byte[0x37] = Some(KeyCode::NumpadStar); // 37
|
||||
scancode_set.single_byte[0x38] = Some(KeyCode::AltLeft); // 38
|
||||
scancode_set.single_byte[0x39] = Some(KeyCode::Spacebar); // 39
|
||||
scancode_set.single_byte[0x3A] = Some(KeyCode::CapsLock); // 3A
|
||||
scancode_set.single_byte[0x3B] = Some(KeyCode::F1); // 3B
|
||||
scancode_set.single_byte[0x3C] = Some(KeyCode::F2); // 3C
|
||||
scancode_set.single_byte[0x3D] = Some(KeyCode::F3); // 3D
|
||||
scancode_set.single_byte[0x3E] = Some(KeyCode::F4); // 3E
|
||||
scancode_set.single_byte[0x3F] = Some(KeyCode::F5); // 3F
|
||||
scancode_set.single_byte[0x40] = Some(KeyCode::F6); // 40
|
||||
scancode_set.single_byte[0x41] = Some(KeyCode::F7); // 41
|
||||
scancode_set.single_byte[0x42] = Some(KeyCode::F8); // 42
|
||||
scancode_set.single_byte[0x43] = Some(KeyCode::F9); // 43
|
||||
scancode_set.single_byte[0x44] = Some(KeyCode::F10); // 44
|
||||
scancode_set.single_byte[0x45] = Some(KeyCode::NumpadLock); // 45
|
||||
scancode_set.single_byte[0x46] = Some(KeyCode::ScrollLock); // 46
|
||||
scancode_set.single_byte[0x47] = Some(KeyCode::Numpad7); // 47
|
||||
scancode_set.single_byte[0x48] = Some(KeyCode::Numpad8); // 48
|
||||
scancode_set.single_byte[0x49] = Some(KeyCode::Numpad9); // 49
|
||||
scancode_set.single_byte[0x4A] = Some(KeyCode::NumpadMinus); // 4A
|
||||
scancode_set.single_byte[0x4B] = Some(KeyCode::Numpad4); // 4B
|
||||
scancode_set.single_byte[0x4C] = Some(KeyCode::Numpad5); // 4C
|
||||
scancode_set.single_byte[0x4D] = Some(KeyCode::Numpad6); // 4D
|
||||
scancode_set.single_byte[0x4E] = Some(KeyCode::NumpadPlus); // 4E
|
||||
scancode_set.single_byte[0x4F] = Some(KeyCode::Numpad1); // 4F
|
||||
scancode_set.single_byte[0x50] = Some(KeyCode::Numpad2); // 50
|
||||
scancode_set.single_byte[0x51] = Some(KeyCode::Numpad3); // 51
|
||||
scancode_set.single_byte[0x52] = Some(KeyCode::Numpad0); // 52
|
||||
scancode_set.single_byte[0x53] = Some(KeyCode::NumpadPeriod); // 53
|
||||
// 0x54
|
||||
// 0x55
|
||||
// 0x56
|
||||
scancode_set.single_byte[0x57] = Some(KeyCode::F11); // 57
|
||||
scancode_set.single_byte[0x58] = Some(KeyCode::F12); // 58
|
||||
for i in 0x81..=0xD8 {
|
||||
scancode_set.single_byte[i] = scancode_set.single_byte[i - 0x80];
|
||||
}
|
||||
scancode_set.extended[0x10] = Some(KeyCode::PrevTrack); // E010
|
||||
//0x11
|
||||
//0x12
|
||||
//0x13
|
||||
//0x14
|
||||
//0x15
|
||||
//0x16
|
||||
//0x17
|
||||
//0x18
|
||||
scancode_set.extended[0x19] = Some(KeyCode::NextTrack); // E019
|
||||
//0x1A
|
||||
//0x1B
|
||||
scancode_set.extended[0x1C] = Some(KeyCode::NumpadEnter); // E01C
|
||||
scancode_set.extended[0x1D] = Some(KeyCode::ControlRight); // E01D
|
||||
//0x1E
|
||||
//0x1F
|
||||
scancode_set.extended[0x20] = Some(KeyCode::Mute); // E020
|
||||
scancode_set.extended[0x21] = Some(KeyCode::Calculator); // E021
|
||||
scancode_set.extended[0x22] = Some(KeyCode::Play); // E022
|
||||
//0x23
|
||||
scancode_set.extended[0x24] = Some(KeyCode::Stop); // E024
|
||||
//0x25
|
||||
//0x26
|
||||
//0x27
|
||||
//0x28
|
||||
//0x29
|
||||
//0x2A
|
||||
//0x2B
|
||||
//0x2C
|
||||
//0x2D
|
||||
scancode_set.extended[0x2E] = Some(KeyCode::VolumeDown); // E02E
|
||||
//0x2F
|
||||
scancode_set.extended[0x30] = Some(KeyCode::VolumeUp); // E030
|
||||
//0x31
|
||||
scancode_set.extended[0x32] = Some(KeyCode::WWWHome); // E032
|
||||
//0x33
|
||||
//0x34
|
||||
scancode_set.extended[0x35] = Some(KeyCode::NumpadSlash); // E035
|
||||
//0x36
|
||||
//0x37
|
||||
scancode_set.extended[0x38] = Some(KeyCode::AltRight); // E038
|
||||
//0x39
|
||||
//0x3A
|
||||
//0x3B
|
||||
//0x3C
|
||||
//0x3D
|
||||
//0x3E
|
||||
//0x3F
|
||||
//0x40
|
||||
//0x41
|
||||
//0x42
|
||||
//0x43
|
||||
//0x44
|
||||
//0x45
|
||||
//0x46
|
||||
scancode_set.extended[0x47] = Some(KeyCode::Home); // E047
|
||||
scancode_set.extended[0x48] = Some(KeyCode::ArrowUp); // E048
|
||||
scancode_set.extended[0x49] = Some(KeyCode::PageUp); // E049
|
||||
//0x4A
|
||||
scancode_set.extended[0x4B] = Some(KeyCode::ArrowLeft); // E04B
|
||||
//0x4C
|
||||
scancode_set.extended[0x4D] = Some(KeyCode::ArrowRight); // E04D
|
||||
//0x4E
|
||||
scancode_set.extended[0x4F] = Some(KeyCode::End); // E04F
|
||||
scancode_set.extended[0x50] = Some(KeyCode::ArrowDown); // E050
|
||||
scancode_set.extended[0x51] = Some(KeyCode::PageDown); // E051
|
||||
scancode_set.extended[0x52] = Some(KeyCode::Insert); // E052
|
||||
scancode_set.extended[0x53] = Some(KeyCode::Delete); // E053
|
||||
for i in 0x90..=0xED {
|
||||
scancode_set.extended[i] = scancode_set.extended[i - 0x80];
|
||||
}
|
||||
scancode_set
|
||||
}
|
||||
pub fn scancode_set2() -> Self {
|
||||
Self {
|
||||
single_byte: [None; 256],
|
||||
extended: [None; 256],
|
||||
}
|
||||
}
|
||||
pub fn scancode_set1() -> Self {
|
||||
let mut scancode_set = Self {
|
||||
single_byte: [None; 256],
|
||||
extended: [None; 256],
|
||||
};
|
||||
scancode_set.single_byte[0x01] = Some(KeyCode::Escape); // 01
|
||||
scancode_set.single_byte[0x02] = Some(KeyCode::Key1); // 02
|
||||
scancode_set.single_byte[0x03] = Some(KeyCode::Key2); // 03
|
||||
scancode_set.single_byte[0x04] = Some(KeyCode::Key3); // 04
|
||||
scancode_set.single_byte[0x05] = Some(KeyCode::Key4); // 05
|
||||
scancode_set.single_byte[0x06] = Some(KeyCode::Key5); // 06
|
||||
scancode_set.single_byte[0x07] = Some(KeyCode::Key6); // 07
|
||||
scancode_set.single_byte[0x08] = Some(KeyCode::Key7); // 08
|
||||
scancode_set.single_byte[0x09] = Some(KeyCode::Key8); // 09
|
||||
scancode_set.single_byte[0x0A] = Some(KeyCode::Key9); // 0A
|
||||
scancode_set.single_byte[0x0B] = Some(KeyCode::Key0); // 0B
|
||||
scancode_set.single_byte[0x0C] = Some(KeyCode::Minus); // 0C
|
||||
scancode_set.single_byte[0x0D] = Some(KeyCode::Equals); // 0D
|
||||
scancode_set.single_byte[0x0E] = Some(KeyCode::Backspace); // 0E
|
||||
scancode_set.single_byte[0x0F] = Some(KeyCode::Tab); // 0F
|
||||
scancode_set.single_byte[0x10] = Some(KeyCode::Q); // 10
|
||||
scancode_set.single_byte[0x11] = Some(KeyCode::W); // 11
|
||||
scancode_set.single_byte[0x12] = Some(KeyCode::E); // 12
|
||||
scancode_set.single_byte[0x13] = Some(KeyCode::R); // 13
|
||||
scancode_set.single_byte[0x14] = Some(KeyCode::T); // 14
|
||||
scancode_set.single_byte[0x15] = Some(KeyCode::Y); // 15
|
||||
scancode_set.single_byte[0x16] = Some(KeyCode::U); // 16
|
||||
scancode_set.single_byte[0x17] = Some(KeyCode::I); // 17
|
||||
scancode_set.single_byte[0x18] = Some(KeyCode::O); // 18
|
||||
scancode_set.single_byte[0x19] = Some(KeyCode::P); // 19
|
||||
scancode_set.single_byte[0x1A] = Some(KeyCode::BracketSquareLeft); // 1A
|
||||
scancode_set.single_byte[0x1B] = Some(KeyCode::BracketSquareRight); // 1B
|
||||
scancode_set.single_byte[0x1C] = Some(KeyCode::Enter); // 1C
|
||||
scancode_set.single_byte[0x1D] = Some(KeyCode::ControlLeft); // 1D
|
||||
scancode_set.single_byte[0x1E] = Some(KeyCode::A); // 1E
|
||||
scancode_set.single_byte[0x1F] = Some(KeyCode::S); // 1F
|
||||
scancode_set.single_byte[0x20] = Some(KeyCode::D); // 20
|
||||
scancode_set.single_byte[0x21] = Some(KeyCode::F); // 21
|
||||
scancode_set.single_byte[0x22] = Some(KeyCode::G); // 22
|
||||
scancode_set.single_byte[0x23] = Some(KeyCode::H); // 23
|
||||
scancode_set.single_byte[0x24] = Some(KeyCode::J); // 24
|
||||
scancode_set.single_byte[0x25] = Some(KeyCode::K); // 25
|
||||
scancode_set.single_byte[0x26] = Some(KeyCode::L); // 26
|
||||
scancode_set.single_byte[0x27] = Some(KeyCode::SemiColon); // 27
|
||||
scancode_set.single_byte[0x28] = Some(KeyCode::Quote); // 28
|
||||
scancode_set.single_byte[0x29] = Some(KeyCode::BackTick); // 29
|
||||
scancode_set.single_byte[0x2A] = Some(KeyCode::ShiftLeft); // 2A
|
||||
scancode_set.single_byte[0x2B] = Some(KeyCode::BackSlash); // 2B
|
||||
scancode_set.single_byte[0x2C] = Some(KeyCode::Z); // 2C
|
||||
scancode_set.single_byte[0x2D] = Some(KeyCode::X); // 2D
|
||||
scancode_set.single_byte[0x2E] = Some(KeyCode::C); // 2E
|
||||
scancode_set.single_byte[0x2F] = Some(KeyCode::V); // 2F
|
||||
scancode_set.single_byte[0x30] = Some(KeyCode::B); // 30
|
||||
scancode_set.single_byte[0x31] = Some(KeyCode::N); // 31
|
||||
scancode_set.single_byte[0x32] = Some(KeyCode::M); // 32
|
||||
scancode_set.single_byte[0x33] = Some(KeyCode::Comma); // 33
|
||||
scancode_set.single_byte[0x34] = Some(KeyCode::Fullstop); // 34
|
||||
scancode_set.single_byte[0x35] = Some(KeyCode::Slash); // 35
|
||||
scancode_set.single_byte[0x36] = Some(KeyCode::ShiftRight); // 36
|
||||
scancode_set.single_byte[0x37] = Some(KeyCode::NumpadStar); // 37
|
||||
scancode_set.single_byte[0x38] = Some(KeyCode::AltLeft); // 38
|
||||
scancode_set.single_byte[0x39] = Some(KeyCode::Spacebar); // 39
|
||||
scancode_set.single_byte[0x3A] = Some(KeyCode::CapsLock); // 3A
|
||||
scancode_set.single_byte[0x3B] = Some(KeyCode::F1); // 3B
|
||||
scancode_set.single_byte[0x3C] = Some(KeyCode::F2); // 3C
|
||||
scancode_set.single_byte[0x3D] = Some(KeyCode::F3); // 3D
|
||||
scancode_set.single_byte[0x3E] = Some(KeyCode::F4); // 3E
|
||||
scancode_set.single_byte[0x3F] = Some(KeyCode::F5); // 3F
|
||||
scancode_set.single_byte[0x40] = Some(KeyCode::F6); // 40
|
||||
scancode_set.single_byte[0x41] = Some(KeyCode::F7); // 41
|
||||
scancode_set.single_byte[0x42] = Some(KeyCode::F8); // 42
|
||||
scancode_set.single_byte[0x43] = Some(KeyCode::F9); // 43
|
||||
scancode_set.single_byte[0x44] = Some(KeyCode::F10); // 44
|
||||
scancode_set.single_byte[0x45] = Some(KeyCode::NumpadLock); // 45
|
||||
scancode_set.single_byte[0x46] = Some(KeyCode::ScrollLock); // 46
|
||||
scancode_set.single_byte[0x47] = Some(KeyCode::Numpad7); // 47
|
||||
scancode_set.single_byte[0x48] = Some(KeyCode::Numpad8); // 48
|
||||
scancode_set.single_byte[0x49] = Some(KeyCode::Numpad9); // 49
|
||||
scancode_set.single_byte[0x4A] = Some(KeyCode::NumpadMinus); // 4A
|
||||
scancode_set.single_byte[0x4B] = Some(KeyCode::Numpad4); // 4B
|
||||
scancode_set.single_byte[0x4C] = Some(KeyCode::Numpad5); // 4C
|
||||
scancode_set.single_byte[0x4D] = Some(KeyCode::Numpad6); // 4D
|
||||
scancode_set.single_byte[0x4E] = Some(KeyCode::NumpadPlus); // 4E
|
||||
scancode_set.single_byte[0x4F] = Some(KeyCode::Numpad1); // 4F
|
||||
scancode_set.single_byte[0x50] = Some(KeyCode::Numpad2); // 50
|
||||
scancode_set.single_byte[0x51] = Some(KeyCode::Numpad3); // 51
|
||||
scancode_set.single_byte[0x52] = Some(KeyCode::Numpad0); // 52
|
||||
scancode_set.single_byte[0x53] = Some(KeyCode::NumpadPeriod); // 53
|
||||
// 0x54
|
||||
// 0x55
|
||||
// 0x56
|
||||
scancode_set.single_byte[0x57] = Some(KeyCode::F11); // 57
|
||||
scancode_set.single_byte[0x58] = Some(KeyCode::F12); // 58
|
||||
for i in 0x81..=0xD8 {
|
||||
scancode_set.single_byte[i] = scancode_set.single_byte[i - 0x80];
|
||||
}
|
||||
scancode_set.extended[0x10] = Some(KeyCode::PrevTrack); // E010
|
||||
//0x11
|
||||
//0x12
|
||||
//0x13
|
||||
//0x14
|
||||
//0x15
|
||||
//0x16
|
||||
//0x17
|
||||
//0x18
|
||||
scancode_set.extended[0x19] = Some(KeyCode::NextTrack); // E019
|
||||
//0x1A
|
||||
//0x1B
|
||||
scancode_set.extended[0x1C] = Some(KeyCode::NumpadEnter); // E01C
|
||||
scancode_set.extended[0x1D] = Some(KeyCode::ControlRight); // E01D
|
||||
//0x1E
|
||||
//0x1F
|
||||
scancode_set.extended[0x20] = Some(KeyCode::Mute); // E020
|
||||
scancode_set.extended[0x21] = Some(KeyCode::Calculator); // E021
|
||||
scancode_set.extended[0x22] = Some(KeyCode::Play); // E022
|
||||
//0x23
|
||||
scancode_set.extended[0x24] = Some(KeyCode::Stop); // E024
|
||||
//0x25
|
||||
//0x26
|
||||
//0x27
|
||||
//0x28
|
||||
//0x29
|
||||
//0x2A
|
||||
//0x2B
|
||||
//0x2C
|
||||
//0x2D
|
||||
scancode_set.extended[0x2E] = Some(KeyCode::VolumeDown); // E02E
|
||||
//0x2F
|
||||
scancode_set.extended[0x30] = Some(KeyCode::VolumeUp); // E030
|
||||
//0x31
|
||||
scancode_set.extended[0x32] = Some(KeyCode::WWWHome); // E032
|
||||
//0x33
|
||||
//0x34
|
||||
scancode_set.extended[0x35] = Some(KeyCode::NumpadSlash); // E035
|
||||
//0x36
|
||||
//0x37
|
||||
scancode_set.extended[0x38] = Some(KeyCode::AltRight); // E038
|
||||
//0x39
|
||||
//0x3A
|
||||
//0x3B
|
||||
//0x3C
|
||||
//0x3D
|
||||
//0x3E
|
||||
//0x3F
|
||||
//0x40
|
||||
//0x41
|
||||
//0x42
|
||||
//0x43
|
||||
//0x44
|
||||
//0x45
|
||||
//0x46
|
||||
scancode_set.extended[0x47] = Some(KeyCode::Home); // E047
|
||||
scancode_set.extended[0x48] = Some(KeyCode::ArrowUp); // E048
|
||||
scancode_set.extended[0x49] = Some(KeyCode::PageUp); // E049
|
||||
//0x4A
|
||||
scancode_set.extended[0x4B] = Some(KeyCode::ArrowLeft); // E04B
|
||||
//0x4C
|
||||
scancode_set.extended[0x4D] = Some(KeyCode::ArrowRight); // E04D
|
||||
//0x4E
|
||||
scancode_set.extended[0x4F] = Some(KeyCode::End); // E04F
|
||||
scancode_set.extended[0x50] = Some(KeyCode::ArrowDown); // E050
|
||||
scancode_set.extended[0x51] = Some(KeyCode::PageDown); // E051
|
||||
scancode_set.extended[0x52] = Some(KeyCode::Insert); // E052
|
||||
scancode_set.extended[0x53] = Some(KeyCode::Delete); // E053
|
||||
for i in 0x90..=0xED {
|
||||
scancode_set.extended[i] = scancode_set.extended[i - 0x80];
|
||||
}
|
||||
scancode_set
|
||||
}
|
||||
pub fn scancode_set2() -> Self {
|
||||
Self {
|
||||
single_byte: [None; 256],
|
||||
extended: [None; 256],
|
||||
}
|
||||
}
|
||||
}
|
||||
impl ScancodeSet for CustomScancodeSet {
|
||||
fn advance_state(&self, state: &mut DecodeState, code: u8) -> Result<Option<KeyEvent>, Error> {
|
||||
match *state {
|
||||
DecodeState::Start => {
|
||||
match code {
|
||||
EXTENDED_KEY_CODE => {
|
||||
*state = DecodeState::Extended;
|
||||
Ok(None)
|
||||
}
|
||||
0x80..=0xFF => {
|
||||
// Release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_scancode(code - 0x80)?,
|
||||
KeyState::Up,
|
||||
)))
|
||||
}
|
||||
_ => {
|
||||
// Normal codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_scancode(code)?,
|
||||
KeyState::Down,
|
||||
)))
|
||||
}
|
||||
fn advance_state(&self, state: &mut DecodeState, code: u8) -> Result<Option<KeyEvent>, Error> {
|
||||
match *state {
|
||||
DecodeState::Start => {
|
||||
match code {
|
||||
EXTENDED_KEY_CODE => {
|
||||
*state = DecodeState::Extended;
|
||||
Ok(None)
|
||||
}
|
||||
0x80..=0xFF => {
|
||||
// Release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_scancode(code - 0x80)?,
|
||||
KeyState::Up,
|
||||
)))
|
||||
}
|
||||
_ => {
|
||||
// Normal codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_scancode(code)?,
|
||||
KeyState::Down,
|
||||
)))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
DecodeState::Extended => {
|
||||
*state = DecodeState::Start;
|
||||
match code {
|
||||
0x80..=0xFF => {
|
||||
// Extended Release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_extended_scancode(code - 0x80)?,
|
||||
KeyState::Up,
|
||||
)))
|
||||
}
|
||||
_ => {
|
||||
// Normal release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_extended_scancode(code)?,
|
||||
KeyState::Down,
|
||||
)))
|
||||
}
|
||||
DecodeState::Extended => {
|
||||
*state = DecodeState::Start;
|
||||
match code {
|
||||
0x80..=0xFF => {
|
||||
// Extended Release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_extended_scancode(code - 0x80)?,
|
||||
KeyState::Up,
|
||||
)))
|
||||
}
|
||||
_ => {
|
||||
// Normal release codes
|
||||
Ok(Some(KeyEvent::new(
|
||||
self.map_extended_scancode(code)?,
|
||||
KeyState::Down,
|
||||
)))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_ => {
|
||||
// Can't get in to this state
|
||||
unimplemented!();
|
||||
}
|
||||
}
|
||||
}
|
||||
fn map_scancode(&self, code: u8) -> Result<KeyCode, Error> {
|
||||
if let Some(kc) = self.single_byte[code as usize] {
|
||||
Ok(kc)
|
||||
} else {
|
||||
Err(Error::UnknownKeyCode)
|
||||
}
|
||||
}
|
||||
fn map_extended_scancode(&self, code: u8) -> Result<KeyCode, Error> {
|
||||
if let Some(kc) = self.extended[code as usize] {
|
||||
Ok(kc)
|
||||
} else {
|
||||
Err(Error::UnknownKeyCode)
|
||||
}
|
||||
}
|
||||
}
|
||||
_ => {
|
||||
// Can't get in to this state
|
||||
unimplemented!();
|
||||
}
|
||||
}
|
||||
}
|
||||
fn map_scancode(&self, code: u8) -> Result<KeyCode, Error> {
|
||||
if let Some(kc) = self.single_byte[code as usize] {
|
||||
Ok(kc)
|
||||
} else {
|
||||
Err(Error::UnknownKeyCode)
|
||||
}
|
||||
}
|
||||
fn map_extended_scancode(&self, code: u8) -> Result<KeyCode, Error> {
|
||||
if let Some(kc) = self.extended[code as usize] {
|
||||
Ok(kc)
|
||||
} else {
|
||||
Err(Error::UnknownKeyCode)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,104 +2,102 @@ use super::DecodedKey;
|
|||
|
||||
#[derive(Debug, Clone, Copy)]
|
||||
pub enum LayoutEntryKind {
|
||||
Regular,
|
||||
Numlockable,
|
||||
Capslockable,
|
||||
Regular,
|
||||
Numlockable,
|
||||
Capslockable,
|
||||
}
|
||||
|
||||
impl Default for LayoutEntryKind {
|
||||
fn default() -> Self {
|
||||
Self::Regular
|
||||
}
|
||||
fn default() -> Self {
|
||||
Self::Regular
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Copy, Default)]
|
||||
pub struct LayoutEntry {
|
||||
pub kind: LayoutEntryKind,
|
||||
pub unshifted: Option<DecodedKey>,
|
||||
pub shifted: Option<DecodedKey>,
|
||||
pub locked: Option<DecodedKey>,
|
||||
pub locked_shifted: Option<DecodedKey>,
|
||||
pub altgr: Option<DecodedKey>,
|
||||
pub raw_unicode: Option<DecodedKey>,
|
||||
pub kind: LayoutEntryKind,
|
||||
pub unshifted: Option<DecodedKey>,
|
||||
pub shifted: Option<DecodedKey>,
|
||||
pub locked: Option<DecodedKey>,
|
||||
pub locked_shifted: Option<DecodedKey>,
|
||||
pub altgr: Option<DecodedKey>,
|
||||
pub raw_unicode: Option<DecodedKey>,
|
||||
}
|
||||
|
||||
impl LayoutEntry {
|
||||
#[must_use]
|
||||
pub fn regular() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Regular,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn numpad() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Numlockable,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn alphabet() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Capslockable,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn unshifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.unshifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn shifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.shifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn altgr(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.altgr = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn raw_unicode(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.raw_unicode = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn locked(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.locked = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn locked_shifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.locked_shifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn common(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self
|
||||
.unshifted(c.clone())
|
||||
.shifted(c.clone())
|
||||
.locked(c.clone())
|
||||
.locked_shifted(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn low(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.unshifted(c.clone()).locked_shifted(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn high(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.shifted(c.clone()).locked(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn all(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self
|
||||
.unshifted(c.clone())
|
||||
.shifted(c.clone())
|
||||
.locked(c.clone())
|
||||
.locked_shifted(c.clone())
|
||||
.altgr(c.clone())
|
||||
.raw_unicode(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn regular() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Regular,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn numpad() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Numlockable,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn alphabet() -> Self {
|
||||
Self {
|
||||
kind: LayoutEntryKind::Capslockable,
|
||||
..Default::default()
|
||||
}
|
||||
}
|
||||
#[must_use]
|
||||
pub fn unshifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.unshifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn shifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.shifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn altgr(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.altgr = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn raw_unicode(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.raw_unicode = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn locked(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.locked = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn locked_shifted(mut self, c: impl Into<DecodedKey>) -> Self {
|
||||
self.locked_shifted = Some(c.into());
|
||||
self
|
||||
}
|
||||
#[must_use]
|
||||
pub fn common(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.unshifted(c.clone())
|
||||
.shifted(c.clone())
|
||||
.locked(c.clone())
|
||||
.locked_shifted(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn low(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.unshifted(c.clone()).locked_shifted(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn high(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.shifted(c.clone()).locked(c)
|
||||
}
|
||||
#[must_use]
|
||||
pub fn all(self, c: impl Into<DecodedKey> + Clone) -> Self {
|
||||
self.unshifted(c.clone())
|
||||
.shifted(c.clone())
|
||||
.locked(c.clone())
|
||||
.locked_shifted(c.clone())
|
||||
.altgr(c.clone())
|
||||
.raw_unicode(c)
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,111 +1,111 @@
|
|||
#![allow(non_snake_case)]
|
||||
#[derive(Debug)]
|
||||
pub struct Modifiers {
|
||||
pub lshift: bool,
|
||||
pub rshift: bool,
|
||||
pub lctrl: bool,
|
||||
pub rctrl: bool,
|
||||
pub numlock: bool,
|
||||
pub capslock: bool,
|
||||
pub alt_gr: bool,
|
||||
pub lshift: bool,
|
||||
pub rshift: bool,
|
||||
pub lctrl: bool,
|
||||
pub rctrl: bool,
|
||||
pub numlock: bool,
|
||||
pub capslock: bool,
|
||||
pub alt_gr: bool,
|
||||
}
|
||||
impl Modifiers {
|
||||
pub fn is_shifted(&self) -> bool {
|
||||
self.lshift | self.rshift
|
||||
}
|
||||
pub fn is_ctrl(&self) -> bool {
|
||||
self.lctrl | self.rctrl
|
||||
}
|
||||
pub fn is_caps(&self) -> bool {
|
||||
self.capslock
|
||||
}
|
||||
pub fn is_shifted(&self) -> bool {
|
||||
self.lshift | self.rshift
|
||||
}
|
||||
pub fn is_ctrl(&self) -> bool {
|
||||
self.lctrl | self.rctrl
|
||||
}
|
||||
pub fn is_caps(&self) -> bool {
|
||||
self.capslock
|
||||
}
|
||||
}
|
||||
#[derive(Debug, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum KeyState {
|
||||
Up,
|
||||
Down,
|
||||
Up,
|
||||
Down,
|
||||
}
|
||||
#[derive(Debug, PartialEq, Eq, Clone)]
|
||||
pub struct KeyEvent {
|
||||
pub code: KeyCode,
|
||||
pub state: KeyState,
|
||||
pub code: KeyCode,
|
||||
pub state: KeyState,
|
||||
}
|
||||
impl KeyEvent {
|
||||
pub fn new(code: KeyCode, state: KeyState) -> KeyEvent {
|
||||
KeyEvent { code, state }
|
||||
}
|
||||
pub fn new(code: KeyCode, state: KeyState) -> KeyEvent {
|
||||
KeyEvent { code, state }
|
||||
}
|
||||
}
|
||||
#[derive(Debug, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum HandleControl {
|
||||
/// If either Ctrl key is held down, convert the letters A through Z into
|
||||
/// Unicode chars U+0001 through U+001A. If the Ctrl keys are not held
|
||||
/// down, letters go through normally.
|
||||
MapLettersToUnicode,
|
||||
/// Don't do anything special - send through the Ctrl key up/down events,
|
||||
/// and leave the letters as letters.
|
||||
Ignore,
|
||||
/// If either Ctrl key is held down, convert the letters A through Z into
|
||||
/// Unicode chars U+0001 through U+001A. If the Ctrl keys are not held
|
||||
/// down, letters go through normally.
|
||||
MapLettersToUnicode,
|
||||
/// Don't do anything special - send through the Ctrl key up/down events,
|
||||
/// and leave the letters as letters.
|
||||
Ignore,
|
||||
}
|
||||
#[derive(Debug, Copy, Clone, Eq, PartialEq)]
|
||||
pub enum DecodeState {
|
||||
Start,
|
||||
Extended,
|
||||
Release,
|
||||
ExtendedRelease,
|
||||
Start,
|
||||
Extended,
|
||||
Release,
|
||||
ExtendedRelease,
|
||||
}
|
||||
/// Indicates different error conditions.
|
||||
#[derive(Debug, PartialEq, Eq, Copy, Clone)]
|
||||
pub enum Error {
|
||||
BadStartBit,
|
||||
BadStopBit,
|
||||
ParityError,
|
||||
UnknownKeyCode,
|
||||
InvalidState,
|
||||
BadStartBit,
|
||||
BadStopBit,
|
||||
ParityError,
|
||||
UnknownKeyCode,
|
||||
InvalidState,
|
||||
}
|
||||
#[derive(Debug, PartialEq, Eq, Copy, Clone)]
|
||||
#[repr(u8)]
|
||||
pub enum DecodedKeyKind {
|
||||
RawKey = 0,
|
||||
Unicode = 1,
|
||||
RawKey = 0,
|
||||
Unicode = 1,
|
||||
}
|
||||
#[derive(Debug, PartialEq, Eq, Copy, Clone)]
|
||||
#[repr(C)]
|
||||
pub struct DecodedKey {
|
||||
pub kind: DecodedKeyKind,
|
||||
pub value: u32,
|
||||
pub kind: DecodedKeyKind,
|
||||
pub value: u32,
|
||||
}
|
||||
impl From<char> for DecodedKey {
|
||||
fn from(ch: char) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: ch as u32,
|
||||
}
|
||||
}
|
||||
fn from(ch: char) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: ch as u32,
|
||||
}
|
||||
}
|
||||
}
|
||||
impl From<KeyCode> for DecodedKey {
|
||||
fn from(kc: KeyCode) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::RawKey,
|
||||
value: kc as u32,
|
||||
}
|
||||
}
|
||||
fn from(kc: KeyCode) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::RawKey,
|
||||
value: kc as u32,
|
||||
}
|
||||
}
|
||||
}
|
||||
impl DecodedKey {
|
||||
pub const ZERO: Self = Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: 0,
|
||||
};
|
||||
pub fn Unicode(ch: char) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: ch.into(),
|
||||
}
|
||||
}
|
||||
pub fn RawKey(byte: u8) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::RawKey,
|
||||
value: byte.into(),
|
||||
}
|
||||
}
|
||||
pub const ZERO: Self = Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: 0,
|
||||
};
|
||||
pub fn Unicode(ch: char) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::Unicode,
|
||||
value: ch.into(),
|
||||
}
|
||||
}
|
||||
pub fn RawKey(byte: u8) -> Self {
|
||||
Self {
|
||||
kind: DecodedKeyKind::RawKey,
|
||||
value: byte.into(),
|
||||
}
|
||||
}
|
||||
}
|
||||
macro_rules! keycode_enum {
|
||||
(@get_last $Variant:ident) => {
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
use alloc::{boxed::Box};
|
||||
|
||||
use alloc::boxed::Box;
|
||||
|
||||
pub struct BinCodeWriter {
|
||||
pub stream: Box<u8>,
|
||||
|
|
|
@ -1,20 +1,20 @@
|
|||
pub struct Time {
|
||||
pub year: u16,
|
||||
pub month: u16,
|
||||
pub day: u16,
|
||||
pub hour: u16,
|
||||
pub minutes: u16,
|
||||
pub seconds: u16,
|
||||
pub microseconds: u32,
|
||||
pub year: u16,
|
||||
pub month: u16,
|
||||
pub day: u16,
|
||||
pub hour: u16,
|
||||
pub minutes: u16,
|
||||
pub seconds: u16,
|
||||
pub microseconds: u32,
|
||||
}
|
||||
impl fmt::Display for Time {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"{:?}/{:?}/{:?} {:02}:{:02}:{:02}",
|
||||
self.year, self.month, self.day, self.hour, self.minutes, self.seconds
|
||||
)
|
||||
}
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
write!(
|
||||
f,
|
||||
"{:?}/{:?}/{:?} {:02}:{:02}:{:02}",
|
||||
self.year, self.month, self.day, self.hour, self.minutes, self.seconds
|
||||
)
|
||||
}
|
||||
}
|
||||
pub mod kilotime;
|
||||
use core::fmt;
|
||||
|
|
|
@ -3,11 +3,11 @@ use shadeable::pixel_format::Rgba64;
|
|||
use crate::SCREEN_BUFFER;
|
||||
|
||||
use {
|
||||
ab_glyph::{Font, FontRef, Glyph},
|
||||
vga::{
|
||||
colors::Color16,
|
||||
writers::{Graphics640x480x16, GraphicsWriter},
|
||||
},
|
||||
ab_glyph::{Font, FontRef, Glyph},
|
||||
vga::{
|
||||
colors::Color16,
|
||||
writers::{Graphics640x480x16, GraphicsWriter},
|
||||
},
|
||||
};
|
||||
|
||||
lazy_static::lazy_static! {
|
||||
|
@ -20,28 +20,27 @@ lazy_static::lazy_static! {
|
|||
pub static ref VGAE_BUFF_OFFSET_Y: spin::Mutex<u8> = spin::Mutex::new(0);
|
||||
}
|
||||
|
||||
|
||||
/// Converts a number to ... i forgor 💀
|
||||
pub fn num_to_vga16(num: u8) -> Color16 {
|
||||
use Color16::*;
|
||||
match num {
|
||||
0 => Black,
|
||||
1 => Blue,
|
||||
2 => Green,
|
||||
3 => Cyan,
|
||||
4 => Red,
|
||||
5 => Magenta,
|
||||
6 => Brown,
|
||||
7 => LightGrey,
|
||||
8 => DarkGrey,
|
||||
9 => LightBlue,
|
||||
10 => LightGreen,
|
||||
11 => LightCyan,
|
||||
12 => LightRed,
|
||||
13 => Pink,
|
||||
14 => Yellow,
|
||||
15 => White,
|
||||
// NOTE: Leasve the in
|
||||
_ => Color16::Pink,
|
||||
}
|
||||
use Color16::*;
|
||||
match num {
|
||||
0 => Black,
|
||||
1 => Blue,
|
||||
2 => Green,
|
||||
3 => Cyan,
|
||||
4 => Red,
|
||||
5 => Magenta,
|
||||
6 => Brown,
|
||||
7 => LightGrey,
|
||||
8 => DarkGrey,
|
||||
9 => LightBlue,
|
||||
10 => LightGreen,
|
||||
11 => LightCyan,
|
||||
12 => LightRed,
|
||||
13 => Pink,
|
||||
14 => Yellow,
|
||||
15 => White,
|
||||
// NOTE: Leasve the in
|
||||
_ => Color16::Pink,
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4,46 +4,46 @@ use clap::Parser;
|
|||
#[clap(version = clap::crate_version!(), author = clap::crate_authors!("\n"))]
|
||||
/// Hello Remember this is a feature
|
||||
enum Command {
|
||||
Run {
|
||||
#[clap(long, short)]
|
||||
debug: bool,
|
||||
Run {
|
||||
#[clap(long, short)]
|
||||
debug: bool,
|
||||
|
||||
#[clap(long, short, arg_enum)]
|
||||
machine: Option<MachineType>,
|
||||
},
|
||||
#[clap(long, short, arg_enum)]
|
||||
machine: Option<MachineType>,
|
||||
},
|
||||
|
||||
Doc {
|
||||
#[clap(long, short, arg_enum)]
|
||||
machine: Option<MachineType>,
|
||||
},
|
||||
Doc {
|
||||
#[clap(long, short, arg_enum)]
|
||||
machine: Option<MachineType>,
|
||||
},
|
||||
}
|
||||
|
||||
#[derive(clap::ArgEnum, Debug, Clone)]
|
||||
enum MachineType {
|
||||
X86,
|
||||
RISCV,
|
||||
ARM,
|
||||
X86,
|
||||
RISCV,
|
||||
ARM,
|
||||
}
|
||||
|
||||
fn main() -> anyhow::Result<()> {
|
||||
let args = Command::parse();
|
||||
let args = Command::parse();
|
||||
|
||||
match args {
|
||||
Command::Run { debug, machine } => {
|
||||
let _dir = xshell::pushd("./ableos");
|
||||
match args {
|
||||
Command::Run { debug, machine } => {
|
||||
let _dir = xshell::pushd("./ableos");
|
||||
|
||||
let _debug_log: &[&str] = match debug {
|
||||
true => &["-D", "debug.log"],
|
||||
false => &[],
|
||||
};
|
||||
match machine.unwrap_or(MachineType::X86) {
|
||||
MachineType::X86 => {
|
||||
xshell::cmd!("cargo run --release").run()?;
|
||||
}
|
||||
MachineType::ARM => {
|
||||
xshell::cmd!("cargo build --release --target=json_targets/aarch64-ableos.json")
|
||||
.run()?;
|
||||
#[rustfmt::skip]
|
||||
let _debug_log: &[&str] = match debug {
|
||||
true => &["-D", "debug.log"],
|
||||
false => &[],
|
||||
};
|
||||
match machine.unwrap_or(MachineType::X86) {
|
||||
MachineType::X86 => {
|
||||
xshell::cmd!("cargo run --release").run()?;
|
||||
}
|
||||
MachineType::ARM => {
|
||||
xshell::cmd!("cargo build --release --target=json_targets/aarch64-ableos.json")
|
||||
.run()?;
|
||||
#[rustfmt::skip]
|
||||
xshell::cmd!(
|
||||
"qemu-system-aarch64
|
||||
-machine virt
|
||||
|
@ -53,10 +53,11 @@ fn main() -> anyhow::Result<()> {
|
|||
-device virtio-keyboard
|
||||
"
|
||||
).run()?;
|
||||
}
|
||||
MachineType::RISCV => {
|
||||
xshell::cmd!("cargo build --release --target=riscv64gc-unknown-none-elf").run()?;
|
||||
#[rustfmt::skip]
|
||||
}
|
||||
MachineType::RISCV => {
|
||||
xshell::cmd!("cargo build --release --target=riscv64gc-unknown-none-elf")
|
||||
.run()?;
|
||||
#[rustfmt::skip]
|
||||
xshell::cmd!(
|
||||
"qemu-system-riscv64
|
||||
-machine virt
|
||||
|
@ -66,26 +67,27 @@ fn main() -> anyhow::Result<()> {
|
|||
-bios src/arch/riscv/firmwear/opensbi-riscv64-generic-fw_jump.bin
|
||||
-kernel target/riscv64gc-unknown-none-elf/release/ableos"
|
||||
).run()?;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Command::Doc { machine } => {
|
||||
let _dir = xshell::pushd("./ableos");
|
||||
Command::Doc { machine } => {
|
||||
let _dir = xshell::pushd("./ableos");
|
||||
|
||||
match machine.unwrap_or(MachineType::X86) {
|
||||
MachineType::X86 => {
|
||||
xshell::cmd!("cargo doc --open").run()?;
|
||||
match machine.unwrap_or(MachineType::X86) {
|
||||
MachineType::X86 => {
|
||||
xshell::cmd!("cargo doc --open").run()?;
|
||||
}
|
||||
MachineType::ARM => {
|
||||
xshell::cmd!("cargo doc --open --target=json_targets/aarch64-ableos.json")
|
||||
.run()?;
|
||||
}
|
||||
MachineType::RISCV => {
|
||||
xshell::cmd!("cargo doc --open --target=riscv64gc-unknown-none-elf").run()?;
|
||||
}
|
||||
}
|
||||
MachineType::ARM => {
|
||||
xshell::cmd!("cargo doc --open --target=json_targets/aarch64-ableos.json").run()?;
|
||||
}
|
||||
MachineType::RISCV => {
|
||||
xshell::cmd!("cargo doc --open --target=riscv64gc-unknown-none-elf").run()?;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Ok(())
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -4,167 +4,164 @@ use vga::colors::Color16;
|
|||
pub type Rgba64 = u64;
|
||||
|
||||
pub fn get_r(rgba: Rgba64) -> u8 {
|
||||
rgba.bitand(0xff_00_00_00).shr(0o30) as u8
|
||||
rgba.bitand(0xff_00_00_00).shr(0o30) as u8
|
||||
}
|
||||
pub fn get_g(rgba: Rgba64) -> u8 {
|
||||
rgba.bitand(0xff_00_00).shr(0o20) as u8
|
||||
rgba.bitand(0xff_00_00).shr(0o20) as u8
|
||||
}
|
||||
|
||||
pub fn get_b(rgba: Rgba64) -> u8 {
|
||||
rgba.bitand(0xff_00).shr(0o10) as u8
|
||||
rgba.bitand(0xff_00).shr(0o10) as u8
|
||||
}
|
||||
|
||||
pub fn get_a(rgba: Rgba64) -> u8 {
|
||||
(rgba & 0xff) as u8
|
||||
(rgba & 0xff) as u8
|
||||
}
|
||||
|
||||
pub fn set_r(rgba: Rgba64, r: u8) -> Rgba64 {
|
||||
rgba
|
||||
.bitand(0xffffffff_00_ff_ff_ff)
|
||||
.bitor((r as Rgba64).shr(0o30))
|
||||
rgba.bitand(0xffffffff_00_ff_ff_ff)
|
||||
.bitor((r as Rgba64).shr(0o30))
|
||||
}
|
||||
|
||||
pub fn set_g(rgba: Rgba64, g: u8) -> Rgba64 {
|
||||
rgba
|
||||
.bitand(0xffffffff_ff_00_ff_ff)
|
||||
.bitor((g as Rgba64).shr(0o20))
|
||||
rgba.bitand(0xffffffff_ff_00_ff_ff)
|
||||
.bitor((g as Rgba64).shr(0o20))
|
||||
}
|
||||
|
||||
pub fn set_b(rgba: Rgba64, b: u8) -> Rgba64 {
|
||||
rgba
|
||||
.bitand(0xffffffff_ff_ff_00_ff)
|
||||
.bitor((b as Rgba64).shr(0o10))
|
||||
rgba.bitand(0xffffffff_ff_ff_00_ff)
|
||||
.bitor((b as Rgba64).shr(0o10))
|
||||
}
|
||||
|
||||
pub fn set_a(rgba: Rgba64, a: u8) -> Rgba64 {
|
||||
rgba.bitand(0xffffffff_ff_ff_ff_00).bitor(a as Rgba64)
|
||||
rgba.bitand(0xffffffff_ff_ff_ff_00).bitor(a as Rgba64)
|
||||
}
|
||||
|
||||
pub fn rgba_div(a: Rgba64, b: Rgba64) -> Rgba64 {
|
||||
set_r(0, get_r(a) / get_r(b))
|
||||
| set_g(0, get_g(a) / get_g(b))
|
||||
| set_g(0, get_b(a) / get_b(b))
|
||||
| set_g(0, get_a(a) / get_a(b))
|
||||
set_r(0, get_r(a) / get_r(b))
|
||||
| set_g(0, get_g(a) / get_g(b))
|
||||
| set_g(0, get_b(a) / get_b(b))
|
||||
| set_g(0, get_a(a) / get_a(b))
|
||||
}
|
||||
|
||||
pub fn new_rgba64(r: u8, g: u8, b: u8, a: u8) -> Rgba64 {
|
||||
set_r(0, r) | set_g(0, g) | set_b(0, b) | set_a(0, a)
|
||||
set_r(0, r) | set_g(0, g) | set_b(0, b) | set_a(0, a)
|
||||
}
|
||||
|
||||
enum ChannelValue {
|
||||
Dark,
|
||||
Low,
|
||||
Mid,
|
||||
High,
|
||||
Dark,
|
||||
Low,
|
||||
Mid,
|
||||
High,
|
||||
}
|
||||
|
||||
impl From<u8> for ChannelValue {
|
||||
fn from(b: u8) -> Self {
|
||||
use ChannelValue::*;
|
||||
match b {
|
||||
0x00..=0x3f => Dark,
|
||||
0x40..=0x7f => Low,
|
||||
0x80..=0xbf => Mid,
|
||||
0xc0..=0xff => High,
|
||||
}
|
||||
}
|
||||
fn from(b: u8) -> Self {
|
||||
use ChannelValue::*;
|
||||
match b {
|
||||
0x00..=0x3f => Dark,
|
||||
0x40..=0x7f => Low,
|
||||
0x80..=0xbf => Mid,
|
||||
0xc0..=0xff => High,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn into_vga_16(rgba_64: Rgba64) -> Color16 {
|
||||
use ChannelValue::*;
|
||||
use Color16::*;
|
||||
match (
|
||||
get_r(rgba_64).into(),
|
||||
get_g(rgba_64).into(),
|
||||
get_b(rgba_64).into(),
|
||||
) {
|
||||
(Dark, Dark, Dark) => Black,
|
||||
(Dark, Dark, Low) => Black,
|
||||
(Dark, Dark, Mid) => Blue,
|
||||
(Dark, Dark, High) => Blue,
|
||||
(Dark, Low, Dark) => Black,
|
||||
(Dark, Low, Low) => Black,
|
||||
(Dark, Low, Mid) => Blue,
|
||||
(Dark, Low, High) => Blue,
|
||||
(Dark, Mid, Dark) => Green,
|
||||
(Dark, Mid, Low) => Green,
|
||||
(Dark, Mid, Mid) => Cyan,
|
||||
(Dark, Mid, High) => Cyan,
|
||||
(Dark, High, Dark) => Green,
|
||||
(Dark, High, Low) => Green,
|
||||
(Dark, High, Mid) => Green,
|
||||
(Dark, High, High) => Cyan,
|
||||
(Low, Dark, Dark) => Black,
|
||||
(Low, Dark, Low) => Black,
|
||||
(Low, Dark, Mid) => Blue,
|
||||
(Low, Dark, High) => Blue,
|
||||
(Low, Low, Dark) => Black,
|
||||
(Low, Low, Low) => DarkGrey,
|
||||
(Low, Low, Mid) => LightGrey,
|
||||
(Low, Low, High) => Blue,
|
||||
(Low, Mid, Dark) => DarkGrey,
|
||||
(Low, Mid, Low) => LightGrey,
|
||||
(Low, Mid, Mid) => Cyan,
|
||||
(Low, Mid, High) => Cyan,
|
||||
(Low, High, Dark) => Green,
|
||||
(Low, High, Low) => Green,
|
||||
(Low, High, Mid) => Cyan,
|
||||
(Low, High, High) => Cyan,
|
||||
(Mid, Dark, Dark) => Red,
|
||||
(Mid, Dark, Low) => Red,
|
||||
(Mid, Dark, Mid) => Magenta,
|
||||
(Mid, Dark, High) => Magenta,
|
||||
(Mid, Low, Dark) => Brown,
|
||||
(Mid, Low, Low) => Red,
|
||||
(Mid, Low, Mid) => DarkGrey,
|
||||
(Mid, Low, High) => LightBlue,
|
||||
(Mid, Mid, Dark) => Brown,
|
||||
(Mid, Mid, Low) => Brown,
|
||||
(Mid, Mid, Mid) => LightGrey,
|
||||
(Mid, Mid, High) => LightBlue,
|
||||
(Mid, High, Dark) => Green,
|
||||
(Mid, High, Low) => Green,
|
||||
(Mid, High, Mid) => LightGreen,
|
||||
(Mid, High, High) => LightCyan,
|
||||
(High, Dark, Dark) => Red,
|
||||
(High, Dark, _) => Magenta,
|
||||
(High, Low, Dark) => Red,
|
||||
(High, Low, Low) => LightRed,
|
||||
(High, Low, Mid) => Pink,
|
||||
(High, Low, High) => Magenta,
|
||||
(High, Mid, Dark) => Yellow,
|
||||
(High, Mid, Low) => Yellow,
|
||||
(High, Mid, Mid) => LightRed,
|
||||
(High, Mid, High) => Pink,
|
||||
(High, High, Dark) => Yellow,
|
||||
(High, High, Low) => White,
|
||||
(High, High, Mid) => White,
|
||||
(High, High, High) => White,
|
||||
}
|
||||
use ChannelValue::*;
|
||||
use Color16::*;
|
||||
match (
|
||||
get_r(rgba_64).into(),
|
||||
get_g(rgba_64).into(),
|
||||
get_b(rgba_64).into(),
|
||||
) {
|
||||
(Dark, Dark, Dark) => Black,
|
||||
(Dark, Dark, Low) => Black,
|
||||
(Dark, Dark, Mid) => Blue,
|
||||
(Dark, Dark, High) => Blue,
|
||||
(Dark, Low, Dark) => Black,
|
||||
(Dark, Low, Low) => Black,
|
||||
(Dark, Low, Mid) => Blue,
|
||||
(Dark, Low, High) => Blue,
|
||||
(Dark, Mid, Dark) => Green,
|
||||
(Dark, Mid, Low) => Green,
|
||||
(Dark, Mid, Mid) => Cyan,
|
||||
(Dark, Mid, High) => Cyan,
|
||||
(Dark, High, Dark) => Green,
|
||||
(Dark, High, Low) => Green,
|
||||
(Dark, High, Mid) => Green,
|
||||
(Dark, High, High) => Cyan,
|
||||
(Low, Dark, Dark) => Black,
|
||||
(Low, Dark, Low) => Black,
|
||||
(Low, Dark, Mid) => Blue,
|
||||
(Low, Dark, High) => Blue,
|
||||
(Low, Low, Dark) => Black,
|
||||
(Low, Low, Low) => DarkGrey,
|
||||
(Low, Low, Mid) => LightGrey,
|
||||
(Low, Low, High) => Blue,
|
||||
(Low, Mid, Dark) => DarkGrey,
|
||||
(Low, Mid, Low) => LightGrey,
|
||||
(Low, Mid, Mid) => Cyan,
|
||||
(Low, Mid, High) => Cyan,
|
||||
(Low, High, Dark) => Green,
|
||||
(Low, High, Low) => Green,
|
||||
(Low, High, Mid) => Cyan,
|
||||
(Low, High, High) => Cyan,
|
||||
(Mid, Dark, Dark) => Red,
|
||||
(Mid, Dark, Low) => Red,
|
||||
(Mid, Dark, Mid) => Magenta,
|
||||
(Mid, Dark, High) => Magenta,
|
||||
(Mid, Low, Dark) => Brown,
|
||||
(Mid, Low, Low) => Red,
|
||||
(Mid, Low, Mid) => DarkGrey,
|
||||
(Mid, Low, High) => LightBlue,
|
||||
(Mid, Mid, Dark) => Brown,
|
||||
(Mid, Mid, Low) => Brown,
|
||||
(Mid, Mid, Mid) => LightGrey,
|
||||
(Mid, Mid, High) => LightBlue,
|
||||
(Mid, High, Dark) => Green,
|
||||
(Mid, High, Low) => Green,
|
||||
(Mid, High, Mid) => LightGreen,
|
||||
(Mid, High, High) => LightCyan,
|
||||
(High, Dark, Dark) => Red,
|
||||
(High, Dark, _) => Magenta,
|
||||
(High, Low, Dark) => Red,
|
||||
(High, Low, Low) => LightRed,
|
||||
(High, Low, Mid) => Pink,
|
||||
(High, Low, High) => Magenta,
|
||||
(High, Mid, Dark) => Yellow,
|
||||
(High, Mid, Low) => Yellow,
|
||||
(High, Mid, Mid) => LightRed,
|
||||
(High, Mid, High) => Pink,
|
||||
(High, High, Dark) => Yellow,
|
||||
(High, High, Low) => White,
|
||||
(High, High, Mid) => White,
|
||||
(High, High, High) => White,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn from_vga_16(color: Color16) -> Rgba64 {
|
||||
use Color16::*;
|
||||
match color {
|
||||
Black => new_rgba64(0, 0, 0, 0),
|
||||
DarkGrey => new_rgba64(105, 105, 105, 0),
|
||||
LightGrey => new_rgba64(211, 211, 211, 0),
|
||||
//
|
||||
Blue => new_rgba64(0, 0, 0xff, 0),
|
||||
Green => new_rgba64(0, 0xff, 0, 0),
|
||||
Red => new_rgba64(0xff, 0, 0, 0),
|
||||
//
|
||||
Yellow => new_rgba64(0xff, 0xff, 0, 0),
|
||||
Cyan => new_rgba64(0, 0xff, 0xff, 0),
|
||||
Magenta => new_rgba64(0xff, 0, 0xff, 0),
|
||||
use Color16::*;
|
||||
match color {
|
||||
Black => new_rgba64(0, 0, 0, 0),
|
||||
DarkGrey => new_rgba64(105, 105, 105, 0),
|
||||
LightGrey => new_rgba64(211, 211, 211, 0),
|
||||
//
|
||||
Blue => new_rgba64(0, 0, 0xff, 0),
|
||||
Green => new_rgba64(0, 0xff, 0, 0),
|
||||
Red => new_rgba64(0xff, 0, 0, 0),
|
||||
//
|
||||
Yellow => new_rgba64(0xff, 0xff, 0, 0),
|
||||
Cyan => new_rgba64(0, 0xff, 0xff, 0),
|
||||
Magenta => new_rgba64(0xff, 0, 0xff, 0),
|
||||
|
||||
Brown => new_rgba64(165, 42, 42, 0),
|
||||
Pink => new_rgba64(0xff, 105, 180, 0),
|
||||
White => new_rgba64(0xff, 0xff, 0xff, 0),
|
||||
Brown => new_rgba64(165, 42, 42, 0),
|
||||
Pink => new_rgba64(0xff, 105, 180, 0),
|
||||
White => new_rgba64(0xff, 0xff, 0xff, 0),
|
||||
|
||||
LightBlue => new_rgba64(173, 216, 230, 0),
|
||||
LightGreen => new_rgba64(144, 238, 144, 0),
|
||||
LightCyan => new_rgba64(88, 100, 100, 0),
|
||||
LightRed => new_rgba64(0xff, 204, 203, 0),
|
||||
}
|
||||
LightBlue => new_rgba64(173, 216, 230, 0),
|
||||
LightGreen => new_rgba64(144, 238, 144, 0),
|
||||
LightCyan => new_rgba64(88, 100, 100, 0),
|
||||
LightRed => new_rgba64(0xff, 204, 203, 0),
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue