Repository: incubator-mynewt-core Updated Branches: refs/heads/develop 8d757705f -> 389d7f4ad
net/oic; support IPv4. Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/commit/9064dbaf Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/tree/9064dbaf Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/diff/9064dbaf Branch: refs/heads/develop Commit: 9064dbafc0fab24833c1bae77c52755e02108ea6 Parents: a42c0c1 Author: Marko Kiiskila <ma...@runtime.io> Authored: Tue Feb 21 10:09:25 2017 -0800 Committer: Marko Kiiskila <ma...@runtime.io> Committed: Tue Feb 21 10:09:25 2017 -0800 ---------------------------------------------------------------------- net/oic/src/api/oc_client_api.c | 61 ++++- net/oic/src/port/mynewt/adaptor.c | 32 ++- net/oic/src/port/mynewt/adaptor.h | 16 +- net/oic/src/port/mynewt/ip4_adaptor.c | 354 +++++++++++++++++++++++++++++ net/oic/src/port/mynewt/ip_adaptor.c | 96 ++++---- net/oic/src/port/oc_connectivity.h | 15 +- net/oic/syscfg.yml | 6 + net/oic/test/syscfg.yml | 2 + 8 files changed, 512 insertions(+), 70 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/api/oc_client_api.c ---------------------------------------------------------------------- diff --git a/net/oic/src/api/oc_client_api.c b/net/oic/src/api/oc_client_api.c index 692e0f6..d87683c 100644 --- a/net/oic/src/api/oc_client_api.c +++ b/net/oic/src/api/oc_client_api.c @@ -263,22 +263,16 @@ oc_stop_observe(const char *uri, oc_server_handle_t *server) return status; } -bool -oc_do_ip_discovery(const char *rt, oc_discovery_cb_t handler) +#if MYNEWT_VAL(OC_TRANSPORT_IP) +static bool +oc_send_ip_discovery(oc_server_handle_t *handle, const char *rt, + oc_discovery_cb_t handler) { - oc_server_handle_t handle; oc_client_cb_t *cb; bool status = false; oc_string_t query; - oc_make_ip_endpoint(mcast, IP | MULTICAST, 5683, - 0xff, 0x02, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xfd); - mcast.oe_ip.v6.scope = 0; - - memcpy(&handle.endpoint, &mcast, sizeof(oc_endpoint_t)); - - cb = oc_ri_alloc_client_cb("/oic/res", &handle, OC_GET, handler, LOW_QOS); - + cb = oc_ri_alloc_client_cb("/oic/res", handle, OC_GET, handler, LOW_QOS); if (!cb) { return false; } @@ -297,4 +291,49 @@ oc_do_ip_discovery(const char *rt, oc_discovery_cb_t handler) } return status; } + +#if MYNEWT_VAL(OC_TRANSPORT_IPV6) +bool +oc_do_ip6_discovery(const char *rt, oc_discovery_cb_t handler) +{ + oc_server_handle_t handle; + + oc_make_ip_endpoint(mcast, IP | MULTICAST, 5683, + 0xff, 0x02, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0xfd); + mcast.oe_ip.v6.scope = 0; + memcpy(&handle.endpoint, &mcast, sizeof(oc_endpoint_t)); + + return oc_send_ip_discovery(&handle, rt, handler); + +} +#endif + +#if MYNEWT_VAL(OC_TRANSPORT_IPV4) +bool +oc_do_ip4_discovery(const char *rt, oc_discovery_cb_t handler) +{ + oc_server_handle_t handle; + + oc_make_ip4_endpoint(mcast, IP4 | MULTICAST, 5683, 0xe0, 0, 0x01, 0xbb); + memcpy(&handle.endpoint, &mcast, sizeof(oc_endpoint_t)); + + return oc_send_ip_discovery(&handle, rt, handler); +} +#endif + +bool +oc_do_ip_discovery(const char *rt, oc_discovery_cb_t handler) +{ + bool status = false; + +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) + status = oc_do_ip6_discovery(rt, handler); +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) + status = oc_do_ip4_discovery(rt, handler); +#endif + return status; +} +#endif + #endif /* OC_CLIENT */ http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/port/mynewt/adaptor.c ---------------------------------------------------------------------- diff --git a/net/oic/src/port/mynewt/adaptor.c b/net/oic/src/port/mynewt/adaptor.c index 0212592..dd6b986 100644 --- a/net/oic/src/port/mynewt/adaptor.c +++ b/net/oic/src/port/mynewt/adaptor.c @@ -51,9 +51,14 @@ oc_send_buffer(struct os_mbuf *m) oe = OC_MBUF_ENDPOINT(m); switch (oe->oe.flags) { -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) case IP: - oc_send_buffer_ip(m); + oc_send_buffer_ip6(m); + break; +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) + case IP4: + oc_send_buffer_ip4(m); break; #endif #if (MYNEWT_VAL(OC_TRANSPORT_GATT) == 1) @@ -79,8 +84,11 @@ oc_send_multicast_message(struct os_mbuf *m) * Send on all the transports. */ void (*funcs[])(struct os_mbuf *) = { -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) - oc_send_buffer_ip_mcast, +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) + oc_send_buffer_ip6_mcast, +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) + oc_send_buffer_ip4_mcast, #endif #if (MYNEWT_VAL(OC_TRANSPORT_GATT) == 1) /* no multicast for GATT, just send unicast */ @@ -108,8 +116,11 @@ oc_send_multicast_message(struct os_mbuf *m) void oc_connectivity_shutdown(void) { -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) - oc_connectivity_shutdown_ip(); +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) + oc_connectivity_shutdown_ip6(); +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) + oc_connectivity_shutdown_ip4(); #endif #if (MYNEWT_VAL(OC_TRANSPORT_SERIAL) == 1) oc_connectivity_shutdown_serial(); @@ -124,8 +135,13 @@ oc_connectivity_init(void) { int rc = -1; -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) - if (oc_connectivity_init_ip() == 0) { +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) + if (oc_connectivity_init_ip6() == 0) { + rc = 0; + } +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) + if (oc_connectivity_init_ip4() == 0) { rc = 0; } #endif http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/port/mynewt/adaptor.h ---------------------------------------------------------------------- diff --git a/net/oic/src/port/mynewt/adaptor.h b/net/oic/src/port/mynewt/adaptor.h index 7ea0c4d..ba13e90 100644 --- a/net/oic/src/port/mynewt/adaptor.h +++ b/net/oic/src/port/mynewt/adaptor.h @@ -26,11 +26,17 @@ extern "C" { struct os_eventq *oc_evq_get(void); -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) -int oc_connectivity_init_ip(void); -void oc_connectivity_shutdown_ip(void); -void oc_send_buffer_ip(struct os_mbuf *); -void oc_send_buffer_ip_mcast(struct os_mbuf *); +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) +int oc_connectivity_init_ip6(void); +void oc_connectivity_shutdown_ip6(void); +void oc_send_buffer_ip6(struct os_mbuf *); +void oc_send_buffer_ip6_mcast(struct os_mbuf *); +#endif +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) +int oc_connectivity_init_ip4(void); +void oc_connectivity_shutdown_ip4(void); +void oc_send_buffer_ip4(struct os_mbuf *); +void oc_send_buffer_ip4_mcast(struct os_mbuf *); #endif #if (MYNEWT_VAL(OC_TRANSPORT_GATT) == 1) http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/port/mynewt/ip4_adaptor.c ---------------------------------------------------------------------- diff --git a/net/oic/src/port/mynewt/ip4_adaptor.c b/net/oic/src/port/mynewt/ip4_adaptor.c new file mode 100644 index 0000000..9757fdd --- /dev/null +++ b/net/oic/src/port/mynewt/ip4_adaptor.c @@ -0,0 +1,354 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ + +#include <syscfg/syscfg.h> +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV4) == 1) +#include <assert.h> +#include <string.h> + +#include <os/os.h> +#include <os/endian.h> + +#include <log/log.h> +#include <mn_socket/mn_socket.h> +#include <stats/stats.h> + +#include "port/oc_connectivity.h" +#include "oic/oc_log.h" +#include "api/oc_buffer.h" +#include "adaptor.h" + +static void oc_event_ip4(struct os_event *ev); + +static struct os_event oc_sock4_read_event = { + .ev_cb = oc_event_ip4, +}; + +#ifdef OC_SECURITY +#error This implementation does not yet support security +#endif + +#define COAP_PORT_UNSECURED (5683) + +/* 224.0.1.187 */ +static const struct mn_in_addr coap_all_nodes_v4 = { + .s_addr = htonl(0xe00001bb) +}; + +STATS_SECT_START(oc_ip4_stats) + STATS_SECT_ENTRY(iframe) + STATS_SECT_ENTRY(ibytes) + STATS_SECT_ENTRY(ierr) + STATS_SECT_ENTRY(oucast) + STATS_SECT_ENTRY(omcast) + STATS_SECT_ENTRY(obytes) + STATS_SECT_ENTRY(oerr) +STATS_SECT_END +STATS_SECT_DECL(oc_ip4_stats) oc_ip4_stats; +STATS_NAME_START(oc_ip4_stats) + STATS_NAME(oc_ip4_stats, iframe) + STATS_NAME(oc_ip4_stats, ibytes) + STATS_NAME(oc_ip4_stats, ierr) + STATS_NAME(oc_ip4_stats, oucast) + STATS_NAME(oc_ip4_stats, omcast) + STATS_NAME(oc_ip4_stats, obytes) + STATS_NAME(oc_ip4_stats, oerr) +STATS_NAME_END(oc_ip4_stats) + +/* sockets to use for coap unicast and multicast */ +static struct mn_socket *oc_ucast4; + +#if (MYNEWT_VAL(OC_SERVER) == 1) +static struct mn_socket *oc_mcast4; +#endif + +static void +oc_send_buffer_ip4_int(struct os_mbuf *m, int is_mcast) +{ + struct mn_sockaddr_in to; + struct oc_endpoint *oe; + struct mn_itf itf; + uint32_t if2_idx; + struct os_mbuf *n; + int rc; + + assert(OS_MBUF_USRHDR_LEN(m) >= sizeof(struct oc_endpoint_ip)); + oe = OC_MBUF_ENDPOINT(m); + if ((oe->oe_ip.flags & IP4) == 0) { + os_mbuf_free_chain(m); + return; + } + to.msin_len = sizeof(to); + to.msin_family = MN_AF_INET; + to.msin_port = htons(oe->oe_ip.v4.port); + memcpy(&to.msin_addr, oe->oe_ip.v4.address, sizeof(to.msin_addr)); + + STATS_INCN(oc_ip4_stats, obytes, OS_MBUF_PKTLEN(m)); + if (is_mcast) { + memset(&itf, 0, sizeof(itf)); + if2_idx = 0; + + while (1) { + rc = mn_itf_getnext(&itf); + if (rc) { + break; + } + + if ((itf.mif_flags & (MN_ITF_F_UP | MN_ITF_F_MULTICAST)) != + (MN_ITF_F_UP | MN_ITF_F_MULTICAST)) { + continue; + } + + if (!if2_idx) { + if2_idx = itf.mif_idx; + continue; + } + + rc = mn_setsockopt(oc_ucast4, MN_SO_LEVEL, MN_MCAST_IF, &if2_idx); + if (rc) { + STATS_INC(oc_ip4_stats, oerr); + continue; + } + n = os_mbuf_dup(m); + if (!n) { + STATS_INC(oc_ip4_stats, oerr); + break; + } + rc = mn_sendto(oc_ucast4, n, (struct mn_sockaddr *)&to); + if (rc != 0) { + OC_LOG_ERROR("Failed to send buffer %u on %x\n", + OS_MBUF_PKTHDR(m)->omp_len, if2_idx); + STATS_INC(oc_ip4_stats, oerr); + os_mbuf_free_chain(n); + } + if2_idx = itf.mif_idx; + } + if (if2_idx) { + rc = mn_setsockopt(oc_ucast4, MN_SO_LEVEL, MN_MCAST_IF, &if2_idx); + if (rc) { + STATS_INC(oc_ip4_stats, oerr); + os_mbuf_free_chain(m); + } else { + rc = mn_sendto(oc_ucast4, m, (struct mn_sockaddr *) &to); + if (rc != 0) { + OC_LOG_ERROR("Failed sending buffer %u on itf %x\n", + OS_MBUF_PKTHDR(m)->omp_len, if2_idx); + STATS_INC(oc_ip4_stats, oerr); + os_mbuf_free_chain(m); + } + } + } else { + os_mbuf_free_chain(m); + } + } else { + rc = mn_sendto(oc_ucast4, m, (struct mn_sockaddr *) &to); + if (rc != 0) { + OC_LOG_ERROR("Failed to send buffer %u ucast\n", + OS_MBUF_PKTHDR(m)->omp_len); + STATS_INC(oc_ip4_stats, oerr); + os_mbuf_free_chain(m); + } + } +} + +void +oc_send_buffer_ip4(struct os_mbuf *m) +{ + STATS_INC(oc_ip4_stats, oucast); + oc_send_buffer_ip4_int(m, 0); +} +void +oc_send_buffer_ip4_mcast(struct os_mbuf *m) +{ + STATS_INC(oc_ip4_stats, omcast); + oc_send_buffer_ip4_int(m, 1); +} + +static struct os_mbuf * +oc_attempt_rx_ip4_sock(struct mn_socket *rxsock) +{ + int rc; + struct os_mbuf *m; + struct os_mbuf *n; + struct oc_endpoint *oe; + struct mn_sockaddr_in from; + + rc = mn_recvfrom(rxsock, &n, (struct mn_sockaddr *) &from); + if (rc != 0) { + return NULL; + } + assert(OS_MBUF_IS_PKTHDR(n)); + + STATS_INC(oc_ip4_stats, iframe); + STATS_INCN(oc_ip4_stats, ibytes, OS_MBUF_PKTLEN(n)); + m = os_msys_get_pkthdr(0, sizeof(struct oc_endpoint_ip)); + if (!m) { + OC_LOG_ERROR("Could not allocate RX buffer\n"); + goto rx_attempt_err; + } + OS_MBUF_PKTHDR(m)->omp_len = OS_MBUF_PKTHDR(n)->omp_len; + SLIST_NEXT(m, om_next) = n; + + oe = OC_MBUF_ENDPOINT(m); + + oe->oe_ip.flags = IP4; + memcpy(&oe->oe_ip.v4.address, &from.msin_addr, + sizeof(oe->oe_ip.v4.address)); + oe->oe_ip.v4.port = ntohs(from.msin_port); + + return m; + + /* add the addr info to the message */ +rx_attempt_err: + STATS_INC(oc_ip4_stats, ierr); + os_mbuf_free_chain(n); + return NULL; +} + +static struct os_mbuf * +oc_attempt_rx_ip4(void) +{ + struct os_mbuf *m; + + m = oc_attempt_rx_ip4_sock(oc_ucast4); +#if (MYNEWT_VAL(OC_SERVER) == 1) + if (m == NULL) { + m = oc_attempt_rx_ip4_sock(oc_mcast4); + } +#endif + return m; +} + +static void oc_socks4_readable(void *cb_arg, int err); + +union mn_socket_cb oc_sock4_cbs = { + .socket.readable = oc_socks4_readable, + .socket.writable = NULL +}; + +void +oc_socks4_readable(void *cb_arg, int err) +{ + os_eventq_put(oc_evq_get(), &oc_sock4_read_event); +} + +void +oc_connectivity_shutdown_ip4(void) +{ + if (oc_ucast4) { + mn_close(oc_ucast4); + } + +#if (MYNEWT_VAL(OC_SERVER) == 1) + if (oc_mcast4) { + mn_close(oc_mcast4); + } +#endif +} + +static void +oc_event_ip4(struct os_event *ev) +{ + struct os_mbuf *m; + + while ((m = oc_attempt_rx_ip4()) != NULL) { + oc_recv_message(m); + } +} + +int +oc_connectivity_init_ip4(void) +{ + int rc; + struct mn_sockaddr_in sin; + struct mn_itf itf; + + memset(&itf, 0, sizeof(itf)); + + rc = mn_socket(&oc_ucast4, MN_PF_INET, MN_SOCK_DGRAM, 0); + if (rc != 0 || !oc_ucast4) { + OC_LOG_ERROR("Could not create oc unicast v4 socket\n"); + return rc; + } + mn_socket_set_cbs(oc_ucast4, oc_ucast4, &oc_sock4_cbs); + +#if (MYNEWT_VAL(OC_SERVER) == 1) + rc = mn_socket(&oc_mcast4, MN_PF_INET, MN_SOCK_DGRAM, 0); + if (rc != 0 || !oc_mcast4) { + mn_close(oc_ucast4); + OC_LOG_ERROR("Could not create oc multicast v4 socket\n"); + return rc; + } + mn_socket_set_cbs(oc_mcast4, oc_mcast4, &oc_sock4_cbs); +#endif + + sin.msin_len = sizeof(sin); + sin.msin_family = MN_AF_INET; + sin.msin_port = 11111; + memset(&sin.msin_addr, 0, sizeof(sin.msin_addr)); + + rc = mn_bind(oc_ucast4, (struct mn_sockaddr *)&sin); + if (rc != 0) { + OC_LOG_ERROR("Could not bind oc unicast v4 socket\n"); + goto oc_connectivity_init_err; + } + +#if (MYNEWT_VAL(OC_SERVER) == 1) + /* Set socket option to join multicast group on all valid interfaces */ + while (1) { + struct mn_mreq join; + + rc = mn_itf_getnext(&itf); + if (rc) { + break; + } + + if ((itf.mif_flags & (MN_ITF_F_UP | MN_ITF_F_MULTICAST)) != + (MN_ITF_F_UP | MN_ITF_F_MULTICAST)) { + continue; + } + + memcpy(&join.mm_addr.v4, &coap_all_nodes_v4, sizeof(coap_all_nodes_v4)); + join.mm_idx = itf.mif_idx; + join.mm_family = MN_AF_INET; + + rc = mn_setsockopt(oc_mcast4, MN_SO_LEVEL, MN_MCAST_JOIN_GROUP, &join); + if (rc != 0) { + continue; + } + + OC_LOG_DEBUG("Joined Coap v4 mcast group on %s\n", itf.mif_name); + } + + sin.msin_port = htons(COAP_PORT_UNSECURED); + rc = mn_bind(oc_mcast4, (struct mn_sockaddr *)&sin); + if (rc != 0) { + OC_LOG_ERROR("Could not bind oc v4 multicast socket\n"); + goto oc_connectivity_init_err; + } +#endif + + return 0; + +oc_connectivity_init_err: + oc_connectivity_shutdown(); + return rc; +} + +#endif http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/port/mynewt/ip_adaptor.c ---------------------------------------------------------------------- diff --git a/net/oic/src/port/mynewt/ip_adaptor.c b/net/oic/src/port/mynewt/ip_adaptor.c index d933b2a..9dcbeb9 100644 --- a/net/oic/src/port/mynewt/ip_adaptor.c +++ b/net/oic/src/port/mynewt/ip_adaptor.c @@ -18,7 +18,7 @@ */ #include <syscfg/syscfg.h> -#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) +#if (MYNEWT_VAL(OC_TRANSPORT_IP) == 1) && (MYNEWT_VAL(OC_TRANSPORT_IPV6) == 1) #include <assert.h> #include <string.h> @@ -34,10 +34,10 @@ #include "api/oc_buffer.h" #include "adaptor.h" -static void oc_event_ip(struct os_event *ev); +static void oc_event_ip6(struct os_event *ev); -static struct os_event oc_sock_read_event = { - .ev_cb = oc_event_ip, +static struct os_event oc_sock6_read_event = { + .ev_cb = oc_event_ip6, }; #ifdef OC_SECURITY @@ -46,10 +46,13 @@ static struct os_event oc_sock_read_event = { #define COAP_PORT_UNSECURED (5683) -/* TODO use inet_pton when its available */ + +/* link-local scoped address ff02::fd */ static const struct mn_in6_addr coap_all_nodes_v6 = { - .s_addr = {0xFF,0x02,0x00,0x00,0x00,0x00,0x00,0x00, - 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFD} + .s_addr = { + 0xFF, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xFD + } }; STATS_SECT_START(oc_ip_stats) @@ -73,14 +76,14 @@ STATS_NAME_START(oc_ip_stats) STATS_NAME_END(oc_ip_stats) /* sockets to use for coap unicast and multicast */ -static struct mn_socket *oc_ucast; +static struct mn_socket *oc_ucast6; #if (MYNEWT_VAL(OC_SERVER) == 1) -static struct mn_socket *oc_mcast; +static struct mn_socket *oc_mcast6; #endif static void -oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) +oc_send_buffer_ip6_int(struct os_mbuf *m, int is_mcast) { struct mn_sockaddr_in6 to; struct oc_endpoint *oe; @@ -91,7 +94,10 @@ oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) assert(OS_MBUF_USRHDR_LEN(m) >= sizeof(struct oc_endpoint_ip)); oe = OC_MBUF_ENDPOINT(m); - + if ((oe->oe_ip.flags & IP) == 0) { + os_mbuf_free_chain(m); + return; + } to.msin6_len = sizeof(to); to.msin6_family = MN_AF_INET6; to.msin6_port = htons(oe->oe_ip.v6.port); @@ -126,7 +132,7 @@ oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) break; } to.msin6_scope_id = itf2.mif_idx; - rc = mn_sendto(oc_ucast, n, (struct mn_sockaddr *) &to); + rc = mn_sendto(oc_ucast6, n, (struct mn_sockaddr *) &to); if (rc != 0) { OC_LOG_ERROR("Failed to send buffer %u on itf %d\n", OS_MBUF_PKTHDR(m)->omp_len, to.msin6_scope_id); @@ -137,7 +143,7 @@ oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) } if (itf2.mif_idx) { to.msin6_scope_id = itf2.mif_idx; - rc = mn_sendto(oc_ucast, m, (struct mn_sockaddr *) &to); + rc = mn_sendto(oc_ucast6, m, (struct mn_sockaddr *) &to); if (rc != 0) { OC_LOG_ERROR("Failed sending buffer %u on itf %d\n", OS_MBUF_PKTHDR(m)->omp_len, to.msin6_scope_id); @@ -148,7 +154,7 @@ oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) os_mbuf_free_chain(m); } } else { - rc = mn_sendto(oc_ucast, m, (struct mn_sockaddr *) &to); + rc = mn_sendto(oc_ucast6, m, (struct mn_sockaddr *) &to); if (rc != 0) { OC_LOG_ERROR("Failed to send buffer %u on itf %d\n", OS_MBUF_PKTHDR(m)->omp_len, to.msin6_scope_id); @@ -159,20 +165,20 @@ oc_send_buffer_ip_int(struct os_mbuf *m, int is_mcast) } void -oc_send_buffer_ip(struct os_mbuf *m) +oc_send_buffer_ip6(struct os_mbuf *m) { STATS_INC(oc_ip_stats, oucast); - oc_send_buffer_ip_int(m, 0); + oc_send_buffer_ip6_int(m, 0); } void -oc_send_buffer_ip_mcast(struct os_mbuf *m) +oc_send_buffer_ip6_mcast(struct os_mbuf *m) { STATS_INC(oc_ip_stats, omcast); - oc_send_buffer_ip_int(m, 1); + oc_send_buffer_ip6_int(m, 1); } static struct os_mbuf * -oc_attempt_rx_ip_sock(struct mn_socket *rxsock) +oc_attempt_rx_ip6_sock(struct mn_socket *rxsock) { int rc; struct os_mbuf *m; @@ -214,59 +220,59 @@ rx_attempt_err: } static struct os_mbuf * -oc_attempt_rx_ip(void) +oc_attempt_rx_ip6(void) { struct os_mbuf *m; - m = oc_attempt_rx_ip_sock(oc_ucast); + m = oc_attempt_rx_ip6_sock(oc_ucast6); #if (MYNEWT_VAL(OC_SERVER) == 1) if (m == NULL) { - m = oc_attempt_rx_ip_sock(oc_mcast); + m = oc_attempt_rx_ip6_sock(oc_mcast6); } #endif return m; } -static void oc_socks_readable(void *cb_arg, int err); +static void oc_socks6_readable(void *cb_arg, int err); -union mn_socket_cb oc_sock_cbs = { - .socket.readable = oc_socks_readable, +union mn_socket_cb oc_sock6_cbs = { + .socket.readable = oc_socks6_readable, .socket.writable = NULL }; void -oc_socks_readable(void *cb_arg, int err) +oc_socks6_readable(void *cb_arg, int err) { - os_eventq_put(oc_evq_get(), &oc_sock_read_event); + os_eventq_put(oc_evq_get(), &oc_sock6_read_event); } void -oc_connectivity_shutdown_ip(void) +oc_connectivity_shutdown_ip6(void) { - if (oc_ucast) { - mn_close(oc_ucast); + if (oc_ucast6) { + mn_close(oc_ucast6); } #if (MYNEWT_VAL(OC_SERVER) == 1) - if (oc_mcast) { - mn_close(oc_mcast); + if (oc_mcast6) { + mn_close(oc_mcast6); } #endif } static void -oc_event_ip(struct os_event *ev) +oc_event_ip6(struct os_event *ev) { struct os_mbuf *m; - while ((m = oc_attempt_rx_ip()) != NULL) { + while ((m = oc_attempt_rx_ip6()) != NULL) { oc_recv_message(m); } } int -oc_connectivity_init_ip(void) +oc_connectivity_init_ip6(void) { int rc; struct mn_sockaddr_in6 sin; @@ -274,21 +280,21 @@ oc_connectivity_init_ip(void) memset(&itf, 0, sizeof(itf)); - rc = mn_socket(&oc_ucast, MN_PF_INET6, MN_SOCK_DGRAM, 0); - if (rc != 0 || !oc_ucast) { + rc = mn_socket(&oc_ucast6, MN_PF_INET6, MN_SOCK_DGRAM, 0); + if (rc != 0 || !oc_ucast6) { OC_LOG_ERROR("Could not create oc unicast socket\n"); return rc; } - mn_socket_set_cbs(oc_ucast, oc_ucast, &oc_sock_cbs); + mn_socket_set_cbs(oc_ucast6, oc_ucast6, &oc_sock6_cbs); #if (MYNEWT_VAL(OC_SERVER) == 1) - rc = mn_socket(&oc_mcast, MN_PF_INET6, MN_SOCK_DGRAM, 0); - if (rc != 0 || !oc_mcast) { - mn_close(oc_ucast); + rc = mn_socket(&oc_mcast6, MN_PF_INET6, MN_SOCK_DGRAM, 0); + if (rc != 0 || !oc_mcast6) { + mn_close(oc_ucast6); OC_LOG_ERROR("Could not create oc multicast socket\n"); return rc; } - mn_socket_set_cbs(oc_mcast, oc_mcast, &oc_sock_cbs); + mn_socket_set_cbs(oc_mcast6, oc_mcast6, &oc_sock6_cbs); #endif sin.msin6_len = sizeof(sin); @@ -298,7 +304,7 @@ oc_connectivity_init_ip(void) sin.msin6_scope_id = 0; memcpy(&sin.msin6_addr, nm_in6addr_any, sizeof(sin.msin6_addr)); - rc = mn_bind(oc_ucast, (struct mn_sockaddr *)&sin); + rc = mn_bind(oc_ucast6, (struct mn_sockaddr *)&sin); if (rc != 0) { OC_LOG_ERROR("Could not bind oc unicast socket\n"); goto oc_connectivity_init_err; @@ -323,7 +329,7 @@ oc_connectivity_init_ip(void) join.mm_idx = itf.mif_idx; join.mm_family = MN_AF_INET6; - rc = mn_setsockopt(oc_mcast, MN_SO_LEVEL, MN_MCAST_JOIN_GROUP, &join); + rc = mn_setsockopt(oc_mcast6, MN_SO_LEVEL, MN_MCAST_JOIN_GROUP, &join); if (rc != 0) { continue; } @@ -332,7 +338,7 @@ oc_connectivity_init_ip(void) } sin.msin6_port = htons(COAP_PORT_UNSECURED); - rc = mn_bind(oc_mcast, (struct mn_sockaddr *)&sin); + rc = mn_bind(oc_mcast6, (struct mn_sockaddr *)&sin); if (rc != 0) { OC_LOG_ERROR("Could not bind oc multicast socket\n"); goto oc_connectivity_init_err; http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/src/port/oc_connectivity.h ---------------------------------------------------------------------- diff --git a/net/oic/src/port/oc_connectivity.h b/net/oic/src/port/oc_connectivity.h index c4d205c..a7cce39 100644 --- a/net/oic/src/port/oc_connectivity.h +++ b/net/oic/src/port/oc_connectivity.h @@ -30,6 +30,11 @@ typedef struct { uint8_t scope; } oc_ipv6_addr_t; +typedef struct { + uint16_t port; + uint8_t address[4]; +} oc_ipv4_addr_t; + enum oc_transport_flags { IP = 1 << 0, GATT = 1 << 1, @@ -37,6 +42,7 @@ enum oc_transport_flags { MULTICAST = 1 << 3, SECURED = 1 << 4, SERIAL = 1 << 5, + IP4 = 1 << 6, }; /* @@ -48,7 +54,10 @@ enum oc_transport_flags { */ struct oc_endpoint_ip { enum oc_transport_flags flags; - oc_ipv6_addr_t v6; + union { + oc_ipv6_addr_t v6; + oc_ipv4_addr_t v4; + }; }; /* @@ -83,6 +92,10 @@ typedef struct oc_endpoint { oc_endpoint_t __name__ = {.oe_ip = {.flags = __flags__, \ .v6 = {.port = __port__, \ .address = { __VA_ARGS__ } } } } +#define oc_make_ip4_endpoint(__name__, __flags__, __port__, ...) \ + oc_endpoint_t __name__ = {.oe_ip = {.flags = __flags__, \ + .v4 = {.port = __port__, \ + .address = { __VA_ARGS__ } } } } #ifdef OC_SECURITY uint16_t oc_connectivity_get_dtls_port(void); http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/syscfg.yml ---------------------------------------------------------------------- diff --git a/net/oic/syscfg.yml b/net/oic/syscfg.yml index 3b7460a..51d86e2 100644 --- a/net/oic/syscfg.yml +++ b/net/oic/syscfg.yml @@ -29,6 +29,12 @@ syscfg.defs: OC_TRANSPORT_IP: description: 'Enables OIC transport over IP UDP' value: '0' + OC_TRANSPORT_IPV6: + description: 'Support IPv6' + value: '1' + OC_TRANSPORT_IPV4: + description: 'Support IPv4' + value: '0' OC_CLIENT: description: 'Enables OIC client support' value: '0' http://git-wip-us.apache.org/repos/asf/incubator-mynewt-core/blob/9064dbaf/net/oic/test/syscfg.yml ---------------------------------------------------------------------- diff --git a/net/oic/test/syscfg.yml b/net/oic/test/syscfg.yml index 47ceb25..a8ed09e 100644 --- a/net/oic/test/syscfg.yml +++ b/net/oic/test/syscfg.yml @@ -20,5 +20,7 @@ syscfg.vals: OC_TRANSPORT_IP: 1 + OC_TRANSPORT_IPV6: 1 + OC_TRANSPORT_IPV4: 0 OC_SERVER: 1 OC_CLIENT: 1