linux/arch/s390/kvm/gaccess.c
<<
>>
Prefs
   1/*
   2 * guest access functions
   3 *
   4 * Copyright IBM Corp. 2014
   5 *
   6 */
   7
   8#include <linux/vmalloc.h>
   9#include <linux/err.h>
  10#include <asm/pgtable.h>
  11#include "kvm-s390.h"
  12#include "gaccess.h"
  13#include <asm/switch_to.h>
  14
  15union asce {
  16        unsigned long val;
  17        struct {
  18                unsigned long origin : 52; /* Region- or Segment-Table Origin */
  19                unsigned long    : 2;
  20                unsigned long g  : 1; /* Subspace Group Control */
  21                unsigned long p  : 1; /* Private Space Control */
  22                unsigned long s  : 1; /* Storage-Alteration-Event Control */
  23                unsigned long x  : 1; /* Space-Switch-Event Control */
  24                unsigned long r  : 1; /* Real-Space Control */
  25                unsigned long    : 1;
  26                unsigned long dt : 2; /* Designation-Type Control */
  27                unsigned long tl : 2; /* Region- or Segment-Table Length */
  28        };
  29};
  30
  31enum {
  32        ASCE_TYPE_SEGMENT = 0,
  33        ASCE_TYPE_REGION3 = 1,
  34        ASCE_TYPE_REGION2 = 2,
  35        ASCE_TYPE_REGION1 = 3
  36};
  37
  38union region1_table_entry {
  39        unsigned long val;
  40        struct {
  41                unsigned long rto: 52;/* Region-Table Origin */
  42                unsigned long    : 2;
  43                unsigned long p  : 1; /* DAT-Protection Bit */
  44                unsigned long    : 1;
  45                unsigned long tf : 2; /* Region-Second-Table Offset */
  46                unsigned long i  : 1; /* Region-Invalid Bit */
  47                unsigned long    : 1;
  48                unsigned long tt : 2; /* Table-Type Bits */
  49                unsigned long tl : 2; /* Region-Second-Table Length */
  50        };
  51};
  52
  53union region2_table_entry {
  54        unsigned long val;
  55        struct {
  56                unsigned long rto: 52;/* Region-Table Origin */
  57                unsigned long    : 2;
  58                unsigned long p  : 1; /* DAT-Protection Bit */
  59                unsigned long    : 1;
  60                unsigned long tf : 2; /* Region-Third-Table Offset */
  61                unsigned long i  : 1; /* Region-Invalid Bit */
  62                unsigned long    : 1;
  63                unsigned long tt : 2; /* Table-Type Bits */
  64                unsigned long tl : 2; /* Region-Third-Table Length */
  65        };
  66};
  67
  68struct region3_table_entry_fc0 {
  69        unsigned long sto: 52;/* Segment-Table Origin */
  70        unsigned long    : 1;
  71        unsigned long fc : 1; /* Format-Control */
  72        unsigned long p  : 1; /* DAT-Protection Bit */
  73        unsigned long    : 1;
  74        unsigned long tf : 2; /* Segment-Table Offset */
  75        unsigned long i  : 1; /* Region-Invalid Bit */
  76        unsigned long cr : 1; /* Common-Region Bit */
  77        unsigned long tt : 2; /* Table-Type Bits */
  78        unsigned long tl : 2; /* Segment-Table Length */
  79};
  80
  81struct region3_table_entry_fc1 {
  82        unsigned long rfaa : 33; /* Region-Frame Absolute Address */
  83        unsigned long    : 14;
  84        unsigned long av : 1; /* ACCF-Validity Control */
  85        unsigned long acc: 4; /* Access-Control Bits */
  86        unsigned long f  : 1; /* Fetch-Protection Bit */
  87        unsigned long fc : 1; /* Format-Control */
  88        unsigned long p  : 1; /* DAT-Protection Bit */
  89        unsigned long co : 1; /* Change-Recording Override */
  90        unsigned long    : 2;
  91        unsigned long i  : 1; /* Region-Invalid Bit */
  92        unsigned long cr : 1; /* Common-Region Bit */
  93        unsigned long tt : 2; /* Table-Type Bits */
  94        unsigned long    : 2;
  95};
  96
  97union region3_table_entry {
  98        unsigned long val;
  99        struct region3_table_entry_fc0 fc0;
 100        struct region3_table_entry_fc1 fc1;
 101        struct {
 102                unsigned long    : 53;
 103                unsigned long fc : 1; /* Format-Control */
 104                unsigned long    : 4;
 105                unsigned long i  : 1; /* Region-Invalid Bit */
 106                unsigned long cr : 1; /* Common-Region Bit */
 107                unsigned long tt : 2; /* Table-Type Bits */
 108                unsigned long    : 2;
 109        };
 110};
 111
 112struct segment_entry_fc0 {
 113        unsigned long pto: 53;/* Page-Table Origin */
 114        unsigned long fc : 1; /* Format-Control */
 115        unsigned long p  : 1; /* DAT-Protection Bit */
 116        unsigned long    : 3;
 117        unsigned long i  : 1; /* Segment-Invalid Bit */
 118        unsigned long cs : 1; /* Common-Segment Bit */
 119        unsigned long tt : 2; /* Table-Type Bits */
 120        unsigned long    : 2;
 121};
 122
 123struct segment_entry_fc1 {
 124        unsigned long sfaa : 44; /* Segment-Frame Absolute Address */
 125        unsigned long    : 3;
 126        unsigned long av : 1; /* ACCF-Validity Control */
 127        unsigned long acc: 4; /* Access-Control Bits */
 128        unsigned long f  : 1; /* Fetch-Protection Bit */
 129        unsigned long fc : 1; /* Format-Control */
 130        unsigned long p  : 1; /* DAT-Protection Bit */
 131        unsigned long co : 1; /* Change-Recording Override */
 132        unsigned long    : 2;
 133        unsigned long i  : 1; /* Segment-Invalid Bit */
 134        unsigned long cs : 1; /* Common-Segment Bit */
 135        unsigned long tt : 2; /* Table-Type Bits */
 136        unsigned long    : 2;
 137};
 138
 139union segment_table_entry {
 140        unsigned long val;
 141        struct segment_entry_fc0 fc0;
 142        struct segment_entry_fc1 fc1;
 143        struct {
 144                unsigned long    : 53;
 145                unsigned long fc : 1; /* Format-Control */
 146                unsigned long    : 4;
 147                unsigned long i  : 1; /* Segment-Invalid Bit */
 148                unsigned long cs : 1; /* Common-Segment Bit */
 149                unsigned long tt : 2; /* Table-Type Bits */
 150                unsigned long    : 2;
 151        };
 152};
 153
 154enum {
 155        TABLE_TYPE_SEGMENT = 0,
 156        TABLE_TYPE_REGION3 = 1,
 157        TABLE_TYPE_REGION2 = 2,
 158        TABLE_TYPE_REGION1 = 3
 159};
 160
 161union page_table_entry {
 162        unsigned long val;
 163        struct {
 164                unsigned long pfra : 52; /* Page-Frame Real Address */
 165                unsigned long z  : 1; /* Zero Bit */
 166                unsigned long i  : 1; /* Page-Invalid Bit */
 167                unsigned long p  : 1; /* DAT-Protection Bit */
 168                unsigned long co : 1; /* Change-Recording Override */
 169                unsigned long    : 8;
 170        };
 171};
 172
 173/*
 174 * vaddress union in order to easily decode a virtual address into its
 175 * region first index, region second index etc. parts.
 176 */
 177union vaddress {
 178        unsigned long addr;
 179        struct {
 180                unsigned long rfx : 11;
 181                unsigned long rsx : 11;
 182                unsigned long rtx : 11;
 183                unsigned long sx  : 11;
 184                unsigned long px  : 8;
 185                unsigned long bx  : 12;
 186        };
 187        struct {
 188                unsigned long rfx01 : 2;
 189                unsigned long       : 9;
 190                unsigned long rsx01 : 2;
 191                unsigned long       : 9;
 192                unsigned long rtx01 : 2;
 193                unsigned long       : 9;
 194                unsigned long sx01  : 2;
 195                unsigned long       : 29;
 196        };
 197};
 198
 199/*
 200 * raddress union which will contain the result (real or absolute address)
 201 * after a page table walk. The rfaa, sfaa and pfra members are used to
 202 * simply assign them the value of a region, segment or page table entry.
 203 */
 204union raddress {
 205        unsigned long addr;
 206        unsigned long rfaa : 33; /* Region-Frame Absolute Address */
 207        unsigned long sfaa : 44; /* Segment-Frame Absolute Address */
 208        unsigned long pfra : 52; /* Page-Frame Real Address */
 209};
 210
 211union alet {
 212        u32 val;
 213        struct {
 214                u32 reserved : 7;
 215                u32 p        : 1;
 216                u32 alesn    : 8;
 217                u32 alen     : 16;
 218        };
 219};
 220
 221union ald {
 222        u32 val;
 223        struct {
 224                u32     : 1;
 225                u32 alo : 24;
 226                u32 all : 7;
 227        };
 228};
 229
 230struct ale {
 231        unsigned long i      : 1; /* ALEN-Invalid Bit */
 232        unsigned long        : 5;
 233        unsigned long fo     : 1; /* Fetch-Only Bit */
 234        unsigned long p      : 1; /* Private Bit */
 235        unsigned long alesn  : 8; /* Access-List-Entry Sequence Number */
 236        unsigned long aleax  : 16; /* Access-List-Entry Authorization Index */
 237        unsigned long        : 32;
 238        unsigned long        : 1;
 239        unsigned long asteo  : 25; /* ASN-Second-Table-Entry Origin */
 240        unsigned long        : 6;
 241        unsigned long astesn : 32; /* ASTE Sequence Number */
 242} __packed;
 243
 244struct aste {
 245        unsigned long i      : 1; /* ASX-Invalid Bit */
 246        unsigned long ato    : 29; /* Authority-Table Origin */
 247        unsigned long        : 1;
 248        unsigned long b      : 1; /* Base-Space Bit */
 249        unsigned long ax     : 16; /* Authorization Index */
 250        unsigned long atl    : 12; /* Authority-Table Length */
 251        unsigned long        : 2;
 252        unsigned long ca     : 1; /* Controlled-ASN Bit */
 253        unsigned long ra     : 1; /* Reusable-ASN Bit */
 254        unsigned long asce   : 64; /* Address-Space-Control Element */
 255        unsigned long ald    : 32;
 256        unsigned long astesn : 32;
 257        /* .. more fields there */
 258} __packed;
 259
 260int ipte_lock_held(struct kvm_vcpu *vcpu)
 261{
 262        if (vcpu->arch.sie_block->eca & 1) {
 263                int rc;
 264
 265                read_lock(&vcpu->kvm->arch.sca_lock);
 266                rc = kvm_s390_get_ipte_control(vcpu->kvm)->kh != 0;
 267                read_unlock(&vcpu->kvm->arch.sca_lock);
 268                return rc;
 269        }
 270        return vcpu->kvm->arch.ipte_lock_count != 0;
 271}
 272
 273static void ipte_lock_simple(struct kvm_vcpu *vcpu)
 274{
 275        union ipte_control old, new, *ic;
 276
 277        mutex_lock(&vcpu->kvm->arch.ipte_mutex);
 278        vcpu->kvm->arch.ipte_lock_count++;
 279        if (vcpu->kvm->arch.ipte_lock_count > 1)
 280                goto out;
 281retry:
 282        read_lock(&vcpu->kvm->arch.sca_lock);
 283        ic = kvm_s390_get_ipte_control(vcpu->kvm);
 284        do {
 285                old = READ_ONCE(*ic);
 286                if (old.k) {
 287                        read_unlock(&vcpu->kvm->arch.sca_lock);
 288                        cond_resched();
 289                        goto retry;
 290                }
 291                new = old;
 292                new.k = 1;
 293        } while (cmpxchg(&ic->val, old.val, new.val) != old.val);
 294        read_unlock(&vcpu->kvm->arch.sca_lock);
 295out:
 296        mutex_unlock(&vcpu->kvm->arch.ipte_mutex);
 297}
 298
 299static void ipte_unlock_simple(struct kvm_vcpu *vcpu)
 300{
 301        union ipte_control old, new, *ic;
 302
 303        mutex_lock(&vcpu->kvm->arch.ipte_mutex);
 304        vcpu->kvm->arch.ipte_lock_count--;
 305        if (vcpu->kvm->arch.ipte_lock_count)
 306                goto out;
 307        read_lock(&vcpu->kvm->arch.sca_lock);
 308        ic = kvm_s390_get_ipte_control(vcpu->kvm);
 309        do {
 310                old = READ_ONCE(*ic);
 311                new = old;
 312                new.k = 0;
 313        } while (cmpxchg(&ic->val, old.val, new.val) != old.val);
 314        read_unlock(&vcpu->kvm->arch.sca_lock);
 315        wake_up(&vcpu->kvm->arch.ipte_wq);
 316out:
 317        mutex_unlock(&vcpu->kvm->arch.ipte_mutex);
 318}
 319
 320static void ipte_lock_siif(struct kvm_vcpu *vcpu)
 321{
 322        union ipte_control old, new, *ic;
 323
 324retry:
 325        read_lock(&vcpu->kvm->arch.sca_lock);
 326        ic = kvm_s390_get_ipte_control(vcpu->kvm);
 327        do {
 328                old = READ_ONCE(*ic);
 329                if (old.kg) {
 330                        read_unlock(&vcpu->kvm->arch.sca_lock);
 331                        cond_resched();
 332                        goto retry;
 333                }
 334                new = old;
 335                new.k = 1;
 336                new.kh++;
 337        } while (cmpxchg(&ic->val, old.val, new.val) != old.val);
 338        read_unlock(&vcpu->kvm->arch.sca_lock);
 339}
 340
 341static void ipte_unlock_siif(struct kvm_vcpu *vcpu)
 342{
 343        union ipte_control old, new, *ic;
 344
 345        read_lock(&vcpu->kvm->arch.sca_lock);
 346        ic = kvm_s390_get_ipte_control(vcpu->kvm);
 347        do {
 348                old = READ_ONCE(*ic);
 349                new = old;
 350                new.kh--;
 351                if (!new.kh)
 352                        new.k = 0;
 353        } while (cmpxchg(&ic->val, old.val, new.val) != old.val);
 354        read_unlock(&vcpu->kvm->arch.sca_lock);
 355        if (!new.kh)
 356                wake_up(&vcpu->kvm->arch.ipte_wq);
 357}
 358
 359void ipte_lock(struct kvm_vcpu *vcpu)
 360{
 361        if (vcpu->arch.sie_block->eca & 1)
 362                ipte_lock_siif(vcpu);
 363        else
 364                ipte_lock_simple(vcpu);
 365}
 366
 367void ipte_unlock(struct kvm_vcpu *vcpu)
 368{
 369        if (vcpu->arch.sie_block->eca & 1)
 370                ipte_unlock_siif(vcpu);
 371        else
 372                ipte_unlock_simple(vcpu);
 373}
 374
 375static int ar_translation(struct kvm_vcpu *vcpu, union asce *asce, ar_t ar,
 376                          enum gacc_mode mode)
 377{
 378        union alet alet;
 379        struct ale ale;
 380        struct aste aste;
 381        unsigned long ald_addr, authority_table_addr;
 382        union ald ald;
 383        int eax, rc;
 384        u8 authority_table;
 385
 386        if (ar >= NUM_ACRS)
 387                return -EINVAL;
 388
 389        save_access_regs(vcpu->run->s.regs.acrs);
 390        alet.val = vcpu->run->s.regs.acrs[ar];
 391
 392        if (ar == 0 || alet.val == 0) {
 393                asce->val = vcpu->arch.sie_block->gcr[1];
 394                return 0;
 395        } else if (alet.val == 1) {
 396                asce->val = vcpu->arch.sie_block->gcr[7];
 397                return 0;
 398        }
 399
 400        if (alet.reserved)
 401                return PGM_ALET_SPECIFICATION;
 402
 403        if (alet.p)
 404                ald_addr = vcpu->arch.sie_block->gcr[5];
 405        else
 406                ald_addr = vcpu->arch.sie_block->gcr[2];
 407        ald_addr &= 0x7fffffc0;
 408
 409        rc = read_guest_real(vcpu, ald_addr + 16, &ald.val, sizeof(union ald));
 410        if (rc)
 411                return rc;
 412
 413        if (alet.alen / 8 > ald.all)
 414                return PGM_ALEN_TRANSLATION;
 415
 416        if (0x7fffffff - ald.alo * 128 < alet.alen * 16)
 417                return PGM_ADDRESSING;
 418
 419        rc = read_guest_real(vcpu, ald.alo * 128 + alet.alen * 16, &ale,
 420                             sizeof(struct ale));
 421        if (rc)
 422                return rc;
 423
 424        if (ale.i == 1)
 425                return PGM_ALEN_TRANSLATION;
 426        if (ale.alesn != alet.alesn)
 427                return PGM_ALE_SEQUENCE;
 428
 429        rc = read_guest_real(vcpu, ale.asteo * 64, &aste, sizeof(struct aste));
 430        if (rc)
 431                return rc;
 432
 433        if (aste.i)
 434                return PGM_ASTE_VALIDITY;
 435        if (aste.astesn != ale.astesn)
 436                return PGM_ASTE_SEQUENCE;
 437
 438        if (ale.p == 1) {
 439                eax = (vcpu->arch.sie_block->gcr[8] >> 16) & 0xffff;
 440                if (ale.aleax != eax) {
 441                        if (eax / 16 > aste.atl)
 442                                return PGM_EXTENDED_AUTHORITY;
 443
 444                        authority_table_addr = aste.ato * 4 + eax / 4;
 445
 446                        rc = read_guest_real(vcpu, authority_table_addr,
 447                                             &authority_table,
 448                                             sizeof(u8));
 449                        if (rc)
 450                                return rc;
 451
 452                        if ((authority_table & (0x40 >> ((eax & 3) * 2))) == 0)
 453                                return PGM_EXTENDED_AUTHORITY;
 454                }
 455        }
 456
 457        if (ale.fo == 1 && mode == GACC_STORE)
 458                return PGM_PROTECTION;
 459
 460        asce->val = aste.asce;
 461        return 0;
 462}
 463
 464struct trans_exc_code_bits {
 465        unsigned long addr : 52; /* Translation-exception Address */
 466        unsigned long fsi  : 2;  /* Access Exception Fetch/Store Indication */
 467        unsigned long      : 6;
 468        unsigned long b60  : 1;
 469        unsigned long b61  : 1;
 470        unsigned long as   : 2;  /* ASCE Identifier */
 471};
 472
 473enum {
 474        FSI_UNKNOWN = 0, /* Unknown wether fetch or store */
 475        FSI_STORE   = 1, /* Exception was due to store operation */
 476        FSI_FETCH   = 2  /* Exception was due to fetch operation */
 477};
 478
 479static int get_vcpu_asce(struct kvm_vcpu *vcpu, union asce *asce,
 480                         ar_t ar, enum gacc_mode mode)
 481{
 482        int rc;
 483        struct psw_bits psw = psw_bits(vcpu->arch.sie_block->gpsw);
 484        struct kvm_s390_pgm_info *pgm = &vcpu->arch.pgm;
 485        struct trans_exc_code_bits *tec_bits;
 486
 487        memset(pgm, 0, sizeof(*pgm));
 488        tec_bits = (struct trans_exc_code_bits *)&pgm->trans_exc_code;
 489        tec_bits->fsi = mode == GACC_STORE ? FSI_STORE : FSI_FETCH;
 490        tec_bits->as = psw.as;
 491
 492        if (!psw.t) {
 493                asce->val = 0;
 494                asce->r = 1;
 495                return 0;
 496        }
 497
 498        if (mode == GACC_IFETCH)
 499                psw.as = psw.as == PSW_AS_HOME ? PSW_AS_HOME : PSW_AS_PRIMARY;
 500
 501        switch (psw.as) {
 502        case PSW_AS_PRIMARY:
 503                asce->val = vcpu->arch.sie_block->gcr[1];
 504                return 0;
 505        case PSW_AS_SECONDARY:
 506                asce->val = vcpu->arch.sie_block->gcr[7];
 507                return 0;
 508        case PSW_AS_HOME:
 509                asce->val = vcpu->arch.sie_block->gcr[13];
 510                return 0;
 511        case PSW_AS_ACCREG:
 512                rc = ar_translation(vcpu, asce, ar, mode);
 513                switch (rc) {
 514                case PGM_ALEN_TRANSLATION:
 515                case PGM_ALE_SEQUENCE:
 516                case PGM_ASTE_VALIDITY:
 517                case PGM_ASTE_SEQUENCE:
 518                case PGM_EXTENDED_AUTHORITY:
 519                        vcpu->arch.pgm.exc_access_id = ar;
 520                        break;
 521                case PGM_PROTECTION:
 522                        tec_bits->b60 = 1;
 523                        tec_bits->b61 = 1;
 524                        break;
 525                }
 526                if (rc > 0)
 527                        pgm->code = rc;
 528                return rc;
 529        }
 530        return 0;
 531}
 532
 533static int deref_table(struct kvm *kvm, unsigned long gpa, unsigned long *val)
 534{
 535        return kvm_read_guest(kvm, gpa, val, sizeof(*val));
 536}
 537
 538/**
 539 * guest_translate - translate a guest virtual into a guest absolute address
 540 * @vcpu: virtual cpu
 541 * @gva: guest virtual address
 542 * @gpa: points to where guest physical (absolute) address should be stored
 543 * @asce: effective asce
 544 * @mode: indicates the access mode to be used
 545 *
 546 * Translate a guest virtual address into a guest absolute address by means
 547 * of dynamic address translation as specified by the architecture.
 548 * If the resulting absolute address is not available in the configuration
 549 * an addressing exception is indicated and @gpa will not be changed.
 550 *
 551 * Returns: - zero on success; @gpa contains the resulting absolute address
 552 *          - a negative value if guest access failed due to e.g. broken
 553 *            guest mapping
 554 *          - a positve value if an access exception happened. In this case
 555 *            the returned value is the program interruption code as defined
 556 *            by the architecture
 557 */
 558static unsigned long guest_translate(struct kvm_vcpu *vcpu, unsigned long gva,
 559                                     unsigned long *gpa, const union asce asce,
 560                                     enum gacc_mode mode)
 561{
 562        union vaddress vaddr = {.addr = gva};
 563        union raddress raddr = {.addr = gva};
 564        union page_table_entry pte;
 565        int dat_protection = 0;
 566        union ctlreg0 ctlreg0;
 567        unsigned long ptr;
 568        int edat1, edat2;
 569
 570        ctlreg0.val = vcpu->arch.sie_block->gcr[0];
 571        edat1 = ctlreg0.edat && test_kvm_facility(vcpu->kvm, 8);
 572        edat2 = edat1 && test_kvm_facility(vcpu->kvm, 78);
 573        if (asce.r)
 574                goto real_address;
 575        ptr = asce.origin * 4096;
 576        switch (asce.dt) {
 577        case ASCE_TYPE_REGION1:
 578                if (vaddr.rfx01 > asce.tl)
 579                        return PGM_REGION_FIRST_TRANS;
 580                ptr += vaddr.rfx * 8;
 581                break;
 582        case ASCE_TYPE_REGION2:
 583                if (vaddr.rfx)
 584                        return PGM_ASCE_TYPE;
 585                if (vaddr.rsx01 > asce.tl)
 586                        return PGM_REGION_SECOND_TRANS;
 587                ptr += vaddr.rsx * 8;
 588                break;
 589        case ASCE_TYPE_REGION3:
 590                if (vaddr.rfx || vaddr.rsx)
 591                        return PGM_ASCE_TYPE;
 592                if (vaddr.rtx01 > asce.tl)
 593                        return PGM_REGION_THIRD_TRANS;
 594                ptr += vaddr.rtx * 8;
 595                break;
 596        case ASCE_TYPE_SEGMENT:
 597                if (vaddr.rfx || vaddr.rsx || vaddr.rtx)
 598                        return PGM_ASCE_TYPE;
 599                if (vaddr.sx01 > asce.tl)
 600                        return PGM_SEGMENT_TRANSLATION;
 601                ptr += vaddr.sx * 8;
 602                break;
 603        }
 604        switch (asce.dt) {
 605        case ASCE_TYPE_REGION1: {
 606                union region1_table_entry rfte;
 607
 608                if (kvm_is_error_gpa(vcpu->kvm, ptr))
 609                        return PGM_ADDRESSING;
 610                if (deref_table(vcpu->kvm, ptr, &rfte.val))
 611                        return -EFAULT;
 612                if (rfte.i)
 613                        return PGM_REGION_FIRST_TRANS;
 614                if (rfte.tt != TABLE_TYPE_REGION1)
 615                        return PGM_TRANSLATION_SPEC;
 616                if (vaddr.rsx01 < rfte.tf || vaddr.rsx01 > rfte.tl)
 617                        return PGM_REGION_SECOND_TRANS;
 618                if (edat1)
 619                        dat_protection |= rfte.p;
 620                ptr = rfte.rto * 4096 + vaddr.rsx * 8;
 621        }
 622                /* fallthrough */
 623        case ASCE_TYPE_REGION2: {
 624                union region2_table_entry rste;
 625
 626                if (kvm_is_error_gpa(vcpu->kvm, ptr))
 627                        return PGM_ADDRESSING;
 628                if (deref_table(vcpu->kvm, ptr, &rste.val))
 629                        return -EFAULT;
 630                if (rste.i)
 631                        return PGM_REGION_SECOND_TRANS;
 632                if (rste.tt != TABLE_TYPE_REGION2)
 633                        return PGM_TRANSLATION_SPEC;
 634                if (vaddr.rtx01 < rste.tf || vaddr.rtx01 > rste.tl)
 635                        return PGM_REGION_THIRD_TRANS;
 636                if (edat1)
 637                        dat_protection |= rste.p;
 638                ptr = rste.rto * 4096 + vaddr.rtx * 8;
 639        }
 640                /* fallthrough */
 641        case ASCE_TYPE_REGION3: {
 642                union region3_table_entry rtte;
 643
 644                if (kvm_is_error_gpa(vcpu->kvm, ptr))
 645                        return PGM_ADDRESSING;
 646                if (deref_table(vcpu->kvm, ptr, &rtte.val))
 647                        return -EFAULT;
 648                if (rtte.i)
 649                        return PGM_REGION_THIRD_TRANS;
 650                if (rtte.tt != TABLE_TYPE_REGION3)
 651                        return PGM_TRANSLATION_SPEC;
 652                if (rtte.cr && asce.p && edat2)
 653                        return PGM_TRANSLATION_SPEC;
 654                if (rtte.fc && edat2) {
 655                        dat_protection |= rtte.fc1.p;
 656                        raddr.rfaa = rtte.fc1.rfaa;
 657                        goto absolute_address;
 658                }
 659                if (vaddr.sx01 < rtte.fc0.tf)
 660                        return PGM_SEGMENT_TRANSLATION;
 661                if (vaddr.sx01 > rtte.fc0.tl)
 662                        return PGM_SEGMENT_TRANSLATION;
 663                if (edat1)
 664                        dat_protection |= rtte.fc0.p;
 665                ptr = rtte.fc0.sto * 4096 + vaddr.sx * 8;
 666        }
 667                /* fallthrough */
 668        case ASCE_TYPE_SEGMENT: {
 669                union segment_table_entry ste;
 670
 671                if (kvm_is_error_gpa(vcpu->kvm, ptr))
 672                        return PGM_ADDRESSING;
 673                if (deref_table(vcpu->kvm, ptr, &ste.val))
 674                        return -EFAULT;
 675                if (ste.i)
 676                        return PGM_SEGMENT_TRANSLATION;
 677                if (ste.tt != TABLE_TYPE_SEGMENT)
 678                        return PGM_TRANSLATION_SPEC;
 679                if (ste.cs && asce.p)
 680                        return PGM_TRANSLATION_SPEC;
 681                if (ste.fc && edat1) {
 682                        dat_protection |= ste.fc1.p;
 683                        raddr.sfaa = ste.fc1.sfaa;
 684                        goto absolute_address;
 685                }
 686                dat_protection |= ste.fc0.p;
 687                ptr = ste.fc0.pto * 2048 + vaddr.px * 8;
 688        }
 689        }
 690        if (kvm_is_error_gpa(vcpu->kvm, ptr))
 691                return PGM_ADDRESSING;
 692        if (deref_table(vcpu->kvm, ptr, &pte.val))
 693                return -EFAULT;
 694        if (pte.i)
 695                return PGM_PAGE_TRANSLATION;
 696        if (pte.z)
 697                return PGM_TRANSLATION_SPEC;
 698        if (pte.co && !edat1)
 699                return PGM_TRANSLATION_SPEC;
 700        dat_protection |= pte.p;
 701        raddr.pfra = pte.pfra;
 702real_address:
 703        raddr.addr = kvm_s390_real_to_abs(vcpu, raddr.addr);
 704absolute_address:
 705        if (mode == GACC_STORE && dat_protection)
 706                return PGM_PROTECTION;
 707        if (kvm_is_error_gpa(vcpu->kvm, raddr.addr))
 708                return PGM_ADDRESSING;
 709        *gpa = raddr.addr;
 710        return 0;
 711}
 712
 713static inline int is_low_address(unsigned long ga)
 714{
 715        /* Check for address ranges 0..511 and 4096..4607 */
 716        return (ga & ~0x11fful) == 0;
 717}
 718
 719static int low_address_protection_enabled(struct kvm_vcpu *vcpu,
 720                                          const union asce asce)
 721{
 722        union ctlreg0 ctlreg0 = {.val = vcpu->arch.sie_block->gcr[0]};
 723        psw_t *psw = &vcpu->arch.sie_block->gpsw;
 724
 725        if (!ctlreg0.lap)
 726                return 0;
 727        if (psw_bits(*psw).t && asce.p)
 728                return 0;
 729        return 1;
 730}
 731
 732static int guest_page_range(struct kvm_vcpu *vcpu, unsigned long ga,
 733                            unsigned long *pages, unsigned long nr_pages,
 734                            const union asce asce, enum gacc_mode mode)
 735{
 736        struct kvm_s390_pgm_info *pgm = &vcpu->arch.pgm;
 737        psw_t *psw = &vcpu->arch.sie_block->gpsw;
 738        struct trans_exc_code_bits *tec_bits;
 739        int lap_enabled, rc;
 740
 741        tec_bits = (struct trans_exc_code_bits *)&pgm->trans_exc_code;
 742        lap_enabled = low_address_protection_enabled(vcpu, asce);
 743        while (nr_pages) {
 744                ga = kvm_s390_logical_to_effective(vcpu, ga);
 745                tec_bits->addr = ga >> PAGE_SHIFT;
 746                if (mode == GACC_STORE && lap_enabled && is_low_address(ga)) {
 747                        pgm->code = PGM_PROTECTION;
 748                        return pgm->code;
 749                }
 750                ga &= PAGE_MASK;
 751                if (psw_bits(*psw).t) {
 752                        rc = guest_translate(vcpu, ga, pages, asce, mode);
 753                        if (rc < 0)
 754                                return rc;
 755                        if (rc == PGM_PROTECTION)
 756                                tec_bits->b61 = 1;
 757                        if (rc)
 758                                pgm->code = rc;
 759                } else {
 760                        *pages = kvm_s390_real_to_abs(vcpu, ga);
 761                        if (kvm_is_error_gpa(vcpu->kvm, *pages))
 762                                pgm->code = PGM_ADDRESSING;
 763                }
 764                if (pgm->code)
 765                        return pgm->code;
 766                ga += PAGE_SIZE;
 767                pages++;
 768                nr_pages--;
 769        }
 770        return 0;
 771}
 772
 773int access_guest(struct kvm_vcpu *vcpu, unsigned long ga, ar_t ar, void *data,
 774                 unsigned long len, enum gacc_mode mode)
 775{
 776        psw_t *psw = &vcpu->arch.sie_block->gpsw;
 777        unsigned long _len, nr_pages, gpa, idx;
 778        unsigned long pages_array[2];
 779        unsigned long *pages;
 780        int need_ipte_lock;
 781        union asce asce;
 782        int rc;
 783
 784        if (!len)
 785                return 0;
 786        rc = get_vcpu_asce(vcpu, &asce, ar, mode);
 787        if (rc)
 788                return rc;
 789        nr_pages = (((ga & ~PAGE_MASK) + len - 1) >> PAGE_SHIFT) + 1;
 790        pages = pages_array;
 791        if (nr_pages > ARRAY_SIZE(pages_array))
 792                pages = vmalloc(nr_pages * sizeof(unsigned long));
 793        if (!pages)
 794                return -ENOMEM;
 795        need_ipte_lock = psw_bits(*psw).t && !asce.r;
 796        if (need_ipte_lock)
 797                ipte_lock(vcpu);
 798        rc = guest_page_range(vcpu, ga, pages, nr_pages, asce, mode);
 799        for (idx = 0; idx < nr_pages && !rc; idx++) {
 800                gpa = *(pages + idx) + (ga & ~PAGE_MASK);
 801                _len = min(PAGE_SIZE - (gpa & ~PAGE_MASK), len);
 802                if (mode == GACC_STORE)
 803                        rc = kvm_write_guest(vcpu->kvm, gpa, data, _len);
 804                else
 805                        rc = kvm_read_guest(vcpu->kvm, gpa, data, _len);
 806                len -= _len;
 807                ga += _len;
 808                data += _len;
 809        }
 810        if (need_ipte_lock)
 811                ipte_unlock(vcpu);
 812        if (nr_pages > ARRAY_SIZE(pages_array))
 813                vfree(pages);
 814        return rc;
 815}
 816
 817int access_guest_real(struct kvm_vcpu *vcpu, unsigned long gra,
 818                      void *data, unsigned long len, enum gacc_mode mode)
 819{
 820        unsigned long _len, gpa;
 821        int rc = 0;
 822
 823        while (len && !rc) {
 824                gpa = kvm_s390_real_to_abs(vcpu, gra);
 825                _len = min(PAGE_SIZE - (gpa & ~PAGE_MASK), len);
 826                if (mode)
 827                        rc = write_guest_abs(vcpu, gpa, data, _len);
 828                else
 829                        rc = read_guest_abs(vcpu, gpa, data, _len);
 830                len -= _len;
 831                gra += _len;
 832                data += _len;
 833        }
 834        return rc;
 835}
 836
 837/**
 838 * guest_translate_address - translate guest logical into guest absolute address
 839 *
 840 * Parameter semantics are the same as the ones from guest_translate.
 841 * The memory contents at the guest address are not changed.
 842 *
 843 * Note: The IPTE lock is not taken during this function, so the caller
 844 * has to take care of this.
 845 */
 846int guest_translate_address(struct kvm_vcpu *vcpu, unsigned long gva, ar_t ar,
 847                            unsigned long *gpa, enum gacc_mode mode)
 848{
 849        struct kvm_s390_pgm_info *pgm = &vcpu->arch.pgm;
 850        psw_t *psw = &vcpu->arch.sie_block->gpsw;
 851        struct trans_exc_code_bits *tec;
 852        union asce asce;
 853        int rc;
 854
 855        gva = kvm_s390_logical_to_effective(vcpu, gva);
 856        tec = (struct trans_exc_code_bits *)&pgm->trans_exc_code;
 857        rc = get_vcpu_asce(vcpu, &asce, ar, mode);
 858        tec->addr = gva >> PAGE_SHIFT;
 859        if (rc)
 860                return rc;
 861        if (is_low_address(gva) && low_address_protection_enabled(vcpu, asce)) {
 862                if (mode == GACC_STORE) {
 863                        rc = pgm->code = PGM_PROTECTION;
 864                        return rc;
 865                }
 866        }
 867
 868        if (psw_bits(*psw).t && !asce.r) {      /* Use DAT? */
 869                rc = guest_translate(vcpu, gva, gpa, asce, mode);
 870                if (rc > 0) {
 871                        if (rc == PGM_PROTECTION)
 872                                tec->b61 = 1;
 873                        pgm->code = rc;
 874                }
 875        } else {
 876                rc = 0;
 877                *gpa = kvm_s390_real_to_abs(vcpu, gva);
 878                if (kvm_is_error_gpa(vcpu->kvm, *gpa))
 879                        rc = pgm->code = PGM_ADDRESSING;
 880        }
 881
 882        return rc;
 883}
 884
 885/**
 886 * check_gva_range - test a range of guest virtual addresses for accessibility
 887 */
 888int check_gva_range(struct kvm_vcpu *vcpu, unsigned long gva, ar_t ar,
 889                    unsigned long length, enum gacc_mode mode)
 890{
 891        unsigned long gpa;
 892        unsigned long currlen;
 893        int rc = 0;
 894
 895        ipte_lock(vcpu);
 896        while (length > 0 && !rc) {
 897                currlen = min(length, PAGE_SIZE - (gva % PAGE_SIZE));
 898                rc = guest_translate_address(vcpu, gva, ar, &gpa, mode);
 899                gva += currlen;
 900                length -= currlen;
 901        }
 902        ipte_unlock(vcpu);
 903
 904        return rc;
 905}
 906
 907/**
 908 * kvm_s390_check_low_addr_prot_real - check for low-address protection
 909 * @gra: Guest real address
 910 *
 911 * Checks whether an address is subject to low-address protection and set
 912 * up vcpu->arch.pgm accordingly if necessary.
 913 *
 914 * Return: 0 if no protection exception, or PGM_PROTECTION if protected.
 915 */
 916int kvm_s390_check_low_addr_prot_real(struct kvm_vcpu *vcpu, unsigned long gra)
 917{
 918        struct kvm_s390_pgm_info *pgm = &vcpu->arch.pgm;
 919        psw_t *psw = &vcpu->arch.sie_block->gpsw;
 920        struct trans_exc_code_bits *tec_bits;
 921        union ctlreg0 ctlreg0 = {.val = vcpu->arch.sie_block->gcr[0]};
 922
 923        if (!ctlreg0.lap || !is_low_address(gra))
 924                return 0;
 925
 926        memset(pgm, 0, sizeof(*pgm));
 927        tec_bits = (struct trans_exc_code_bits *)&pgm->trans_exc_code;
 928        tec_bits->fsi = FSI_STORE;
 929        tec_bits->as = psw_bits(*psw).as;
 930        tec_bits->addr = gra >> PAGE_SHIFT;
 931        pgm->code = PGM_PROTECTION;
 932
 933        return pgm->code;
 934}
 935