File: SoapyRPCSocket.hpp

package info (click to toggle)
soapyremote 0.4.3-1
  • links: PTS, VCS
  • area: main
  • in suites: bullseye, buster, sid
  • size: 504 kB
  • sloc: cpp: 6,740; makefile: 13
file content (173 lines) | stat: -rw-r--r-- 4,359 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
// Copyright (c) 2015-2018 Josh Blum
// SPDX-License-Identifier: BSL-1.0

#pragma once
#include "SoapyRemoteConfig.hpp"
#include <cstddef>
#include <string>

class SockAddrData;

/*!
 * Create one instance of the session per process to use sockets.
 */
class SOAPY_REMOTE_API SoapySocketSession
{
public:
    SoapySocketSession(void);
    ~SoapySocketSession(void);
};

/*!
 * A simple socket wrapper with a TCP-like socket API.
 * The implementation may be swapped out in the future.
 */
class SOAPY_REMOTE_API SoapyRPCSocket
{
public:
    SoapyRPCSocket(void);

    /*!
     * Make the underlying socket (but does not bind or connect).
     * This function is called automatically by bind and connect,
     * however it can be used to test if a protocol is possible.
     */
    SoapyRPCSocket(const std::string &url);

    ~SoapyRPCSocket(void);

    /*!
     * Is the socket null?
     * The default constructor makes a null socket.
     * The socket is non null after bind or connect,
     * and after accept returns a successful socket.
     */
    bool null(void);

    /*!
     * Is the socket in a good state?
     * Return true for good, false for error.
     * The last error message will be set on error.
     */
    bool status(void);

    /*!
     * Explicit close the socket, also done by destructor.
     */
    int close(void);

    /*!
     * Server bind.
     * URL examples:
     * 0.0.0.0:1234
     * [::]:1234
     */
    int bind(const std::string &url);

    /*!
     * Server listen.
     */
    int listen(int backlog);

    /*!
     * Server accept connection.
     * Socket will be null on failure.
     * Caller owns the client socket.
     */
    SoapyRPCSocket *accept(void);

    /*!
     * Client connect.
     * URL examples:
     * 10.10.1.123:1234
     * [2001:db8:0:1]:1234
     * hostname:1234
     */
    int connect(const std::string &url);

    /*!
     * Connect to client with a timeout is microseconds.
     */
    int connect(const std::string &url, const long timeoutUs);

    //! set or clear non blocking on socket
    int setNonBlocking(const bool nonblock);

    /*!
     * Join a multi-cast group.
     * \param group the url for the multicast group and port number
     * \param loop specify to receive local loopback
     * \param ttl specify time to live for send packets
     * \param iface the IPv6 interface index or 0 for automatic
     */
    int multicastJoin(const std::string &group, const bool loop = true, const int ttl = 1, const int iface = 0);

    /*!
     * Send the buffer and return bytes sent or error.
     */
    int send(const void *buf, size_t len, int flags = 0);

    /*!
     * Receive into buffer and return bytes received or error.
     */
    int recv(void *buf, size_t len, int flags = 0);

    /*!
     * Send to a specific destination.
     */
    int sendto(const void *buf, size_t len, const std::string &url, int flags = 0);

    /*!
     * Receive from an unconnected socket.
     */
    int recvfrom(void *buf, size_t len, std::string &url, int flags = 0);

    /*!
     * Wait for recv to become ready with timeout.
     * Return true for ready, false for timeout.
     */
    bool selectRecv(const long timeoutUs);

    /*!
     * Query the last error message as a string.
     */
    const char *lastErrorMsg(void) const
    {
        return _lastErrorMsg.c_str();
    }

    /*!
     * Get the URL of the local socket.
     * Return an empty string on error.
     */
    std::string getsockname(void);

    /*!
     * Get the URL of the remote socket.
     * Return an empty string on error.
     */
    std::string getpeername(void);

    /*!
     * Set the socket buffer size in bytes.
     * \param isRecv true for RCVBUF, false for SNDBUF
     * \return 0 for success or negative error code.
     */
    int setBuffSize(const bool isRecv, const size_t numBytes);

    /*!
     * Get the socket buffer size in bytes.
     * \param isRecv true for RCVBUF, false for SNDBUF
     * \return the actual size set or negative error code.
     */
    int getBuffSize(const bool isRecv);

private:
    int _sock;
    std::string _lastErrorMsg;

    void reportError(const std::string &what, const std::string &errorMsg);
    void reportError(const std::string &what, const int err);
    void reportError(const std::string &what);
    void setDefaultTcpSockOpts(void);
};