137fdb2f5SManos Pitsidianakis // Copyright 2024, Linaro Limited 237fdb2f5SManos Pitsidianakis // Author(s): Manos Pitsidianakis <manos.pitsidianakis@linaro.org> 337fdb2f5SManos Pitsidianakis // SPDX-License-Identifier: GPL-2.0-or-later 437fdb2f5SManos Pitsidianakis 5718e255fSPaolo Bonzini use core::ptr::NonNull; 6718e255fSPaolo Bonzini use std::os::raw::{c_int, c_void}; 737fdb2f5SManos Pitsidianakis 893243319SManos Pitsidianakis use qemu_api::{ 9b800a313SPaolo Bonzini bindings::*, c_str, vmstate_clock, vmstate_fields, vmstate_of, vmstate_subsections, 10b800a313SPaolo Bonzini vmstate_unused, zeroable::Zeroable, 1193243319SManos Pitsidianakis }; 1237fdb2f5SManos Pitsidianakis 13b800a313SPaolo Bonzini use crate::device::PL011State; 1437fdb2f5SManos Pitsidianakis 1593243319SManos Pitsidianakis extern "C" fn pl011_clock_needed(opaque: *mut c_void) -> bool { 1693243319SManos Pitsidianakis unsafe { 1793243319SManos Pitsidianakis debug_assert!(!opaque.is_null()); 1893243319SManos Pitsidianakis let state = NonNull::new_unchecked(opaque.cast::<PL011State>()); 1993243319SManos Pitsidianakis state.as_ref().migrate_clock 2093243319SManos Pitsidianakis } 2193243319SManos Pitsidianakis } 2293243319SManos Pitsidianakis 2393243319SManos Pitsidianakis /// Migration subsection for [`PL011State`] clock. 2493243319SManos Pitsidianakis pub static VMSTATE_PL011_CLOCK: VMStateDescription = VMStateDescription { 25718e255fSPaolo Bonzini name: c_str!("pl011/clock").as_ptr(), 2693243319SManos Pitsidianakis version_id: 1, 2793243319SManos Pitsidianakis minimum_version_id: 1, 2893243319SManos Pitsidianakis needed: Some(pl011_clock_needed), 2993243319SManos Pitsidianakis fields: vmstate_fields! { 30*24f0e8d8SPaolo Bonzini vmstate_clock!(PL011State, clock), 3193243319SManos Pitsidianakis }, 3293243319SManos Pitsidianakis ..Zeroable::ZERO 3393243319SManos Pitsidianakis }; 3493243319SManos Pitsidianakis 3593243319SManos Pitsidianakis extern "C" fn pl011_post_load(opaque: *mut c_void, version_id: c_int) -> c_int { 3693243319SManos Pitsidianakis unsafe { 3793243319SManos Pitsidianakis debug_assert!(!opaque.is_null()); 3893243319SManos Pitsidianakis let mut state = NonNull::new_unchecked(opaque.cast::<PL011State>()); 3993243319SManos Pitsidianakis let result = state.as_mut().post_load(version_id as u32); 4093243319SManos Pitsidianakis if result.is_err() { 4193243319SManos Pitsidianakis -1 4293243319SManos Pitsidianakis } else { 4393243319SManos Pitsidianakis 0 4493243319SManos Pitsidianakis } 4593243319SManos Pitsidianakis } 4693243319SManos Pitsidianakis } 4793243319SManos Pitsidianakis 4837fdb2f5SManos Pitsidianakis pub static VMSTATE_PL011: VMStateDescription = VMStateDescription { 49718e255fSPaolo Bonzini name: c_str!("pl011").as_ptr(), 5093243319SManos Pitsidianakis version_id: 2, 5193243319SManos Pitsidianakis minimum_version_id: 2, 5293243319SManos Pitsidianakis post_load: Some(pl011_post_load), 5393243319SManos Pitsidianakis fields: vmstate_fields! { 5493243319SManos Pitsidianakis vmstate_unused!(core::mem::size_of::<u32>()), 55b800a313SPaolo Bonzini vmstate_of!(PL011State, flags), 56b800a313SPaolo Bonzini vmstate_of!(PL011State, line_control), 57b800a313SPaolo Bonzini vmstate_of!(PL011State, receive_status_error_clear), 58b800a313SPaolo Bonzini vmstate_of!(PL011State, control), 59b800a313SPaolo Bonzini vmstate_of!(PL011State, dmacr), 60b800a313SPaolo Bonzini vmstate_of!(PL011State, int_enabled), 61b800a313SPaolo Bonzini vmstate_of!(PL011State, int_level), 62b800a313SPaolo Bonzini vmstate_of!(PL011State, read_fifo), 63b800a313SPaolo Bonzini vmstate_of!(PL011State, ilpr), 64b800a313SPaolo Bonzini vmstate_of!(PL011State, ibrd), 65b800a313SPaolo Bonzini vmstate_of!(PL011State, fbrd), 66b800a313SPaolo Bonzini vmstate_of!(PL011State, ifl), 67b800a313SPaolo Bonzini vmstate_of!(PL011State, read_pos), 68b800a313SPaolo Bonzini vmstate_of!(PL011State, read_count), 69b800a313SPaolo Bonzini vmstate_of!(PL011State, read_trigger), 7093243319SManos Pitsidianakis }, 7193243319SManos Pitsidianakis subsections: vmstate_subsections! { 7293243319SManos Pitsidianakis VMSTATE_PL011_CLOCK 7393243319SManos Pitsidianakis }, 746e50bde1SPaolo Bonzini ..Zeroable::ZERO 7537fdb2f5SManos Pitsidianakis }; 7637fdb2f5SManos Pitsidianakis 7737fdb2f5SManos Pitsidianakis qemu_api::declare_properties! { 7837fdb2f5SManos Pitsidianakis PL011_PROPERTIES, 7937fdb2f5SManos Pitsidianakis qemu_api::define_property!( 80718e255fSPaolo Bonzini c_str!("chardev"), 8137fdb2f5SManos Pitsidianakis PL011State, 8237fdb2f5SManos Pitsidianakis char_backend, 8337fdb2f5SManos Pitsidianakis unsafe { &qdev_prop_chr }, 8437fdb2f5SManos Pitsidianakis CharBackend 8537fdb2f5SManos Pitsidianakis ), 8637fdb2f5SManos Pitsidianakis qemu_api::define_property!( 87718e255fSPaolo Bonzini c_str!("migrate-clk"), 8837fdb2f5SManos Pitsidianakis PL011State, 8937fdb2f5SManos Pitsidianakis migrate_clock, 9037fdb2f5SManos Pitsidianakis unsafe { &qdev_prop_bool }, 91113c6688SPaolo Bonzini bool, 92113c6688SPaolo Bonzini default = true 9337fdb2f5SManos Pitsidianakis ), 9437fdb2f5SManos Pitsidianakis } 95