1/* $NetBSD: bbstart.s,v 1.12 2008/04/28 20:23:13 martin Exp $ */
2
3/*-
4 * Copyright (c) 1996 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Ignatios Souvatzis.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32#include <machine/asm.h>
33#include "elf2bb.h"
34
35#define LVOAllocMem	-0x0c6
36#define LVODoIO		-0x1c8
37#define LVOCacheClearU	-0x27c
38
39#define IOcmd	28
40#define IOerr	31
41#define IOlen	36
42#define IObuf	40
43#define IOoff	44
44
45#define Cmd_Rd	2
46
47	.text
48#if defined(_PRIMARY_BOOT) || defined(AUTOLOAD)
49Lzero:	.asciz "DOS"			| "DOS type"
50#else
51Lzero:	.ascii	"BOOT"			| Secondary Boot
52#endif
53	/*
54	 * We put the relocator version here, for elf2bb, which replaces
55	 * it with the bootblock checksum.
56	 */
57Chksum:	.long RELVER_RELATIVE_BYTES_FORWARD
58Filesz:	.long 8192			| dummy
59
60/*
61 * Entry point from Kickstart.
62 * A1 points to an IOrequest, A6 points to ExecBase, we have a stack.
63 * _must_ be at offset 12.
64 */
65ENTRY_NOPROFILE(start)
66#ifdef AUTOLOAD
67	jra	Lautoload
68#else
69	jra	Lrelocate
70#endif
71
72Lreltab:
73	.word 0			| elf2bb puts the reloc table address here
74
75	.globl _C_LABEL(default_command)
76_C_LABEL(default_command):
77	.asciz	"netbsd -ASn2"
78	.org	(_C_LABEL(default_command)+32)
79
80#ifdef AUTOLOAD
81/*
82 * autoload
83 */
84Lautoload:
85	movl	%a6,%sp@-			|SysBase
86	movl	%a1,%sp@-			|IORequest
87
88	movl	#AUTOLOAD,%d0		|Howmuch
89	movl	%d0,%a1@(IOlen)		| for the actual read...
90	movl	#0x10001,%d1		|MEMF_CLEAR|MEMF_PUBLIC
91	jsr	%a6@(LVOAllocMem)
92	movl	%sp@+,%a1			|IORequest
93	movl	%sp@+,%a6			|SysBase
94	orl	%d0,%d0
95	jne	Lgotmem
96	movql	#1,%d0
97	rts
98
99Lgotmem:
100	movl	%d0,%sp@-			|Address
101	movl	%a1@(IOoff),%sp@-		|Old offset
102	movl	%a1,%sp@-
103	movl	%a6,%sp@-
104
105/* we've set IOlen above */
106	movl	%d0,%a1@(IObuf)
107	movw	#Cmd_Rd,%a1@(IOcmd)
108	jsr	%a6@(LVODoIO)
109
110	movl	%sp@+,%a6
111	movl	%sp@+,%a1
112	movl	%sp@+,%a1@(IOoff)
113
114	tstb	%a1@(IOerr)
115	jne	Lioerr
116	addl	#Lrelocate-Lzero,%sp@
117
118	movl	%a6,%sp@-
119	jsr	%a6@(LVOCacheClearU)
120	movl	%sp@+,%a6
121	rts
122Lioerr:
123	movql	#1,%d0
124	addql	#4,%sp
125	rts
126#endif
127
128/*
129 * Relocate ourselves, at the same time clearing the relocation table
130 * (in case it overlaps with BSS).
131 *
132 * Register usage:
133 * A2: points into the reloc table, located at our end.
134 * A0: pointer to the longword to relocate.
135 * D0: word offset of longword to relocate
136 * D1: points to our start.
137 *
138 * Table has relative byte offsets, if a byte offset is zero, it is
139 * followed by an absolute word offset. If this is zero, too, table
140 * end is reached.
141 */
142
143Lrelocate:
144	lea	%pc@(Lzero),%a0
145	movl	%a0,%d1
146	movw	%pc@(Lreltab),%a2
147	addl	%d1,%a2
148	jra	Loopend
149
150Loopw:
151	clrw	%a2@+
152	movl	%d1,%a0	| for a variant with relative words, erase this line
153Loopb:
154	addl	%d0,%a0
155	addl	%d1,%a0@
156Loopend:
157	movq	#0,%d0
158	movb	%a2@,%d0
159	clrb	%a2@+	| bfclr %a2@+{0:8} is still two shorts
160	tstb	%d0	| we could save one short by using casb %d0,d0,%a2@+
161	jne	Loopb
162
163	movw	%a2@,%d0
164	jne	Loopw
165
166Lendtab:
167	movl	%a6,%sp@-
168	jsr	%a6@(LVOCacheClearU)
169	movl	%sp@+,%a6
170
171/* We are relocated. Now it is safe to initialize _SysBase: */
172
173	movl	%a6,_C_LABEL(SysBase)
174
175#ifndef _PRIMARY_BOOT
176	movl	%a5,%sp@-		| Console info
177#endif
178	movl	%a1,%sp@-
179	bsr	_C_LABEL(pain)
180#ifdef _PRIMARY_BOOT
181	addql	#4,%sp
182#else
183	addql	#8,%sp
184#endif
185
186Lerr:
187	movq	#1,%d0
188	rts
189
190	.comm _C_LABEL(SysBase),4
191