linux/arch/s390/kvm/sigp.c
<<
>>
Prefs
   1/*
   2 * handling interprocessor communication
   3 *
   4 * Copyright IBM Corp. 2008, 2013
   5 *
   6 * This program is free software; you can redistribute it and/or modify
   7 * it under the terms of the GNU General Public License (version 2 only)
   8 * as published by the Free Software Foundation.
   9 *
  10 *    Author(s): Carsten Otte <cotte@de.ibm.com>
  11 *               Christian Borntraeger <borntraeger@de.ibm.com>
  12 *               Christian Ehrhardt <ehrhardt@de.ibm.com>
  13 */
  14
  15#include <linux/kvm.h>
  16#include <linux/kvm_host.h>
  17#include <linux/slab.h>
  18#include <asm/sigp.h>
  19#include "gaccess.h"
  20#include "kvm-s390.h"
  21#include "trace.h"
  22
  23static int __sigp_sense(struct kvm_vcpu *vcpu, struct kvm_vcpu *dst_vcpu,
  24                        u64 *reg)
  25{
  26        struct kvm_s390_local_interrupt *li;
  27        int cpuflags;
  28        int rc;
  29        int ext_call_pending;
  30
  31        li = &dst_vcpu->arch.local_int;
  32
  33        cpuflags = atomic_read(li->cpuflags);
  34        ext_call_pending = kvm_s390_ext_call_pending(dst_vcpu);
  35        if (!(cpuflags & CPUSTAT_STOPPED) && !ext_call_pending)
  36                rc = SIGP_CC_ORDER_CODE_ACCEPTED;
  37        else {
  38                *reg &= 0xffffffff00000000UL;
  39                if (ext_call_pending)
  40                        *reg |= SIGP_STATUS_EXT_CALL_PENDING;
  41                if (cpuflags & CPUSTAT_STOPPED)
  42                        *reg |= SIGP_STATUS_STOPPED;
  43                rc = SIGP_CC_STATUS_STORED;
  44        }
  45
  46        VCPU_EVENT(vcpu, 4, "sensed status of cpu %x rc %x", dst_vcpu->vcpu_id,
  47                   rc);
  48        return rc;
  49}
  50
  51static int __inject_sigp_emergency(struct kvm_vcpu *vcpu,
  52                                    struct kvm_vcpu *dst_vcpu)
  53{
  54        struct kvm_s390_irq irq = {
  55                .type = KVM_S390_INT_EMERGENCY,
  56                .u.emerg.code = vcpu->vcpu_id,
  57        };
  58        int rc = 0;
  59
  60        rc = kvm_s390_inject_vcpu(dst_vcpu, &irq);
  61        if (!rc)
  62                VCPU_EVENT(vcpu, 4, "sent sigp emerg to cpu %x",
  63                           dst_vcpu->vcpu_id);
  64
  65        return rc ? rc : SIGP_CC_ORDER_CODE_ACCEPTED;
  66}
  67
  68static int __sigp_emergency(struct kvm_vcpu *vcpu, struct kvm_vcpu *dst_vcpu)
  69{
  70        return __inject_sigp_emergency(vcpu, dst_vcpu);
  71}
  72
  73static int __sigp_conditional_emergency(struct kvm_vcpu *vcpu,
  74                                        struct kvm_vcpu *dst_vcpu,
  75                                        u16 asn, u64 *reg)
  76{
  77        const u64 psw_int_mask = PSW_MASK_IO | PSW_MASK_EXT;
  78        u16 p_asn, s_asn;
  79        psw_t *psw;
  80        u32 flags;
  81
  82        flags = atomic_read(&dst_vcpu->arch.sie_block->cpuflags);
  83        psw = &dst_vcpu->arch.sie_block->gpsw;
  84        p_asn = dst_vcpu->arch.sie_block->gcr[4] & 0xffff;  /* Primary ASN */
  85        s_asn = dst_vcpu->arch.sie_block->gcr[3] & 0xffff;  /* Secondary ASN */
  86
  87        /* Inject the emergency signal? */
  88        if (!(flags & CPUSTAT_STOPPED)
  89            || (psw->mask & psw_int_mask) != psw_int_mask
  90            || ((flags & CPUSTAT_WAIT) && psw->addr != 0)
  91            || (!(flags & CPUSTAT_WAIT) && (asn == p_asn || asn == s_asn))) {
  92                return __inject_sigp_emergency(vcpu, dst_vcpu);
  93        } else {
  94                *reg &= 0xffffffff00000000UL;
  95                *reg |= SIGP_STATUS_INCORRECT_STATE;
  96                return SIGP_CC_STATUS_STORED;
  97        }
  98}
  99
 100static int __sigp_external_call(struct kvm_vcpu *vcpu,
 101                                struct kvm_vcpu *dst_vcpu, u64 *reg)
 102{
 103        struct kvm_s390_irq irq = {
 104                .type = KVM_S390_INT_EXTERNAL_CALL,
 105                .u.extcall.code = vcpu->vcpu_id,
 106        };
 107        int rc;
 108
 109        rc = kvm_s390_inject_vcpu(dst_vcpu, &irq);
 110        if (rc == -EBUSY) {
 111                *reg &= 0xffffffff00000000UL;
 112                *reg |= SIGP_STATUS_EXT_CALL_PENDING;
 113                return SIGP_CC_STATUS_STORED;
 114        } else if (rc == 0) {
 115                VCPU_EVENT(vcpu, 4, "sent sigp ext call to cpu %x",
 116                           dst_vcpu->vcpu_id);
 117        }
 118
 119        return rc ? rc : SIGP_CC_ORDER_CODE_ACCEPTED;
 120}
 121
 122static int __sigp_stop(struct kvm_vcpu *vcpu, struct kvm_vcpu *dst_vcpu)
 123{
 124        struct kvm_s390_irq irq = {
 125                .type = KVM_S390_SIGP_STOP,
 126        };
 127        int rc;
 128
 129        rc = kvm_s390_inject_vcpu(dst_vcpu, &irq);
 130        if (rc == -EBUSY)
 131                rc = SIGP_CC_BUSY;
 132        else if (rc == 0)
 133                VCPU_EVENT(vcpu, 4, "sent sigp stop to cpu %x",
 134                           dst_vcpu->vcpu_id);
 135
 136        return rc;
 137}
 138
 139static int __sigp_stop_and_store_status(struct kvm_vcpu *vcpu,
 140                                        struct kvm_vcpu *dst_vcpu, u64 *reg)
 141{
 142        struct kvm_s390_irq irq = {
 143                .type = KVM_S390_SIGP_STOP,
 144                .u.stop.flags = KVM_S390_STOP_FLAG_STORE_STATUS,
 145        };
 146        int rc;
 147
 148        rc = kvm_s390_inject_vcpu(dst_vcpu, &irq);
 149        if (rc == -EBUSY)
 150                rc = SIGP_CC_BUSY;
 151        else if (rc == 0)
 152                VCPU_EVENT(vcpu, 4, "sent sigp stop and store status to cpu %x",
 153                           dst_vcpu->vcpu_id);
 154
 155        return rc;
 156}
 157
 158static int __sigp_set_arch(struct kvm_vcpu *vcpu, u32 parameter)
 159{
 160        int rc;
 161        unsigned int i;
 162        struct kvm_vcpu *v;
 163
 164        switch (parameter & 0xff) {
 165        case 0:
 166                rc = SIGP_CC_NOT_OPERATIONAL;
 167                break;
 168        case 1:
 169        case 2:
 170                kvm_for_each_vcpu(i, v, vcpu->kvm) {
 171                        v->arch.pfault_token = KVM_S390_PFAULT_TOKEN_INVALID;
 172                        kvm_clear_async_pf_completion_queue(v);
 173                }
 174
 175                rc = SIGP_CC_ORDER_CODE_ACCEPTED;
 176                break;
 177        default:
 178                rc = -EOPNOTSUPP;
 179        }
 180        return rc;
 181}
 182
 183static int __sigp_set_prefix(struct kvm_vcpu *vcpu, struct kvm_vcpu *dst_vcpu,
 184                             u32 address, u64 *reg)
 185{
 186        struct kvm_s390_irq irq = {
 187                .type = KVM_S390_SIGP_SET_PREFIX,
 188                .u.prefix.address = address & 0x7fffe000u,
 189        };
 190        int rc;
 191
 192        /*
 193         * Make sure the new value is valid memory. We only need to check the
 194         * first page, since address is 8k aligned and memory pieces are always
 195         * at least 1MB aligned and have at least a size of 1MB.
 196         */
 197        if (kvm_is_error_gpa(vcpu->kvm, irq.u.prefix.address)) {
 198                *reg &= 0xffffffff00000000UL;
 199                *reg |= SIGP_STATUS_INVALID_PARAMETER;
 200                return SIGP_CC_STATUS_STORED;
 201        }
 202
 203        rc = kvm_s390_inject_vcpu(dst_vcpu, &irq);
 204        if (rc == -EBUSY) {
 205                *reg &= 0xffffffff00000000UL;
 206                *reg |= SIGP_STATUS_INCORRECT_STATE;
 207                return SIGP_CC_STATUS_STORED;
 208        } else if (rc == 0) {
 209                VCPU_EVENT(vcpu, 4, "set prefix of cpu %02x to %x",
 210                           dst_vcpu->vcpu_id, irq.u.prefix.address);
 211        }
 212
 213        return rc;
 214}
 215
 216static int __sigp_store_status_at_addr(struct kvm_vcpu *vcpu,
 217                                       struct kvm_vcpu *dst_vcpu,
 218                                       u32 addr, u64 *reg)
 219{
 220        int flags;
 221        int rc;
 222
 223        flags = atomic_read(dst_vcpu->arch.local_int.cpuflags);
 224        if (!(flags & CPUSTAT_STOPPED)) {
 225                *reg &= 0xffffffff00000000UL;
 226                *reg |= SIGP_STATUS_INCORRECT_STATE;
 227                return SIGP_CC_STATUS_STORED;
 228        }
 229
 230        addr &= 0x7ffffe00;
 231        rc = kvm_s390_store_status_unloaded(dst_vcpu, addr);
 232        if (rc == -EFAULT) {
 233                *reg &= 0xffffffff00000000UL;
 234                *reg |= SIGP_STATUS_INVALID_PARAMETER;
 235                rc = SIGP_CC_STATUS_STORED;
 236        }
 237        return rc;
 238}
 239
 240static int __sigp_sense_running(struct kvm_vcpu *vcpu,
 241                                struct kvm_vcpu *dst_vcpu, u64 *reg)
 242{
 243        struct kvm_s390_local_interrupt *li;
 244        int rc;
 245
 246        li = &dst_vcpu->arch.local_int;
 247        if (atomic_read(li->cpuflags) & CPUSTAT_RUNNING) {
 248                /* running */
 249                rc = SIGP_CC_ORDER_CODE_ACCEPTED;
 250        } else {
 251                /* not running */
 252                *reg &= 0xffffffff00000000UL;
 253                *reg |= SIGP_STATUS_NOT_RUNNING;
 254                rc = SIGP_CC_STATUS_STORED;
 255        }
 256
 257        VCPU_EVENT(vcpu, 4, "sensed running status of cpu %x rc %x",
 258                   dst_vcpu->vcpu_id, rc);
 259
 260        return rc;
 261}
 262
 263static int __prepare_sigp_re_start(struct kvm_vcpu *vcpu,
 264                                   struct kvm_vcpu *dst_vcpu, u8 order_code)
 265{
 266        struct kvm_s390_local_interrupt *li = &dst_vcpu->arch.local_int;
 267        /* handle (RE)START in user space */
 268        int rc = -EOPNOTSUPP;
 269
 270        /* make sure we don't race with STOP irq injection */
 271        spin_lock(&li->lock);
 272        if (kvm_s390_is_stop_irq_pending(dst_vcpu))
 273                rc = SIGP_CC_BUSY;
 274        spin_unlock(&li->lock);
 275
 276        return rc;
 277}
 278
 279static int __prepare_sigp_cpu_reset(struct kvm_vcpu *vcpu,
 280                                    struct kvm_vcpu *dst_vcpu, u8 order_code)
 281{
 282        /* handle (INITIAL) CPU RESET in user space */
 283        return -EOPNOTSUPP;
 284}
 285
 286static int __prepare_sigp_unknown(struct kvm_vcpu *vcpu,
 287                                  struct kvm_vcpu *dst_vcpu)
 288{
 289        /* handle unknown orders in user space */
 290        return -EOPNOTSUPP;
 291}
 292
 293static int handle_sigp_dst(struct kvm_vcpu *vcpu, u8 order_code,
 294                           u16 cpu_addr, u32 parameter, u64 *status_reg)
 295{
 296        int rc;
 297        struct kvm_vcpu *dst_vcpu;
 298
 299        if (cpu_addr >= KVM_MAX_VCPUS)
 300                return SIGP_CC_NOT_OPERATIONAL;
 301
 302        dst_vcpu = kvm_get_vcpu(vcpu->kvm, cpu_addr);
 303        if (!dst_vcpu)
 304                return SIGP_CC_NOT_OPERATIONAL;
 305
 306        switch (order_code) {
 307        case SIGP_SENSE:
 308                vcpu->stat.instruction_sigp_sense++;
 309                rc = __sigp_sense(vcpu, dst_vcpu, status_reg);
 310                break;
 311        case SIGP_EXTERNAL_CALL:
 312                vcpu->stat.instruction_sigp_external_call++;
 313                rc = __sigp_external_call(vcpu, dst_vcpu, status_reg);
 314                break;
 315        case SIGP_EMERGENCY_SIGNAL:
 316                vcpu->stat.instruction_sigp_emergency++;
 317                rc = __sigp_emergency(vcpu, dst_vcpu);
 318                break;
 319        case SIGP_STOP:
 320                vcpu->stat.instruction_sigp_stop++;
 321                rc = __sigp_stop(vcpu, dst_vcpu);
 322                break;
 323        case SIGP_STOP_AND_STORE_STATUS:
 324                vcpu->stat.instruction_sigp_stop_store_status++;
 325                rc = __sigp_stop_and_store_status(vcpu, dst_vcpu, status_reg);
 326                break;
 327        case SIGP_STORE_STATUS_AT_ADDRESS:
 328                vcpu->stat.instruction_sigp_store_status++;
 329                rc = __sigp_store_status_at_addr(vcpu, dst_vcpu, parameter,
 330                                                 status_reg);
 331                break;
 332        case SIGP_SET_PREFIX:
 333                vcpu->stat.instruction_sigp_prefix++;
 334                rc = __sigp_set_prefix(vcpu, dst_vcpu, parameter, status_reg);
 335                break;
 336        case SIGP_COND_EMERGENCY_SIGNAL:
 337                vcpu->stat.instruction_sigp_cond_emergency++;
 338                rc = __sigp_conditional_emergency(vcpu, dst_vcpu, parameter,
 339                                                  status_reg);
 340                break;
 341        case SIGP_SENSE_RUNNING:
 342                vcpu->stat.instruction_sigp_sense_running++;
 343                rc = __sigp_sense_running(vcpu, dst_vcpu, status_reg);
 344                break;
 345        case SIGP_START:
 346                vcpu->stat.instruction_sigp_start++;
 347                rc = __prepare_sigp_re_start(vcpu, dst_vcpu, order_code);
 348                break;
 349        case SIGP_RESTART:
 350                vcpu->stat.instruction_sigp_restart++;
 351                rc = __prepare_sigp_re_start(vcpu, dst_vcpu, order_code);
 352                break;
 353        case SIGP_INITIAL_CPU_RESET:
 354                vcpu->stat.instruction_sigp_init_cpu_reset++;
 355                rc = __prepare_sigp_cpu_reset(vcpu, dst_vcpu, order_code);
 356                break;
 357        case SIGP_CPU_RESET:
 358                vcpu->stat.instruction_sigp_cpu_reset++;
 359                rc = __prepare_sigp_cpu_reset(vcpu, dst_vcpu, order_code);
 360                break;
 361        default:
 362                vcpu->stat.instruction_sigp_unknown++;
 363                rc = __prepare_sigp_unknown(vcpu, dst_vcpu);
 364        }
 365
 366        if (rc == -EOPNOTSUPP)
 367                VCPU_EVENT(vcpu, 4,
 368                           "sigp order %u -> cpu %x: handled in user space",
 369                           order_code, dst_vcpu->vcpu_id);
 370
 371        return rc;
 372}
 373
 374static int handle_sigp_order_in_user_space(struct kvm_vcpu *vcpu, u8 order_code)
 375{
 376        if (!vcpu->kvm->arch.user_sigp)
 377                return 0;
 378
 379        switch (order_code) {
 380        case SIGP_SENSE:
 381        case SIGP_EXTERNAL_CALL:
 382        case SIGP_EMERGENCY_SIGNAL:
 383        case SIGP_COND_EMERGENCY_SIGNAL:
 384        case SIGP_SENSE_RUNNING:
 385                return 0;
 386        /* update counters as we're directly dropping to user space */
 387        case SIGP_STOP:
 388                vcpu->stat.instruction_sigp_stop++;
 389                break;
 390        case SIGP_STOP_AND_STORE_STATUS:
 391                vcpu->stat.instruction_sigp_stop_store_status++;
 392                break;
 393        case SIGP_STORE_STATUS_AT_ADDRESS:
 394                vcpu->stat.instruction_sigp_store_status++;
 395                break;
 396        case SIGP_SET_PREFIX:
 397                vcpu->stat.instruction_sigp_prefix++;
 398                break;
 399        case SIGP_START:
 400                vcpu->stat.instruction_sigp_start++;
 401                break;
 402        case SIGP_RESTART:
 403                vcpu->stat.instruction_sigp_restart++;
 404                break;
 405        case SIGP_INITIAL_CPU_RESET:
 406                vcpu->stat.instruction_sigp_init_cpu_reset++;
 407                break;
 408        case SIGP_CPU_RESET:
 409                vcpu->stat.instruction_sigp_cpu_reset++;
 410                break;
 411        default:
 412                vcpu->stat.instruction_sigp_unknown++;
 413        }
 414
 415        VCPU_EVENT(vcpu, 4, "sigp order %u: completely handled in user space",
 416                   order_code);
 417
 418        return 1;
 419}
 420
 421int kvm_s390_handle_sigp(struct kvm_vcpu *vcpu)
 422{
 423        int r1 = (vcpu->arch.sie_block->ipa & 0x00f0) >> 4;
 424        int r3 = vcpu->arch.sie_block->ipa & 0x000f;
 425        u32 parameter;
 426        u16 cpu_addr = vcpu->run->s.regs.gprs[r3];
 427        u8 order_code;
 428        int rc;
 429
 430        /* sigp in userspace can exit */
 431        if (vcpu->arch.sie_block->gpsw.mask & PSW_MASK_PSTATE)
 432                return kvm_s390_inject_program_int(vcpu, PGM_PRIVILEGED_OP);
 433
 434        order_code = kvm_s390_get_base_disp_rs(vcpu);
 435        if (handle_sigp_order_in_user_space(vcpu, order_code))
 436                return -EOPNOTSUPP;
 437
 438        if (r1 % 2)
 439                parameter = vcpu->run->s.regs.gprs[r1];
 440        else
 441                parameter = vcpu->run->s.regs.gprs[r1 + 1];
 442
 443        trace_kvm_s390_handle_sigp(vcpu, order_code, cpu_addr, parameter);
 444        switch (order_code) {
 445        case SIGP_SET_ARCHITECTURE:
 446                vcpu->stat.instruction_sigp_arch++;
 447                rc = __sigp_set_arch(vcpu, parameter);
 448                break;
 449        default:
 450                rc = handle_sigp_dst(vcpu, order_code, cpu_addr,
 451                                     parameter,
 452                                     &vcpu->run->s.regs.gprs[r1]);
 453        }
 454
 455        if (rc < 0)
 456                return rc;
 457
 458        kvm_s390_set_psw_cc(vcpu, rc);
 459        return 0;
 460}
 461
 462/*
 463 * Handle SIGP partial execution interception.
 464 *
 465 * This interception will occur at the source cpu when a source cpu sends an
 466 * external call to a target cpu and the target cpu has the WAIT bit set in
 467 * its cpuflags. Interception will occurr after the interrupt indicator bits at
 468 * the target cpu have been set. All error cases will lead to instruction
 469 * interception, therefore nothing is to be checked or prepared.
 470 */
 471int kvm_s390_handle_sigp_pei(struct kvm_vcpu *vcpu)
 472{
 473        int r3 = vcpu->arch.sie_block->ipa & 0x000f;
 474        u16 cpu_addr = vcpu->run->s.regs.gprs[r3];
 475        struct kvm_vcpu *dest_vcpu;
 476        u8 order_code = kvm_s390_get_base_disp_rs(vcpu);
 477
 478        trace_kvm_s390_handle_sigp_pei(vcpu, order_code, cpu_addr);
 479
 480        if (order_code == SIGP_EXTERNAL_CALL) {
 481                dest_vcpu = kvm_get_vcpu(vcpu->kvm, cpu_addr);
 482                BUG_ON(dest_vcpu == NULL);
 483
 484                kvm_s390_vcpu_wakeup(dest_vcpu);
 485                kvm_s390_set_psw_cc(vcpu, SIGP_CC_ORDER_CODE_ACCEPTED);
 486                return 0;
 487        }
 488
 489        return -EOPNOTSUPP;
 490}
 491