unsigned long      : 3;
                unsigned long ccc  : 1; /* Cryptography counter control */
                unsigned long pec  : 1; /* PAI extension control */
-               unsigned long      : 17;
-               unsigned long      : 3;
+               unsigned long      : 15;
+               unsigned long wti  : 1; /* Warning-track */
+               unsigned long      : 4;
                unsigned long lap  : 1; /* Low-address-protection control */
                unsigned long      : 4;
                unsigned long edat : 1; /* Enhanced-DAT-enablement control */
 
        DIAG_STAT_X308,
        DIAG_STAT_X318,
        DIAG_STAT_X320,
+       DIAG_STAT_X49C,
        DIAG_STAT_X500,
        NR_DIAG_STAT
 };
 void _diag308_reset_amode31(void);
 int _diag8c_amode31(struct diag8c *addr, struct ccw_dev_id *devno, size_t len);
 
+/* diag 49c subcodes */
+enum diag49c_sc {
+       DIAG49C_SUBC_ACK = 0,
+       DIAG49C_SUBC_REG = 1
+};
+
+int diag49c(unsigned long subcode);
+
 #endif /* _ASM_S390_DIAG_H */
 
        IRQEXT_CMS,
        IRQEXT_CMC,
        IRQEXT_FTP,
+       IRQEXT_WTI,
        IRQIO_CIO,
        IRQIO_DAS,
        IRQIO_C15,
 enum irq_subclass {
        IRQ_SUBCLASS_MEASUREMENT_ALERT = 5,
        IRQ_SUBCLASS_SERVICE_SIGNAL = 9,
+       IRQ_SUBCLASS_WARNING_TRACK = 33,
 };
 
 #define CR0_IRQ_SUBCLASS_MASK                                    \
 
        unsigned char has_core_type : 1;
        unsigned char has_sprp : 1;
        unsigned char has_hvs : 1;
+       unsigned char has_wti : 1;
        unsigned char has_esca : 1;
        unsigned char has_sief2 : 1;
        unsigned char has_64bscao : 1;
 
        [DIAG_STAT_X308] = { .code = 0x308, .name = "List-Directed IPL" },
        [DIAG_STAT_X318] = { .code = 0x318, .name = "CP Name and Version Codes" },
        [DIAG_STAT_X320] = { .code = 0x320, .name = "Certificate Store" },
+       [DIAG_STAT_X49C] = { .code = 0x49c, .name = "Warning-Track Interruption" },
        [DIAG_STAT_X500] = { .code = 0x500, .name = "Virtio Service" },
 };
 
        return diag_amode31_ops.diag26c(virt_to_phys(req), virt_to_phys(resp), subcode);
 }
 EXPORT_SYMBOL(diag26c);
+
+int diag49c(unsigned long subcode)
+{
+       int rc;
+
+       diag_stat_inc(DIAG_STAT_X49C);
+       asm volatile(
+               "       diag    %[subcode],0,0x49c\n"
+               "       ipm     %[rc]\n"
+               "       srl     %[rc],28\n"
+               : [rc] "=d" (rc)
+               : [subcode] "d" (subcode)
+               : "cc");
+       return rc;
+}
+EXPORT_SYMBOL(diag49c);
 
        {.irq = IRQEXT_CMS, .name = "CMS", .desc = "[EXT] CPU-Measurement: Sampling"},
        {.irq = IRQEXT_CMC, .name = "CMC", .desc = "[EXT] CPU-Measurement: Counter"},
        {.irq = IRQEXT_FTP, .name = "FTP", .desc = "[EXT] HMC FTP Service"},
+       {.irq = IRQEXT_WTI, .name = "WTI", .desc = "[EXT] Warning Track"},
        {.irq = IRQIO_CIO,  .name = "CIO", .desc = "[I/O] Common I/O Layer Interrupt"},
        {.irq = IRQIO_DAS,  .name = "DAS", .desc = "[I/O] DASD"},
        {.irq = IRQIO_C15,  .name = "C15", .desc = "[I/O] 3215"},
 
        sclp.has_ibs = !!(sccb->fac117 & 0x20);
        sclp.has_gisaf = !!(sccb->fac118 & 0x08);
        sclp.has_hvs = !!(sccb->fac119 & 0x80);
+       sclp.has_wti = !!(sccb->fac119 & 0x40);
        sclp.has_kss = !!(sccb->fac98 & 0x01);
        sclp.has_aisii = !!(sccb->fac118 & 0x40);
        sclp.has_aeni = !!(sccb->fac118 & 0x20);