Пример #1
0
uint32_t coap_transport_write(const coap_port_t    * p_port,
                              const coap_remote_t  * p_remote,
                              const uint8_t        * p_data,
                              uint16_t               datalen)
{

    err_t err = NRF_ERROR_NOT_FOUND;
    uint32_t index;

    NULL_PARAM_CHECK(p_port);
    NULL_PARAM_CHECK(p_remote);
    NULL_PARAM_CHECK(p_data);

	//Search for the corresponding port.
    for (index = 0; index < COAP_PORT_COUNT; index++)
    {
        if (m_port_table[index].port_number == p_port->port_number)
        {
		    //Allocate Buffer to send the data on port.
            struct pbuf * lwip_buffer = pbuf_alloc(PBUF_TRANSPORT, datalen, PBUF_RAM);

            if (NULL != lwip_buffer)
            {
			    //Make a copy of the data onto the buffer.
                memcpy(lwip_buffer->payload, p_data, datalen);

                COAP_MUTEX_UNLOCK();

				//Send on UDP port.
                err = udp_sendto(m_port_table[index].p_socket,
                                 lwip_buffer,
                                 (ip6_addr_t *)p_remote->addr,
                                 p_remote->port_number);

                COAP_MUTEX_LOCK();


                if (err != ERR_OK)
                {
				    //Free the allocated buffer as send procedure has failed.
                    err = NRF_ERROR_INTERNAL;
                }
                UNUSED_VARIABLE(pbuf_free(lwip_buffer));
            }
            else
            {
			    //Buffer allocation failed, cannot send data.
                err = NRF_ERROR_NO_MEM;
            }
            break;
        }
    }
    return err;
}
Пример #2
0
/**
 * @breif Creates DTLS session between remote and local endpoint.
 *
 * @param[in]  local_port_index    Identifies local endpoint.
 * @param[in]  role                Identifies DTLS role to be played (server or client).
 * @param[in]  p_remote            Identifies remote endpoint.
 * @param[in]  p_settings          Security settings to be used for the session.
 * @param[out] pp_session          Pointer to the session created (if any).
 *
 * @retval NRF_SUCCESS is procedure succeeded else an error code indicating reason for failure.
 */
static uint32_t session_create(uint32_t                       local_port_index,
                               nrf_tls_role_t                 role,
                               const coap_remote_t    * const p_remote,
                               nrf_tls_key_settings_t * const p_settings,
                               coap_remote_session_t  **      pp_session)
{
    uint32_t err_code = NRF_ERROR_NO_MEM;

    for (uint32_t index = 0; index < COAP_MAX_REMOTE_SESSION; index++)
    {
        if (m_remote_session[index].remote_endpoint.port_number == 0)
        {
            // Found free session.
            m_remote_session[index].remote_endpoint.port_number = p_remote->port_number;
            memcpy(m_remote_session[index].remote_endpoint.addr, p_remote->addr, IPV6_ADDR_SIZE);
            m_remote_session[index].local_port_index = local_port_index;

            // Attempt Allocate TLS session.
            const nrf_tls_options_t dtls_options =
            {
                .output_fn      = dtls_output_handler,
                .transport_type = NRF_TLS_TYPE_DATAGRAM,
                .role           = role,
                .p_key_settings = p_settings
            };

            m_remote_session[index].dtls_instance.transport_id = index;
            
            COAP_MUTEX_UNLOCK();

            err_code = nrf_tls_alloc(&m_remote_session[index].dtls_instance, &dtls_options);
            
            COAP_MUTEX_LOCK();

            COAPT_TRC("[CoAP-DTLS]:[%p]: nrf_tls_alloc result %08x\r\n",
                       &m_remote_session[index],
                       err_code);

            // TLS allocation succeeded, book keep information for endpoint.
            if (err_code == NRF_SUCCESS)
            {
                (*pp_session) = &m_remote_session[index];
                break;
            }
            else
            {
                // If free the session and notify failure.
                remote_session_init(&m_remote_session[index]);
            }
        }
    }
Пример #3
0
/**@brief Callback handler to receive data on the UDP port.
 *
 * @details Callback handler to receive data on the UDP port.
 *
 * @param[in]   p_arg            Receive argument associated with the UDP socket.
 * @param[in]   p_socket         Socket identifier.
 * @param[in]   p_ip_header      IPv6 header containing source and destination addresses.
 * @param[in]   p_remote_addr    IPv6 address of the remote device.
 * @param[in]   port             Port number identifying the remote endpoint.
 *
 * @retval NRF_SUCCESS          Indicates received data was handled successfully, else an an
 *                              error code indicating reason for failure.
 */
static void udp_recv_data_handler(void                 * p_arg,
                                  struct udp_pcb       * p_socket,
                                  struct pbuf          * p_buffer,
                                  const ip6_addr_t     * p_remote_addr,
                                  u16_t                  port)
{
    uint32_t                index;
    coap_remote_t           remote_endpoint;
    coap_port_t             local_port = {p_socket->local_port};

    for (index = 0; index < COAP_PORT_COUNT; index++)
    {
        if (m_port_table[index].p_socket == p_socket)
        {
            memcpy (remote_endpoint.addr, p_remote_addr, 16);
            remote_endpoint.port_number = port;

            COAP_MUTEX_LOCK();

            UNUSED_VARIABLE(coap_transport_read(&local_port,
                                         &remote_endpoint,
                                         NULL,
                                         NRF_SUCCESS,
                                         (uint8_t *)p_buffer->payload,
                                         (uint32_t)p_buffer->len));

            COAP_MUTEX_UNLOCK();

            break;
        }
    }

    //Freeing packet (irrespective of matching p_socket is found or not
    //to avoid memory leaks in the system.
    UNUSED_VARIABLE(pbuf_free(p_buffer));
}