#include <oskittcp.h>
#include <oskitdebug.h>
-#include <ntddk.h>
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/socket.h>
unsigned volatile ipending;
struct timeval boottime;
+void *fbsd_malloc( unsigned int bytes, const char *file, int line, ... ) {
+ if( !OtcpEvent.TCPMalloc ) panic("no malloc");
+ return OtcpEvent.TCPMalloc
+ ( OtcpEvent.ClientData,
+ (OSK_UINT)bytes, (OSK_PCHAR)file, (OSK_UINT)line );
+}
+
+void fbsd_free( void *data, const char *file, int line, ... ) {
+ if( !OtcpEvent.TCPFree ) panic("no free");
+ OtcpEvent.TCPFree( OtcpEvent.ClientData,
+ data, (OSK_PCHAR)file, (OSK_UINT)line );
+}
+
void InitOskitTCP() {
OS_DbgPrint(OSK_MID_TRACE,("Init Called\n"));
+ OS_DbgPrint(OSK_MID_TRACE,("MB Init\n"));
+ mbinit();
+ OS_DbgPrint(OSK_MID_TRACE,("Rawip Init\n"));
+ rip_init();
+ raw_init();
+ OS_DbgPrint(OSK_MID_TRACE,("Route Init\n"));
+ route_init();
OS_DbgPrint(OSK_MID_TRACE,("Init fake freebsd scheduling\n"));
init_freebsd_sched();
OS_DbgPrint(OSK_MID_TRACE,("Init clock\n"));
void TimerOskitTCP() {
tcp_slowtimo();
+ tcp_fasttimo();
}
void RegisterOskitTCPEventHandlers( POSKITTCP_EVENT_HANDLERS EventHandlers ) {
if( OtcpEvent.PacketSend )
OS_DbgPrint(OSK_MID_TRACE,("SendPacket handler registered: %x\n",
OtcpEvent.PacketSend));
- if( OtcpEvent.Bind )
- OS_DbgPrint(OSK_MID_TRACE,("Bind handler registered: %x\n",
- OtcpEvent.Bind));
}
void OskitDumpBuffer( OSK_PCHAR Data, OSK_UINT Len ) {
for( i = 0; i < Len; i++ ) {
if( i && !(i & 0xf) ) DbgPrint( "\n" );
- if( !(i & 0xf) ) DbgPrint( "%08x: ", (UINT)(Data + i) );
+ if( !(i & 0xf) ) DbgPrint( "%08x: ", (OSK_UINT)(Data + i) );
DbgPrint( " %02x", Data[i] );
}
DbgPrint("\n");
int error = socreate(domain, &so, type, proto);
if( !error ) {
so->so_connection = context;
+ so->so_state = SS_NBIO;
*aso = so;
}
return error;
-#if 0
- register struct protosw *prp;
- register struct socket *so;
- register int error;
+}
- if (proto) {
- prp = pffindproto(domain, proto, type);
- } else {
- prp = pffindtype(domain, type);
- }
- if (prp == 0 || prp->pr_usrreq == 0) {
- return (EPROTONOSUPPORT);
- }
- if (prp->pr_type != type) {
- return (EPROTOTYPE);
+int OskitTCPRecv( void *connection,
+ OSK_PCHAR Data,
+ OSK_UINT Len,
+ OSK_UINT *OutLen,
+ OSK_UINT Flags ) {
+ struct mbuf *paddr = 0;
+ struct mbuf m, *mp;
+ struct uio uio = { 0 };
+ int error = 0;
+ int tcp_flags = 0;
+
+ if( Flags & OSK_MSG_OOB ) tcp_flags |= MSG_OOB;
+ if( Flags & OSK_MSG_DONTWAIT ) tcp_flags |= MSG_DONTWAIT;
+ if( Flags & OSK_MSG_PEEK ) tcp_flags |= MSG_PEEK;
+
+ uio.uio_resid = Len;
+ m.m_len = Len;
+ m.m_data = Data;
+ m.m_type = MT_DATA;
+ m.m_flags = M_PKTHDR | M_EOR;
+
+ mp = &m;
+
+ OS_DbgPrint(OSK_MID_TRACE,("Reading %d bytes from TCP:\n", Len));
+
+ error = soreceive( connection, &paddr, &uio, &mp, NULL /* SCM_RIGHTS */,
+ &tcp_flags );
+
+ if( error == 0 ) {
+ OS_DbgPrint(OSK_MID_TRACE,("Successful read from TCP:\n"));
+ OskitDumpBuffer( m.m_data, uio.uio_resid );
}
- MALLOC(so, struct socket *, sizeof(*so), M_SOCKET, M_WAIT);
- bzero((caddr_t)so, sizeof(*so));
- so->so_type = type;
- so->so_proto = prp;
- error =
- (*prp->pr_usrreq)(so, PRU_ATTACH,
- (struct mbuf *)0,
- (struct mbuf *)proto,
- (struct mbuf *)0);
- if (error) {
- so->so_state |= SS_NOFDREF;
- sofree(so);
- return (error);
- }
- *aso = so;
- OS_DbgPrint(OSK_MAX_TRACE,("Returning Socket %x\n", so));
- return STATUS_SUCCESS;
-#endif
-}
+ *OutLen = uio.uio_resid;
+ return error;
+}
+
static int
getsockaddr(namp, uaddr, len)
/* [<][>][^][v][top][bottom][index][help] */
return error;
}
-NTSTATUS OskitTCPConnect( PVOID socket, PVOID connection,
- PVOID nam, OSK_UINT namelen ) {
+int OskitTCPBind( void *socket, void *connection,
+ void *nam, OSK_UINT namelen ) {
+ int error = EFAULT;
+ struct socket *so = socket;
+ struct mbuf sabuf = { 0 };
+ struct sockaddr addr;
+
+ OS_DbgPrint(OSK_MID_TRACE,("Called, socket = %08x\n", socket));
+
+ if( nam )
+ addr = *((struct sockaddr *)nam);
+
+ sabuf.m_data = (void *)&addr;
+ sabuf.m_len = sizeof(addr);
+
+ addr.sa_family = addr.sa_len;
+ addr.sa_len = sizeof(struct sockaddr);
+
+ OskitDumpBuffer( (OSK_PCHAR)&addr, sizeof(addr) );
+
+ error = sobind(so, &sabuf);
+
+ OS_DbgPrint(OSK_MID_TRACE,("Ending: %08x\n", error));
+ return (error);
+}
+
+int OskitTCPConnect( void *socket, void *connection,
+ void *nam, OSK_UINT namelen ) {
struct socket *so = socket;
struct connect_args _uap = {
0, nam, namelen
goto done;
}
- s = splnet();
-
- while ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) {
- error = tsleep((caddr_t)&so->so_timeo, PSOCK | PCATCH,
- "connect", 0);
- if (error)
- break;
- }
-
- if (error == 0) {
- error = so->so_error;
- so->so_error = 0;
- }
-
- splx(s);
-
bad:
so->so_state &= ~SS_ISCONNECTING;
return (error);
}
-DWORD OskitTCPClose( VOID *socket ) {
+int OskitTCPClose( void *socket ) {
+ struct socket *so = socket;
+ so->so_connection = 0;
+ soclose( so );
+ return 0;
}
-DWORD OskitTCPSend( VOID *socket, OSK_PCHAR Data, OSK_UINT Len, int flags ) {
- OskitDumpBuffer( Data, Len );
+int OskitTCPSend( void *socket, OSK_PCHAR Data, OSK_UINT Len,
+ OSK_UINT *OutLen, OSK_UINT flags ) {
struct mbuf mb;
+ /*struct uio uio = { 0 };*/
+ int error = 0;
+ OskitDumpBuffer( Data, Len );
+ /*uio.uio_resid = Len;*/
mb.m_data = Data;
mb.m_len = Len;
- return sosend( socket, NULL, NULL, (struct mbuf *)&mb, NULL, 0 );
+ mb.m_flags = M_EOR;
+ error = sosend( socket, NULL, NULL /*&uio*/, (struct mbuf *)&mb, NULL, 0 );
+ /*printf("uio.uio_resid = %d\n", uio.uio_resid);*/
+ *OutLen = Len /*uio.uio_resid*/;
+ return error;
}
-void OskitTCPReceive( VOID *socket, PVOID AddrOut,
- OSK_PCHAR Data, OSK_UINT Len, OSK_UINT *OutLen ) {
-}
+int OskitTCPAccept( void *socket,
+ void *AddrOut,
+ OSK_UINT AddrLen,
+ OSK_UINT *OutAddrLen ) {
+ struct mbuf nam;
+ int error;
-VOID *OskitTCPAccept( VOID *socket, PVOID AddrOut ) {
+ nam.m_data = AddrOut;
+ nam.m_len = AddrLen;
+
+ return soaccept( socket, &nam );
}
+/* The story so far
+ *
+ * We have a packet. While we store the fields we want in host byte order
+ * outside the original packet, the bsd stack modifies them in place.
+ */
+
void OskitTCPReceiveDatagram( OSK_PCHAR Data, OSK_UINT Len,
OSK_UINT IpHeaderLen ) {
- struct mbuf *Ip = m_get(M_DONTWAIT, MT_DATA);
- char *NewData = malloc( Len );
+ struct mbuf *Ip = m_devget( Data, Len, 0, NULL, NULL );
+ struct ip *iph;
+
+ if( !Ip ) return; /* drop the segment */
- OS_DbgPrint(OSK_MAX_TRACE, ("OskitTCPReceiveDatagram: %d Bytes\n", Len));
+ memcpy( Ip->m_data, Data, Len );
+ Ip->m_pkthdr.len = IpHeaderLen;
- OskitDumpBuffer( Data, Len );
+ /* Do the transformations on the header that tcp_input expects */
+ iph = mtod(Ip, struct ip *);
+ NTOHS(iph->ip_len);
+ iph->ip_len -= sizeof(struct ip);
- memset( Ip, 0, sizeof( *Ip ) );
- Ip->m_len = Len;
- Ip->m_data = NewData;
- memcpy( Ip->m_data, Data, Len );
+ OS_DbgPrint(OSK_MAX_TRACE,
+ ("OskitTCPReceiveDatagram: %d (%d header) Bytes\n", Len,
+ IpHeaderLen));
+
+ OskitDumpBuffer( Data, Len );
tcp_input(Ip, IpHeaderLen);
/* The buffer Ip is freed by tcp_input */
}
-void OskitTCPBind( VOID *socket, PVOID name ) {
-}
-
-void OskitTCPListen( VOID *socket, int backlog ) {
+int OskitTCPListen( void *socket, int backlog ) {
+ return solisten( socket, backlog );
}
-void OskitTCPSetAddress( VOID *socket,
- ULONG LocalAddress,
- USHORT LocalPort,
- ULONG RemoteAddress,
- USHORT RemotePort ) {
+void OskitTCPSetAddress( void *socket,
+ OSK_UINT LocalAddress,
+ OSK_UI16 LocalPort,
+ OSK_UINT RemoteAddress,
+ OSK_UI16 RemotePort ) {
struct socket *so = socket;
struct inpcb *inp = so->so_pcb;
inp->inp_laddr.s_addr = LocalAddress;
RemoteAddress, RemotePort);
}
-void OskitTCPGetAddress( VOID *socket,
- PULONG LocalAddress,
- PUSHORT LocalPort,
- PULONG RemoteAddress,
- PUSHORT RemotePort ) {
+void OskitTCPGetAddress( void *socket,
+ OSK_UINT *LocalAddress,
+ OSK_UI16 *LocalPort,
+ OSK_UINT *RemoteAddress,
+ OSK_UI16 *RemotePort ) {
struct socket *so = socket;
struct inpcb *inp = so ? so->so_pcb : 0;
if( inp ) {
}
}
+struct ifaddr *ifa_iffind(struct sockaddr *addr, int type)
+{
+ if( OtcpEvent.FindInterface )
+ return OtcpEvent.FindInterface( OtcpEvent.ClientData,
+ PF_INET,
+ type,
+ addr );
+ else
+ return NULL;
+}
+
void oskittcp_die( const char *file, int line ) {
DbgPrint("\n\n*** OSKITTCP: Panic Called at %s:%d ***\n", file, line);
- KeBugCheck(0);
+ *((int *)0) = 0;
+}
+
+/* Stuff supporting the BSD network-interface interface */
+struct ifaddr **ifnet_addrs;
+struct ifnet *ifnet;
+
+void
+ifinit()
+{
+}
+
+
+void
+if_attach(ifp)
+ struct ifnet *ifp;
+{
+ panic("if_attach\n");
+}
+
+struct ifnet *
+ifunit(char *name)
+{
+ return 0;
}
+
+/*
+ * Handle interface watchdog timer routines. Called
+ * from softclock, we decrement timers (if set) and
+ * call the appropriate interface routine on expiration.
+ */
+void
+if_slowtimo(arg)
+ void *arg;
+{
+#if 0
+ register struct ifnet *ifp;
+ int s = splimp();
+
+ for (ifp = ifnet; ifp; ifp = ifp->if_next) {
+ if (ifp->if_timer == 0 || --ifp->if_timer)
+ continue;
+ if (ifp->if_watchdog)
+ (*ifp->if_watchdog)(ifp->if_unit);
+ }
+ splx(s);
+ timeout(if_slowtimo, (void *)0, hz / IFNET_SLOWHZ);
+#endif
+}
+
+/*
+ * Locate an interface based on a complete address.
+ */
+
+/*ARGSUSED*/
+struct ifaddr *ifa_ifwithaddr(addr)
+ struct sockaddr *addr;
+{
+ struct ifaddr *ifaddr = ifa_ifwithnet( addr );
+ struct sockaddr_in *addr_in;
+ struct sockaddr_in *faddr_in;
+
+ if( !ifaddr ) {
+ OS_DbgPrint(OSK_MID_TRACE,("No ifaddr\n"));
+ return NULL;
+ } else {
+ OS_DbgPrint(OSK_MID_TRACE,("ifaddr @ %x\n", ifaddr));
+ }
+
+ addr_in = (struct sockaddr_in *)addr;
+ faddr_in = (struct sockaddr_in *)ifaddr->ifa_addr;
+
+ if( faddr_in->sin_addr.s_addr == addr_in->sin_addr.s_addr )
+ return ifaddr;
+ else
+ return NULL;
+}
+
+/*
+ * Locate the point to point interface with a given destination address.
+ */
+/*ARGSUSED*/
+struct ifaddr *
+ifa_ifwithdstaddr(addr)
+ register struct sockaddr *addr;
+{
+ OS_DbgPrint(OSK_MID_TRACE,("Called\n"));
+ return ifa_iffind(addr, IFF_POINTOPOINT);
+}
+
+/*
+ * Find an interface on a specific network. If many, choice
+ * is most specific found.
+ */
+struct ifaddr *ifa_ifwithnet(addr)
+ struct sockaddr *addr;
+{
+ struct sockaddr_in *sin;
+ struct ifaddr *ifaddr = ifa_iffind(addr, IFF_UNICAST);
+
+ sin = (struct sockaddr *)&ifaddr->ifa_addr;
+
+ OS_DbgPrint(OSK_MID_TRACE,("ifaddr->addr = %x\n", sin->sin_addr.s_addr));
+
+ return ifaddr;
+}
+