|
@@ -30,11 +30,12 @@
|
30
|
30
|
* Parameters:
|
31
|
31
|
* %esi : byte offset within loaded image (must be a multiple of 16)
|
32
|
32
|
* %es:edi : destination address
|
33
|
|
- * %ecx : length to install
|
|
33
|
+ * %ecx : length of (decompressed) data
|
|
34
|
+ * %edx : total length of block (including any uninitialised data portion)
|
34
|
35
|
* Returns:
|
35
|
36
|
* none
|
36
|
37
|
* Corrupts:
|
37
|
|
- * %esi, %edi, %ecx
|
|
38
|
+ * %esi, %edi, %ecx, %edx
|
38
|
39
|
****************************************************************************
|
39
|
40
|
*/
|
40
|
41
|
.section ".prefix.lib"
|
|
@@ -42,7 +43,7 @@
|
42
|
43
|
install_block:
|
43
|
44
|
/* Preserve registers */
|
44
|
45
|
pushw %ds
|
45
|
|
- pushw %ax
|
|
46
|
+ pushw %eax
|
46
|
47
|
|
47
|
48
|
/* Starting segment => %ds */
|
48
|
49
|
movw %cs, %ax
|
|
@@ -51,12 +52,22 @@ install_block:
|
51
|
52
|
movw %ax, %ds
|
52
|
53
|
xorl %esi, %esi
|
53
|
54
|
|
|
55
|
+ /* Calculate start and length of uninitialised data portion */
|
|
56
|
+ leal (%edi,%ecx), %eax
|
|
57
|
+ subl %ecx, %edx
|
|
58
|
+
|
54
|
59
|
/* Do the copy */
|
55
|
60
|
cld
|
56
|
|
- addr32 rep movsb /* or "call decompress16" */
|
|
61
|
+ rep addr32 movsb /* or "call decompress16" */
|
|
62
|
+
|
|
63
|
+ /* Zero remaining space */
|
|
64
|
+ movl %eax, %edi
|
|
65
|
+ movl %edx, %ecx
|
|
66
|
+ xorb %al, %al
|
|
67
|
+ rep addr32 stosb
|
57
|
68
|
|
58
|
69
|
/* Restore registers */
|
59
|
|
- popw %ax
|
|
70
|
+ popw %eax
|
60
|
71
|
popw %ds
|
61
|
72
|
ret
|
62
|
73
|
.size install_block, . - install_block
|
|
@@ -79,7 +90,6 @@ install_block:
|
79
|
90
|
*/
|
80
|
91
|
.section ".prefix.lib"
|
81
|
92
|
.code16
|
82
|
|
- .globl alloc_basemem
|
83
|
93
|
alloc_basemem:
|
84
|
94
|
/* FBMS => %ax as segment address */
|
85
|
95
|
movw $0x40, %ax
|
|
@@ -121,19 +131,20 @@ alloc_basemem:
|
121
|
131
|
*/
|
122
|
132
|
.section ".prefix.lib"
|
123
|
133
|
.code16
|
124
|
|
- .globl install_basemem
|
125
|
134
|
install_basemem:
|
126
|
135
|
/* Preserve registers */
|
127
|
136
|
pushw %es
|
128
|
137
|
pushl %esi
|
129
|
138
|
pushl %edi
|
130
|
139
|
pushl %ecx
|
|
140
|
+ pushl %edx
|
131
|
141
|
|
132
|
142
|
/* Install .text16 */
|
133
|
143
|
movw %ax, %es
|
134
|
144
|
xorl %edi, %edi
|
135
|
145
|
movl $_text16_load_offset, %esi
|
136
|
146
|
movl $_text16_size, %ecx
|
|
147
|
+ movl %ecx, %edx
|
137
|
148
|
call install_block
|
138
|
149
|
|
139
|
150
|
/* Install .data16 */
|
|
@@ -141,9 +152,11 @@ install_basemem:
|
141
|
152
|
xorl %edi, %edi
|
142
|
153
|
movl $_data16_load_offset, %esi
|
143
|
154
|
movl $_data16_progbits_size, %ecx
|
|
155
|
+ movl $_data16_size, %edx
|
144
|
156
|
call install_block
|
145
|
157
|
|
146
|
158
|
/* Restore registers */
|
|
159
|
+ popl %edx
|
147
|
160
|
popl %ecx
|
148
|
161
|
popl %edi
|
149
|
162
|
popl %esi
|
|
@@ -160,6 +173,9 @@ install_basemem:
|
160
|
173
|
* simpler.
|
161
|
174
|
****************************************************************************
|
162
|
175
|
*/
|
|
176
|
+
|
|
177
|
+#ifndef KEEP_IT_REAL
|
|
178
|
+
|
163
|
179
|
.section ".prefix.lib"
|
164
|
180
|
.align 16
|
165
|
181
|
gdt:
|
|
@@ -180,6 +196,8 @@ flat_ds: /* Flat real mode data segment */
|
180
|
196
|
gdt_end:
|
181
|
197
|
.equ gdt_length, gdt_end - gdt
|
182
|
198
|
.size gdt, . - gdt
|
|
199
|
+
|
|
200
|
+#endif /* KEEP_IT_REAL */
|
183
|
201
|
|
184
|
202
|
/****************************************************************************
|
185
|
203
|
* set_segment_limits (real-mode near call)
|
|
@@ -190,6 +208,9 @@ gdt_end:
|
190
|
208
|
* %cx : Segment limit ($REAL_DS or $FLAT_DS)
|
191
|
209
|
****************************************************************************
|
192
|
210
|
*/
|
|
211
|
+
|
|
212
|
+#ifndef KEEP_IT_REAL
|
|
213
|
+
|
193
|
214
|
.section ".prefix.lib"
|
194
|
215
|
.code16
|
195
|
216
|
set_segment_limits:
|
|
@@ -222,6 +243,8 @@ set_segment_limits:
|
222
|
243
|
ret
|
223
|
244
|
.size set_segment_limits, . - set_segment_limits
|
224
|
245
|
|
|
246
|
+#endif /* KEEP_IT_REAL */
|
|
247
|
+
|
225
|
248
|
/****************************************************************************
|
226
|
249
|
* install_highmem (real-mode near call)
|
227
|
250
|
*
|
|
@@ -235,15 +258,18 @@ set_segment_limits:
|
235
|
258
|
* none
|
236
|
259
|
****************************************************************************
|
237
|
260
|
*/
|
|
261
|
+
|
|
262
|
+#ifndef KEEP_IT_REAL
|
|
263
|
+
|
238
|
264
|
.section ".prefix.lib"
|
239
|
265
|
.code16
|
240
|
|
- .globl install_highmem
|
241
|
266
|
install_highmem:
|
242
|
267
|
/* Preserve registers and interrupt status */
|
243
|
268
|
pushfl
|
244
|
269
|
pushl %esi
|
245
|
270
|
pushl %edi
|
246
|
271
|
pushl %ecx
|
|
272
|
+ pushl %edx
|
247
|
273
|
|
248
|
274
|
/* Disable interrupts and flatten real mode */
|
249
|
275
|
cli
|
|
@@ -253,8 +279,9 @@ install_highmem:
|
253
|
279
|
/* Install .text and .data to specified address */
|
254
|
280
|
xorw %cx, %cx
|
255
|
281
|
movw %cx, %es
|
256
|
|
- movl $_text_load_offset, %esi
|
257
|
|
- movl $_text_progbits_size, %ecx
|
|
282
|
+ movl $_textdata_load_offset, %esi
|
|
283
|
+ movl $_textdata_progbits_size, %ecx
|
|
284
|
+ movl $_textdata_size, %edx
|
258
|
285
|
call install_block
|
259
|
286
|
|
260
|
287
|
/* Unflatten real mode */
|
|
@@ -262,9 +289,71 @@ install_highmem:
|
262
|
289
|
call set_segment_limits
|
263
|
290
|
|
264
|
291
|
/* Restore registers and interrupt status */
|
|
292
|
+ popl %edx
|
265
|
293
|
popl %ecx
|
266
|
294
|
popl %edi
|
267
|
295
|
popl %esi
|
268
|
296
|
popfl
|
269
|
297
|
ret
|
270
|
298
|
.size install_highmem, . - install_highmem
|
|
299
|
+
|
|
300
|
+#endif /* KEEP_IT_REAL */
|
|
301
|
+
|
|
302
|
+/****************************************************************************
|
|
303
|
+ * install (real-mode near call)
|
|
304
|
+ * install_prealloc (real-mode near call)
|
|
305
|
+ *
|
|
306
|
+ * Install all text and data segments.
|
|
307
|
+ *
|
|
308
|
+ * Parameters:
|
|
309
|
+ * %ax : .text16 segment address (install_prealloc only)
|
|
310
|
+ * %bx : .data16 segment address (install_prealloc only)
|
|
311
|
+ * Returns:
|
|
312
|
+ * %ax : .text16 segment address
|
|
313
|
+ * %bx : .data16 segment address
|
|
314
|
+ * %edi : .text physical address (if applicable)
|
|
315
|
+ * Corrupts:
|
|
316
|
+ * none
|
|
317
|
+ ****************************************************************************
|
|
318
|
+ */
|
|
319
|
+ .section ".prefix.lib"
|
|
320
|
+ .code16
|
|
321
|
+ .globl install
|
|
322
|
+install:
|
|
323
|
+ /* Allocate space for .text16 and .data16 */
|
|
324
|
+ call alloc_basemem
|
|
325
|
+ .size install, . - install
|
|
326
|
+ .globl install_prealloc
|
|
327
|
+install_prealloc:
|
|
328
|
+ /* Install .text16 and .data16 */
|
|
329
|
+ call install_basemem
|
|
330
|
+
|
|
331
|
+#ifndef KEEP_IT_REAL
|
|
332
|
+ /* Install .text and .data to 2MB mark. Use 2MB to avoid
|
|
333
|
+ * problems with A20.
|
|
334
|
+ */
|
|
335
|
+ movl $(2<<20), %edi
|
|
336
|
+ call install_highmem
|
|
337
|
+
|
|
338
|
+ /* Continue executing in .text16 segment */
|
|
339
|
+ pushw %cs
|
|
340
|
+ pushw $2f
|
|
341
|
+ pushw %ax
|
|
342
|
+ pushw $1f
|
|
343
|
+ lret
|
|
344
|
+ .section ".text16", "awx", @progbits
|
|
345
|
+1:
|
|
346
|
+ /* Set up protected-mode GDT, call relocate(), reset GDT */
|
|
347
|
+ call init_gdt
|
|
348
|
+ pushl $relocate
|
|
349
|
+ data32 call prot_call
|
|
350
|
+ addw $4, %sp
|
|
351
|
+ call init_gdt
|
|
352
|
+
|
|
353
|
+ /* Return to executing in .prefix section */
|
|
354
|
+ lret
|
|
355
|
+ .section ".prefix.lib"
|
|
356
|
+2:
|
|
357
|
+#endif
|
|
358
|
+ ret
|
|
359
|
+ .size install_prealloc, . - install_prealloc
|