#ifndef _NT_SOCKET_H_
#define _NT_SOCKET_H_
/**
* socket api:
* -----------
* here we provide native libraries and applications
* with a minimal socket abstraction layer;
* if you are interested in posix socket semantics
* then this header is REALLY NOT what you
* are looking for, as the most portable scenario
* (psxscl+libc) neither requires nor allows for
* direct interaction with the below interfaces.
*
* (additional information for the yet curious...)
*
* client libraries and applications are responsible
* for the entire bookkeeping, which should be
* easy using the nt_socket structure.
*
* kernel sockets are created using ZwCreateFile,
* and are then manipulated (bind, connect, send,
* recv, listen, accept, getsockname, etc.) using
* ZwDeviceIoControlFile. accordingly, the main
* objective of the below interfaces is to provide
* thin wrappers around the above NT system calls,
* thereby releasing you from the tedious task
* of formatting control messages according to
* individual IOCTL codes, protocol types, or
* different versions of the operating system.
*
* another noteworthy objective is the direct
* translation between posix socket semantics on the
* one hand, and the interfaces that this module
* provides on the other. functions in this module
* normally take the same arguments as their
* posix equivalents, yet require a pointer
* to an nt_socket structure in place of an integer
* file descriptor (in the posix library, the task
* of converting an integer file descriptor to the
* above pointer is a trivial one). for functions
* such as send() and recv(), the return value is
* the system's native NTSTATUS; the number of bytes
* sent or received is then returned in a separate
* argument, and can also be obtained, along with
* extended status, from the info member of the iosb
* argument. last but not least, each function in
* this module accepts one or more optional arguments
* of questionable relevance:-)
**/
#include "nt_abi.h"
#include "nt_status.h"
#include "nt_object.h"
#include "nt_tty.h"
/* afd socket domains */
#define NT_AF_UNSPEC (0x0000u)
#define NT_AF_UNIX (0x0001u)
#define NT_AF_INET (0x0002u)
#define NT_AF_IMPLINK (0x0003u)
#define NT_AF_PUP (0x0004u)
#define NT_AF_CHAOS (0x0005u)
#define NT_AF_NS (0x0006u)
#define NT_AF_IPX (0x0006u) /* synonym */
#define NT_AF_ISO (0x0007u)
#define NT_AF_OSI (0x0007u) /* synonym */
#define NT_AF_ECMA (0x0008u)
#define NT_AF_DATAKIT (0x0009u)
#define NT_AF_CCITT (0x000Au)
#define NT_AF_SNA (0x000Bu)
#define NT_AF_DECnet (0x000Cu)
#define NT_AF_DLI (0x000Du)
#define NT_AF_LAT (0x000Eu)
#define NT_AF_HYLINK (0x000Fu)
#define NT_AF_APPLETALK (0x0010u)
#define NT_AF_NETBIOS (0x0011u)
#define NT_AF_VOICEVIEW (0x0012u)
#define NT_AF_FIREFOX (0x0013u)
#define NT_AF_UNKNOWN_1ST (0x0014u)
#define NT_AF_BAN (0x0015u)
#define NT_AF_ATM (0x0016u)
#define NT_AF_INET6 (0x0017u)
#define NT_AF_CLUSTER (0x0018u)
#define NT_AF_12844 (0x0019u)
#define NT_AF_IRDA (0x001Au)
#define NT_AF_NETDES (0x001Cu)
#define NT_AF_TCNPROCESS (0x001Du)
#define NT_AF_TCNMESSAGE (0x001Eu)
#define NT_AF_ICLFXBM (0x001Fu)
#define NT_AF_BTH (0x0020u)
#define NT_AF_LINK (0x0021u)
/* afd socket types */
#define NT_SOCK_STREAM (0x0001u)
#define NT_SOCK_DGRAM (0x0002u)
#define NT_SOCK_RAW (0x0003u)
#define NT_SOCK_RDM (0x0004u)
#define NT_SOCK_SEQPACKET (0x0005u)
/* afd socket protocols */
#define NT_IPPROTO_IP 0
#define NT_IPPROTO_HOPOPTS 0
#define NT_IPPROTO_ICMP 1
#define NT_IPPROTO_IGMP 2
#define NT_IPPROTO_GGP 3
#define NT_IPPROTO_IPV4 4
#define NT_IPPROTO_ST 5
#define NT_IPPROTO_TCP 6
#define NT_IPPROTO_CBT 7
#define NT_IPPROTO_EGP 8
#define NT_IPPROTO_IGP 9
#define NT_IPPROTO_PUP 12
#define NT_IPPROTO_UDP 17
#define NT_IPPROTO_IDP 22
#define NT_IPPROTO_RDP 27
#define NT_IPPROTO_IPV6 41
#define NT_IPPROTO_ROUTING 43
#define NT_IPPROTO_FRAGMENT 44
#define NT_IPPROTO_ESP 50
#define NT_IPPROTO_AH 51
#define NT_IPPROTO_ICMPV6 58
#define NT_IPPROTO_NONE 59
#define NT_IPPROTO_DSTOPTS 60
#define NT_IPPROTO_ND 77
#define NT_IPPROTO_ICLFXBM 78
#define NT_IPPROTO_PIM 103
#define NT_IPPROTO_PGM 113
#define NT_IPPROTO_L2TP 115
#define NT_IPPROTO_SCTP 132
#define NT_IPPROTO_RAW 255
#define NT_IPPROTO_MAX 256
#define NT_IPPROTO_RESERVED_RAW 257
#define NT_IPPROTO_RESERVED_IPSEC 258
#define NT_IPPROTO_RESERVED_IPSECOFFLOAD 259
#define NT_IPPROTO_RESERVED_WNV 260
#define NT_IPPROTO_RESERVED_MAX 261
/* afd socket option levels */
#define NT_SOL_IPV6 41
#define NT_SOL_SOCKET 0xffff
/* afd socket-level socket options */
#define NT_SO_DEBUG (0x0001)
#define NT_SO_ACCEPTCONN (0x0002)
#define NT_SO_REUSEADDR (0x0004)
#define NT_SO_KEEPALIVE (0x0008)
#define NT_SO_DONTROUTE (0x0010)
#define NT_SO_BROADCAST (0x0020)
#define NT_SO_USELOOPBACK (0x0040)
#define NT_SO_LINGER (0x0080)
#define NT_SO_OOBINLINE (0x0100)
#define NT_SO_SNDBUF (0x1001)
#define NT_SO_RCVBUF (0x1002)
#define NT_SO_SNDLOWAT (0x1003)
#define NT_SO_RCVLOWAT (0x1004)
#define NT_SO_SNDTIMEO (0x1005)
#define NT_SO_RCVTIMEO (0x1006)
#define NT_SO_ERROR (0x1007)
#define NT_SO_TYPE (0x1008)
#define NT_SO_GROUP_ID (0x2001)
#define NT_SO_GROUP_PRIORITY (0x2002)
#define NT_SO_MAX_MSG_SIZE (0x2003)
/* afd ipv6 socket options */
#define NT_IPV6_HOPOPTS 1
#define NT_IPV6_HDRINCL 2
#define NT_IPV6_UNICAST_HOPS 4
#define NT_IPV6_MULTICAST_IF 9
#define NT_IPV6_MULTICAST_HOPS 10
#define NT_IPV6_MULTICAST_LOOP 11
#define NT_IPV6_ADD_MEMBERSHIP 12
#define NT_IPV6_DROP_MEMBERSHIP 13
#define NT_IPV6_DONTFRAG 14
#define NT_IPV6_PKTINFO 19
#define NT_IPV6_HOPLIMIT 21
#define NT_IPV6_PROTECTION_LEVEL 23
#define NT_IPV6_RECVIF 24
#define NT_IPV6_RECVDSTADDR 25
#define NT_IPV6_CHECKSUM 26
#define NT_IPV6_V6ONLY 27
#define NT_IPV6_IFLIST 28
#define NT_IPV6_ADD_IFLIST 29
#define NT_IPV6_DEL_IFLIST 30
#define NT_IPV6_UNICAST_IF 31
#define NT_IPV6_RTHDR 32
#define NT_IPV6_RECVRTHDR 38
#define NT_IPV6_TCLASS 39
#define NT_IPV6_RECVTCLASS 40
#define NT_IPV6_JOIN_GROUP IPV6_ADD_MEMBERSHIP
#define NT_IPV6_LEAVE_GROUP IPV6_DROP_MEMBERSHIP
/* tdi receive modes */
#define NT_TDI_RECEIVE_BROADCAST (0x0004u)
#define NT_TDI_RECEIVE_MULTICAST (0x0008u)
#define NT_TDI_RECEIVE_PARTIAL (0x0010u)
#define NT_TDI_RECEIVE_NORMAL (0x0020u)
#define NT_TDI_RECEIVE_EXPEDITED (0x0040u)
#define NT_TDI_RECEIVE_PEEK (0x0080u)
#define NT_TDI_RECEIVE_NO_RESPONSE_EXP (0x0100u)
#define NT_TDI_RECEIVE_COPY_LOOKAHEAD (0x0200u)
#define NT_TDI_RECEIVE_ENTIRE_MESSAGE (0x0400u)
#define NT_TDI_RECEIVE_AT_DISPATCH_LEVEL (0x0800u)
#define NT_TDI_RECEIVE_CONTROL_INFO (0x1000u)
#define NT_TDI_RECEIVE_FORCE_INDICATION (0x2000u)
#define NT_TDI_RECEIVE_NO_PUSH (0x4000u)
/* tdi send modes */
#define NT_TDI_SEND_EXPEDITED (0x0020u)
#define NT_TDI_SEND_PARTIAL (0x0040u)
#define NT_TDI_SEND_NO_RESPONSE_EXPECTED (0x0080u)
#define NT_TDI_SEND_NON_BLOCKING (0x0100u)
#define NT_TDI_SEND_AND_DISCONNECT (0x0200u)
/* tdi listen modes */
#define NT_TDI_QUERY_ACCEPT (0x0001u)
/* tdi disconnect modes */
#define NT_TDI_DISCONNECT_WAIT (0x0001u)
#define NT_TDI_DISCONNECT_ABORT (0x0002u)
#define NT_TDI_DISCONNECT_RELEASE (0x0004u)
/* afd ioctl codes */
#define NT_AFD_IOCTL_BIND (0x12003u)
#define NT_AFD_IOCTL_CONNECT (0x12007u)
#define NT_AFD_IOCTL_LISTEN (0x1200Bu)
#define NT_AFD_IOCTL_ACCEPT (0x1200Cu)
#define NT_AFD_IOCTL_DUPLICATE (0x12010u)
#define NT_AFD_IOCTL_SEND (0x1201Fu)
#define NT_AFD_IOCTL_UDP_SEND (0x12023u)
#define NT_AFD_IOCTL_RECV (0x12017u)
#define NT_AFD_IOCTL_UDP_RECV (0x1201bu)
#define NT_AFD_IOCTL_DISCONNECT (0x1202Bu)
#define NT_AFD_IOCTL_SELECT (0x12024u)
#define NT_AFD_IOCTL_GET_SOCK_NAME (0x1202Fu)
#define NT_AFD_IOCTL_GET_PEER_NAME (0x12033u)
#define NT_AFD_IOCTL_SET_CONTEXT (0x12047u)
#define NT_AFD_IOCTL_GET_CONTEXT (0x12043u)
#define NT_AFD_IOCTL_SET_INFO (0x1203bu)
#define NT_AFD_IOCTL_GET_INFO (0x1207bu)
#define NT_AFD_IOCTL_SOCKOPT (0x120bfu)
/* afd listen/accept bits */
#define NT_AFD_DEFER_ACCEPT (0x01u)
/* afd sockopt mode bits */
#define NT_AFD_SOCKOPT_SET (0x01u)
#define NT_AFD_SOCKOPT_GET (0x02u)
/* afd poll socket info bits */
#define NT_AFD_POLL_RECEIVE (0x01u)
#define NT_AFD_POLL_RECEIVE_EXPEDITED (0x02u)
#define NT_AFD_POLL_SEND (0x04u)
#define NT_AFD_POLL_DISCONNECT (0x08u)
#define NT_AFD_POLL_ABORT (0x10u)
#define NT_AFD_POLL_LOCAL_CLOSE (0x20u)
#define NT_AFD_POLL_CONNECT (0x40u)
#define NT_AFD_POLL_ACCEPT (0x80u)
#define NT_AFD_POLL_CONNECT_FAIL (0x100u)
/* afd socket shutdown bits */
#define NT_AFD_DISCONNECT_WR (0x01u)
#define NT_AFD_DISCONNECT_RD (0x02u)
/* afd socket share bits */
#define NT_AFD_SHARE_UNIQUE (0x00u)
#define NT_AFD_SHARE_REUSE (0x01u)
#define NT_AFD_SHARE_WILDCARD (0x02u)
#define NT_AFD_SHARE_EXCLUSIVE (0x03u)
/* socket structures */
typedef struct _nt_socket {
union {
void * hsocket;
void * hfile;
void * hpipe;
nt_pty * hpty;
};
void * hevent;
int32_t refcnt; /* reserved for client */
uint16_t fdtype; /* reserved for client */
uint16_t sctype; /* reserved for client */
uint16_t state; /* reserved for client */
uint16_t iomode; /* reserved for client */
uint32_t ctxid; /* reserved for client */
uint32_t psxflags; /* reserved for client */
uint32_t ntflags; /* sc_wait alert flags */
nt_large_integer timeout;
int32_t iostatus;
int32_t waitstatus;
union {
struct {
uint16_t domain;
uint16_t type;
uint32_t protocol;
};
void * vfd;
void * vmount;
void * hpair;
void * dirctx;
};
} nt_socket;
typedef struct _nt_scope_id{
union {
struct {
uint32_t zone : 28;
uint32_t level : 4;
};
uint32_t value;
};
} nt_scope_id;
typedef struct _nt_sockaddr_in4 {
uint16_t sa_family;
char sa_data[14];
} nt_sockaddr_in4;
typedef struct _nt_sockaddr_in6 {
uint16_t sa_family;
uint16_t sa_port;
uint32_t sa_flow;
unsigned char sa_data[16];
nt_scope_id sa_scope;
} nt_sockaddr_in6;
typedef union _nt_sockaddr {
nt_sockaddr_in4 sa_addr_in4;
nt_sockaddr_in6 sa_addr_in6;
} nt_sockaddr;
typedef struct _nt_sockaddr_reply {
uint32_t addrlen;
nt_sockaddr addr;
} nt_sockaddr_reply;
typedef struct _nt_afd_buffer {
size_t length;
char * buffer;
} nt_afd_buffer;
typedef struct _nt_afd_listen_info {
uint32_t unknown;
uint32_t backlog;
uint32_t flags;
} nt_afd_listen_info;
typedef struct _nt_afd_accept_info {
uint32_t sequence;
nt_sockaddr addr;
uint32_t legacy[2];
} nt_afd_accept_info;
typedef struct _nt_afd_duplicate_info {
uint32_t unknown;
uint32_t sequence;
void * hsocket_dedicated;
} nt_afd_duplicate_info;
typedef struct _nt_afd_send_info {
nt_afd_buffer * afd_buffer_array;
uint32_t buffer_count;
uint32_t afd_flags;
uint32_t tdi_flags;
} nt_afd_send_info;
typedef struct _nt_afd_recv_info {
nt_afd_buffer * afd_buffer_array;
uint32_t buffer_count;
uint32_t afd_flags;
uint32_t tdi_flags;
} nt_afd_recv_info;
typedef struct _nt_afd_sockopt_info {
uint32_t mode;
uint32_t level;
uint32_t optname;
uint32_t ding;
const void * optval;
size_t optlen;
} nt_afd_sockopt_info;
typedef struct _nt_afd_poll_socket_info {
void * hsocket;
uint32_t events;
int32_t status;
} nt_afd_poll_socket_info;
typedef struct _nt_afd_poll_info {
nt_timeout timeout;
uint32_t nfds;
uint32_t options;
nt_afd_poll_socket_info pollfds[];
} nt_afd_poll_info;
typedef struct _nt_afd_disconnect_info {
uint32_t shutdown_flags;
uint32_t unknown[3];
} nt_afd_disconnect_info;
/* socket functions */
typedef int32_t __cdecl ntapi_sc_socket(
__out nt_socket * hssocket,
__in int32_t domain,
__in int32_t type,
__in uint32_t protocol,
__in uint32_t desired_access __optional,
__in nt_sqos * sqos __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_bind(
__in nt_socket * hssocket,
__in const nt_sockaddr * addr,
__in uintptr_t addrlen,
__in uint32_t afdflags __optional,
__in uint32_t srvflags __optional,
__out nt_sockaddr * sockaddr __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_listen(
__in nt_socket * hssocket,
__in uint32_t backlog,
__in uint32_t afdflags __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_accept(
__in nt_socket * hssock_listen,
__in nt_sockaddr * addr,
__in uint16_t * addrlen,
__out nt_socket * hssock_dedicated,
__in uintptr_t afdflags __optional,
__in uintptr_t tdiflags __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_connect(
__in nt_socket * hssocket,
__in nt_sockaddr * addr,
__in uintptr_t addrlen,
__in uintptr_t service_flags __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_send(
__in nt_socket * hssocket,
__in const void * buffer,
__in size_t len,
__out ssize_t * bytes_sent __optional,
__in const nt_sockaddr * addr __optional,
__in size_t addrlen __optional,
__in uintptr_t afdflags __optional,
__in uintptr_t tdiflags __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_recv(
__in nt_socket * hssocket,
__in const void * buffer,
__in size_t len,
__out ssize_t * bytes_received __optional,
__in nt_sockaddr_reply * raddr __optional,
__in uintptr_t afdflags __optional,
__in uintptr_t tdiflags __optional,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_shutdown(
__in nt_socket * hssocket,
__in uint32_t afdhow,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_getsockname(
__in nt_socket * hssocket,
__in nt_sockaddr * addr,
__in uint16_t * addrlen,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_getpeername(
__in nt_socket * hssocket,
__in nt_sockaddr * addr,
__in uint16_t * addrlen,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_server_accept_connection(
__in nt_socket * hssocket,
__out nt_afd_accept_info * accept_info,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_server_duplicate_socket(
__in nt_socket * hssock_listen,
__in nt_socket * hssock_dedicated,
__in nt_afd_accept_info * accept_info,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_setsockopt(
__in nt_socket * hssocket,
__in int32_t level,
__in int32_t optname,
__in const void * optval,
__in uint32_t optlen,
__out nt_io_status_block * iosb __optional);
typedef int32_t __cdecl ntapi_sc_getsockopt(
__in nt_socket * hssocket,
__in int32_t level,
__in int32_t optname,
__out void * optval,
__in uint32_t optlen,
__out nt_io_status_block * iosb);
typedef int32_t __cdecl ntapi_sc_wait(nt_socket * hssocket, nt_iosb * iosb, nt_timeout * timeout);
#endif