1cde3c425SPaolo Bonzini // Copyright 2024, Linaro Limited 2cde3c425SPaolo Bonzini // Author(s): Manos Pitsidianakis <manos.pitsidianakis@linaro.org> 3cde3c425SPaolo Bonzini // SPDX-License-Identifier: GPL-2.0-or-later 4cde3c425SPaolo Bonzini 58c80c472SPaolo Bonzini use std::ffi::CStr; 6cde3c425SPaolo Bonzini 7cde3c425SPaolo Bonzini use qemu_api::{ 8716d89f9SPaolo Bonzini bindings::*, 9*c2f41c1bSPaolo Bonzini c_str, 10*c2f41c1bSPaolo Bonzini cell::{self, BqlCell}, 11*c2f41c1bSPaolo Bonzini declare_properties, define_property, 12716d89f9SPaolo Bonzini prelude::*, 13716d89f9SPaolo Bonzini qdev::{DeviceImpl, DeviceState, Property}, 14716d89f9SPaolo Bonzini qom::ObjectImpl, 15716d89f9SPaolo Bonzini vmstate::VMStateDescription, 16716d89f9SPaolo Bonzini zeroable::Zeroable, 17cde3c425SPaolo Bonzini }; 18cde3c425SPaolo Bonzini 19cde3c425SPaolo Bonzini // Test that macros can compile. 200a65e412SManos Pitsidianakis pub static VMSTATE: VMStateDescription = VMStateDescription { 21718e255fSPaolo Bonzini name: c_str!("name").as_ptr(), 22cde3c425SPaolo Bonzini unmigratable: true, 230a65e412SManos Pitsidianakis ..Zeroable::ZERO 240a65e412SManos Pitsidianakis }; 25cde3c425SPaolo Bonzini 26f3518400SJunjie Mao #[derive(qemu_api_macros::offsets)] 27cde3c425SPaolo Bonzini #[repr(C)] 28cde3c425SPaolo Bonzini #[derive(qemu_api_macros::Object)] 29cde3c425SPaolo Bonzini pub struct DummyState { 30*c2f41c1bSPaolo Bonzini parent: DeviceState, 31*c2f41c1bSPaolo Bonzini migrate_clock: bool, 32cde3c425SPaolo Bonzini } 33cde3c425SPaolo Bonzini 34cde3c425SPaolo Bonzini declare_properties! { 35cde3c425SPaolo Bonzini DUMMY_PROPERTIES, 36cde3c425SPaolo Bonzini define_property!( 37718e255fSPaolo Bonzini c_str!("migrate-clk"), 38cde3c425SPaolo Bonzini DummyState, 39cde3c425SPaolo Bonzini migrate_clock, 40cde3c425SPaolo Bonzini unsafe { &qdev_prop_bool }, 41cde3c425SPaolo Bonzini bool 42cde3c425SPaolo Bonzini ), 43cde3c425SPaolo Bonzini } 44cde3c425SPaolo Bonzini 457bd8e3efSPaolo Bonzini unsafe impl ObjectType for DummyState { 466dd818fbSPaolo Bonzini type Class = <DeviceState as ObjectType>::Class; 47718e255fSPaolo Bonzini const TYPE_NAME: &'static CStr = c_str!("dummy"); 487bd8e3efSPaolo Bonzini } 497bd8e3efSPaolo Bonzini 507bd8e3efSPaolo Bonzini impl ObjectImpl for DummyState { 51166e8a1fSPaolo Bonzini type ParentType = DeviceState; 527bd8e3efSPaolo Bonzini const ABSTRACT: bool = false; 53cde3c425SPaolo Bonzini } 54cde3c425SPaolo Bonzini 558c80c472SPaolo Bonzini impl DeviceImpl for DummyState { 568c80c472SPaolo Bonzini fn properties() -> &'static [Property] { 578c80c472SPaolo Bonzini &DUMMY_PROPERTIES 58cde3c425SPaolo Bonzini } 598c80c472SPaolo Bonzini fn vmsd() -> Option<&'static VMStateDescription> { 608c80c472SPaolo Bonzini Some(&VMSTATE) 618c80c472SPaolo Bonzini } 628c80c472SPaolo Bonzini } 638c80c472SPaolo Bonzini 64*c2f41c1bSPaolo Bonzini fn init_qom() { 65*c2f41c1bSPaolo Bonzini static ONCE: BqlCell<bool> = BqlCell::new(false); 66*c2f41c1bSPaolo Bonzini 67*c2f41c1bSPaolo Bonzini cell::bql_start_test(); 68*c2f41c1bSPaolo Bonzini if !ONCE.get() { 69cde3c425SPaolo Bonzini unsafe { 70cde3c425SPaolo Bonzini module_call_init(module_init_type::MODULE_INIT_QOM); 71*c2f41c1bSPaolo Bonzini } 72*c2f41c1bSPaolo Bonzini ONCE.set(true); 73*c2f41c1bSPaolo Bonzini } 74*c2f41c1bSPaolo Bonzini } 75*c2f41c1bSPaolo Bonzini 76*c2f41c1bSPaolo Bonzini #[test] 77*c2f41c1bSPaolo Bonzini /// Create and immediately drop an instance. 78*c2f41c1bSPaolo Bonzini fn test_object_new() { 79*c2f41c1bSPaolo Bonzini init_qom(); 80*c2f41c1bSPaolo Bonzini unsafe { 817a35e2fbSPaolo Bonzini object_unref(object_new(DummyState::TYPE_NAME.as_ptr()).cast()); 82cde3c425SPaolo Bonzini } 83cde3c425SPaolo Bonzini } 84