This program connects to a few sensors via I2C and sends the data collected to a WNC Cellular Module which is located on an Avnet WNC-Shield card.

Dependencies:   FXOS8700CQ MODSERIAL mbed

/media/uploads/kevinkeryk/avnet_logo_tagline_rgb.png

Avnet Cellular IoT Instructions

  • One problematic area is setting the MY_SERVER_URL. When you copy the URL from the flow, you must make sure the MY_SERVER_URL is also set to the appropriate server. It can be either "run-east.att.io" or "run-west.att.io".

Useful Links

Adding Additional Sensors

The FLOW_DEVICE_NAME field must contain the name of the instance of the Virtual Starter Kit in FLOW you will be communicating with. Usually this is "vstarterkit001", but if you have problems communicating you can verify this is correct. Note: This device will not be created until you click the “Initialize” input on the Virtual Device tab of the Starter Kit project in FLOW. At that point, it becomes available in M2X and you can see it as the DEVICE SERIAL field under Devices as in the image below. /media/uploads/JMF/vstarterkit.png

Sensors: When executing, the FRDM-K64F board uploads sensor measurements to AT&T’s Flow environment every 5 seconds, using the Cellular shield board. You can adjust how often you want to do this by editing the SENSOR_UPDATE_INTERVAL_MS value in the header file.

Temperature and humidity: By default, the board reports readings from the HTS221 temperature and humidity sensor. These two values are sent to the HTTP IN /climate port in FLOW with field names “temp” and “humidity”. Temperature is in degrees Fahrenheit and humidity is a %. This default assignment is: iSensorsToReport = TEMP_HUMIDITY_ONLY;

Accelerometer: If you want to expand and use the onboard motion sensor, you can also send 3-axis accelerometer information from the board as “accelX”, “accelY”, and “accelZ”. This is useful if you want to know the stationary position of the board with regards to gravity, or whether it is in motion. These readings are in g’s. To send these values, change the assignment to: iSensorsToReport = TEMP_HUMIDITY_ACCELEROMETER;

PMOD Sensors: If you have a Silicon Labs sensor module that can plug into the PMOD connector on the Cellular shield, you are able to measure proximity, UV light, ambient visible and infrared light from the Si1145 sensor. This PMOD also has a temperature and humidity sensor, but in this case it is redundant. When enabled, the fields “proximity”, “light_uv”, “light_vis” and “light_ir” are also sent. To enable all these sensors, change the assignment to: iSensorsToReport = TEMP_HUMIDITY_ACCELEROMETER_PMODSENSORS;

Connecting the PMOD sensors: Because the pinouts do not align, the SiLabs PMOD sensor board cannot be plugged into the J10 PMOD receptacle on the shield directly. The following wiring instructions must be followed:

SignalJ10ShieldPMOD Color in the image below
VCCPin 6Pin 6Red
GNDPin 5Pin 5Black
SDAPin4Pin 3Green
SCLPin3Pin 2Yellow

/media/uploads/JMF/xyz.jpg

AT&T M2X and FLOW Instructions

M2X & FLOW Instructions

Link to AT&T M2X

M2X

Link to AT&T Flow

FLOW

Avnet WNC-Shield Information

Getting Started with the Avnet WNC-Shield Software

  • This project uses Revision 119 of the MBED library because of I2C implementation differences with the tip (Revision 121).
  • This project uses Revision 4 of the FXOS8700CQ library for sensors.

Easily Modifiable Parameters

