Revision 39ac8455 hw/spapr_hcall.c

b/hw/spapr_hcall.c
248 248
    return H_SUCCESS;
249 249
}
250 250

  
251
spapr_hcall_fn hypercall_table[(MAX_HCALL_OPCODE / 4) + 1];
251
static target_ulong h_rtas(CPUState *env, sPAPREnvironment *spapr,
252
                           target_ulong opcode, target_ulong *args)
253
{
254
    target_ulong rtas_r3 = args[0];
255
    uint32_t token = ldl_phys(rtas_r3);
256
    uint32_t nargs = ldl_phys(rtas_r3 + 4);
257
    uint32_t nret = ldl_phys(rtas_r3 + 8);
258

  
259
    return spapr_rtas_call(spapr, token, nargs, rtas_r3 + 12,
260
                           nret, rtas_r3 + 12 + 4*nargs);
261
}
262

  
263
spapr_hcall_fn papr_hypercall_table[(MAX_HCALL_OPCODE / 4) + 1];
264
spapr_hcall_fn kvmppc_hypercall_table[KVMPPC_HCALL_MAX - KVMPPC_HCALL_BASE];
252 265

  
253 266
void spapr_register_hypercall(target_ulong opcode, spapr_hcall_fn fn)
254 267
{
255
    spapr_hcall_fn old_fn;
268
    spapr_hcall_fn *slot;
269

  
270
    if (opcode <= MAX_HCALL_OPCODE) {
271
        assert((opcode & 0x3) == 0);
256 272

  
257
    assert(opcode <= MAX_HCALL_OPCODE);
258
    assert((opcode & 0x3) == 0);
273
        slot = &papr_hypercall_table[opcode / 4];
274
    } else {
275
        assert((opcode >= KVMPPC_HCALL_BASE) && (opcode <= KVMPPC_HCALL_MAX));
259 276

  
260
    old_fn = hypercall_table[opcode / 4];
261 277

  
262
    assert(!old_fn || (fn == old_fn));
278
        slot = &kvmppc_hypercall_table[opcode - KVMPPC_HCALL_BASE];
279
    }
263 280

  
264
    hypercall_table[opcode / 4] = fn;
281
    assert(!(*slot) || (fn == *slot));
282
    *slot = fn;
265 283
}
266 284

  
267 285
target_ulong spapr_hypercall(CPUState *env, target_ulong opcode,
......
274 292

  
275 293
    if ((opcode <= MAX_HCALL_OPCODE)
276 294
        && ((opcode & 0x3) == 0)) {
277
        spapr_hcall_fn fn = hypercall_table[opcode / 4];
295
        spapr_hcall_fn fn = papr_hypercall_table[opcode / 4];
296

  
297
        if (fn) {
298
            return fn(env, spapr, opcode, args);
299
        }
300
    } else if ((opcode >= KVMPPC_HCALL_BASE) &&
301
               (opcode <= KVMPPC_HCALL_MAX)) {
302
        spapr_hcall_fn fn = kvmppc_hypercall_table[opcode - KVMPPC_HCALL_BASE];
278 303

  
279 304
        if (fn) {
280 305
            return fn(env, spapr, opcode, args);
......
291 316
    spapr_register_hypercall(H_ENTER, h_enter);
292 317
    spapr_register_hypercall(H_REMOVE, h_remove);
293 318
    spapr_register_hypercall(H_PROTECT, h_protect);
319

  
320
    /* qemu/KVM-PPC specific hcalls */
321
    spapr_register_hypercall(KVMPPC_H_RTAS, h_rtas);
294 322
}
295 323
device_init(hypercall_init);

Also available in: Unified diff