git-svn-id: http://svn.code.sf.net/p/netboot65/code@142 93682198-c243-4bdb-bd91-e943c89aac3b

This commit is contained in:
jonnosan 2009-06-26 13:19:46 +00:00
parent f788a3292c
commit 6640871a89
3 changed files with 260 additions and 22 deletions

View File

@ -13,5 +13,7 @@ SEGMENTS {
BSS: load = RAM, type = bss; BSS: load = RAM, type = bss;
ZEROPAGE: load = ZP, type = zp; ZEROPAGE: load = ZP, type = zp;
IP65ZP: load = IP65ZP, type = zp; IP65ZP: load = IP65ZP, type = zp;
EXEHDR: load = DISCARD, type = ro; EXEHDR: load = DISCARD, type = ro;
TCP_VARS: load = RAM, type = bss;
} }

View File

@ -10,33 +10,240 @@
.export tcp_init .export tcp_init
.export tcp_process .export tcp_process
.export tcp_add_listener .export tcp_listen
.export tcp_remove_listener .export tcp_connect
.export tcp_send .export tcp_callback
.export tcp_remote_ip
.import ip_calc_cksum
.import ip_send
.import ip_create_packet
.import ip_inp
.import ip_outp
.importzp ip_cksum_ptr
.importzp ip_header_cksum
.importzp ip_src
.importzp ip_dest
.importzp ip_data
.importzp ip_proto
.importzp ip_proto_tcp
.importzp ip_id
.importzp ip_len
.import copymem
.importzp copy_src
.importzp copy_dest
.import cfg_ip
.segment "TCP_VARS" .segment "TCP_VARS"
tcp_cxn_state =0
tcp_cxn_local_port =1
tcp_cxn_remote_port =3
tcp_cxn_remote_ip =5
tcp_cxn_local_seq =9
tcp_cxn_remote_seq =13
tcp_cxn_entry_size =17 tcp_cxn_state_listening = 1 ;(waiting for an inbound SYN)
tcp_max_connections =10 tcp_cxn_state_syn_sent = 2 ;(waiting for an inbound SYN/ACK)
; tcp packet offsets
tcp_inp = ip_inp + ip_data ;pointer to tcp packet inside inbound ethernet frame
tcp_outp = ip_outp + ip_data ;pointer to tcp packet inside outbound ethernet frame
tcp_src_port = 0 ;offset of source port field in tcp packet
tcp_dest_port = 2 ;offset of destination port field in tcp packet
tcp_seq = 4 ;offset of sequence number field in tcp packet
tcp_ack = 8 ;offset of acknowledgement field in tcp packet
tcp_header_length = 12 ;offset of header length field in tcp packet
tcp_flags_field = 13 ;offset of flags field in tcp packet
tcp_window_size = 14 ; offset of window size field in tcp packet
tcp_checksum = 16 ; offset of checksum field in tcp packet
tcp_urgent_pointer = 18 ; offset of urgent pointer field in tcp packet
tcp_data=20 ;offset of data in tcp packet
; virtual header
tcp_vh = tcp_outp - 12
tcp_vh_src = 0
tcp_vh_dest = 4
tcp_vh_zero = 8
tcp_vh_proto = 9
tcp_vh_len = 10
;
tcp_flag_FIN =1
tcp_flag_SYN =2
tcp_flag_RST =4
tcp_flag_PSH =8
tcp_flag_ACK =16
tcp_flag_URG =32
.segment "TCP_VARS"
tcp_state: .res 1
tcp_local_port: .res 2
tcp_remote_port: .res 2
tcp_remote_ip: .res 4
tcp_sequence_number: .res 4
tcp_ack_number: .res 4
tcp_data_ptr: .res 2
tcp_data_len: .res 2
tcp_callback: .res 2
tcp_flags: .res 1
.data
tcp_client_port: .word $0004 ;=$0400 in network byte order
tcp_connections:
.res tcp_max_connections*tcp_cxn_entry_size
.code .code
tcp_add_listener:
tcp_remove_listener:
tcp_send:
tcp_process:
lda #NB65_ERROR_FUNCTION_NOT_SUPPORTED
sta ip65_error
sec
tcp_init: tcp_init:
rts
;make outbound tcp connection
;inputs:
; tcp_remote_ip: destination ip address (4 bytes)
; AX: destination port (2 bytes)
; tcp_callback: vector to call when data arrives on this connection
;outputs:
; carry flag is set if an error occured, clear otherwise
tcp_connect:
stax tcp_remote_port
inc tcp_client_port
ldax tcp_client_port
stax tcp_local_port
lda #tcp_cxn_state_syn_sent
sta tcp_state
lda #tcp_flag_SYN
sta tcp_flags
ldax #0
stax tcp_data_len
stax tcp_ack_number
stax tcp_ack_number+2
jsr tcp_send_packet
rts rts
;send a single tcp packet
;inputs:
; tcp_remote_ip: IP address of destination server
; tcp_remote_port: destination tcp port
; tcp_local_port: source tcp port
; tcp_flags: 6 bit flags
; tcp_data_ptr: pointer to data to include in this packet
; tcp_data_len: length of data pointed at by tcp_data_ptr
;outputs:
; carry flag is set if an error occured, clear otherwise
tcp_send_packet:
ldax tcp_data_ptr
stax copy_src ; copy data to output buffer
ldax #tcp_outp + tcp_data
stax copy_dest
ldax tcp_data_len
jsr copymem
ldx #3 ; copy virtual header addresses
: lda tcp_remote_ip,x
sta tcp_vh + tcp_vh_dest,x ; set virtual header destination
lda cfg_ip,x
sta tcp_vh + tcp_vh_src,x ; set virtual header source
dex
bpl :-
lda tcp_local_port ; copy source port
sta tcp_outp + tcp_src_port + 1
lda tcp_local_port + 1
sta tcp_outp + tcp_src_port
lda tcp_remote_port ; copy destination port
sta tcp_outp + tcp_dest_port + 1
lda tcp_remote_port + 1
sta tcp_outp + tcp_dest_port
ldx #3 ; copy sequence and ack numbers (in reverse order)
ldy #0
: lda tcp_sequence_number,x
sta tcp_outp + tcp_seq,y
lda tcp_ack_number,x
sta tcp_outp + tcp_ack,y
iny
dex
bpl :-
lda #$50 ;4 bit header length in 32bit words + 4 bits of zero
sta tcp_outp+tcp_header_length
lda tcp_flags
sta tcp_outp+tcp_flags_field
lda #ip_proto_tcp
sta tcp_vh + tcp_vh_proto
ldax #$1000
stax tcp_outp+tcp_window_size
lda #0 ; clear checksum
sta tcp_outp + tcp_checksum
sta tcp_outp + tcp_checksum + 1
sta tcp_vh + tcp_vh_zero ; clear virtual header zero byte
ldax #tcp_vh ; checksum pointer to virtual header
stax ip_cksum_ptr
lda tcp_data_len ; copy length + 20
clc
adc #20
sta tcp_vh + tcp_vh_len + 1 ; lsb for virtual header
tay
lda tcp_data_len + 1
adc #0
sta tcp_vh + tcp_vh_len ; msb for virtual header
tax ; length to A/X
tya
clc ; add 12 bytes for virtual header
adc #12
bcc :+
inx
:
jsr ip_calc_cksum ; calculate checksum
stax tcp_outp + tcp_checksum
ldx #3 ; copy addresses
: lda tcp_remote_ip,x
sta ip_outp + ip_dest,x ; set ip destination address
dex
bpl :-
jsr ip_create_packet ; create ip packet template
lda tcp_outp + tcp_data_len + 1 ; ip len = tcp data length +20 byte ip header + 20 byte tcp header
ldx tcp_outp + tcp_data_len
clc
adc #40
bcc :+
inx
: sta ip_outp + ip_len + 1 ; set length
stx ip_outp + ip_len
ldax #$1234 ; set ID
stax ip_outp + ip_id
lda #ip_proto_tcp ; set protocol
sta ip_outp + ip_proto
jmp ip_send ; send packet, sec on error
;listen on the tcp port specified
; tcp_callback: vector to call when data arrives on specified port
; AX: set to tcp port to listen on
tcp_listen:
rts
tcp_process:
;process incoming tcp packet
;inputs:
; eth_inp: should contain an ethernet frame encapsulating an inbound tcp packet
;outputs:
; carry flag set if any error occured (including if packet not part of
; existing connection)
; carry flag clear if no error
; if connection was found, an outbound message may be created, overwriting eth_outp
rts

View File

@ -6,6 +6,12 @@
.import parse_dotted_quad .import parse_dotted_quad
.import dotted_quad_value .import dotted_quad_value
.import tcp_listen
.import tcp_callback
.import ip65_process
.import tcp_connect
.import tcp_remote_ip
.import __CODE_LOAD__ .import __CODE_LOAD__
.import __CODE_SIZE__ .import __CODE_SIZE__
@ -105,9 +111,29 @@ init:
ldax #$1234 ldax #$1234
jsr test_add_16_32 jsr test_add_16_32
jsr print_cr
init_ip_via_dhcp
jsr print_ip_config
@loop_forever:
ldax #tcp_callback_routine
stax tcp_callback
ldax tcp_dest_ip
stax tcp_remote_ip
ldax tcp_dest_ip+2
stax tcp_remote_ip+2
ldax #80
jsr tcp_connect
jsr ip65_process
jmp @loop_forever
rts rts
tcp_callback_routine:
rts
;assumes acc32 & op32 already set ;assumes acc32 & op32 already set
@ -226,3 +252,6 @@ number15:
number16: number16:
.byte $00,$00,$00,$00 .byte $00,$00,$00,$00
tcp_dest_ip:
.byte 10,5,1,1