/* * This work is licensed under the terms of the GNU GPL, version 2 or later. * See the COPYING file in the top-level directory. */ #include "qemu/osdep.h" #include "libqtest.h" #include "libqos/rtas.h" static void qrtas_copy_args(uint64_t target_args, uint32_t nargs, uint32_t *args) { int i; for (i = 0; i < nargs; i++) { writel(target_args + i * sizeof(uint32_t), args[i]); } } static void qrtas_copy_ret(uint64_t target_ret, uint32_t nret, uint32_t *ret) { int i; for (i = 0; i < nret; i++) { ret[i] = readl(target_ret + i * sizeof(uint32_t)); } } static uint64_t qrtas_call(QGuestAllocator *alloc, const char *name, uint32_t nargs, uint32_t *args, uint32_t nret, uint32_t *ret) { uint64_t res; uint64_t target_args, target_ret; target_args = guest_alloc(alloc, nargs * sizeof(uint32_t)); target_ret = guest_alloc(alloc, nret * sizeof(uint32_t)); qrtas_copy_args(target_args, nargs, args); res = qtest_rtas_call(global_qtest, name, nargs, target_args, nret, target_ret); qrtas_copy_ret(target_ret, nret, ret); guest_free(alloc, target_ret); guest_free(alloc, target_args); return res; } int qrtas_get_time_of_day(QGuestAllocator *alloc, struct tm *tm, uint32_t *ns) { int res; uint32_t ret[8]; res = qrtas_call(alloc, "get-time-of-day", 0, NULL, 8, ret); if (res != 0) { return res; } res = ret[0]; memset(tm, 0, sizeof(*tm)); tm->tm_year = ret[1] - 1900; tm->tm_mon = ret[2] - 1; tm->tm_mday = ret[3]; tm->tm_hour = ret[4]; tm->tm_min = ret[5]; tm->tm_sec = ret[6]; *ns = ret[7]; return res; } uint32_t qrtas_ibm_read_pci_config(QGuestAllocator *alloc, uint64_t buid, uint32_t addr, uint32_t size) { int res; uint32_t args[4], ret[2]; args[0] = addr; args[1] = buid >> 32; args[2] = buid & 0xffffffff; args[3] = size; res = qrtas_call(alloc, "ibm,read-pci-config", 4, args, 2, ret); if (res != 0) { return -1; } if (ret[0] != 0) { return -1; } return ret[1]; } int qrtas_ibm_write_pci_config(QGuestAllocator *alloc, uint64_t buid, uint32_t addr, uint32_t size, uint32_t val) { int res; uint32_t args[5], ret[1]; args[0] = addr; args[1] = buid >> 32; args[2] = buid & 0xffffffff; args[3] = size; args[4] = val; res = qrtas_call(alloc, "ibm,write-pci-config", 5, args, 1, ret); if (res != 0) { return -1; } if (ret[0] != 0) { return -1; } return 0; }