sandbox / mbed-client-classic

Fork of mbed-client-classic by Christopher Haster

Revision:
8:bdd418027540
Parent:
7:774e507fc261
Child:
9:17cb48fbeb85
--- a/source/m2mconnectionhandlerpimpl.cpp	Thu Mar 03 21:47:11 2016 +0000
+++ b/source/m2mconnectionhandlerpimpl.cpp	Sat Apr 02 00:40:01 2016 +0300
@@ -25,8 +25,9 @@
 
 #include "NetworkInterface.h"
 #include "UDPSocket.h"
+#include "mbed-trace/mbed_trace.h"
 
-
+#define TRACE_GROUP "mClt"
 
 M2MConnectionHandlerPimpl::M2MConnectionHandlerPimpl(M2MConnectionHandler* base, M2MConnectionObserver &observer,
                                                      M2MConnectionSecurity* sec,
@@ -38,12 +39,9 @@
  _use_secure_connection(false),
  _binding_mode(mode),
  _network_stack(stack),
- _resolved(true),
- _is_handshaking(false),
  _socket(0),
  _listening(false),
- _listen_thread(0),
- _socket_thread(0)
+ _listen_thread(0)
 {
     memset(&_address_buffer, 0, sizeof _address_buffer);
     memset(&_address, 0, sizeof _address);
@@ -52,45 +50,25 @@
     if (_network_stack != M2MInterface::LwIP_IPv4) {
         error("ConnectionHandler: Unsupported network stack, only IPv4 is currently supported");
     }
-    
-    if (_binding_mode == M2MInterface::TCP ||
-        _binding_mode == M2MInterface::TCP_QUEUE) {
-        error("ConnectionHandler: Unsupported binding mode, only UDP based modes are currently supported");
-    }
-    
-    _running = true;
-    _socket_thread = rtos::create_thread<
-        M2MConnectionHandlerPimpl,
-        &M2MConnectionHandlerPimpl::socket_handler>(this, osPriorityAboveNormal);
-    _listen_thread = rtos::create_thread<
-        M2MConnectionHandlerPimpl,
-        &M2MConnectionHandlerPimpl::listen_handler>(this);    
 }
 
 M2MConnectionHandlerPimpl::~M2MConnectionHandlerPimpl()
 {
     _listening = false;
-    _running = false;
-    
+
     if (_listen_thread) {
         delete _listen_thread;
         _listen_thread = 0;
     }
-    
-    if (_socket_thread) {
-        delete _socket_thread;
-        _socket_thread = 0;
-    }
-    
     if (_socket) {
         delete _socket;
         _socket = 0;
     }
-    
+
     delete _security_impl;
 }
 
-bool M2MConnectionHandlerPimpl::bind_connection(const uint16_t listen_port)
+bool M2MConnectionHandlerPimpl::bind_connection(const uint16_t /*listen_port*/)
 {
     return true;
 }
@@ -100,104 +78,96 @@
                                                        M2MConnectionObserver::ServerType server_type,
                                                        const M2MSecurity* security)
 {
+    bool success = false;
     NetworkInterface *iface = M2MNetwork::getInterface();
     if (!iface) {
         return false;
     }
-    
+
     if (_socket) {
         delete _socket;
     }
-    
+
     _socket = new UDPSocket(iface);
     if (_socket->open(server_address.c_str(), server_port) < 0) {
         return false;
+    } else {
+        success = true;
     }
 
     if (security) {
         if (security->resource_value_int(M2MSecurity::SecurityMode) == M2MSecurity::Certificate ||
             security->resource_value_int(M2MSecurity::SecurityMode) == M2MSecurity::Psk) {
-            if (_security_impl != NULL) {
+            if( _security_impl != NULL ){
                 _security_impl->reset();
                 _security_impl->init(security);
-                
-                if (_security_impl->connect(_base) < 0) {
-                    return false;
+                tr_debug("M2MConnectionHandlerPimpl::resolve_server_address - connect DTLS");
+                success = 0 == _security_impl->connect(_base);
+                if( success ) {
+                    _use_secure_connection = true;
                 }
-                
-                _use_secure_connection = true;
             }
         }
     }
-    
-    _address._address = (void*)_socket->getIPAddress();
-    _address._length = strlen((char*)_address._address);
-    _address._port = _socket->getPort();
-    _address._stack = _network_stack;
-    
-    _observer.address_ready(_address,
-                            server_type,
-                            _address._port);
-    
-    return true;
-}
-
+    if(success) {
+        _address._address = (void*)_socket->getIPAddress();
+        _address._length = strlen((char*)_address._address);
+        _address._port = _socket->getPort();
+        _address._stack = _network_stack;
 
-void M2MConnectionHandlerPimpl::socket_handler()
-{
-    while (_running) {
-        if (!_socket || !_socket->isConnected()) {
-            rtos::Thread::wait(1000);
-            continue;
-        }
-        
-        // check recvs
-        int size = _socket->recv((char*)_recv_buffer, sizeof _recv_buffer, false);
-        if (size > 0) {
-            _recv_queue.put(new std::string(_recv_buffer, _recv_buffer+size));
-            continue;
-        }
-        
-        // check sends
-        osEvent e = _send_queue.get(0);
-        if (e.status == osEventMessage) {
-            std::string *packet = (std::string*)e.value.p;
-            int size = _socket->send((char*)packet->data(), packet->size());
-            delete packet;
-            continue;
-        }
-        
-        // no activity
-        rtos::Thread::wait(10);
+        _observer.address_ready(_address,
+                                server_type,
+                                _address._port);
     }
+    return success;
 }
 
-
 bool M2MConnectionHandlerPimpl::send_data(uint8_t *data,
                                           uint16_t data_len,
                                           sn_nsdl_addr_s *address)
 {
+    tr_debug("M2MConnectionHandlerPimpl::send_data");
     if (address == NULL || data == NULL) {
         return false;
     }
-    
-    if (_use_secure_connection) {
-        if (_security_impl->send_message(data, data_len) < 0) {
-            return false;
-        }
-    } else {
-        if (send_to_socket(data, data_len) < 0) {
-            return false;
+
+    bool success = false;
+    if(data){
+        if( _use_secure_connection ){
+            if( _security_impl->send_message(data, data_len) > 0){
+                success = true;
+                _observer.data_sent();
+            }else{
+                _observer.socket_error(1);
+            }
+        } else {
+            if(address) {
+                ssize_t ret = -1;
+
+                ret = _socket->send(data, data_len);
+
+                if (ret==-1) {
+                    //tr_debug("M2MConnectionHandlerPimpl::send_data - Error Code is %d\n",errno);
+                    _observer.socket_error(1);
+                } else {
+                     success = true;
+                    _observer.data_sent();
+                }
+            } else {
+                //TODO: Define memory fail error code
+                _observer.socket_error(3);
+            }
         }
     }
-    
-    _observer.data_sent();
-    return true;
+    return success;
 }
 
 bool M2MConnectionHandlerPimpl::start_listening_for_data()
 {
     _listening = true;
+    _listen_thread = rtos::create_thread<
+        M2MConnectionHandlerPimpl,
+        &M2MConnectionHandlerPimpl::listen_handler>(this);
     return true;
 }
 
@@ -208,58 +178,59 @@
 
 void M2MConnectionHandlerPimpl::listen_handler()
 {
-    while (_running) {
-        if (!_listening) {
-            rtos::Thread::wait(1000);
-            continue;
+    tr_debug("M2MConnectionHandlerPimpl::listen_handler");
+    memset(_recv_buffer, 0, sizeof(_recv_buffer));
+    int rcv_size = -1;
+
+    if (_use_secure_connection) {
+        while(_listening){
+             rcv_size = _security_impl->read(_recv_buffer, sizeof(_recv_buffer));
+            if(rcv_size > 0) {
+                _observer.data_available(_recv_buffer, rcv_size, _address);
+            }
+            else if(rcv_size == 0){
+                //We are in initializing phase, so do nothing
+            }
+            else{
+                _listening = false;
+                _observer.socket_error(1);
+            }
+            memset(_recv_buffer, 0, sizeof(_recv_buffer));
         }
-            
-        memset(_listen_buffer, 0, sizeof _listen_buffer);
-        int size;
-            
-        if (_use_secure_connection) {
-            size = _security_impl->read(_listen_buffer, sizeof _listen_buffer);
-        } else {
-            size = receive_from_socket(_listen_buffer, sizeof _listen_buffer);
-        }
-            
-        if (size > 0) {
-            _observer.data_available((uint8_t*)_listen_buffer, size, _address);
-        } else if (size != 0) {
-            _listening = false;
-            _observer.socket_error(2);
+    } else {
+        while(_listening) {
+            int rcv_size = _socket->recv((char*)_recv_buffer, sizeof _recv_buffer, true);
+            if (rcv_size == -1) {
+               //TODO: Define receive error code
+                _observer.socket_error(2);
+                _listening = false;
+            }
+
+            /* If message received.. */
+            if(rcv_size > 0) {
+                _observer.data_available(_recv_buffer,rcv_size,_address);
+            }
+            memset(_recv_buffer, 0, sizeof(_recv_buffer));
         }
     }
 }
 
-
 int M2MConnectionHandlerPimpl::send_to_socket(const unsigned char *buf, size_t len)
 {
-    if (_send_queue.put(new std::string(buf, buf+len)) != osOK) {
-        return M2MConnectionHandler::CONNECTION_ERROR_WANTS_WRITE;
-    } else {
-        return len;
-    }
+    tr_debug("M2MConnectionHandlerPimpl::send_to_socket len - %d", len);
+    int size = _socket->send(buf,len);
+    tr_debug("M2MConnectionHandlerPimpl::send_to_socket size - %d", size);
+    return size;
 }
 
 int M2MConnectionHandlerPimpl::receive_from_socket(unsigned char *buf, size_t len)
 {
-    osEvent e = _recv_queue.get();
-    if (e.status == osEventMessage) {
-        std::string *packet = (std::string*)e.value.p;
-        int size = packet->size();
-        
-        if (size <= len) {
-            memcpy(buf, packet->data(), size);
-            delete packet;
-            return size;
-        }
-    }
-    
-    return M2MConnectionHandler::CONNECTION_ERROR_WANTS_READ;
+    tr_debug("M2MConnectionHandlerPimpl::receive_from_socket - blocking call");
+    return _socket->recv(buf, len);
 }
 
 void M2MConnectionHandlerPimpl::handle_connection_error(int /*error*/)
 {
+    tr_debug("M2MConnectionHandlerPimpl::handle_connection_error");
     _observer.socket_error(4);
 }