[kvm:queue 19/54] arch/x86/kvm/mmu/paging_tmpl.h:532:8: error: use of undeclared identifier 'EPT_VIOLATION_RWX_SHIFT'

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



tree:   https://git.kernel.org/pub/scm/virt/kvm/kvm.git queue
head:   59d9e75d641565603e7c293f4cec182d86db8586
commit: 68ca1f59584e5793a3949d8806f683f9245d33f9 [19/54] KVM: x86/mmu: Derive EPT violation RWX bits from EPTE RWX bits
config: x86_64-randconfig-a014 (https://download.01.org/0day-ci/archive/20220409/202204091254.FzYg6D71-lkp@xxxxxxxxx/config)
compiler: clang version 15.0.0 (https://github.com/llvm/llvm-project c29a51b3a257908aebc01cd7c4655665db317d66)
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # https://git.kernel.org/pub/scm/virt/kvm/kvm.git/commit/?id=68ca1f59584e5793a3949d8806f683f9245d33f9
        git remote add kvm https://git.kernel.org/pub/scm/virt/kvm/kvm.git
        git fetch --no-tags kvm queue
        git checkout 68ca1f59584e5793a3949d8806f683f9245d33f9
        # save the config file to linux build tree
        mkdir build_dir
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=clang make.cross W=1 O=build_dir ARCH=x86_64 SHELL=/bin/bash

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@xxxxxxxxx>

All errors (new ones prefixed by >>):

   In file included from arch/x86/kvm/mmu/mmu.c:4259:
>> arch/x86/kvm/mmu/paging_tmpl.h:532:8: error: use of undeclared identifier 'EPT_VIOLATION_RWX_SHIFT'
                                                    EPT_VIOLATION_RWX_SHIFT;
                                                    ^
   1 error generated.
--
>> arch/x86/kvm/vmx/vmx.c:5408:38: error: use of undeclared identifier 'EPT_VIOLATION_RWX_SHIFT'
           error_code |= (exit_qualification & EPT_VIOLATION_RWX_MASK)
                                               ^
   arch/x86/include/asm/vmx.h:551:54: note: expanded from macro 'EPT_VIOLATION_RWX_MASK'
   #define EPT_VIOLATION_RWX_MASK          (VMX_EPT_RWX_MASK << EPT_VIOLATION_RWX_SHIFT)
                                                                ^
   1 error generated.


vim +/EPT_VIOLATION_RWX_SHIFT +532 arch/x86/kvm/mmu/paging_tmpl.h

   301	
   302	static inline bool FNAME(is_last_gpte)(struct kvm_mmu *mmu,
   303					       unsigned int level, unsigned int gpte)
   304	{
   305		/*
   306		 * For EPT and PAE paging (both variants), bit 7 is either reserved at
   307		 * all level or indicates a huge page (ignoring CR3/EPTP).  In either
   308		 * case, bit 7 being set terminates the walk.
   309		 */
   310	#if PTTYPE == 32
   311		/*
   312		 * 32-bit paging requires special handling because bit 7 is ignored if
   313		 * CR4.PSE=0, not reserved.  Clear bit 7 in the gpte if the level is
   314		 * greater than the last level for which bit 7 is the PAGE_SIZE bit.
   315		 *
   316		 * The RHS has bit 7 set iff level < (2 + PSE).  If it is clear, bit 7
   317		 * is not reserved and does not indicate a large page at this level,
   318		 * so clear PT_PAGE_SIZE_MASK in gpte if that is the case.
   319		 */
   320		gpte &= level - (PT32_ROOT_LEVEL + mmu->mmu_role.ext.cr4_pse);
   321	#endif
   322		/*
   323		 * PG_LEVEL_4K always terminates.  The RHS has bit 7 set
   324		 * iff level <= PG_LEVEL_4K, which for our purpose means
   325		 * level == PG_LEVEL_4K; set PT_PAGE_SIZE_MASK in gpte then.
   326		 */
   327		gpte |= level - PG_LEVEL_4K - 1;
   328	
   329		return gpte & PT_PAGE_SIZE_MASK;
   330	}
   331	/*
   332	 * Fetch a guest pte for a guest virtual address, or for an L2's GPA.
   333	 */
   334	static int FNAME(walk_addr_generic)(struct guest_walker *walker,
   335					    struct kvm_vcpu *vcpu, struct kvm_mmu *mmu,
   336					    gpa_t addr, u64 access)
   337	{
   338		int ret;
   339		pt_element_t pte;
   340		pt_element_t __user *ptep_user;
   341		gfn_t table_gfn;
   342		u64 pt_access, pte_access;
   343		unsigned index, accessed_dirty, pte_pkey;
   344		u64 nested_access;
   345		gpa_t pte_gpa;
   346		bool have_ad;
   347		int offset;
   348		u64 walk_nx_mask = 0;
   349		const int write_fault = access & PFERR_WRITE_MASK;
   350		const int user_fault  = access & PFERR_USER_MASK;
   351		const int fetch_fault = access & PFERR_FETCH_MASK;
   352		u16 errcode = 0;
   353		gpa_t real_gpa;
   354		gfn_t gfn;
   355	
   356		trace_kvm_mmu_pagetable_walk(addr, access);
   357	retry_walk:
   358		walker->level = mmu->root_level;
   359		pte           = mmu->get_guest_pgd(vcpu);
   360		have_ad       = PT_HAVE_ACCESSED_DIRTY(mmu);
   361	
   362	#if PTTYPE == 64
   363		walk_nx_mask = 1ULL << PT64_NX_SHIFT;
   364		if (walker->level == PT32E_ROOT_LEVEL) {
   365			pte = mmu->get_pdptr(vcpu, (addr >> 30) & 3);
   366			trace_kvm_mmu_paging_element(pte, walker->level);
   367			if (!FNAME(is_present_gpte)(pte))
   368				goto error;
   369			--walker->level;
   370		}
   371	#endif
   372		walker->max_level = walker->level;
   373		ASSERT(!(is_long_mode(vcpu) && !is_pae(vcpu)));
   374	
   375		/*
   376		 * FIXME: on Intel processors, loads of the PDPTE registers for PAE paging
   377		 * by the MOV to CR instruction are treated as reads and do not cause the
   378		 * processor to set the dirty flag in any EPT paging-structure entry.
   379		 */
   380		nested_access = (have_ad ? PFERR_WRITE_MASK : 0) | PFERR_USER_MASK;
   381	
   382		pte_access = ~0;
   383		++walker->level;
   384	
   385		do {
   386			unsigned long host_addr;
   387	
   388			pt_access = pte_access;
   389			--walker->level;
   390	
   391			index = PT_INDEX(addr, walker->level);
   392			table_gfn = gpte_to_gfn(pte);
   393			offset    = index * sizeof(pt_element_t);
   394			pte_gpa   = gfn_to_gpa(table_gfn) + offset;
   395	
   396			BUG_ON(walker->level < 1);
   397			walker->table_gfn[walker->level - 1] = table_gfn;
   398			walker->pte_gpa[walker->level - 1] = pte_gpa;
   399	
   400			real_gpa = kvm_translate_gpa(vcpu, mmu, gfn_to_gpa(table_gfn),
   401						     nested_access, &walker->fault);
   402	
   403			/*
   404			 * FIXME: This can happen if emulation (for of an INS/OUTS
   405			 * instruction) triggers a nested page fault.  The exit
   406			 * qualification / exit info field will incorrectly have
   407			 * "guest page access" as the nested page fault's cause,
   408			 * instead of "guest page structure access".  To fix this,
   409			 * the x86_exception struct should be augmented with enough
   410			 * information to fix the exit_qualification or exit_info_1
   411			 * fields.
   412			 */
   413			if (unlikely(real_gpa == UNMAPPED_GVA))
   414				return 0;
   415	
   416			host_addr = kvm_vcpu_gfn_to_hva_prot(vcpu, gpa_to_gfn(real_gpa),
   417						    &walker->pte_writable[walker->level - 1]);
   418			if (unlikely(kvm_is_error_hva(host_addr)))
   419				goto error;
   420	
   421			ptep_user = (pt_element_t __user *)((void *)host_addr + offset);
   422			if (unlikely(__get_user(pte, ptep_user)))
   423				goto error;
   424			walker->ptep_user[walker->level - 1] = ptep_user;
   425	
   426			trace_kvm_mmu_paging_element(pte, walker->level);
   427	
   428			/*
   429			 * Inverting the NX it lets us AND it like other
   430			 * permission bits.
   431			 */
   432			pte_access = pt_access & (pte ^ walk_nx_mask);
   433	
   434			if (unlikely(!FNAME(is_present_gpte)(pte)))
   435				goto error;
   436	
   437			if (unlikely(FNAME(is_rsvd_bits_set)(mmu, pte, walker->level))) {
   438				errcode = PFERR_RSVD_MASK | PFERR_PRESENT_MASK;
   439				goto error;
   440			}
   441	
   442			walker->ptes[walker->level - 1] = pte;
   443	
   444			/* Convert to ACC_*_MASK flags for struct guest_walker.  */
   445			walker->pt_access[walker->level - 1] = FNAME(gpte_access)(pt_access ^ walk_nx_mask);
   446		} while (!FNAME(is_last_gpte)(mmu, walker->level, pte));
   447	
   448		pte_pkey = FNAME(gpte_pkeys)(vcpu, pte);
   449		accessed_dirty = have_ad ? pte_access & PT_GUEST_ACCESSED_MASK : 0;
   450	
   451		/* Convert to ACC_*_MASK flags for struct guest_walker.  */
   452		walker->pte_access = FNAME(gpte_access)(pte_access ^ walk_nx_mask);
   453		errcode = permission_fault(vcpu, mmu, walker->pte_access, pte_pkey, access);
   454		if (unlikely(errcode))
   455			goto error;
   456	
   457		gfn = gpte_to_gfn_lvl(pte, walker->level);
   458		gfn += (addr & PT_LVL_OFFSET_MASK(walker->level)) >> PAGE_SHIFT;
   459	
   460		if (PTTYPE == 32 && walker->level > PG_LEVEL_4K && is_cpuid_PSE36())
   461			gfn += pse36_gfn_delta(pte);
   462	
   463		real_gpa = kvm_translate_gpa(vcpu, mmu, gfn_to_gpa(gfn), access, &walker->fault);
   464		if (real_gpa == UNMAPPED_GVA)
   465			return 0;
   466	
   467		walker->gfn = real_gpa >> PAGE_SHIFT;
   468	
   469		if (!write_fault)
   470			FNAME(protect_clean_gpte)(mmu, &walker->pte_access, pte);
   471		else
   472			/*
   473			 * On a write fault, fold the dirty bit into accessed_dirty.
   474			 * For modes without A/D bits support accessed_dirty will be
   475			 * always clear.
   476			 */
   477			accessed_dirty &= pte >>
   478				(PT_GUEST_DIRTY_SHIFT - PT_GUEST_ACCESSED_SHIFT);
   479	
   480		if (unlikely(!accessed_dirty)) {
   481			ret = FNAME(update_accessed_dirty_bits)(vcpu, mmu, walker,
   482								addr, write_fault);
   483			if (unlikely(ret < 0))
   484				goto error;
   485			else if (ret)
   486				goto retry_walk;
   487		}
   488	
   489		pgprintk("%s: pte %llx pte_access %x pt_access %x\n",
   490			 __func__, (u64)pte, walker->pte_access,
   491			 walker->pt_access[walker->level - 1]);
   492		return 1;
   493	
   494	error:
   495		errcode |= write_fault | user_fault;
   496		if (fetch_fault && (is_efer_nx(mmu) || is_cr4_smep(mmu)))
   497			errcode |= PFERR_FETCH_MASK;
   498	
   499		walker->fault.vector = PF_VECTOR;
   500		walker->fault.error_code_valid = true;
   501		walker->fault.error_code = errcode;
   502	
   503	#if PTTYPE == PTTYPE_EPT
   504		/*
   505		 * Use PFERR_RSVD_MASK in error_code to to tell if EPT
   506		 * misconfiguration requires to be injected. The detection is
   507		 * done by is_rsvd_bits_set() above.
   508		 *
   509		 * We set up the value of exit_qualification to inject:
   510		 * [2:0] - Derive from the access bits. The exit_qualification might be
   511		 *         out of date if it is serving an EPT misconfiguration.
   512		 * [5:3] - Calculated by the page walk of the guest EPT page tables
   513		 * [7:8] - Derived from [7:8] of real exit_qualification
   514		 *
   515		 * The other bits are set to 0.
   516		 */
   517		if (!(errcode & PFERR_RSVD_MASK)) {
   518			vcpu->arch.exit_qualification &= (EPT_VIOLATION_GVA_IS_VALID |
   519							  EPT_VIOLATION_GVA_TRANSLATED);
   520			if (write_fault)
   521				vcpu->arch.exit_qualification |= EPT_VIOLATION_ACC_WRITE;
   522			if (user_fault)
   523				vcpu->arch.exit_qualification |= EPT_VIOLATION_ACC_READ;
   524			if (fetch_fault)
   525				vcpu->arch.exit_qualification |= EPT_VIOLATION_ACC_INSTR;
   526	
   527			/*
   528			 * Note, pte_access holds the raw RWX bits from the EPTE, not
   529			 * ACC_*_MASK flags!
   530			 */
   531			vcpu->arch.exit_qualification |= (pte_access & VMX_EPT_RWX_MASK) <<
 > 532							 EPT_VIOLATION_RWX_SHIFT;
   533		}
   534	#endif
   535		walker->fault.address = addr;
   536		walker->fault.nested_page_fault = mmu != vcpu->arch.walk_mmu;
   537		walker->fault.async_page_fault = false;
   538	
   539		trace_kvm_mmu_walker_error(walker->fault.error_code);
   540		return 0;
   541	}
   542	

-- 
0-DAY CI Kernel Test Service
https://01.org/lkp



[Index of Archives]     [KVM ARM]     [KVM ia64]     [KVM ppc]     [Virtualization Tools]     [Spice Development]     [Libvirt]     [Libvirt Users]     [Linux USB Devel]     [Linux Audio Users]     [Yosemite Questions]     [Linux Kernel]     [Linux SCSI]     [XFree86]

  Powered by Linux