From 8922eeb01424df8abd60e2e6eaacd5515ea21cb1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Teppo=20J=C3=A4rvelin?= Date: Tue, 28 May 2019 13:55:18 +0300 Subject: [PATCH] Cellular: add method to set authentication type to CellularContext Authentication type must be able to set. It was hard coded to CHAP. Added unit tests for CellularContext to be able to add test for new function. --- .../cellularcontext/cellularcontexttest.cpp | 307 ++++++++++++++++++ .../device/cellularcontext/unittest.cmake | 42 +++ UNITTESTS/stubs/CellularContext_stub.cpp | 5 + UNITTESTS/stubs/CellularDevice_stub.cpp | 24 +- UNITTESTS/stubs/CellularDevice_stub.h | 4 + UNITTESTS/stubs/ControlPlane_netif_stub.h | 7 +- UNITTESTS/stubs/ThisThread_stub.cpp | 4 + UNITTESTS/target_h/myCellularDevice.h | 14 +- .../cellular/framework/API/CellularContext.h | 6 + .../framework/device/CellularContext.cpp | 5 + 10 files changed, 412 insertions(+), 6 deletions(-) create mode 100644 UNITTESTS/features/cellular/framework/device/cellularcontext/cellularcontexttest.cpp create mode 100644 UNITTESTS/features/cellular/framework/device/cellularcontext/unittest.cmake diff --git a/UNITTESTS/features/cellular/framework/device/cellularcontext/cellularcontexttest.cpp b/UNITTESTS/features/cellular/framework/device/cellularcontext/cellularcontexttest.cpp new file mode 100644 index 00000000000..8e913582301 --- /dev/null +++ b/UNITTESTS/features/cellular/framework/device/cellularcontext/cellularcontexttest.cpp @@ -0,0 +1,307 @@ +/* + * Copyright (c) 2018, Arm Limited and affiliates. + * SPDX-License-Identifier: Apache-2.0 + * + * Licensed 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 "gtest/gtest.h" +#include + +#include "CellularContext.h" +#include "CellularDevice_stub.h" +#include "ControlPlane_netif_stub.h" +#include "myCellularDevice.h" + +using namespace mbed; + +// AStyle ignored as the definition is not clear due to preprocessor usage +// *INDENT-OFF* +class TestCellularContext : public testing::Test { +protected: + + void SetUp() + { + CellularDevice_stub::create_in_get_default = true; + } + + void TearDown() + { + } +}; + +class testContext : public CellularContext +{ +public: + + testContext(CellularDevice *dev = NULL) + { + _device = dev; + _cp_netif = new ControlPlane_netif_stub(); + } + + ~testContext() + { + delete _cp_netif; + } + int get_retry_count() + { + return _retry_count; + } + CellularContext::AuthenticationType get_auth_type() + { + return _authentication_type; + } + nsapi_error_t set_blocking(bool blocking) + { + _is_blocking = blocking; + return NSAPI_ERROR_OK; + } + + NetworkStack *get_stack() + { + return NULL; + } + + const char *get_ip_address() + { + return NULL; + } + virtual void attach(mbed::Callback status_cb) + { + _status_cb = status_cb; + } + virtual nsapi_error_t connect() + { + return NSAPI_ERROR_OK; + } + + virtual nsapi_error_t disconnect() + { + return NSAPI_ERROR_OK; + } + + virtual void set_plmn(const char *plmn) + { + } + virtual void set_sim_pin(const char *sim_pin) + { + } + virtual nsapi_error_t connect(const char *sim_pin, const char *apn = 0, const char *uname = 0, + const char *pwd = 0) + { + return NSAPI_ERROR_OK; + } + virtual void set_credentials(const char *apn, const char *uname = 0, const char *pwd = 0) + { + } + virtual const char *get_netmask() + { + return NULL; + } + virtual const char *get_gateway() + { + return NULL; + } + virtual bool is_connected() + { + return false; + } + nsapi_error_t set_device_ready() + { + return NSAPI_ERROR_OK; + } + nsapi_error_t set_sim_ready() + { + return NSAPI_ERROR_OK; + } + nsapi_error_t register_to_network() + { + return NSAPI_ERROR_OK; + } + nsapi_error_t attach_to_network() + { + return NSAPI_ERROR_OK; + } + nsapi_error_t get_rate_control(CellularContext::RateControlExceptionReports &reports, + CellularContext::RateControlUplinkTimeUnit &time_unit, int &uplink_rate) + { + return NSAPI_ERROR_OK; + } + nsapi_error_t get_pdpcontext_params(pdpContextList_t ¶ms_list) + { + return NSAPI_ERROR_OK; + } + nsapi_error_t get_apn_backoff_timer(int &backoff_timer) + { + return NSAPI_ERROR_OK; + } + void set_file_handle(FileHandle *fh) + { + + } +#if (DEVICE_SERIAL && DEVICE_INTERRUPTIN) || defined(DOXYGEN_ONLY) + virtual void set_file_handle(UARTSerial *serial, PinName dcd_pin = NC, bool active_high = false) + { + + } +#endif + ControlPlane_netif *get_cp_netif() + { + return _cp_netif; + } + void cellular_callback(nsapi_event_t ev, intptr_t ptr) + { + + } + void enable_hup(bool enable) + { + + } + + void cp_data_received() + { + CellularContext::cp_data_received(); + } + + virtual void do_connect() + { + } + + void set_cell_callback_data(cell_callback_data_t &cb_data) + { + _cb_data = cb_data; + } + + void do_connect_with_retry() + { + CellularContext::do_connect_with_retry(); + } +}; + +static int network_cb_count = 0; +static void network_cb(nsapi_event_t ev, intptr_t intptr) +{ + network_cb_count++; +} + +// *INDENT-ON* +TEST_F(TestCellularContext, test_create_delete) +{ + CellularDevice_stub::create_in_get_default = false; + CellularContext *ctx = CellularContext::get_default_instance(); + EXPECT_TRUE(ctx == NULL); + + ctx = CellularContext::get_default_nonip_instance(); + EXPECT_TRUE(ctx == NULL); + + CellularDevice_stub::create_in_get_default = true; + ctx = CellularContext::get_default_instance(); + EXPECT_TRUE(ctx != NULL); + + ctx = CellularContext::get_default_nonip_instance(); + EXPECT_TRUE(ctx != NULL); +} + +TEST_F(TestCellularContext, get_device) +{ + CellularContext *ctx = CellularContext::get_default_instance(); + EXPECT_TRUE(ctx != NULL); + + CellularDevice *dev = ctx->get_device(); + EXPECT_TRUE(dev != NULL); +} + +TEST_F(TestCellularContext, get_cid) +{ + CellularContext *ctx = CellularContext::get_default_instance(); + EXPECT_TRUE(ctx != NULL); + + int cid = ctx->get_cid(); + ASSERT_EQ(cid, -1); +} + +TEST_F(TestCellularContext, set_authentication_type) +{ + testContext *ctx = new testContext(); + EXPECT_TRUE(ctx != NULL); + + ASSERT_EQ(ctx->get_auth_type(), CellularContext::CHAP); + ctx->set_authentication_type(CellularContext::PAP); + ASSERT_EQ(ctx->get_auth_type(), CellularContext::PAP); + + delete ctx; +} + +TEST_F(TestCellularContext, cp_data_received) +{ + testContext *ctx = new testContext(); + EXPECT_TRUE(ctx != NULL); + + ControlPlane_netif_stub *netif = (ControlPlane_netif_stub *)ctx->get_cp_netif(); + EXPECT_TRUE(!netif->cp_data_received_called); + ctx->cp_data_received(); + EXPECT_TRUE(netif->cp_data_received_called); + + delete ctx; +} + +TEST_F(TestCellularContext, do_connect_with_retry) +{ + testContext *ctx = new testContext(); + EXPECT_TRUE(ctx != NULL); + ctx->attach(network_cb); + + cell_callback_data_t cb_data; + cb_data.final_try = true; + ctx->set_cell_callback_data(cb_data); + ctx->do_connect_with_retry(); + ASSERT_EQ(network_cb_count, 0); + + cb_data.error = NSAPI_ERROR_OK; + cb_data.final_try = false; + ctx->set_cell_callback_data(cb_data); + ctx->do_connect_with_retry(); + + CellularDevice_stub::retry_array_length = 2; + cb_data.error = NSAPI_ERROR_DEVICE_ERROR; + cb_data.final_try = false; + ctx->set_cell_callback_data(cb_data); + ctx->do_connect_with_retry(); + ASSERT_EQ(ctx->get_retry_count(), 2); + + delete ctx; +} + +TEST_F(TestCellularContext, do_connect_with_retry_async) +{ + myCellularDevice *dev = new myCellularDevice(0); + testContext *ctx = new testContext(dev); + EXPECT_TRUE(ctx != NULL); + ctx->attach(network_cb); + ASSERT_EQ(NSAPI_ERROR_OK, ctx->set_blocking(false)); + + cell_callback_data_t cb_data; + CellularDevice_stub::retry_array_length = 2; + cb_data.error = NSAPI_ERROR_DEVICE_ERROR; + cb_data.final_try = false; + ctx->set_cell_callback_data(cb_data); + ctx->do_connect_with_retry(); + ASSERT_EQ(ctx->get_retry_count(), 1); + + delete ctx; + delete dev; +} + + + + diff --git a/UNITTESTS/features/cellular/framework/device/cellularcontext/unittest.cmake b/UNITTESTS/features/cellular/framework/device/cellularcontext/unittest.cmake new file mode 100644 index 00000000000..b85f32586eb --- /dev/null +++ b/UNITTESTS/features/cellular/framework/device/cellularcontext/unittest.cmake @@ -0,0 +1,42 @@ + +#################### +# UNIT TESTS +#################### + +# Add test specific include paths +set(unittest-includes ${unittest-includes} + /features/cellular/framework/device/cellulardevice + ../features/cellular/framework/device + ../features/cellular/framework/common + ../features/netsocket/cellular +) + +# Source files +set(unittest-sources + ../features/cellular/framework/device/CellularContext.cpp +) + +# Test files +set(unittest-test-sources + features/cellular/framework/device/cellularcontext/cellularcontexttest.cpp + stubs/FileHandle_stub.cpp + stubs/CellularStateMachine_stub.cpp + stubs/EventQueue_stub.cpp + stubs/mbed_assert_stub.c + stubs/UARTSerial_stub.cpp + stubs/SerialBase_stub.cpp + stubs/ATHandler_stub.cpp + stubs/AT_CellularNetwork_stub.cpp + stubs/AT_CellularBase_stub.cpp + stubs/AT_CellularContext_stub.cpp + stubs/Semaphore_stub.cpp + stubs/NetworkInterface_stub.cpp + stubs/NetworkInterfaceDefaults_stub.cpp + stubs/CellularDevice_stub.cpp + stubs/equeue_stub.c + stubs/ThisThread_stub.cpp +) + +# defines +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DMDMRTS=PTC0 -DMDMCTS=PTC1 -DMDMTXD=NC -DMDMRXD=NC -DMBED_CONF_PLATFORM_DEFAULT_SERIAL_BAUD_RATE=115200 -DCELLULAR_DEVICE=myCellularDevice -DDEVICE_SERIAL_FC=1 -DMBED_CONF_CELLULAR_CONTROL_PLANE_OPT=0") +set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DMDMRTS=PTC0 -DMDMCTS=PTC1 -DMDMTXD=NC -DMDMRXD=NC -DMBED_CONF_PLATFORM_DEFAULT_SERIAL_BAUD_RATE=115200 -DCELLULAR_DEVICE=myCellularDevice -DDEVICE_SERIAL_FC=1 -DMBED_CONF_CELLULAR_CONTROL_PLANE_OPT=0") diff --git a/UNITTESTS/stubs/CellularContext_stub.cpp b/UNITTESTS/stubs/CellularContext_stub.cpp index 156016a03b9..f976643848d 100644 --- a/UNITTESTS/stubs/CellularContext_stub.cpp +++ b/UNITTESTS/stubs/CellularContext_stub.cpp @@ -43,6 +43,11 @@ int CellularContext::get_cid() const return _cid; } +void CellularContext::set_authentication_type(AuthenticationType type) +{ + _authentication_type = type; +} + void CellularContext::do_connect_with_retry() { do_connect(); diff --git a/UNITTESTS/stubs/CellularDevice_stub.cpp b/UNITTESTS/stubs/CellularDevice_stub.cpp index a0aeb850aba..0d89887cbdc 100644 --- a/UNITTESTS/stubs/CellularDevice_stub.cpp +++ b/UNITTESTS/stubs/CellularDevice_stub.cpp @@ -15,19 +15,26 @@ * limitations under the License. */ -#include "CellularDevice.h" #include "CellularDevice_stub.h" #include "events/EventQueue.h" #include "CellularUtil.h" +#include "myCellularDevice.h" using namespace mbed; int CellularDevice_stub::connect_counter = -1; - +bool CellularDevice_stub::create_in_get_default = false; +uint16_t CellularDevice_stub::retry_timeout_array[CELLULAR_RETRY_ARRAY_SIZE] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; +int CellularDevice_stub::retry_array_length = 0; MBED_WEAK CellularDevice *CellularDevice::get_default_instance() { - return NULL; + if (CellularDevice_stub::create_in_get_default) { + static myCellularDevice dev(NULL); + return &dev; + } else { + return NULL; + } } CellularDevice::CellularDevice(FileHandle *fh) : _network_ref_count(0), _sms_ref_count(0), @@ -58,6 +65,17 @@ CellularContext *CellularDevice::get_context_list() const return NULL; } +void CellularDevice::get_retry_timeout_array(uint16_t *timeout, int &array_len) const +{ + array_len = CellularDevice_stub::retry_array_length; + + if (CellularDevice_stub::retry_array_length == 0) { + timeout = 0; + } else { + timeout = CellularDevice_stub::retry_timeout_array; + } +} + nsapi_error_t CellularDevice::set_device_ready() { return NSAPI_ERROR_OK; diff --git a/UNITTESTS/stubs/CellularDevice_stub.h b/UNITTESTS/stubs/CellularDevice_stub.h index 6e865e353cb..b8aa69e00c4 100644 --- a/UNITTESTS/stubs/CellularDevice_stub.h +++ b/UNITTESTS/stubs/CellularDevice_stub.h @@ -17,9 +17,13 @@ #ifndef CELLULARDEVICE_STUB_H_ #define CELLULARDEVICE_STUB_H_ +#include "CellularDevice.h" namespace CellularDevice_stub { extern int connect_counter; +extern bool create_in_get_default; +extern uint16_t retry_timeout_array[CELLULAR_RETRY_ARRAY_SIZE]; +extern int retry_array_length; } diff --git a/UNITTESTS/stubs/ControlPlane_netif_stub.h b/UNITTESTS/stubs/ControlPlane_netif_stub.h index 52661c52b87..d473056ec6e 100644 --- a/UNITTESTS/stubs/ControlPlane_netif_stub.h +++ b/UNITTESTS/stubs/ControlPlane_netif_stub.h @@ -24,10 +24,12 @@ class ControlPlane_netif_stub : public ControlPlane_netif { public: std::list return_values; nsapi_error_t return_value; + bool cp_data_received_called; ControlPlane_netif_stub() { return_value = 0; + cp_data_received_called = false; } protected: @@ -51,7 +53,10 @@ class ControlPlane_netif_stub : public ControlPlane_netif { return return_value; }; - virtual void data_received() {}; + virtual void data_received() + { + cp_data_received_called = true; + }; virtual void attach(void (*callback)(void *), void *data) {}; }; diff --git a/UNITTESTS/stubs/ThisThread_stub.cpp b/UNITTESTS/stubs/ThisThread_stub.cpp index 28eb18fa8bc..e829dbbdb46 100644 --- a/UNITTESTS/stubs/ThisThread_stub.cpp +++ b/UNITTESTS/stubs/ThisThread_stub.cpp @@ -23,4 +23,8 @@ void ThisThread::sleep_until(uint64_t millisec) { } +void ThisThread::sleep_for(uint32_t millisec) +{ +} + } diff --git a/UNITTESTS/target_h/myCellularDevice.h b/UNITTESTS/target_h/myCellularDevice.h index 16c96d8b286..ff99be062cd 100644 --- a/UNITTESTS/target_h/myCellularDevice.h +++ b/UNITTESTS/target_h/myCellularDevice.h @@ -54,17 +54,27 @@ class myCellularDevice : public CellularDevice { virtual CellularContext *create_context(UARTSerial *serial, const char *const apn, PinName dcd_pin, bool active_high, bool cp_req = false, bool nonip_req = false) { - return NULL; + if (_context_list) { + return _context_list; + } + EventQueue que; + ATHandler at(serial, que, 0, ","); + _context_list = new AT_CellularContext(at, this); + return _context_list; } virtual CellularContext *create_context(FileHandle *fh = NULL, const char *apn = NULL, bool cp_req = false, bool nonip_req = false) { + if (_context_list) { + return _context_list; + } EventQueue que; FileHandle_stub fh1; ATHandler at(&fh1, que, 0, ","); - _context_list = new AT_CellularContext(at, NULL); + _context_list = new AT_CellularContext(at, this); return _context_list; } + virtual void delete_context(CellularContext *context) { delete _context_list; diff --git a/features/cellular/framework/API/CellularContext.h b/features/cellular/framework/API/CellularContext.h index fb8765f03cc..947461f5dd0 100644 --- a/features/cellular/framework/API/CellularContext.h +++ b/features/cellular/framework/API/CellularContext.h @@ -289,6 +289,12 @@ class CellularContext : public CellularInterface { */ int get_cid() const; + /** Set the authentication type to be used in user authentication if user name and password are defined + * + * @param type enum AuthenticationType + */ + void set_authentication_type(AuthenticationType type); + protected: // Device specific implementations might need these so protected enum ContextOperation { OP_INVALID = -1, diff --git a/features/cellular/framework/device/CellularContext.cpp b/features/cellular/framework/device/CellularContext.cpp index 665cc2c8442..0b4ea68bd94 100644 --- a/features/cellular/framework/device/CellularContext.cpp +++ b/features/cellular/framework/device/CellularContext.cpp @@ -82,6 +82,11 @@ int CellularContext::get_cid() const return _cid; } +void CellularContext::set_authentication_type(AuthenticationType type) +{ + _authentication_type = type; +} + void CellularContext::do_connect_with_retry() { if (_cb_data.final_try) {