diff --git a/src/migtd/src/bin/migtd/main.rs b/src/migtd/src/bin/migtd/main.rs index 74a222a0..ec1e1c22 100644 --- a/src/migtd/src/bin/migtd/main.rs +++ b/src/migtd/src/bin/migtd/main.rs @@ -8,7 +8,8 @@ extern crate alloc; use log::info; -use migtd::migration::{session::MigrationSession, MigrationResult}; +use migtd::migration::session::{migrate, query, report_status, wait_for_request}; +use migtd::migration::MigrationResult; use migtd::{config, event_log, migration}; const MIGTD_VERSION: &str = env!("CARGO_PKG_VERSION"); @@ -88,29 +89,26 @@ fn get_ca_and_measure(event_log: &mut [u8]) { fn handle_pre_mig() { migration::event::register_callback(); // Query the capability of VMM - if MigrationSession::query().is_err() { + if query().is_err() { panic!("Migration is not supported by VMM"); } // Loop to wait for request info!("Loop to wait for request"); loop { - let mut session = MigrationSession::new(); - if session.wait_for_request().is_ok() { + if let Ok(info) = wait_for_request() { #[cfg(feature = "vmcall-vsock")] { // Safe to unwrap because we have got the request information - let info = session.info().unwrap(); migtd::driver::vsock::vmcall_vsock_device_init( info.mig_info.mig_request_id, info.mig_socket_info.mig_td_cid, ); } - let status = session - .op() + let status = migrate(&info) .map(|_| MigrationResult::Success) .unwrap_or_else(|e| e); - let _ = session.report_status(status as u8); + let _ = report_status(&info, status as u8); #[cfg(all(feature = "coverage", feature = "tdx"))] { const MAX_COVERAGE_DATA_PAGE_COUNT: usize = 0x200; diff --git a/src/migtd/src/migration/session.rs b/src/migtd/src/migration/session.rs index c10a2f77..36cf5dea 100644 --- a/src/migtd/src/migration/session.rs +++ b/src/migtd/src/migration/session.rs @@ -29,6 +29,9 @@ const GSM_FIELD_MAX_EXPORT_VERSION: u64 = 0x2000000100000002; const GSM_FIELD_MIN_IMPORT_VERSION: u64 = 0x2000000100000003; const GSM_FIELD_MAX_IMPORT_VERSION: u64 = 0x2000000100000004; +const OPERATION_NO_OP: u8 = 0; +const OPERATION_START_MIG: u8 = 1; + pub struct MigrationInformation { pub mig_info: MigtdMigrationInformation, pub mig_socket_info: MigtdStreamSocketInfo, @@ -41,12 +44,6 @@ impl MigrationInformation { } } -#[derive(Debug, Clone, Copy)] -struct RequestInformation { - request_id: u64, - operation: u8, -} - struct ExchangeInformation { min_ver: u16, max_ver: u16, @@ -73,51 +70,79 @@ impl ExchangeInformation { } } -enum MigrationState { - WaitForRequest, - Operate(MigrationOperation), - Complete(RequestInformation), -} +pub fn query() -> Result<()> { + // Allocate one shared page for command and response buffer + let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + + // Set Migration query command buffer + let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_COMMON_GUID) + .ok_or(MigrationResult::InvalidParameter)?; + let query = ServiceMigWaitForReqCommand { + version: 0, + command: QUERY_COMMAND, + reserved: [0; 2], + }; + cmd.write(query.as_bytes())?; + cmd.write(VMCALL_SERVICE_MIGTD_GUID.as_bytes())?; + let _ = VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_COMMON_GUID) + .ok_or(MigrationResult::InvalidParameter)?; -enum MigrationOperation { - Migrate(MigrationInformation), -} + #[cfg(feature = "vmcall-interrupt")] + { + tdx::tdvmcall_service( + cmd_mem.as_bytes(), + rsp_mem.as_mut_bytes(), + event::VMCALL_SERVICE_VECTOR as u64, + 0, + )?; + event::wait_for_event(&event::VMCALL_SERVICE_FLAG); + } + #[cfg(not(feature = "vmcall-interrupt"))] + tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; -pub struct MigrationSession { - state: MigrationState, -} + let private_mem = rsp_mem.copy_to_private_shadow(); -impl Default for MigrationSession { - fn default() -> Self { - Self::new() + // Parse the response data + // Check the GUID of the reponse + let rsp = + VmcallServiceResponse::try_read(private_mem).ok_or(MigrationResult::InvalidParameter)?; + if rsp.read_guid() != VMCALL_SERVICE_COMMON_GUID.as_bytes() { + return Err(MigrationResult::InvalidParameter); } -} + let query = rsp + .read_data::(0) + .ok_or(MigrationResult::InvalidParameter)?; -impl MigrationSession { - pub fn new() -> Self { - MigrationSession { - state: MigrationState::WaitForRequest, - } + if query.command != QUERY_COMMAND || &query.guid != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { + return Err(MigrationResult::InvalidParameter); + } + if query.status != 0 { + return Err(MigrationResult::Unsupported); } - pub fn query() -> Result<()> { - // Allocate one shared page for command and response buffer - let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + log::info!("Migration is supported by VMM\n"); + Ok(()) +} - // Set Migration query command buffer - let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_COMMON_GUID) - .ok_or(MigrationResult::InvalidParameter)?; - let query = ServiceMigWaitForReqCommand { - version: 0, - command: QUERY_COMMAND, - reserved: [0; 2], - }; - cmd.write(query.as_bytes())?; - cmd.write(VMCALL_SERVICE_MIGTD_GUID.as_bytes())?; - let _ = VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_COMMON_GUID) - .ok_or(MigrationResult::InvalidParameter)?; +pub fn wait_for_request() -> Result { + // Allocate shared page for command and response buffer + let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + + // Set Migration wait for request command buffer + let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) + .ok_or(MigrationResult::InvalidParameter)?; + let wfr = ServiceMigWaitForReqCommand { + version: 0, + command: MIG_COMMAND_WAIT, + reserved: [0; 2], + }; + cmd.write(wfr.as_bytes())?; + let _ = VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) + .ok_or(MigrationResult::InvalidParameter)?; + loop { #[cfg(feature = "vmcall-interrupt")] { tdx::tdvmcall_service( @@ -133,335 +158,238 @@ impl MigrationSession { let private_mem = rsp_mem.copy_to_private_shadow(); - // Parse the response data - // Check the GUID of the reponse + // Parse out the response data let rsp = VmcallServiceResponse::try_read(private_mem) .ok_or(MigrationResult::InvalidParameter)?; - if rsp.read_guid() != VMCALL_SERVICE_COMMON_GUID.as_bytes() { + // Check the GUID of the reponse + if rsp.read_guid() != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { return Err(MigrationResult::InvalidParameter); } - let query = rsp - .read_data::(0) + let wfr = rsp + .read_data::(0) .ok_or(MigrationResult::InvalidParameter)?; - - if query.command != QUERY_COMMAND || &query.guid != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { + if wfr.command != MIG_COMMAND_WAIT { return Err(MigrationResult::InvalidParameter); } - if query.status != 0 { - return Err(MigrationResult::Unsupported); + if wfr.operation == OPERATION_START_MIG { + let mig_info = + read_mig_info(&private_mem[24 + size_of::()..]) + .ok_or(MigrationResult::InvalidParameter)?; + + return Ok(mig_info); + } else if wfr.operation != OPERATION_NO_OP { + break; } - - log::info!("Migration is supported by VMM\n"); - Ok(()) } + Err(MigrationResult::InvalidParameter) +} - pub fn wait_for_request(&mut self) -> Result<()> { - match self.state { - MigrationState::WaitForRequest => { - // Allocate shared page for command and response buffer - let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - - // Set Migration wait for request command buffer - let mut cmd = - VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) - .ok_or(MigrationResult::InvalidParameter)?; - let wfr = ServiceMigWaitForReqCommand { - version: 0, - command: MIG_COMMAND_WAIT, - reserved: [0; 2], - }; - cmd.write(wfr.as_bytes())?; - let _ = - VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) - .ok_or(MigrationResult::InvalidParameter)?; - - loop { - #[cfg(feature = "vmcall-interrupt")] - { - tdx::tdvmcall_service( - cmd_mem.as_bytes(), - rsp_mem.as_mut_bytes(), - event::VMCALL_SERVICE_VECTOR as u64, - 0, - )?; - event::wait_for_event(&event::VMCALL_SERVICE_FLAG); - } - #[cfg(not(feature = "vmcall-interrupt"))] - tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; - - let private_mem = rsp_mem.copy_to_private_shadow(); - - // Parse out the response data - let rsp = VmcallServiceResponse::try_read(private_mem) - .ok_or(MigrationResult::InvalidParameter)?; - // Check the GUID of the reponse - if rsp.read_guid() != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { - return Err(MigrationResult::InvalidParameter); - } - let wfr = rsp - .read_data::(0) - .ok_or(MigrationResult::InvalidParameter)?; - if wfr.command != MIG_COMMAND_WAIT { - return Err(MigrationResult::InvalidParameter); - } - if wfr.operation == 1 { - let mig_info = Self::read_mig_info( - &private_mem[24 + size_of::()..], - ) - .ok_or(MigrationResult::InvalidParameter)?; - self.state = MigrationState::Operate(MigrationOperation::Migrate(mig_info)); - - return Ok(()); - } else if wfr.operation != 0 { - break; - } - } - Err(MigrationResult::InvalidParameter) - } - _ => Err(MigrationResult::InvalidParameter), - } - } +pub fn shutdown() -> Result<()> { + // Allocate shared page for command and response buffer + let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - pub fn info(&self) -> Option<&MigrationInformation> { - match &self.state { - MigrationState::Operate(operation) => match operation { - MigrationOperation::Migrate(info) => Some(info), - }, - _ => None, - } - } + // Set Command + let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) + .ok_or(MigrationResult::InvalidParameter)?; - #[cfg(feature = "main")] - pub fn op(&mut self) -> Result<()> { - match &self.state { - MigrationState::Operate(operation) => match operation { - MigrationOperation::Migrate(info) => { - let state = Self::migrate(info); - self.state = MigrationState::Complete(RequestInformation { - request_id: info.mig_info.mig_request_id, - operation: 1, - }); - - state - } - }, - _ => Err(MigrationResult::InvalidParameter), - } - } + let sd = ServiceMigWaitForReqShutdown { + version: 0, + command: MIG_COMMAND_SHUT_DOWN, + reserved: [0; 2], + }; + cmd.write(sd.as_bytes())?; + tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; + Ok(()) +} - pub fn shutdown() -> Result<()> { - // Allocate shared page for command and response buffer - let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; +pub fn report_status(request: &MigrationInformation, status: u8) -> Result<()> { + // Allocate shared page for command and response buffer + let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + + // Set Command + let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) + .ok_or(MigrationResult::InvalidParameter)?; + + let rs = ServiceMigReportStatusCommand { + version: 0, + command: MIG_COMMAND_REPORT_STATUS, + operation: OPERATION_START_MIG, + status, + mig_request_id: request.mig_info.mig_request_id, + }; - // Set Command - let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) - .ok_or(MigrationResult::InvalidParameter)?; + cmd.write(rs.as_bytes())?; - let sd = ServiceMigWaitForReqShutdown { - version: 0, - command: MIG_COMMAND_SHUT_DOWN, - reserved: [0; 2], - }; - cmd.write(sd.as_bytes())?; - tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; - Ok(()) - } + let _ = VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) + .ok_or(MigrationResult::InvalidParameter)?; - pub fn report_status(&self, status: u8) -> Result<()> { - let request = match &self.state { - MigrationState::Complete(request) => *request, - _ => return Err(MigrationResult::InvalidParameter), - }; + tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; - // Allocate shared page for command and response buffer - let mut cmd_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; - let mut rsp_mem = SharedMemory::new(1).ok_or(MigrationResult::OutOfResource)?; + let private_mem = rsp_mem.copy_to_private_shadow(); - // Set Command - let mut cmd = VmcallServiceCommand::new(cmd_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) - .ok_or(MigrationResult::InvalidParameter)?; + // Parse the response data + // Check the GUID of the reponse + let rsp = + VmcallServiceResponse::try_read(private_mem).ok_or(MigrationResult::InvalidParameter)?; + if rsp.read_guid() != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { + return Err(MigrationResult::InvalidParameter); + } + let query = rsp + .read_data::(0) + .ok_or(MigrationResult::InvalidParameter)?; - let rs = ServiceMigReportStatusCommand { - version: 0, - command: MIG_COMMAND_REPORT_STATUS, - operation: request.operation, - status, - mig_request_id: request.request_id, - }; + // Ensure the response matches the command + if query.command != MIG_COMMAND_REPORT_STATUS { + return Err(MigrationResult::InvalidParameter); + } + Ok(()) +} - cmd.write(rs.as_bytes())?; +#[cfg(feature = "main")] +pub fn migrate(info: &MigrationInformation) -> Result<()> { + let mut msk = MigrationSessionKey::new(); + + for idx in 0..msk.fields.len() { + let ret = tdx::tdcall_servtd_rd( + info.mig_info.binding_handle, + TDCS_FIELD_MIG_ENC_KEY + idx as u64, + &info.mig_info.target_td_uuid, + )?; + msk.fields[idx] = ret.content; + } - let _ = VmcallServiceResponse::new(rsp_mem.as_mut_bytes(), VMCALL_SERVICE_MIGTD_GUID) - .ok_or(MigrationResult::InvalidParameter)?; + let transport; + #[cfg(feature = "virtio-serial")] + { + use virtio_serial::VirtioSerialPort; + const VIRTIO_SERIAL_PORT_ID: u32 = 1; - tdx::tdvmcall_service(cmd_mem.as_bytes(), rsp_mem.as_mut_bytes(), 0, 0)?; + let port = VirtioSerialPort::new(VIRTIO_SERIAL_PORT_ID); + port.open()?; + transport = port; + }; - let private_mem = rsp_mem.copy_to_private_shadow(); + #[cfg(not(feature = "virtio-serial"))] + { + use vsock::{stream::VsockStream, VsockAddr}; + // Establish the vsock connection with host + let mut vsock = VsockStream::new()?; + vsock.connect(&VsockAddr::new( + info.mig_socket_info.mig_td_cid as u32, + info.mig_socket_info.mig_channel_port, + ))?; + + transport = vsock; + }; - // Parse the response data - // Check the GUID of the reponse - let rsp = VmcallServiceResponse::try_read(private_mem) - .ok_or(MigrationResult::InvalidParameter)?; - if rsp.read_guid() != VMCALL_SERVICE_MIGTD_GUID.as_bytes() { - return Err(MigrationResult::InvalidParameter); - } - let query = rsp - .read_data::(0) - .ok_or(MigrationResult::InvalidParameter)?; + let mut remote_information = ExchangeInformation::default(); + let mut exchange_information = ExchangeInformation { + key: msk, + ..Default::default() + }; - // Ensure the response matches the command - if query.command != MIG_COMMAND_REPORT_STATUS { + // Establish TLS layer connection and negotiate the MSK + if info.is_src() { + let min_export_version = tdcall_sys_rd(GSM_FIELD_MIN_EXPORT_VERSION)?.1; + let max_export_version = tdcall_sys_rd(GSM_FIELD_MAX_EXPORT_VERSION)?.1; + if min_export_version > u16::MAX as u64 || max_export_version > u16::MAX as u64 { return Err(MigrationResult::InvalidParameter); } - Ok(()) - } - - #[cfg(feature = "main")] - fn migrate(info: &MigrationInformation) -> Result<()> { - let mut msk = MigrationSessionKey::new(); - - for idx in 0..msk.fields.len() { - let ret = tdx::tdcall_servtd_rd( - info.mig_info.binding_handle, - TDCS_FIELD_MIG_ENC_KEY + idx as u64, - &info.mig_info.target_td_uuid, - )?; - msk.fields[idx] = ret.content; + exchange_information.min_ver = min_export_version as u16; + exchange_information.max_ver = max_export_version as u16; + + // TLS client + let mut ratls_client = + ratls::client(transport).map_err(|_| MigrationResult::SecureSessionError)?; + + // MigTD-S send Migration Session Forward key to peer + ratls_client.write(exchange_information.as_bytes())?; + let size = ratls_client.read(remote_information.as_bytes_mut())?; + if size < size_of::() { + return Err(MigrationResult::NetworkError); } + } else { + let min_import_version = tdcall_sys_rd(GSM_FIELD_MIN_IMPORT_VERSION)?.1; + let max_import_version = tdcall_sys_rd(GSM_FIELD_MAX_IMPORT_VERSION)?.1; + if min_import_version > u16::MAX as u64 || max_import_version > u16::MAX as u64 { + return Err(MigrationResult::InvalidParameter); + } + exchange_information.min_ver = min_import_version as u16; + exchange_information.max_ver = max_import_version as u16; - let transport; - #[cfg(feature = "virtio-serial")] - { - use virtio_serial::VirtioSerialPort; - const VIRTIO_SERIAL_PORT_ID: u32 = 1; - - let port = VirtioSerialPort::new(VIRTIO_SERIAL_PORT_ID); - port.open()?; - transport = port; - }; + // TLS server + let mut ratls_server = + ratls::server(transport).map_err(|_| MigrationResult::SecureSessionError)?; - #[cfg(not(feature = "virtio-serial"))] - { - use vsock::{stream::VsockStream, VsockAddr}; - // Establish the vsock connection with host - let mut vsock = VsockStream::new()?; - vsock.connect(&VsockAddr::new( - info.mig_socket_info.mig_td_cid as u32, - info.mig_socket_info.mig_channel_port, - ))?; - - transport = vsock; - }; - - let mut remote_information = ExchangeInformation::default(); - let mut exchange_information = ExchangeInformation { - key: msk, - ..Default::default() - }; - - // Establish TLS layer connection and negotiate the MSK - if info.is_src() { - let min_export_version = tdcall_sys_rd(GSM_FIELD_MIN_EXPORT_VERSION)?.1; - let max_export_version = tdcall_sys_rd(GSM_FIELD_MAX_EXPORT_VERSION)?.1; - if min_export_version > u16::MAX as u64 || max_export_version > u16::MAX as u64 { - return Err(MigrationResult::InvalidParameter); - } - exchange_information.min_ver = min_export_version as u16; - exchange_information.max_ver = max_export_version as u16; - - // TLS client - let mut ratls_client = - ratls::client(transport).map_err(|_| MigrationResult::SecureSessionError)?; - - // MigTD-S send Migration Session Forward key to peer - ratls_client.write(exchange_information.as_bytes())?; - let size = ratls_client.read(remote_information.as_bytes_mut())?; - if size < size_of::() { - return Err(MigrationResult::NetworkError); - } - } else { - let min_import_version = tdcall_sys_rd(GSM_FIELD_MIN_IMPORT_VERSION)?.1; - let max_import_version = tdcall_sys_rd(GSM_FIELD_MAX_IMPORT_VERSION)?.1; - if min_import_version > u16::MAX as u64 || max_import_version > u16::MAX as u64 { - return Err(MigrationResult::InvalidParameter); - } - exchange_information.min_ver = min_import_version as u16; - exchange_information.max_ver = max_import_version as u16; - - // TLS server - let mut ratls_server = - ratls::server(transport).map_err(|_| MigrationResult::SecureSessionError)?; - - ratls_server.write(exchange_information.as_bytes())?; - let size = ratls_server.read(remote_information.as_bytes_mut())?; - if size < size_of::() { - return Err(MigrationResult::NetworkError); - } + ratls_server.write(exchange_information.as_bytes())?; + let size = ratls_server.read(remote_information.as_bytes_mut())?; + if size < size_of::() { + return Err(MigrationResult::NetworkError); } + } - let mig_ver = cal_mig_version(info.is_src(), &exchange_information, &remote_information)?; - set_mig_version(info, mig_ver)?; - - for idx in 0..remote_information.key.fields.len() { - tdx::tdcall_servtd_wr( - info.mig_info.binding_handle, - TDCS_FIELD_MIG_DEC_KEY + idx as u64, - remote_information.key.fields[idx], - &info.mig_info.target_td_uuid, - ) - .map_err(|_| MigrationResult::TdxModuleError)?; - } - log::info!("Set MSK and report status\n"); - exchange_information.key.clear(); - remote_information.key.clear(); + let mig_ver = cal_mig_version(info.is_src(), &exchange_information, &remote_information)?; + set_mig_version(info, mig_ver)?; - Ok(()) + for idx in 0..remote_information.key.fields.len() { + tdx::tdcall_servtd_wr( + info.mig_info.binding_handle, + TDCS_FIELD_MIG_DEC_KEY + idx as u64, + remote_information.key.fields[idx], + &info.mig_info.target_td_uuid, + ) + .map_err(|_| MigrationResult::TdxModuleError)?; } + log::info!("Set MSK and report status\n"); + exchange_information.key.clear(); + remote_information.key.clear(); - fn read_mig_info(hob: &[u8]) -> Option { - let mig_info_hob = - hob_lib::get_next_extension_guid_hob(hob, MIGRATION_INFORMATION_HOB_GUID.as_bytes())?; + Ok(()) +} - let mig_info = hob_lib::get_guid_data(mig_info_hob)? - .pread::(0) - .ok()?; +fn read_mig_info(hob: &[u8]) -> Option { + let mig_info_hob = + hob_lib::get_next_extension_guid_hob(hob, MIGRATION_INFORMATION_HOB_GUID.as_bytes())?; - let mig_socket_hob = - hob_lib::get_next_extension_guid_hob(hob, STREAM_SOCKET_INFO_HOB_GUID.as_bytes())?; + let mig_info = hob_lib::get_guid_data(mig_info_hob)? + .pread::(0) + .ok()?; - let mig_socket_info = hob_lib::get_guid_data(mig_socket_hob)? - .pread::(0) - .ok()?; + let mig_socket_hob = + hob_lib::get_next_extension_guid_hob(hob, STREAM_SOCKET_INFO_HOB_GUID.as_bytes())?; - // Migration Information is optional here - let mut mig_policy = None; - if let Some(policy_info_hob) = - hob_lib::get_next_extension_guid_hob(hob, MIGPOLICY_HOB_GUID.as_bytes()) - { - if let Some(policy_raw) = hob_lib::get_guid_data(policy_info_hob) { - let policy_header = policy_raw.pread::(0).ok()?; - let mut policy_data: Vec = Vec::new(); - let offset = size_of::(); - policy_data.extend_from_slice( - &policy_raw[offset..offset + policy_header.mig_policy_size as usize], - ); - mig_policy = Some(MigtdMigpolicy { - header: policy_header, - mig_policy: policy_data, - }); - } + let mig_socket_info = hob_lib::get_guid_data(mig_socket_hob)? + .pread::(0) + .ok()?; + + // Migration Information is optional here + let mut mig_policy = None; + if let Some(policy_info_hob) = + hob_lib::get_next_extension_guid_hob(hob, MIGPOLICY_HOB_GUID.as_bytes()) + { + if let Some(policy_raw) = hob_lib::get_guid_data(policy_info_hob) { + let policy_header = policy_raw.pread::(0).ok()?; + let mut policy_data: Vec = Vec::new(); + let offset = size_of::(); + policy_data.extend_from_slice( + &policy_raw[offset..offset + policy_header.mig_policy_size as usize], + ); + mig_policy = Some(MigtdMigpolicy { + header: policy_header, + mig_policy: policy_data, + }); } + } - let mig_info = MigrationInformation { - mig_info, - mig_socket_info, - mig_policy, - }; + let mig_info = MigrationInformation { + mig_info, + mig_socket_info, + mig_policy, + }; - Some(mig_info) - } + Some(mig_info) } /// Used to read a TDX Module global-scope metadata field. diff --git a/tests/test-td-payload/src/testservice.rs b/tests/test-td-payload/src/testservice.rs index 9e541b47..c938d71d 100644 --- a/tests/test-td-payload/src/testservice.rs +++ b/tests/test-td-payload/src/testservice.rs @@ -10,7 +10,7 @@ use core::ffi::c_void; use td_payload::print; use test_td_payload::{TestCase, TestResult}; -use migtd::migration::session::MigrationSession; +use migtd::migration::session::query; use serde::{Deserialize, Serialize}; @@ -27,7 +27,7 @@ pub struct Tdservice { impl Tdservice { fn test_query(&mut self) -> TestResult { // Query the capability of VMM - if MigrationSession::query().is_err() { + if query().is_err() { print!("Migration is not supported by VMM"); return TestResult::Fail; }