Skip to content

Commit 10f2c05

Browse files
authored
Merge pull request #9898 from jarvte/connect_disconnect_fix
Cellular: fix connect-disconnect sequence called many times
2 parents f559d03 + 0905f01 commit 10f2c05

File tree

12 files changed

+93
-82
lines changed

12 files changed

+93
-82
lines changed

UNITTESTS/features/cellular/framework/AT/at_cellularnetwork/at_cellularnetworktest.cpp

Lines changed: 0 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -653,20 +653,6 @@ TEST_F(TestAT_CellularNetwork, test_AT_CellularNetwork_attach)
653653
cn.attach(&network_cb);
654654
}
655655

656-
TEST_F(TestAT_CellularNetwork, test_get_connection_status)
657-
{
658-
EventQueue que;
659-
FileHandle_stub fh1;
660-
ATHandler at(&fh1, que, 0, ",");
661-
662-
AT_CellularNetwork cn(at);
663-
664-
ATHandler_stub::nsapi_error_value = NSAPI_ERROR_OK;
665-
network_cb_count = 0;
666-
cn.attach(&network_cb);
667-
EXPECT_TRUE(NSAPI_STATUS_DISCONNECTED == cn.get_connection_status());
668-
}
669-
670656
TEST_F(TestAT_CellularNetwork, test_AT_CellularNetwork_set_receive_period)
671657
{
672658
EventQueue que;

UNITTESTS/stubs/AT_CellularNetwork_stub.cpp

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -44,11 +44,6 @@ void AT_CellularNetwork::attach(Callback<void(nsapi_event_t, intptr_t)> status_c
4444
{
4545
}
4646

47-
nsapi_connection_status_t AT_CellularNetwork::get_connection_status() const
48-
{
49-
return NSAPI_STATUS_LOCAL_UP;
50-
}
51-
5247
nsapi_error_t AT_CellularNetwork::set_registration_urc(RegistrationType type, bool urc_on)
5348
{
5449
if (AT_CellularNetwork_stub::set_registration_urc_fail_counter) {

UNITTESTS/stubs/CellularDevice_stub.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -103,6 +103,6 @@ nsapi_error_t CellularDevice::shutdown()
103103
return NSAPI_ERROR_OK;
104104
}
105105

106-
void CellularDevice::cellular_callback(nsapi_event_t ev, intptr_t ptr)
106+
void CellularDevice::cellular_callback(nsapi_event_t ev, intptr_t ptr, CellularContext *ctx)
107107
{
108108
}

features/cellular/framework/API/CellularContext.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,8 @@ class CellularContext : public CellularInterface {
133133
* The parameters on the callback are the event type and event type dependent reason parameter.
134134
*
135135
* @remark deleting CellularDevice/CellularContext in callback is not allowed.
136+
* @remark Allocating/adding lots of traces not recommended as callback is called mostly from State machines thread which
137+
* is now 2048. You can change to main thread for example via EventQueue.
136138
*
137139
* @param status_cb The callback for status changes.
138140
*/

features/cellular/framework/API/CellularDevice.h

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -283,8 +283,8 @@ class CellularDevice {
283283
* The parameters on the callback are the event type and event-type dependent reason parameter.
284284
*
285285
* @remark deleting CellularDevice/CellularContext in callback not allowed.
286-
* @remark application should not attach to this function if using CellularContext::attach as it will contain the
287-
* same information.
286+
* @remark Allocating/adding lots of traces not recommended as callback is called mostly from State machines thread which
287+
* is now 2048. You can change to main thread for example via EventQueue.
288288
*
289289
* @param status_cb The callback for status changes.
290290
*/
@@ -420,8 +420,8 @@ class CellularDevice {
420420
* This method will broadcast to every interested classes:
421421
* CellularContext (might be many) and CellularStateMachine if available.
422422
*/
423-
void cellular_callback(nsapi_event_t ev, intptr_t ptr);
424-
423+
void cellular_callback(nsapi_event_t ev, intptr_t ptr, CellularContext *ctx = NULL);
424+
void stm_callback(nsapi_event_t ev, intptr_t ptr);
425425
int _network_ref_count;
426426
int _sms_ref_count;
427427
int _info_ref_count;

features/cellular/framework/API/CellularNetwork.h

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -319,16 +319,14 @@ class CellularNetwork {
319319
* on the network. The parameters on the callback are the event type and
320320
* event-type dependent reason parameter.
321321
*
322+
* @remark Application should not call attach if using CellularContext class. Call instead CellularContext::attach
323+
* as CellularDevice is dependent of this attach if CellularContext/CellularDevice is used to get
324+
* device/sim ready, registered, attached, connected.
325+
*
322326
* @param status_cb The callback for status changes
323327
*/
324328
virtual void attach(mbed::Callback<void(nsapi_event_t, intptr_t)> status_cb) = 0;
325329

326-
/** Get the connection status
327-
*
328-
* @return The connection status according to ConnectionStatusType
329-
*/
330-
virtual nsapi_connection_status_t get_connection_status() const = 0;
331-
332330
/** Read operator names
333331
*
334332
* @param op_names on successful return contains linked list of operator names.

features/cellular/framework/AT/ATHandler.cpp

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1256,22 +1256,27 @@ void ATHandler::debug_print(const char *p, int len)
12561256
bool ATHandler::sync(int timeout_ms)
12571257
{
12581258
tr_debug("AT sync");
1259+
lock();
1260+
uint32_t timeout = _at_timeout;
1261+
_at_timeout = timeout_ms;
12591262
// poll for 10 seconds
12601263
for (int i = 0; i < 10; i++) {
1261-
lock();
1262-
set_at_timeout(timeout_ms, false);
12631264
// For sync use an AT command that is supported by all modems and likely not used frequently,
12641265
// especially a common response like OK could be response to previous request.
1266+
clear_error();
1267+
_start_time = rtos::Kernel::get_ms_count();
12651268
cmd_start("AT+CMEE?");
12661269
cmd_stop();
12671270
resp_start("+CMEE:");
12681271
resp_stop();
1269-
restore_at_timeout();
1270-
unlock();
12711272
if (!_last_err) {
1273+
_at_timeout = timeout;
1274+
unlock();
12721275
return true;
12731276
}
12741277
}
12751278
tr_error("AT sync failed");
1279+
_at_timeout = timeout;
1280+
unlock();
12761281
return false;
12771282
}

features/cellular/framework/AT/AT_CellularContext.cpp

Lines changed: 40 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -498,7 +498,6 @@ nsapi_error_t AT_CellularContext::activate_context()
498498
if (err != NSAPI_ERROR_OK) {
499499
_at.unlock();
500500
tr_error("Failed to activate network context! (%d)", err);
501-
call_network_cb(NSAPI_STATUS_DISCONNECTED);
502501
return err;
503502
}
504503

@@ -551,16 +550,18 @@ void AT_CellularContext::do_connect()
551550
{
552551
if (!_is_context_active) {
553552
_cb_data.error = do_activate_context();
553+
} else {
554+
_cb_data.error = NSAPI_ERROR_OK;
555+
}
556+
554557
#if !NSAPI_PPP_AVAILABLE
555-
// in PPP mode we did not activate any context, just searched the correct _cid
556-
if (_status_cb) {
557-
_status_cb((nsapi_event_t)CellularActivatePDPContext, (intptr_t)&_cb_data);
558-
}
559-
#endif // !NSAPI_PPP_AVAILABLE
558+
// in PPP mode we did not activate any context, just searched the correct _cid
559+
if (_status_cb) {
560+
_status_cb((nsapi_event_t)CellularActivatePDPContext, (intptr_t)&_cb_data);
560561
}
562+
#endif // !NSAPI_PPP_AVAILABLE
561563

562564
if (_cb_data.error != NSAPI_ERROR_OK) {
563-
call_network_cb(NSAPI_STATUS_DISCONNECTED);
564565
_is_connected = false;
565566
return;
566567
}
@@ -630,16 +631,23 @@ void AT_CellularContext::ppp_status_cb(nsapi_event_t ev, intptr_t ptr)
630631
tr_debug("ppp_status_cb: event %d, ptr %d", ev, ptr);
631632
if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_GLOBAL_UP) {
632633
_is_connected = true;
633-
} else if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_DISCONNECTED) {
634-
ppp_disconnected();
635634
} else {
636635
_is_connected = false;
637636
}
638637

639638
_connect_status = (nsapi_connection_status_t)ptr;
640639

640+
// catch all NSAPI_STATUS_DISCONNECTED events but send to device only when we did not ask for disconnect.
641+
if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_DISCONNECTED) {
642+
if (_is_connected) {
643+
ppp_disconnected();
644+
_device->cellular_callback(ev, ptr, this);
645+
}
646+
return;
647+
}
648+
641649
// call device's callback, it will broadcast this to here (cellular_callback)
642-
_device->cellular_callback(ev, ptr);
650+
_device->cellular_callback(ev, ptr, this);
643651
}
644652

645653
void AT_CellularContext::ppp_disconnected()
@@ -660,10 +668,13 @@ void AT_CellularContext::ppp_disconnected()
660668

661669
nsapi_error_t AT_CellularContext::disconnect()
662670
{
663-
tr_info("CellularContext disconnect");
671+
tr_info("CellularContext disconnect()");
664672
if (!_nw || !_is_connected) {
665673
return NSAPI_ERROR_NO_CONNECTION;
666674
}
675+
676+
// set false here so callbacks know that we are not connected and so should not send DISCONNECTED
677+
_is_connected = false;
667678
#if NSAPI_PPP_AVAILABLE
668679
nsapi_error_t err = nsapi_ppp_disconnect(_at.get_file_handle());
669680
if (err != NSAPI_ERROR_OK) {
@@ -681,11 +692,12 @@ nsapi_error_t AT_CellularContext::disconnect()
681692
} else {
682693
deactivate_ip_context();
683694
}
684-
} else {
685-
call_network_cb(NSAPI_STATUS_DISCONNECTED);
686695
}
696+
_is_context_active = false;
697+
_connect_status = NSAPI_STATUS_DISCONNECTED;
687698

688-
_is_connected = false;
699+
// call device's callback, it will broadcast this to here (cellular_callback)
700+
_device->cellular_callback(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, NSAPI_STATUS_DISCONNECTED, this);
689701

690702
return _at.unlock_return_error();
691703
}
@@ -928,27 +940,32 @@ void AT_CellularContext::cellular_callback(nsapi_event_t ev, intptr_t ptr)
928940
if (_is_blocking) {
929941
if (data->error != NSAPI_ERROR_OK) {
930942
// operation failed, release semaphore
943+
_current_op = OP_INVALID;
931944
_semaphore.release();
932945
} else {
933946
if ((st == CellularDeviceReady && _current_op == OP_DEVICE_READY) ||
934947
(st == CellularSIMStatusChanged && _current_op == OP_SIM_READY &&
935948
data->status_data == CellularDevice::SimStateReady)) {
936949
// target reached, release semaphore
950+
_current_op = OP_INVALID;
937951
_semaphore.release();
938952
} else if (st == CellularRegistrationStatusChanged && (data->status_data == CellularNetwork::RegisteredHomeNetwork ||
939953
data->status_data == CellularNetwork::RegisteredRoaming || data->status_data == CellularNetwork::AlreadyRegistered) && _current_op == OP_REGISTER) {
940954
// target reached, release semaphore
955+
_current_op = OP_INVALID;
941956
_semaphore.release();
942957
} else if (st == CellularAttachNetwork && (_current_op == OP_ATTACH || _current_op == OP_CONNECT) &&
943958
data->status_data == CellularNetwork::Attached) {
944959
// target reached, release semaphore
960+
_current_op = OP_INVALID;
945961
_semaphore.release();
946962
}
947963
}
948964
} else {
949965
// non blocking
950966
if (st == CellularAttachNetwork && _current_op == OP_CONNECT && data->error == NSAPI_ERROR_OK &&
951967
data->status_data == CellularNetwork::Attached) {
968+
_current_op = OP_INVALID;
952969
// forward to application
953970
if (_status_cb) {
954971
_status_cb(ev, ptr);
@@ -963,14 +980,18 @@ void AT_CellularContext::cellular_callback(nsapi_event_t ev, intptr_t ptr)
963980
if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_GLOBAL_UP) {
964981
tr_info("CellularContext IP %s", get_ip_address());
965982
_cb_data.error = NSAPI_ERROR_OK;
966-
_semaphore.release();
967983
} else if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_DISCONNECTED) {
968984
tr_info("PPP disconnected");
969985
_cb_data.error = NSAPI_ERROR_NO_CONNECTION;
970-
_semaphore.release();
971986
}
972987
}
973-
#endif
988+
#else
989+
#if MBED_CONF_MBED_TRACE_ENABLE
990+
if (ev == NSAPI_EVENT_CONNECTION_STATUS_CHANGE && ptr == NSAPI_STATUS_DISCONNECTED) {
991+
tr_info("cb: CellularContext disconnected");
992+
}
993+
#endif // MBED_CONF_MBED_TRACE_ENABLE
994+
#endif // NSAPI_PPP_AVAILABLE
974995
}
975996

976997
// forward to application
@@ -1044,8 +1065,7 @@ void AT_CellularContext::ciot_opt_cb(mbed::CellularNetwork::CIoT_Supported_Opt
10441065

10451066
void AT_CellularContext::set_disconnect()
10461067
{
1068+
tr_debug("AT_CellularContext::set_disconnect()");
10471069
_is_connected = false;
1048-
cell_callback_data_t data;
1049-
data.error = NSAPI_STATUS_DISCONNECTED;
1050-
_device->cellular_callback(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, (intptr_t)&data);
1070+
_device->cellular_callback(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, NSAPI_STATUS_DISCONNECTED, this);
10511071
}

features/cellular/framework/AT/AT_CellularNetwork.cpp

Lines changed: 3 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -171,7 +171,7 @@ void AT_CellularNetwork::read_reg_params_and_compare(RegistrationType type)
171171
reg_params._status == RegisteredRoaming)) {
172172
if (previous_registration_status == RegisteredHomeNetwork ||
173173
previous_registration_status == RegisteredRoaming) {
174-
_connection_status_cb(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, NSAPI_STATUS_DISCONNECTED);
174+
call_network_cb(NSAPI_STATUS_DISCONNECTED);
175175
}
176176
}
177177
}
@@ -200,11 +200,8 @@ void AT_CellularNetwork::urc_cgreg()
200200

201201
void AT_CellularNetwork::call_network_cb(nsapi_connection_status_t status)
202202
{
203-
if (_connect_status != status) {
204-
_connect_status = status;
205-
if (_connection_status_cb) {
206-
_connection_status_cb(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, _connect_status);
207-
}
203+
if (_connection_status_cb) {
204+
_connection_status_cb(NSAPI_EVENT_CONNECTION_STATUS_CHANGE, _connect_status);
208205
}
209206
}
210207

@@ -213,11 +210,6 @@ void AT_CellularNetwork::attach(Callback<void(nsapi_event_t, intptr_t)> status_c
213210
_connection_status_cb = status_cb;
214211
}
215212

216-
nsapi_connection_status_t AT_CellularNetwork::get_connection_status() const
217-
{
218-
return _connect_status;
219-
}
220-
221213
nsapi_error_t AT_CellularNetwork::set_registration_urc(RegistrationType type, bool urc_on)
222214
{
223215
int index = (int)type;

features/cellular/framework/AT/AT_CellularNetwork.h

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -63,8 +63,6 @@ class AT_CellularNetwork : public CellularNetwork, public AT_CellularBase {
6363

6464
virtual void attach(Callback<void(nsapi_event_t, intptr_t)> status_cb);
6565

66-
virtual nsapi_connection_status_t get_connection_status() const;
67-
6866
virtual nsapi_error_t set_access_technology(RadioAccessTechnology rat);
6967

7068
virtual nsapi_error_t scan_plmn(operList_t &operators, int &ops_count);

0 commit comments

Comments
 (0)