Skip to content

Commit

Permalink
add headphone state polling to codec
Browse files Browse the repository at this point in the history
  • Loading branch information
bunnie committed Nov 14, 2022
1 parent 474a02c commit 04f700a
Show file tree
Hide file tree
Showing 4 changed files with 51 additions and 1 deletion.
11 changes: 11 additions & 0 deletions services/codec/src/api.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,10 +44,21 @@ pub(crate) enum Opcode {
/// set headphone volume -- L&R channels are ganged together in this API, but codec can do separately
SetHeadphoneVolume,

/// get headphone type code
GetHeadphoneCode,

/// Suspend/resume callback
SuspendResume,
}

#[derive(Debug, num_derive::FromPrimitive, num_derive::ToPrimitive)]
pub enum HeadphoneState {
NotPresent = 0,
PresentWithMic = 1,
PresentWithoutMic = 2,
Reserved = 3,
CodecOff = 4,
}

#[derive(Debug, num_derive::FromPrimitive, num_derive::ToPrimitive)]
pub enum VolumeOps {
Expand Down
4 changes: 3 additions & 1 deletion services/codec/src/backend/tlv320aic3100.rs
Original file line number Diff line number Diff line change
Expand Up @@ -310,7 +310,9 @@ impl Codec {
pub fn get_headset_code(&mut self) -> u8 {
self.w(0, &[0]);
let mut code: [u8; 1] = [0; 1];
self.r(67, &mut code);
if !self.r(67, &mut code) {
log::warn!("headset code read unsuccessful");
};
code[0]
}

Expand Down
14 changes: 14 additions & 0 deletions services/codec/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -142,6 +142,20 @@ impl Codec {
_ => Err(xous::Error::InternalError)
}
}
pub fn poll_headphone_state(&self) -> Result<HeadphoneState, xous::Error> {
match send_message(self.conn,
Message::new_blocking_scalar(Opcode::GetHeadphoneCode.to_usize().unwrap(), 0, 0, 0, 0)
) {
Ok(xous::Result::Scalar1(code)) => {
let retcode: Option<HeadphoneState> = FromPrimitive::from_usize(code);
match retcode {
Some(code) => Ok(code),
None => Err(xous::Error::InternalError),
}
}
_ => Err(xous::Error::InternalError)
}
}
}

use core::sync::atomic::{AtomicU32, Ordering};
Expand Down
23 changes: 23 additions & 0 deletions services/codec/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,29 @@ fn main() -> ! {
};
codec.set_headphone_gain_db(headphone_analog_gain_db, headphone_analog_gain_db);
}),
Some(api::Opcode::GetHeadphoneCode) => xous::msg_blocking_scalar_unpack!(msg, _, _, _, _, {
if codec.is_init() && codec.is_on() {
let hp_code = codec.get_headset_code();
if hp_code & 0x80 != 0x80 {
log::warn!("Headphone detection polled, but detection is not enabled in hardware!");
}
log::debug!("headset code: 0x{:x}", hp_code);
let code = if hp_code == 0xff { // kind of a hack, we could also check codec power state
HeadphoneState::CodecOff
} else {
match (hp_code >> 5) & 0x3 {
0b00 => HeadphoneState::NotPresent,
0b01 => HeadphoneState::PresentWithoutMic,
0b10 => HeadphoneState::Reserved,
0b11 => HeadphoneState::PresentWithMic,
_ => HeadphoneState::Reserved,
}
};
xous::return_scalar(msg.sender, code as usize).ok();
} else {
xous::return_scalar(msg.sender, HeadphoneState::CodecOff as usize).ok();
}
}),
None => {
log::error!("couldn't convert opcode");
break
Expand Down

0 comments on commit 04f700a

Please sign in to comment.