/* Web Polygraph http://www.web-polygraph.org/ * (C) 2003-2006 The Measurement Factory * Licensed under the Apache License, Version 2.0 */ #ifndef POLYGRAPH__XSTD_SOCKET_H #define POLYGRAPH__XSTD_SOCKET_H #include "xstd/h/sys/socket.h" #include "xstd/Error.h" #include "xstd/Time.h" #include "xstd/Size.h" #include "xstd/NetAddr.h" #include "xstd/Array.h" class InetIfAliasReq; class Inet6IfAliasReq; struct ifconf; // socket option holder class SockOpt { public: SockOpt(): nagle(0) {} public: Time linger; // linger delay int nagle; // 3-way bool /* more to come */ }; // socket wrapper class Socket { public: static void Configure(); static void Clean(); static int Level() { return TheLevel; } static void TooManyFiles(); static bool IsEnabled; // bind,connect,listen,read,write calls are enabled static int TheMaxLevel; // will not allow Level to go higher public: Socket(): theFD(-1) {} Socket(int aFD): theFD(aFD) {} ~Socket() {} bool create(int family); bool create(int domain, int type, int protocol); bool connect(const NetAddr &addr); bool bind(const NetAddr &addr); bool listen(); Socket accept(struct sockaddr *addr, socklen_t *addr_len); Socket accept(NetAddr &addr); Size read(void *buf, Size sz); Size write(const void *buf, Size sz); Size recvFrom(void *buf, Size sz, NetAddr &addr, int flags = 0); Size sendTo(const void *buf, Size sz, const NetAddr &addr, int flags = 0); bool close(); bool reuseAddr(bool set); bool reusePort(bool set); bool linger(Time delay); bool blocking(bool set); bool tcpDelay(bool set); bool sendBuf(Size size); bool recvBuf(Size size); /* ioctl wrappers */ bool getIfConf(struct ifconf &cfg); bool getV4IfAddr(const String &ifname, InAddress &addr); bool getV6IfAddr(const String &ifname, InAddress &addr); bool getIfBcastAddr(const String &ifname, struct sockaddr &addr); bool addV4IfAddr(const InetIfAliasReq &req, int idx = -1); bool addV6IfAddr(const Inet6IfAliasReq &req, int idx = -1); bool delIfAddr(const InetIfAliasReq &req, int idx = -1); bool configure(const SockOpt &opt); int fd() const { return theFD; } bool isOpen() const { return theFD >= 0; } bool isBlocking() const; int flags() const; int lport() const; int rport() const; Time rcvTimeout() const; Size sendBuf() const; Size recvBuf() const; Error error() const; bool peerAddr(struct sockaddr *addr, socklen_t &len) const; NetAddr peerAddr() const; NetAddr localAddr() const; operator void*() const { return theFD >= 0 ? (void*)-1 : (void*)0; } // always treat two these methods as protected! bool setOpt(int level, int optName, const void *optVal, socklen_t optLen); bool getOpt(int level, int optName, void *optVal, socklen_t *optLen) const; protected: bool noteNewFD(); bool setOpt(int optName, bool set); bool setOpt(int optName, const void *optVal, socklen_t optLen); bool getOpt(int optName, void *optVal, socklen_t *optLen) const; Size sysRead(void *buf, Size sz); Size sysWrite(const void *buf, Size sz); bool sysClose(); bool numberedIface(InetIfAliasReq &r, int idx) const; bool unsupOpt(void *dummy = 0) const; protected: int theFD; static int TheLevel; // number of open sockets }; #endif