diff --git a/tools/kvm/Makefile b/tools/kvm/Makefile
index 5df358d..e288731 100644
--- a/tools/kvm/Makefile
+++ b/tools/kvm/Makefile
@@ -178,7 +178,7 @@ ifeq ($(ARCH), arm64)
 	OBJS		+= arm/aarch64/kvm-cpu.o
 	ARCH_INCLUDE	:= $(HDRS_ARM_COMMON)
 	ARCH_INCLUDE	+= -Iarm/aarch64/include
-
+	CFLAGS		+= -static
 	ARCH_WANT_LIBFDT := y
 endif
 
diff --git a/tools/kvm/arm/aarch64/cortex-a57.c b/tools/kvm/arm/aarch64/cortex-a57.c
index 0c340fb..d079fd4 100644
--- a/tools/kvm/arm/aarch64/cortex-a57.c
+++ b/tools/kvm/arm/aarch64/cortex-a57.c
@@ -71,10 +71,17 @@ static struct kvm_arm_target target_cortex_a57 = {
 	.init		= cortex_a57__vcpu_init,
 };
 
+static struct kvm_arm_target target_xgene_potenza = {
+	.id		= KVM_ARM_TARGET_XGENE_POTENZA,
+	.compatible	= "arm,arm-v8",
+	.init		= cortex_a57__vcpu_init,
+};
+
 static int cortex_a57__core_init(struct kvm *kvm)
 {
 	return (kvm_cpu__register_kvm_arm_target(&target_aem_v8) ||
 		kvm_cpu__register_kvm_arm_target(&target_foundation_v8) ||
-		kvm_cpu__register_kvm_arm_target(&target_cortex_a57));
+		kvm_cpu__register_kvm_arm_target(&target_cortex_a57) ||
+		kvm_cpu__register_kvm_arm_target(&target_xgene_potenza));
 }
 core_init(cortex_a57__core_init);
diff --git a/tools/kvm/arm/fdt.c b/tools/kvm/arm/fdt.c
index 5e18c11..4433829 100644
--- a/tools/kvm/arm/fdt.c
+++ b/tools/kvm/arm/fdt.c
@@ -160,6 +160,8 @@ static int setup_fdt(struct kvm *kvm)
 	_FDT(fdt_property_cell(fdt, "cpu_off", KVM_PSCI_FN_CPU_OFF));
 	_FDT(fdt_property_cell(fdt, "cpu_on", KVM_PSCI_FN_CPU_ON));
 	_FDT(fdt_property_cell(fdt, "migrate", KVM_PSCI_FN_MIGRATE));
+	_FDT(fdt_property_cell(fdt, "system_off", KVM_PSCI_FN_SYSTEM_OFF));
+	_FDT(fdt_property_cell(fdt, "system_reset", KVM_PSCI_FN_SYSTEM_RESET));
 	_FDT(fdt_end_node(fdt));
 
 	/* Finalise. */
diff --git a/tools/kvm/arm/kvm-cpu.c b/tools/kvm/arm/kvm-cpu.c
index d31e7b1..2297b04 100644
--- a/tools/kvm/arm/kvm-cpu.c
+++ b/tools/kvm/arm/kvm-cpu.c
@@ -33,7 +33,7 @@ struct kvm_cpu *kvm_cpu__arch_init(struct kvm *kvm, unsigned long cpu_id)
 	struct kvm_arm_target *target;
 	struct kvm_cpu *vcpu;
 	int coalesced_offset, mmap_size, err = -1;
-	unsigned int i;
+	struct kvm_vcpu_init pinit = { 0 };
 	struct kvm_vcpu_init vcpu_init = {
 		.features = ARM_VCPU_FEATURE_FLAGS(kvm, cpu_id)
 	};
@@ -55,19 +55,32 @@ struct kvm_cpu *kvm_cpu__arch_init(struct kvm *kvm, unsigned long cpu_id)
 	if (vcpu->kvm_run == MAP_FAILED)
 		die("unable to mmap vcpu fd");
 
-	/* Find an appropriate target CPU type. */
-	for (i = 0; i < ARRAY_SIZE(kvm_arm_targets); ++i) {
-		if (!kvm_arm_targets[i])
-			continue;
-		target = kvm_arm_targets[i];
-		vcpu_init.target = target->id;
-		err = ioctl(vcpu->vcpu_fd, KVM_ARM_VCPU_INIT, &vcpu_init);
-		if (!err)
-			break;
-	}
+	/* Find an preferred target CPU type. */
+	err = ioctl(kvm->vm_fd, KVM_ARM_PREFERRED_TARGET, &pinit);
+	if (err)
+		die("KVM_ARM_PREFERRED_TARGET ioctl failed (err %d)\n", err);
+
+	/* Sanity check on target type returned by KVM */
+	if (ARRAY_SIZE(kvm_arm_targets) <= pinit.target)
+		die("Unknown vcpu target type %d from KVM\n", pinit.target);
+
+	/* Get a registerd target type */
+	target = kvm_arm_targets[pinit.target];
+	if (!target)
+		die("Target type %d not registered\n", pinit.target);
+
+	/* Prepare VCPU init target */
+	vcpu_init.target = pinit.target;
+	vcpu_init.features[0] |= pinit.features[0];
+
+	/* Call VCPU init ioctl */
+	err = ioctl(vcpu->vcpu_fd, KVM_ARM_VCPU_INIT, &vcpu_init);
+	if (err)
+		die("KVM_ARM_VCPU_INIT ioctl failed (err %d)\n", err);
 
-	if (err || target->init(vcpu))
-		die("Unable to initialise ARM vcpu");
+	/* Do target specific init */
+	if (target->init(vcpu))
+		die("Unable to initialise ARM vcpu\n");
 
 	coalesced_offset = ioctl(kvm->sys_fd, KVM_CHECK_EXTENSION,
 				 KVM_CAP_COALESCED_MMIO);
diff --git a/tools/kvm/kvm-cpu.c b/tools/kvm/kvm-cpu.c
index be05c49..de33a0a 100644
--- a/tools/kvm/kvm-cpu.c
+++ b/tools/kvm/kvm-cpu.c
@@ -153,6 +153,10 @@ int kvm_cpu__start(struct kvm_cpu *cpu)
 				break;
 			goto exit_kvm;
 		case KVM_EXIT_SHUTDOWN:
+			printf("KVMTOOL: got shutdown exit\n");
+			goto exit_kvm;
+		case KVM_EXIT_RESET:
+			printf("KVMTOOL: got reset exit\n");
 			goto exit_kvm;
 		default: {
 			bool ret;
diff --git a/tools/kvm/kvm.c b/tools/kvm/kvm.c
index cfd30dd..6965fd4 100644
--- a/tools/kvm/kvm.c
+++ b/tools/kvm/kvm.c
@@ -55,6 +55,7 @@ const char *kvm_exit_reasons[] = {
 #ifdef CONFIG_PPC64
 	DEFINE_KVM_EXIT_REASON(KVM_EXIT_PAPR_HCALL),
 #endif
+	DEFINE_KVM_EXIT_REASON(KVM_EXIT_RESET),
 };
 
 static int pause_event;