Commit d6c7bb58 authored by jan.koester's avatar jan.koester
Browse files

succes

parent 7c62c6ad
Loading
Loading
Loading
Loading
+4 −0
Original line number Diff line number Diff line
@@ -10,6 +10,8 @@ list(APPEND netplussrc
    crypto/rc4.cpp
    crypto/rsa.cpp
    crypto/x509.cpp
    crypto/ecc_u256.cpp
    crypto/ecc_p256.cpp
)

if(${CMAKE_HOST_SYSTEM_NAME} STREQUAL "Windows")
@@ -53,6 +55,8 @@ set(headers
    crypto/rc4.h
    crypto/rsa.h
    crypto/x509.h
    crypto/ecc_u256.h
    crypto/ecc_p256.h
)

add_library(netplus SHARED ${netplussrc} ${headers})
+14 −4
Original line number Diff line number Diff line
@@ -69,10 +69,14 @@ void netplus::socket::close() {
}

void socket::setFlag(int flag, int value) {
    int sockopts = ::fcntl(_Socket, F_GETFL, 0);
    int sockopts;
    do {
        sockopts = ::fcntl(_Socket, F_GETFL, 0);
    } while (sockopts < 0 && errno == EINTR);

    if (sockopts < 0) {
        NetException e;
        e[NetException::Error] << "fcntl(F_GETFL) failed";
        e[NetException::Error] << "fcntl(F_GETFL) failed: " << strerror(errno);
        throw e;
    }

@@ -81,13 +85,19 @@ void socket::setFlag(int flag, int value) {
    else
        sockopts &= ~flag;

    if (::fcntl(_Socket, F_SETFL, sockopts) < 0) {
    int r;
    do {
        r = ::fcntl(_Socket, F_SETFL, sockopts);
    } while (r < 0 && errno == EINTR);

    if (r < 0) {
        NetException e;
        e[NetException::Error] << "fcntl(F_SETFL) failed";
        e[NetException::Error] << "fcntl(F_SETFL) failed: " << strerror(errno);
        throw e;
    }
}


void socket::setTimeout(int msec) {
    timeval timeout{};
    timeout.tv_sec  = msec / 1000;
+56 −22
Original line number Diff line number Diff line
@@ -159,6 +159,10 @@ void tcp::setNonBlock() {
    setFlag(O_NONBLOCK, 1);
}

void tcp::setBlock() {
    setFlag(O_NONBLOCK, 0);
}

int tcp::getMaxconnections() {
    return _Maxconnections;
}
@@ -210,8 +214,12 @@ size_t tcp::recvData(buffer& data, int flags) {
        data.size = (size_t)r;
        return (size_t)r;
    }
    if (r == 0)
        return 0;

    if (r == 0) {
        NetException e;
        e[NetException::Error] << "tcp::recvData peer closed (EOF)";
        throw e;
    }

    if (errno == EAGAIN || errno == EWOULDBLOCK) {
        NetException e;
@@ -247,55 +255,81 @@ void netplus::tcp::connect(const std::string& addr, int port, bool nonblock)

    for (addrinfo* rp = result; rp; rp = rp->ai_next) {

        // socket erstellen, falls noch keiner existiert oder family mismatch
        // -------------------------------------------------------
        // 1) ensure socket exists and matches family
        // -------------------------------------------------------
        if (_Socket >= 0) {
            // if family mismatch, close and recreate
            sockaddr_storage tmp{};
            socklen_t tmpLen = sizeof(tmp);
            if (::getsockname(_Socket, (sockaddr*)&tmp, &tmpLen) == 0) {
                if (tmp.ss_family != rp->ai_family) {
                    ::close(_Socket);
                    _Socket = -1;
                }
            }
        }

        if (_Socket < 0) {
            _Socket = ::socket(rp->ai_family, rp->ai_socktype, rp->ai_protocol);
            if (_Socket < 0)
                continue;
        }

        if (nonblock)
        // -------------------------------------------------------
        // 2) set nonblock BEFORE connect() if requested
        // -------------------------------------------------------
        if (nonblock) {
            try {
                setNonBlock();
            } catch (...) {
                ::close(_Socket);
                _Socket = -1;
                continue;
            }
        }

        // optional: SO_REUSEADDR (bei client meistens egal aber ok)
        int opt = 1;
        ::setsockopt(_Socket, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt));

        // connect
        // -------------------------------------------------------
        // 3) connect()
        // -------------------------------------------------------
        if (::connect(_Socket, rp->ai_addr, rp->ai_addrlen) == 0) {
            // ✅ sofort verbunden
            copyAddrInfo(&_SocketInfo, reinterpret_cast<ULONG_PTR>(rp), sizeof(addrinfo));
            _SocketInfoLen = rp->ai_addrlen;
            // ✅ connected immediately
            setAddrFromAI(rp);

            ::freeaddrinfo(result);
            return;
        }

        // nonblocking connect -> EINPROGRESS ist ok
        if (nonblock && errno == EINPROGRESS) {
            copyAddrInfo(&_SocketInfo, reinterpret_cast<ULONG_PTR>(rp), sizeof(addrinfo));
            _SocketInfoLen = rp->ai_addrlen;
        // -------------------------------------------------------
        // 4) nonblocking in progress
        // -------------------------------------------------------
        if (nonblock && (errno == EINPROGRESS || errno == EWOULDBLOCK)) {
            setAddrFromAI(rp);

            ::freeaddrinfo(result);

            NetException n;
            n[NetException::Note] << "tcp::connect: EINPROGRESS";
            throw n; // du wartest auf EPOLLOUT
            throw n; // caller waits EPOLLOUT/select
        }

        // echter Fehler
        // -------------------------------------------------------
        // 5) fatal error -> try next addrinfo
        // -------------------------------------------------------
        ::close(_Socket);
        _Socket = -1;
    }

    ::freeaddrinfo(result);

    exception[NetException::Error] << "tcp::connect: could not connect to "
    exception[NetException::Error]
        << "tcp::connect: could not connect to "
        << addr << ":" << port
        << " (" << strerror(errno) << ")";
    throw exception;
}


void tcp::getAddress(std::string& addr) {
    char buf[INET6_ADDRSTRLEN]{};

+4 −0
Original line number Diff line number Diff line
@@ -151,6 +151,10 @@ void udp::setNonBlock() {
    setFlag(O_NONBLOCK, 1);
}

void udp::setBlock() {
    setFlag(O_NONBLOCK, 0);
}

int udp::getMaxconnections() {
    return _Maxconnections;
}
+23 −4
Original line number Diff line number Diff line
@@ -158,6 +158,7 @@ namespace netplus {

		virtual void accept(std::unique_ptr<socket>& csock,bool nonblock) = 0;
		virtual void handshake_after_accept(){};
		virtual void  handshake_after_connect(){};

#ifdef Windows
		virtual void accept(LPFN_ACCEPTEX lpfnAcceptEx, std::unique_ptr<socket>& csock, buffer& data) = 0;
@@ -170,6 +171,7 @@ namespace netplus {
		virtual void bind() = 0;
		virtual void listen() = 0;
		virtual void setNonBlock() = 0;
		virtual void setBlock()=0;

		virtual int getMaxconnections() = 0;

@@ -248,6 +250,7 @@ namespace netplus {
		void bind() override;
		void listen() override;
		void setNonBlock() override;
		void setBlock() override;
		netplus::tcp& operator=(SOCKET sock) override;

		int getMaxconnections() override;
@@ -286,6 +289,7 @@ namespace netplus {
		void bind() override;
		void listen() override;
		void setNonBlock() override;
		void setBlock() override;

		udp& operator=(SOCKET socket) override;
		int getMaxconnections() override;
@@ -315,6 +319,7 @@ namespace netplus {

		void accept(std::unique_ptr<socket>& csock,bool nonblock) override;
		void handshake_after_accept() override;
		void handshake_after_connect() override;
		void connect(const std::string& addr, int port, bool nonblock = false) override;
		void close() override;

@@ -345,7 +350,6 @@ namespace netplus {
		void flush_out() override;

		std::vector<uint8_t> readTlsRecordAsync();
		std::vector<uint8_t> readHandshakeMessageAsync();

		void resetTLS();

@@ -414,7 +418,7 @@ namespace netplus {
		netplus::x509cert _peer_cert;
		std::shared_ptr<netplus::x509cert> _cert;
		netplus::rsa _rsa;

		std::string _hostname;
		bool     _secure_reneg = true;
		uint16_t _chosenSuite = 0x002F;
		bool     _ccs_received = false;
@@ -453,16 +457,30 @@ namespace netplus {

		bool _client_offered_tls13 = false;

		void _queueClientHello();

		enum class HsState {
			// server
			READ_CLIENT_HELLO,
			SEND_SERVER_FLIGHT,
			WAIT_CKE,
			WAIT_CCS,
			WAIT_FIN,
			SEND_CCS_FIN,

			// client
			CLI_FLUSH_CH,
			CLI_WAIT_SERVER_HELLO,
			CLI_WAIT_CERT,
			CLI_WAIT_SHD,
			CLI_SEND_CKE,
			CLI_SEND_CCS_FIN,
			CLI_WAIT_SCCS,
			CLI_WAIT_SFIN,

			DONE,
			FAIL,
			IDLE,
			READ_CLIENT_HELLO
			IDLE
		};

		HsState _hs_state = HsState::READ_CLIENT_HELLO;
@@ -471,6 +489,7 @@ namespace netplus {
		std::vector<uint8_t> _handshake_transcript;

		bool _handshakeDone;
		bool _is_server = true;

		friend class poll;
		friend class event;
Loading