Inside the mbed Avnet_ATT_Cellular_IOT project, the parameters needed to customize your board are in the config_me.h file.

  • FLOW parameters: This project assumes you are using a fork of the Starter Kit Base project, which is a reference design created using AT&T’s FLOW (https://flow.att.com) that allows the creation of online virtualization and other IoT functionality. The default parameters in the config_me.h file are done for a specific instance of this project. When you fork the original project, you get your own instance and it will have its own base address. At the bottom of the FLOW environment, when you click on the Endpoints tab, URL information that is specific to your instance is displayed. Of note is the Base URL. In the example below (as in the default mbed project), the Base URL is: https://run-west.att.io/1e464b19cdcde/774c88d68202/86694923d5bf28a/in/flow You have to take note of two parts of this address. The run-west.att.io part is the server URL, and you have to make sure the
  • MY_SERVER_URL field in config_me.h matches this. The rest of the base URL, in green above, needs to be pasted into the FLOW_BASE_URL field.

There is also a FLOW_INPUT_NAME field. This should match the name of the HTTP IN port in the FLOW project that you want to send sensor data to. The default is "/climate", as in the FLOW image below.

/media/uploads/JMF/sf.png

Where is the Binary I compiled

When the COMPILE button is pressed, it compiles your project and links it. The result is placed in the DOWNLOAD folder you use when downloading files from the Internet. It will be called AvnetATT_shape_hackathon_K64F.bin.

Additional Information on Compiling/Configuring

Comprehensive instructions can be found at: Quick Start Instructions

Committer:
root@developer-sjc-indigo-compiler.local.mbed.org
Date:
Mon Dec 11 21:51:32 2017 +0000
Revision:
83:55778a2d5c5e
Parent:
78:00cca62e5d9f
Added tag att_cellular_K64_wnc_14A2A_20171211 for changeset 65cde5d7070c

Who changed what in which revision?

UserRevisionLine numberNew contents of line
fkellermavnet 68:6e311c747045 1 /* ===================================================================
fkellermavnet 74:3e3ee15584e5 2 Copyright c 2016, AVNET Inc.
fkellermavnet 68:6e311c747045 3
fkellermavnet 68:6e311c747045 4 Licensed under the Apache License, Version 2.0 (the "License");
fkellermavnet 68:6e311c747045 5 you may not use this file except in compliance with the License.
fkellermavnet 68:6e311c747045 6 You may obtain a copy of the License at
fkellermavnet 68:6e311c747045 7
fkellermavnet 68:6e311c747045 8 http://www.apache.org/licenses/LICENSE-2.0
fkellermavnet 68:6e311c747045 9
fkellermavnet 68:6e311c747045 10 Unless required by applicable law or agreed to in writing,
fkellermavnet 68:6e311c747045 11 software distributed under the License is distributed on an
fkellermavnet 68:6e311c747045 12 "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
fkellermavnet 68:6e311c747045 13 either express or implied. See the License for the specific
fkellermavnet 68:6e311c747045 14 language governing permissions and limitations under the License.
fkellermavnet 68:6e311c747045 15
fkellermavnet 68:6e311c747045 16 ======================================================================== */
fkellermavnet 68:6e311c747045 17
stefanrousseau 61:f6b93129f954 18 #include "mbed.h"
stefanrousseau 61:f6b93129f954 19 #include <cctype>
stefanrousseau 61:f6b93129f954 20 #include <string>
stefanrousseau 61:f6b93129f954 21
stefanrousseau 61:f6b93129f954 22 #include "config_me.h"
stefanrousseau 61:f6b93129f954 23 #include "wnc_control.h"
stefanrousseau 61:f6b93129f954 24 #include "hardware.h"
stefanrousseau 61:f6b93129f954 25
stefanrousseau 61:f6b93129f954 26 #define MDM_DBG_OFF 0
stefanrousseau 61:f6b93129f954 27 #define MDM_DBG_AT_CMDS (1 << 0)
stefanrousseau 61:f6b93129f954 28 int mdm_dbgmask = MDM_DBG_OFF;
stefanrousseau 61:f6b93129f954 29
stefanrousseau 61:f6b93129f954 30 #define WNC_WAIT_FOR_AT_CMD_MS 40
stefanrousseau 61:f6b93129f954 31
stefanrousseau 61:f6b93129f954 32 DigitalOut mdm_uart2_rx_boot_mode_sel(PTC17); // on powerup, 0 = boot mode, 1 = normal boot
stefanrousseau 61:f6b93129f954 33 DigitalOut mdm_power_on(PTB9); // 0 = turn modem on, 1 = turn modem off (should be held high for >5 seconds to cycle modem)
stefanrousseau 61:f6b93129f954 34 DigitalOut mdm_wakeup_in(PTC2); // 0 = let modem sleep, 1 = keep modem awake -- Note: pulled high on shield
stefanrousseau 61:f6b93129f954 35
stefanrousseau 61:f6b93129f954 36 DigitalOut mdm_reset(PTC12); // active high
stefanrousseau 61:f6b93129f954 37
stefanrousseau 61:f6b93129f954 38 DigitalOut shield_3v3_1v8_sig_trans_ena(PTC4); // 0 = disabled (all signals high impedence, 1 = translation active
stefanrousseau 61:f6b93129f954 39 DigitalOut mdm_uart1_cts(PTD0);
stefanrousseau 61:f6b93129f954 40
stefanrousseau 61:f6b93129f954 41 #define TOUPPER(a) (a) //toupper(a)
stefanrousseau 61:f6b93129f954 42
stefanrousseau 61:f6b93129f954 43 const char ok_str[] = "OK";
stefanrousseau 61:f6b93129f954 44 const char error_str[] = "ERROR";
stefanrousseau 61:f6b93129f954 45
stefanrousseau 61:f6b93129f954 46 #define MDM_OK 0
stefanrousseau 61:f6b93129f954 47 #define MDM_ERR_TIMEOUT -1
stefanrousseau 61:f6b93129f954 48
stefanrousseau 61:f6b93129f954 49 #define MAX_AT_RSP_LEN 255
stefanrousseau 61:f6b93129f954 50
stefanrousseau 61:f6b93129f954 51 ssize_t mdm_getline(char *buff, size_t size, int timeout_ms) {
stefanrousseau 61:f6b93129f954 52 int cin = -1;
stefanrousseau 61:f6b93129f954 53 int cin_last;
stefanrousseau 61:f6b93129f954 54
stefanrousseau 61:f6b93129f954 55 if (NULL == buff || size == 0) {
stefanrousseau 61:f6b93129f954 56 return -1;
stefanrousseau 61:f6b93129f954 57 }
stefanrousseau 61:f6b93129f954 58
stefanrousseau 61:f6b93129f954 59 size_t len = 0;
stefanrousseau 61:f6b93129f954 60 Timer timer;
stefanrousseau 61:f6b93129f954 61 timer.start();
stefanrousseau 61:f6b93129f954 62 while ((len < (size-1)) && (timer.read_ms() < timeout_ms)) {
stefanrousseau 61:f6b93129f954 63 if (mdm.readable()) {
stefanrousseau 61:f6b93129f954 64 cin_last = cin;
stefanrousseau 61:f6b93129f954 65 cin = mdm.getc();
stefanrousseau 61:f6b93129f954 66 if (isprint(cin)) {
stefanrousseau 61:f6b93129f954 67 buff[len++] = (char)cin;
stefanrousseau 61:f6b93129f954 68 continue;
stefanrousseau 61:f6b93129f954 69 } else if (('\r' == cin_last) && ('\n' == cin)) {
stefanrousseau 61:f6b93129f954 70 break;
stefanrousseau 61:f6b93129f954 71 }
stefanrousseau 61:f6b93129f954 72 }
stefanrousseau 61:f6b93129f954 73 // wait_ms(1);
stefanrousseau 61:f6b93129f954 74 }
stefanrousseau 61:f6b93129f954 75 buff[len] = (char)NULL;
stefanrousseau 61:f6b93129f954 76
stefanrousseau 61:f6b93129f954 77 return len;
stefanrousseau 61:f6b93129f954 78 }
stefanrousseau 61:f6b93129f954 79
stefanrousseau 61:f6b93129f954 80 int mdm_sendAtCmd(const char *cmd, const char **rsp_list, int timeout_ms) {
stefanrousseau 61:f6b93129f954 81 // Per WNC wait:
stefanrousseau 61:f6b93129f954 82 wait_ms(WNC_WAIT_FOR_AT_CMD_MS);
stefanrousseau 61:f6b93129f954 83
stefanrousseau 61:f6b93129f954 84 if (cmd && strlen(cmd) > 0) {
stefanrousseau 61:f6b93129f954 85 if (mdm_dbgmask & MDM_DBG_AT_CMDS) {
stefanrousseau 64:09004cd610df 86 PRINTF(MAG "ATCMD: " DEF "--> " GRN "%s" DEF "\n", cmd);
stefanrousseau 61:f6b93129f954 87 }
stefanrousseau 61:f6b93129f954 88 mdm.puts(cmd);
stefanrousseau 61:f6b93129f954 89 mdm.puts("\r\n");
stefanrousseau 61:f6b93129f954 90 }
stefanrousseau 61:f6b93129f954 91
stefanrousseau 61:f6b93129f954 92 if (rsp_list) {
stefanrousseau 61:f6b93129f954 93 Timer timer;
stefanrousseau 61:f6b93129f954 94 char rsp[MAX_AT_RSP_LEN+1];
stefanrousseau 61:f6b93129f954 95 int len;
stefanrousseau 61:f6b93129f954 96
stefanrousseau 61:f6b93129f954 97 timer.start();
stefanrousseau 61:f6b93129f954 98 while (timer.read_ms() < timeout_ms) {
stefanrousseau 61:f6b93129f954 99 len = mdm_getline(rsp, sizeof(rsp), timeout_ms - timer.read_ms());
stefanrousseau 61:f6b93129f954 100
stefanrousseau 61:f6b93129f954 101 if (len < 0)
stefanrousseau 61:f6b93129f954 102 return MDM_ERR_TIMEOUT;
stefanrousseau 61:f6b93129f954 103
stefanrousseau 61:f6b93129f954 104 if (len == 0)
stefanrousseau 61:f6b93129f954 105 continue;
stefanrousseau 61:f6b93129f954 106
stefanrousseau 61:f6b93129f954 107 if (mdm_dbgmask & MDM_DBG_AT_CMDS) {
stefanrousseau 64:09004cd610df 108 PRINTF(MAG "ATRSP: " DEF "<-- " CYN "%s" DEF "\n", rsp);
stefanrousseau 61:f6b93129f954 109 }
stefanrousseau 61:f6b93129f954 110
stefanrousseau 61:f6b93129f954 111 if (rsp_list) {
stefanrousseau 61:f6b93129f954 112 int rsp_idx = 0;
stefanrousseau 61:f6b93129f954 113 while (rsp_list[rsp_idx]) {
stefanrousseau 61:f6b93129f954 114 if (strcasecmp(rsp, rsp_list[rsp_idx]) == 0) {
stefanrousseau 61:f6b93129f954 115 return rsp_idx;
fkellermavnet 74:3e3ee15584e5 116 } else if (strncmp(rsp, "@EXTERR", 7) == 0){
fkellermavnet 74:3e3ee15584e5 117 pc.printf("----- We got EXTERR ---\r\n");
fkellermavnet 74:3e3ee15584e5 118 return 2;
fkellermavnet 74:3e3ee15584e5 119 } else if (strncmp(rsp, "+CME", 4) == 0){
fkellermavnet 74:3e3ee15584e5 120 return 3;
fkellermavnet 74:3e3ee15584e5 121 }
stefanrousseau 61:f6b93129f954 122 rsp_idx++;
stefanrousseau 61:f6b93129f954 123 }
stefanrousseau 61:f6b93129f954 124 }
stefanrousseau 61:f6b93129f954 125 }
stefanrousseau 61:f6b93129f954 126 return MDM_ERR_TIMEOUT;
stefanrousseau 61:f6b93129f954 127 }
stefanrousseau 61:f6b93129f954 128 return MDM_OK;
stefanrousseau 61:f6b93129f954 129 }
stefanrousseau 61:f6b93129f954 130
stefanrousseau 61:f6b93129f954 131 int mdm_init(void) {
stefanrousseau 61:f6b93129f954 132 // Hard reset the modem (doesn't go through
stefanrousseau 61:f6b93129f954 133 // the signal level translator)
stefanrousseau 61:f6b93129f954 134 mdm_reset = 0;
stefanrousseau 61:f6b93129f954 135
stefanrousseau 61:f6b93129f954 136 // disable signal level translator (necessary
stefanrousseau 61:f6b93129f954 137 // for the modem to boot properly). All signals
stefanrousseau 61:f6b93129f954 138 // except mdm_reset go through the level translator
stefanrousseau 61:f6b93129f954 139 // and have internal pull-up/down in the module. While
stefanrousseau 61:f6b93129f954 140 // the level translator is disabled, these pins will
stefanrousseau 61:f6b93129f954 141 // be in the correct state.
stefanrousseau 61:f6b93129f954 142 shield_3v3_1v8_sig_trans_ena = 0;
stefanrousseau 61:f6b93129f954 143
stefanrousseau 61:f6b93129f954 144 // While the level translator is disabled and ouptut pins
stefanrousseau 61:f6b93129f954 145 // are tristated, make sure the inputs are in the same state
stefanrousseau 61:f6b93129f954 146 // as the WNC Module pins so that when the level translator is
stefanrousseau 61:f6b93129f954 147 // enabled, there are no differences.
stefanrousseau 61:f6b93129f954 148 mdm_uart2_rx_boot_mode_sel = 1; // UART2_RX should be high
stefanrousseau 61:f6b93129f954 149 mdm_power_on = 0; // powr_on should be low
stefanrousseau 61:f6b93129f954 150 mdm_wakeup_in = 1; // wake-up should be high
stefanrousseau 61:f6b93129f954 151 mdm_uart1_cts = 0; // indicate that it is ok to send
stefanrousseau 61:f6b93129f954 152
stefanrousseau 61:f6b93129f954 153 // Now, wait for the WNC Module to perform its initial boot correctly
stefanrousseau 61:f6b93129f954 154 wait(1.0);
stefanrousseau 61:f6b93129f954 155
stefanrousseau 61:f6b93129f954 156 // The WNC module initializes comms at 115200 8N1 so set it up
stefanrousseau 61:f6b93129f954 157 mdm.baud(115200);
stefanrousseau 61:f6b93129f954 158
stefanrousseau 61:f6b93129f954 159 //Now, enable the level translator, the input pins should now be the
stefanrousseau 61:f6b93129f954 160 //same as how the M14A module is driving them with internal pull ups/downs.
stefanrousseau 61:f6b93129f954 161 //When enabled, there will be no changes in these 4 pins...
stefanrousseau 61:f6b93129f954 162 shield_3v3_1v8_sig_trans_ena = 1;
stefanrousseau 61:f6b93129f954 163
stefanrousseau 61:f6b93129f954 164 // Now, give the modem 60 seconds to start responding by
stefanrousseau 61:f6b93129f954 165 // sending simple 'AT' commands to modem once per second.
stefanrousseau 61:f6b93129f954 166 Timer timer;
stefanrousseau 61:f6b93129f954 167 timer.start();
stefanrousseau 61:f6b93129f954 168 while (timer.read() < 60) {
stefanrousseau 61:f6b93129f954 169 const char * rsp_lst[] = { ok_str, error_str, NULL };
stefanrousseau 61:f6b93129f954 170 int rc = mdm_sendAtCmd("AT", rsp_lst, 500);
stefanrousseau 61:f6b93129f954 171 if (rc == 0)
stefanrousseau 61:f6b93129f954 172 return true; //timer.read();
stefanrousseau 61:f6b93129f954 173 wait_ms(1000 - (timer.read_ms() % 1000));
stefanrousseau 64:09004cd610df 174 PRINTF("\r%d",timer.read_ms()/1000);
stefanrousseau 61:f6b93129f954 175 }
stefanrousseau 61:f6b93129f954 176 return false;
stefanrousseau 61:f6b93129f954 177 }
stefanrousseau 61:f6b93129f954 178
stefanrousseau 61:f6b93129f954 179 int mdm_sendAtCmdRsp(const char *cmd, const char **rsp_list, int timeout_ms, string * rsp, int * len) {
stefanrousseau 61:f6b93129f954 180 static char cmd_buf[3200]; // Need enough room for the WNC sockreads (over 3000 chars)
stefanrousseau 61:f6b93129f954 181 size_t n = strlen(cmd);
stefanrousseau 61:f6b93129f954 182
stefanrousseau 61:f6b93129f954 183 // Per WNC wait:
stefanrousseau 61:f6b93129f954 184 wait_ms(WNC_WAIT_FOR_AT_CMD_MS);
stefanrousseau 61:f6b93129f954 185
stefanrousseau 61:f6b93129f954 186 if (cmd && n > 0) {
stefanrousseau 61:f6b93129f954 187 if (mdm_dbgmask & MDM_DBG_AT_CMDS) {
stefanrousseau 64:09004cd610df 188 PRINTF(MAG "ATCMD: " DEF "--> " GRN "%s" DEF "\n", cmd);
stefanrousseau 61:f6b93129f954 189 }
stefanrousseau 61:f6b93129f954 190 // mdm.puts(cmd);
stefanrousseau 61:f6b93129f954 191 // mdm.puts("\r\n");
stefanrousseau 61:f6b93129f954 192 while (n--) {
stefanrousseau 61:f6b93129f954 193 mdm.putc(*cmd++);
stefanrousseau 61:f6b93129f954 194 wait_us(1000);
stefanrousseau 61:f6b93129f954 195 };
stefanrousseau 61:f6b93129f954 196 mdm.putc('\r');
stefanrousseau 61:f6b93129f954 197 wait_us(1000);
stefanrousseau 61:f6b93129f954 198 mdm.putc('\n');
stefanrousseau 61:f6b93129f954 199 wait_us(1000);
stefanrousseau 61:f6b93129f954 200 }
stefanrousseau 61:f6b93129f954 201
stefanrousseau 61:f6b93129f954 202 if (rsp_list) {
stefanrousseau 61:f6b93129f954 203 rsp->erase(); // Clean up from prior cmd response
stefanrousseau 61:f6b93129f954 204 *len = 0;
stefanrousseau 61:f6b93129f954 205 Timer timer;
stefanrousseau 61:f6b93129f954 206 timer.start();
stefanrousseau 61:f6b93129f954 207 while (timer.read_ms() < timeout_ms) {
stefanrousseau 61:f6b93129f954 208 int lenCmd = mdm_getline(cmd_buf, sizeof(cmd_buf), timeout_ms - timer.read_ms());
stefanrousseau 61:f6b93129f954 209
stefanrousseau 61:f6b93129f954 210 if (lenCmd == 0)
stefanrousseau 61:f6b93129f954 211 continue;
stefanrousseau 61:f6b93129f954 212
stefanrousseau 61:f6b93129f954 213 if (lenCmd < 0)
stefanrousseau 61:f6b93129f954 214 return MDM_ERR_TIMEOUT;
stefanrousseau 61:f6b93129f954 215 else {
stefanrousseau 61:f6b93129f954 216 *len += lenCmd;
stefanrousseau 61:f6b93129f954 217 *rsp += cmd_buf;
stefanrousseau 61:f6b93129f954 218 }
stefanrousseau 61:f6b93129f954 219
stefanrousseau 61:f6b93129f954 220 if (mdm_dbgmask & MDM_DBG_AT_CMDS) {
stefanrousseau 64:09004cd610df 221 PRINTF(MAG "ATRSP: " DEF "<-- " CYN "%s" DEF "\n", cmd_buf);
stefanrousseau 61:f6b93129f954 222 }
stefanrousseau 61:f6b93129f954 223
stefanrousseau 61:f6b93129f954 224 int rsp_idx = 0;
fkellermavnet 73:da723fedfdd2 225 // TODO: Test if @EXTERR:<code>
stefanrousseau 61:f6b93129f954 226 while (rsp_list[rsp_idx]) {
stefanrousseau 61:f6b93129f954 227 if (strcasecmp(cmd_buf, rsp_list[rsp_idx]) == 0) {
stefanrousseau 61:f6b93129f954 228 return rsp_idx;
fkellermavnet 73:da723fedfdd2 229 } else if (strncmp(cmd_buf, "@EXTERR", 7) == 0){
fkellermavnet 75:8cc98a3b9c62 230 PRINTF("----- We got EXTERR ---\r\n");
fkellermavnet 74:3e3ee15584e5 231 return 2;
fkellermavnet 74:3e3ee15584e5 232 } else if (strncmp(cmd_buf, "+CME", 4) == 0){
fkellermavnet 74:3e3ee15584e5 233 return 3;
fkellermavnet 74:3e3ee15584e5 234 }
stefanrousseau 61:f6b93129f954 235 rsp_idx++;
stefanrousseau 61:f6b93129f954 236 }
stefanrousseau 61:f6b93129f954 237 }
stefanrousseau 61:f6b93129f954 238 return MDM_ERR_TIMEOUT;
stefanrousseau 61:f6b93129f954 239 }
stefanrousseau 61:f6b93129f954 240
stefanrousseau 61:f6b93129f954 241 return MDM_OK;
stefanrousseau 61:f6b93129f954 242 }
stefanrousseau 61:f6b93129f954 243
stefanrousseau 61:f6b93129f954 244 void reinitialize_mdm(void)
stefanrousseau 61:f6b93129f954 245 {
stefanrousseau 61:f6b93129f954 246 // Initialize the modem
stefanrousseau 64:09004cd610df 247 PRINTF(GRN "Modem RE-initializing..." DEF "\r\n");
stefanrousseau 61:f6b93129f954 248 if (!mdm_init()) {
stefanrousseau 64:09004cd610df 249 PRINTF(RED "\n\rModem RE-initialization failed!" DEF "\n");
stefanrousseau 61:f6b93129f954 250 }
stefanrousseau 64:09004cd610df 251 PRINTF("\r\n");
stefanrousseau 61:f6b93129f954 252 }
stefanrousseau 61:f6b93129f954 253 // These are built on the fly
stefanrousseau 61:f6b93129f954 254 string MyServerIpAddress;
stefanrousseau 61:f6b93129f954 255 string MySocketData;
stefanrousseau 61:f6b93129f954 256
stefanrousseau 61:f6b93129f954 257 //********************************************************************************************************************************************
stefanrousseau 61:f6b93129f954 258 //* Process JSON response messages
stefanrousseau 61:f6b93129f954 259 //********************************************************************************************************************************************
stefanrousseau 61:f6b93129f954 260 bool extract_JSON(char* search_field, char* found_string)
stefanrousseau 61:f6b93129f954 261 {
stefanrousseau 61:f6b93129f954 262 char* beginquote;
stefanrousseau 61:f6b93129f954 263 char* endquote;
stefanrousseau 61:f6b93129f954 264 beginquote = strchr(search_field, '{'); //start of JSON
stefanrousseau 61:f6b93129f954 265 endquote = strchr(search_field, '}'); //end of JSON
stefanrousseau 61:f6b93129f954 266 if (beginquote)
stefanrousseau 61:f6b93129f954 267 {
stefanrousseau 61:f6b93129f954 268 uint16_t ifoundlen;
stefanrousseau 61:f6b93129f954 269 if (endquote)
stefanrousseau 61:f6b93129f954 270 {
stefanrousseau 61:f6b93129f954 271 ifoundlen = (uint16_t) (endquote - beginquote) + 1;
stefanrousseau 61:f6b93129f954 272 strncpy(found_string, beginquote, ifoundlen );
stefanrousseau 61:f6b93129f954 273 found_string[ifoundlen] = 0; //null terminate
stefanrousseau 61:f6b93129f954 274 return true;
stefanrousseau 61:f6b93129f954 275 }
stefanrousseau 61:f6b93129f954 276 else
stefanrousseau 61:f6b93129f954 277 {
stefanrousseau 61:f6b93129f954 278 endquote = strchr(search_field, '\0'); //end of string... sometimes the end bracket is missing
stefanrousseau 61:f6b93129f954 279 ifoundlen = (uint16_t) (endquote - beginquote) + 1;
stefanrousseau 61:f6b93129f954 280 strncpy(found_string, beginquote, ifoundlen );
stefanrousseau 61:f6b93129f954 281 found_string[ifoundlen] = 0; //null terminate
stefanrousseau 61:f6b93129f954 282 return false;
stefanrousseau 61:f6b93129f954 283 }
stefanrousseau 61:f6b93129f954 284 }
stefanrousseau 61:f6b93129f954 285 else
stefanrousseau 61:f6b93129f954 286 {
stefanrousseau 61:f6b93129f954 287 return false;
stefanrousseau 61:f6b93129f954 288 }
stefanrousseau 61:f6b93129f954 289 } //extract_JSON
stefanrousseau 61:f6b93129f954 290
stefanrousseau 61:f6b93129f954 291 int cell_modem_init()
stefanrousseau 61:f6b93129f954 292 {
stefanrousseau 61:f6b93129f954 293 int i;
stefanrousseau 61:f6b93129f954 294
stefanrousseau 61:f6b93129f954 295 pc.baud(115200);
stefanrousseau 61:f6b93129f954 296 // Initialize the modem
stefanrousseau 64:09004cd610df 297 PRINTF(GRN "Modem initializing... will take up to 60 seconds" DEF "\r\n");
stefanrousseau 61:f6b93129f954 298 do {
stefanrousseau 61:f6b93129f954 299 i=mdm_init();
stefanrousseau 61:f6b93129f954 300 if (!i) {
stefanrousseau 64:09004cd610df 301 PRINTF(RED "Modem initialization failed!" DEF "\n");
stefanrousseau 61:f6b93129f954 302 }
stefanrousseau 61:f6b93129f954 303 } while (!i);
stefanrousseau 61:f6b93129f954 304
stefanrousseau 61:f6b93129f954 305 //Software init
stefanrousseau 61:f6b93129f954 306 software_init_mdm();
stefanrousseau 61:f6b93129f954 307
stefanrousseau 61:f6b93129f954 308 // Resolve URL to IP address to connect to
stefanrousseau 61:f6b93129f954 309 resolve_mdm();
stefanrousseau 61:f6b93129f954 310 // Open the socket (connect to the server)
stefanrousseau 61:f6b93129f954 311 sockopen_mdm();
stefanrousseau 61:f6b93129f954 312 return (0);
stefanrousseau 61:f6b93129f954 313 }
stefanrousseau 61:f6b93129f954 314
stefanrousseau 61:f6b93129f954 315 int cell_modem_Sendreceive(char* tx_string, char* rx_string)
stefanrousseau 61:f6b93129f954 316 {
stefanrousseau 61:f6b93129f954 317 int iStatus = 0; //error by default
stefanrousseau 64:09004cd610df 318 PRINTF(DEF "\r\n");
stefanrousseau 64:09004cd610df 319 PRINTF(BLU "Sending to modem : %s" DEF "\r\n", &tx_string[0]);
stefanrousseau 61:f6b93129f954 320 sockwrite_mdm(&tx_string[0]);
stefanrousseau 61:f6b93129f954 321 if (sockread_mdm(&MySocketData, 1024, 20))
stefanrousseau 61:f6b93129f954 322 {
stefanrousseau 64:09004cd610df 323 PRINTF(DEF "\r\n");
fkellermavnet 78:00cca62e5d9f 324 PRINTF(YEL "Read back : %s" DEF "\r\n", MySocketData.c_str());
stefanrousseau 61:f6b93129f954 325 char stringToCharBuf[BUF_SIZE_FOR_N_MAX_SOCKREAD*MAX_WNC_SOCKREAD_PAYLOAD+1]; // WNC can return max of 1500 (per sockread)
stefanrousseau 61:f6b93129f954 326 if ((MySocketData.length() + 1) < sizeof(stringToCharBuf))
stefanrousseau 61:f6b93129f954 327 {
stefanrousseau 61:f6b93129f954 328 strcpy(stringToCharBuf, MySocketData.c_str());
stefanrousseau 61:f6b93129f954 329 if (extract_JSON(stringToCharBuf, &rx_string[0]))
stefanrousseau 61:f6b93129f954 330 {
stefanrousseau 64:09004cd610df 331 PRINTF(GRN "JSON : %s" DEF "\n", &rx_string[0]);
stefanrousseau 61:f6b93129f954 332 iStatus = 1; //all good
stefanrousseau 61:f6b93129f954 333 }
stefanrousseau 61:f6b93129f954 334 }
stefanrousseau 61:f6b93129f954 335 else
stefanrousseau 61:f6b93129f954 336 {
stefanrousseau 64:09004cd610df 337 PRINTF(RED "BUFFER not big enough for sock data!" DEF "\r\n");
stefanrousseau 61:f6b93129f954 338 }
stefanrousseau 61:f6b93129f954 339 }
stefanrousseau 61:f6b93129f954 340 else
stefanrousseau 61:f6b93129f954 341 {
stefanrousseau 64:09004cd610df 342 PRINTF(RED "No response..." DEF "\r\n");
stefanrousseau 61:f6b93129f954 343 }
stefanrousseau 61:f6b93129f954 344 return iStatus;
stefanrousseau 61:f6b93129f954 345 }
fkellermavnet 77:c65eae5b9958 346
fkellermavnet 77:c65eae5b9958 347 void display_wnc_firmware_rev(void)
fkellermavnet 77:c65eae5b9958 348 {
fkellermavnet 77:c65eae5b9958 349 display_modem_firmware_version();
fkellermavnet 77:c65eae5b9958 350 }