@@ -97,92 +97,35 @@ void QUECTEL_BG96::set_ready_cb(Callback<void()> callback)
97
97
_at->set_urc_handler (DEVICE_READY_URC, callback);
98
98
}
99
99
100
- nsapi_error_t QUECTEL_BG96::hard_power_on ()
101
- {
102
- if (_pwr.is_connected ()) {
103
- tr_info (" Modem power on" );
104
- ThisThread::sleep_for (250 );
105
- _pwr = !_active_high;
106
- ThisThread::sleep_for (250 ); // BG96_Hardware_Design_V1.1 says 100 ms, but 250 ms seems to be more robust
107
- _pwr = _active_high;
108
- ThisThread::sleep_for (500 );
109
- }
110
-
111
- return NSAPI_ERROR_OK;
112
- }
113
-
114
100
nsapi_error_t QUECTEL_BG96::soft_power_on ()
115
- {
116
- if (!_rst.is_connected ()) {
117
- return NSAPI_ERROR_OK;
118
- }
119
-
120
- tr_info (" Reset modem" );
121
- _rst = !_active_high;
122
- ThisThread::sleep_for (100 );
123
- _rst = _active_high;
124
- ThisThread::sleep_for (150 + 460 ); // RESET_N timeout from BG96_Hardware_Design_V1.1
125
- _rst = !_active_high;
126
- ThisThread::sleep_for (500 );
127
-
128
- // wait for RDY
129
- _at->lock ();
130
- _at->set_at_timeout (10 * 1000 );
131
- _at->resp_start ();
132
- _at->set_stop_tag (" RDY" );
133
- bool rdy = _at->consume_to_stop_tag ();
134
- _at->set_stop_tag (OK);
135
- _at->restore_at_timeout ();
136
-
137
- if (!rdy) {
138
- // check if modem was silently powered on
139
- _at->clear_error ();
140
- _at->set_at_timeout (100 );
141
- _at->at_cmd_discard (" " , " " ); // Send AT
142
- _at->restore_at_timeout ();
143
- }
144
- return _at->unlock_return_error ();
145
- }
146
-
147
- nsapi_error_t QUECTEL_BG96::hard_power_off ()
148
101
{
149
102
if (_pwr.is_connected ()) {
150
- tr_info (" Modem power off" );
151
- _pwr = _active_high;
152
- ThisThread::sleep_for (650 ); // from BG96_Hardware_Design_V1.1
153
- _pwr = !_active_high;
103
+ tr_info (" QUECTEL_BG96::soft_power_on" );
104
+ // check if modem was powered on already
105
+ if (wake_up ()) {
106
+ return NSAPI_ERROR_OK;
107
+ }
108
+ if (!wake_up (true )) {
109
+ tr_error (" Modem not responding" );
110
+ soft_power_off ();
111
+ return NSAPI_ERROR_DEVICE_ERROR;
112
+ }
154
113
}
155
114
156
115
return NSAPI_ERROR_OK;
157
116
}
158
117
159
- nsapi_error_t QUECTEL_BG96::init ()
118
+ nsapi_error_t QUECTEL_BG96::soft_power_off ()
160
119
{
161
- setup_at_handler ();
162
-
163
- int retry = 0 ;
164
-
165
120
_at->lock ();
166
- _at->flush ();
167
- _at->at_cmd_discard (" E0" , " " ); // echo off
168
-
169
- _at->at_cmd_discard (" +CMEE" , " =1" ); // verbose responses
170
-
121
+ _at->cmd_start (" AT+QPOWD" );
122
+ _at->cmd_stop_read_resp ();
171
123
if (_at->get_last_error () != NSAPI_ERROR_OK) {
172
- return _at->unlock_return_error ();
173
- }
174
-
175
- do {
176
- _at->clear_error ();
177
- _at->at_cmd_discard (" +CFUN" , " =1" ); // set full functionality
178
- if (_at->get_last_error () == NSAPI_ERROR_OK) {
179
- break ;
124
+ tr_warn (" Force modem off" );
125
+ if (_pwr.is_connected ()) {
126
+ press_button (_pwr, 650 ); // BG96_Hardware_Design_V1.1: Power off signal at least 650 ms
180
127
}
181
- // wait some time that modem gets ready for CFUN command, and try again
182
- retry++;
183
- ThisThread::sleep_for (64 ); // experimental value
184
- } while (retry < 3 );
185
-
128
+ }
186
129
return _at->unlock_return_error ();
187
130
}
188
131
@@ -215,3 +158,52 @@ void QUECTEL_BG96::urc_pdpdeact()
215
158
}
216
159
send_disconnect_to_context (cid);
217
160
}
161
+
162
+ void QUECTEL_BG96::press_button (DigitalOut &button, uint32_t timeout)
163
+ {
164
+ if (!button.is_connected ()) {
165
+ return ;
166
+ }
167
+ button = _active_high;
168
+ ThisThread::sleep_for (timeout);
169
+ button = !_active_high;
170
+ }
171
+
172
+ bool QUECTEL_BG96::wake_up (bool reset)
173
+ {
174
+ // check if modem is already ready
175
+ _at->lock ();
176
+ _at->flush ();
177
+ _at->set_at_timeout (30 );
178
+ _at->cmd_start (" AT" );
179
+ _at->cmd_stop_read_resp ();
180
+ nsapi_error_t err = _at->get_last_error ();
181
+ _at->restore_at_timeout ();
182
+ _at->unlock ();
183
+ // modem is not responding, power it on
184
+ if (err != NSAPI_ERROR_OK) {
185
+ if (!reset) {
186
+ // BG96_Hardware_Design_V1.1 requires VBAT to be stable over 30 ms, that's handled above
187
+ tr_info (" Power on modem" );
188
+ press_button (_pwr, 250 ); // BG96_Hardware_Design_V1.1 requires time 100 ms, but 250 ms seems to be more robust
189
+ } else {
190
+ tr_warn (" Reset modem" );
191
+ press_button (_rst, 150 ); // BG96_Hardware_Design_V1.1 requires RESET_N timeout at least 150 ms
192
+ }
193
+ _at->lock ();
194
+ // According to BG96_Hardware_Design_V1.1 USB is active after 4.2s, but it seems to take over 5s
195
+ _at->set_at_timeout (6000 );
196
+ _at->resp_start ();
197
+ _at->set_stop_tag (" RDY" );
198
+ bool rdy = _at->consume_to_stop_tag ();
199
+ _at->set_stop_tag (OK);
200
+ _at->restore_at_timeout ();
201
+ _at->unlock ();
202
+ if (!rdy) {
203
+ return false ;
204
+ }
205
+ }
206
+
207
+ // sync to check that AT is really responsive and to clear garbage
208
+ return _at->sync (500 );
209
+ }
0 commit comments