Rtos API example

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers NetworkStack.cpp Source File

NetworkStack.cpp

00001 /* Socket
00002  * Copyright (c) 2015 ARM Limited
00003  *
00004  * Licensed under the Apache License, Version 2.0 (the "License");
00005  * you may not use this file except in compliance with the License.
00006  * You may obtain a copy of the License at
00007  *
00008  *     http://www.apache.org/licenses/LICENSE-2.0
00009  *
00010  * Unless required by applicable law or agreed to in writing, software
00011  * distributed under the License is distributed on an "AS IS" BASIS,
00012  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00013  * See the License for the specific language governing permissions and
00014  * limitations under the License.
00015  */
00016 
00017 #include "NetworkStack.h"
00018 #include "nsapi_dns.h"
00019 #include "mbed.h"
00020 #include "stddef.h"
00021 #include <new>
00022 
00023 
00024 // Default NetworkStack operations
00025 nsapi_error_t NetworkStack::gethostbyname(const char *name, SocketAddress *address, nsapi_version_t version)
00026 {
00027     // check for simple ip addresses
00028     if (address->set_ip_address(name)) {
00029         if (version != NSAPI_UNSPEC  && address->get_ip_version() != version) {
00030             return NSAPI_ERROR_DNS_FAILURE ;
00031         }
00032 
00033         return NSAPI_ERROR_OK ;
00034     }
00035 
00036     // if the version is unspecified, try to guess the version from the
00037     // ip address of the underlying stack
00038     if (version == NSAPI_UNSPEC ) {
00039         SocketAddress testaddress;
00040         if (testaddress.set_ip_address(this->get_ip_address())) {
00041             version = testaddress.get_ip_version();
00042         }
00043     }
00044 
00045     return nsapi_dns_query(this, name, address, version);
00046 }
00047 
00048 nsapi_error_t NetworkStack::add_dns_server(const SocketAddress &address)
00049 {
00050     return nsapi_dns_add_server(address);
00051 }
00052 
00053 nsapi_error_t NetworkStack::setstackopt(int level, int optname, const void *optval, unsigned optlen)
00054 {
00055     return NSAPI_ERROR_UNSUPPORTED ;
00056 }
00057 
00058 nsapi_error_t NetworkStack::getstackopt(int level, int optname, void *optval, unsigned *optlen)
00059 {
00060     return NSAPI_ERROR_UNSUPPORTED ;
00061 }
00062 
00063 nsapi_error_t NetworkStack::setsockopt(void *handle, int level, int optname, const void *optval, unsigned optlen)
00064 {
00065     return NSAPI_ERROR_UNSUPPORTED ;
00066 }
00067 
00068 nsapi_error_t NetworkStack::getsockopt(void *handle, int level, int optname, void *optval, unsigned *optlen)
00069 {
00070     return NSAPI_ERROR_UNSUPPORTED ;
00071 }
00072 
00073 
00074 // NetworkStackWrapper class for encapsulating the raw nsapi_stack structure
00075 class NetworkStackWrapper : public NetworkStack
00076 {
00077 private:
00078     inline nsapi_stack_t *_stack()
00079     {
00080         return reinterpret_cast<nsapi_stack_t *>(
00081                 reinterpret_cast<uint8_t *>(this)
00082                 - offsetof(nsapi_stack_t, _stack_buffer));
00083     }
00084 
00085     inline const nsapi_stack_api_t *_stack_api()
00086     {
00087         return _stack()->stack_api;
00088     }
00089 
00090 public:
00091     virtual const char *get_ip_address()
00092     {
00093         if (!_stack_api()->get_ip_address) {
00094             return 0;
00095         }
00096 
00097         static uint8_t buffer[sizeof(SocketAddress)];
00098         SocketAddress *address = new (buffer) SocketAddress(_stack_api()->get_ip_address(_stack()));
00099         return address->get_ip_address();
00100     }
00101 
00102     virtual nsapi_error_t gethostbyname(const char *name, SocketAddress *address, nsapi_version_t version)
00103     {
00104         if (!_stack_api()->gethostbyname) {
00105             return NetworkStack::gethostbyname(name, address, version);
00106         }
00107 
00108         nsapi_addr_t addr = {NSAPI_UNSPEC , 0};
00109         nsapi_error_t err = _stack_api()->gethostbyname(_stack(), name, &addr, version);
00110         address->set_addr(addr);
00111         return err;
00112     }
00113 
00114     virtual nsapi_error_t add_dns_server(const SocketAddress &address)
00115     {
00116         if (!_stack_api()->add_dns_server) {
00117             return NetworkStack::add_dns_server(address);
00118         }
00119 
00120         return _stack_api()->add_dns_server(_stack(), address.get_addr());
00121     }
00122 
00123     virtual nsapi_error_t setstackopt(int level, int optname, const void *optval, unsigned optlen)
00124     {
00125         if (!_stack_api()->setstackopt) {
00126             return NSAPI_ERROR_UNSUPPORTED ;
00127         }
00128 
00129         return _stack_api()->setstackopt(_stack(), level, optname, optval, optlen);
00130     }
00131 
00132     virtual nsapi_error_t getstackopt(int level, int optname, void *optval, unsigned *optlen)
00133     {
00134         if (!_stack_api()->getstackopt) {
00135             return NSAPI_ERROR_UNSUPPORTED ;
00136         }
00137 
00138         return _stack_api()->getstackopt(_stack(), level, optname, optval, optlen);
00139     }
00140 
00141 protected:
00142     virtual nsapi_error_t socket_open(nsapi_socket_t *socket, nsapi_protocol_t proto)
00143     {
00144         if (!_stack_api()->socket_open) {
00145             return NSAPI_ERROR_UNSUPPORTED ;
00146         }
00147 
00148         return _stack_api()->socket_open(_stack(), socket, proto);
00149     }
00150 
00151     virtual nsapi_error_t socket_close(nsapi_socket_t socket)
00152     {
00153         if (!_stack_api()->socket_close) {
00154             return NSAPI_ERROR_UNSUPPORTED ;
00155         }
00156 
00157         return _stack_api()->socket_close(_stack(), socket);
00158     }
00159 
00160     virtual nsapi_error_t socket_bind(nsapi_socket_t socket, const SocketAddress &address)
00161     {
00162         if (!_stack_api()->socket_bind) {
00163             return NSAPI_ERROR_UNSUPPORTED ;
00164         }
00165 
00166         return _stack_api()->socket_bind(_stack(), socket, address.get_addr(), address.get_port());
00167     }
00168 
00169     virtual nsapi_error_t socket_listen(nsapi_socket_t socket, int backlog)
00170     {
00171         if (!_stack_api()->socket_listen) {
00172             return NSAPI_ERROR_UNSUPPORTED ;
00173         }
00174 
00175         return _stack_api()->socket_listen(_stack(), socket, backlog);
00176     }
00177 
00178     virtual nsapi_error_t socket_connect(nsapi_socket_t socket, const SocketAddress &address)
00179     {
00180         if (!_stack_api()->socket_connect) {
00181             return NSAPI_ERROR_UNSUPPORTED ;
00182         }
00183 
00184         return _stack_api()->socket_connect(_stack(), socket, address.get_addr(), address.get_port());
00185     }
00186 
00187     virtual nsapi_error_t socket_accept(nsapi_socket_t server, nsapi_socket_t *socket, SocketAddress *address)
00188     {
00189         if (!_stack_api()->socket_accept) {
00190             return NSAPI_ERROR_UNSUPPORTED ;
00191         }
00192 
00193         nsapi_addr_t addr = {NSAPI_IPv4 , 0};
00194         uint16_t port = 0;
00195 
00196         nsapi_error_t err = _stack_api()->socket_accept(_stack(), server, socket, &addr, &port);
00197 
00198         if (address) {
00199             address->set_addr(addr);
00200             address->set_port(port);
00201         }
00202 
00203         return err;
00204     }
00205 
00206     virtual nsapi_size_or_error_t socket_send(nsapi_socket_t socket, const void *data, nsapi_size_t size)
00207     {
00208         if (!_stack_api()->socket_send) {
00209             return NSAPI_ERROR_UNSUPPORTED ;
00210         }
00211 
00212         return _stack_api()->socket_send(_stack(), socket, data, size);
00213     }
00214 
00215     virtual nsapi_size_or_error_t socket_recv(nsapi_socket_t socket, void *data, nsapi_size_t size)
00216     {
00217         if (!_stack_api()->socket_recv) {
00218             return NSAPI_ERROR_UNSUPPORTED ;
00219         }
00220 
00221         return _stack_api()->socket_recv(_stack(), socket, data, size);
00222     }
00223 
00224     virtual nsapi_size_or_error_t socket_sendto(nsapi_socket_t socket, const SocketAddress &address, const void *data, nsapi_size_t size)
00225     {
00226         if (!_stack_api()->socket_sendto) {
00227             return NSAPI_ERROR_UNSUPPORTED ;
00228         }
00229 
00230         return _stack_api()->socket_sendto(_stack(), socket, address.get_addr(), address.get_port(), data, size);
00231     }
00232 
00233     virtual nsapi_size_or_error_t socket_recvfrom(nsapi_socket_t socket, SocketAddress *address, void *data, nsapi_size_t size)
00234     {
00235         if (!_stack_api()->socket_recvfrom) {
00236             return NSAPI_ERROR_UNSUPPORTED ;
00237         }
00238 
00239         nsapi_addr_t addr = {NSAPI_IPv4 , 0};
00240         uint16_t port = 0;
00241 
00242         nsapi_size_or_error_t err = _stack_api()->socket_recvfrom(_stack(), socket, &addr, &port, data, size);
00243 
00244         if (address) {
00245             address->set_addr(addr);
00246             address->set_port(port);
00247         }
00248 
00249         return err;
00250     }
00251 
00252     virtual void socket_attach(nsapi_socket_t socket, void (*callback)(void *), void *data)
00253     {
00254         if (!_stack_api()->socket_attach) {
00255             return;
00256         }
00257 
00258         return _stack_api()->socket_attach(_stack(), socket, callback, data);
00259     }
00260 
00261     virtual nsapi_error_t setsockopt(nsapi_socket_t socket, int level, int optname, const void *optval, unsigned optlen)
00262     {
00263         if (!_stack_api()->setsockopt) {
00264             return NSAPI_ERROR_UNSUPPORTED ;
00265         }
00266 
00267         return _stack_api()->setsockopt(_stack(), socket, level, optname, optval, optlen);
00268     }
00269 
00270     virtual nsapi_error_t getsockopt(nsapi_socket_t socket, int level, int optname, void *optval, unsigned *optlen)
00271     {
00272         if (!_stack_api()->getsockopt) {
00273             return NSAPI_ERROR_UNSUPPORTED ;
00274         }
00275 
00276         return _stack_api()->getsockopt(_stack(), socket, level, optname, optval, optlen);
00277     }
00278 };
00279 
00280 
00281 // Conversion function for network stacks
00282 NetworkStack *nsapi_create_stack(nsapi_stack_t *stack)
00283 {
00284     MBED_STATIC_ASSERT(sizeof stack->_stack_buffer >= sizeof(NetworkStackWrapper),
00285             "The nsapi_stack_t stack buffer must fit a NetworkStackWrapper");
00286     return new (stack->_stack_buffer) NetworkStackWrapper;
00287 }
00288 
00289 NetworkStack *nsapi_create_stack(NetworkStack *stack)
00290 {
00291     return stack;
00292 }
00293