]> cloudbase.mooo.com Git - z180-stamp-cpm3.git/blame - cbios/mm.180
b0call --> b0hlcall
[z180-stamp-cpm3.git] / cbios / mm.180
CommitLineData
2a7e38b4
L
1 page 255\r
2 .z80\r
3\r
4\r
5 public mmuinit\r
6 public bnk2log,bnk2phy,hwl2phy,phy2log\r
7 public isv_sw\r
8 public b_ld_a,b_ld_hl,b_st_a,b_st_hl\r
9\r
10\r
11 extrn @cbnk\r
12 extrn ijphl\r
13\r
14\r
15 maclib z180reg.inc\r
16 maclib config.inc\r
17\r
18\r
19;----------------------------------------------------------------------\r
20; Memory Map 1:\r
21;\r
22; Common CAStart .. 0FFFF\r
23; Bank 0 00000 .. CAStart-1\r
24; Bank 1 10000 ..\r
25; Bank 2\r
26;\r
27; Memory Map 2:\r
28;\r
29; Common 18000 .. 1BFFF BANK1\r
30;\r
31; Bank 0 00000 .. 0BFFF 0\r
32; Bank 1 0C000 .. 17FFF 1*BNK_SIZE\r
33; Bank 2 1C000 .. 27FFF 2*BNK_SIZE + CMN_SIZE\r
34; Bank 3 28000 .. 33FFF 3*BNK_SIZE + CMN_SIZE\r
35; Bank n n*BNK_SIZE + (n < 2) ? 0 : CMN_SIZE\r
36;\r
37;----------------------------------------------------------------------\r
38\r
39 cseg\r
40\r
41mmuinit:\r
42 ld a,USR$CBAR\r
43 out0 (cbar),a\r
44 ret\r
45\r
46;--------------------------------------------------------------------\r
47; Return the BBR value for the given bank number\r
48;\r
49; in a: Bank number\r
50; out a: bbr value\r
51\r
52 if 0 ; Memory Map 1\r
53\r
54bnk2log:\r
55 or a ;\r
56 ret z ; Bank 0 is at physical address 0\r
57\r
58 dec a ;\r
59 push bc ;\r
60 ld c,a ;\r
61 ld b,BNK_SIZE ;\r
62 mlt bc ; bank size * bank number\r
63 ld a,c ;\r
64 add a,10h ; add bank0 + common\r
65 pop bc ;\r
66 ret ;\r
67\r
68 else ; Memory Map 2\r
69\r
70bnk2log:\r
71 or a\r
72 ret z ; Bank 0 is at physical address 0\r
73\r
74 push bc\r
75 ld c,a ;\r
76 ld b,BNK_SIZE ;\r
77 mlt bc ; bank size * bank number\r
78 cp 2 ;\r
79 ld a,c ;\r
80 pop bc\r
81 ret c\r
82 add a,CMN_SIZE\r
83 ret\r
84\r
85 endif\r
86\r
87 if 0 ; table version\r
88\r
89 push hl\r
90 ld hl,bnk_table ;\r
91 add a,l ;\r
92 ld l,a ;\r
93 jr nc,$+3 ;\r
94 inc h ;\r
95 ld a,(hl) ;\r
96 pop hl\r
97 ret\r
98\r
99 endif\r
100\r
101;--------------------------------------------------------------\r
102\r
103;in hl: Log. Address\r
104; a: Bank number\r
105;\r
106;out ahl: Phys. (linear) Address\r
107\r
108\r
109bnk2phy:\r
110 push bc\r
111 ld c,a\r
112 ld a,h\r
113 and a,0f0h\r
114 cp CA*16\r
115 ld a,c\r
116 pop bc\r
117 jr c,b2p_banked\r
118 ; address is in common\r
119 if 0 ; Memory Map 1\r
120 ld a,0 ; base is 0\r
121 else ; Memory Map 2\r
122 ld a,1 ; same as bank1\r
123 endif\r
124\r
125b2p_banked:\r
126 call bnk2log ; get address base\r
127\r
128 ; fall thru\r
129\r
130;--------------------------------------------------------------\r
131;\r
132; hl: Log. Address\r
133; a: Bank base (bbr)\r
134;\r
135; 2 0 0\r
136; 0 6 8 0\r
137; hl hhhhhhhhllllllll\r
138; a + bbbbbbbb\r
139;\r
140; OP: ahl = (a<<12) + (h<<8) + l\r
141;\r
142;out ahl: Phys. (linear) Address\r
143\r
144log2phy:\r
145 push bc ;\r
146l2p_i:\r
147 ld c,a ;\r
148 ld b,16 ;\r
149 mlt bc ; bc = a<<4\r
150 ld a,c ;\r
151 add a,h ;\r
152 ld h,a ;\r
153 ld a,b ;\r
154 adc a,0 ;\r
155 pop bc ;\r
156 ret ;\r
157\r
158;--------------------------------------------------------------\r
159;\r
160; hl: Log. Address\r
161;\r
162;\r
163; OP: ahl = (bankbase<<12) + (h<<8) + l\r
164;\r
165;out ahl: Phys. (linear) Address\r
166\r
167\r
168hwl2phy:\r
169 push bc ;\r
170 in0 c,(cbar) ;\r
171 ld a,h ;\r
172 or 00fh ; log. addr in common1?\r
173 cp c\r
174 jr c,hlp_1\r
175\r
176 in0 a,(cbr) ; yes, cbr is address base\r
177 jr hl2p_x\r
178hlp_1:\r
179 ld b,16 ; log. address in baked area?\r
180 mlt bc\r
181 ld a,h\r
182 cp c\r
183 jr c,hlp_2\r
184 in0 a,(bbr) ; yes, bbr is address base\r
185 jr hl2p_x\r
186hlp_2:\r
187 xor a ; common1\r
188hl2p_x:\r
189 jr nz,l2p_i\r
190\r
191 pop bc ; bank part is 0, no translation\r
192 ret ;\r
193\r
194\r
195;--------------------------------------------------------------\r
196; return logical bank 0 address for given physical address.\r
197;\r
198; in: ahl: pyhsical addres (20 bit)\r
199; out hl: logical address.\r
200; logical address is in bank 0 or common, no bank number returned\r
201;\r
202\r
203phy2log:\r
204 or a\r
205 ret z\r
206\r
207 push bc\r
208 push hl\r
209 ld l,h\r
210 ld h,0\r
211 ld bc,-16*SYS$CBR\r
212 add hl,bc\r
213 ld h,l\r
214 pop bc\r
215 ld l,c\r
216 pop bc\r
217 ret\r
218\r
219;--------------------------------------------------------------\r
220; Trampoline for routines in banked ram.\r
221; Switch stack pointer to "system" stack in top ram\r
222; Save cbar\r
aa1cd3a9
L
223;\r
224; HL: function pointer\r
2a7e38b4 225;\r
2a7e38b4
L
226 cseg ; common!\r
227\r
aa1cd3a9
L
228 public _b0hlcall\r
229_b0hlcall:\r
230 ld (b0_save_r),hl\r
2a7e38b4
L
231\r
232 ld hl,bs$stack-bs$stack$size\r
233 ld a,h\r
234 dec a\r
235 ld hl,0\r
236 add hl,sp ;\r
237 cp h\r
238 jr c,$ + 5 ;skip if stack allready in common bios ram\r
2a7e38b4
L
239 ld sp,bs$stack ;\r
240\r
241 push hl ;save user stack pointer\r
242\r
243 in0 h,(bbr) ;\r
244 push hl ;\r
aa1cd3a9 245 ld hl,b0hlc_ret\r
2a7e38b4
L
246 push hl\r
247 xor a\r
248 out0 (bbr),a ;\r
aa1cd3a9
L
249 ld hl,(b0_save_r)\r
250 jp (hl)\r
251b0hlc_ret:\r
252 ld (b0_save_r),hl\r
2a7e38b4
L
253\r
254 pop hl ;\r
255 out0 (bbr),h ;\r
256 pop hl ;\r
257 ld sp,hl ;\r
aa1cd3a9 258 ld hl,(b0_save_r)\r
2a7e38b4 259 ret ;\r
2a7e38b4 260\r
2a7e38b4 261\r
aa1cd3a9 262b0_save_r: dw 0\r
2a7e38b4
L
263\r
264;--------------------------------------------------------------------\r
265; Trampoline for interrupt routines in banked ram.\r
266; Switch stack pointer to "system" stack in top ram\r
267; Save bbr\r
268\r
269 cseg\r
270\r
271 if 0\r
272\r
273isv_sw: ;\r
274 ex (sp),hl ;save hl, 'return adr' in hl\r
275 push de ;\r
276 push af ;\r
277 ex de,hl ;'return address' in de\r
278\r
279 if 0\r
280 if 0 ; link80\r
281\r
282 ld hl,0\r
283 add hl,sp ;\r
284 ld a,h\r
285 cp high (bs$stack-bs$stack$size) ;link80 can't process this\r
286 jr nc,$ + 5 ;skip if stack allready in common bios ram\r
287\r
288 else\r
289\r
290 ld hl,bs$stack-bs$stack$size\r
291 ld a,h\r
292 dec a\r
293 ld hl,0\r
294 add hl,sp ;\r
295 cp h\r
296 jr c,$ + 5 ;skip if stack allready in common bios ram\r
297 endif\r
298 ld sp,bs$stack ;\r
299 else\r
300 ld hl,0\r
301 add hl,sp\r
302 ld sp,istack\r
303 endif\r
304 push hl ;save user stack pointer\r
305 in0 h,(bbr) ;\r
306 push hl ;\r
307 xor a ;\r
308 out0 (bbr),a ;\r
309 ex de,hl ;\r
310 ld e,(hl) ;\r
311 inc hl ;\r
312 ld d,(hl) ;\r
313 ex de,hl ;\r
314 push bc ;\r
315 call ijphl ;\r
316\r
317 pop bc ;\r
318 pop hl ;\r
319 out0 (bbr),h ;\r
320 pop hl ;\r
321 ld sp,hl ;\r
322 pop af ;\r
323 pop de ;\r
324 pop hl ;\r
325 ei ;\r
326 ret ;\r
327\r
328 else\r
329\r
330isv_sw: ;\r
331 ex (sp),hl ;save hl, 'return adr' in hl\r
332\r
023a0215
L
333 ld (i$stack),sp ;save user stack pointer\r
334 ld sp,i$stack\r
2a7e38b4
L
335 push de ;\r
336 push bc ;\r
337 push af ;\r
338 in0 a,(bbr) ;\r
339 push af ;\r
340 xor a ;\r
341 out0 (bbr),a ;\r
342 ld e,(hl) ;\r
343 inc hl ;\r
344 ld d,(hl) ;\r
345 ex de,hl ;\r
346 call ijphl ;\r
347\r
348 pop af ;\r
349 out0 (bbr),a ;\r
350 pop af ;\r
351 pop bc ;\r
352 pop de ;\r
023a0215 353 ld sp,(i$stack) ;\r
2a7e38b4
L
354 pop hl ;\r
355 ei ;\r
356 ret ;\r
357\r
358 endif\r
023a0215
L
359\r
360 public i$stack\r
361 rept 24\r
362 db '|'\r
363 endm\r
364i$stack:\r
2a7e38b4
L
365 dw 0\r
366\r
367 dseg\r
368\r
369;--------------------------------------------------------------------\r
370; Load byte/word from user ram\r
371;\r
372; de: src address in users bank\r
373; return\r
374; a: value (byte)\r
375; hl: value (word)\r
376\r
377b_ld_a:\r
378 push hl\r
379 or a ; clear carry == byte store\r
380 jr $+3\r
381b_ld_hl:\r
382 scf ; set carry == word store\r
383 push af ; save flag\r
384 push hl ; make space on stack\r
385\r
386 ld a,(@cbnk)\r
387 ld b,a ; b = src bank\r
388\r
389 ld hl,0\r
390 ld a,l\r
391 ld c,l ; c = dst bank (0)\r
392 add hl,sp ; hl = dst\r
393 adc a,1 ; a = count\r
394 ex de,hl\r
395 call dma_move\r
396 ex de,hl\r
397 pop hl\r
398 pop af\r
399 ret c\r
400 ld a,l\r
401 pop hl\r
402 ret\r
403\r
404;--------------------------------------------------------------------\r
405; Store byte/word to user ram\r
406;\r
407; de: dst address in users bank\r
408; a: value (byte)\r
409; hl: value (word)\r
410\r
411b_st_a:\r
412 push hl\r
413 ld l,a\r
414 or a ; clear carry == byte store\r
415 jr $+3\r
416b_st_hl:\r
417 scf ; set carry == word store\r
418 push af ; save flag\r
419 push hl ; put value on stack\r
420\r
421 ld a,(@cbnk) ;\r
422 ld c,a ; c = dst bank\r
423 ld a,0\r
424 ld l,a\r
425 ld h,a\r
426 ld b,a ; b = src bank (0)\r
427 add hl,sp ; hl = src\r
428 adc a,1 ; a = count\r
429\r
430 call dma_move\r
431\r
432 pop hl ; restore value\r
433 pop af ; carry\r
434 ret c\r
435 pop hl\r
436 ret\r
437\r
438;--------------------------------------------------------------------\r
439;\r
440; hl: src\r
441; de: dst\r
442; b: src bank\r
443; c: dst bank\r
444; a: count\r
445\r
446dma_move:\r
447 out0 (bcr0l),a ; setup DMA count\r
448 xor a\r
449 out0 (bcr0h),a\r
450\r
451 push hl\r
452 ld a,b\r
453 call bnk2phy\r
454 out0 (sar0l),l ; setup DMA src address\r
455 out0 (sar0h),h\r
456 out0 (sar0b),a\r
457\r
458 ld l,e\r
459 ld h,d\r
460 ld a,c\r
461 call bnk2phy\r
462 out0 (dar0l),l ; setup DMA dst address\r
463 out0 (dar0h),h\r
464 out0 (dar0b),a\r
465\r
466 ld a,M_MMOD ; DMA burst mode\r
467 out0 (dmode),a\r
468 ld a,M_DE0+M_NDWE1 ; enable DMA0\r
469 out0 (dstat),a ; move ...\r
470 pop hl\r
471 ret\r
472\r
473\r
474;====================================================================\r
475\r
476 cseg\r
477\r
478 if 0\r
479\r
480;--------------------------------------------------------------------\r
481; Return the BBR value for the given bank number\r
482\r
483bnk2bbr:\r
484 or a ; 4\r
485 ret z ; 5/10 | 11 14\r
486\r
487 push bc ;11 | 11\r
488 ld b,a ; 4\r
489 ld c,CA ; 6\r
490 mlt bc ;17 >45\r
491 ld a,c ; 4\r
492 add a,10h ; 6\r
493 pop bc ; 9 | 10\r
494 ret ; 9 | 10 76\r
495\r
496 push ix ;2 / 14 | 15\r
497 ld ix,bnktbl ;4 / 12 | 14\r
498 ld ($+3+2),a ;3 / 15 | 19\r
499 ld a,(ix+0) ;3 / 14 | 19\r
500 pop ix ;2 / 12 | 14\r
501 ret ;1 / 9 | 10 15 / 76|91\r
502\r
503 push hl ;1 / 11 | 11\r
504 ld hl,bnktbl ;3 / 9 | 10\r
505 add a,l ;1 / 4 | 4\r
506 ld l,a ;1 / 4 | 4\r
507 ld a,0 ;1 / 6 | 7\r
508 adc a,h ;1 / 4 | 4\r
509 ld h,a ;1 / 4 | 4\r
510 ld a,(hl) ;1 / 6 | 7\r
511 pop hl ;1 / 9 | 10\r
512 ret ;1 / 9 | 10 12 / 66|71\r
513\r
514 push hl ;1 / 11 | 11\r
515 add a,low bnktbl ;2 / 6 | 7\r
516 ld l,a ;1 / 4 | 4\r
517 ld a,0 ;1 / 6 | 7\r
518 adc a,high bnktbl ;2 / 6 | 7\r
519 ld h,a ;1 / 4 | 4\r
520 ld a,(hl) ;1 / 6 | 7\r
521 pop hl ;1 / 9 | 10\r
522 ret ;1 / 9 | 10 11 / 61|67\r
523\r
524 endif\r
525\r
526\r
023a0215
L
527 cseg\r
528 public bs$stack\r
529\r
530 rept bs$stack$size\r
531 db '|'\r
532 endm\r
533bs$stack:\r
7f282135 534 dw 0\r
023a0215 535\r
2a7e38b4 536 end\r