diff options
| -rw-r--r-- | hw/s390x/sclpcpi.c | 74 | ||||
| -rw-r--r-- | include/hw/s390x/event-facility.h | 5 |
2 files changed, 79 insertions, 0 deletions
diff --git a/hw/s390x/sclpcpi.c b/hw/s390x/sclpcpi.c index 6e2090b27f..440a5ff1eb 100644 --- a/hw/s390x/sclpcpi.c +++ b/hw/s390x/sclpcpi.c @@ -50,7 +50,10 @@ */ #include "qemu/osdep.h" +#include "qemu/timer.h" #include "hw/s390x/event-facility.h" +#include "hw/s390x/ebcdic.h" +#include "qapi/qapi-visit-machine.h" typedef struct Data { uint8_t id_format; @@ -90,11 +93,58 @@ static int write_event_data(SCLPEvent *event, EventBufferHeader *evt_buf_hdr) { ControlProgramIdMsg *cpim = container_of(evt_buf_hdr, ControlProgramIdMsg, ebh); + SCLPEventCPI *e = SCLP_EVENT_CPI(event); + + ascii_put(e->system_type, (char *)cpim->data.system_type, + sizeof(cpim->data.system_type)); + ascii_put(e->system_name, (char *)cpim->data.system_name, + sizeof(cpim->data.system_name)); + ascii_put(e->sysplex_name, (char *)cpim->data.sysplex_name, + sizeof(cpim->data.sysplex_name)); + e->system_level = ldq_be_p(&cpim->data.system_level); + e->timestamp = qemu_clock_get_ns(QEMU_CLOCK_HOST); cpim->ebh.flags = SCLP_EVENT_BUFFER_ACCEPTED; return SCLP_RC_NORMAL_COMPLETION; } +static char *get_system_type(Object *obj, Error **errp) +{ + SCLPEventCPI *e = SCLP_EVENT_CPI(obj); + + return g_strndup((char *) e->system_type, sizeof(e->system_type)); +} + +static char *get_system_name(Object *obj, Error **errp) +{ + SCLPEventCPI *e = SCLP_EVENT_CPI(obj); + + return g_strndup((char *) e->system_name, sizeof(e->system_name)); +} + +static char *get_sysplex_name(Object *obj, Error **errp) +{ + SCLPEventCPI *e = SCLP_EVENT_CPI(obj); + + return g_strndup((char *) e->sysplex_name, sizeof(e->sysplex_name)); +} + +static void get_system_level(Object *obj, Visitor *v, const char *name, + void *opaque, Error **errp) +{ + SCLPEventCPI *e = SCLP_EVENT_CPI(obj); + + visit_type_uint64(v, name, &e->system_level, errp); +} + +static void get_timestamp(Object *obj, Visitor *v, const char *name, + void *opaque, Error **errp) +{ + SCLPEventCPI *e = SCLP_EVENT_CPI(obj); + + visit_type_uint64(v, name, &e->timestamp, errp); +} + static void cpi_class_init(ObjectClass *klass, const void *data) { DeviceClass *dc = DEVICE_CLASS(klass); @@ -106,6 +156,30 @@ static void cpi_class_init(ObjectClass *klass, const void *data) k->get_send_mask = send_mask; k->get_receive_mask = receive_mask; k->write_event_data = write_event_data; + + object_class_property_add_str(klass, "system_type", get_system_type, NULL); + object_class_property_set_description(klass, "system_type", + "operating system e.g. \"LINUX \""); + + object_class_property_add_str(klass, "system_name", get_system_name, NULL); + object_class_property_set_description(klass, "system_name", + "user configurable name of the VM e.g. \"TESTVM \""); + + object_class_property_add_str(klass, "sysplex_name", get_sysplex_name, + NULL); + object_class_property_set_description(klass, "sysplex_name", + "name of the cluster which the VM belongs to, if any" + " e.g. \"PLEX \""); + + object_class_property_add(klass, "system_level", "uint64", get_system_level, + NULL, NULL, NULL); + object_class_property_set_description(klass, "system_level", + "distribution and kernel version in Linux e.g. 74872343805430528"); + + object_class_property_add(klass, "timestamp", "uint64", get_timestamp, + NULL, NULL, NULL); + object_class_property_set_description(klass, "timestamp", + "latest update of CPI data in nanoseconds since the UNIX EPOCH"); } static const TypeInfo sclp_cpi_info = { diff --git a/include/hw/s390x/event-facility.h b/include/hw/s390x/event-facility.h index e81bc80498..eac7a51100 100644 --- a/include/hw/s390x/event-facility.h +++ b/include/hw/s390x/event-facility.h @@ -201,6 +201,11 @@ OBJECT_DECLARE_TYPE(SCLPEventCPI, SCLPEventCPIClass, struct SCLPEventCPI { SCLPEvent event; + uint8_t system_type[8]; + uint8_t system_name[8]; + uint64_t system_level; + uint8_t sysplex_name[8]; + uint64_t timestamp; }; #define TYPE_SCLP_EVENT_FACILITY "s390-sclp-event-facility" |