Mercurial > hg > Members > kono > nitros9-code
view level2/modules/kernel/fmove.asm @ 2118:7fca19b7c923
ChangeLog udpated
FSRqMem optimization added
author | boisy |
---|---|
date | Fri, 24 Aug 2007 03:30:33 +0000 |
parents | 1da8ab9ba433 |
children | 8900c6809408 |
line wrap: on
line source
************************************************** * System Call: F$Move * * Function: Move data (low bound first) * * Input: A = Source task # * B = Destination task # * X = Source pointer * Y = Number of bytes to move * U = Destination pointer * * Output: None * * Error: CC = C bit set; B = error code * IFEQ H6309 L0A01 clrb rts ENDC FMove ldd R$D,u get source & destination task #'s L0B25 ldy R$Y,u Get # bytes to move beq L0A01 None, exit without error ldx R$X,u get source pointer ldu R$U,u get destination pointer L0B2C pshs d,x,y,u preserve it all pshs d,y save task #'s & byte count tfr a,b copy source task to B lbsr L0BF5 calculate block offset of source leay a,u point to block pshs x,y save source pointer & DAT pointer of source ldb 9,s get destination task # ldx 14,s get destination pointer lbsr L0BF5 calculate block offset leay a,u point to block pshs x,y save dest. pointer & DAT pointer to dest. * try ldq #$20002000/ subr x,w / pshsw (+3), take out ldd (-3) ldd #DAT.BlSz get block size subd ,s take off offset pshs d preserve ldd #DAT.BlSz init offset in block subd 6,s pshs d save distance to end?? ldx 8,s get source pointer leax -$6000,x make X point to where we'll map block ($a000) ldu 4,s get destination pointer leau -$4000,u make U point to where we'll map block ($c000) ldy <D.SysDAT Get ptr to system DAT image lda 11,y Get MMU block #5 ldb 13,y Get MMU block #6 tfr d,y Move to Y since unused in loop below * Main move loop * Stack: 0,s=distance to end of source block * 2,s=distance to end of destination block * 4,s=pointer to destination * 6,s=pointer to destination DAT image * 8,s=pointer to source * 10,s=pointer to source DAT image * 12,s=task # of source * 13,s=task # of destination * 14,s=total byte count of move * Registers: X=Source pointer * U=Destination pointer L0B6A equ * IFNE H6309 ldd [<6,s] [B]=Block # of source ldw [<10,s] [A]=Block # of destination tfr f,a * Calculate move length for this pass ldw 14,s get full byte count cmpw ,s we gonna overlap source? bls L0B82 no, skip ahead ldw ,s get remaining bytes in source block L0B82 cmpw 2,s we gonna overlap destination? bls L0B89 no, skip ahead ldw 2,s get remaining bytes in destination block L0B89 cmpw #$0100 less than 128 bytes? bls L0B92 yes, skip ahead ldw #$0100 force to 128 bytes L0B92 stw 12,s save count orcc #IntMasks Shut off interrupts std >$FFA5 map in the blocks tfm x+,u+ Copy up to 128 bytes sty >$FFA5 Restore system blocks 5&6 to normal andcc #^IntMasks ldd 14,s get full count subd 12,s done? beq L0BEF yes, return std 14,s save updated count ldd ,s get current offset in block subd 12,s need to switch source block? bne L0BD7 no, skip ahead lda #$20 B=0 from 'bne' above subr d,x reset source back to begining of block inc 11,s add 2 to source DAT pointer inc 11,s L0BD7 std ,s save updated source offset in block ldd 2,s get destination offset subd 12,s need to switch destination block? bne L0BEA no, skip ahead lda #$20 B=0 from 'bne', above subr d,u reset destination back to beginning of block inc 7,s add 2 to destination DAT pointer inc 7,s L0BEA std 2,s save updated destination offset in block bra L0B6A go do next block * Block move done, return L0BEF leas 16,s purge stack L0BF2 clrb clear errors puls d,x,y,u,pc return ELSE * Main move loop * Stack: 0,s=distance to end of source block * 2,s=distance to end of destination block * 4,s=pointer to destination * 6,s=pointer to destination DAT image * 8,s=pointer to source * 10,s=pointer to source DAT image * 12,s=task # of source * 13,s=task # of destination * 14,s=total byte count of move * Registers: X=Source pointer * U=Destination pointer L0BXA pshs cc ldd [<$07,s] pshs b ldd [<$0C,s] pshs b ldd <$11,s cmpd $03,s bls L0B82 ldd $03,s L0B82 cmpd $05,s bls L0B89 ldd $05,s L0B89 cmpd #$0040 bls L0B84 ldd #$0040 L0B84 std $0F,s puls y orcc #IntMasks sty >$FFA5 andb #$07 beq L0B99 L0B92 lda ,x+ sta ,u+ decb bne L0B92 L0B99 ldb $0E,s lsrb lsrb lsrb beq L0BBC pshs b exg x,u L0BA4 pulu y,b,a std ,x sty $02,x pulu y,b,a std $04,x sty $06,x leax $08,x dec ,s bne L0BA4 leas $01,s exg x,u L0BBC ldy <D.SysDAT lda $0B,y ldb $0D,y std >$FFA5 puls cc ldd $0E,s subd $0C,s beq L0BEF std $0E,s ldd ,s subd $0C,s bne L0BD7 ldd #DAT.BlSz leax >-DAT.BlSz,x inc $0B,s inc $0B,s L0BD7 std ,s ldd $02,s subd $0C,s bne L0BEA ldd #DAT.BlSz leau >-DAT.BlSz,u inc $07,s inc $07,s L0BEA std $02,s lbra L0BXA L0BEF leas <$10,s L0BF2 clrb puls pc,u,y,x,b,a ENDC L0BF3 tfr u,y save a copy of U for later * Calculate offset within DAT image * Entry: B=Task # * X=Pointer to data * Exit : A=Offset into DAT image * X=Offset within block from original pointer * Possible bug: No one ever checks if the DAT image, in fact, exists. L0BF5 ldu <D.TskIPt get task image ptr table lslb ldu b,u get ptr to this task's DAT image tfr x,d copy logical address to D anda #%11100000 Keep only which 8K bank it's in beq L0C07 Bank 0, no further calcs needed clrb force it to start on an 8K boundary IFNE H6309 subr d,x now X=offset into the block ELSE pshs d tfr x,d subd ,s tfr d,x puls d ENDC lsra Calculate offset into DAT image to get proper lsra 8K bank (remember that each entry in a DAT image lsra is 2 bytes) lsra L0C07 rts