Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0 */
0002 /*
0003  * Code that needs to run below 2 GB.
0004  *
0005  * Copyright IBM Corp. 2019
0006  */
0007 
0008 #include <linux/linkage.h>
0009 #include <asm/asm-extable.h>
0010 #include <asm/errno.h>
0011 #include <asm/sigp.h>
0012 
0013     .section .amode31.text,"ax"
0014 /*
0015  * Simplified version of expoline thunk. The normal thunks can not be used here,
0016  * because they might be more than 2 GB away, and not reachable by the relative
0017  * branch. No comdat, exrl, etc. optimizations used here, because it only
0018  * affects a few functions that are not performance-relevant.
0019  */
0020     .macro BR_EX_AMODE31_r14
0021     larl    %r1,0f
0022     ex  0,0(%r1)
0023     j   .
0024 0:  br  %r14
0025     .endm
0026 
0027 /*
0028  * int _diag14_amode31(unsigned long rx, unsigned long ry1, unsigned long subcode)
0029  */
0030 ENTRY(_diag14_amode31)
0031     lgr %r1,%r2
0032     lgr %r2,%r3
0033     lgr %r3,%r4
0034     lhi %r5,-EIO
0035     sam31
0036     diag    %r1,%r2,0x14
0037 .Ldiag14_ex:
0038     ipm %r5
0039     srl %r5,28
0040 .Ldiag14_fault:
0041     sam64
0042     lgfr    %r2,%r5
0043     BR_EX_AMODE31_r14
0044     EX_TABLE_AMODE31(.Ldiag14_ex, .Ldiag14_fault)
0045 ENDPROC(_diag14_amode31)
0046 
0047 /*
0048  * int _diag210_amode31(struct diag210 *addr)
0049  */
0050 ENTRY(_diag210_amode31)
0051     lgr %r1,%r2
0052     lhi %r2,-1
0053     sam31
0054     diag    %r1,%r0,0x210
0055 .Ldiag210_ex:
0056     ipm %r2
0057     srl %r2,28
0058 .Ldiag210_fault:
0059     sam64
0060     lgfr    %r2,%r2
0061     BR_EX_AMODE31_r14
0062     EX_TABLE_AMODE31(.Ldiag210_ex, .Ldiag210_fault)
0063 ENDPROC(_diag210_amode31)
0064 
0065 /*
0066  * int _diag26c_amode31(void *req, void *resp, enum diag26c_sc subcode)
0067  */
0068 ENTRY(_diag26c_amode31)
0069     lghi    %r5,-EOPNOTSUPP
0070     sam31
0071     diag    %r2,%r4,0x26c
0072 .Ldiag26c_ex:
0073     sam64
0074     lgfr    %r2,%r5
0075     BR_EX_AMODE31_r14
0076     EX_TABLE_AMODE31(.Ldiag26c_ex, .Ldiag26c_ex)
0077 ENDPROC(_diag26c_amode31)
0078 
0079 /*
0080  * void _diag0c_amode31(struct hypfs_diag0c_entry *entry)
0081  */
0082 ENTRY(_diag0c_amode31)
0083     sam31
0084     diag    %r2,%r2,0x0c
0085     sam64
0086     BR_EX_AMODE31_r14
0087 ENDPROC(_diag0c_amode31)
0088 
0089 /*
0090  * void _diag308_reset_amode31(void)
0091  *
0092  * Calls diag 308 subcode 1 and continues execution
0093  */
0094 ENTRY(_diag308_reset_amode31)
0095     larl    %r4,.Lctlregs       # Save control registers
0096     stctg   %c0,%c15,0(%r4)
0097     lg  %r2,0(%r4)      # Disable lowcore protection
0098     nilh    %r2,0xefff
0099     larl    %r4,.Lctlreg0
0100     stg %r2,0(%r4)
0101     lctlg   %c0,%c0,0(%r4)
0102     larl    %r4,.Lfpctl     # Floating point control register
0103     stfpc   0(%r4)
0104     larl    %r4,.Lprefix        # Save prefix register
0105     stpx    0(%r4)
0106     larl    %r4,.Lprefix_zero   # Set prefix register to 0
0107     spx 0(%r4)
0108     larl    %r4,.Lcontinue_psw  # Save PSW flags
0109     epsw    %r2,%r3
0110     stm %r2,%r3,0(%r4)
0111     larl    %r4,.Lrestart_part2 # Setup restart PSW at absolute 0
0112     larl    %r3,.Lrestart_diag308_psw
0113     og  %r4,0(%r3)      # Save PSW
0114     lghi    %r3,0
0115     sturg   %r4,%r3         # Use sturg, because of large pages
0116     lghi    %r1,1
0117     lghi    %r0,0
0118     diag    %r0,%r1,0x308
0119 .Lrestart_part2:
0120     lhi %r0,0           # Load r0 with zero
0121     lhi %r1,2           # Use mode 2 = ESAME (dump)
0122     sigp    %r1,%r0,SIGP_SET_ARCHITECTURE   # Switch to ESAME mode
0123     sam64               # Switch to 64 bit addressing mode
0124     larl    %r4,.Lctlregs       # Restore control registers
0125     lctlg   %c0,%c15,0(%r4)
0126     larl    %r4,.Lfpctl     # Restore floating point ctl register
0127     lfpc    0(%r4)
0128     larl    %r4,.Lprefix        # Restore prefix register
0129     spx 0(%r4)
0130     larl    %r4,.Lcontinue_psw  # Restore PSW flags
0131     larl    %r2,.Lcontinue
0132     stg %r2,8(%r4)
0133     lpswe   0(%r4)
0134 .Lcontinue:
0135     BR_EX_AMODE31_r14
0136 ENDPROC(_diag308_reset_amode31)
0137 
0138     .section .amode31.data,"aw",@progbits
0139 .align  8
0140 .Lrestart_diag308_psw:
0141     .long   0x00080000,0x80000000
0142 
0143 .align 8
0144 .Lcontinue_psw:
0145     .quad   0,0
0146 
0147 .align 8
0148 .Lctlreg0:
0149     .quad   0
0150 .Lctlregs:
0151     .rept   16
0152     .quad   0
0153     .endr
0154 .Lfpctl:
0155     .long   0
0156 .Lprefix:
0157     .long   0
0158 .Lprefix_zero:
0159     .long   0