rewrite vt100 and telnet.
This commit is contained in:
parent
9285503c5f
commit
9cc53483ad
|
@ -0,0 +1,32 @@
|
||||||
|
PROG = fctelnet
|
||||||
|
OBJS = o/fctelnet.a o/vt100.a o/telnet.a o/ansi.a o/chars.a o/marinetti.a o/display.a
|
||||||
|
|
||||||
|
OPTIMIZE ?= 79
|
||||||
|
|
||||||
|
CFLAGS = -w-1 -O $(OPTIMIZE)
|
||||||
|
CC = occ --gno
|
||||||
|
|
||||||
|
$(PROG): $(OBJS)
|
||||||
|
$(RM) o/ansi.root
|
||||||
|
$(RM) o/chars.root
|
||||||
|
$(CC) $(OBJS) -o $@
|
||||||
|
|
||||||
|
|
||||||
|
fctelnet.o: fctelnet.c marinetti.h
|
||||||
|
vt100.o: vt100.c CLAGS+=-r
|
||||||
|
ansi.o: ansi.asm
|
||||||
|
chars.o: chars.asm
|
||||||
|
marinetti.o: marinetti.c CLAGS+=-r
|
||||||
|
telnet.o: telnet.c CLAGS+=-r
|
||||||
|
|
||||||
|
o/%.a : %.c
|
||||||
|
$(CC) -c $(CFLAGS) -o $@ $^
|
||||||
|
|
||||||
|
o/%.a : %.asm
|
||||||
|
$(CC) -c $(CFLAGS) -o $@ $^
|
||||||
|
|
||||||
|
|
||||||
|
clean:
|
||||||
|
$(RM) -f *.o *.root *.a *.r
|
||||||
|
clobber: clean
|
||||||
|
$(RM) -f $(PROG)
|
661
ansi.asm
661
ansi.asm
|
@ -3,6 +3,46 @@
|
||||||
dummy start
|
dummy start
|
||||||
end
|
end
|
||||||
|
|
||||||
|
tables privdata
|
||||||
|
|
||||||
|
;
|
||||||
|
; each line is 160 pixels.
|
||||||
|
; top/bottom margin is 4 lines (4*160 pixels)
|
||||||
|
|
||||||
|
rows anop
|
||||||
|
dc i2'0*8*160+4*160+$2000'
|
||||||
|
dc i2'1*8*160+4*160+$2000'
|
||||||
|
dc i2'2*8*160+4*160+$2000'
|
||||||
|
dc i2'3*8*160+4*160+$2000'
|
||||||
|
dc i2'4*8*160+4*160+$2000'
|
||||||
|
dc i2'5*8*160+4*160+$2000'
|
||||||
|
dc i2'6*8*160+4*160+$2000'
|
||||||
|
dc i2'7*8*160+4*160+$2000'
|
||||||
|
dc i2'8*8*160+4*160+$2000'
|
||||||
|
dc i2'9*8*160+4*160+$2000'
|
||||||
|
dc i2'10*8*160+4*160+$2000'
|
||||||
|
dc i2'11*8*160+4*160+$2000'
|
||||||
|
dc i2'12*8*160+4*160+$2000'
|
||||||
|
dc i2'13*8*160+4*160+$2000'
|
||||||
|
dc i2'14*8*160+4*160+$2000'
|
||||||
|
dc i2'15*8*160+4*160+$2000'
|
||||||
|
dc i2'16*8*160+4*160+$2000'
|
||||||
|
dc i2'17*8*160+4*160+$2000'
|
||||||
|
dc i2'18*8*160+4*160+$2000'
|
||||||
|
dc i2'19*8*160+4*160+$2000'
|
||||||
|
dc i2'20*8*160+4*160+$2000'
|
||||||
|
dc i2'21*8*160+4*160+$2000'
|
||||||
|
dc i2'22*8*160+4*160+$2000'
|
||||||
|
dc i2'23*8*160+4*160+$2000'
|
||||||
|
dc i2'24*8*160+4*160+$2000'
|
||||||
|
|
||||||
|
;
|
||||||
|
; columns are simply x * 2
|
||||||
|
;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
end
|
||||||
;
|
;
|
||||||
;ReverseScrollRegion(line1, line2)
|
;ReverseScrollRegion(line1, line2)
|
||||||
;
|
;
|
||||||
|
@ -12,6 +52,8 @@ line1 equ 7
|
||||||
_rtlb equ 3
|
_rtlb equ 3
|
||||||
_d equ 1
|
_d equ 1
|
||||||
|
|
||||||
|
using tables
|
||||||
|
|
||||||
; brk $ea
|
; brk $ea
|
||||||
|
|
||||||
phb
|
phb
|
||||||
|
@ -20,36 +62,28 @@ _d equ 1
|
||||||
tcd
|
tcd
|
||||||
|
|
||||||
lda <line1
|
lda <line1
|
||||||
cmp #0
|
bmi exit
|
||||||
bcc exit
|
|
||||||
|
|
||||||
lda <line2
|
lda <line2
|
||||||
cmp #24
|
cmp #25
|
||||||
bcs exit
|
bcs exit
|
||||||
|
|
||||||
lda <line1
|
lda <line1
|
||||||
cmp <line2
|
cmp <line2
|
||||||
bcs exit
|
bcs exit
|
||||||
|
|
||||||
; a = (line2 - line1) * 8 * 160 - 1
|
asl line1
|
||||||
|
asl line2
|
||||||
|
|
||||||
lda <line2
|
; count = (line2 - line1) * 8 * 160 - 1
|
||||||
sec
|
|
||||||
sbc <line1
|
|
||||||
; a = a * 256 * 5
|
|
||||||
xba ; a = a * 256
|
|
||||||
; 5x = 4x + x
|
|
||||||
|
|
||||||
pha ; save
|
ldx <line2
|
||||||
asl a ; x2
|
lda >rows,x
|
||||||
asl a ; x4
|
clc ; dec a
|
||||||
clc
|
ldx <line1
|
||||||
adc 1,s
|
sbc >rows,x
|
||||||
sta 1,s
|
pha
|
||||||
pla
|
|
||||||
dec a ; a = a - 1
|
|
||||||
|
|
||||||
pha ; save
|
|
||||||
|
|
||||||
;
|
;
|
||||||
; mvn:
|
; mvn:
|
||||||
|
@ -66,21 +100,14 @@ _d equ 1
|
||||||
; x = src address = dest - 160*8
|
; x = src address = dest - 160*8
|
||||||
|
|
||||||
|
|
||||||
lda <line2
|
ldx <line2
|
||||||
inc a
|
lda >rows,x
|
||||||
xba ; x256
|
dec a
|
||||||
pha ; save
|
tay
|
||||||
asl a ; x 2
|
|
||||||
asl a ; x 4
|
|
||||||
clc
|
|
||||||
adc #$2000+4*160
|
|
||||||
adc 1,s
|
|
||||||
dec a ; - 1
|
|
||||||
sta 1,s ;store it...
|
|
||||||
sec
|
sec
|
||||||
sbc #1280
|
sbc #160*8
|
||||||
tax ; src address
|
tax
|
||||||
ply ; dest address
|
|
||||||
pla ; length
|
pla ; length
|
||||||
|
|
||||||
mvp $e10000,$e10000
|
mvp $e10000,$e10000
|
||||||
|
@ -88,8 +115,8 @@ _d equ 1
|
||||||
;
|
;
|
||||||
; now empty first line
|
; now empty first line
|
||||||
;
|
;
|
||||||
pei (line1)
|
ldx <line1
|
||||||
jsl ClearLine
|
jsr _ClearLine
|
||||||
|
|
||||||
exit anop
|
exit anop
|
||||||
|
|
||||||
|
@ -113,6 +140,8 @@ exit anop
|
||||||
;
|
;
|
||||||
ScrollRegion START
|
ScrollRegion START
|
||||||
|
|
||||||
|
using tables
|
||||||
|
|
||||||
line2 equ 9
|
line2 equ 9
|
||||||
line1 equ 7
|
line1 equ 7
|
||||||
_rtlb equ 3
|
_rtlb equ 3
|
||||||
|
@ -126,36 +155,28 @@ _d equ 1
|
||||||
tcd
|
tcd
|
||||||
|
|
||||||
lda <line1
|
lda <line1
|
||||||
cmp #0
|
bmi exit
|
||||||
bcc exit
|
|
||||||
|
|
||||||
lda <line2
|
lda <line2
|
||||||
cmp #24
|
cmp #25
|
||||||
bcs exit
|
bcs exit
|
||||||
|
|
||||||
lda <line1
|
lda <line1
|
||||||
cmp <line2
|
cmp <line2
|
||||||
bcs exit
|
bcs exit
|
||||||
|
|
||||||
|
asl line1
|
||||||
|
asl line2
|
||||||
|
|
||||||
; a = (line2 - line1) * 8 * 160 - 1
|
; a = (line2 - line1) * 8 * 160 - 1
|
||||||
|
|
||||||
lda <line2
|
ldx <line2
|
||||||
sec
|
lda >rows,x
|
||||||
sbc <line1
|
clc ; dec a
|
||||||
; a = a * 256 * 5
|
ldx <line1
|
||||||
xba ; a = a * 256
|
sbc >rows,x
|
||||||
; 5x = 4x + x
|
pha
|
||||||
|
|
||||||
pha ; save
|
|
||||||
asl a ; x2
|
|
||||||
asl a ; x4
|
|
||||||
clc
|
|
||||||
adc 1,s
|
|
||||||
sta 1,s
|
|
||||||
pla
|
|
||||||
dec a ; a = a - 1
|
|
||||||
|
|
||||||
pha ; save
|
|
||||||
|
|
||||||
; src address = $2000 + line1
|
; src address = $2000 + line1
|
||||||
|
|
||||||
|
@ -166,18 +187,13 @@ _d equ 1
|
||||||
; dest = $2000 + 640 + line1 * 8 * 160
|
; dest = $2000 + 640 + line1 * 8 * 160
|
||||||
; src = dest + 1280
|
; src = dest + 1280
|
||||||
|
|
||||||
lda <line1
|
ldx <line1
|
||||||
xba ; x256
|
lda >rows,x
|
||||||
pha ; save
|
tay
|
||||||
asl a ; x 2
|
|
||||||
asl a ; x 4
|
|
||||||
clc
|
clc
|
||||||
adc #$2000+4*160
|
adc #8*160
|
||||||
adc 1,s
|
tax
|
||||||
sta 1,s ;store it...
|
|
||||||
adc #1280
|
|
||||||
tax ; src address
|
|
||||||
ply ; dest address
|
|
||||||
pla ; length
|
pla ; length
|
||||||
|
|
||||||
mvn $e10000,$e10000
|
mvn $e10000,$e10000
|
||||||
|
@ -185,8 +201,10 @@ _d equ 1
|
||||||
;
|
;
|
||||||
; now empty last line
|
; now empty last line
|
||||||
;
|
;
|
||||||
pei (line2)
|
ldx line2
|
||||||
jsl ClearLine
|
dex
|
||||||
|
dex
|
||||||
|
jsr _ClearLine
|
||||||
|
|
||||||
exit anop
|
exit anop
|
||||||
|
|
||||||
|
@ -210,6 +228,8 @@ exit anop
|
||||||
;
|
;
|
||||||
ScrollDown START
|
ScrollDown START
|
||||||
|
|
||||||
|
using tables
|
||||||
|
|
||||||
phb
|
phb
|
||||||
;
|
;
|
||||||
; mvn:
|
; mvn:
|
||||||
|
@ -232,8 +252,8 @@ ScrollDown START
|
||||||
;
|
;
|
||||||
; now empty outline #24
|
; now empty outline #24
|
||||||
;
|
;
|
||||||
pea 23
|
ldx #23
|
||||||
jsl ClearLine
|
jsr _ClearLine
|
||||||
|
|
||||||
|
|
||||||
plb
|
plb
|
||||||
|
@ -241,54 +261,50 @@ ScrollDown START
|
||||||
|
|
||||||
END
|
END
|
||||||
|
|
||||||
|
|
||||||
|
; clear line in X (which has been pre-multiplied)
|
||||||
|
_ClearLine PRIVATE
|
||||||
|
|
||||||
|
using tables
|
||||||
|
|
||||||
|
lda >rows,x
|
||||||
|
tax
|
||||||
|
lda #0
|
||||||
|
sta >$e10000,x ; stick a 0 in there
|
||||||
|
txy ; destination address (src + 2)
|
||||||
|
iny
|
||||||
|
iny
|
||||||
|
|
||||||
|
lda #8*160-3 ; length -1
|
||||||
|
mvn $e10000,$e10000
|
||||||
|
rts
|
||||||
|
END
|
||||||
;
|
;
|
||||||
; ClearLine(int line_no); clears the line
|
; ClearLine(int line_no); clears the line
|
||||||
;
|
;
|
||||||
ClearLine START
|
ClearLine START
|
||||||
|
|
||||||
line equ 9
|
line equ 7
|
||||||
_rtlb equ 5
|
_rtlb equ 3
|
||||||
tmp equ 3
|
|
||||||
_d equ 1
|
_d equ 1
|
||||||
|
|
||||||
|
|
||||||
; brk $ea
|
; brk $ea
|
||||||
phb
|
phb
|
||||||
pha
|
|
||||||
|
|
||||||
phd
|
phd
|
||||||
tsc
|
tsc
|
||||||
tcd
|
tcd
|
||||||
|
|
||||||
; line * 8 * 160 + 4*160
|
|
||||||
; = line * 1024 + line * 256 + 4*160
|
|
||||||
lda <line
|
lda <line
|
||||||
|
cmp #24
|
||||||
|
bcs exit
|
||||||
|
|
||||||
and #$00ff
|
asl a
|
||||||
xba ; x256
|
|
||||||
sta <tmp
|
|
||||||
asl a ; x 512
|
|
||||||
asl a ; x 1024
|
|
||||||
clc
|
|
||||||
adc <tmp
|
|
||||||
sta <tmp
|
|
||||||
|
|
||||||
clc
|
|
||||||
adc #4*160
|
|
||||||
sta <tmp
|
|
||||||
clc
|
|
||||||
adc #$2000 ; graphics begin @ $e12000
|
|
||||||
|
|
||||||
tax
|
tax
|
||||||
lda #0
|
jsr _ClearLine
|
||||||
sta >$e10000,x ; stick a 0 in there
|
|
||||||
txy ; destination address (src + 2)
|
|
||||||
iny
|
|
||||||
iny
|
|
||||||
|
|
||||||
|
exit anop
|
||||||
lda #8*160-3 ; length -1
|
|
||||||
mvn $e10000,$e10000
|
|
||||||
|
|
||||||
lda <_rtlb+2
|
lda <_rtlb+2
|
||||||
sta <_rtlb+4
|
sta <_rtlb+4
|
||||||
|
@ -297,74 +313,76 @@ _d equ 1
|
||||||
|
|
||||||
pld
|
pld
|
||||||
pla
|
pla
|
||||||
pla
|
|
||||||
plb
|
plb
|
||||||
rtl
|
rtl
|
||||||
|
|
||||||
END
|
END
|
||||||
|
|
||||||
|
|
||||||
;extern void ClearScreenFrom(int Y);
|
|
||||||
;
|
;
|
||||||
|
; ClearScreen2(int start, int end);
|
||||||
;
|
;
|
||||||
;
|
ClearScreen2 START
|
||||||
ClearScreenFrom START
|
|
||||||
|
|
||||||
Y equ 9
|
using tables
|
||||||
_rtlb equ 5
|
|
||||||
tmp equ 3
|
line2 equ 9
|
||||||
|
line1 equ 7
|
||||||
|
_rtlb equ 3
|
||||||
_d equ 1
|
_d equ 1
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
; brk $ea
|
; brk $ea
|
||||||
phb
|
phb
|
||||||
pha
|
|
||||||
|
|
||||||
phd
|
phd
|
||||||
tsc
|
tsc
|
||||||
tcd
|
tcd
|
||||||
|
|
||||||
; line * 8 * 160 + 4*160
|
lda <line1
|
||||||
; = line * 1024 + line * 256 + 4*160
|
bmi exit
|
||||||
lda <Y
|
|
||||||
|
|
||||||
and #$00ff
|
lda line2
|
||||||
xba ; x256
|
cmp #25
|
||||||
sta <tmp
|
bcs exit
|
||||||
asl a ; x 512
|
|
||||||
asl a ; x 1024
|
|
||||||
clc
|
|
||||||
adc <tmp
|
|
||||||
sta <tmp
|
|
||||||
|
|
||||||
clc
|
lda <line1
|
||||||
adc #4*160
|
cmp <line2
|
||||||
sta <tmp
|
bcs exit
|
||||||
clc
|
|
||||||
adc #$2000 ; graphics begin @ $e12000
|
|
||||||
|
|
||||||
|
asl line1
|
||||||
|
asl line2
|
||||||
|
|
||||||
|
ldx <line2
|
||||||
|
lda >rows,x
|
||||||
|
clc
|
||||||
|
ldx <line1
|
||||||
|
sbc >rows,x
|
||||||
|
dec a
|
||||||
|
dec a
|
||||||
|
pha ; save length
|
||||||
|
|
||||||
|
|
||||||
|
ldx <line2
|
||||||
|
lda >rows,x
|
||||||
tax
|
tax
|
||||||
|
tay
|
||||||
|
iny
|
||||||
|
iny
|
||||||
|
|
||||||
lda #0
|
lda #0
|
||||||
sta >$e10000,x ; stick a 0 in there
|
sta >$e1000,x
|
||||||
txy ; destination address (src + 2)
|
pla ; restore length
|
||||||
iny
|
|
||||||
iny
|
|
||||||
|
|
||||||
|
|
||||||
phy
|
|
||||||
lda #$9d00-2 ; end of graphics + $2000
|
|
||||||
sec
|
|
||||||
sbc 1,s
|
|
||||||
ply
|
|
||||||
|
|
||||||
; a now equals length to clear
|
|
||||||
|
|
||||||
mvn $e10000,$e10000
|
mvn $e10000,$e10000
|
||||||
|
|
||||||
|
|
||||||
|
exit anop
|
||||||
lda <_rtlb+2
|
lda <_rtlb+2
|
||||||
sta <_rtlb+4
|
sta <line2
|
||||||
lda <_rtlb
|
lda <_rtlb
|
||||||
sta <_rtlb+2
|
sta <line1
|
||||||
|
|
||||||
pld
|
pld
|
||||||
pla
|
pla
|
||||||
|
@ -375,22 +393,23 @@ _d equ 1
|
||||||
END
|
END
|
||||||
|
|
||||||
;
|
;
|
||||||
;extern void ClearLineFrom(int Y, int X);
|
; ClearLine2(int line, int start, int end);
|
||||||
;
|
;
|
||||||
|
|
||||||
;
|
;
|
||||||
; clear the end of the line from a given x & y
|
; clear a section of a given line.
|
||||||
;
|
;
|
||||||
ClearLineFrom START
|
ClearLine2 START
|
||||||
|
|
||||||
X equ 11
|
using tables
|
||||||
Y equ 9
|
|
||||||
_rtlb equ 5
|
end equ 11
|
||||||
tmp equ 3
|
start equ 9
|
||||||
|
line equ 7
|
||||||
|
_rtlb equ 3
|
||||||
_d equ 1
|
_d equ 1
|
||||||
|
|
||||||
phb
|
phb
|
||||||
pha
|
|
||||||
phd
|
phd
|
||||||
tsc
|
tsc
|
||||||
tcd
|
tcd
|
||||||
|
@ -400,62 +419,62 @@ _d equ 1
|
||||||
plb
|
plb
|
||||||
|
|
||||||
|
|
||||||
;
|
lda start
|
||||||
; if X is >= 80, skip it...
|
|
||||||
;
|
|
||||||
lda <X
|
|
||||||
cmp #80
|
|
||||||
bcs exit
|
|
||||||
|
|
||||||
lda <Y
|
|
||||||
and #$00ff
|
|
||||||
xba ; x 256
|
|
||||||
sta <tmp
|
|
||||||
asl a ; x 512
|
|
||||||
asl a ; x 1024
|
|
||||||
clc
|
|
||||||
adc <tmp ; Y * 8 * 160
|
|
||||||
clc
|
|
||||||
adc #160*4
|
|
||||||
sta <tmp
|
|
||||||
|
|
||||||
; each char takes up 2 bytes
|
|
||||||
lda <X
|
|
||||||
asl a ; x 2
|
|
||||||
clc
|
|
||||||
adc <tmp
|
|
||||||
sta <tmp
|
|
||||||
|
|
||||||
tax
|
|
||||||
|
|
||||||
lda #80
|
|
||||||
sec
|
|
||||||
sbc <X
|
|
||||||
loop anop
|
|
||||||
|
|
||||||
dec a
|
|
||||||
bmi exit
|
bmi exit
|
||||||
|
|
||||||
stz $2000,x
|
lda end
|
||||||
stz $2000+160,x
|
cmp #81
|
||||||
stz $2000+320,x
|
bcs exit
|
||||||
stz $2000+480,x
|
|
||||||
stz $2000+640,x
|
lda start
|
||||||
stz $2000+800,x
|
cmp end
|
||||||
stz $2000+960,x
|
bcs exit
|
||||||
stz $2000+1120,x
|
|
||||||
|
sec
|
||||||
|
lda end
|
||||||
|
sbc start
|
||||||
|
; bmi exit
|
||||||
|
; beq exit
|
||||||
|
tay ; counter
|
||||||
|
|
||||||
|
asl start ; x 2
|
||||||
|
asl line
|
||||||
|
|
||||||
|
ldx <line
|
||||||
|
lda >rows,x
|
||||||
|
|
||||||
|
clc
|
||||||
|
adc start
|
||||||
|
tax
|
||||||
|
|
||||||
|
|
||||||
|
loop anop
|
||||||
|
|
||||||
|
stz |0,x
|
||||||
|
stz |160,x
|
||||||
|
stz |320,x
|
||||||
|
stz |480,x
|
||||||
|
stz |640,x
|
||||||
|
stz |800,x
|
||||||
|
stz |960,x
|
||||||
|
stz |1120,x
|
||||||
inx
|
inx
|
||||||
inx
|
inx
|
||||||
bra loop
|
dey
|
||||||
|
bne loop
|
||||||
|
|
||||||
exit anop
|
exit anop
|
||||||
|
|
||||||
|
lda <_rtlb+2
|
||||||
|
sta <end
|
||||||
|
lda <_rtlb
|
||||||
|
sta <start
|
||||||
|
|
||||||
pld
|
pld
|
||||||
pla
|
pla
|
||||||
pla
|
pla
|
||||||
sta 3,s
|
|
||||||
pla
|
pla
|
||||||
sta 3,s
|
|
||||||
plb
|
plb
|
||||||
rtl
|
rtl
|
||||||
END
|
END
|
||||||
|
@ -533,242 +552,214 @@ ClearScreen START
|
||||||
plb
|
plb
|
||||||
plb
|
plb
|
||||||
lda #0
|
lda #0
|
||||||
ldy #0
|
ldy #32000
|
||||||
loop anop
|
loop anop
|
||||||
sta $2000,y
|
sta |$2000-2,y
|
||||||
iny
|
dey
|
||||||
iny
|
dey
|
||||||
cpy #32000
|
bne loop
|
||||||
bcc loop
|
|
||||||
plb
|
plb
|
||||||
rtl
|
rtl
|
||||||
|
|
||||||
;
|
|
||||||
; this will, in 1 atomic action, blast the screen with 0
|
|
||||||
;
|
|
||||||
|
|
||||||
phb
|
|
||||||
lda #0
|
|
||||||
sta >$e12000
|
|
||||||
lda #32000-3 ;length
|
|
||||||
ldx #$2000
|
|
||||||
ldy #$2002
|
|
||||||
mvn $e10000,$e10000
|
|
||||||
|
|
||||||
plb
|
|
||||||
rtl
|
|
||||||
END
|
END
|
||||||
;
|
;
|
||||||
; draw a character at the current Xpos & Ypos
|
; draw a character at the current Xpos & Ypos
|
||||||
;
|
;
|
||||||
;
|
;
|
||||||
|
; PrintChar(x, y, char, andMask, xorMask)
|
||||||
PrintChar START
|
PrintChar START
|
||||||
|
|
||||||
andMask equ 11
|
using tables
|
||||||
char equ 9
|
|
||||||
_rtlb equ 5
|
xorMask equ 15
|
||||||
pos equ 3
|
andMask equ 13
|
||||||
|
char equ 11
|
||||||
|
yy equ 9
|
||||||
|
xx equ 7
|
||||||
|
_rtlb equ 3
|
||||||
_d equ 1
|
_d equ 1
|
||||||
|
|
||||||
; brk $ea
|
; brk $ea
|
||||||
phb
|
phb
|
||||||
pha
|
|
||||||
|
|
||||||
phd
|
phd
|
||||||
tsc
|
tsc
|
||||||
tcd
|
tcd
|
||||||
|
|
||||||
; sanity check on Xpos && Ypos
|
; sanity check on Xpos && Ypos
|
||||||
lda Xpos
|
|
||||||
cmp #80
|
|
||||||
bcc _ok
|
|
||||||
lda Ypos
|
|
||||||
cmp #24
|
|
||||||
bcc _ok
|
|
||||||
brl exit
|
|
||||||
_ok anop
|
|
||||||
|
|
||||||
|
ldx xx
|
||||||
|
cpx #80
|
||||||
|
bcc ok2
|
||||||
|
|
||||||
|
exit2 anop
|
||||||
|
brl exit
|
||||||
|
|
||||||
|
ok2 anop
|
||||||
|
ldy yy
|
||||||
|
cpy #24
|
||||||
|
bcs exit2
|
||||||
|
|
||||||
|
lda <char
|
||||||
|
cmp #$7f
|
||||||
|
bcs space
|
||||||
|
sec
|
||||||
|
sbc #$20
|
||||||
|
bmi space
|
||||||
|
asl a ; x2
|
||||||
|
asl a ; x4
|
||||||
|
asl a ; x8
|
||||||
|
asl a ; x16
|
||||||
|
sta char
|
||||||
|
bra ok
|
||||||
|
|
||||||
|
|
||||||
|
space anop
|
||||||
|
stz <char
|
||||||
|
|
||||||
|
ok anop
|
||||||
|
|
||||||
pea $e1e1
|
pea $e1e1
|
||||||
plb
|
plb
|
||||||
plb
|
plb
|
||||||
|
|
||||||
;
|
asl xx
|
||||||
; each line has a width of 160 pixels
|
asl yy
|
||||||
;
|
|
||||||
; start drawing the letter at $e12000 + (Ypos x 160 x 8) + Xpos
|
|
||||||
|
|
||||||
|
ldx yy
|
||||||
; 160 * 8 = 1240 = 1024 + 256
|
lda >rows,x
|
||||||
lda >Ypos
|
|
||||||
and #$00ff
|
|
||||||
xba ; x 256
|
|
||||||
sta <pos ; store temporarily
|
|
||||||
|
|
||||||
asl a ; x 512
|
|
||||||
asl a ; x 1024
|
|
||||||
clc
|
clc
|
||||||
adc <pos
|
adc xx
|
||||||
sta <pos
|
|
||||||
|
|
||||||
;
|
|
||||||
; lower 1/2 row additional
|
|
||||||
;
|
|
||||||
clc
|
|
||||||
adc #160*4
|
|
||||||
sta <pos
|
|
||||||
|
|
||||||
;
|
|
||||||
; for x offset, 160 bytes per row / 80 chars = 2 bytes/letter
|
|
||||||
;
|
|
||||||
lda >Xpos
|
|
||||||
asl a ; x 2
|
|
||||||
clc
|
|
||||||
adc <pos
|
|
||||||
sta <pos
|
|
||||||
tay
|
tay
|
||||||
|
|
||||||
|
|
||||||
;
|
;
|
||||||
; $e12000 + pos = location to start drawing the character
|
; $e12000 + pos = location to start drawing the character
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
||||||
lda <char
|
|
||||||
|
|
||||||
cmp #$20 ; smallest printing char
|
|
||||||
bcc exit ; not printable....
|
|
||||||
cmp #127 ; 126 is biggest
|
|
||||||
bcs exit ; not printable
|
|
||||||
|
|
||||||
;
|
;
|
||||||
; each char takes up 16 bytes :. the offset is (char - $20) * 16
|
; each char takes up 16 bytes :. the offset is (char - $20) * 16
|
||||||
;
|
;
|
||||||
|
|
||||||
sec
|
ldx char
|
||||||
sbc #$20
|
|
||||||
asl a ; x2
|
|
||||||
asl a ; x4
|
|
||||||
asl a ; x8
|
|
||||||
asl a ; x16
|
|
||||||
|
|
||||||
tax
|
|
||||||
lda >CHAR_SPACE,x
|
lda >CHAR_SPACE,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000,y ; blast it to the screen
|
sta |0,y ; blast it to the screen
|
||||||
|
|
||||||
lda >CHAR_SPACE+2,x
|
lda >CHAR_SPACE+2,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+160,y
|
sta |160,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+4,x
|
lda >CHAR_SPACE+4,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+320,y
|
sta |320,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+6,x
|
lda >CHAR_SPACE+6,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+480,y
|
sta |480,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+8,x
|
lda >CHAR_SPACE+8,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+640,y
|
sta |640,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+10,x
|
lda >CHAR_SPACE+10,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+800,y
|
sta |800,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+12,x
|
lda >CHAR_SPACE+12,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+960,y
|
sta |960,y
|
||||||
|
|
||||||
lda >CHAR_SPACE+14,x
|
lda >CHAR_SPACE+14,x
|
||||||
eor >xor_mask
|
eor <xorMask
|
||||||
and <andMask
|
and <andMask
|
||||||
sta |$2000+1120,y
|
sta |1120,y
|
||||||
|
|
||||||
exit anop
|
exit anop
|
||||||
|
|
||||||
lda <_rtlb+2
|
lda <_rtlb+2
|
||||||
sta <andMask
|
sta <xorMask
|
||||||
lda <_rtlb
|
lda <_rtlb
|
||||||
sta <char
|
sta <andMask
|
||||||
pld
|
pld
|
||||||
pla
|
pla
|
||||||
pla
|
pla
|
||||||
pla
|
pla
|
||||||
|
pla
|
||||||
|
pla
|
||||||
plb
|
plb
|
||||||
rtl
|
rtl
|
||||||
end
|
end
|
||||||
|
|
||||||
Cursor START
|
;Cursor START
|
||||||
|
|
||||||
StartCursor ENTRY
|
;StartCursor ENTRY
|
||||||
|
|
||||||
pha
|
; pha
|
||||||
; ~ReadBParam #$2f
|
;; ~ReadBParam #$2f
|
||||||
pla
|
; pla
|
||||||
sta blinkRate
|
; sta blinkRate
|
||||||
|
|
||||||
stz savedX
|
; stz savedX
|
||||||
stz savedY
|
; stz savedY
|
||||||
|
|
||||||
; ~SetHeartBeat #CursorHB
|
;; ~SetHeartBeat #CursorHB
|
||||||
rtl
|
; rtl
|
||||||
|
|
||||||
|
|
||||||
StopCursor ENTRY
|
;StopCursor ENTRY
|
||||||
; ~DelHeartBeat #CursorHB
|
;; ~DelHeartBeat #CursorHB
|
||||||
rtl
|
; rtl
|
||||||
|
|
||||||
notSafe ENTRY
|
;notSafe ENTRY
|
||||||
ds 2
|
; ds 2
|
||||||
blinkRate ds 2
|
;blinkRate ds 2
|
||||||
savedX ds 2
|
;savedX ds 2
|
||||||
savedY ds 2
|
;savedY ds 2
|
||||||
|
|
||||||
CursorHB anop
|
;CursorHB anop
|
||||||
dc i4'0'
|
; dc i4'0'
|
||||||
count dc i2'30'
|
;count dc i2'30'
|
||||||
dc h'5AA5'
|
; dc h'5AA5'
|
||||||
|
|
||||||
longa off
|
; longa off
|
||||||
|
|
||||||
phb
|
; phb
|
||||||
phk
|
; phk
|
||||||
plb
|
; plb
|
||||||
php
|
; php
|
||||||
|
|
||||||
; long ai
|
;; long ai
|
||||||
lda notSafe
|
; lda notSafe
|
||||||
bne exit
|
; bne exit
|
||||||
|
|
||||||
lda Xpos
|
; lda Xpos
|
||||||
cmp savedX
|
; cmp savedX
|
||||||
bne moved
|
; bne moved
|
||||||
lda Ypos
|
; lda Ypos
|
||||||
cmp savedY
|
; cmp savedY
|
||||||
bne moved
|
; bne moved
|
||||||
bra exit
|
; bra exit
|
||||||
|
|
||||||
moved jsr drawCursor
|
;moved jsr drawCursor
|
||||||
|
|
||||||
|
|
||||||
exit anop
|
;exit anop
|
||||||
|
|
||||||
plp
|
; plp
|
||||||
plb
|
; plb
|
||||||
clc
|
; clc
|
||||||
rtl
|
; rtl
|
||||||
|
|
||||||
drawCursor anop
|
;drawCursor anop
|
||||||
|
|
||||||
rts
|
; rts
|
||||||
|
|
||||||
END
|
; END
|
||||||
|
|
384
display.c
384
display.c
|
@ -1,54 +1,21 @@
|
||||||
#pragma noroot
|
#pragma noroot
|
||||||
#pragma lint -1
|
|
||||||
|
|
||||||
#include <types.h>
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <ctype.h>
|
|
||||||
#include <Event.h>
|
|
||||||
#include "Marinetti.h"
|
#include "Marinetti.h"
|
||||||
|
|
||||||
#define ESC "\x1b"
|
|
||||||
|
|
||||||
extern void ScrollRegion(word,word);
|
struct errlist {
|
||||||
extern void ScrollDown(void);
|
|
||||||
extern void PrintChar(int the_char, unsigned int andMask);
|
|
||||||
extern void ClearScreen(void);
|
|
||||||
extern void ClearScreenFrom(int Y);
|
|
||||||
extern void ClearLine(int Y);
|
|
||||||
extern void ClearLineFrom(int Y, int X);
|
|
||||||
|
|
||||||
void handle_ansi(word code, char *buffer, word cnt);
|
|
||||||
|
|
||||||
extern void GrafOn(void) inline(0x0a04, 0xe10000);
|
|
||||||
extern void GrafOff(void) inline(0x0b04, 0xe10000);
|
|
||||||
extern pascal void SetColorTable(Word, ColorTable) inline(0x0E04,dispatcher);
|
|
||||||
extern pascal void SysBeep2(Word) inline(0x3803,dispatcher);
|
|
||||||
extern pascal void SetAllSCBs(Word) inline(0x1404,dispatcher);
|
|
||||||
extern pascal void SetMasterSCB(Word) inline(0x1604,dispatcher);
|
|
||||||
extern pascal void InitColorTable(ColorTable) inline(0x0D04,dispatcher);
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
extern word Xpos;
|
|
||||||
extern word Ypos;
|
|
||||||
extern word __scroll[2];
|
|
||||||
extern word and_mask;
|
|
||||||
extern word xor_mask;
|
|
||||||
|
|
||||||
word esc;
|
|
||||||
char esc_buffer[256];
|
|
||||||
|
|
||||||
struct errlist
|
|
||||||
{
|
|
||||||
Word Error;
|
Word Error;
|
||||||
Word MsgLen;
|
Word MsgLen;
|
||||||
const char *Msg;
|
const char *Msg;
|
||||||
};
|
};
|
||||||
|
|
||||||
#define _ERR(n,msg) { n, sizeof(msg), msg }
|
#define ESC "\x1b"
|
||||||
|
#define _ERR(n,msg) { n, sizeof(msg) - 1, msg }
|
||||||
|
|
||||||
struct errlist errors[] =
|
extern void vt100_process(const unsigned char *buffer, unsigned buffer_size);
|
||||||
{
|
|
||||||
|
static struct errlist errors[] = {
|
||||||
_ERR(1,"tcperrDeafDestPort"),
|
_ERR(1,"tcperrDeafDestPort"),
|
||||||
_ERR(2,"tcperrHostReset"),
|
_ERR(2,"tcperrHostReset"),
|
||||||
_ERR(3,"tcperrConExists"),
|
_ERR(3,"tcperrConExists"),
|
||||||
|
@ -63,346 +30,27 @@ struct errlist errors[] =
|
||||||
_ERR(0x0c,"tcperrConReset"),
|
_ERR(0x0c,"tcperrConReset"),
|
||||||
_ERR(0x0d,"tcperrUserTimeout"),
|
_ERR(0x0d,"tcperrUserTimeout"),
|
||||||
_ERR(0x0e,"tcperrConRefused"),
|
_ERR(0x0e,"tcperrConRefused"),
|
||||||
|
|
||||||
{0,0,NULL}
|
|
||||||
};
|
};
|
||||||
void display_str(const char *buffer, word cnt);
|
|
||||||
|
|
||||||
void display_err(Word err)
|
void display_err(Word err) {
|
||||||
{
|
|
||||||
struct errlist *l;
|
|
||||||
|
|
||||||
for (l = &errors[0]; l->Error; l++)
|
if (err == 0 || err >= 0x0f) return;
|
||||||
if (l->Error == err) break;
|
--err;
|
||||||
if (l->Error != err) return;
|
vt100_process("\r\n" ESC "[1m", 6); // bold on
|
||||||
|
vt100_process(errors[err].Msg, errors[err].MsgLen);
|
||||||
display_str("\r\n" "\x1b" "[1m", 6); // bold on
|
vt100_process(ESC "[0m", 4); // bold off
|
||||||
display_str(l->Msg, l->MsgLen); // show the string
|
|
||||||
display_str("\x1b" "[0m", 4); // bold off
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void display_cstr(const char *cstr)
|
void display_cstr(const char *cstr) {
|
||||||
{
|
|
||||||
if (cstr && *cstr)
|
if (cstr && *cstr)
|
||||||
display_str(cstr, strlen(cstr));
|
vt100_process(cstr, strlen(cstr));
|
||||||
}
|
}
|
||||||
|
|
||||||
void display_pstr(const char *pstr)
|
void display_pstr(const char *pstr) {
|
||||||
{
|
|
||||||
if (pstr && *pstr)
|
if (pstr && *pstr)
|
||||||
display_str(pstr + 1, *pstr);
|
vt100_process(pstr + 1, *pstr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void display_char(char c)
|
|
||||||
{
|
|
||||||
switch(c)
|
|
||||||
{
|
|
||||||
case 0x07:
|
|
||||||
SysBeep2(0);
|
|
||||||
break;
|
|
||||||
|
|
||||||
//backspace
|
|
||||||
case 0x08:
|
|
||||||
if (Xpos) Xpos--;
|
|
||||||
break;
|
|
||||||
|
|
||||||
//tab
|
|
||||||
case 0x09:
|
|
||||||
// 1, 9, 17, 25, ...
|
|
||||||
// not sure this is right
|
|
||||||
Xpos = Xpos & 0xf8;
|
|
||||||
Xpos += 8;
|
|
||||||
//TODO - wrapping
|
|
||||||
break;
|
|
||||||
|
|
||||||
// line feed
|
|
||||||
case 0x0A:
|
|
||||||
if (++Ypos > 23)
|
|
||||||
{
|
|
||||||
ScrollRegion(__scroll[0], __scroll[1]);
|
|
||||||
Ypos = 23;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
|
|
||||||
case 0x0D: //carriage return
|
|
||||||
Xpos = 0;
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
if (isprint(c));
|
|
||||||
{
|
|
||||||
// check the wrapping flag ...
|
|
||||||
if (Xpos > 80)
|
|
||||||
{
|
|
||||||
Xpos = 0;
|
|
||||||
if (++Ypos > 23)
|
|
||||||
{
|
|
||||||
ScrollRegion(__scroll[0],
|
|
||||||
__scroll[1]);
|
|
||||||
|
|
||||||
Ypos = 23;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
PrintChar(c, and_mask);
|
|
||||||
Xpos++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* this reads text & has it drawn on the shr screen
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
// todo - and_mask + xor_mask
|
|
||||||
void display_str(const char *buffer, word cnt)
|
|
||||||
{
|
|
||||||
word i;
|
|
||||||
|
|
||||||
|
|
||||||
asm
|
|
||||||
{
|
|
||||||
phk
|
|
||||||
plb
|
|
||||||
}
|
|
||||||
|
|
||||||
for ( i = 0; i < cnt; i++)
|
|
||||||
{
|
|
||||||
if (esc)
|
|
||||||
{
|
|
||||||
esc_buffer[esc++] = buffer[i];
|
|
||||||
if (isalpha(buffer[i])
|
|
||||||
|| buffer[i] == '~'
|
|
||||||
|| buffer[i] == '='
|
|
||||||
|| buffer[i] == '>'
|
|
||||||
)
|
|
||||||
{
|
|
||||||
handle_ansi(buffer[i],
|
|
||||||
esc_buffer, esc);
|
|
||||||
esc = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else switch (buffer[i])
|
|
||||||
{
|
|
||||||
// bell
|
|
||||||
case 0x07:
|
|
||||||
SysBeep2(0);
|
|
||||||
break;
|
|
||||||
|
|
||||||
//backspace
|
|
||||||
case 0x08:
|
|
||||||
if (Xpos) Xpos--;
|
|
||||||
break;
|
|
||||||
|
|
||||||
//tab
|
|
||||||
case 0x09:
|
|
||||||
// 1, 9, 17, 25, ...
|
|
||||||
// not sure this is right
|
|
||||||
Xpos = Xpos & 0xf8;
|
|
||||||
Xpos += 8;
|
|
||||||
//TODO - wrapping
|
|
||||||
break;
|
|
||||||
|
|
||||||
// line feed
|
|
||||||
case 0x0A:
|
|
||||||
if (++Ypos > 23)
|
|
||||||
{
|
|
||||||
ScrollRegion(__scroll[0],
|
|
||||||
__scroll[1]);
|
|
||||||
|
|
||||||
Ypos = 23;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
|
|
||||||
case 0x0D: //carriage return
|
|
||||||
Xpos = 0;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x1b: //start of escape sequence
|
|
||||||
|
|
||||||
esc = 1;
|
|
||||||
esc_buffer[0] = 0x1b;
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
if (isprint(buffer[i]))
|
|
||||||
{
|
|
||||||
// check the wrapping flag ...
|
|
||||||
if (Xpos > 80)
|
|
||||||
{
|
|
||||||
Xpos = 0;
|
|
||||||
if (++Ypos > 23)
|
|
||||||
{
|
|
||||||
ScrollRegion(__scroll[0],
|
|
||||||
__scroll[1]);
|
|
||||||
|
|
||||||
Ypos = 23;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
PrintChar(buffer[i], and_mask);
|
|
||||||
Xpos++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//
|
|
||||||
// remap the iigs key to a vt100 code (if necessary) and send it out.
|
|
||||||
|
|
||||||
void send_event(EventRecord *event, Word ipid)
|
|
||||||
{
|
|
||||||
char *cp;
|
|
||||||
int len = 0;
|
|
||||||
word key;
|
|
||||||
word mods;
|
|
||||||
|
|
||||||
key = event->message;
|
|
||||||
mods = event->modifiers;
|
|
||||||
|
|
||||||
|
|
||||||
if (mods & keyPad)
|
|
||||||
{
|
|
||||||
switch (key)
|
|
||||||
{
|
|
||||||
case 0x72: // insert
|
|
||||||
cp = ESC "[2~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x75: // delete
|
|
||||||
cp = ESC "[3~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x73: // home
|
|
||||||
cp = ESC "[1~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x77: // end
|
|
||||||
cp = ESC "[4~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x74: // page up
|
|
||||||
cp = ESC "[5~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x79: // page down
|
|
||||||
cp = ESC "[6~";
|
|
||||||
len = 4;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x7a: // f1
|
|
||||||
cp = mods & shiftKey ? ESC "[23~" : ESC "[11~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x78: // f2
|
|
||||||
cp = mods & shiftKey ? ESC "[24~" : ESC "[12~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x63: // f3
|
|
||||||
cp = mods & shiftKey ? ESC "[25~" : ESC "[13~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x76: // f4
|
|
||||||
cp = mods & shiftKey ? ESC "[26~" : ESC "[14~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
|
|
||||||
case 0x60: // f5
|
|
||||||
cp = mods & shiftKey ? ESC "[28~" : ESC "[15~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x61: // f6
|
|
||||||
cp = mods & shiftKey ? ESC "[29~" : ESC "[17~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
|
|
||||||
case 0x62: // f7
|
|
||||||
cp = mods & shiftKey ? ESC "[31~" : ESC "[18~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x64: // f8
|
|
||||||
cp = mods & shiftKey ? ESC "[32~" : ESC "[19~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x65: // f9
|
|
||||||
cp = mods & shiftKey ? ESC "[33~" : ESC "[20~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x6d: // f10
|
|
||||||
cp = mods & shiftKey ? ESC "[34~" : ESC "[21~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x67: // f11
|
|
||||||
cp = ESC "[23~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 0x6f: // f12
|
|
||||||
cp = ESC "[24~";
|
|
||||||
len = 5;
|
|
||||||
break;
|
|
||||||
|
|
||||||
default: len = 0; cp = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (mods & controlKey)
|
|
||||||
{
|
|
||||||
cp = (char *)&event->message;
|
|
||||||
len = 1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
switch(key)
|
|
||||||
{
|
|
||||||
case 0x0d:
|
|
||||||
cp = "\r\n";
|
|
||||||
len = 2;
|
|
||||||
break;
|
|
||||||
case 0x08: // <--- arrow
|
|
||||||
cp = ESC "[D";
|
|
||||||
len = 3;
|
|
||||||
break;
|
|
||||||
case 0x0A: // down arrow
|
|
||||||
cp = ESC "[B";
|
|
||||||
len = 3;
|
|
||||||
break;
|
|
||||||
case 0x0B: // up arrow
|
|
||||||
cp = ESC "[A";
|
|
||||||
len = 3;
|
|
||||||
break;
|
|
||||||
case 0x15: // ---> arrow
|
|
||||||
cp = ESC "[C";
|
|
||||||
len = 3;
|
|
||||||
break;
|
|
||||||
|
|
||||||
// backspace to delete char
|
|
||||||
case 0x7f:
|
|
||||||
cp = "\x08";
|
|
||||||
len = 1;
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
cp = (char *)&event->message;
|
|
||||||
len = 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (len) TCPIPWriteTCP(ipid, cp, len, false, false);
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
487
fctelnet.c
487
fctelnet.c
|
@ -1,4 +1,4 @@
|
||||||
#include "Marinetti.h"
|
#include <tcpip.h>
|
||||||
#include <Locator.h>
|
#include <Locator.h>
|
||||||
#include <Memory.h>
|
#include <Memory.h>
|
||||||
#include <texttool.h>
|
#include <texttool.h>
|
||||||
|
@ -22,16 +22,11 @@
|
||||||
|
|
||||||
#include "telnet.h"
|
#include "telnet.h"
|
||||||
|
|
||||||
extern void ScrollRegion(word,word);
|
|
||||||
extern void ScrollDown(void);
|
|
||||||
extern void PrintChar(int the_char, unsigned int andMask);
|
|
||||||
extern void ClearScreen(void);
|
extern void ClearScreen(void);
|
||||||
extern void ClearScreenFrom(int Y);
|
|
||||||
extern void ClearLine(int Y);
|
|
||||||
extern void ClearLineFrom(int Y, int X);
|
|
||||||
|
|
||||||
extern void GrafOn(void) inline(0x0a04, 0xe10000);
|
extern pascal void GrafOn(void) inline(0x0a04, dispatcher);
|
||||||
extern void GrafOff(void) inline(0x0b04, 0xe10000);
|
extern pascal void GrafOff(void) inline(0x0b04, dispatcher);
|
||||||
|
|
||||||
extern pascal void SetColorTable(Word, ColorTable) inline(0x0E04,dispatcher);
|
extern pascal void SetColorTable(Word, ColorTable) inline(0x0E04,dispatcher);
|
||||||
extern pascal void SysBeep2(Word) inline(0x3803,dispatcher);
|
extern pascal void SysBeep2(Word) inline(0x3803,dispatcher);
|
||||||
extern pascal void SetAllSCBs(Word) inline(0x1404,dispatcher);
|
extern pascal void SetAllSCBs(Word) inline(0x1404,dispatcher);
|
||||||
|
@ -39,26 +34,30 @@ extern pascal void SetMasterSCB(Word) inline(0x1604,dispatcher);
|
||||||
extern pascal void InitColorTable(ColorTable) inline(0x0D04,dispatcher);
|
extern pascal void InitColorTable(ColorTable) inline(0x0D04,dispatcher);
|
||||||
|
|
||||||
|
|
||||||
Word MyID;
|
|
||||||
Word __gno;
|
|
||||||
|
|
||||||
Word modeTelnet = 1;
|
|
||||||
Word flagEcho = 1; // if *I* echo
|
|
||||||
|
|
||||||
|
|
||||||
void init_ansi(void);
|
|
||||||
|
|
||||||
Word ResolveHost(const char *name, cvtRecPtr cvt);
|
Word ResolveHost(const char *name, cvtRecPtr cvt);
|
||||||
Word GetChar(word ipid, unsigned char *c);
|
int WaitForStatus(word ipid, word status);
|
||||||
Word UngetChar(char c);
|
|
||||||
|
|
||||||
|
|
||||||
void display_str(const char *txt, word cnt);
|
|
||||||
void display_pstr(const char *);
|
void display_pstr(const char *);
|
||||||
void display_cstr(const char *);
|
void display_cstr(const char *);
|
||||||
void display_err(Word);
|
void display_err(Word);
|
||||||
|
|
||||||
void send_event(EventRecord *, Word);
|
extern void telnet_init(void);
|
||||||
|
extern void telnet_process(void);
|
||||||
|
|
||||||
|
extern void vt100_init(void);
|
||||||
|
extern void vt100_process(const unsigned char *buffer, unsigned buffer_size);
|
||||||
|
extern void vt100_event(EventRecord *event);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
Word MyID;
|
||||||
|
Word __gno;
|
||||||
|
|
||||||
|
|
||||||
|
#define ESC "\x1b"
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
#pragma databank 1
|
#pragma databank 1
|
||||||
|
@ -67,25 +66,17 @@ void send_event(EventRecord *, Word);
|
||||||
* called to print connect/disconnect messages from
|
* called to print connect/disconnect messages from
|
||||||
* Marinetti. msg is a pstring.
|
* Marinetti. msg is a pstring.
|
||||||
*/
|
*/
|
||||||
void printCallBack(const char *msg)
|
void printCallBack(const char *msg) {
|
||||||
{
|
if (msg && *msg) {
|
||||||
word i;
|
display_cstr(ESC "\n\r[1m"); // bold on
|
||||||
i = *msg;
|
display_pstr(msg); // show the string
|
||||||
if (i)
|
display_cstr(ESC "[0m\n\r"); // bold off
|
||||||
{
|
|
||||||
display_str("\x1b" "[1m", 4); // bold on
|
|
||||||
display_str(msg + 1, i); // show the string
|
|
||||||
display_str("\x1b" "[0m\n\r", 6); // bold off
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#pragma databank 0
|
#pragma databank 0
|
||||||
|
|
||||||
extern word esc;
|
|
||||||
extern word Xpos;
|
|
||||||
extern word Ypos;
|
|
||||||
|
|
||||||
void init_screen(void)
|
static void screen_init(void) {
|
||||||
{
|
|
||||||
#define WHITE 0x0fff
|
#define WHITE 0x0fff
|
||||||
#define YELLOW 0x0ff0
|
#define YELLOW 0x0ff0
|
||||||
#define BLACK 0x0000
|
#define BLACK 0x0000
|
||||||
|
@ -93,30 +84,30 @@ void init_screen(void)
|
||||||
#define GREEN 0x00f0
|
#define GREEN 0x00f0
|
||||||
#define RED 0x0f00
|
#define RED 0x0f00
|
||||||
|
|
||||||
static ColorTable ct =
|
static ColorTable ct =
|
||||||
{
|
{
|
||||||
BLACK, // background
|
BLACK, // background
|
||||||
RED, // underline / blink
|
RED, // underline / blink
|
||||||
BLUE, // bold
|
BLUE, // bold
|
||||||
GREEN, // foreground
|
GREEN, // foreground
|
||||||
|
|
||||||
BLACK,
|
BLACK,
|
||||||
RED,
|
RED,
|
||||||
BLUE,
|
BLUE,
|
||||||
GREEN,
|
GREEN,
|
||||||
|
|
||||||
BLACK,
|
BLACK,
|
||||||
RED,
|
RED,
|
||||||
BLUE,
|
BLUE,
|
||||||
GREEN,
|
GREEN,
|
||||||
|
|
||||||
BLACK,
|
BLACK,
|
||||||
RED,
|
RED,
|
||||||
BLUE,
|
BLUE,
|
||||||
GREEN,
|
GREEN,
|
||||||
};
|
};
|
||||||
int i;
|
|
||||||
|
|
||||||
|
unsigned i;
|
||||||
|
|
||||||
// linearize memory, disable shadowing.
|
// linearize memory, disable shadowing.
|
||||||
asm
|
asm
|
||||||
|
@ -138,175 +129,66 @@ int i;
|
||||||
SetMasterSCB(0xc080);
|
SetMasterSCB(0xc080);
|
||||||
SetAllSCBs(0xc080);
|
SetAllSCBs(0xc080);
|
||||||
//InitColorTable(ct);
|
//InitColorTable(ct);
|
||||||
for (i = 0; i < 15; i++)
|
for (i = 0; i < 16; i++)
|
||||||
SetColorTable(i, ct);
|
SetColorTable(i, ct);
|
||||||
|
|
||||||
ClearScreen();
|
ClearScreen();
|
||||||
GrafOn();
|
GrafOn();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static char out_buffer[1024];
|
||||||
|
static char out_buffer_size = 0;
|
||||||
|
|
||||||
/*
|
static word ipid = -1;
|
||||||
* this is (more or less) a state machine.
|
|
||||||
* old state (and character) are passed in
|
|
||||||
* new state is returned.
|
|
||||||
*
|
|
||||||
* 0 = starting state.
|
|
||||||
*/
|
|
||||||
#define SB_IAC 0xfaff
|
|
||||||
Word do_iac(Word state, char c, Word ipid)
|
|
||||||
{
|
|
||||||
static char buffer[64];
|
|
||||||
static int cnt;
|
|
||||||
|
|
||||||
if (state == 0) return c == IAC ? IAC : 0;
|
static void flush(void) {
|
||||||
// FF must be escaped as FF FF within SB.
|
if (out_buffer_size) {
|
||||||
// SB_IAC means the first FF has been processed.
|
TCPIPWriteTCP(ipid, out_buffer, out_buffer_size, true, false);
|
||||||
if (state == SB)
|
out_buffer_size = 0;
|
||||||
{
|
|
||||||
if (c == IAC) return SB_IAC;
|
|
||||||
buffer[cnt++] = c;
|
|
||||||
return SB;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (state == SB_IAC)
|
|
||||||
{
|
|
||||||
// it was an escaped FF
|
|
||||||
if (c == IAC)
|
|
||||||
{
|
|
||||||
buffer[cnt++] = IAC;
|
|
||||||
return SB;
|
|
||||||
}
|
|
||||||
else state = IAC; // process below...
|
|
||||||
}
|
|
||||||
if (state == IAC)
|
|
||||||
switch (c)
|
|
||||||
{
|
|
||||||
case DONT:
|
|
||||||
case DO:
|
|
||||||
case WONT:
|
|
||||||
case WILL:
|
|
||||||
return c;
|
|
||||||
case SB:
|
|
||||||
cnt = 0;
|
|
||||||
return c;
|
|
||||||
case SE:
|
|
||||||
// buffer is the data between
|
|
||||||
// IAC SB <...> IAC SE
|
|
||||||
if (buffer[0] == TELOPT_TTYPE
|
|
||||||
&& buffer[1] == TELQUAL_SEND)
|
|
||||||
{
|
|
||||||
static char msg[] =
|
|
||||||
{
|
|
||||||
IAC, SB, TELOPT_TTYPE, TELQUAL_IS,
|
|
||||||
'V', 'T', '1', '0', '0',
|
|
||||||
IAC, SE
|
|
||||||
};
|
|
||||||
TCPIPWriteTCP(ipid, msg,
|
|
||||||
sizeof(msg), true, false);
|
|
||||||
}
|
|
||||||
else if (buffer[0] == TELOPT_NAWS
|
|
||||||
&& buffer[1] == TELQUAL_SEND)
|
|
||||||
{
|
|
||||||
static char msg[] =
|
|
||||||
{
|
|
||||||
IAC, SB, TELOPT_NAWS,
|
|
||||||
0, 80, 0, 24,
|
|
||||||
IAC, SE
|
|
||||||
};
|
|
||||||
TCPIPWriteTCP(ipid, msg,
|
|
||||||
sizeof(msg), true, false);
|
|
||||||
}
|
|
||||||
else if (buffer[0] == TELOPT_TSPEED
|
|
||||||
&& buffer[1] == TELQUAL_SEND)
|
|
||||||
{
|
|
||||||
static char msg[] =
|
|
||||||
{
|
|
||||||
IAC, SB, TELOPT_TSPEED,
|
|
||||||
'9', '6', '0', '0', ',', '9', '6', '0', '0',
|
|
||||||
IAC, SE
|
|
||||||
};
|
|
||||||
TCPIPWriteTCP(ipid, msg,
|
|
||||||
sizeof(msg), true, false);
|
|
||||||
}
|
|
||||||
cnt = 0;
|
|
||||||
return 0;
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
if (state == DO)
|
|
||||||
{
|
|
||||||
buffer[0] = IAC;
|
|
||||||
buffer[1] = WONT;
|
|
||||||
buffer[2] = c;
|
|
||||||
if (c == TELOPT_TTYPE
|
|
||||||
|| c == TELOPT_SGA
|
|
||||||
|| c == TELOPT_NAWS
|
|
||||||
|| c == TELOPT_TSPEED)
|
|
||||||
{
|
|
||||||
buffer[1] = WILL;
|
|
||||||
}
|
|
||||||
TCPIPWriteTCP(ipid, buffer, 3, true, false);
|
|
||||||
|
|
||||||
}
|
|
||||||
if (state == DONT)
|
|
||||||
{
|
|
||||||
buffer[0] = IAC;
|
|
||||||
buffer[1] = WONT;
|
|
||||||
buffer[2] = c;
|
|
||||||
|
|
||||||
TCPIPWriteTCP(ipid, buffer, 3, true, false);
|
|
||||||
}
|
|
||||||
if (state == WILL || state == WONT)
|
|
||||||
{
|
|
||||||
buffer[0] = IAC;
|
|
||||||
buffer[1] = DONT;
|
|
||||||
buffer[2] = c;
|
|
||||||
if (c == TELOPT_ECHO)
|
|
||||||
{
|
|
||||||
buffer[1] = DO;
|
|
||||||
}
|
|
||||||
cnt = 3;
|
|
||||||
|
|
||||||
TCPIPWriteTCP(ipid, buffer, cnt, true, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
int main(int argc, char **argv)
|
|
||||||
{
|
void send(char *data, unsigned size) {
|
||||||
static EventRecord event;
|
|
||||||
static srBuffer sr;
|
if (out_buffer_size + size > sizeof(out_buffer)) {
|
||||||
static rrBuff rr;
|
flush();
|
||||||
static char str[16];
|
}
|
||||||
static cvtRec cvt;
|
if (size > sizeof(out_buffer) / 2) {
|
||||||
static QuitRecGS qDCB = {2, 0, 0x4000};
|
TCPIPWriteTCP(ipid, data, size, true, false);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
memcpy(out_buffer + out_buffer_size, data, size);
|
||||||
|
out_buffer_size += size;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
unsigned buffer_size;
|
||||||
|
unsigned char buffer[2048]; // 1500 is normal MTU size?
|
||||||
|
|
||||||
|
|
||||||
|
int main(int argc, char **argv) {
|
||||||
|
|
||||||
|
static EventRecord event;
|
||||||
|
static rrBuff rr;
|
||||||
|
static char str[16];
|
||||||
|
static cvtRec cvt;
|
||||||
|
static QuitRecGS qDCB = {2, 0, 0x4000};
|
||||||
|
|
||||||
|
|
||||||
Word iLoaded;
|
Word iLoaded;
|
||||||
Word iConnected;
|
Word iConnected;
|
||||||
Word iStarted;
|
Word iStarted;
|
||||||
Word Quit;
|
|
||||||
Word ipid;
|
|
||||||
Handle dp;
|
Handle dp;
|
||||||
|
|
||||||
|
|
||||||
int i;
|
|
||||||
Word key;
|
|
||||||
Word err;
|
Word err;
|
||||||
unsigned char c;
|
int ok;
|
||||||
//int fd;
|
|
||||||
int iac_state;
|
|
||||||
|
|
||||||
|
|
||||||
Xpos = Ypos = 0;
|
|
||||||
esc = 0;
|
|
||||||
//iac = 0;
|
|
||||||
iLoaded = iStarted = iConnected = false;
|
iLoaded = iStarted = iConnected = false;
|
||||||
__gno = false;
|
__gno = false;
|
||||||
|
ipid = -1;
|
||||||
|
|
||||||
MyID = MMStartUp();
|
MyID = MMStartUp();
|
||||||
|
|
||||||
|
@ -321,58 +203,53 @@ static QuitRecGS qDCB = {2, 0, 0x4000};
|
||||||
dp = NewHandle(0x0100, MyID,
|
dp = NewHandle(0x0100, MyID,
|
||||||
attrBank | attrPage |attrNoCross | attrFixed | attrLocked,
|
attrBank | attrPage |attrNoCross | attrFixed | attrLocked,
|
||||||
0x000000);
|
0x000000);
|
||||||
HLock(dp);
|
|
||||||
EMStartUp((Word)*dp, 0x14, 0, 0, 0, 0, MyID);
|
EMStartUp((Word)*dp, 0x14, 0, 0, 0, 0, MyID);
|
||||||
|
|
||||||
|
|
||||||
if (argc != 2)
|
// todo: -vt52 -> start in vt52 mode (DECANM = 0)
|
||||||
{
|
// todo:keypad flag of some sort?
|
||||||
|
|
||||||
|
if (argc != 2) {
|
||||||
ErrWriteCString("Usage: marlene host[:port]\r\n");
|
ErrWriteCString("Usage: marlene host[:port]\r\n");
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
init_screen();
|
screen_init();
|
||||||
|
|
||||||
init_ansi();
|
vt100_init();
|
||||||
|
|
||||||
|
|
||||||
TCPIPStatus();
|
TCPIPStatus();
|
||||||
if (_toolErr)
|
if (_toolErr) {
|
||||||
{
|
display_cstr("Loading Marinetti...\n\r");
|
||||||
display_str("\n\rLoading Marinetti...\n\r", 23);
|
|
||||||
LoadOneTool(0x36, 0x200); //load Marinetti
|
LoadOneTool(0x36, 0x200); //load Marinetti
|
||||||
if (_toolErr)
|
if (_toolErr) {
|
||||||
{
|
display_cstr("Unable to load Marinetti.\r\n");
|
||||||
ErrWriteCString("Unable to load Marinetti\r\n");
|
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
iLoaded = true;
|
iLoaded = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Marinetti now loaded
|
// Marinetti now loaded
|
||||||
if (!TCPIPStatus())
|
if (!TCPIPStatus()) {
|
||||||
{
|
display_cstr("Starting Marinetti...\n\r");
|
||||||
display_str("\n\rStarting Marinetti...\n\r", 24);
|
TCPIPStartUp();
|
||||||
TCPIPStartUp();
|
|
||||||
iStarted = true;
|
iStarted = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!TCPIPGetConnectStatus())
|
if (!TCPIPGetConnectStatus()) {
|
||||||
{
|
display_cstr("Connecting Marinetti...\n\r");
|
||||||
display_str("\n\rConnecting Marinetti...\n\r", 26);
|
|
||||||
TCPIPConnect(printCallBack);
|
TCPIPConnect(printCallBack);
|
||||||
if (_toolErr)
|
if (_toolErr) {
|
||||||
{
|
display_cstr("Unable to establish network connection.\r\n");
|
||||||
ErrWriteCString("Unable to establish network connection\r\n");
|
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
iConnected = true;
|
iConnected = true;
|
||||||
}
|
}
|
||||||
// marinetti is now connected
|
// marinetti is now connected
|
||||||
|
|
||||||
if (!ResolveHost(argv[1], &cvt))
|
if (!ResolveHost(argv[1], &cvt)) {
|
||||||
{
|
display_cstr("Unable to resolve address.\r\n");
|
||||||
ErrWriteCString("Unable to resolve address\r\n");
|
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -380,122 +257,105 @@ static QuitRecGS qDCB = {2, 0, 0x4000};
|
||||||
|
|
||||||
ipid = TCPIPLogin(MyID, cvt.cvtIPAddress, cvt.cvtPort, 0, 0x0040);
|
ipid = TCPIPLogin(MyID, cvt.cvtIPAddress, cvt.cvtPort, 0, 0x0040);
|
||||||
|
|
||||||
display_str("\n\rConnecting to ", 16);
|
TCPIPConvertIPToCASCII(cvt.cvtIPAddress, str, 0);
|
||||||
display_str(str, TCPIPConvertIPToCAscii(cvt.cvtIPAddress, str, 0));
|
display_cstr("Connecting to ");
|
||||||
|
display_cstr(str);
|
||||||
|
display_cstr("...\n\r");
|
||||||
|
|
||||||
TCPIPOpenTCP(ipid);
|
TCPIPOpenTCP(ipid);
|
||||||
|
|
||||||
// wait for the connection to occur.
|
// wait for the connection to occur.
|
||||||
while (1)
|
ok = WaitForStatus(ipid, TCPSESTABLISHED);
|
||||||
{
|
if (ok > 0) display_err(ok);
|
||||||
TCPIPPoll();
|
if (ok != 0) goto _exit2;
|
||||||
err = TCPIPStatusTCP(ipid, &sr);
|
|
||||||
if (err)
|
|
||||||
{
|
|
||||||
display_err(err);
|
|
||||||
goto _exit1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (sr.srState == tcpsESTABLISHED) break;
|
|
||||||
//if (sr.srState == tcpsCLOSED) goto _exit1;
|
|
||||||
GetNextEvent(keyDownMask | autoKeyMask ,&event);
|
|
||||||
if (event.what != keyDownEvt) continue;
|
|
||||||
if (!(event.modifiers & appleKey)) continue;
|
|
||||||
if ((Word)event.message == '.') goto _exit1;
|
|
||||||
if ((Word)event.message == 'q') goto _exit1;
|
|
||||||
if ((Word)event.message == 'Q') goto _exit1;
|
|
||||||
}
|
|
||||||
|
|
||||||
display_str("\n\rConnected\n\r", 13);
|
display_cstr("Connected.\n\r");
|
||||||
|
|
||||||
|
telnet_init();
|
||||||
|
|
||||||
//fd = open ("tcp.log", O_TRUNC | O_WRONLY | O_CREAT, 0777);
|
//fd = open ("tcp.log", O_TRUNC | O_WRONLY | O_CREAT, 0777);
|
||||||
|
|
||||||
Quit = false;
|
for(;;) {
|
||||||
|
static rrBuff rr;
|
||||||
|
|
||||||
|
|
||||||
iac_state = 0;
|
|
||||||
while (!Quit)
|
|
||||||
{
|
|
||||||
|
|
||||||
TCPIPPoll();
|
TCPIPPoll();
|
||||||
|
|
||||||
// check for incoming data...
|
rr.rrBuffCount = 0;
|
||||||
// 0xffff = no data
|
err = TCPIPReadTCP(ipid, 0, (Ref)buffer, sizeof(buffer), &rr);
|
||||||
// 0 = data
|
// tcperrConClosing and tcperrClosing aren't fatal.
|
||||||
// otherwise = marinetti error.
|
|
||||||
err = GetChar(ipid, &c);
|
|
||||||
|
|
||||||
if (err && (err != 0xffff))
|
buffer_size = rr.rrBuffCount;
|
||||||
{
|
if (buffer_size) err = 0;
|
||||||
display_err(err);
|
if (err) {
|
||||||
Quit++;
|
if (err == tcperrConClosing || err == tcperrClosing)
|
||||||
continue;
|
display_cstr("\r\nTCP Connection Closed.\r\n");
|
||||||
|
else
|
||||||
|
display_err(err);
|
||||||
|
goto _exit1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (err == 0)
|
if (buffer_size) {
|
||||||
{
|
telnet_process();
|
||||||
//if (fd > 0) write(fd, &c, 1);
|
}
|
||||||
if (iac_state)
|
if (buffer_size) {
|
||||||
iac_state = do_iac(iac_state, c, ipid);
|
vt100_process(buffer, buffer_size);
|
||||||
else if (modeTelnet && c == IAC)
|
|
||||||
iac_state = do_iac(0, c, ipid);
|
|
||||||
else display_str(&c, 1);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
GetNextEvent(keyDownMask | autoKeyMask, &event);
|
GetNextEvent(keyDownMask | autoKeyMask, &event);
|
||||||
if (event.what != keyDownEvt) continue;
|
if (event.what == keyDownEvt) {
|
||||||
c = key = event.message;
|
|
||||||
|
|
||||||
if (event.modifiers & appleKey)
|
unsigned char key = event.message;
|
||||||
{
|
|
||||||
switch (key)
|
if (event.modifiers & appleKey) {
|
||||||
{
|
switch (key) {
|
||||||
case 'Q': // quit
|
case 'Q': // quit
|
||||||
case 'q':
|
case 'q':
|
||||||
Quit++;
|
goto _exit1;
|
||||||
break;
|
break;
|
||||||
case 'V': // paste
|
case 'V': // paste...
|
||||||
case 'v':
|
case 'v':
|
||||||
break;
|
break;
|
||||||
case 'Z': // suspend (gnome)
|
case 'Z': // suspend (gnome)
|
||||||
case 'z':
|
case 'z':
|
||||||
if (__gno)
|
if (__gno) {
|
||||||
{
|
static struct sgttyb sb;
|
||||||
static struct sgttyb sb;
|
static int err;
|
||||||
static int err;
|
gtty(1,&sb);
|
||||||
gtty(1,&sb);
|
sb.sg_flags &= ~RAW;
|
||||||
sb.sg_flags &= ~RAW;
|
stty(1,&sb);
|
||||||
stty(1,&sb);
|
GrafOff();
|
||||||
GrafOff();
|
Kkill(Kgetpid(), SIGSTOP, &err);
|
||||||
Kkill(Kgetpid(), SIGSTOP, &err);
|
sb.sg_flags |= RAW;
|
||||||
sb.sg_flags |= RAW;
|
stty(1,&sb);
|
||||||
stty(1,&sb);
|
GrafOn();
|
||||||
GrafOn();
|
}
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
break;
|
|
||||||
|
} else {
|
||||||
|
vt100_event(&event);
|
||||||
}
|
}
|
||||||
continue;
|
|
||||||
|
|
||||||
}
|
}
|
||||||
else send_event(&event, ipid);
|
flush();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
_exit1:
|
_exit1:
|
||||||
//if (fd > 0) close(fd);
|
flush();
|
||||||
TCPIPCloseTCP(ipid);
|
|
||||||
TCPIPPoll(); // wait until closed...
|
|
||||||
TCPIPLogout(ipid);
|
|
||||||
|
|
||||||
// be nice and
|
display_cstr("\n\rClosing TCP Connection...\n\r");
|
||||||
while (GetNextEvent(keyDownMask | autoKeyMask, &event));
|
|
||||||
display_str("\n\rPress any key to exit.\n\r", 26);
|
TCPIPCloseTCP(ipid);
|
||||||
while (!GetNextEvent(keyDownMask | autoKeyMask, &event));
|
WaitForStatus(ipid, TCPSCLOSED);
|
||||||
|
|
||||||
|
_exit2:
|
||||||
|
|
||||||
|
|
||||||
_exit:
|
_exit:
|
||||||
|
|
||||||
|
if (ipid != -1) TCPIPLogout(ipid);
|
||||||
|
|
||||||
if (iConnected)
|
if (iConnected)
|
||||||
TCPIPDisconnect(false, printCallBack);
|
TCPIPDisconnect(false, printCallBack);
|
||||||
|
|
||||||
|
@ -506,10 +366,17 @@ _exit:
|
||||||
UnloadOneTool(0x36);
|
UnloadOneTool(0x36);
|
||||||
|
|
||||||
|
|
||||||
|
// flush q
|
||||||
|
while (GetNextEvent(keyDownMask | autoKeyMask, &event)) ;
|
||||||
|
display_cstr("\n\rPress any key to exit.\n\r");
|
||||||
|
while (!GetNextEvent(keyDownMask | autoKeyMask, &event)) ;
|
||||||
|
|
||||||
|
|
||||||
EMShutDown();
|
EMShutDown();
|
||||||
|
DisposeHandle(dp);
|
||||||
GrafOff();
|
GrafOff();
|
||||||
TextShutDown();
|
TextShutDown();
|
||||||
QuitGS(&qDCB);
|
QuitGS(&qDCB);
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
3
makefile
3
makefile
|
@ -1,5 +1,5 @@
|
||||||
PROG = fctelnet
|
PROG = fctelnet
|
||||||
OBJS = fctelnet.o vt100.o ansi.o chars.o marinetti.o display.o
|
OBJS = fctelnet.o vt100.o telnet.o ansi.o chars.o marinetti.o display.o
|
||||||
|
|
||||||
OPTIMIZE *= 79
|
OPTIMIZE *= 79
|
||||||
|
|
||||||
|
@ -16,6 +16,7 @@ vt100.o: vt100.c
|
||||||
ansi.o: ansi.asm
|
ansi.o: ansi.asm
|
||||||
chars.o: chars.asm
|
chars.o: chars.asm
|
||||||
marinetti.o: marinetti.c
|
marinetti.o: marinetti.c
|
||||||
|
telnet.o: telnet.c
|
||||||
|
|
||||||
clean:
|
clean:
|
||||||
$(RM) -f *.o *.root *.a *.r
|
$(RM) -f *.o *.root *.a *.r
|
||||||
|
|
66
marinetti.c
66
marinetti.c
|
@ -60,25 +60,21 @@ EventRecord event;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
TCPIPDNRNameToIP(pstr, &dnr);
|
TCPIPDNRNameToIP(pstr, &dnr);
|
||||||
if (_toolErr)
|
if (_toolErr) {
|
||||||
{
|
|
||||||
free(pstr);
|
free(pstr);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
while (dnr.DNRStatus == DNRPending)
|
while (dnr.DNRStatus == DNRPending) {
|
||||||
{
|
|
||||||
TCPIPPoll();
|
TCPIPPoll();
|
||||||
GetNextEvent(keyDownMask | autoKeyMask, &event);
|
GetNextEvent(keyDownMask | autoKeyMask, &event);
|
||||||
if ((event.what == keyDownEvt)
|
if ((event.what == keyDownEvt)
|
||||||
&& (event.modifiers & appleKey)
|
&& (event.modifiers & appleKey)
|
||||||
&& ((Word)event.message == '.'))
|
&& ((Word)event.message == '.')) {
|
||||||
{
|
|
||||||
TCPIPCancelDNR(&dnr);
|
TCPIPCancelDNR(&dnr);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (dnr.DNRStatus == DNROK)
|
if (dnr.DNRStatus == DNROK) {
|
||||||
{
|
|
||||||
cvt->cvtIPAddress = dnr.DNRIPAddress;
|
cvt->cvtIPAddress = dnr.DNRIPAddress;
|
||||||
cvt->cvtPort = port;
|
cvt->cvtPort = port;
|
||||||
free(pstr);
|
free(pstr);
|
||||||
|
@ -91,47 +87,25 @@ EventRecord event;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int WaitForStatus(word ipid, word status) {
|
||||||
|
static srBuffer sr;
|
||||||
|
EventRecord event;
|
||||||
|
Word err;
|
||||||
|
|
||||||
/*
|
for(;;) {
|
||||||
* pcnt is the next place to store data
|
TCPIPPoll();
|
||||||
* bptr is the current ptr.
|
err = TCPIPStatusTCP(ipid, &sr);
|
||||||
*/
|
|
||||||
static unsigned char buffer[1024];
|
|
||||||
static unsigned char pushback[1024];
|
|
||||||
static int pcnt = 0;
|
|
||||||
static int bcnt = 0;
|
|
||||||
static int bptr = 0;
|
|
||||||
static rrBuff rr;
|
|
||||||
|
|
||||||
Word GetChar(word ipid, unsigned char *c)
|
|
||||||
{
|
|
||||||
word err;
|
|
||||||
|
|
||||||
*c = 0;
|
|
||||||
|
|
||||||
if (pcnt)
|
|
||||||
{
|
|
||||||
*c = pushback[--pcnt];
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
if (!bcnt)
|
|
||||||
{
|
|
||||||
err = TCPIPReadTCP(ipid, 0, (Ref)buffer, 1024, &rr);
|
|
||||||
bcnt = rr.rrBuffCount;
|
|
||||||
bptr = 0;
|
|
||||||
if (err) return err;
|
if (err) return err;
|
||||||
|
|
||||||
|
if (sr.srState == status) return 0;
|
||||||
|
GetNextEvent(keyDownMask | autoKeyMask, &event);
|
||||||
|
if (event.what != keyDownEvt) continue;
|
||||||
|
if (!(event.modifiers & appleKey)) continue;
|
||||||
|
if ((Word)event.message == '.') return -1;
|
||||||
|
//if ((Word)event.message == 'q') return -1;
|
||||||
|
//if ((Word)event.message == 'Q') return -1;
|
||||||
}
|
}
|
||||||
if (bcnt)
|
return 0;
|
||||||
{
|
|
||||||
bcnt--;
|
|
||||||
*c = buffer[bptr++];
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
return 0xffff;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void UngetChar(char c)
|
|
||||||
{
|
|
||||||
pushback[pcnt++] = c;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue