cachepc-qemu

Fork of AMDESE/qemu with changes for cachepc side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-qemu
Log | Files | Refs | Submodules | LICENSE | sfeed.txt

ci.c (1882B)


      1#include "vof.h"
      2
      3struct prom_args {
      4    uint32_t service;
      5    uint32_t nargs;
      6    uint32_t nret;
      7    uint32_t args[10];
      8};
      9
     10typedef unsigned long prom_arg_t;
     11
     12#define ADDR(x) (uint32_t)(x)
     13
     14static int prom_handle(struct prom_args *pargs)
     15{
     16    void *rtasbase;
     17    uint32_t rtassize = 0;
     18    phandle rtas;
     19
     20    if (strcmp("call-method", (void *)(unsigned long)pargs->service)) {
     21        return -1;
     22    }
     23
     24    if (strcmp("instantiate-rtas", (void *)(unsigned long)pargs->args[0])) {
     25        return -1;
     26    }
     27
     28    rtas = ci_finddevice("/rtas");
     29    /* rtas-size is set by QEMU depending of FWNMI support */
     30    ci_getprop(rtas, "rtas-size", &rtassize, sizeof(rtassize));
     31    if (rtassize < hv_rtas_size) {
     32        return -1;
     33    }
     34
     35    rtasbase = (void *)(unsigned long) pargs->args[2];
     36
     37    memcpy(rtasbase, hv_rtas, hv_rtas_size);
     38    pargs->args[pargs->nargs] = 0;
     39    pargs->args[pargs->nargs + 1] = pargs->args[2];
     40
     41    return 0;
     42}
     43
     44void prom_entry(uint32_t args)
     45{
     46    if (prom_handle((void *)(unsigned long) args)) {
     47        ci_entry(args);
     48    }
     49}
     50
     51static int call_ci(const char *service, int nargs, int nret, ...)
     52{
     53    int i;
     54    struct prom_args args;
     55    va_list list;
     56
     57    args.service = ADDR(service);
     58    args.nargs = nargs;
     59    args.nret = nret;
     60
     61    va_start(list, nret);
     62    for (i = 0; i < nargs; i++) {
     63        args.args[i] = va_arg(list, prom_arg_t);
     64    }
     65    va_end(list);
     66
     67    for (i = 0; i < nret; i++) {
     68        args.args[nargs + i] = 0;
     69    }
     70
     71    if (ci_entry((uint32_t)(&args)) < 0) {
     72        return -1;
     73    }
     74
     75    return (nret > 0) ? args.args[nargs] : 0;
     76}
     77
     78void ci_panic(const char *str)
     79{
     80    call_ci("exit", 0, 0);
     81}
     82
     83phandle ci_finddevice(const char *path)
     84{
     85    return call_ci("finddevice", 1, 1, path);
     86}
     87
     88uint32_t ci_getprop(phandle ph, const char *propname, void *prop, int len)
     89{
     90    return call_ci("getprop", 4, 1, ph, propname, prop, len);
     91}