Commit 998d11e1 authored by Bibo Mao's avatar Bibo Mao Committed by Hongchen Zhang
Browse files

LoongArch: kvm: KVM support for 5.10

LoongArch inclusion
category: feature
bugzilla: https://gitee.com/openeuler/kernel/issues/I6BWFP



--------------------------------

KVM adapts to 5.10 kernel based on 4.19 kernel KVM code.

Signed-off-by: default avatarXiangLai Li <lixianglai@loongson.cn>
Signed-off-by: default avatarBibo Mao <maobibo@loongson.cn>

Change-Id: Iea4333d8e0905ab5c04c725defd0e4c421bfe916
parent b61e10dd
Loading
Loading
Loading
Loading
+4 −1
Original line number Diff line number Diff line
obj-y += kernel/
obj-y += mm/
obj-y += vdso/
obj-$(CONFIG_KVM)	+= kvm/

ifdef CONFIG_KVM
obj-y += kvm/
endif

# for cleaning
subdir- += boot
+5 −0
Original line number Diff line number Diff line
@@ -49,6 +49,11 @@ CONFIG_CPU_FREQ_GOV_POWERSAVE=y
CONFIG_LOONGSON3_ACPI_CPUFREQ=y
CONFIG_EFI_CAPSULE_LOADER=m
CONFIG_EFI_TEST=m
CONFIG_VIRTUALIZATION=y
CONFIG_KVM=m
CONFIG_VHOST_NET=m
CONFIG_VHOST_SCSI=m
CONFIG_VHOST_VSOCK=m
CONFIG_MODULES=y
CONFIG_MODULE_FORCE_LOAD=y
CONFIG_MODULE_UNLOAD=y
+0 −1
Original line number Diff line number Diff line
@@ -26,4 +26,3 @@ generic-y += poll.h
generic-y += param.h
generic-y += posix_types.h
generic-y += resource.h
generic-y += kvm_para.h
+92 −11
Original line number Diff line number Diff line
@@ -42,17 +42,18 @@ enum reg1i21_op {
};

enum reg2i12_op {
	addiw_op	= 0x0a,
	addid_op	= 0x0b,
	lu52id_op	= 0x0c,
	ldb_op		= 0xa0,
	ldh_op		= 0xa1,
	ldw_op		= 0xa2,
	ldd_op		= 0xa3,
	stb_op		= 0xa4,
	sth_op		= 0xa5,
	stw_op		= 0xa6,
	std_op		= 0xa7,
	slti_op = 0x8, sltui_op, addiw_op, addid_op,
	lu52id_op, cache_op = 0x18, xvldreplb_op = 0xca,
	ldb_op = 0xa0, ldh_op, ldw_op, ldd_op, stb_op, sth_op,
	stw_op, std_op, ldbu_op, ldhu_op, ldwu_op, preld_op,
	flds_op, fsts_op, fldd_op, fstd_op, vld_op, vst_op, xvld_op,
	xvst_op, ldlw_op = 0xb8, ldrw_op, ldld_op, ldrd_op, stlw_op,
	strw_op, stld_op, strd_op, vldreplb_op = 0xc2,
};

enum reg2i14_op {
	llw_op = 0x20, scw_op, lld_op, scd_op, ldptrw_op, stptrw_op,
	ldptrd_op, stptrd_op,
};

enum reg2i16_op {
@@ -65,6 +66,49 @@ enum reg2i16_op {
	bgeu_op		= 0x1b,
};

enum reg3_op {
	asrtled_op = 0x2, asrtgtd_op,
	addw_op = 0x20, addd_op, subw_op, subd_op,
	slt_op, sltu_op, maskeqz_op, masknez_op,
	nor_op, and_op, or_op, xor_op, orn_op,
	andn_op, sllw_op, srlw_op, sraw_op, slld_op,
	srld_op, srad_op, rotrb_op, rotrh_op,
	rotrw_op, rotrd_op, mulw_op, mulhw_op,
	mulhwu_op, muld_op, mulhd_op, mulhdu_op,
	mulwdw_op, mulwdwu_op, divw_op, modw_op,
	divwu_op, modwu_op, divd_op, modd_op,
	divdu_op, moddu_op, crcwbw_op,
	crcwhw_op, crcwww_op, crcwdw_op, crccwbw_op,
	crccwhw_op, crccwww_op, crccwdw_op, addu12iw_op,
	addu12id_op,
	adcb_op = 0x60, adch_op, adcw_op, adcd_op,
	sbcb_op, sbch_op, sbcw_op, sbcd_op,
	rcrb_op, rcrh_op, rcrw_op, rcrd_op,
	ldxb_op = 0x7000, ldxh_op = 0x7008, ldxw_op = 0x7010, ldxd_op = 0x7018,
	stxb_op = 0x7020, stxh_op = 0x7028, stxw_op = 0x7030, stxd_op = 0x7038,
	ldxbu_op = 0x7040, ldxhu_op = 0x7048, ldxwu_op = 0x7050,
	preldx_op = 0x7058, fldxs_op = 0x7060, fldxd_op = 0x7068,
	fstxs_op = 0x7070, fstxd_op = 0x7078, vldx_op = 0x7080,
	vstx_op = 0x7088, xvldx_op = 0x7090, xvstx_op = 0x7098,
	amswapw_op = 0x70c0, amswapd_op, amaddw_op, amaddd_op, amandw_op,
	amandd_op, amorw_op, amord_op, amxorw_op, amxord_op, ammaxw_op,
	ammaxd_op, amminw_op, ammind_op, ammaxwu_op, ammaxdu_op,
	amminwu_op, ammindu_op, amswap_dbw_op, amswap_dbd_op, amadd_dbw_op,
	amadd_dbd_op, amand_dbw_op, amand_dbd_op, amor_dbw_op, amor_dbd_op,
	amxor_dbw_op, amxor_dbd_op, ammax_dbw_op, ammax_dbd_op, ammin_dbw_op,
	ammin_dbd_op, ammax_dbwu_op, ammax_dbdu_op, ammin_dbwu_op,
	ammin_dbdu_op, fldgts_op = 0x70e8, fldgtd_op,
	fldles_op, fldled_op, fstgts_op, fstgtd_op, fstles_op, fstled_op,
	ldgtb_op, ldgth_op, ldgtw_op, ldgtd_op, ldleb_op, ldleh_op, ldlew_op,
	ldled_op, stgtb_op, stgth_op, stgtw_op, stgtd_op, stleb_op, stleh_op,
	stlew_op, stled_op,
};

enum reg2_op {
	iocsrrdb_op = 0x19200, iocsrrdh_op, iocsrrdw_op, iocsrrdd_op,
	iocsrwrb_op, iocsrwrh_op, iocsrwrw_op, iocsrwrd_op,
};

struct reg0i26_format {
	unsigned int immediate_h : 10;
	unsigned int immediate_l : 16;
@@ -84,6 +128,12 @@ struct reg1i21_format {
	unsigned int opcode : 6;
};

struct reg2_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
	unsigned int opcode : 22;
};

struct reg2i12_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
@@ -91,6 +141,18 @@ struct reg2i12_format {
	unsigned int opcode : 10;
};

struct reg2i14_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
	unsigned int simmediate : 14;
	unsigned int opcode : 8;
};

