xref: /DragonOS/kernel/src/driver/keyboard/ps2_keyboard.rs (revision e28411791f090c421fe4b6fa5956fb1bd362a8d9)
1*e2841179SLoGin use core::hint::spin_loop;
264aea4b3SGou Ngai 
3*e2841179SLoGin use alloc::{
4*e2841179SLoGin     string::ToString,
5*e2841179SLoGin     sync::{Arc, Weak},
6*e2841179SLoGin };
7*e2841179SLoGin 
8*e2841179SLoGin use unified_init::macros::unified_init;
9004e86ffSlogin 
10004e86ffSlogin use crate::{
11*e2841179SLoGin     arch::{io::PortIOArch, CurrentPortIOArch},
12*e2841179SLoGin     driver::{
13*e2841179SLoGin         base::device::device_number::{DeviceNumber, Major},
14*e2841179SLoGin         input::ps2_dev::Ps2StatusRegister,
15*e2841179SLoGin     },
16*e2841179SLoGin     exception::{
17*e2841179SLoGin         irqdata::IrqHandlerData,
18*e2841179SLoGin         irqdesc::{IrqHandleFlags, IrqHandler, IrqReturn},
19*e2841179SLoGin         manage::irq_manager,
20*e2841179SLoGin         IrqNumber,
21*e2841179SLoGin     },
22004e86ffSlogin     filesystem::{
23004e86ffSlogin         devfs::{devfs_register, DevFS, DeviceINode},
246b4e7a29SLoGin         vfs::{
254ad52e57S裕依2439             core::generate_inode_id, file::FileMode, syscall::ModeType, FilePrivateData,
264ad52e57S裕依2439             FileSystem, FileType, IndexNode, Metadata,
276b4e7a29SLoGin         },
28004e86ffSlogin     },
29*e2841179SLoGin     init::initcall::INITCALL_DEVICE,
305fb12ce4SGou Ngai     libs::{keyboard_parser::TypeOneFSM, rwlock::RwLock, spinlock::SpinLock},
315fb12ce4SGou Ngai     time::TimeSpec,
32004e86ffSlogin };
3391e9d4abSLoGin use system_error::SystemError;
34*e2841179SLoGin 
35*e2841179SLoGin /// PS2键盘的中断向量号
36*e2841179SLoGin const PS2_KEYBOARD_INTR_VECTOR: IrqNumber = IrqNumber::new(0x21);
37*e2841179SLoGin 
38*e2841179SLoGin const PORT_PS2_KEYBOARD_DATA: u8 = 0x60;
39*e2841179SLoGin const PORT_PS2_KEYBOARD_STATUS: u8 = 0x64;
40*e2841179SLoGin const PORT_PS2_KEYBOARD_CONTROL: u8 = 0x64;
41*e2841179SLoGin 
42*e2841179SLoGin /// 向键盘发送配置命令
43*e2841179SLoGin const PS2_KEYBOARD_COMMAND_WRITE: u8 = 0x60;
44*e2841179SLoGin 
45*e2841179SLoGin /// 读取键盘的配置值
46*e2841179SLoGin #[allow(dead_code)]
47*e2841179SLoGin const PS2_KEYBOARD_COMMAND_READ: u8 = 0x20;
48*e2841179SLoGin /// 初始化键盘控制器的配置值
49*e2841179SLoGin const PS2_KEYBOARD_PARAM_INIT: u8 = 0x47;
50*e2841179SLoGin 
51004e86ffSlogin #[derive(Debug)]
52*e2841179SLoGin pub struct LockedPS2KeyBoardInode(RwLock<PS2KeyBoardInode>);
53004e86ffSlogin 
545fb12ce4SGou Ngai lazy_static! {
5552da9a59SGnoCiYeH     static ref PS2_KEYBOARD_FSM: SpinLock<TypeOneFSM> = SpinLock::new(TypeOneFSM::new());
565fb12ce4SGou Ngai }
575fb12ce4SGou Ngai 
58004e86ffSlogin #[derive(Debug)]
59004e86ffSlogin pub struct PS2KeyBoardInode {
60004e86ffSlogin     /// uuid 暂时不知道有什么用(x
61004e86ffSlogin     // uuid: Uuid,
62004e86ffSlogin     /// 指向自身的弱引用
63004e86ffSlogin     self_ref: Weak<LockedPS2KeyBoardInode>,
64004e86ffSlogin     /// 指向inode所在的文件系统对象的指针
65004e86ffSlogin     fs: Weak<DevFS>,
66004e86ffSlogin     /// INode 元数据
67004e86ffSlogin     metadata: Metadata,
68004e86ffSlogin }
69004e86ffSlogin 
70004e86ffSlogin impl LockedPS2KeyBoardInode {
71*e2841179SLoGin     pub fn new() -> Arc<Self> {
72004e86ffSlogin         let inode = PS2KeyBoardInode {
73004e86ffSlogin             // uuid: Uuid::new_v5(),
74004e86ffSlogin             self_ref: Weak::default(),
75004e86ffSlogin             fs: Weak::default(),
76004e86ffSlogin             metadata: Metadata {
77004e86ffSlogin                 dev_id: 1,
78004e86ffSlogin                 inode_id: generate_inode_id(),
79004e86ffSlogin                 size: 0,
80004e86ffSlogin                 blk_size: 0,
81004e86ffSlogin                 blocks: 0,
82004e86ffSlogin                 atime: TimeSpec::default(),
83004e86ffSlogin                 mtime: TimeSpec::default(),
84004e86ffSlogin                 ctime: TimeSpec::default(),
85004e86ffSlogin                 file_type: FileType::CharDevice, // 文件夹,block设备,char设备
866b4e7a29SLoGin                 mode: ModeType::from_bits_truncate(0o666),
87004e86ffSlogin                 nlinks: 1,
88004e86ffSlogin                 uid: 0,
89004e86ffSlogin                 gid: 0,
9002343d0bSLoGin                 raw_dev: DeviceNumber::new(Major::INPUT_MAJOR, 0), // 这里用来作为device number
91004e86ffSlogin             },
92004e86ffSlogin         };
93004e86ffSlogin 
94*e2841179SLoGin         let result = Arc::new(LockedPS2KeyBoardInode(RwLock::new(inode)));
9564aea4b3SGou Ngai         result.0.write().self_ref = Arc::downgrade(&result);
96004e86ffSlogin 
97004e86ffSlogin         return result;
98004e86ffSlogin     }
99004e86ffSlogin }
100004e86ffSlogin 
101004e86ffSlogin impl DeviceINode for LockedPS2KeyBoardInode {
102004e86ffSlogin     fn set_fs(&self, fs: Weak<DevFS>) {
10364aea4b3SGou Ngai         self.0.write().fs = fs;
104004e86ffSlogin     }
105004e86ffSlogin }
106004e86ffSlogin 
107*e2841179SLoGin fn ps2_keyboard_register() {
108*e2841179SLoGin     devfs_register("ps2_keyboard", LockedPS2KeyBoardInode::new())
109004e86ffSlogin         .expect("Failed to register ps/2 keyboard");
110004e86ffSlogin }
111004e86ffSlogin 
112004e86ffSlogin impl IndexNode for LockedPS2KeyBoardInode {
113004e86ffSlogin     fn read_at(
114004e86ffSlogin         &self,
115004e86ffSlogin         _offset: usize,
116*e2841179SLoGin         _len: usize,
117*e2841179SLoGin         _buf: &mut [u8],
1184ad52e57S裕依2439         _data: &mut FilePrivateData,
119676b8ef6SMork     ) -> Result<usize, SystemError> {
120*e2841179SLoGin         return Err(SystemError::ENOSYS);
121004e86ffSlogin     }
122004e86ffSlogin 
123004e86ffSlogin     fn write_at(
124004e86ffSlogin         &self,
125004e86ffSlogin         _offset: usize,
126004e86ffSlogin         _len: usize,
127004e86ffSlogin         _buf: &[u8],
1284ad52e57S裕依2439         _data: &mut FilePrivateData,
129676b8ef6SMork     ) -> Result<usize, SystemError> {
130*e2841179SLoGin         return Err(SystemError::ENOSYS);
131004e86ffSlogin     }
132004e86ffSlogin 
1334ad52e57S裕依2439     fn open(&self, _data: &mut FilePrivateData, _mode: &FileMode) -> Result<(), SystemError> {
134004e86ffSlogin         return Ok(());
135004e86ffSlogin     }
136004e86ffSlogin 
1374ad52e57S裕依2439     fn close(&self, _data: &mut FilePrivateData) -> Result<(), SystemError> {
138004e86ffSlogin         return Ok(());
139004e86ffSlogin     }
140004e86ffSlogin 
141676b8ef6SMork     fn metadata(&self) -> Result<Metadata, SystemError> {
14264aea4b3SGou Ngai         return Ok(self.0.read().metadata.clone());
143004e86ffSlogin     }
144004e86ffSlogin 
145676b8ef6SMork     fn set_metadata(&self, metadata: &Metadata) -> Result<(), SystemError> {
14664aea4b3SGou Ngai         let mut inode = self.0.write();
147004e86ffSlogin         inode.metadata.atime = metadata.atime;
148004e86ffSlogin         inode.metadata.mtime = metadata.mtime;
149004e86ffSlogin         inode.metadata.ctime = metadata.ctime;
150004e86ffSlogin         inode.metadata.mode = metadata.mode;
151004e86ffSlogin         inode.metadata.uid = metadata.uid;
152004e86ffSlogin         inode.metadata.gid = metadata.gid;
153004e86ffSlogin 
154004e86ffSlogin         return Ok(());
155004e86ffSlogin     }
156004e86ffSlogin 
1574ad52e57S裕依2439     fn fs(&self) -> alloc::sync::Arc<dyn FileSystem> {
15864aea4b3SGou Ngai         return self.0.read().fs.upgrade().unwrap();
159004e86ffSlogin     }
160004e86ffSlogin 
161004e86ffSlogin     fn as_any_ref(&self) -> &dyn core::any::Any {
162004e86ffSlogin         self
163004e86ffSlogin     }
164004e86ffSlogin 
165676b8ef6SMork     fn list(&self) -> Result<alloc::vec::Vec<alloc::string::String>, SystemError> {
16679a452ceShoumkh         return Err(SystemError::EOPNOTSUPP_OR_ENOTSUP);
167004e86ffSlogin     }
168004e86ffSlogin }
1695fb12ce4SGou Ngai 
170*e2841179SLoGin #[derive(Debug)]
171*e2841179SLoGin struct Ps2KeyboardIrqHandler;
172*e2841179SLoGin 
173*e2841179SLoGin impl IrqHandler for Ps2KeyboardIrqHandler {
174*e2841179SLoGin     fn handle(
175*e2841179SLoGin         &self,
176*e2841179SLoGin         _irq: IrqNumber,
177*e2841179SLoGin         _static_data: Option<&dyn IrqHandlerData>,
178*e2841179SLoGin         _dev_id: Option<Arc<dyn IrqHandlerData>>,
179*e2841179SLoGin     ) -> Result<IrqReturn, SystemError> {
180*e2841179SLoGin         // 先检查状态寄存器,看看是否有数据
181*e2841179SLoGin         let status = unsafe { CurrentPortIOArch::in8(PORT_PS2_KEYBOARD_STATUS.into()) };
182*e2841179SLoGin         let status = Ps2StatusRegister::from(status);
183*e2841179SLoGin         if !status.outbuf_full() {
184*e2841179SLoGin             return Ok(IrqReturn::NotHandled);
185*e2841179SLoGin         }
186*e2841179SLoGin 
187*e2841179SLoGin         let input = unsafe { CurrentPortIOArch::in8(PORT_PS2_KEYBOARD_DATA.into()) };
188*e2841179SLoGin         // wait_ps2_keyboard_read();
1895fb12ce4SGou Ngai         PS2_KEYBOARD_FSM.lock().parse(input);
190*e2841179SLoGin 
191*e2841179SLoGin         return Ok(IrqReturn::Handled);
192*e2841179SLoGin     }
193*e2841179SLoGin }
194*e2841179SLoGin 
195*e2841179SLoGin impl Ps2KeyboardIrqHandler {
196*e2841179SLoGin     const INTR_HANDLE_FLAGS: IrqHandleFlags =
197*e2841179SLoGin         IrqHandleFlags::from_bits_truncate(IrqHandleFlags::IRQF_TRIGGER_RISING.bits());
198*e2841179SLoGin }
199*e2841179SLoGin 
200*e2841179SLoGin /// 等待 PS/2 键盘的输入缓冲区为空
201*e2841179SLoGin fn wait_ps2_keyboard_write() {
202*e2841179SLoGin     let mut status: Ps2StatusRegister;
203*e2841179SLoGin     loop {
204*e2841179SLoGin         status = Ps2StatusRegister::from(unsafe {
205*e2841179SLoGin             CurrentPortIOArch::in8(PORT_PS2_KEYBOARD_STATUS.into())
206*e2841179SLoGin         });
207*e2841179SLoGin         if !status.inbuf_full() {
208*e2841179SLoGin             break;
209*e2841179SLoGin         }
210*e2841179SLoGin 
211*e2841179SLoGin         spin_loop();
212*e2841179SLoGin     }
213*e2841179SLoGin }
214*e2841179SLoGin #[unified_init(INITCALL_DEVICE)]
215*e2841179SLoGin fn ps2_keyboard_init() -> Result<(), SystemError> {
216*e2841179SLoGin     // ======== 初始化键盘控制器,写入配置值 =========
217*e2841179SLoGin     wait_ps2_keyboard_write();
218*e2841179SLoGin     unsafe {
219*e2841179SLoGin         CurrentPortIOArch::out8(PORT_PS2_KEYBOARD_CONTROL.into(), PS2_KEYBOARD_COMMAND_WRITE);
220*e2841179SLoGin         wait_ps2_keyboard_write();
221*e2841179SLoGin         CurrentPortIOArch::out8(PORT_PS2_KEYBOARD_DATA.into(), PS2_KEYBOARD_PARAM_INIT);
222*e2841179SLoGin         wait_ps2_keyboard_write();
223*e2841179SLoGin     }
224*e2841179SLoGin 
225*e2841179SLoGin     // 执行一百万次nop,等待键盘控制器把命令执行完毕
226*e2841179SLoGin     for _ in 0..1000000 {
227*e2841179SLoGin         spin_loop();
228*e2841179SLoGin     }
229*e2841179SLoGin 
230*e2841179SLoGin     irq_manager()
231*e2841179SLoGin         .request_irq(
232*e2841179SLoGin             PS2_KEYBOARD_INTR_VECTOR,
233*e2841179SLoGin             "ps2keyboard".to_string(),
234*e2841179SLoGin             &Ps2KeyboardIrqHandler,
235*e2841179SLoGin             Ps2KeyboardIrqHandler::INTR_HANDLE_FLAGS,
236*e2841179SLoGin             None,
237*e2841179SLoGin         )
238*e2841179SLoGin         .expect("Failed to request irq for ps2 keyboard");
239*e2841179SLoGin 
240*e2841179SLoGin     // 先读一下键盘的数据,防止由于在键盘初始化之前,由于按键被按下从而导致接收不到中断。
241*e2841179SLoGin     let status = unsafe { CurrentPortIOArch::in8(PORT_PS2_KEYBOARD_STATUS.into()) };
242*e2841179SLoGin     let status = Ps2StatusRegister::from(status);
243*e2841179SLoGin     if status.outbuf_full() {
244*e2841179SLoGin         unsafe { CurrentPortIOArch::in8(PORT_PS2_KEYBOARD_DATA.into()) };
245*e2841179SLoGin     }
246*e2841179SLoGin 
247*e2841179SLoGin     // 将设备挂载到devfs
248*e2841179SLoGin     ps2_keyboard_register();
249*e2841179SLoGin 
250*e2841179SLoGin     Ok(())
2515fb12ce4SGou Ngai }
252