home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Club Amiga de Montreal - CAM
/
CAM_CD_1.iso
/
files
/
455.lha
/
Wreq
/
Wreq.a
< prev
next >
Wrap
Text File
|
1990-12-10
|
23KB
|
368 lines
INCLUDE "exec/types.i"
INCLUDE "exec/tasks.i"
INCLUDE "exec/memory.i"
INCLUDE "exec/funcdef.i"
INCLUDE "exec/exec_lib.i"
INCLUDE "libraries/dos_lib.i"
INCLUDE "libraries/dos.i"
INCLUDE "intuition/intuition.i"
csect wreq.o,0,0,1,2
xdef _autorequest
xdef __main
NULL EQU 0 ; Pointing to nowhere
absexecbase EQU 4 ; Adress to get the ExecBase
CR EQU 13 ; Carriage return
LF EQU 10 ; Line feed
TRUE EQU 1 ; Boolean TRUE-value
FALSE EQU 0 ; Boolean FALSE-value
autoreqoffset EQU $FEA4 ; Library offset
ONE EQU '1' ; Primary option
TWO EQU '2' ; Secondary option
HIT_RET_LEN EQU 27 ; Prompt lenght
UP_CASE EQU $DF ; Bit 5 masked
FIRST_LEGAL EQU 'A' ; First alphabet
LAST_LEGAL EQU 'Z' ; End of range
OPT_LEN EQU 4 ; Lenght per option query
WRITING EQU 10000 ; Not just measuring
ONE_LINE EQU 20000 ; No linefeeds
MAX_COL EQU 76 ; Max line lenght
MAX_OPT EQU 72 ; Including the option
OPT_ONE_LINE EQU 13 ; For both in same line
LIST_LEN EQU 64 ; Lenght of the index list
__main MOVEM.L A2/D2,-(A7) ; save registers
MOVEA.L absexecbase,A6 ; Exec-librarys base to use
LEA intuitionname(PC),A1 ; A1 = Name of the library
MOVEQ #0,D0 ; D0 = Version
JSR _LVOOpenLibrary(A6) ;Open the intuition-library
CMPI.L #NULL,D0 ; If the library pointer is NULL
BEQ s_exit ; Then exit immediately
MOVEA.L D0,A2 ; Save the pointer to library
LEA _autorequest(PC),A0 ; Start of function
LEA intuitionname(PC),A1 ; End of function and data
SUBA.L A0,A1 ; Calculate the size
MOVE.L A1,D2 ; Save the size
MOVE.L A1,D0 ; D0 = Size in bytes
MOVE.L #MEMF_PUBLIC,D1 ; D1 = Requirements
JSR _LVOAllocMem(A6) ; Allocate memory
CMPI.L #NULL,D0 ; If there was no memory
BEQ close ; Then close and exit
MOVEA.L D0,A1 ; D0 = Pointer to memory
SUBQ.W #1,D2 ; Adjust the counter
LEA _autorequest(PC),A0 ; Pointer to function
copyfunc MOVE.B (A0)+,(A1)+ ; Copy bytes
DBRA D2,copyfunc ; Decrement and branch
MOVEA.L #autoreqoffset,A0 ; A0 = library offset
MOVEA.L A2,A1 ; A1 = pointer to library
JSR _LVOSetFunction(A6) ; Replace function
close MOVEA.L A2,A1 ; Restore the pointer to library
JSR _LVOCloseLibrary(A6) ; Close intuition-library
s_exit MOVEQ #FALSE,D0 ; Return FALSE
MOVEM.L (A7)+,A2/D2 ; Restore registers
RTS ; Return to caller
_autorequest MOVEM.L D2-D7/A2-A6,-(A7) ; Save registers
MOVEQ #FALSE,D6 ; Return FALSE
MOVE.L A1,A4 ; A1 -> Bodytext (IntuiText)
MOVEA.L absexecbase,A6 ; Exec-librarys base to use
MOVEA.L #0,A1 ; A1 = NULL (my task)
JSR _LVOFindTask(A6) ; Find the task structure
MOVEA.L D0,A1 ; Structure base to A1
CMPI.B #NT_PROCESS,LN_TYPE(A1) ;If my task is not a process
BNE a_exit ; Then exit immediately
LEA doslibname(PC),A1 ; A1 = Name of the dos-library
MOVEQ #0,D0 ; D0 = Version
JSR _LVOOpenLibrary(A6) ;Open dos-library
CMPI.L #NULL,D0 ; If the library pointer is NULL
BEQ a_exit ; Then exit immediately
MOVEA.L D0,A6 ; Dos-librarys base to use
JSR _LVOInput(A6) ; Get standard input file
CMPI.L #NULL,D0 ; If the file pointer is NULL
BEQ done ; Then do not write
LEA input(PC),A0 ; Get storing address
MOVE.L D0,(A0) ; Save the file pointer
MOVE.L D0,D1 ; D1 = file pointer
JSR _LVOIsInteractive(A6) ;Check the input file type
TST.L D0 ; If not interactive
BEQ done ; Then do not write
JSR _LVOOutput(A6) ; Get standard output file
CMPI.L #NULL,D0 ; If the file pointer is NULL
BEQ done ; Then do not write
MOVE.L D0,D4 ; Save file pointer in D4
CMPA.L #NULL,A2 ; If the positive text not NULL
BNE may_query ; Query is still possible
CMPA.L #NULL,A3 ; If the negative text not NULL
BNE no_options ; No need to query
CMPA.L #NULL,A4 ; If the body text is also NULL
BEQ done ; Then no text to display
no_options LEA posit(PC),A0 ; Pointer to good option
MOVE.B #0,(A0)+ ; Mark it meaningless
BRA options_set ; Go to display text
may_query CMPA.L #NULL,A3 ; If the negative text not NULL
BNE query ; Then read line
MOVEQ #TRUE,D6 ; Return TRUE
BRA no_options ; No other option
query MOVEQ #0,D7 ; Zero the counters
MOVEA.L A3,A5 ; A5 = negative text
JSR writetext(PC) ; Sort the text
MOVEA.L first(PC),A0 ; Pointer to negative string
MOVE.L A0,-(A7) ; Save the negative pointer
MOVEA.L A2,A5 ; A5 = positive text
JSR writetext(PC) ; Sort the text
MOVEA.L first(PC),A0 ; Pointer to positive string
MOVEA.L (A7)+,A1 ; Restore the negative pointer
MOVE.B (A0),D0 ; First character
JSR check_char ; Check if legal
TST.B D0 ; Was it illegal?
BEQ one_two ; Then ask with numbers
LEA posit(PC),A0 ; Positive option = first char
MOVE.B D0,(A0)+ ; A0 -> negat
MOVE.B (A1),D0 ; First character
JSR check_char ; Check if legal
TST.B D0 ; Was it illegal?
BEQ one_two ; Then ask with numbers
MOVE.B D0,(A0)+ ; Negative option = first char
CMP.B posit(PC),D0 ; Aren't the options identical?
BNE options_set ; Then they are ok.
one_two LEA posit(PC),A0 ; A0 -> positive option
MOVE.B #ONE,(A0)+ ; Positive option = '1'
MOVE.B #TWO,(A0)+ ; Negative option = '2'
options_set JSR linefeed(PC) ; D4 = file pointer
MOVEQ #0,D7 ; Zero the counter
MOVEA.L A4,A5 ; A5 = body text
JSR writetext(PC) ; Measure text
MOVEA.L A4,A5 ; A5 = body text
CMP.W #MAX_COL,D7 ; Is it too long for one line
BHI high_body ; Then use many lines
MOVE.W #ONE_LINE,D7 ; Use one line
BRA write_body ; Go to write it
high_body MOVE.W #WRITING,D7 ; Set write mode
write_body JSR writetext(PC) ; Write body text
CMPI.W #WRITING,D7 ; Is there LF already
BEQ ask_option ; Then don't write an other one
JSR linefeed(PC) ; D4 = file pointer
ask_option SWAP D6 ; Save return value
MOVE.W #OPT_ONE_LINE,D6 ; Set counter starting value
MOVEQ #0,D7 ; Zero the counters
MOVEA.L A3,A5 ; A5 = negative text
JSR writetext(PC) ; Measure text
ADD.W D7,D6 ; Add lenght to counter
CMP.W #MAX_OPT,D7 ; Is it too long for one line
BHI high_negat ; Then use many lines
MOVE.W #ONE_LINE,D7 ; Use one line
BRA normal_negat ; Go to write it
high_negat MOVE.W #WRITING,D7 ; Set write mode
normal_negat SWAP D7 ; Save value
MOVEA.L A2,A5 ; A5 = positive text
JSR writetext(PC) ; Measure text
ADD.W D7,D6 ; Add lenght to counter
CMP.W #MAX_OPT,D7 ; Is it too long for one line
BHI high_posit ; Then use many lines
MOVE.W #ONE_LINE,D7 ; Use one line
BRA normal_posit ; Go to write it
high_posit MOVE.W #WRITING,D7 ; Set write mode
normal_posit MOVEQ #0,D0 ; Get zero
CMP.B posit(PC),D0 ; Is option meaningless
BEQ reply ; Then just wait for RETURN
CMP.W #MAX_COL,D6 ; Are the options too long
BHI too_long ; Then use separate lines
MOVE.W #0,D6 ; Use one line for options
BRA show_options ; Go to show the options
too_long JSR linefeed(PC) ; D4 = file pointer
show_options LEA option(PC),A0 ; Pointer to option
MOVE.B posit(PC),0(A0) ; Option is positive
MOVEQ #OPT_LEN,D3 ; D3 = lenght of write
JSR write_out(PC) ; Write to output
MOVEA.L A2,A5 ; A5 = positive text
JSR writetext(PC) ; Write it out
TST.W D6 ; Aren't we using separate lines?
BEQ write_mid ; Then separate options
CMPI.W #WRITING,D7 ; Is there LF already
BEQ show_negat ; Then don't write an other one
JSR linefeed(PC) ; D4 = file pointer
BRA show_negat ; Go to show the negative option
write_mid LEA mid_part(PC),A0 ; Pointer to option separator
JSR write_two(PC) ; Write it out
show_negat LEA option(PC),A0 ; Pointer option
MOVE.B negat(PC),0(A0) ; Option is negative
MOVEQ #OPT_LEN,D3 ; D3 = lenght of write
JSR write_out(PC) ; Write to output
SWAP D7 ; Restore value
MOVEA.L A3,A5 ; A5 = negative text
JSR writetext(PC) ; Write it out
TST.W D6 ; Aren't we using separate lines?
BEQ right_after ; Then put it right after
CMPI.W #WRITING,D7 ; Is there LF already
BEQ right_after ; Then don't write an other one
JSR linefeed(PC) ; D4 = file pointer
right_after LEA prompt(PC),A0 ; Pointer to prompt
JSR write_two(PC) ; Write lenght of two
BRA wait ; Go to wait answer
reply MOVEA.L A2,A5 ; A5 = positive text
JSR writetext(PC) ; Write it out
SWAP D7 ; Restore value
MOVEA.L A3,A5 ; A5 = negative text
JSR writetext(PC) ; Write it out
LEA hit_ret(PC),A0 ; Pointer to Press RETURN text
MOVE.L #HIT_RET_LEN,D3 ; D3 = lenght of write
jsr write_out(PC) ; Write it out
wait MOVE.L input(PC),D5 ; Restore input file pointer
SWAP D6 ; Restore return value
LEA answer(PC),A0 ; Pointer to answer
MOVE.L D5,D1 ; D1 = pointer to file (input)
MOVE.L A0,D2 ; D2 = pointer to buffer
MOVEQ #1,D3 ; D3 = lenght of read
JSR _LVORead(A6) ; Read a character
MOVEA.L D2,A0 ; Reastore pointer
CMPI.B #LF,(A0) ; Was it end of the line
BEQ empty ; Then stop reading
LEA bucket(PC),A0 ; Pointer to bucket
MOVE.L A0,D2 ; D2 = pointer to buffer
read_next MOVE.L D5,D1 ; D1 = pointer to file (input)
JSR _LVORead(A6) ; Read a character
MOVEA.L D2,A0 ; Reastore pointer
CMPI.B #LF,(A0) ; Wasn't it end of the line
BNE read_next ; Then read next character
empty MOVEQ #0,D0 ; Get zero
CMP.B posit(PC),D0 ; Is the option meaningless
BEQ done ; Then the job is done
MOVE.B answer(PC),D0 ; Pointer to answer
CMPI.B #FIRST_LEGAL,D0 ; Can it be digit
BLT digit ; Then don't modify
ANDI.B #UP_CASE,D0 ; Convert to upper case
digit CMP.B negat(PC),D0 ; Is it negative
BEQ done ; Then go return FALSE
CMP.B posit(PC),D0 ; Isn't it positive
BNE ask_option ; Then go to ask again
MOVEQ #TRUE,D6 ; Return TRUE
done MOVEA.L A6,A1 ; A1 = pointer to library (dos)
MOVEA.L absexecbase,A6 ; Exec-librarys base to use
JSR _LVOCloseLibrary(A6) ; Close dos-library
a_exit MOVEQ #0,D0 ; Zero the long register
MOVE.B D6,D0 ; Boolean return value
MOVEM.L (A7)+,D2-D7/A2-A6 ; Restore registers
RTS ; Return to caller
writetext LEA list(PC),A0 ; Pointer to index list
MOVEA.L A5,A1 ; Pointer to first structure
MOVEQ #0,D5 ; Zero the index counter
count_next CMPA.L #NULL,A1 ; If the IntuiText pointer is NULL
BEQ last ; Then this was the last one
MOVE.B D5,(A0)+ ; Put index to list
ADDQ.B #1,D5 ; Increment the index
CMPI.W #LIST_LEN,D5 ; If the index is too big
BEQ last ; Then this was the last one
MOVEA.L it_NextText(A1),A1 ; Pointer to next IntuiText
BRA count_next ; Next structure
last TST.B D5 ; Was there NULL-pointer
BEQ return ; Then return to caller
MOVE.L D5,D3 ; Initialize outer counter
SUBQ.B #2,D3 ; Adjust the counter
BMI sorted ; Nothing to sort?
outer_loop MOVEQ #0,D2 ; Initialize inner counter
inner_loop LEA list(PC,D2.W),A1 ; Pointer to current index
ADDQ.B #1,D2 ; Increment inner counter
CMP.B D5,D2 ; If counter reached max value
BEQ loop_end ; Then the loop has exhausted
MOVEQ #0,D0 ; Zero the register
MOVE.B (A1)+,D0 ; Get index value
JSR getstruct(PC) ; Get current structure
MOVEQ #0,D0 ; Zero the register
MOVE.B (A1),D0 ; Get next index value
MOVEA.L A0,A1 ; Current structure to A1
JSR getstruct(PC) ; Get next structure
MOVE.W it_TopEdge(A0),D0 ; Get the next top edge
CMP.W it_TopEdge(A1),D0 ; If current < next top edge
BLT inner_loop ; Then don't swap them
BNE swap ; Swap only if not equal
MOVE.W it_LeftEdge(A0),D0 ; Get the next left edge
CMP.W it_LeftEdge(A1),D0 ; If current < next left edge
BLT inner_loop ; Then don't swap them
swap LEA list(PC,D2.W),A0 ; Pointer to next index
MOVE.B (A0),D0 ; Get next index value
SWAP D0 ; Save next index value
MOVE.B -(A0),D0 ; Get current index value
SWAP D0 ; Swap index values
MOVE.B D0,(A0)+ ; Set current index value
SWAP D0 ; Restore next index value
MOVE.B D0,(A0)+ ; Set next index value
BRA inner_loop ; Continue looping
loop_end DBRA D3,outer_loop ; Check if outer loop done
sorted MOVE.L D5,D0 ; Get counter value
SUBQ.B #1,D0 ; Point to last index
MOVE.B list(PC,D0.W),D0 ; Get last index value
JSR getstruct(PC) ; Get last IntuiText structure
LEA first(PC),A1 ; Pointer to saving address
MOVE.L it_IText(A0),(A1)+ ; Save string pointer
BRA check_counter ; Go to write loop
list DS.B LIST_LEN ; Sorttable index list
continue MOVEQ #0,D0 ; Zero the register
MOVE.B list(PC,D5.W),D0 ; Get current index value
JSR getstruct(PC) ; Get current structure
MOVEA.L it_IText(A0),A0 ; Pointer to string
MOVE.L A0,D2 ; D2 = NULL-terminated string
MOVEQ #-1,D3 ; D3 = lenght to be written
strlen ADDQ.L #1,D3 ; Increment lenght
TST.B (A0)+ ; While terminator not found
BNE strlen ; If lenght = 0 then D3 = -1 + 1
CMPI.W #WRITING,D7 ; Are we actually writing this
BGE writing ; Then go to write it
ADD.W D3,D7 ; Add lenght to counter
ADDQ.W #1,D7 ; Add one for space character
BRA check_counter ; Continue measuring
writing JSR write_file(PC) ; Write to output
CMPI.W #ONE_LINE,D7 ; Are we using only one line
BEQ put_space ; Then don't write linefeed
writenext JSR linefeed(PC) ; D4 = file pointer
check_counter DBRA D5,continue ; If counter exhausted
return RTS ; Then return to caller
put_space TST.B D5 ; If counter exhausting
BEQ return ; Then the write is done
LEA space(PC),A0 ; Pointer to space string
MOVEQ #1,D3 ; D3 = lenght of write
JSR write_out(PC) ; Write the space character
BRA sorted ; Continue the line
getstruct MOVEA.L A5,A0 ; Pointer to first structure
BRA dec_counter ; Go to counting loop
next_struct MOVEA.L it_NextText(A0),A0 ; Pointer to next IntuiText
dec_counter DBRA D0,next_struct ; If counter exhausted
RTS ; Then return to caller
linefeed LEA crlf(PC),A0 ; Pointer to line-end string
write_two MOVEQ #2,D3 ; D3 = lenght to be written
write_out MOVE.L A0,D2 ; D2 = string (not terminated)
write_file MOVE.L D4,D1 ; D1 = file pointer
JMP _LVOWrite(A6) ; Write to output
check_char CMPI.B #FIRST_LEGAL,D0 ; Is it less than 'A'
BLT not_a_z ; Then it's not legal
ANDI.B #UP_CASE,D0 ; Convert to upper case
CMPI.B #LAST_LEGAL,D0 ; Is it less or equal to 'Z'
BLE legal ; Then it's legal
not_a_z MOVEQ #0,D0 ; Zero means illegal
legal RTS ; Return to caller
input DC.L 0 ; Pointer to input file
first DC.L 0 ; First IntuiText string
doslibname DOSNAME ; Name of the dos-library
crlf DC.B CR,LF ; End of line characters
prompt DC.B '?' ; Prompt for query
space DC.B ' ' ; Space for separator
mid_part DC.B ', ' ; Option separator
option DC.B 'X = ' ; Option expression
answer DC.B ' ' ; Store for the answer
bucket DC.B ' ' ; Store for the rest ones
posit DC.B 0 ; Positive option
negat DC.B 0 ; Negative option
hit_ret DC.B LF,'Press RETURN to continue! ' ;Dummy query
intuitionname DC.B 'intuition.library',0 ; Name of the intuition-library
END