Added C interface to TCP functions.

This commit is contained in:
Oliver Schmidt 2017-11-06 23:36:44 +01:00
parent c4f5c7dbfc
commit 9a8ba804bc
5 changed files with 264 additions and 7 deletions

View File

@ -45,11 +45,6 @@ extern unsigned long cfg_dns;
//
extern unsigned long dhcp_server;
//
//
extern unsigned char* tcp_packet;
extern unsigned int tcp_packet_len;
// Initialise the IP stack
//
// This calls the individual protocol & driver initialisations, so this is
@ -178,6 +173,56 @@ unsigned char __fastcall__ udp_send(const unsigned char* buf, unsigned int len,
unsigned long dest, unsigned int dest_port,
unsigned int src_port);
// Listen for an inbound TCP connection
//
// This is a 'blocking' call, i.e. it will not return until a connection has been made.
//
// Inputs: port: TCP port to listen on
// callback: Vector to call when data arrives on this connection
// Output: 1 if an error occured, 0 otherwise
//
unsigned char __fastcall__ tcp_listen(unsigned int port, void (*callback)(void));
// Make outbound TCP connection
//
// Inputs: dest: Destination IP address
// dest_port: Destination port
// callback: Vector to call when data arrives on this connection
// Output: 1 if an error occured, 0 otherwise
//
unsigned char __fastcall__ tcp_connect(unsigned long dest, unsigned int dest_port,
void (*callback)(void));
// Close the current TCP connection
//
// Inputs: None
// Output: 1 if an error occured, 0 otherwise
//
unsigned char tcp_close(void);
// Access to received TCP data
//
// Access to the two items below is only valid in the context of a callback
// set with tcp_listen or tcp_connect.
//
extern unsigned char* tcp_recv_buf; // Pointer to buffer with data received
extern int tcp_recv_len; // -1 on close, otherwise length of data received
// Send data on the current TCP connection
//
// Inputs: buf: Pointer to buffer containing data to be sent
// len: Length of data to send (exclusive of any headers)
// Output: 1 if an error occured, 0 otherwise
//
unsigned char __fastcall__ tcp_send(const unsigned char* buf, unsigned int len);
// Send an empty ACK packet on the current TCP connection
//
// Inputs: None
// Output: 1 if an error occured, 0 otherwise
//
unsigned char tcp_send_keep_alive(void);
// Get number of milliseconds since initialization
//
// Inputs: None

View File

@ -28,6 +28,7 @@ IP65OBJS=\
input_c.o \
ip65.o \
ip65_c.o \
tcp_c.o \
tftp.o \
timer.o \
timer_c.o \

75
ip65/tcp_c.s Normal file
View File

@ -0,0 +1,75 @@
.include "../inc/common.i"
.export _tcp_listen
.export _tcp_connect
.export _tcp_close
.export _tcp_recv_buf
.export _tcp_recv_len
.export _tcp_send
.export _tcp_send_keep_alive
.import tcp_listen
.import tcp_connect
.import tcp_close
.import tcp_inbound_data_ptr
.import tcp_inbound_data_length
.import tcp_send
.import tcp_send_keep_alive
.import tcp_callback
.import tcp_connect_ip
.import tcp_send_data_len
.import popax, popeax
.importzp ptr1, sreg
_tcp_listen:
stax tcp_callback
jsr popax
jsr tcp_listen
ldx #$00
txa
rol
rts
_tcp_connect:
stax tcp_callback
jsr popax
stax ptr1
jsr popeax
stax tcp_connect_ip
ldax sreg
stax tcp_connect_ip+2
ldax ptr1
jsr tcp_connect
ldx #$00
txa
rol
rts
_tcp_close:
jsr tcp_close
ldx #$00
txa
rol
rts
_tcp_recv_buf := tcp_inbound_data_ptr
_tcp_recv_len := tcp_inbound_data_length
_tcp_send:
stax tcp_send_data_len
jsr popax
jsr tcp_send
ldx #$00
txa
rol
rts
_tcp_send_keep_alive:
jsr tcp_send_keep_alive
ldx #$00
txa
rol
rts

