UDP address classes for Windows
Stefan Schuermans

Stefan Schuermans commited on 2017-10-08 20:02:30
Showing 6 changed files, with 546 additions and 0 deletions.

... ...
@@ -0,0 +1,77 @@
1
+/*
2
+implementations in this file are taken from
3
+https://github.com/pkulchenko/luasocket/blob/5a58786a39bbef7ed4805821cc921f1d40f12068/src/inet.c
4
+
5
+LuaSocket 2.1 license
6
+Copyright © 2004-2012 Diego Nehab
7
+
8
+Permission is hereby granted, free of charge, to any person obtaining a
9
+copy of this software and associated documentation files (the "Software"),
10
+to deal in the Software without restriction, including without limitation
11
+the rights to use, copy, modify, merge, publish, distribute, sublicense,
12
+and/or sell copies of the Software, and to permit persons to whom the
13
+Software is furnished to do so, subject to the following conditions:
14
+
15
+The above copyright notice and this permission notice shall be included in
16
+all copies or substantial portions of the Software.
17
+
18
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21
+AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22
+LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
23
+FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
24
+DEALINGS IN THE SOFTWARE.
25
+*/
26
+
27
+#include <winsock2.h>
28
+#include <windows.h>
29
+#include <ws2tcpip.h>
30
+
31
+#include "InetTools.h"
32
+
33
+#define NS_INT16SZ 2
34
+#define NS_INADDRSZ 4
35
+#define NS_IN6ADDRSZ 16
36
+
37
+namespace Blinker {
38
+
39
+const char *inet_ntop(int af, const void *src, char *dst, socklen_t cnt)
40
+{
41
+  if (af == AF_INET) {
42
+    struct sockaddr_in in;
43
+    memset(&in, 0, sizeof(in));
44
+    in.sin_family = AF_INET;
45
+    memcpy(&in.sin_addr, src, sizeof(struct in_addr));
46
+    getnameinfo((struct sockaddr *)&in, sizeof(struct sockaddr_in), dst, cnt, NULL, 0, NI_NUMERICHOST);
47
+    return dst;
48
+  } else if (af == AF_INET6) {
49
+    struct sockaddr_in6 in;
50
+    memset(&in, 0, sizeof(in));
51
+    in.sin6_family = AF_INET6;
52
+    memcpy(&in.sin6_addr, src, sizeof(struct in_addr6));
53
+    getnameinfo((struct sockaddr *)&in, sizeof(struct sockaddr_in6), dst, cnt, NULL, 0, NI_NUMERICHOST);
54
+    return dst;
55
+  }
56
+  return NULL;
57
+}
58
+
59
+int inet_pton(int af, const char *src, void *dst)
60
+{
61
+  struct addrinfo hints, *res, *ressave;
62
+  memset(&hints, 0, sizeof(struct addrinfo));
63
+  hints.ai_family = af;
64
+  if (getaddrinfo(src, NULL, &hints, &res) != 0) {
65
+    return -1;
66
+  }
67
+  ressave = res;
68
+  while (res) {
69
+    memcpy(dst, res->ai_addr, res->ai_addrlen);
70
+    res = res->ai_next;
71
+  }
72
+  freeaddrinfo(ressave);
73
+  return 0;
74
+}
75
+
76
+} // namespace Blinker
77
+
... ...
@@ -0,0 +1,21 @@
1
+/* Blinker
2
+   Copyright 2011-2014 Stefan Schuermans <stefan@blinkenarea.org>
3
+   Copyleft GNU public license - http://www.gnu.org/copyleft/gpl.html
4
+   a blinkenarea.org project */
5
+
6
+#ifndef INETTOOLS_H
7
+#define INTETOOLS_H
8
+
9
+#include <winsock2.h>
10
+#include <windows.h>
11
+#include <ws2tcpip.h>
12
+
13
+namespace Blinker {
14
+
15
+const char * inet_ntop(int af, const void *src, char *dst, socklen_t cnt);
16
+int inet_pton(int af, const char *src, void *dst);
17
+
18
+} // namespace Blinker
19
+
20
+#endif // #ifndef INETTOOLS_H
21
+
... ...
@@ -0,0 +1,150 @@
1
+/* Blinker
2
+   Copyright 2011-2014 Stefan Schuermans <stefan@blinkenarea.org>
3
+   Copyleft GNU public license - http://www.gnu.org/copyleft/gpl.html
4
+   a blinkenarea.org project */
5
+
6
+#include <winsock2.h>
7
+#include <windows.h>
8
+
9
+#include <sstream>
10
+#include <stdlib.h>
11
+#include <string>
12
+
13
+#include "InetTools.h"
14
+#include "Udp4Addr.h"
15
+
16
+namespace Blinker {
17
+
18
+/// constructor
19
+Udp4Addr::Udp4Addr()
20
+{
21
+  m_addr.sin_family = AF_INET;
22
+  m_addr.sin_port = htons(0);
23
+  m_addr.sin_addr.s_addr = htonl(INADDR_NONE);
24
+}
25
+
26
+/// virtual destructor
27
+Udp4Addr::~Udp4Addr()
28
+{
29
+}
30
+
31
+/// comparison
32
+//@{
33
+
34
+int Udp4Addr::compare(const Udp4Addr &that) const
35
+{
36
+  if (m_addr.sin_family < that.m_addr.sin_family)
37
+    return -1;
38
+  if (m_addr.sin_family > that.m_addr.sin_family)
39
+    return 1;
40
+  if (ntohl(m_addr.sin_addr.s_addr) < ntohl(that.m_addr.sin_addr.s_addr))
41
+    return -1;
42
+  if (ntohl(m_addr.sin_addr.s_addr) > ntohl(that.m_addr.sin_addr.s_addr))
43
+    return 1;
44
+  if (ntohs(m_addr.sin_port) < ntohs(that.m_addr.sin_port))
45
+    return -1;
46
+  if (ntohs(m_addr.sin_port) > ntohs(that.m_addr.sin_port))
47
+    return 1;
48
+  return 0;
49
+}
50
+
51
+bool Udp4Addr::operator==(const Udp4Addr &that) const
52
+{
53
+  return compare(that) == 0;
54
+}
55
+
56
+bool Udp4Addr::operator!=(const Udp4Addr &that) const
57
+{
58
+  return compare(that) != 0;
59
+}
60
+
61
+bool Udp4Addr::operator<(const Udp4Addr &that) const
62
+{
63
+  return compare(that) < 0;
64
+}
65
+
66
+bool Udp4Addr::operator>(const Udp4Addr &that) const
67
+{
68
+  return compare(that) > 0;
69
+}
70
+
71
+bool Udp4Addr::operator<=(const Udp4Addr &that) const
72
+{
73
+  return compare(that) <= 0;
74
+}
75
+
76
+bool Udp4Addr::operator>=(const Udp4Addr &that) const
77
+{
78
+  return compare(that) >= 0;
79
+}
80
+
81
+//@}
82
+
83
+/// return address family
84
+int Udp4Addr::getFamily() const
85
+{
86
+  return AF_INET;
87
+}
88
+
89
+/// return port (use this function only if absolutely necessary)
90
+int Udp4Addr::getPort() const
91
+{
92
+  return ntohs(m_addr.sin_port);
93
+}
94
+
95
+/// set port (use this function only if absolutely necessary)
96
+void Udp4Addr::setPort(int port)
97
+{
98
+  m_addr.sin_port = htons(port);
99
+}
100
+
101
+/**
102
+ * @brief parse from string format
103
+ * @param[in] str string format
104
+ * @return if parsing was successful
105
+ */
106
+bool Udp4Addr::fromStr(const std::string &str)
107
+{
108
+  std::string::size_type posColon;
109
+  std::string strIp, strPort;
110
+  struct in_addr iaIp;
111
+  unsigned long iPort;
112
+  const char *szPort;
113
+  char *szPortEnd;
114
+
115
+  // split address into IP and port
116
+  posColon = str.find(':');
117
+  if (posColon == std::string::npos)
118
+    return false;
119
+  strIp = str.substr(0, posColon);
120
+  strPort = str.substr(posColon + 1);
121
+
122
+  // parse IP
123
+  if (!inet_pton(AF_INET, strIp.c_str(), &iaIp))
124
+    return false;
125
+
126
+  // parse port
127
+  szPort = strPort.c_str();
128
+  iPort = strtoul(szPort, &szPortEnd, 10);
129
+  if (*szPort == 0 || *szPortEnd != 0)
130
+    return false;
131
+
132
+  m_addr.sin_family = AF_INET;
133
+  m_addr.sin_port = htons(iPort);
134
+  m_addr.sin_addr = iaIp;
135
+  return true;
136
+}
137
+
138
+/**
139
+ * @brief convert to string format
140
+ * @return string format
141
+ */
142
+std::string Udp4Addr::toStr() const
143
+{
144
+  std::stringstream strm;
145
+  strm << inet_ntoa(m_addr.sin_addr) << ":" << ntohs(m_addr.sin_port);
146
+  return strm.str();
147
+}
148
+
149
+} // namespace Blinker
150
+
... ...
@@ -0,0 +1,70 @@
1
+/* Blinker
2
+   Copyright 2011-2014 Stefan Schuermans <stefan@blinkenarea.org>
3
+   Copyleft GNU public license - http://www.gnu.org/copyleft/gpl.html
4
+   a blinkenarea.org project */
5
+
6
+#ifndef UDP4ADDR_H
7
+#define UDP4ADDR_H
8
+
9
+#include <winsock2.h>
10
+#include <windows.h>
11
+
12
+#include <string>
13
+
14
+#include "Addr.h"
15
+
16
+namespace Blinker {
17
+
18
+/// UDP v4 address
19
+class Udp4Addr: public Addr
20
+{
21
+public:
22
+  /// constructor
23
+  Udp4Addr();
24
+
25
+  /// virtual destructor
26
+  virtual ~Udp4Addr();
27
+
28
+public:
29
+  /// comparison
30
+  //@{
31
+  int compare(const Udp4Addr &that) const;
32
+  bool operator==(const Udp4Addr &that) const;
33
+  bool operator!=(const Udp4Addr &that) const;
34
+  bool operator<(const Udp4Addr &that) const;
35
+  bool operator>(const Udp4Addr &that) const;
36
+  bool operator<=(const Udp4Addr &that) const;
37
+  bool operator>=(const Udp4Addr &that) const;
38
+  //@}
39
+
40
+  /// return address family
41
+  virtual int getFamily() const;
42
+
43
+  /// return port (use this function only if absolutely necessary)
44
+  virtual int getPort() const;
45
+
46
+  /// set port (use this function only if absolutely necessary)
47
+  virtual void setPort(int port);
48
+
49
+  /**
50
+   * @brief parse from string format
51
+   * @param[in] str string format
52
+   * @return if parsing was successful
53
+   */
54
+  virtual bool fromStr(const std::string &str);
55
+
56
+  /**
57
+   * @brief convert to string format
58
+   * @return string format
59
+   */
60
+  virtual std::string toStr() const;
61
+protected:
62
+  struct sockaddr_in m_addr;
63
+
64
+friend class Udp4Sock;
65
+}; // class Udp4Addr
66
+
67
+} // namespace Blinker
68
+
69
+#endif // #ifndef UDP4ADDR_H
70
+
... ...
@@ -0,0 +1,157 @@
1
+/* Blinker
2
+   Copyright 2011-2014 Stefan Schuermans <stefan@blinkenarea.org>
3
+   Copyleft GNU public license - http://www.gnu.org/copyleft/gpl.html
4
+   a blinkenarea.org project */
5
+
6
+#include <winsock2.h>
7
+#include <windows.h>
8
+#include <ws2tcpip.h>
9
+
10
+#include <sstream>
11
+#include <stdlib.h>
12
+#include <string>
13
+#include <string.h>
14
+
15
+#include "InetTools.h"
16
+#include "Udp6Addr.h"
17
+
18
+namespace Blinker {
19
+
20
+/// constructor
21
+Udp6Addr::Udp6Addr()
22
+{
23
+  m_addr.sin6_family = AF_INET6;
24
+  m_addr.sin6_port = htons(0);
25
+  inet_pton(AF_INET6, "::", &m_addr.sin6_addr);
26
+}
27
+
28
+/// virtual destructor
29
+Udp6Addr::~Udp6Addr()
30
+{
31
+}
32
+
33
+/// comparison
34
+//@{
35
+
36
+int Udp6Addr::compare(const Udp6Addr &that) const
37
+{
38
+  if (m_addr.sin6_family < that.m_addr.sin6_family)
39
+    return -1;
40
+  if (m_addr.sin6_family > that.m_addr.sin6_family)
41
+    return 1;
42
+  int cmp = memcmp(&m_addr.sin6_addr, &that.m_addr.sin6_addr,
43
+                   sizeof(m_addr.sin6_addr));
44
+  if (cmp != 0)
45
+    return cmp;
46
+  if (ntohs(m_addr.sin6_port) < ntohs(that.m_addr.sin6_port))
47
+    return -1;
48
+  if (ntohs(m_addr.sin6_port) > ntohs(that.m_addr.sin6_port))
49
+    return 1;
50
+  return 0;
51
+}
52
+
53
+bool Udp6Addr::operator==(const Udp6Addr &that) const
54
+{
55
+  return compare(that) == 0;
56
+}
57
+
58
+bool Udp6Addr::operator!=(const Udp6Addr &that) const
59
+{
60
+  return compare(that) != 0;
61
+}
62
+
63
+bool Udp6Addr::operator<(const Udp6Addr &that) const
64
+{
65
+  return compare(that) < 0;
66
+}
67
+
68
+bool Udp6Addr::operator>(const Udp6Addr &that) const
69
+{
70
+  return compare(that) > 0;
71
+}
72
+
73
+bool Udp6Addr::operator<=(const Udp6Addr &that) const
74
+{
75
+  return compare(that) <= 0;
76
+}
77
+
78
+bool Udp6Addr::operator>=(const Udp6Addr &that) const
79
+{
80
+  return compare(that) >= 0;
81
+}
82
+
83
+//@}
84
+
85
+/// return address family
86
+int Udp6Addr::getFamily() const
87
+{
88
+  return AF_INET6;
89
+}
90
+
91
+/// return port (use this function only if absolutely necessary)
92
+int Udp6Addr::getPort() const
93
+{
94
+  return ntohs(m_addr.sin6_port);
95
+}
96
+
97
+/// set port (use this function only if absolutely necessary)
98
+void Udp6Addr::setPort(int port)
99
+{
100
+  m_addr.sin6_port = htons(port);
101
+}
102
+
103
+/**
104
+ * @brief parse from string format
105
+ * @param[in] str string format
106
+ * @return if parsing was successful
107
+ */
108
+bool Udp6Addr::fromStr(const std::string &str)
109
+{
110
+  std::string::size_type posBraceColon;
111
+  std::string strIp, strPort;
112
+  struct in6_addr iaIp;
113
+  unsigned long iPort;
114
+  const char *szPort;
115
+  char *szPortEnd;
116
+
117
+  // split address into IP and port
118
+  if (str.length() < 1 || str.at(0) != '[')
119
+    return false;
120
+  posBraceColon = str.find("]:");
121
+  if (posBraceColon == std::string::npos)
122
+    return false;
123
+  strIp = str.substr(1, posBraceColon - 1);
124
+  strPort = str.substr(posBraceColon + 2);
125
+
126
+  // parse IP
127
+  if (!inet_pton(AF_INET6, strIp.c_str(), &iaIp))
128
+    return false;
129
+
130
+  // parse port
131
+  szPort = strPort.c_str();
132
+  iPort = strtoul(szPort, &szPortEnd, 10);
133
+  if (*szPort == 0 || *szPortEnd != 0)
134
+    return false;
135
+
136
+  m_addr.sin6_family = AF_INET6;
137
+  m_addr.sin6_port = htons(iPort);
138
+  m_addr.sin6_addr = iaIp;
139
+  return true;
140
+}
141
+
142
+/**
143
+ * @brief convert to string format
144
+ * @return string format
145
+ */
146
+std::string Udp6Addr::toStr() const
147
+{
148
+  std::stringstream strm;
149
+  char buf[INET6_ADDRSTRLEN];
150
+  strm << "["
151
+       << inet_ntop(AF_INET6, &m_addr.sin6_addr, buf, INET6_ADDRSTRLEN)
152
+       << "]:" << ntohs(m_addr.sin6_port);
153
+  return strm.str();
154
+}
155
+
156
+} // namespace Blinker
157
+
... ...
@@ -0,0 +1,71 @@
1
+/* Blinker
2
+   Copyright 2011-2014 Stefan Schuermans <stefan@blinkenarea.org>
3
+   Copyleft GNU public license - http://www.gnu.org/copyleft/gpl.html
4
+   a blinkenarea.org project */
5
+
6
+#ifndef UDP6ADDR_H
7
+#define UDP6ADDR_H
8
+
9
+#include <winsock2.h>
10
+#include <windows.h>
11
+#include <ws2tcpip.h>
12
+
13
+#include <string>
14
+
15
+#include "Addr.h"
16
+
17
+namespace Blinker {
18
+
19
+/// UDP v6 address
20
+class Udp6Addr: public Addr
21
+{
22
+public:
23
+  /// constructor
24
+  Udp6Addr();
25
+
26
+  /// virtual destructor
27
+  virtual ~Udp6Addr();
28
+
29
+public:
30
+  /// comparison
31
+  //@{
32
+  int compare(const Udp6Addr &that) const;
33
+  bool operator==(const Udp6Addr &that) const;
34
+  bool operator!=(const Udp6Addr &that) const;
35
+  bool operator<(const Udp6Addr &that) const;
36
+  bool operator>(const Udp6Addr &that) const;
37
+  bool operator<=(const Udp6Addr &that) const;
38
+  bool operator>=(const Udp6Addr &that) const;
39
+  //@}
40
+
41
+  /// return address family
42
+  virtual int getFamily() const;
43
+
44
+  /// return port (use this function only if absolutely necessary)
45
+  virtual int getPort() const;
46
+
47
+  /// set port (use this function only if absolutely necessary)
48
+  virtual void setPort(int port);
49
+
50
+  /**
51
+   * @brief parse from string format
52
+   * @param[in] str string format
53
+   * @return if parsing was successful
54
+   */
55
+  virtual bool fromStr(const std::string &str);
56
+
57
+  /**
58
+   * @brief convert to string format
59
+   * @return string format
60
+   */
61
+  virtual std::string toStr() const;
62
+protected:
63
+  struct sockaddr_in6 m_addr;
64
+
65
+friend class Udp6Sock;
66
+}; // class Udp6Addr
67
+
68
+} // namespace Blinker
69
+
70
+#endif // #ifndef UDP6ADDR_H
71
+
0 72