mirror of
https://git.tartarus.org/simon/putty.git
synced 2025-03-21 22:28:37 -05:00
Add reception support for MacTCP. Now I can log in over TELNET, just about.
There are still lots of things to fix, like urgent data or the fact that everything seems to happen one keypress too late, but this is an important milestone. [originally from svn r2458]
This commit is contained in:
parent
a7ba273b5b
commit
30bff47c89
@ -1,4 +1,4 @@
|
|||||||
$Id: README.mac,v 1.7 2003/01/02 18:09:21 ben Exp $
|
$Id: README.mac,v 1.8 2003/01/05 12:53:38 ben Exp $
|
||||||
|
|
||||||
Information about PuTTY for the Mac OS
|
Information about PuTTY for the Mac OS
|
||||||
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
|
-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=
|
||||||
@ -54,6 +54,7 @@ Known bugs:
|
|||||||
|
|
||||||
Features we need (and aren't entirely obvious):
|
Features we need (and aren't entirely obvious):
|
||||||
|
|
||||||
|
* TCP urgent data.
|
||||||
* Scroll-conflation -- scroll_display should change the in-memory
|
* Scroll-conflation -- scroll_display should change the in-memory
|
||||||
display and remember the scroll, then do_scroll should be called
|
display and remember the scroll, then do_scroll should be called
|
||||||
only when scroll_display gets called for a different rectangle or
|
only when scroll_display gets called for a different rectangle or
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
/* $Id: mac.c,v 1.18 2003/01/05 10:52:56 ben Exp $ */
|
/* $Id: mac.c,v 1.19 2003/01/05 12:53:38 ben Exp $ */
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 1999 Ben Harris
|
* Copyright (c) 1999 Ben Harris
|
||||||
* All rights reserved.
|
* All rights reserved.
|
||||||
@ -213,6 +213,7 @@ static void mac_eventloop(void) {
|
|||||||
mac_adjustcursor(cursrgn);
|
mac_adjustcursor(cursrgn);
|
||||||
if (gotevent)
|
if (gotevent)
|
||||||
mac_event(&event);
|
mac_event(&event);
|
||||||
|
mactcp_poll();
|
||||||
}
|
}
|
||||||
DisposeRgn(cursrgn);
|
DisposeRgn(cursrgn);
|
||||||
}
|
}
|
||||||
|
@ -88,6 +88,7 @@ extern void init_ucs(void);
|
|||||||
/* from mtcpnet.c */
|
/* from mtcpnet.c */
|
||||||
extern OSErr mactcp_init(void);
|
extern OSErr mactcp_init(void);
|
||||||
extern void mactcp_shutdown(void);
|
extern void mactcp_shutdown(void);
|
||||||
|
extern void mactcp_poll(void);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -37,6 +37,7 @@
|
|||||||
|
|
||||||
#include <assert.h>
|
#include <assert.h>
|
||||||
|
|
||||||
|
#define DEFINE_PLUG_METHOD_MACROS
|
||||||
#include "putty.h"
|
#include "putty.h"
|
||||||
#include "network.h"
|
#include "network.h"
|
||||||
#include "mac.h"
|
#include "mac.h"
|
||||||
@ -161,6 +162,8 @@ struct Socket_tag {
|
|||||||
int oobinline;
|
int oobinline;
|
||||||
int pending_error; /* in case send() returns error */
|
int pending_error; /* in case send() returns error */
|
||||||
int listener;
|
int listener;
|
||||||
|
struct Socket_tag *next;
|
||||||
|
struct Socket_tag **prev;
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -184,6 +187,7 @@ static struct {
|
|||||||
Handle dnr_handle;
|
Handle dnr_handle;
|
||||||
int initialised;
|
int initialised;
|
||||||
short refnum;
|
short refnum;
|
||||||
|
Actual_Socket socklist;
|
||||||
} mactcp;
|
} mactcp;
|
||||||
|
|
||||||
static pascal void mactcp_lookupdone(struct hostInfo *hi, char *cookie);
|
static pascal void mactcp_lookupdone(struct hostInfo *hi, char *cookie);
|
||||||
@ -197,6 +201,8 @@ static void *mactcp_get_private_ptr(Socket);
|
|||||||
static char *mactcp_socket_error(Socket);
|
static char *mactcp_socket_error(Socket);
|
||||||
static void mactcp_set_frozen(Socket, int);
|
static void mactcp_set_frozen(Socket, int);
|
||||||
|
|
||||||
|
static void mactcp_recv(Actual_Socket s, size_t len);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Initialise MacTCP.
|
* Initialise MacTCP.
|
||||||
* This should be called once before any TCP connection is opened.
|
* This should be called once before any TCP connection is opened.
|
||||||
@ -287,11 +293,16 @@ void sk_getaddr(SockAddr addr, char *buf, int buflen)
|
|||||||
char mybuf[16];
|
char mybuf[16];
|
||||||
OSErr err;
|
OSErr err;
|
||||||
|
|
||||||
|
if (addr->resolved) {
|
||||||
/* XXX only return first address */
|
/* XXX only return first address */
|
||||||
err = AddrToStr(addr->hostinfo.addr[0], mybuf);
|
err = AddrToStr(addr->hostinfo.addr[0], mybuf);
|
||||||
buf[0] = '\0';
|
buf[0] = '\0';
|
||||||
if (err != noErr)
|
if (err != noErr)
|
||||||
strncat(buf, mybuf, buflen - 1);
|
strncat(buf, mybuf, buflen - 1);
|
||||||
|
} else {
|
||||||
|
buf[0] = '\0';
|
||||||
|
strncat(buf, addr->hostname, buflen - 1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* I think "local" here really means "loopback" */
|
/* I think "local" here really means "loopback" */
|
||||||
@ -387,6 +398,7 @@ Socket sk_new(SockAddr addr, int port, int privport, int oobinline,
|
|||||||
ret->frozen_readable = 0;
|
ret->frozen_readable = 0;
|
||||||
ret->localhost_only = 0; /* unused, but best init anyway */
|
ret->localhost_only = 0; /* unused, but best init anyway */
|
||||||
ret->pending_error = 0;
|
ret->pending_error = 0;
|
||||||
|
ret->oobinline = oobinline;
|
||||||
ret->oobpending = FALSE;
|
ret->oobpending = FALSE;
|
||||||
ret->listener = 0;
|
ret->listener = 0;
|
||||||
|
|
||||||
@ -451,6 +463,11 @@ Socket sk_new(SockAddr addr, int port, int privport, int oobinline,
|
|||||||
ret->connected = TRUE;
|
ret->connected = TRUE;
|
||||||
ret->writable = TRUE;
|
ret->writable = TRUE;
|
||||||
|
|
||||||
|
/* Add this to the list of all sockets */
|
||||||
|
ret->next = mactcp.socklist;
|
||||||
|
ret->prev = &mactcp.socklist;
|
||||||
|
mactcp.socklist = ret;
|
||||||
|
|
||||||
fprintf(stderr, "Socket connected\n");
|
fprintf(stderr, "Socket connected\n");
|
||||||
return (Socket)ret;
|
return (Socket)ret;
|
||||||
}
|
}
|
||||||
@ -488,6 +505,12 @@ static void mactcp_close(Socket sock)
|
|||||||
s->err = PBControlSync((ParmBlkPtr)&pb);
|
s->err = PBControlSync((ParmBlkPtr)&pb);
|
||||||
if (s->err == noErr)
|
if (s->err == noErr)
|
||||||
sfree(pb.csParam.create.rcvBuff);
|
sfree(pb.csParam.create.rcvBuff);
|
||||||
|
|
||||||
|
/* Unhitch from list of sockets */
|
||||||
|
*s->prev = s->next;
|
||||||
|
if (s->next != NULL)
|
||||||
|
s->next->prev = s->prev;
|
||||||
|
|
||||||
sfree(s);
|
sfree(s);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -497,8 +520,6 @@ static int mactcp_write(Socket sock, char *buf, int len)
|
|||||||
wdsEntry wds[2];
|
wdsEntry wds[2];
|
||||||
TCPiopb pb;
|
TCPiopb pb;
|
||||||
|
|
||||||
fprintf(stderr, "Write data, %d bytes\n", len);
|
|
||||||
|
|
||||||
wds[0].length = len;
|
wds[0].length = len;
|
||||||
wds[0].ptr = buf;
|
wds[0].ptr = buf;
|
||||||
wds[1].length = 0;
|
wds[1].length = 0;
|
||||||
@ -521,6 +542,56 @@ static int mactcp_write_oob(Socket sock, char *buf, int len)
|
|||||||
fatalbox("mactcp_write_oob");
|
fatalbox("mactcp_write_oob");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Called from our event loop if there's work to do.
|
||||||
|
*/
|
||||||
|
void mactcp_poll(void)
|
||||||
|
{
|
||||||
|
Actual_Socket s;
|
||||||
|
TCPiopb pb;
|
||||||
|
|
||||||
|
for (s = mactcp.socklist; s != NULL; s = s->next) {
|
||||||
|
/* XXX above can't handle sockets being deleted. */
|
||||||
|
pb.ioCRefNum = mactcp.refnum;
|
||||||
|
pb.csCode = TCPStatus;
|
||||||
|
pb.tcpStream = s->s;
|
||||||
|
pb.csParam.status.userDataPtr = (Ptr)s;
|
||||||
|
s->err = PBControlSync((ParmBlkPtr)&pb);
|
||||||
|
if (s->err != noErr)
|
||||||
|
continue;
|
||||||
|
if (pb.csParam.status.amtUnreadData > 0)
|
||||||
|
mactcp_recv(s, pb.csParam.status.amtUnreadData);
|
||||||
|
/* Should check connectionState in case remote has closed */
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void mactcp_recv(Actual_Socket s, size_t len)
|
||||||
|
{
|
||||||
|
rdsEntry rds[2];
|
||||||
|
TCPiopb pb;
|
||||||
|
|
||||||
|
if (s->frozen) return;
|
||||||
|
|
||||||
|
while (len > 0) {
|
||||||
|
pb.ioCRefNum = mactcp.refnum;
|
||||||
|
pb.csCode = TCPNoCopyRcv;
|
||||||
|
pb.tcpStream = s->s;
|
||||||
|
pb.csParam.receive.commandTimeoutValue = 0;
|
||||||
|
pb.csParam.receive.rdsPtr = (Ptr)rds;
|
||||||
|
pb.csParam.receive.rdsLength = lenof(rds) - 1;
|
||||||
|
pb.csParam.receive.userDataPtr = (Ptr)s;
|
||||||
|
s->err = PBControlSync((ParmBlkPtr)&pb);
|
||||||
|
if (s->err != noErr)
|
||||||
|
return;
|
||||||
|
plug_receive(s->plug, 0, rds[0].ptr, rds[0].length);
|
||||||
|
len -= rds[0].length;
|
||||||
|
pb.csCode = TCPRcvBfrReturn;
|
||||||
|
s->err = PBControlSync((ParmBlkPtr)&pb);
|
||||||
|
if (s->err != noErr)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Each socket abstraction contains a `void *' private field in
|
* Each socket abstraction contains a `void *' private field in
|
||||||
* which the client can keep state.
|
* which the client can keep state.
|
||||||
@ -589,8 +660,11 @@ static char *mactcp_socket_error(Socket sock)
|
|||||||
|
|
||||||
static void mactcp_set_frozen(Socket sock, int is_frozen)
|
static void mactcp_set_frozen(Socket sock, int is_frozen)
|
||||||
{
|
{
|
||||||
|
Actual_Socket s = (Actual_Socket) sock;
|
||||||
|
|
||||||
fatalbox("mactcp_set_frozen");
|
if (s->frozen == is_frozen)
|
||||||
|
return;
|
||||||
|
s->frozen = is_frozen;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
Loading…
x
Reference in New Issue
Block a user