Преглед изворни кода

Fix socket-api byte order issue when host/network order are the same (#1327)

Fix socket-api byte order issue for systems where host byte order
and network byte order are the same:
- Document data structures used for storing IP addresses
- Fix bug in bind and connect methods by updating code in wasi_socket_ext
Marcin Kolny пре 3 година
родитељ
комит
08fd714551

+ 17 - 3
core/iwasm/libraries/lib-socket/inc/wasi_socket_ext.h

@@ -20,7 +20,12 @@ typedef uint16_t __wasi_ip_port_t;
 
 
 typedef enum { IPv4 = 0, IPv6 } __wasi_addr_type_t;
 typedef enum { IPv4 = 0, IPv6 } __wasi_addr_type_t;
 
 
-/* n0.n1.n2.n3 */
+/*
+ n0.n1.n2.n3
+ Example:
+  IP Address: 127.0.0.1
+  Structure: {n0: 127, n1: 0, n2: 0, n3: 1}
+*/
 typedef struct __wasi_addr_ip4_t {
 typedef struct __wasi_addr_ip4_t {
     uint8_t n0;
     uint8_t n0;
     uint8_t n1;
     uint8_t n1;
@@ -30,9 +35,18 @@ typedef struct __wasi_addr_ip4_t {
 
 
 typedef struct __wasi_addr_ip4_port_t {
 typedef struct __wasi_addr_ip4_port_t {
     __wasi_addr_ip4_t addr;
     __wasi_addr_ip4_t addr;
-    __wasi_ip_port_t port;
+    __wasi_ip_port_t port; /* host byte order */
 } __wasi_addr_ip4_port_t;
 } __wasi_addr_ip4_port_t;
 
 
+/*
+ n0:n1:n2:n3:h0:h1:h2:h3, each 16bit value uses host byte order
+ Example (little-endian system)
+  IP Address fe80::3ba2:893b:4be0:e3dd
+  Structure: {
+    n0: 0xfe80, n1:0x0, n2: 0x0, n3: 0x0,
+    h0: 0x3ba2, h1: 0x893b, h2: 0x4be0, h3: 0xe3dd
+  }
+*/
 typedef struct __wasi_addr_ip6_t {
 typedef struct __wasi_addr_ip6_t {
     uint16_t n0;
     uint16_t n0;
     uint16_t n1;
     uint16_t n1;
@@ -46,7 +60,7 @@ typedef struct __wasi_addr_ip6_t {
 
 
 typedef struct __wasi_addr_ip6_port_t {
 typedef struct __wasi_addr_ip6_port_t {
     __wasi_addr_ip6_t addr;
     __wasi_addr_ip6_t addr;
-    __wasi_ip_port_t port;
+    __wasi_ip_port_t port; /* host byte order */
 } __wasi_addr_ip6_port_t;
 } __wasi_addr_ip6_port_t;
 
 
 typedef struct __wasi_addr_t {
 typedef struct __wasi_addr_t {

+ 12 - 8
core/iwasm/libraries/lib-socket/src/wasi/wasi_socket_ext.c

@@ -22,12 +22,13 @@
 static void
 static void
 ipv4_addr_to_wasi_addr(uint32_t addr_num, uint16_t port, __wasi_addr_t *out)
 ipv4_addr_to_wasi_addr(uint32_t addr_num, uint16_t port, __wasi_addr_t *out)
 {
 {
+    addr_num = ntohl(addr_num);
     out->kind = IPv4;
     out->kind = IPv4;
     out->addr.ip4.port = ntohs(port);
     out->addr.ip4.port = ntohs(port);
-    out->addr.ip4.addr.n3 = (addr_num & 0xFF000000) >> 24;
-    out->addr.ip4.addr.n2 = (addr_num & 0x00FF0000) >> 16;
-    out->addr.ip4.addr.n1 = (addr_num & 0x0000FF00) >> 8;
-    out->addr.ip4.addr.n0 = (addr_num & 0x000000FF);
+    out->addr.ip4.addr.n0 = (addr_num & 0xFF000000) >> 24;
+    out->addr.ip4.addr.n1 = (addr_num & 0x00FF0000) >> 16;
+    out->addr.ip4.addr.n2 = (addr_num & 0x0000FF00) >> 8;
+    out->addr.ip4.addr.n3 = (addr_num & 0x000000FF);
 }
 }
 
 
 static __wasi_errno_t
 static __wasi_errno_t
@@ -57,6 +58,7 @@ static __wasi_errno_t
 sock_addr_remote(__wasi_fd_t fd, struct sockaddr *sock_addr, socklen_t *addrlen)
 sock_addr_remote(__wasi_fd_t fd, struct sockaddr *sock_addr, socklen_t *addrlen)
 {
 {
     __wasi_addr_t wasi_addr = { 0 };
     __wasi_addr_t wasi_addr = { 0 };
+    uint32_t s_addr;
     __wasi_errno_t error;
     __wasi_errno_t error;
 
 
     error =
     error =
@@ -68,11 +70,13 @@ sock_addr_remote(__wasi_fd_t fd, struct sockaddr *sock_addr, socklen_t *addrlen)
     if (IPv4 == wasi_addr.kind) {
     if (IPv4 == wasi_addr.kind) {
         struct sockaddr_in sock_addr_in = { 0 };
         struct sockaddr_in sock_addr_in = { 0 };
 
 
+        s_addr = (wasi_addr.addr.ip4.addr.n0 << 24)
+                 | (wasi_addr.addr.ip4.addr.n1 << 16)
+                 | (wasi_addr.addr.ip4.addr.n2 << 8)
+                 | wasi_addr.addr.ip4.addr.n3;
+
         sock_addr_in.sin_family = AF_INET;
         sock_addr_in.sin_family = AF_INET;
-        sock_addr_in.sin_addr.s_addr = (wasi_addr.addr.ip4.addr.n3 << 24)
-                                       | (wasi_addr.addr.ip4.addr.n2 << 16)
-                                       | (wasi_addr.addr.ip4.addr.n1 << 8)
-                                       | wasi_addr.addr.ip4.addr.n0;
+        sock_addr_in.sin_addr.s_addr = htonl(s_addr);
         sock_addr_in.sin_port = htons(wasi_addr.addr.ip4.port);
         sock_addr_in.sin_port = htons(wasi_addr.addr.ip4.port);
         memcpy(sock_addr, &sock_addr_in, sizeof(sock_addr_in));
         memcpy(sock_addr, &sock_addr_in, sizeof(sock_addr_in));
 
 

+ 1 - 3
core/shared/platform/common/posix/posix_socket.c

@@ -60,9 +60,7 @@ os_socket_bind(bh_socket_t socket, const char *host, int *port)
         goto fail;
         goto fail;
     }
     }
 
 
-    addr.sin_addr.s_addr = inet_addr(host);
-    addr.sin_port = htons(*port);
-    addr.sin_family = AF_INET;
+    textual_addr_to_sockaddr(host, *port, &addr);
 
 
     ret = bind(socket, (struct sockaddr *)&addr, sizeof(addr));
     ret = bind(socket, (struct sockaddr *)&addr, sizeof(addr));
     if (ret < 0) {
     if (ret < 0) {