cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

relocate_kernel.S (7602B)


      1/* SPDX-License-Identifier: GPL-2.0-only */
      2/*
      3 * arch/ia64/kernel/relocate_kernel.S
      4 *
      5 * Relocate kexec'able kernel and start it
      6 *
      7 * Copyright (C) 2005 Hewlett-Packard Development Company, L.P.
      8 * Copyright (C) 2005 Khalid Aziz  <khalid.aziz@hp.com>
      9 * Copyright (C) 2005 Intel Corp,  Zou Nan hai <nanhai.zou@intel.com>
     10 */
     11#include <linux/pgtable.h>
     12#include <asm/asmmacro.h>
     13#include <asm/kregs.h>
     14#include <asm/page.h>
     15#include <asm/mca_asm.h>
     16
     17       /* Must be relocatable PIC code callable as a C function
     18        */
     19GLOBAL_ENTRY(relocate_new_kernel)
     20	.prologue
     21	alloc r31=ar.pfs,4,0,0,0
     22        .body
     23.reloc_entry:
     24{
     25	rsm psr.i| psr.ic
     26	mov r2=ip
     27}
     28	;;
     29{
     30        flushrs                         // must be first insn in group
     31        srlz.i
     32}
     33	;;
     34	dep r2=0,r2,61,3		//to physical address
     35	;;
     36	//first switch to physical mode
     37	add r3=1f-.reloc_entry, r2
     38	movl r16 = IA64_PSR_AC|IA64_PSR_BN|IA64_PSR_IC
     39	mov ar.rsc=0	          	// put RSE in enforced lazy mode
     40	;;
     41	add sp=(memory_stack_end - 16 - .reloc_entry),r2
     42	add r8=(register_stack - .reloc_entry),r2
     43	;;
     44	mov r18=ar.rnat
     45	mov ar.bspstore=r8
     46	;;
     47        mov cr.ipsr=r16
     48        mov cr.iip=r3
     49        mov cr.ifs=r0
     50	srlz.i
     51	;;
     52	mov ar.rnat=r18
     53	rfi				// note: this unmask MCA/INIT (psr.mc)
     54	;;
     551:
     56	//physical mode code begin
     57	mov b6=in1
     58	dep r28=0,in2,61,3	//to physical address
     59
     60	// purge all TC entries
     61#define O(member)       IA64_CPUINFO_##member##_OFFSET
     62        GET_THIS_PADDR(r2, ia64_cpu_info) // load phys addr of cpu_info into r2
     63        ;;
     64        addl r17=O(PTCE_STRIDE),r2
     65        addl r2=O(PTCE_BASE),r2
     66        ;;
     67        ld8 r18=[r2],(O(PTCE_COUNT)-O(PTCE_BASE));;    	// r18=ptce_base
     68        ld4 r19=[r2],4                                  // r19=ptce_count[0]
     69        ld4 r21=[r17],4                                 // r21=ptce_stride[0]
     70        ;;
     71        ld4 r20=[r2]                                    // r20=ptce_count[1]
     72        ld4 r22=[r17]                                   // r22=ptce_stride[1]
     73        mov r24=r0
     74        ;;
     75        adds r20=-1,r20
     76        ;;
     77#undef O
     782:
     79        cmp.ltu p6,p7=r24,r19
     80(p7)    br.cond.dpnt.few 4f
     81        mov ar.lc=r20
     823:
     83        ptc.e r18
     84        ;;
     85        add r18=r22,r18
     86        br.cloop.sptk.few 3b
     87        ;;
     88        add r18=r21,r18
     89        add r24=1,r24
     90        ;;
     91        br.sptk.few 2b
     924:
     93        srlz.i
     94        ;;
     95	// purge TR entry for kernel text and data
     96        movl r16=KERNEL_START
     97        mov r18=KERNEL_TR_PAGE_SHIFT<<2
     98        ;;
     99        ptr.i r16, r18
    100        ptr.d r16, r18
    101        ;;
    102        srlz.i
    103        ;;
    104
    105        // purge TR entry for pal code
    106        mov r16=in3
    107        mov r18=IA64_GRANULE_SHIFT<<2
    108        ;;
    109        ptr.i r16,r18
    110        ;;
    111        srlz.i
    112	;;
    113
    114        // purge TR entry for stack
    115        mov r16=IA64_KR(CURRENT_STACK)
    116        ;;
    117        shl r16=r16,IA64_GRANULE_SHIFT
    118        movl r19=PAGE_OFFSET
    119        ;;
    120        add r16=r19,r16
    121        mov r18=IA64_GRANULE_SHIFT<<2
    122        ;;
    123        ptr.d r16,r18
    124        ;;
    125        srlz.i
    126	;;
    127
    128	//copy segments
    129	movl r16=PAGE_MASK
    130        mov  r30=in0                    // in0 is page_list
    131        br.sptk.few .dest_page
    132	;;
    133.loop:
    134	ld8  r30=[in0], 8;;
    135.dest_page:
    136	tbit.z p0, p6=r30, 0;;    	// 0x1 dest page
    137(p6)	and r17=r30, r16
    138(p6)	br.cond.sptk.few .loop;;
    139
    140	tbit.z p0, p6=r30, 1;;		// 0x2 indirect page
    141(p6)	and in0=r30, r16
    142(p6)	br.cond.sptk.few .loop;;
    143
    144	tbit.z p0, p6=r30, 2;;		// 0x4 end flag
    145(p6)	br.cond.sptk.few .end_loop;;
    146
    147	tbit.z p6, p0=r30, 3;;		// 0x8 source page
    148(p6)	br.cond.sptk.few .loop
    149
    150	and r18=r30, r16
    151
    152	// simple copy page, may optimize later
    153	movl r14=PAGE_SIZE/8 - 1;;
    154	mov ar.lc=r14;;
    1551:
    156	ld8 r14=[r18], 8;;
    157	st8 [r17]=r14;;
    158	fc.i r17
    159	add r17=8, r17
    160	br.ctop.sptk.few 1b
    161	br.sptk.few .loop
    162	;;
    163
    164.end_loop:
    165	sync.i			// for fc.i
    166	;;
    167	srlz.i
    168	;;
    169	srlz.d
    170	;;
    171	br.call.sptk.many b0=b6;;
    172
    173.align  32
    174memory_stack:
    175	.fill           8192, 1, 0
    176memory_stack_end:
    177register_stack:
    178	.fill           8192, 1, 0
    179register_stack_end:
    180relocate_new_kernel_end:
    181END(relocate_new_kernel)
    182
    183.global relocate_new_kernel_size
    184relocate_new_kernel_size:
    185	data8	relocate_new_kernel_end - relocate_new_kernel
    186
    187GLOBAL_ENTRY(ia64_dump_cpu_regs)
    188        .prologue
    189        alloc loc0=ar.pfs,1,2,0,0
    190        .body
    191        mov     ar.rsc=0                // put RSE in enforced lazy mode
    192        add     loc1=4*8, in0           // save r4 and r5 first
    193        ;;
    194{
    195        flushrs                         // flush dirty regs to backing store
    196        srlz.i
    197}
    198        st8 [loc1]=r4, 8
    199        ;;
    200        st8 [loc1]=r5, 8
    201        ;;
    202        add loc1=32*8, in0
    203        mov r4=ar.rnat
    204        ;;
    205        st8 [in0]=r0, 8			// r0
    206        st8 [loc1]=r4, 8		// rnat
    207        mov r5=pr
    208        ;;
    209        st8 [in0]=r1, 8			// r1
    210        st8 [loc1]=r5, 8		// pr
    211        mov r4=b0
    212        ;;
    213        st8 [in0]=r2, 8			// r2
    214        st8 [loc1]=r4, 8		// b0
    215        mov r5=b1;
    216        ;;
    217        st8 [in0]=r3, 24		// r3
    218        st8 [loc1]=r5, 8		// b1
    219        mov r4=b2
    220        ;;
    221        st8 [in0]=r6, 8			// r6
    222        st8 [loc1]=r4, 8		// b2
    223	mov r5=b3
    224        ;;
    225        st8 [in0]=r7, 8			// r7
    226        st8 [loc1]=r5, 8		// b3
    227        mov r4=b4
    228        ;;
    229        st8 [in0]=r8, 8			// r8
    230        st8 [loc1]=r4, 8		// b4
    231        mov r5=b5
    232        ;;
    233        st8 [in0]=r9, 8			// r9
    234        st8 [loc1]=r5, 8		// b5
    235        mov r4=b6
    236        ;;
    237        st8 [in0]=r10, 8		// r10
    238        st8 [loc1]=r5, 8		// b6
    239        mov r5=b7
    240        ;;
    241        st8 [in0]=r11, 8		// r11
    242        st8 [loc1]=r5, 8		// b7
    243        mov r4=b0
    244        ;;
    245        st8 [in0]=r12, 8		// r12
    246        st8 [loc1]=r4, 8		// ip
    247        mov r5=loc0
    248	;;
    249        st8 [in0]=r13, 8		// r13
    250        extr.u r5=r5, 0, 38		// ar.pfs.pfm
    251	mov r4=r0			// user mask
    252        ;;
    253        st8 [in0]=r14, 8		// r14
    254        st8 [loc1]=r5, 8		// cfm
    255        ;;
    256        st8 [in0]=r15, 8		// r15
    257        st8 [loc1]=r4, 8        	// user mask
    258	mov r5=ar.rsc
    259        ;;
    260        st8 [in0]=r16, 8		// r16
    261        st8 [loc1]=r5, 8        	// ar.rsc
    262        mov r4=ar.bsp
    263        ;;
    264        st8 [in0]=r17, 8		// r17
    265        st8 [loc1]=r4, 8        	// ar.bsp
    266        mov r5=ar.bspstore
    267        ;;
    268        st8 [in0]=r18, 8		// r18
    269        st8 [loc1]=r5, 8        	// ar.bspstore
    270        mov r4=ar.rnat
    271        ;;
    272        st8 [in0]=r19, 8		// r19
    273        st8 [loc1]=r4, 8        	// ar.rnat
    274        mov r5=ar.ccv
    275        ;;
    276        st8 [in0]=r20, 8		// r20
    277	st8 [loc1]=r5, 8        	// ar.ccv
    278        mov r4=ar.unat
    279        ;;
    280        st8 [in0]=r21, 8		// r21
    281        st8 [loc1]=r4, 8        	// ar.unat
    282        mov r5 = ar.fpsr
    283        ;;
    284        st8 [in0]=r22, 8		// r22
    285        st8 [loc1]=r5, 8        	// ar.fpsr
    286        mov r4 = ar.unat
    287        ;;
    288        st8 [in0]=r23, 8		// r23
    289        st8 [loc1]=r4, 8        	// unat
    290        mov r5 = ar.fpsr
    291        ;;
    292        st8 [in0]=r24, 8		// r24
    293        st8 [loc1]=r5, 8        	// fpsr
    294        mov r4 = ar.pfs
    295        ;;
    296        st8 [in0]=r25, 8		// r25
    297        st8 [loc1]=r4, 8        	// ar.pfs
    298        mov r5 = ar.lc
    299        ;;
    300        st8 [in0]=r26, 8		// r26
    301        st8 [loc1]=r5, 8        	// ar.lc
    302        mov r4 = ar.ec
    303        ;;
    304        st8 [in0]=r27, 8		// r27
    305        st8 [loc1]=r4, 8        	// ar.ec
    306        mov r5 = ar.csd
    307        ;;
    308        st8 [in0]=r28, 8		// r28
    309        st8 [loc1]=r5, 8        	// ar.csd
    310        mov r4 = ar.ssd
    311        ;;
    312        st8 [in0]=r29, 8		// r29
    313        st8 [loc1]=r4, 8        	// ar.ssd
    314        ;;
    315        st8 [in0]=r30, 8		// r30
    316        ;;
    317	st8 [in0]=r31, 8		// r31
    318        mov ar.pfs=loc0
    319        ;;
    320        br.ret.sptk.many rp
    321END(ia64_dump_cpu_regs)