1 eÿara.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0z
\ 4.define .sar
10 ! a0 : descriptor address
15 move.l (sp)+,d2 ! return address
19 sub (a0),d0 ! index - lower bound : relative index
24 mulu 4(a0),d0 ! total # bytes
25 add d0,a1 ! address of element
32 move.l (sp)+,d2 ! return address
88 cii.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0N
\ 1.define .cii
96 move.l (sp)+,a0 ! return address
97 move (sp)+,d0 ! destination size
98 sub (sp)+,d0 ! destination - source size
100 sub d0,sp ! pop extra bytes
113 cmi.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0ë
\0.define .cmi, .cmi_
135 1cmp.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0Ò
\0.define .cmp
143 move.l (sp)+,a0 ! return address
154 cmu.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\9f\ 1.define .cmu
160 ! d0 : # bytes of 1 block
163 move.l (sp)+,d2 ! reta
164 move.l sp,a0 ! top block
167 add d0,a1 ! lower block
170 move.l #1,d1 ! greater
185 !csa.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0§
\ 1.define .csa2
193 move.l (a0)+,a1 ! default address
194 sub (a0)+,d0 ! index - lower bound
196 cmp (a0)+,d0 ! rel. index <-> upper - lower bound
200 move.l (a0),d1 ! test jump address
206 move.l a1,d0 ! test default jump address
213 scsa4.s
\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0¯
\ 1.define .csa4
221 move.l (a0)+,a1 ! default address
222 sub.l (a0)+,d0 ! index - lower bound
224 cmp.l (a0)+,d0 ! rel. index <-> upper - lower bound
228 move.l (a0),d1 ! test jump address
234 move.l a1,d0 ! test default jump address
241 mcsb.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0p
\ 1.define .csb2
249 move.l (a0)+,a1 ! default jump address
250 move.w (a0)+,d1 ! # entries
255 tst.l (a0)+ ! skip jump address
259 move.l a1,d1 ! default jump address
264 move.l (a0)+,a1 ! get jump address
267 csb4.s
\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0t
\ 1.define .csb4
275 move.l (a0)+,a1 ! default jump address
276 move.l (a0)+,d1 ! # entries
281 tst.l (a0)+ ! skip jump address
285 move.l a1,d1 ! default jump address
290 move.l (a0)+,a1 ! get jump address
293 cuu.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\1d\ 1.define .ciu
305 move.l (sp)+,a0 ! return address
306 move (sp)+,d0 ! destination size
318 exg.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0X
\ 1.define .exg
324 ! d0 : exchange size in bytes
327 move.l (sp)+,d2 ! return address
345 inn.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\89\ 1.define .inn
351 ! d0 : set size in bytes
356 move.l (sp)+,d2 ! return address
378 alos.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0Ë
\ 1.define .los
386 ! a0 : source address
411 ! a0 : source address
418 lrck.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0ñ
\0.define .rck
427 move.l (sp)+,a0 ! descriptor address
438 oret.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\1d\ 1.define .ret
465 move.w #EILLINS,-(sp)
467 lset.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0}
\ 1.define .set
473 ! d0 : setsize in bytes
485 move.l sp,a1 ! set base
498 dsts.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\81\ 1.define .sts
506 ! a0 : destination address
531 snop.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0¸
\0.define .nop
546 fmt: .asciz "test %d\n"
548 mon.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0Ñ
\0.define .mon
562 fmt: .asciz "system call %d not implemented\n"
564 1dvi.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\8d\v.define .dvi
571 !-----------------------------------------------------------------------------
572 ! rewritten by Kai-Uwe Bloem (i5110401@dbstu1.bitnet) for speed.
573 ! #1 01/12/90 initial revision. Minor reduce of shift operations.
574 ! #2 03/07/90 use 68000 divu instruction whereever possible. This change
575 ! makes #1 superflous. (derived from my GNU division routine)
576 !-----------------------------------------------------------------------------
577 ! Some common cases can be handled in a special, much faster way :
579 ! => cause trap, then return to user. Result is undefined
580 ! 2) dividend < divisor
581 ! => quotient = 0, remainder = dividend
582 ! 3) divisor < 0x10000 ( i.e. divisor is only 16 bits wide )
583 ! => quotient and remainder can be calculated quite fast by repeated
584 ! application of 68000 divu operations (ca. 400 cycles)
585 ! 4) otherwise (due to #2, #3 dividend, divisor both wider then 16 bits)
586 ! => do slow division by shift and subtract
587 !-----------------------------------------------------------------------------
598 move.l (sp)+,a1 ! return address
599 move.l (sp)+,d0 ! divisor
600 move.l (sp)+,d2 ! dividend
601 move.l d3,a0 ! save d3
602 move.l d4,-(sp) ! save result sign register
605 bpl 0f ! dividend is negative ?
606 neg.l d2 ! yes - negate
607 not.l d4 ! and note negation in d4
610 bpl 0f ! divisor is negative ?
611 neg.l d0 ! yes - negate
612 not.w d4 ! note negation
614 clr.l d1 ! prepare quotient
615 ! === case 1: divisor = 0
616 tst.l d0 ! divisor = 0 ?
617 beq 9f ! yes - divide by zero trap
618 ! === case 2: dividend < divisor
619 cmp.l d0,d2 ! dividend < divisor ?
620 bcs 8f ! yes - division already finished
621 ! === case 3: divisor <= 0x0ffff
622 cmp.l #0x0ffff,d0 ! is divisor only 16 bits wide ?
624 move.w d2,d3 ! save dividend.l
625 clr.w d2 ! prepare dividend.h for divu operation
627 beq 0f ! dividend.h is all zero, no divu necessary
629 0: move.w d2,d1 ! save quotient.h
631 move.w d3,d2 ! divide dividend.l
632 divu d0,d2 ! (d2.h = remainder of prev divu)
633 move.w d2,d1 ! save qoutient.l
634 clr.w d2 ! get remainder
637 ! === case 4: divisor and dividend both > 0x0ffff
639 move #32-1,d3 ! loop count
641 lsl.l #1,d2 ! shift dividend ...
642 roxl.l #1,d1 ! ... into d1
643 cmp.l d0,d1 ! compare with divisor
645 sub.l d0,d1 ! bigger, subtract divisor
646 add #1,d2 ! note subtraction in result
649 exg d1,d2 ! get results in the correct registers
651 tst.w d4 ! quotient < 0 ?
653 neg.l d1 ! yes - negate
654 0: tst.l d4 ! remainder < 0 ?
657 0: move.l (sp)+,d4 ! restore d4
658 move.l a0,d3 ! restore d3
662 9: move.w #EIDIVZ,-(sp)
664 \0dvu.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0ø .define .dvu
670 ! unsigned long divide
671 !-----------------------------------------------------------------------------
672 ! rewritten by Kai-Uwe Bloem (i5110401@dbstu1.bitnet) for speed.
673 ! #1 01/12/90 initial revision. Minor reduce of shift operations.
674 ! #2 03/07/90 use 68000 divu instruction whereever possible. This change
675 ! makes #1 superflous. (derived from my GNU division routine)
676 !-----------------------------------------------------------------------------
677 ! Some common cases can be handled in a special, much faster way :
679 ! => cause trap, then return to user. Result is undefined
680 ! 2) dividend < divisor
681 ! => quotient = 0, remainder = dividend
682 ! 3) divisor < 0x10000 ( i.e. divisor is only 16 bits wide )
683 ! => quotient and remainder can be calculated quite fast by repeated
684 ! application of 68000 divu operations (ca. 400 cycles)
685 ! 4) otherwise (due to #2, #3 dividend, divisor both wider then 16 bits)
686 ! => do slow division by shift and subtract
687 !-----------------------------------------------------------------------------
698 move.l d3,a0 ! save d3
699 move.l (sp)+,a1 ! return address
700 move.l (sp)+,d0 ! divisor
701 move.l (sp)+,d2 ! dividend
702 clr.l d1 ! prepare quotient
703 ! === case 1: divisor = 0
704 tst.l d0 ! divisor = 0 ?
705 beq 9f ! yes - divide by zero trap
706 ! === case 2: dividend < divisor
707 cmp.l d0,d2 ! dividend < divisor ?
708 bcs 8f ! yes - division already finished
709 ! === case 3: divisor <= 0x0ffff
710 cmp.l #0x0ffff,d0 ! is divisor only 16 bits wide ?
712 move.w d2,d3 ! save dividend.l
713 clr.w d2 ! prepare dividend.h for divu operation
715 beq 0f ! dividend.h is all zero, no divu necessary
717 0: move.w d2,d1 ! save quotient.h
719 move.w d3,d2 ! divide dividend.l
720 divu d0,d2 ! (d2.h = remainder of prev divu)
721 move.w d2,d1 ! save qoutient.l
722 clr.w d2 ! get remainder
725 ! === case 4: divisor and dividend both > 0x0ffff
727 move #32-1,d3 ! loop count
729 lsl.l #1,d2 ! shift dividend ...
730 roxl.l #1,d1 ! ... into d1
731 cmp.l d0,d1 ! compare with divisor
733 sub.l d0,d1 ! bigger, subtract divisor
734 add #1,d2 ! note subtraction in result
737 exg d1,d2 ! get results in the correct registers
739 move.l a0,d3 ! restore d3
743 9: move.w #EIDIVZ,-(sp)
745 mli.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0R .define .mli
751 ! signed long mulitply
752 !-----------------------------------------------------------------------------
753 ! rewritten by Kai-Uwe Bloem (i5110401@dbstu1.bitnet) for speed.
754 ! #1 01/12/90 initial revision
755 !-----------------------------------------------------------------------------
756 ! 3 cases worth to recognize :
757 ! 1) both the upper word of u and v are zero
758 ! => 1 mult : Low*Low
759 ! 2) only one of the upper words is zero
760 ! => 2 mult : Low*HighLow
761 ! 3) both upper words are not zero
762 ! => 4 mult : HighLow*HighLow
763 ! there are other cases (e.g. lower word is zero but high word is not, or
764 ! one operand is all zero). However, this seems not to be very common, so
765 ! they are ignored for the price of superfluous multiplications in these
767 !-----------------------------------------------------------------------------
769 ! entry : d0 multiplicand
771 ! exit : d0 high order result
772 ! d1 low order result
773 ! d2,a0,a1 : destroyed
777 move.l (sp)+,a1 ! return address
778 move.l d3,a0 ! save register
779 movem.w (sp)+,d0-d3 ! get v and u
780 move.w d5,-(sp) ! save sign register
782 bge 0f ! negate u if neccessary
786 bge 0f ! negate v if neccessary
790 0: bne 1f ! case 2) or 3)
793 ! === case 1: _l x _l ===
794 mulu d3,d1 ! r.l = u.l x v.l
795 9: ! (r.h is already zero)
796 tst.w d5 ! negate result if neccessary
800 0: move.w (sp)+,d5 ! return
803 ! === possibly case 2) or case 3) ===
807 ! === case 2: _l x hl ===
808 exg d0,d2 ! exchange u and v
809 exg d1,d3 ! (minimizes number of distinct cases)
811 mulu d1,d2 ! a = v.l x u.h
812 mulu d3,d1 ! r.l = v.l x u.l
813 swap d2 ! a = a << 16
820 ! === case 3: hl x hl ===
822 move.l d4,-(sp) ! need more registers
824 mulu d1,d4 ! a = v.l x u.h
825 mulu d3,d1 ! r.l = u.l x v.l
826 mulu d0,d3 ! b = v.h x u.l
827 mulu d2,d0 ! r.h = u.h x v.h
828 swap d1 ! (just for simplicity)
829 add.w d4,d1 ! r += a << 16
833 add.w d3,d1 ! r += b << 16
838 move.l (sp)+,d4 ! return
840 mlu.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0n
\b.define .mlu
846 ! unsigned long mulitply
847 !-----------------------------------------------------------------------------
848 ! rewritten by Kai-Uwe Bloem (i5110401@dbstu1.bitnet) for speed.
849 ! #1 01/12/90 initial revision
850 !-----------------------------------------------------------------------------
851 ! 3 cases worth to recognize :
852 ! 1) both the upper word of u and v are zero
853 ! => 1 mult : Low*Low
854 ! 2) only one of the upper words is zero
855 ! => 2 mult : Low*HighLow
856 ! 3) both upper words are not zero
857 ! => 4 mult : HighLow*HighLow
858 ! there are other cases (e.g. lower word is zero but high word is not, or
859 ! one operand is all zero). However, this seems not to be very common, so
860 ! they are ignored for the price of superfluous multiplications in these
862 !-----------------------------------------------------------------------------
864 ! entry : d0 multiplicand
866 ! exit : d0 high order result
867 ! d1 low order result
868 ! d2,a0,a1 : destroyed
872 move.l (sp)+,a1 ! return address
873 move.l d3,a0 ! save register
874 movem.w (sp)+,d0-d3 ! get v and u
876 bne 1f ! case 2) or 3)
879 ! === case 1: _l x _l ===
880 mulu d3,d1 ! r.l = u.l x v.l
881 move.l a0,d3 ! (r.h is already zero)
883 ! === possibly case 2) or case 3) ===
887 ! === case 2: _l x hl ===
888 exg d0,d2 ! exchange u and v
889 exg d1,d3 ! (minimizes number of distinct cases)
891 mulu d1,d2 ! a = v.l x u.h
892 mulu d3,d1 ! r.l = v.l x u.l
893 swap d2 ! a = a << 16
899 move.l a0,d3 ! return
901 ! === case 3: hl x hl ===
903 move.l d4,-(sp) ! need more registers
905 mulu d1,d4 ! a = v.l x u.h
906 mulu d3,d1 ! r.l = u.l x v.l
907 mulu d0,d3 ! b = v.h x u.l
908 mulu d2,d0 ! r.h = u.h x v.h
909 swap d1 ! (just for simplicity)
910 add.w d4,d1 ! r += a << 16
914 add.w d3,d1 ! r += b << 16
919 move.l (sp)+,d4 ! return
922 shp.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0x
\ 1.define .strhp
931 move.l (sp)+,d0 ! heap pointer
951 sig.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0¬
\0.define .sig
960 move.l (sp)+,a1 ! trap pc
964 cms.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\09
\ 1.define .cms
970 ! d0 contains set size
974 move.l (sp)+,d2 ! return address
991 ngto.s
\0\0\0\0\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0®
\ 6.define .gto
1001 ! the argument on the stack is a pointer to a GTO-descriptor containing:
1002 ! - the new local base
1003 ! - the new stackpointer
1004 ! - the new program counter
1006 ! The main task of the GTO instruction is to restore the registers
1007 ! used for local variables. It uses a word stored in each stackframe,
1008 ! indicating how many data -and address registers the procedure of
1009 ! that stackframe has.
1012 add.l #8,a0 ! a0 now points to new local base entry
1014 cmp.l (a0),a6 ! GTO within same procedure?
1016 move.l d0,savd0 ! gto may not destroy the return area
1022 move.w (sp)+,d0 ! word indicating which regs. were saved
1030 move.l -8(a0),a0 ! new program counter
1033 move.w #EBADGTO,-(sp)
1037 ! restore the registers. Note that scratch register a0 may
1038 ! not be changed here. d0 contains (8*#addr.regs + #data regs.)
1039 ! note that registers are assigned in the order d7,d6 .. and
1042 move.l (sp)+,d2 ! return address; can't use a0 here
1044 and.l #7,d0 ! #data registers
1056 asr.l #2,d1 ! # address registers
1071 fp68881.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0ß
\11.define .adf4, .adf8, .sbf4, .sbf8, .mlf4, .mlf8, .dvf4, .dvf8
1072 .define .ngf4, .ngf8, .fif4, .fif8, .fef4, .fef8
1073 .define .cif4, .cif8, .cuf4, .cuf8, .cfi, .cfu, .cff4, .cff8
1074 .define .cmf4, .cmf8
1080 ! $Id: fp68881.s,v 1.3 1994/06/24 13:04:30 ceriel Exp $
1082 ! Implement interface to floating point package for M68881
1187 and.l #0x2000,d0 ! set if Infinity
1192 move.l #0x3f000000,2(a1)
1195 move.l #0xbf000000,2(a1)
1218 and.l #0x2000,d0 ! set if Infinity
1223 move.l #0x3fe00000,2(a1)
1227 move.l #0xbfe00000,2(a1)
1284 fsub.l #-2147483648,fp0
1285 fsub.l #-2147483648,fp0
1304 fsub.l #-2147483648,fp0
1305 fsub.l #-2147483648,fp0
1344 cmp.l #0x4f000000,4(sp)
1350 fadd.l #-2147483648,fp0
1359 cmp.l #0x41e00000,(sp)
1365 fadd.l #-2147483648,fp0
1424 \0fat.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0d
\0.define .fat
1434 trp.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0Ô
\ 1.define .trp
1442 move.l (sp)+,a1 ! return address
1443 move.w (sp)+,d0 ! error number
1472 fmt: .asciz "trap %d called\n"
1474 dia.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0U
\f.define .diagnos
1532 move.l 8+0(a6),-(sp)
1537 move.l (sp)+,8+0(a6)
1556 move.l 8+0(a6),-(sp)
1561 move.l (sp)+,8+0(a6)
1624 move.l (sp)+,-12(a6)
1626 move.l -12(a6),-(sp)
1631 move.l (sp)+,-12(a6)
1658 move.w 8+0(a6),-(sp)
1674 move.w 8+0(a6),-(sp)
1695 fmt: .asciz "%s, line %d: "
1696 unknwn: .asciz "unknown file"
1698 llxl.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0B
\ 1.define .lxl
1706 ! #levels on stack (> 0)
1708 move.l (sp)+,a0 ! return address
1709 move.w (sp)+,d2 ! d2 is not destroyed by .lpb
1719 lxa.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0\1a\ 1.define .lxa
1727 ! #levels (>= 0) on stack
1729 move.l (sp)+,a0 ! return address
1742 lpb.s
\01.s
\0\0\0\0\0\0\0\0\0\ 2\ 2¤
\ 1\0\0ä
\ 1.define .lpb
1750 ! convert local to argument base
1751 ! should not destroy register d2 (used by lxa/lxl)
1753 move.l (sp)+,a1 ! return address
1754 move.l (sp)+,a0 ! local base
1755 move.w 4(a0),d0 ! register save word
1757 and.l #7,d0 ! #data registers
1759 asr.l #3,d1 ! #address registers
1761 asl.l #2,d0 ! 4 * #registers
1762 add.w #10,d0 ! reg. save word, lb, pc