aboutsummaryrefslogtreecommitdiffstats
path: root/arch/s390/kernel/head.S
diff options
context:
space:
mode:
authorMartin Schwidefsky <schwidefsky@de.ibm.com>2012-08-23 10:18:09 -0400
committerMartin Schwidefsky <schwidefsky@de.ibm.com>2012-10-09 08:16:58 -0400
commit51eee033dca3d6dc81febc5a69f30b964f3bddf3 (patch)
tree5f5a7b981e2febf38671cb5808e4acddde0005d3 /arch/s390/kernel/head.S
parentcc5b9a45184e90037e6d5353279ec358e57965fd (diff)
s390: add support to start the kernel in 64 bit mode.
Do the switch to z/Architecture (alias 64 bit) mode early in head.S. If the machine is already running in 64 bit mode the sigp turns into a nop. With this change it doesn't matter in which mode the kernel is started. Reviewd-by: Heiko Carstens <heiko.carstens@de.ibm.com> Signed-off-by: Martin Schwidefsky <schwidefsky@de.ibm.com>
Diffstat (limited to 'arch/s390/kernel/head.S')
-rw-r--r--arch/s390/kernel/head.S101
1 files changed, 70 insertions, 31 deletions
diff --git a/arch/s390/kernel/head.S b/arch/s390/kernel/head.S
index 805b6686b641..984726cbce16 100644
--- a/arch/s390/kernel/head.S
+++ b/arch/s390/kernel/head.S
@@ -52,7 +52,7 @@ __HEAD
52 .long 0x02000370,0x60000050 # the channel program the PSW 52 .long 0x02000370,0x60000050 # the channel program the PSW
53 .long 0x020003c0,0x60000050 # at location 0 is loaded. 53 .long 0x020003c0,0x60000050 # at location 0 is loaded.
54 .long 0x02000410,0x60000050 # Initial processing starts 54 .long 0x02000410,0x60000050 # Initial processing starts
55 .long 0x02000460,0x60000050 # at 0xf0 = iplstart. 55 .long 0x02000460,0x60000050 # at 0x200 = iplstart.
56 .long 0x020004b0,0x60000050 56 .long 0x020004b0,0x60000050
57 .long 0x02000500,0x60000050 57 .long 0x02000500,0x60000050
58 .long 0x02000550,0x60000050 58 .long 0x02000550,0x60000050
@@ -62,11 +62,54 @@ __HEAD
62 .long 0x02000690,0x60000050 62 .long 0x02000690,0x60000050
63 .long 0x020006e0,0x20000050 63 .long 0x020006e0,0x20000050
64 64
65 .org 0xf0 65 .org 0x200
66#
67# subroutine to set architecture mode
68#
69.Lsetmode:
70#ifdef CONFIG_64BIT
71 mvi __LC_AR_MODE_ID,1 # set esame flag
72 slr %r0,%r0 # set cpuid to zero
73 lhi %r1,2 # mode 2 = esame (dump)
74 sigp %r1,%r0,0x12 # switch to esame mode
75 bras %r13,0f
76 .fill 16,4,0x0
770: lmh %r0,%r15,0(%r13) # clear high-order half of gprs
78 sam31 # switch to 31 bit addressing mode
79#else
80 mvi __LC_AR_MODE_ID,0 # set ESA flag (mode 0)
81#endif
82 br %r14
83
84#
85# subroutine to wait for end I/O
86#
87.Lirqwait:
88#ifdef CONFIG_64BIT
89 mvc 0x1f0(16),.Lnewpsw # set up IO interrupt psw
90 lpsw .Lwaitpsw
91.Lioint:
92 br %r14
93 .align 8
94.Lnewpsw:
95 .quad 0x0000000080000000,.Lioint
96#else
97 mvc 0x78(8),.Lnewpsw # set up IO interrupt psw
98 lpsw .Lwaitpsw
99.Lioint:
100 br %r14
101 .align 8
102.Lnewpsw:
103 .long 0x00080000,0x80000000+.Lioint
104#endif
105.Lwaitpsw:
106 .long 0x020a0000,0x80000000+.Lioint
107
66# 108#
67# subroutine for loading cards from the reader 109# subroutine for loading cards from the reader
68# 110#
69.Lloader: 111.Lloader:
112 la %r4,0(%r14)
70 la %r3,.Lorb # r2 = address of orb into r2 113 la %r3,.Lorb # r2 = address of orb into r2
71 la %r5,.Lirb # r4 = address of irb 114 la %r5,.Lirb # r4 = address of irb
72 la %r6,.Lccws 115 la %r6,.Lccws
@@ -83,9 +126,7 @@ __HEAD
83 ssch 0(%r3) # load chunk of 1600 bytes 126 ssch 0(%r3) # load chunk of 1600 bytes
84 bnz .Llderr 127 bnz .Llderr
85.Lwait4irq: 128.Lwait4irq:
86 mvc 0x78(8),.Lnewpsw # set up IO interrupt psw 129 bas %r14,.Lirqwait
87 lpsw .Lwaitpsw
88.Lioint:
89 c %r1,0xb8 # compare subchannel number 130 c %r1,0xb8 # compare subchannel number
90 bne .Lwait4irq 131 bne .Lwait4irq
91 tsch 0(%r5) 132 tsch 0(%r5)
@@ -104,7 +145,7 @@ __HEAD
104 sr %r0,%r3 # #ccws*80-residual=#bytes read 145 sr %r0,%r3 # #ccws*80-residual=#bytes read
105 ar %r2,%r0 146 ar %r2,%r0
106 147
107 br %r14 # r2 contains the total size 148 br %r4 # r2 contains the total size
108 149
109.Lcont: 150.Lcont:
110 ahi %r2,0x640 # add 0x640 to total size 151 ahi %r2,0x640 # add 0x640 to total size
@@ -128,10 +169,6 @@ __HEAD
128.Lloadp:.long 0,0 169.Lloadp:.long 0,0
129 .align 8 170 .align 8
130.Lcrash:.long 0x000a0000,0x00000000 171.Lcrash:.long 0x000a0000,0x00000000
131.Lnewpsw:
132 .long 0x00080000,0x80000000+.Lioint
133.Lwaitpsw:
134 .long 0x020a0000,0x80000000+.Lioint
135 172
136 .align 8 173 .align 8
137.Lccws: .rept 19 174.Lccws: .rept 19
@@ -140,6 +177,7 @@ __HEAD
140 .long 0x02200050,0x00000000 177 .long 0x02200050,0x00000000
141 178
142iplstart: 179iplstart:
180 bas %r14,.Lsetmode # Immediately switch to 64 bit mode
143 lh %r1,0xb8 # test if subchannel number 181 lh %r1,0xb8 # test if subchannel number
144 bct %r1,.Lnoload # is valid 182 bct %r1,.Lnoload # is valid
145 l %r1,0xb8 # load ipl subchannel number 183 l %r1,0xb8 # load ipl subchannel number
@@ -209,8 +247,8 @@ iplstart:
209# 247#
210# reset files in VM reader 248# reset files in VM reader
211# 249#
212 stidp __LC_SAVE_AREA_SYNC # store cpuid 250 stidp .Lcpuid # store cpuid
213 tm __LC_SAVE_AREA_SYNC,0xff# running VM ? 251 tm .Lcpuid,0xff # running VM ?
214 bno .Lnoreset 252 bno .Lnoreset
215 la %r2,.Lreset 253 la %r2,.Lreset
216 lhi %r3,26 254 lhi %r3,26
@@ -222,23 +260,14 @@ iplstart:
222 tm 31(%r5),0xff # bits is set in the schib 260 tm 31(%r5),0xff # bits is set in the schib
223 bz .Lnoreset 261 bz .Lnoreset
224.Lwaitforirq: 262.Lwaitforirq:
225 mvc 0x78(8),.Lrdrnewpsw # set up IO interrupt psw 263 bas %r14,.Lirqwait # wait for IO interrupt
226.Lwaitrdrirq:
227 lpsw .Lrdrwaitpsw
228.Lrdrint:
229 c %r1,0xb8 # compare subchannel number 264 c %r1,0xb8 # compare subchannel number
230 bne .Lwaitrdrirq 265 bne .Lwaitforirq
231 la %r5,.Lirb 266 la %r5,.Lirb
232 tsch 0(%r5) 267 tsch 0(%r5)
233.Lnoreset: 268.Lnoreset:
234 b .Lnoload 269 b .Lnoload
235 270
236 .align 8
237.Lrdrnewpsw:
238 .long 0x00080000,0x80000000+.Lrdrint
239.Lrdrwaitpsw:
240 .long 0x020a0000,0x80000000+.Lrdrint
241
242# 271#
243# everything loaded, go for it 272# everything loaded, go for it
244# 273#
@@ -254,6 +283,8 @@ iplstart:
254 .byte 0xc8,0xd6,0xd3,0xc4 # "change rdr all keep nohold" 283 .byte 0xc8,0xd6,0xd3,0xc4 # "change rdr all keep nohold"
255.L_eof: .long 0xc5d6c600 /* C'EOF' */ 284.L_eof: .long 0xc5d6c600 /* C'EOF' */
256.L_hdr: .long 0xc8c4d900 /* C'HDR' */ 285.L_hdr: .long 0xc8c4d900 /* C'HDR' */
286 .align 8
287.Lcpuid:.fill 8,1,0
257 288
258# 289#
259# SALIPL loader support. Based on a patch by Rob van der Heij. 290# SALIPL loader support. Based on a patch by Rob van der Heij.
@@ -263,6 +294,7 @@ iplstart:
263 .org 0x800 294 .org 0x800
264ENTRY(start) 295ENTRY(start)
265 stm %r0,%r15,0x07b0 # store registers 296 stm %r0,%r15,0x07b0 # store registers
297 bas %r14,.Lsetmode # Immediately switch to 64 bit mode
266 basr %r12,%r0 298 basr %r12,%r0
267.base: 299.base:
268 l %r11,.parm 300 l %r11,.parm
@@ -343,6 +375,18 @@ ENTRY(startup)
343ENTRY(startup_kdump) 375ENTRY(startup_kdump)
344 j .Lep_startup_kdump 376 j .Lep_startup_kdump
345.Lep_startup_normal: 377.Lep_startup_normal:
378#ifdef CONFIG_64BIT
379 mvi __LC_AR_MODE_ID,1 # set esame flag
380 slr %r0,%r0 # set cpuid to zero
381 lhi %r1,2 # mode 2 = esame (dump)
382 sigp %r1,%r0,0x12 # switch to esame mode
383 bras %r13,0f
384 .fill 16,4,0x0
3850: lmh %r0,%r15,0(%r13) # clear high-order half of gprs
386 sam31 # switch to 31 bit addressing mode
387#else
388 mvi __LC_AR_MODE_ID,0 # set ESA flag (mode 0)
389#endif
346 basr %r13,0 # get base 390 basr %r13,0 # get base
347.LPG0: 391.LPG0:
348 xc 0x200(256),0x200 # partially clear lowcore 392 xc 0x200(256),0x200 # partially clear lowcore
@@ -410,22 +454,17 @@ ENTRY(startup_kdump)
410#endif 454#endif
411 455
412#ifdef CONFIG_64BIT 456#ifdef CONFIG_64BIT
413 mvi __LC_AR_MODE_ID,1 # set esame flag 457 /* Continue with 64bit startup code in head64.S */
414 slr %r0,%r0 # set cpuid to zero
415 lhi %r1,2 # mode 2 = esame (dump)
416 sigp %r1,%r0,0x12 # switch to esame mode
417 sam64 # switch to 64 bit mode 458 sam64 # switch to 64 bit mode
418 larl %r13,4f
419 lmh %r0,%r15,0(%r13) # clear high-order half
420 jg startup_continue 459 jg startup_continue
4214: .fill 16,4,0x0
422#else 460#else
423 mvi __LC_AR_MODE_ID,0 # set ESA flag (mode 0) 461 /* Continue with 31bit startup code in head31.S */
424 l %r13,4f-.LPG0(%r13) 462 l %r13,4f-.LPG0(%r13)
425 b 0(%r13) 463 b 0(%r13)
426 .align 8 464 .align 8
4274: .long startup_continue 4654: .long startup_continue
428#endif 466#endif
467
429 .align 8 468 .align 8
4305: .long 0x7fffffff,0xffffffff 4695: .long 0x7fffffff,0xffffffff
431 470