The Phone Losers Of England Presents: Last Updated 6th of January 2001
Back To Code Arena
proc main:
global mode%,lineno%,colno%,line$(255)
local f$(128)
f$="\"
dinit "Translator"
dfile f$,"",0
if dialog=0
stop
endif
translat:(f$,%T,"",addr(mode%),addr(lineno%),addr(colno%),addr(line$),0,0)
endp


rem Traslate OPL source by invoking the
rem system translator.

PROC translat:(file$,target%,readfun$,modeptr%,linoptr%,colptr%,qlinptr%,indata%,dbg%)
busy "translating..."
trans2:(file$,target%,readfun$,modeptr%,linoptr%,colptr%,qlinptr%,indata%,dbg%)
busy off
print "translation compleated"
get
endp

PROC trans2:(file$,target%,readfun$,modeptr%,linoptr%,colptr%,qlinptr%,indata%,dbg%)
rem file$=filename

rem target%=   %T->3a   or %t->3

rem readfun$ is THE NAME of a user function
rem that takes a line number and buffer
rem address as input and fills the buffer
rem with the raw text of the opl source line
rem and returns the length of the line.
rem its is an integer function defined as
rem readfun%:(lineno%,linebuf%)
rem and is called using "@".
rem It should be optimised to take account
rem of the fact that the translator makes
rem two passes over each procedure in turn.

rem the remaining parameters hold the location
rem of the first error encountered. 
rem They should all be addresses of integer
rem variables:

rem modeptr% returns translator mode
rem linoptr% returns error line (from 0)
rem colptr% returns error column (from 0)
rem qlinptr% returns error line text

rem indata% is additional data that can be passed
rem through to the user read function -
rem it will usually be a file handle.

rem dbg% = switch to print diagnostics

rem The error value is returned and should
rem always be checked.

rem init msg handling
local qlinbuf$(255)
local clinbuf% rem line buffer - cstring
local qlinbuf% rem line buffer - qstring
local ptsrc%(3)   rem translator source structure.
local ptstat%(4)  rem translator status structure.
local pid%     rem translator pid%
local msp%     rem message block
local msgtype% rem message type
local linelen% rem length of OPL line
local lineno%  rem line number
local readfn2$(8) rem function to read opl lines
local data%
global gtrerr%

rem if user has NOT supplied a function to
rem read opl lines use a default function
rem that just reads the filename.
rem @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
rem the following vars. are really static
rem variables for the default read function
global gnxtlin% rem last requested line number
global ghghlin% rem highest requested line no.
global ghghpos& rem highest file position
global ghandle% rem file handle
global goffset& rem calculated file offset
local handle%    rem file handle

rem @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
rem onerr exit::
rem @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
print "readfun$=<";readfun$;">"
if readfun$<>""
	rem use user supplied read function
	rem this is useful if the OPL is in memory
	rem or you only want to compile selected
	rem parts of a file
	readfn2$=readfun$
	data%=indata% :rem addtional user data
else
	rem use built in read function
	readfn2$="trrdopl"
	rem open text file for random access
	gTrErr%=ioopen(handle%,file$,$0220)
	if gTrErr%<0 : raise gTrErr% : endif
	data%=handle%
endif

if dbg%
	print "readfn2$=<";readfn2$;">"
endif

qlinbuf%=addr(qlinbuf$)
clinbuf%=uadd(qlinbuf%,1)

rem initialise SOURCE
ptsrc%(1)=mypid%:
ptsrc%(2)=clinbuf%
ptsrc%(3)=addr(ptstat%())

qlinbuf$=file$

rem initialise message block
if dbg%
	print "pminit" : dbgget:
endif
gTrErr%=pminit%:(1,64)
if gTrErr%<0 : raise gTrErr% : endif

if dbg%
	print "starting translator" : dbgget:
endif

gTrErr%=startpt%:(target%,addr(ptsrc%()),addr(pid%))
if gTrErr%<0 : raise gTrErr% : endif

if dbg%
	print "process started=" ,hex$(pid%): dbgget:
endif

