From d58d7146ba19f58166e9c0098ea4df0c143c2802 Mon Sep 17 00:00:00 2001 From: b1ackmai1er Date: Tue, 7 Sep 2021 18:40:02 +0800 Subject: [PATCH 1/2] forth updates --- Source/Doc/ROM_Applications.md | 14 ++++- Source/Forth/camel80.azm | 5 +- Source/Forth/camel80d.azm | 2 +- Source/Forth/camel80h.azm | 71 +--------------------- Source/Forth/camel80r.azm | 104 +++++++++++++++++++++++++++++++++ Tools/cpm/bin/ZSM.COM | Bin 22272 -> 22400 bytes 6 files changed, 123 insertions(+), 73 deletions(-) create mode 100644 Source/Forth/camel80r.azm diff --git a/Source/Doc/ROM_Applications.md b/Source/Doc/ROM_Applications.md index 5a1ae7f3..8eaf4f24 100644 --- a/Source/Doc/ROM_Applications.md +++ b/Source/Doc/ROM_Applications.md @@ -246,7 +246,6 @@ To reset Forth to its initial state type ***COLD*** Most code you will find on the internet will not run without modification. -A glossary of available words is listed in the \Source\Forth\glosshi.txt glosslo.txt file. This implementation does not support loading or saving of programs. All programs need to be typed in. Additionally, screen editing and code blocks are not supported. @@ -255,6 +254,19 @@ Extensions and changes to this implementation compared to the original distribut Source code has been converted from Z80mr assembler to Hector Peraza's zsm. +## Structure of Forth source files + +File | Description +--------------|----------------------------- +camel80.azm | Code Primitives + camel80d.azm | CPU Dependencies + camel80h.azm | High Level words + camel80r.asm | ROMWBW additions +glosshi.txt | Glossary of high level words +glosslo.txt | Glossary of low level words + +## ROMWBW Additons + James Bowman's Double precision words have been added from his RC2014 version: (https://github.com/jamesbowman/camelforth-z80) diff --git a/Source/Forth/camel80.azm b/Source/Forth/camel80.azm index c082ead8..e103d8f8 100644 --- a/Source/Forth/camel80.azm +++ b/Source/Forth/camel80.azm @@ -75,7 +75,8 @@ HB_LOC EQU 0FD80h ; b1ackmai1er difficultylevelhigh@gmail.com ; 22-Jan 21 v1.02 Adjust for revised HBIOS ; proxy size. -; b1ackmai1er difficultylevelhigh@gmail.com +; b1ackmai1er difficultylevelhigh@gmail.com +; 07-Sep 21 v1.02 Separate additions. ; =============================================== ; Macros to define Forth headers ; HEAD label,length,name,action @@ -1070,6 +1071,8 @@ snext: next INCLUDE camel80d.azm ; CPU Dependencies INCLUDE camel80h.azm ; High Level words +;INCLUDE camel80r.azm ; ROMWBW additions +;INCLUDE cameltst.azm ; Test Functions lastword EQU link ; nfa of last word in dict. enddict EQU $ ; user's code starts here diff --git a/Source/Forth/camel80d.azm b/Source/Forth/camel80d.azm index b2d15fda..8365b8c8 100644 --- a/Source/Forth/camel80d.azm +++ b/Source/Forth/camel80d.azm @@ -23,7 +23,7 @@ ; ; =============================================== ; CAMEL80D.AZM: CPU and Model Dependencies -; Source code is for the Z80MR macro assembler. +; Source code is for the ZSM macro assembler. ; Forth words are documented as follows: ;* NAME stack -- stack description ; Word names in upper case are from the ANS diff --git a/Source/Forth/camel80h.azm b/Source/Forth/camel80h.azm index 15f195ef..e28466ca 100644 --- a/Source/Forth/camel80h.azm +++ b/Source/Forth/camel80h.azm @@ -1011,75 +1011,6 @@ WDS1: DW DUP,COUNT,TYPE,SPACE,NFATOLFA,FETCH DOTS1: DW II,FETCH,UDOT,LIT,-2,XPLUSLOOP,DOTS1 DOTS2: DW EXIT -;C D. d -- display d signed - head DDOT,2,D.,docolon - DW LESSNUM,DUP,TOR,DABS,NUMS - DW RFROM,SIGN,NUMGREATER,TYPE,SPACE,EXIT - -;X D+ d1 d2 -- d1+d2 Add double numbers - head DPLUS,2,D+,docode - exx - pop bc ; BC'=d2lo - exx - pop hl ; HL=d1hi,BC=d2hi - exx - pop hl ; HL'=d1lo - add hl,bc - push hl ; 2OS=d1lo+d2lo - exx - adc hl,bc ; HL=d1hi+d2hi+cy - ld b,h - ld c,l - next - -;C 2>R d -- 2 to R - head TWOTOR,3,2!>R,docolon - DW SWOP,RFROM,SWOP,TOR,SWOP,TOR,TOR,EXIT - -;C 2R> d -- fetch 2 from R - head TWORFROM,3,2R!>,docolon - DW RFROM,RFROM,RFROM,SWOP,ROT,TOR,EXIT - -TNEGATE: - call docolon - DW TOR,TWODUP,OR,DUP,qbranch,TNEG1,DROP,DNEGATE,lit,1 -TNEG1: - DW RFROM,PLUS,NEGATE,EXIT - -qtneg: - call docolon - DW ZEROLESS,qbranch,qtneg1,TNEGATE -qtneg1: - DW EXIT - -TSTAR: - call docolon - DW TWODUP,XOR,TOR - DW TOR,DABS,RFROM,ABS - DW TWOTOR - DW RFETCH,UMSTAR,lit,0 - DW TWORFROM,UMSTAR - DW DPLUS - DW RFROM - DW qtneg - DW EXIT - -TDIV: - call docolon - DW OVER,TOR,TOR - DW DUP,qtneg - DW RFETCH,UMSLASHMOD - DW ROT,ROT - DW RFROM,UMSLASHMOD - DW NIP,SWOP - DW RFROM,ZEROLESS,qbranch,tdiv1,DNEGATE -tdiv1: - DW EXIT - -;C M*/ d1 n2 u3 -- d=(d1*n2)/u3 double precision mult. div - head MSTARSLASH,3,M*/,docolon - DW TOR,TSTAR,RFROM,TDIV,EXIT - ;Z COLD -- cold start Forth system ; UINIT U0 #INIT CMOVE init user area ; 80 COUNT INTERPRET interpret CP/M cmd @@ -1090,7 +1021,7 @@ tdiv1: ; DW LIT,80h,COUNT,INTERPRET DW XSQUOTE DB 59,0dh,0ah,0dh,0ah - DB 'Z80 CamelForth v1.02 25 Jan 1995, RomWBW 19 Oct 2019' + DB 'Z80 CamelForth v1.02 25 Jan 1995, RomWBW 07 Sep 2021' DB 0dh,0ah DW TYPE,ABORT ; ABORT never returns ; DON'T FORGET TO UPDATE THE BYTE COUNT IF YOU CHANGE THE SIZE OF THE BOOT MSG diff --git a/Source/Forth/camel80r.azm b/Source/Forth/camel80r.azm new file mode 100644 index 00000000..bd2989b4 --- /dev/null +++ b/Source/Forth/camel80r.azm @@ -0,0 +1,104 @@ +; LISTING 4. +; +; =============================================== +; CamelForth for the Zilog Z80 +; Copyright (c) 1994,1995 Bradford J. Rodriguez +; +; This program is free software; you can redistribute it and/or modify +; it under the terms of the GNU General Public License as published by +; the Free Software Foundation; either version 3 of the License, or +; (at your option) any later version. +; +; This program is distributed in the hope that it will be useful, +; but WITHOUT ANY WARRANTY; without even the implied warranty of +; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +; GNU General Public License for more details. +; +; You should have received a copy of the GNU General Public License +; along with this program. If not, see . + +; Commercial inquiries should be directed to the author at +; 115 First St., #105, Collingwood, Ontario L9Y 4W3 Canada +; or via email to bj@camelforth.com +; +; =============================================== +; CAMEL80R.AZM: ROMWBW additions +; Source code is for the ZSM assembler. +; Forth words are documented as follows: +;* NAME stack -- stack description +; Word names in upper case are from the ANS +; Forth Core word set. Names in lower case are +; "internal" implementation words & extensions. +; =============================================== + +; DOUBLE PRECISION WORDS ================== + +;C D. d -- display d signed + head DDOT,2,D.,docolon + DW LESSNUM,DUP,TOR,DABS,NUMS + DW RFROM,SIGN,NUMGREATER,TYPE,SPACE,EXIT + +;X D+ d1 d2 -- d1+d2 Add double numbers + head DPLUS,2,D+,docode + exx + pop bc ; BC'=d2lo + exx + pop hl ; HL=d1hi,BC=d2hi + exx + pop hl ; HL'=d1lo + add hl,bc + push hl ; 2OS=d1lo+d2lo + exx + adc hl,bc ; HL=d1hi+d2hi+cy + ld b,h + ld c,l + next + +;C 2>R d -- 2 to R + head TWOTOR,3,2!>R,docolon + DW SWOP,RFROM,SWOP,TOR,SWOP,TOR,TOR,EXIT + +;C 2R> d -- fetch 2 from R + head TWORFROM,3,2R!>,docolon + DW RFROM,RFROM,RFROM,SWOP,ROT,TOR,EXIT + +TNEGATE: + call docolon + DW TOR,TWODUP,OR,DUP,qbranch,TNEG1,DROP,DNEGATE,lit,1 +TNEG1: + DW RFROM,PLUS,NEGATE,EXIT + +qtneg: + call docolon + DW ZEROLESS,qbranch,qtneg1,TNEGATE +qtneg1: + DW EXIT + +TSTAR: + call docolon + DW TWODUP,XOR,TOR + DW TOR,DABS,RFROM,ABS + DW TWOTOR + DW RFETCH,UMSTAR,lit,0 + DW TWORFROM,UMSTAR + DW DPLUS + DW RFROM + DW qtneg + DW EXIT + +TDIV: + call docolon + DW OVER,TOR,TOR + DW DUP,qtneg + DW RFETCH,UMSLASHMOD + DW ROT,ROT + DW RFROM,UMSLASHMOD + DW NIP,SWOP + DW RFROM,ZEROLESS,qbranch,tdiv1,DNEGATE +tdiv1: + DW EXIT + +;C M*/ d1 n2 u3 -- d=(d1*n2)/u3 double precision mult. div + head MSTARSLASH,3,M*/,docolon + DW TOR,TSTAR,RFROM,TDIV,EXIT + diff --git a/Tools/cpm/bin/ZSM.COM b/Tools/cpm/bin/ZSM.COM index e7504177241c3059c8eec85c3f80bf07e2ce26af..72d3e62ce56b19c19362a8a8965739f4e01d1ef5 100644 GIT binary patch literal 22400 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 literal 22272 zcmeHvdwf*Ywf~uCGI>m95*{ZB!kIYL*4kbljoRWsePtLDGlRzxD_k!%wNsqj)^rp^sE=~E-?h(7612CU z-|zFe_xHJf)X3TU?7jBdYp=ET+H3E<&V+7nDjt%{Ip?rkJSIE;Dl2OZo+{U$WY>do zzv}_n)#Z0>^t*P*t{&OJan5^W=eJ~~sL7GhRxW(5BS&Z8;!pLvj>@jPWYs8tH8~K{;&acbPAIq*sWRKt)klhc+fg|5?DHdb#Z{@x@rPGwR3;}7T zdq7qN!RGM+gts^b z$c+`>D=Y65Mcv2nW^msvj}3Gw`x|*nzp}Kkr1yaESNBilK%_y3hKn$+K;&M%a-^l- zHPYsC%E=KcKPz(Vkoy8civ2%)%E-K)E>THubo9u5VprhEoW}TuF*z?Ft!f<0@@=2X z<%*)Xd+fBjL$Jq=m#i(hGAh(Qfh4c z3Q@VQF^ab1{4>Si=8cWT_sG2mj$GLY=7$<|iC&hBWi=)`>GO@1O4DOK=f(zn*Usf~ zj^|z}u8p2iUe;@9M#gN14>g7!ZY=(>?0y7e_bH2;9A1On-lj`~fE;O@^XGDLP>v}} zRz~}?!4I?h1#rsb(ShMgewikl=VWz#WQD=4$VWSoCb;ANlUxOLueo1br0-fRhHrZw!`xqas@x6to8Cc7S!U4M`rZ^_Qz%GKR2MRq+b zYjltv?U$W*$j*O}onMum_sY)uWM@!ze!=g)U3T3jdsevamcx$4ZO;2;Pl+oeyEpm+ zhhMG*ks;aoLuGr5nkU)SOzE7OCgo;iO7U(nlmAm}P}%PbMm>3wsYm^x^inw&juqbz zaY{CInPeALK{~5ir1zAqEkGO%_wyf8eF=L}9yF+VkvXFKF*$HJx5(Xv9zR)5$~jE* zzAY;k4T`u}bxYR+Pb%;j1BZWPa(6+Meq=(8Qtmnz)7aQ0`!wQF96eJx1Huyf)O;ax zkE)X-l^2Y+1f&In%EPt6%Cz|E-^yuoPL|e&2Z18^+Rscqfk;^qpNhG}r-A^8=m(gK zQJKb~x&>Ay&^t|_*LIuO+!;{rkerXpmq1PP zgr|LgLeee9H{2_uf}gEyH1W<@@!N9WSl0P{-BC{q6s#ibX=6$8A7$!5?PiQkuvCyN zV5cb{>3KWxQ%VPCUMsByJ4(%-Rx}I~{bM%C;=WB*b;3BG(Sxa!LT`Fu6zq++KProT zBnfraYk1@fHus~lPfe9_fI16mk{;jiTRCq|r6Kf|K}j+9RXY}%@9dhv<@SkNxBr=> zlhUK=-%w4*+z-ov;eKcZn^-u?NH&8oUgKl^jDAD;8}oLr$$7!isemG>&9;$HP426@C(9LC^J zl$uvcxz*;i(zI&xl~R_EjpcAzQKq>S&)p$YF|i1Wph{9cG3xV`stq-sqd{ zpCTxf3n<^K8u9E6M9!H3z@U^(OO^RWMQ(_AO%YLmW%|u3jjKQZ%Rr^BifD)J=Hi#ln0QnrtAh^^8@Xe|f54Bj;1W#Pg|1 z@k)8B5c!z}Jr50m2alA zx{s7*A0gXS;kcL@x?sw(lojP$7Fp^n`z+tUUy{4lJNdQl_hr>AH88!R)_0(x`z%SA zy;1tOjI!eQ<-Gu$)f=$hE~TiW)-OrA3??4HeF!}CY=R@CLLWey}vYy|e?h?^Y*oGb;JEz=` ze#Y@U(RDhltmu_A`a79cnqHc&3CzU=#xG`^Wqs_P(#K>eIvuJ+SCEdC^NjL2kS&Cl zinZ;6)h6k!Jd*~)Km=-_mz1Gss*sW_1@U$x2mgSEe?z*)(EtX>_%gppLRyD^MPvw* zObSR%#G?f35{A#GR!OUq?3FSYcjK#}b=RjQJDcc9>*l4&ZfZQg{fC^?n3%MyAi6gI z0vH-n6ttb7chgdu?Hb8M|E8rRV~yB^UH(k_^Exz%?j?FQE!Bv->C^NmHzv5VgTNA& zJmgJBIqN%FawvU5=OQK>l+I++xI$3wqgdD7nOGuWJsz+!CMn;_aXuqYHhLlxjh@I% z8k)%GGXYx$FGsExGTm3nYIEeYRrN>yVl93Ke25feg1=-sdOl6!@1k@%P z&2y?u63EuHA-1}MeaTW<$~*)*bv8{3@1hmLyJ!W&NT!-AAV|5YjU@O>Y^Ol%Gcv|k zHQAe)MwoC3XvO^q1GRSXdTS?b)|fi>5HmEKV5~I@jGdiTR$15I>GwCSH;9_)WkiN56rq3P}?c13lvM)TI9&K^?(OX zTUn9b{?+U%`@^<#+2^t+CZg1emDLWl*Hqf$qOnU8OB-&pKuW zQzr41MMr9jn04Bkv}0`AL}q1!Gbd@BWKqcFoLC|;tqci=Nl&OJT52u;TCpb5V(gIC z5CXQMSlNm)145k5Ru7UInDQB8lJIP_MkTD#5;R(-DXYc~G@3F}4Riqmy&Ry`Q$dq@ zrjcX?NqHd2YW9qVcCgVU`m-8Bui7ugYc+Y|DAZc6Mav2%+-!zY;2~qcL(Ed9CR4KX z5U8gd=_SKT(s1d@GGx`{0#H`5cZkeC-e`K06G~=ZDue^GRAVC0GTfMS|DcC{dtxqq zA)B8$(Qry9XbTMJYB14D5Z!EtQq2K$LaEvO5CKW^Lt@_75P3oYK}x8$pt%5~N`R44 z?H4a9L&dz|Q+mEQQE#!UR1fw5K+}4tlx9#^XN7;Kv*FNG4|fgB-->Bu_-I=J4_hVc z#@pcCy#cz-v`mpr(A>L6nR}-h$D~=p<|7Cwjq-Eo5QHRUqwQ7Jvj#YV%AIs5$XH|O zc!FO=VJ2(5580?Bx$8)DL2G;hey9}nQ}-MRkiDt_WPchkiD-(sPYzWOO82t;(1cPj z&iSN_B<;+xhaS_`&od6mLTA=1A5NowNRghb)Lz)h!90|TbfS_4%exicCl2mBArA$gw8a=Foe+Q_ zv>De7pRM7<}BwI+Tj z>r@M#EF@4iQIeJ%aG$c|pR(WyfF$-wnqSWY&95hEwn-hBI1lDcN|;1O1~WNGspV4m z0!?i$OkpV7s$Z%@PcYAaiZ&*-m?qk29wu5m53X!}etud0*8E=lT`GaZ=3kp|os-s+ zNe2R)VnCAuyJYGW%)am`E4pV2!HM$%D>r+T|BuOzKQr5s8iS@&r`#lO=#1r>StNh9 z`p?<>*<%7yb`6ApCA&=;ie%py1yIiiqi{%KN*<#) zPRxSf$7Yoky*rEk_{-+v&*K0gG<ZHOVu##2*sI&E zd}#9=I#L7~Ot=Y-ea4siyVRr6XLM|{Il(wvP6tl51 z*&<;`6R$KS_fy-%of5mbn948=soL>7A~4@^(h+z3#QCw)BVI2)C=M6I3oM0i7s_*Q zn!9N3cjwNS*D~+^c@NEdV%|IR-kWz}o>j6-`O<93Bi$#xC|Qeehu3=m3~kl!U2yJh zzDm%W+uT2bH*|Rq?!EU(vlAD3I-#I%%qC=^^q^o-uac(YKCyHayK6MjmEdv(_lIsc ziU}lW7vJzWT^Wj)LUe!l6uoHohEH|-=uopqvS{ef>$-6X`h7W!S6ueRpxp4DqZI?x z_7`KvDh9>|)Pdy#A}WiYqPpP7HF#>zFKqb$`arNdL}>RC;5nHrxsD4Y@d4oZLNIloWcheGNb&4%IE z4WKhd^%Qc=T!P>fjo?`cVrik!nnix@L_4C*h&$2s&O^dkqV8QF-aV)EWIt;7*9jIk z+a6A`(ClKS3~?H`Lq@0uu7w%L@%X9i{sZhzrASxexEJm67ax(kJ+HHCSwveLzSe}W z3F0=3$_SjJP>dr8#W+JZr$_cT(p72|NsqWD&7poJ=FBFoCw3H;y=vN5E zM8Ee}Ll+{cH}pr(~(RUsgu1mOrbdM+Y3CG4qTV?aO%|8LM#{xx7RTXn#s zhspS+^&_YpSp)R<$QVYZ@z zhr*`D`wI&ZwZOs}%8Kk&g;pKLjE!oaqpUFIxVsR7V8luP9@hI>IfHNIN}aLJ*IKVP zxB4hGnA@*tsr7k{sjWUOXEL_?{2gZ0Q<`FKsj2h(+EY{3X&DOuwOkta)56CJ`wM?n zc&PBj!cgIGp;CCF@U6npqufv!k2~n`Dm}hIj}!E`j~>6L#}DZ-hJU|EX5OXDqfGA{ zBW>n3$>ea#<|@!1-*7+p#rrTDQ!twhRxTfLJ*hc|BxAQ|`{2-#_0DoG-hMx^Brq_k zlN4SAg|DXQfV*J>Nb|o~RE$uT{j!InsFef+1rY#3FsLh%KnQl(FV9}V-~1VneMt}m z!vJI-?@xdbrx($pBQDlbM1u?<@`Iu}r0Q6r_qQp8rtkcY?r49v*e#Y1;L)uG*(AfF zW)JKEab%7Y6EYm%@V1;su}g<*i{kC~A~J{#CE72F{0pQ3G>rxb%j2@gk?2#fLGjNE z-H62yOg#u~qWGbsWUXMUBH@W<%EozGSv;J;U`t>az@aLw9FdJCwJoyNq+W#wkOJdC z&zM8i9bRiftQ5%%fk2cX_TtGo$H>?sG)tRom}@a@hAAf`kB~hQrI8Kv1rBdC#W2nC z5aEOUZd$jPli}Vj9}?b;-WWy{7e4^1V2VqW2U=kZ!w$2A4xrIXmcL$aY1p(9hM9#L zJyDMwy-);*HXXVGuhbSfu9Eizj!dU02n=|PX_l}!DJ>W3FLoXhe)WN zu>mkYzG1%%OW+*QbR=@Ei4{|*RG8x1pjpGm;~Pfg+>x*rCzV)$t}KFx;44d+2xqY% zl*I(!v9<^SUEv9KOmGACAvCK6^kMms1a>+w4-K4$*E^NJNf!>eX zivr=QFpkElhJPESy@BDX@ZfO=?u4I_btwo&8ws-U-Yu&uBoRJDzB(Y}jAPM2#1Mt} zAuvvaD-cG2SQz19VMK{dHdufLm#G5-q}YI`03KTPPhrg;j~?4uvI~m+E%E@4Ax;tb zd$jyLa=7=vaD2mk%sD`~8Ivp_5JN9E#vBjGM^{Q|gXfeZOU@u*Fc?L+VHH9e!+Wt- z_CohY9nZ+TaTLR#mXQ~VNBi_guaVXaj&9>dx9WNij9#ffqBN2q?~;kC@zHID(XGb5 zU0q_|&Q8QU4fsgJiP%J_cn^l1d3_X@k&7eNfpMk25z~dAJqTdbrUQARHmG$I z14I-(kDc}@e_9eGA{mvJQYZa~2A!Xu8{cpjDP1ynW%Ool^d_D1adBvAF|>1RVAx04 z1}J=`f3#a4E-1ODWbT65i`q(GD^*Lg-OHVsMuWbtt&%hA>uU{MzP`TBpu@BIELPn5 zc0HAJ8u4ss{sbir>&Ce>ee=pxlr*=*FY5Hot=x(f{i?PQXV9?H@z0Y3? zoPMv3)9d{x*E`$m;y30RYU=A!SDBI2a~346^#W%$)HZjl;4%z#bt{*1IzwGsef(c3 zX^#Jh67M2zrdZe3`7)PfsIRG+2ax)PI#YV4Sl_(%2xm7mwAP!rd_#l0Mn}oIj%=2! z`*%P#uUwp}%SYl$)l*WNnnKCSR3jxFsfPTV=GIa@mttsctuq=jk<`Z@L%Y`I_>XmB zb8DxW>iliIK3`l_vr-y0BJm4Iy!AC4mt*kO*T;XZL(&|7Sck$+9haKZ;_cu#tD&`_ zFl;>*Hc?9YM5&kB zBW+2PlWx&FX&0sI4SKY1Ub|+Hvs2m`;j)eOt6JCFIHR#1__2l?8@%le7D`*|TXNA~ zL))5_@$c#=ZH_<0(w6xCyaMPzdwlau<4T{uB?a(JHQtUdayn!4%GTP{)cgX-x|1{5 zj1aaz{%alH>pSCLMSUyA^9;Q=cgAnSyT7fDH{=^3V}Jah4k_xN(iM2?*VNy^O{cW& zK5n|v+uYuf4tiQZNc_ur1ubj55X1~)YfVeTbS{6IucN*t{xzKusXzXl4)2&fx6?cD z{SxnMI!X;(iV1dAsL|1^cGX>>sHH{4^;9uLC_NGD3V)Qq(b?|tH)-=ak zbdPWY#Z+c2L!N7c%<%LK0W!Q7+rmu&SZ11B^C7FwHB| zSf;~&g`G0%nmbzZSf<0@ikWF@u5W1Vm_eD9kbA0$Wnfd#Mf1w$`qosC(Yz9xn3|qn zND}IdKcGXV8JTbC3cdAp9bS%`X7c)=j`_gDyi1hDHJupmk3Xm@ zB+hptgOX;He49!LA!WeyPDqC`5c}=ALSm~ozD8&2XzuVfWN`V@iD5n?mttPn)`ZD$ z8JBNf=&z}7UN@U^>loAY`Q|!bON+17hO$PlueQbu2AH99G)yz)h=ZvaEC&{*X6BQ# z>}{@{smq_si0=$>S##U!YU-LA;#+j)wl%fh<~qUx33haNGj#bW3%x7J4^KBB+vaa> z?N~R5L$+NjHRh*4xxH)Z8)kC(sSAl9a9f~!eS=234tYO}WdqX@E_Qs-ewA#_f^(qU zxVUl&Tn9d_4=$E+!{SQ2n4M#LKlx@5`48YJsLKRhzt59(kE=`W364a=9xr?Z{x8ZM zi;pQ^UwlmM8deL2)#bzL!eRKw6=AjX4b{Cotk%4tZde}fcl`+7QewLmbK<0+{cSmV zOgDozT8IelWZO0b3JWO=aYYzAQbcIOdFU3$;iJW$!U@56j2$jSCl41y=MjAA5Cy{X z7tuu+o1DgsyglJzTSQd-N z@28e05G$Or{0;Q!xU9r7?#L>!Scc3#iYCr$lxJVGa=X7Y=edgEF0ik*2@ZknLQDi7 zdrlY|^Ipsmg>>78(cnmM&v>ZNg-o>4u$q6Rjt@KRZS-Bm9IjlzmlfHrKU08q!l`h+ z1FFd}mr@YSFCu2%v9Qf;>_q5vd7V2Xi`|I$2SDKHOW7ZvaEZtPhIiz1w!p1&;!4f#SAoq= zK)zw0*2Hl1x&h@G7rsge6XEcuHLvL{b%k}_u)5Fc999Rcj^QzzRUEJi;V$=|W#5oN zonD!7Tv@V2`Ic+MgB=|>2jS$lS@wjUEdxm7kQpFWd?mnO@S%X&Oh7$NW^SC|e92Mv zD333}h5?5W56UlAy8Ce;!A2)7!eGy_7=K4rn-VE=jQEs|c((Ngjv#fyr>4}_hSD?O z4`c}x^zj61ANfj|x-K%SMZH3>or@{6T5v`}(mbqd(Zm`%f-(Yai|AUw%@}<26y=XC zV(6hVPbM;+G(4i=b6NOLd8zEoSk}-z^IlysuUicFA$URWDXr>O-2>&NCH#AiZ(puU z<&+06$LtWDf03P={p=GC9mg34WAyonPR}W66({#yUcA{)lLZh_fLv7(EFB#rk#rro zt2|iDntB8b#-82QJ*ayLPJFQ6^`4Ao@V%+oaT@7+a@U=mx8Hf^owqRuIJ*03sW5%8 z)y#?Ur%+ji7OEk5vikDD@p2B*4Tg#?j|M}(T&%qUML8GBFKgMjY3KG`ZVsv(e+uu8 z+sk#9OUFUh0mHzS-Dw!qMnMNKlf%dZW6av@J^9}=lJ@jLZGVEnw2CXmZR6qzd-+1K zO89t>*oAKs3?OJXW>F8#rm0n|Eb!op>7~gM!k?U&;qDs79gz7Uf{6t}#cxXeJnay_0 zBR#{%as0**4`5erHO4o*kLw2WFwTlI>2%p@9OykTVAY4M2D~=X23QNy8P42IN6(?! zBKvPEf$SXcoWU}Ba?{d&S476DfU(`&->iYDU)JiVq1&L*#sbJk*0;jC}abI$fQGv{nxXB>4lUtzq! z+2=0}-B4MxUdPq8uIIQK^jq6nr{`+h;PceBHJI?a*2vYYHE}g)Sp%QCwzVCZ_7slO zzAKy@t?MJ%bzXK|kX;M?Rj$7!M(_NX9eU#;Zoae}^=fIQNp+vhbAws0UF%k*NN$x{ z6q#S8mPCHBOkEIpewkVvd371?e2yuRa;9?g!POyOz?r{18^Jl;r9Rn7d^(PzUI9s8?nz$EPDzkaDQNP1xA6YBiSE zt7Nr63M$9k^i|SdwPWSV&n19c>S@aK0S$~wO1$nDGU$xApO$GVDZq&eU8KNGN^_b{ z=|7UOBIBUxDD^|D(r>Fu!6vmp!5#ts`j8*rIt@cKHl zQ+39s=EkNRq~3=1_Gu_?UE`f@;W$R?T}vH0lbPe^(VK%an{`61Lr*2s9flMnR)>+2 z6o-itE~Y6#v~m`-K+3x1`O5UzAX9~4l>Z~EwO2>Sn+VKajWIIe+GlW9-K9kuo|DIy z5}uTVG9`4O_~)|o1Na+YAVg3SgZfTW-Ib|oO=X6tlH$Tafsor z$5Ee@t;&v6PD)pOIE}_wIKgNFHpo5NC&mc6rcys-8Ou6X{DG|Otv;}8!8Hm#7A;bI4Xmg-m!efQ?@RMSVKIB~>BgTO+w0;bE? zr`jrp2jSLMb&D2@1q(?~ys;uzawk9;)WC z6&=kvnq6wNl#ytY(lSzaxiq1W+Xm|eEvF!DRq zN_OxV%LT~mtgcM$J%FNNF^p%T{tZ@>EGM8895GTo#>8Ma?v0YLQtbgwV5U*+`RVps z9?^0Kw%_tAE%)U1Tb@Af6VLc9zZ^bVb@Z}){(R!CD4+ib*}1^?iRXGsUiQ%Z$GIIX zGh+jSZ}-!XYM2Ubi9(y;)(VxgQ-E>ECpbw}60rPqYIAIu&txg#8$0&&u*c6fSJVei zSwRpCWA6dUOn0jMALH#G<199DFU;Fk{NQ}OoAe#dry z84zQA83_!BF48=W!6xI2-nr^rA)hQ~0Qa*3=AlJO5mBz^<4`0%jXp%RBEtDCvf+3+ zIlqQx06rQ$Jilg-%14T7)ZECISFm^YRes!J%&)<9X*H5422j#hHQ?EYabXxVG>TGq zZu!K>!Wh-%)I#G6wJ6V{Av07$EgkOX{ngC+U#gYNDA?0k50eZLX9osfNg@I@K6yr)#Yk?Ove1@%9`1%sY2p>mRrD;p6x3)!P@h(WR&7A=eH+ zN%;LQ)x`#jul1j}RjnzV-3aD-t3_KDE{+=el>6#L+ecVJPZ0n3QzvSW7T@5{9Y5|_ zj!OJL0v4}QcGRuLKgbHOkGXgFadHCmJ=m0^;ClcI2;T-^xAw_=6g&*ax*Q-NAf;7z zqh=R5GJCK?Nl<>vFF~qEBum+#7=&gABm+r`+D2pS78J1QP~|AEHR}_ruAGHt)sl&* zJ&Qr3Nce;eyy>$8UsBHojuB^6OO{3~-^tZ2{Z6=SWAeN2^m-Mqz!No z*^es#KkgKND@P|G!?Yo0I;veD1|so##kL#^;W%mOR%TDHPHy-;dYIKv|MH2eM1o<4 zI5D*Z3v4PWD{q~&t7KDQ$uYC9_E%{W9C~|6$ijc2-#JXbGgS{h=bSH{gze^!qXV*e znwd9f^k6@Ti7*T{m-LANsSB3E2fMr)jT&J=>adF}29i>>P+Fxr1T%mtq{Z1eiP)H< zjjTY(&N+xp;|m#?f+2%{HiQ2?ek~$BQ}{PAz#CEc8;YIraM@uLe^9}n89Yulg$1UJ z9h1_)Hrm-^K_9^nXMmPq=#d7vOh1=(H~Kvn^@hQIv#n_6bCvpU&$s=?$vOz#el zQDZ9LritKMnp!33GSHBZX9^$k|Ay;dM8E7erzl)g==Y7*J0^1f!g716aNguI8&GX+ zR@BDOdyVHHAam0hUr2522}st8qq(fQrC#~45x1sG8+$`b8?6tp=GGNvJ({-Ehdyky z-m4Yi@^7N(K324PO36M}0#XL8-(cC`Agf(n3-rNttl};{X1#3^?yLL>>$ms=?%Vuo z>M$dYKa0!%=Sp>5dnTxF6+!)F!iV^+4Ye`YWKP8xY@dW#Bf;u^9zSN{zTH3g=INGT zf0gSt|4}<$XS#0p!^^(ikAg6RITjnVeqW=Dkrf10%1ER2hpY@av{FvDgud8{TZ%<= zsK1D=LB*<*HXpYjVV_?3`-99gAUE)K<&yw!nW`|}-2j_>3ntCVf4mAR{tQP<;4 zu^O0Sj-1uXjXr`y#A+#Vp&Gv)L!F2yv;Seur&^-xm}AC7o9e@ltYU!o`acEeun~}k zFyC>nA4KR1umGb&`(OwAeIfiF%=7F7wOU{he^{eI%vf#z^O_{YbF$+*e*A0?&OGB! zS@9zdT%q+r2_K7_z2h=0A6X4};(QQd)(kNrcz$#iCkFCP_F1SI5xGP{f z+glu?tmyd;8e*bofQlRkJDdkQU|XE~{m#4K_ZmB0FUX2P=XhWhVmMY_x9z%J*KXOo zkaK)O@9o=f-nnUuu=Tp@w+P#|-z03^e)G1?+?s70p-I9`+l5U#w`{y=i?IFb&u`g; zT7Z4F^7`v`-E`fyYqZ+B?Kj-8aoc8LSI@SaHtrU-&~Nu}bXC^iZS%L169$v=Axz2# z;ha4Dl!9mdFn)eUGI~}7!q}C1R!75*&#k5n)bSj%0p68``6PWqE5f4ff;hszjcX{r zqvHzR+umXGwsqJz(w;>Fx^1fm*?w59N4R)9JV7r4LDop~)fQ=yx?XZAkE{v?!|<;! zulzt=T6+3KDKu9Mi|i160Q&fx92T)3cu`AULeh7lv~pNAlpcYi1Cp$GB8u%ht6{gP z<7&9ALMBxm$HC4>eD!HLUWY>s`YD~`h^QLTf=`Fq$mc-F%51wb-|J(~YxZ7;sFnW9 zhKuf=SNf5N{n-uPcwJ`aY_4a_fZ)XwRlUFGDs{6~D|dMJxY9dgj>o*Y?3ZP*T^^6Z zx7+K==nU&xIr|MdYNE@D<;VS%rZXi5{x9%s?CD(X9#vneYno_j89%k>JGXrQ)Oe-g zGX7LF%yDzLW!!phH}_rc0QWj~mb2?hb*;Jut2S<1uyV`Q3tBerTu`%PC(@n;t8U(g zf7dUlx%rv}?OS#%@NK$jLF@J}E~wwKX#rvhM`M@^qfvwsVq-5^x)9iS)+_R7XJ@k9 z>@=$>bk?g?k=fCzD2FONs;pVaSB3G71WO!90%7ZPmK?X{ARV#J(CYF4u5Nro-E(ZL zD;zsse6YiQumju4SMF?q?=4~q;P82{_<-N}Yt;B1oIZA3+1Nt!si6hMqVs@%B#KD0 zylg&mT(=Jl#hEk~+BX~r{b(HwvkNd2e*1|(N3-dGUz=HBpa^+dMq^{Qjymr0D}QSl zjfO{KqmKQFJkHTaujEG8>PEMjN4KWLa=UXzx9LZ>8bDo8a9+_ybc|kU99?Ttye%U_ z9y%XS_I?Wf)aWj5bf=CkI3500SZw4f!oHht+Htcs0fp|J*I`O(GmCl#6}PocQlaJh zxY1{IQi>-J6!K@Z{y;ZIrJ7#L@WpfzH(RIJDn{Oj9gna6bq8%SVql~0pdXCDIXo4N z!*VjC7$wHRh@WqbX_hq#vm{whC9I9Hvn(12pNiqEEfPt9>K=;p654?C@-V8wn>bfoG@-rECD(-c6Le zfoop=EaLP47Ct_X%N+Q@f?ytJrhA0RZ@3!fk4X2lAmX&Mf_z-sV;^Ua2}(zF`z~5? zD*u)rZ$IGIRkmAV%AGAyXaV`Z=P!mU!Wrw^TLdhtmMQkqElm7pnaEAeSlTvTvxOCK z|NQTNk^|=dN#qIKZ^@ILT%64Qug>Y7@Av}(!Z_U@))?3Rucq{$#Ql>4|Kz|wIq*Nj Nfp2!^{r~;%KLLw*7pwpP From 6d1b61c7a3202f9696b502db4bcfb9a1d97809a5 Mon Sep 17 00:00:00 2001 From: b1ackmai1er Date: Tue, 7 Sep 2021 21:52:37 +0800 Subject: [PATCH 2/2] Forth fixups, improvement and documentation updates --- Source/Doc/ROM_Applications.md | 25 +++++++++++++++---------- Source/Forth/camel80.azm | 12 +++++++++--- Source/Forth/cameltst.azm | 4 ++-- 3 files changed, 26 insertions(+), 15 deletions(-) diff --git a/Source/Doc/ROM_Applications.md b/Source/Doc/ROM_Applications.md index 8eaf4f24..071abe5d 100644 --- a/Source/Doc/ROM_Applications.md +++ b/Source/Doc/ROM_Applications.md @@ -234,7 +234,7 @@ For those are who are not familiar with Forth, I recommend the wikipedia article (en.wikipedia.org/wiki/Forth_(programming_language)) and the Forth Interest Group website [www.forth.org](www.forth.org) -Important things to know: +## Important things to know Forth is case sensitive. @@ -244,16 +244,12 @@ To get a list of available words type ***WORDS*** To reset Forth to its initial state type ***COLD*** -Most code you will find on the internet will not run without modification. - +Most of the code you find on the internet will not run unless modified or additional Forth +words are added to the dictionary. This implementation does not support loading or saving of programs. All programs need to be typed in. Additionally, screen editing and code blocks are not supported. -Extensions and changes to this implementation compared to the original distribution are: - -Source code has been converted from Z80mr assembler to Hector Peraza's zsm. - ## Structure of Forth source files File | Description @@ -261,13 +257,22 @@ File | Description camel80.azm | Code Primitives camel80d.azm | CPU Dependencies camel80h.azm | High Level words - camel80r.asm | ROMWBW additions + camel80r.azm | ROMWBW additions glosshi.txt | Glossary of high level words glosslo.txt | Glossary of low level words -## ROMWBW Additons +## ROMWBW Additions + +Extensions and changes to this implementation compared to the original distribution are: + +The source code has been converted from Z80mr assembler to Hector Peraza's zsm. + +An additional file camel80r.azm has been added for including additional words to +the dictionary at build time. However, as currently configured there is very little space +allocated for addition words. Exceeding the allocated ROM space will generate an error +message when building. -James Bowman's Double precision words have been added from his RC2014 version: +James Bowman's double precision words have been added from his RC2014 version: (https://github.com/jamesbowman/camelforth-z80) Word | Syntax | Description diff --git a/Source/Forth/camel80.azm b/Source/Forth/camel80.azm index e103d8f8..a85639a9 100644 --- a/Source/Forth/camel80.azm +++ b/Source/Forth/camel80.azm @@ -1071,15 +1071,21 @@ snext: next INCLUDE camel80d.azm ; CPU Dependencies INCLUDE camel80h.azm ; High Level words -;INCLUDE camel80r.azm ; ROMWBW additions +INCLUDE camel80r.azm ; ROMWBW additions ;INCLUDE cameltst.azm ; Test Functions lastword EQU link ; nfa of last word in dict. enddict EQU $ ; user's code starts here ; force padding to page boundary - ds (FTH_SIZ-(enddict-reset)-1) - nop +IF ((enddict-reset) GT FTH_SIZ) + IF2 + FORTH SIZE ERROR + ENDIF +ELSE + ds (FTH_SIZ-(enddict-reset)-1) + nop +ENDIF .DEPHASE END diff --git a/Source/Forth/cameltst.azm b/Source/Forth/cameltst.azm index ad480ed2..d9f6ca39 100644 --- a/Source/Forth/cameltst.azm +++ b/Source/Forth/cameltst.azm @@ -18,7 +18,7 @@ ; =============================================== ;Z >< u1 -- u2 swap the bytes of TOS - head SWAB,2,><,docode + head SWAB,2,!>!<,docode ld a,b ld b,c ld c,a @@ -45,7 +45,7 @@ next ;Z >HEX c1 -- c2 convert nybble to hex char - head TOHEX,4,>HEX,docode + head TOHEX,4,!>HEX,docode ld a,c sub 0ah jr c,numeric