xref: /haiku/src/system/boot/platform/atari_m68k/shell.S (revision c2f0a314a012bea8e4ebb35b8ce9e1a85c798727)
1/*
2 * Copyright 2004-2005, Axel Dörfler, axeld@pinc-software.de. All rights reserved.
3 * Copyright 2005, Ingo Weinhold, bonefish@users.sf.net.
4 * Copyright 2007, Haiku, Inc. All Rights Reserved.
5 * Distributed under the terms of the MIT license.
6 *
7 * Author:
8 *		François Revol, revol@free.fr.
9 */
10
11/**	This file contains the boot floppy and BFS boot block entry points for
12 *	the stage 2 boot loader.
13 * x86 ahead:
14 *	The floppy entry point is at offset 0. It's loaded at 0x07c0:0x000. It
15 *	will load the rest of the loader to 0x1000:0x0200 and execute it.
16 *	The BFS boot block will load the whole stage 2 loader to 0x1000:0x0000
17 *	and will then jump to 0x1000:0x0200 as its entry point.
18 *	This code will then switch to protected mode and will directly call
19 *	the entry function of the embedded ELF part of the loader.
20 */
21
22/*
23 * generate boot floppy:
24 * cd src/system/boot/platform/atari_m68k/ ; make fixup_tos_floppy_chksum; cd -
25 * dd if=generated/objects/haiku/m68k/release/system/boot/haiku_loader of=~/floppy.img bs=512 count=20 conv=notrunc
26 * src/system/boot/platform/atari_m68k/fixup_tos_floppy_chksum ~/floppy.img
27 * generate .prg:
28 * generated.m68k/cross-tools/bin/m68k-unknown-haiku-ld -o haiku.prg -T src/system/ldscripts/m68k/boot_prg_atari_m68k.ld generated/objects/haiku/m68k/release/system/boot/boot_loader_atari_m68k
29 */
30
31/*
32 * references :
33 * http://ftp.netbsd.org/pub/NetBSD/NetBSD-release-3-0/src/sys/arch/atari/stand/xxboot/fdboot/fdboot.S
34 */
35
36#include "atari_memory_map.h"
37#include "toscalls.h"
38
39// 1 enabled verbose output
40//#define DEBUG 1
41
42#define GLOBAL(x) .globl x ; x
43#define FUNCTION(x) .global x; .type x,@function; x
44
45#define DRIVE_RETRIES 3
46	// when the drive reading fails for some reason, it will
47	// retry this many times until it will report a failure
48
49
50#define SECTSIZE 512
51
52//.text
53_bs_entry:
54/* main entry point, both from the floppy boot and .prg */
55	bra.s	real_entry
56
57//FAT lookalike to avoid nasty things from happening
58// http://alive.atari.org/alive10/btmania.php
59// MS-DOS values :
60// http://support.microsoft.com/kb/75131/en
61// http://alumnus.caltech.edu/~pje/dosfiles.html
62	.ascii	"Haiku "
63	.byte	0xbe, 0x50, 0x38 // id
64	//LITTLE ENDIAN!
65	.byte	0x00, 0x02	//BPS
66	.byte	0x02		//SPC
67	//.byte	0x00		//???
68	.byte	0x00, 0x02	//RES - number of reserved sectors
69	.byte	0x00		//NFATS
70	.byte	0x00, 0x00	//NDIRS
71	.byte	0x40, 0x0b	//NSECTS
72	.byte	0xf0		//MEDIA
73	.byte	0x05, 0x00	//SPF
74_fat_spt:
75	.byte	0x12, 0x00	//SPT
76	.byte	0x02, 0x00	//NSIDES
77	.byte	0x00, 0x00	//NHID
78	// we're done
79
80sNumSectors:
81	// this location will contain the length of the boot loader as
82	// written by the "makeflop" command in 512 byte blocks
83	// 0x180 is the allowed maximum, as the zipped TAR with the
84	// kernel and the boot module might start at offset 192 kB
85	//.word	0x0300 //0x0180
86	.word	BOOT_ARCHIVE_IMAGE_OFFSET*2
87
88real_entry:
89
90// save the regs to return safely, like the NetBSD loader does:
91// http://ftp.netbsd.org/pub/NetBSD/NetBSD-release-3-0/src/sys/arch/atari/stand/xxboot/fdboot/fdboot.S
92	movem.l		%d1-%d7/%a0-%a6,-(%sp)
93
94	lea		str,%a0
95	bsr		puts
96
97	// first, determine if .prg (user) or bootsect (super)
98	// Super()
99	move.l		#SUP_INQUIRE,-(%sp)
100	move.w		#0x20,-(%sp)
101	trap		#GEMDOS_TRAP
102	addq.l		#6,%sp
103
104	cmp.l		#SUP_USER,%d0
105	bne			floppy_start
106	bra			prg_start
107
108/*
109 * floppy boot support code
110 */
111
112floppy_start:
113	lea		label_floppy,%a0
114	bsr		puts
115	//bra floppy_start
116
117	// no interrupt
118	//or.w		#0x0700,%sr
119
120	//XXX: check for enough RAM
121
122	// load the rest
123	//move.w		sNumSectors,%d2
124	// load at base + this code.
125	//move.l		#(ATARI_ZBEOS_BASE+512),%a2
126	//move.l		%a2,%d0
127	//bsr putx
128	bsr			load_sectors
129	tst.w			%d0
130	bne			load_failed
131floppy_done:
132	// setup stack
133	move.l		#ATARI_ZBEOS_STACK_END,%sp
134	//jmp			ATARI_ZBEOS_BASE+512
135
136	move.b		#ATARI_BOOT_DRVAPI_FLOPPY,ATARI_ZBEOS_BASE + gBootDriveAPI - _bs_entry
137	move.w		TOSVAR_bootdev,%d0
138	// XXX:	 use uint16 ??
139	move.b		%d0,ATARI_ZBEOS_BASE + gBootDriveID - _bs_entry
140	move.b		#1,ATARI_ZBEOS_BASE + gBootedFromImage - _bs_entry
141
142	lea		msg_j1,%a0
143	bsr		puts
144	move.l		#0,%d0
145
146	jmp		_start
147
148load_failed:
149	//bra			_exit
150
151spin:
152	//bra			spin
153_exit:	/*  */
154	lea			failure_string,%a0
155	bsr			puts
156	bsr			getc
157
158	movem.l	(%sp)+,%d1-%d7/%a0-%a6
159	rts
160	//rts
161
162/**	Loads %d2 sectors from floppy disk, starting at head XXX %dh, sector %cx.
163 *	The data is loaded to %a2.
164 */
165
166load_sectors:
167
168#if 0
169	/* it seems to skip 9 every 9 sectors, buggy side handling ? */
170	// Rwabs
171	//move.l		#1,-(%sp)
172	move.w		#0,-(%sp)	// A:
173	//move.w		#2,-(%sp)	// C:
174	//move.w		#-1,-(%sp)	// 2nd sector
175	move.w		#1,-(%sp)	// 2nd sector
176	move.w		%d2,-(%sp)
177	move.l		%a2,-(%sp)
178	//move.w		#RW_READ+RW_NOTRANSLATE,-(%sp)
179	move.w		#RW_READ+RW_NOMEDIACH,-(%sp)
180	move.w		#4,-(%sp)
181	trap		#13
182	add.l		#14,%sp
183#endif
184#if 0
185	// d2:
186
187	//move.w		%d2,-(%sp)
188	move.w		#1,-(%sp) // count
189	move.w		#0,-(%sp) // sideno
190	move.w		#0,-(%sp) // trackno
191	move.w		#1,-(%sp) // sectno
192	move.w		TOSVAR_bootdev,-(%sp) // devno
193	clr.l		-(%sp) // filler
194	//move.w		#0,-(%sp)
195	//move.l		%a2,-(%sp)
196	move.l		#ATARI_ZBEOS_BASE,-(%sp)
197	move.w		#8,-(%sp)	// floprd
198	trap		#XBIOS_TRAP
199	add.l		#20,%sp
200#endif
201
202	//bsr	putx
203	//rts
204
205	/*
206	 * %d3:	remaining sects
207	 * %d4:	sectno
208	 * %d5:	trackno
209	 * %d6:	sideno
210	 * %d7:	sect / track
211	 * %a5:	buffer
212	 *
213	 */
214	// load the rest
215
216	// XXX:	 the NetBSD loader probes it, but trying to asserts ARAnyM
217	clr.l		%d7
218	move.b		_fat_spt,%d7	// sect/track
219	//move.w		#0,%d7	// sect/track
220	move.w		#0,%d6	// sideno
221	move.w		#0,%d5	// trackno
222	move.w		#1,%d4	// sectno
223	move.w		sNumSectors,%d3	// remainder
224	move.l		#ATARI_ZBEOS_BASE,%a5
225read_sectors_loop:
226	bsr.s		read_sect
227	bne		read_sectors_fail
228	moveq		#'.',%d0
229	bsr		putc
230	subq.w		#1,%d3	// remainder--
231	bne.s		read_sectors_next
232	bsr	putcrlf
233	clr.l		%d0
234	rts
235
236	// compute next track/side/sector
237read_sectors_next:
238#if 0	//DEBUG
239	// [TRAK][SIDE]
240	move.w		%d5,%d0
241	swap		%d0
242	move.w		%d6,%d0
243	bsr		putx
244	// [SECT][S/TK]
245	move.w		%d4,%d0
246	swap		%d0
247	move.w		%d7,%d0
248	bsr		putx
249	//bsr		getc
250#endif	//!DEBUG
251	add.l		#SECTSIZE,%a5
252	addq.w		#1,%d4	// sectno++
253	cmp.w		%d7,%d4	// if (sectno == spt)
254	bne.s		.rs2	// {
255	addq.w		#1,%d6	//	sideno++ ;
256	cmp.w		#2,%d6	//	if (sideno == 2) {
257	bne		.rs1
258	clr.w		%d6	//		sideno = 0 ;
259	addq.w		#1,%d5	//		trackno++ ;
260	bsr	putcrlf
261
262.rs1:				//	}
263	clr.w		%d4	//	sectno = 0 ;
264.rs2:				// }
265
266	bra.s		read_sectors_loop
267
268read_sectors_fail:
269	tst.w		%d7	// s/t
270	bne		read_sectors_fail2
271	move.w		%d4,%d0
272	bsr		putx
273	move.w		%d4,%d7
274	clr.w		%d4
275	//add.w		#1,
276	bra.s		read_sectors_next
277read_sectors_fail2:
278	moveq		#1,%d0
279	rts
280
281
282read_sect:	/* read 1 sector */
283	/*
284	 * %d4:	sectno
285	 * %d5:	trackno
286	 * %d6:	sideno
287	 * %d7:	remaining count
288	 * %a5:	buffer
289	 *
290	 */
291#if 1
292	//move.w		%d2,-(%sp)
293	//move.w		#1,-(%sp) // count
294	//move.w		#0,-(%sp) // sideno
295	//move.w		#0,-(%sp) // trackno
296	//move.w		#2,-(%sp) // sectno
297	move.w		#1,-(%sp)
298	movem.w		%d4-%d6,-(%sp)
299	move.w		TOSVAR_bootdev,-(%sp) // devno
300	clr.l		-(%sp) // filler
301	move.l		%a5,-(%sp)
302	move.w		#8,-(%sp)	// floprd
303	trap		#XBIOS_TRAP
304	add.l		#20,%sp
305	tst.l		%d0
306
307#endif
308	rts
309
310floppy_end:
311//	.org	FAILURE_STRING
312failure_string:
313//	.string " Loading failed! Press key to reboot.\r\n"
314	.string " Loading failed! Press key.\r\n"
315//	.string "FAIL"
316
317//	.org	DOT_STRING
318//	.string	"."
319
320
321
322
323putx:
324	movem.l	%d0-%d2/%a0-%a2,-(%sp)
325	move.l	#8-1,%d2
326	move.l	%d0,%d1
327putxloop:
328	move.l	%d1,%d0
329	lsl.l	#4,%d1
330	//swap	%d0
331	//lsr.l	#8,%d0
332	//lsr.l	#4,%d0
333	rol.l	#4,%d0
334	and.l	#0x0f,%d0
335	cmp.b	#9,%d0
336	ble	putx0
337	add.b	#'a'-'0'-10,%d0
338	//bra	putxdisp
339putx0:
340	add.b	#'0',%d0
341putxdisp:
342	bsr	putc
343	dbf	%d2,putxloop
344	bsr	putcrlf
345	movem.l	(%sp)+,%d0-%d2/%a0-%a2
346	rts
347
348
349puts:
350.loopt:
351	move.b	(%a0)+,%d0
352	beq	.strout
353	bsr	putc
354	bra	.loopt
355.strout:
356putcrlf:
357	move.b	#'\r',%d0
358	bsr	putc
359	move.b	#'\n',%d0
360	bsr	putc
361	rts
362
363
364/* prints the char in d0.b to the console */
365putc:
366	movem.l	%d0-%d2/%a0-%a2,-(%sp)
367	move.w	%d0,-(%sp)
368	move.w	#DEV_CON,-(%sp)	// DEV_CON
369	move.w	#3,-(%sp)	// Bconout
370	trap	#BIOS_TRAP
371	add.l	#6,%sp
372	movem.l	(%sp)+,%d0-%d2/%a0-%a2
373	rts
374
375/* waits for a key */
376getc:
377	movem.l	%d1-%d2/%a0-%a2,-(%sp)
378	move.w	#DEV_CON,-(%sp)	// DEV_CON
379	move.w	#2,-(%sp)	// Bconin
380	trap	#BIOS_TRAP
381	add.l	#4,%sp
382	movem.l	(%sp)+,%d1-%d2/%a0-%a2
383	rts
384
385str:
386	.string "Haiku!"
387label_prg:
388	.string "P" //"RG boot"
389label_floppy:
390	.string "F" //"loppy boot"
391h4:
392	.string "H4"
393h5:
394	.string "H5"
395msg_j1:
396	.string "Jumping to haiku_loader."
397
398shell_end:
399	//.fill	(0x01fe - shell_end), 1, 0x55
400	.org	0x01fe
401	.word	0xaa55-1	// will be replaced by the one calculated by the build.
402		// we make sure PCs don't try to execute it.
403		// this bumps the "start" label to offset 0x0200 as
404		// expected by the BFS boot loader, and also marks
405		// this block as valid boot block for the BIOS
406
407//XXX: put bfs_start here
408
409/*
410 * \AUTO\HAIKU.PRG and ARAnyM BOOTSTRAP() support code
411 */
412
413prg_start:
414	lea		label_prg,%a0
415	bsr		puts
416
417	// .prg:
418	// we need to switch to supervisor mode anyway
419	move.l		#SUP_SET,-(%sp)
420	move.w		#0x20,-(%sp)
421	trap		#1
422	addq.l		#6,%sp
423	move.l		%d0,saved_super_stack
424
425#if 0
426			//_membot
427	move.l		#0x432,%a0
428	move.l		(%a0),%d0
429	bsr		putx
430
431			//_memtop
432	move.l		#0x436,%a0
433	move.l		(%a0),%d0
434	bsr		putx
435
436			//_v_bas_ad
437	move.l		#0x44e,%a0
438	move.l		(%a0),%d0
439	bsr		putx
440#endif
441	// disable interrupts
442	//or.w		#0x0700,%sr
443
444	// setup stack
445	move.l		#ATARI_ZBEOS_STACK_END,%sp
446
447	lea		h5,%a0
448	bsr		puts
449	lea		_bs_entry,%a0
450	move.l		%a0,%d0
451	bsr		putx
452
453	// copy the rest of the prg
454
455	// load counter
456	clr.l		%d0
457	move.w		sNumSectors,%d0
458	sub.w		#1,%d0
459	// load addresses
460	lea		_bs_entry,%a0
461	move.l		#ATARI_ZBEOS_BASE,%a1
462
463
464nextsect:
465	move.l		#512/4-1,%d1
466copysect_loop:
467	move.l		(%a0)+,(%a1)+
468	dbf		%d1,copysect_loop
469	//bsr		putx
470	dbf		%d0,nextsect
471
472	lea		msg_j1,%a0
473	bsr		puts
474	// all done
475super_done:
476	// XXX: copy the rest !
477	move.b		#ATARI_BOOT_DRVAPI_FLOPPY,ATARI_ZBEOS_BASE + gBootDriveAPI - _bs_entry
478	move.b		#0,ATARI_ZBEOS_BASE + gBootDriveID - _bs_entry
479	move.b		#1,ATARI_ZBEOS_BASE + gBootedFromImage - _bs_entry
480
481	move.l		#0,%d0
482
483	//jmp			ATARI_ZBEOS_BASE+512
484	jmp			_start
485
486saved_super_stack:
487	.long	0
488
489GLOBAL(gBootedFromImage):
490	.byte	0
491
492GLOBAL(gBootDriveAPI):
493	.byte	ATARI_BOOT_DRVAPI_UNKNOWN
494
495GLOBAL(gBootDriveID):
496	.byte	0
497
498GLOBAL(gBootPartitionOffset):
499	.long	0
500
501