struct reg0i15_format {
	unsigned int simmediate	: 15;
	unsigned int opcode	: 17;
};

struct reg2i16_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
@@ -98,13 +160,32 @@ struct reg2i16_format {
	unsigned int opcode : 6;
};

struct reg3_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
	unsigned int rk : 5;
	unsigned int opcode : 17;
};

struct reg2csr_format {
	unsigned int rd : 5;
	unsigned int rj : 5;
	unsigned int csr : 14;
	unsigned int opcode : 8;
};

union loongarch_instruction {
	unsigned int word;
	struct reg0i26_format reg0i26_format;
	struct reg1i20_format reg1i20_format;
	struct reg1i21_format reg1i21_format;
	struct reg3_format reg3_format;
	struct reg2_format reg2_format;
	struct reg2i12_format reg2i12_format;
	struct reg2i14_format reg2i14_format;
	struct reg2i16_format reg2i16_format;
	struct reg2csr_format	reg2csr_format;
	struct reg0i15_format	reg0i15_format;
};

#define LOONGARCH_INSN_SIZE	sizeof(union loongarch_instruction)
+4 −19
Original line number Diff line number Diff line
@@ -76,6 +76,8 @@ struct kvm_vcpu_stat {
	u64 huge_merge_exits;
	u64 halt_successful_poll;
	u64 halt_attempted_poll;
	u64 halt_poll_success_ns;
	u64 halt_poll_fail_ns;
	u64 halt_poll_invalid;
	u64 halt_wakeup;
};
@@ -158,23 +160,6 @@ enum emulation_result {
	EMULATE_DO_IOCSR,	/* handle IOCSR request */
};

#define KVM_NR_MEM_OBJS     4
/*
 * We don't want allocation failures within the mmu code, so we preallocate
 * enough memory for a single page fault in a cache.
 */
struct kvm_mmu_memory_cache {
	int nobjs;
	void *objects[KVM_NR_MEM_OBJS];
};

#if defined(CONFIG_CPU_HAS_LASX)
#define FPU_ALIGN		__aligned(32)
#elif defined(CONFIG_CPU_HAS_LSX)
#define FPU_ALIGN		__aligned(16)
#else
#define FPU_ALIGN
#endif
#define KVM_LARCH_FPU		(0x1 << 0)
#define KVM_LARCH_LSX		(0x1 << 1)
#define KVM_LARCH_LASX		(0x1 << 2)
@@ -316,7 +301,7 @@ enum _kvm_fault_result {
#define KVM_ARCH_WANT_MMU_NOTIFIER
int kvm_unmap_hva_range(struct kvm *kvm,
			unsigned long start, unsigned long end, bool blockable);
void kvm_set_spte_hva(struct kvm *kvm, unsigned long hva, pte_t pte);
int kvm_set_spte_hva(struct kvm *kvm, unsigned long hva, pte_t pte);
int kvm_age_hva(struct kvm *kvm, unsigned long start, unsigned long end);
int kvm_test_age_hva(struct kvm *kvm, unsigned long hva);

@@ -344,7 +329,7 @@ static inline bool kvm_is_ifetch_fault(struct kvm_vcpu_arch *arch)
static inline void kvm_arch_hardware_unsetup(void) {}
static inline void kvm_arch_sync_events(struct kvm *kvm) {}
static inline void kvm_arch_free_memslot(struct kvm *kvm,
		struct kvm_memory_slot *free, struct kvm_memory_slot *dont) {}
					struct kvm_memory_slot *slot) {}
static inline void kvm_arch_memslots_updated(struct kvm *kvm, u64 gen) {}
static inline void kvm_arch_sched_in(struct kvm_vcpu *vcpu, int cpu) {}
static inline void kvm_arch_vcpu_blocking(struct kvm_vcpu *vcpu) {}
Loading