use std::collections::HashMap;
use std::sync::atomic::{AtomicU64, Ordering};
pub const CBM_CHANNEL_LOAD: u8 = 0;
pub const CBM_CHANNEL_CTRL: u8 = 15;
#[derive(Debug, Clone)]
pub struct CbmChannel {
_number: u8,
_purpose: CbmChannelPurpose,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum CbmChannelPurpose {
Reset, Directory, FileRead, FileWrite, Command, }
#[derive(Debug)]
pub struct CbmChannelManager {
channels: HashMap<u8, Option<CbmChannel>>,
next_sequence: AtomicU64,
}
impl CbmChannelManager {
pub fn new() -> Self {
let mut channels = HashMap::new();
for i in 0..=15 {
channels.insert(i, None);
}
Self {
channels,
next_sequence: AtomicU64::new(1), }
}
pub fn allocate(
&mut self,
_device_number: u8,
_drive_id: u8,
purpose: CbmChannelPurpose,
) -> Option<u8> {
if purpose == CbmChannelPurpose::Reset {
if let Some(slot) = self.channels.get_mut(&15) {
if slot.is_none() {
let _sequence = self.next_sequence.fetch_add(1, Ordering::SeqCst);
*slot = Some(CbmChannel {
_number: 15,
_purpose: purpose,
});
return Some(15);
}
}
return None;
}
for i in 0..15 {
if let Some(slot) = self.channels.get_mut(&i) {
if slot.is_none() {
let _sequence = self.next_sequence.fetch_add(1, Ordering::SeqCst);
*slot = Some(CbmChannel {
_number: i,
_purpose: purpose,
});
return Some(i);
}
}
}
None
}
pub fn reset(&mut self) {
for i in 0..=15 {
self.channels.insert(i, None);
}
}
}