View File

@ -37,7 +37,8 @@ TCP =\
httpd \
math \
parser \
ping
ping \
tcp
all: $(UDP) $(TCP)
.PHONY: $(UDP) $(TCP)
@ -128,6 +129,7 @@ ip65test.d64: prg
$(C1541) -attach $@ -write parser.prg parser,p
$(C1541) -attach $@ -write ping.prg ping,p
$(C1541) -attach $@ -write sntp.prg sntp,p
$(C1541) -attach $@ -write tcp.prg tcp,p
$(C1541) -attach $@ -write tftp.prg tftp,p
$(C1541) -attach $@ -write udp.prg udp,p
$(C1541) -attach $@ -write vt100.prg vt100,p
@ -143,9 +145,9 @@ ip65test.dsk: bin
java -jar $(AC) -cc65 $@ parser bin < parser.bin
java -jar $(AC) -cc65 $@ ping bin < ping.bin
java -jar $(AC) -cc65 $@ sntp bin < sntp.bin
java -jar $(AC) -cc65 $@ tcp bin < tcp.bin
java -jar $(AC) -cc65 $@ tftp bin < tftp.bin
java -jar $(AC) -cc65 $@ udp bin < udp.bin
java -jar $(AC) -cc65 $@ vt100 bin < vt100.bin
ip65test.atr: com
mkdir atr
@ -159,6 +161,7 @@ ip65test.atr: com
cp parser.com atr/parser.com
cp ping.com atr/ping.com
cp sntp.com atr/sntp.com
cp tcp.com atr/tcp.com
cp tftp.com atr/tftp.com
cp udp.com atr/udp.com
cp vt100.com atr/vt100.com

133
test/tcp.c Normal file
View File

@ -0,0 +1,133 @@
#include <cc65.h>
#include <conio.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "../inc/ip65.h"
#define LEN 500
#define SRV "192.168.0.10"
unsigned char buf[1500];
int len;
void error_exit(void)
{
printf("Error $%X\n", ip65_error);
if (doesclrscrafterexit())
{
printf("Press any key\n");
cgetc();
}
exit(1);
}
void tcp_recv(void)
{
if (len)
{
return;
}
len = tcp_recv_len;
if (len != -1)
{
memcpy(buf, tcp_recv_buf, len);
}
}
void main(void)
{
unsigned i;
unsigned long srv;
char key;
if(!(srv = parse_dotted_quad(SRV)))
{
error_exit();
}
printf("Init\n");
if (ip65_init())
{
error_exit();
}
printf("DHCP\n");
if (dhcp_init())
{
error_exit();
}
printf("IP Addr: %s\n", dotted_quad(cfg_ip));
printf("Netmask: %s\n", dotted_quad(cfg_netmask));
printf("Gateway: %s\n", dotted_quad(cfg_gateway));
printf("DNS Srv: %s\n", dotted_quad(cfg_dns));
printf("Connect to %s\n", SRV);
if (tcp_connect(srv, 6502, tcp_recv))
{
error_exit();
}
printf("(T)CP or e(X)it\n");
do
{
ip65_process();
if (kbhit())
{
key = cgetc();
}
else
{
key = '\0';
}
if (key == 't')
{
printf("Send Len %d", LEN);
for (i = 0; i < LEN; ++i)
{
buf[i] = i;
}
if (tcp_send(buf, LEN))
{
printf("!\n");
}
else
{
printf(".\n");
}
}
if (len == -1)
{
printf("Disconnect\n");
}
else if (len)
{
printf("Recv Len %d", len);
for (i = 0; i < len; ++i)
{
if ((i % 11) == 0)
{
ip65_process();
printf("\n$%04X:", i);
}
printf(" %02X", buf[i]);
}
len = 0;
printf(".\n");
}
}
while (key != 'x' && len != -1);
printf("Close\n");
if (tcp_close())
{
error_exit();
}
printf("Done\n");
}