do
	rem msg receive with wait
	if dbg%
		print "begin pmrecw%"
	endif
	gTrErr% = call($0283,addr(msp%))
	if gTrErr%<0 : raise gTrErr% : endif

	lineno%=peekw(uadd(msp%,8))
	if dbg%
		msgtype%=peekw(uadd(msp%,4))
		print "RECEIVED-REQ LINENO",lineno%
		print "RECEIVED-REQ MSGTYP",msgtype%
	endif
	
	rem TODO trap non exixstance of read function
	linelen%=@%(readfn2$):(lineno%,clinbuf%,data%)
	if linelen%<-1 : raise linelen% : endif

	if dbg%
		if linelen%<>-1
			rem for debugging
			pokeb usub(ptsrc%(2),1),linelen%
			print "check buf<";peek$(usub(ptsrc%(2),1));">",peekb(usub(ptsrc%(2),1))
		endif
	endif

	REM messFree
	if dbg%
		print "beg pmfree ",msp%,linelen%
	endif
	call($0783,msp%,linelen%)
	if dbg%
		print "done pmfree"
		showst%:(ptstat%(1),ptstat%(2),ptstat%(3),ptstat%(4))
	endif
	
	dbgget:
until linelen%=-1	or ptstat%(1)<>0

pokew modeptr%,ptstat%(2)
pokew linoptr%,ptstat%(3)
pokew colptr%,ptstat%(4)
if linelen%<>-1
	linelen%=@%(readfn2$):(peekw(linoptr%)-1,uadd(qlinptr%,1),data%)
	if linelen%<-1 : raise linelen% : endif
	pokeb qlinptr%,linelen%
else
	poke$ qlinptr%,""
endif

return ptstat%(1)

exit::
if dbg%
	print "ABORTING" : dbgget:
	kill%:(pid%)
endif
if handle% : ioclose(handle%) : endif
return ERR
ENDP

rem this is the standard function to read
rem the input file.
rem TRanslator ReaD OPL
rem need to find out how to open text file
rem for random access TODO
proc trrdopl%:(reqlnno%,buf%,handle%)
	local bytes%
	local tmppos&,i&
	local tmplin%
	
	rem print "trrdopl: request for line ",reqlnno%
	if reqlnno%= gnxtlin%
		rem read the next line
		bytes%= ioread(handle%,buf%,255)
		if bytes%<0 : return -1 : endif
		gnxtlin%=gnxtlin%+1
	endwh
	if 1
		print "trrdopl: finished at line ",gnxtlin%,"with",hex$(peekl(buf%))
		get
	endif
	pokeb uadd(buf%,bytes%),0
	return bytes%+1
endp

proc showst%:(status%,mode%,lineno%,erroff%)
	print "RECIEVED-STATUS stat=",status%,err$(status%)
	print "RECIEVED-STATUS trmode=",mode%
	print "RECIEVED-STATUS lineno=",lineno%
	print "RECIEVED-STATUS err offset=",erroff%
endp

rem init msg handling
proc pminit%:(slots%,size%)
local lerr%
print "begin pminit%"
lerr%=call($0083,$100*size%+slots%)
print "end pminit%=",lerr%
if lerr%<0 : raise lerr% : endif
return lerr%
endp

rem process pid
proc mypid%:
return call($0088)
endp

rem kill process 
proc kill%:(pid%)
return call($0D88,pid%)
endp

rem start program translator
proc startpt%:(target%,ptsrc%,pidptr%)
local ax%,bx%,cx%,dx%,si%,di%
local bx$(20)
local i%
local cx$(10)
rem synchronous program execute
ax%=$0100

rem executable
bx$="ROM::SYS$PRGO.IMG"+chr$(0)
bx%=uadd(addr(bx$),1)

rem argument
cx$=chr$(target%)
i%=0
while i%<6
	cx$=cx$+chr$(peekb(uadd(ptsrc%,i%)))
	i%=i%+1
endwh
cx$=cx$+chr$(1)
cx%=addr(cx$)
print "args=<";cx$;">",len(cx$) : dbgget:
dx%=0
si%=0
di%=pidptr%

if os($87,addr(ax%)) and 1
	print "Error in FilExecute",ax%
	return ax%
endif

print "PID=",hex$(peekw(pidptr%)) : dbgget:
gTrErr%=call($0688,peekw(pidptr%))
if gTrErr%<0 : return gTrErr% : endif
print "Translator started ok pid=",peekw(pidptr%),hex$(peekw(pidptr%))
return gTrErr%
endp

proc dbgget:
rem print "?"
rem get
endp
This Site Is © Copyright Project Atlantis, 2000-2001