* we do this, we have to be careful not to call any stack-protected
  * function, which is most of the kernel.
  */
-static void __init xen_setup_stackprotector(void)
+static void __init xen_setup_gdt(void)
 {
+       if (xen_feature(XENFEAT_auto_translated_physmap)) {
+#ifdef CONFIG_X86_64
+               unsigned long dummy;
+
+               switch_to_new_gdt(0); /* GDT and GS set */
+
+               /* We are switching of the Xen provided GDT to our HVM mode
+                * GDT. The new GDT has  __KERNEL_CS with CS.L = 1
+                * and we are jumping to reload it.
+                */
+               asm volatile ("pushq %0\n"
+                             "leaq 1f(%%rip),%0\n"
+                             "pushq %0\n"
+                             "lretq\n"
+                             "1:\n"
+                             : "=&r" (dummy) : "0" (__KERNEL_CS));
+
+               /*
+                * While not needed, we also set the %es, %ds, and %fs
+                * to zero. We don't care about %ss as it is NULL.
+                * Strictly speaking this is not needed as Xen zeros those
+                * out (and also MSR_FS_BASE, MSR_GS_BASE, MSR_KERNEL_GS_BASE)
+                *
+                * Linux zeros them in cpu_init() and in secondary_startup_64
+                * (for BSP).
+                */
+               loadsegment(es, 0);
+               loadsegment(ds, 0);
+               loadsegment(fs, 0);
+#else
+               /* PVH: TODO Implement. */
+               BUG();
+#endif
+               return; /* PVH does not need any PV GDT ops. */
+       }
        pv_cpu_ops.write_gdt_entry = xen_write_gdt_entry_boot;
        pv_cpu_ops.load_gdt = xen_load_gdt_boot;
 
         * Set up kernel GDT and segment registers, mainly so that
         * -fstack-protector code can be executed.
         */
-       xen_setup_stackprotector();
+       xen_setup_gdt();
 
        xen_init_irq_ops();
        xen_init_cpuid_mask();