Daniel Lee / Mbed OS mbed-os-example-cellular_BG96_os511
Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 /*
00002  * Copyright (c) 2017 ARM Limited. All rights reserved.
00003  * SPDX-License-Identifier: Apache-2.0
00004  * Licensed under the Apache License, Version 2.0 (the License); you may
00005  * not use this file except in compliance with the License.
00006  * You may obtain a copy of the License at
00007  *
00008  * http://www.apache.org/licenses/LICENSE-2.0
00009  *
00010  * Unless required by applicable law or agreed to in writing, software
00011  * distributed under the License is distributed on an AS IS BASIS, WITHOUT
00012  * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00013  * See the License for the specific language governing permissions and
00014  * limitations under the License.
00015  */
00016 
00017 #include "mbed.h"
00018 #include "common_functions.h"
00019 #include "UDPSocket.h"
00020 #include "CellularLog.h"
00021 
00022 #define UDP 0
00023 #define TCP 1
00024 
00025 // Number of retries /
00026 #define RETRY_COUNT 3
00027 
00028 /* Pin configuraiton */
00029 // Cat.M1 of WIZnet
00030 #define MBED_CONF_IOTSHIELD_CATM1_RESET             D7
00031 #define MBED_CONF_IOTSHIELD_CATM1_PWRKEY            D9
00032 // On-board sensors
00033 #define MBED_CONF_IOTSHIELD_SENSOR_CDS              A0
00034 #define MBED_CONF_IOTSHIELD_SENSOR_TEMP             A1
00035 
00036 NetworkInterface *iface;
00037 
00038 // Echo server hostname
00039 const char *host_name = MBED_CONF_APP_ECHO_SERVER_HOSTNAME;
00040 
00041 // Echo server port (same for TCP and UDP)
00042 const int port = MBED_CONF_APP_ECHO_SERVER_PORT;
00043 
00044 static rtos::Mutex trace_mutex;
00045 
00046 #if MBED_CONF_MBED_TRACE_ENABLE
00047 static void trace_wait()
00048 {
00049     trace_mutex.lock();
00050 }
00051 
00052 static void trace_release()
00053 {
00054     trace_mutex.unlock();
00055 }
00056 
00057 static char time_st[50];
00058 
00059 static char* trace_time(size_t ss)
00060 {
00061     snprintf(time_st, 49, "[%08llums]", Kernel::get_ms_count());
00062     return time_st;
00063 }
00064 
00065 static void trace_open()
00066 {
00067     mbed_trace_init();
00068     mbed_trace_prefix_function_set( &trace_time );
00069 
00070     mbed_trace_mutex_wait_function_set(trace_wait);
00071     mbed_trace_mutex_release_function_set(trace_release);
00072 
00073     mbed_cellular_trace::mutex_wait_function_set(trace_wait);
00074     mbed_cellular_trace::mutex_release_function_set(trace_release);
00075 }
00076 
00077 static void trace_close()
00078 {
00079     mbed_cellular_trace::mutex_wait_function_set(NULL);
00080     mbed_cellular_trace::mutex_release_function_set(NULL);
00081 
00082     mbed_trace_free();
00083 }
00084 #endif // #if MBED_CONF_MBED_TRACE_ENABLE
00085 
00086 Thread dot_thread(osPriorityNormal, 512);
00087 
00088 void print_function(const char *format, ...)
00089 {
00090     trace_mutex.lock();
00091     va_list arglist;
00092     va_start( arglist, format );
00093     vprintf(format, arglist);
00094     va_end( arglist );
00095     trace_mutex.unlock();
00096 }
00097 
00098 void dot_event()
00099 {
00100     while (true) {
00101         ThisThread::sleep_for(4000);
00102         if (iface && iface->get_connection_status() == NSAPI_STATUS_GLOBAL_UP) {
00103             break;
00104         } else {
00105             trace_mutex.lock();
00106             printf(".");
00107             fflush(stdout);
00108             trace_mutex.unlock();
00109         }
00110     }
00111 }
00112 
00113 /**
00114  * Connects to the Cellular Network
00115  */
00116 nsapi_error_t do_connect()
00117 {
00118     nsapi_error_t retcode = NSAPI_ERROR_OK;
00119     uint8_t retry_counter = 0;
00120 
00121     while (iface->get_connection_status() != NSAPI_STATUS_GLOBAL_UP) {
00122         retcode = iface->connect();
00123         if (retcode == NSAPI_ERROR_AUTH_FAILURE) {
00124             print_function("\n\nAuthentication Failure. Exiting application\n");
00125         } else if (retcode == NSAPI_ERROR_OK) {
00126             print_function("\n\nConnection Established.\n");
00127         } else if (retry_counter > RETRY_COUNT) {
00128             print_function("\n\nFatal connection failure: %d\n", retcode);
00129         } else {
00130             print_function("\n\nCouldn't connect: %d, will retry\n", retcode);
00131             retry_counter++;
00132             continue;
00133         }
00134         break;
00135     }
00136     return retcode;
00137 }
00138 
00139  /*
00140  * WIZnet's BG96 Modem init
00141  */
00142 void iotshield_modem_init(void)
00143 {
00144     DigitalOut _RESET_IOTSHIELD(MBED_CONF_IOTSHIELD_CATM1_RESET);
00145     DigitalOut _PWRKEY_IOTSHIELD(MBED_CONF_IOTSHIELD_CATM1_PWRKEY);
00146 
00147     _RESET_IOTSHIELD = 1;
00148     _PWRKEY_IOTSHIELD = 1;
00149     wait_ms(300);
00150 
00151     _RESET_IOTSHIELD = 0;
00152     _PWRKEY_IOTSHIELD = 0;
00153     wait_ms(400);
00154 
00155     _RESET_IOTSHIELD = 1;
00156     wait_ms(1000);
00157 }
00158 
00159 /**
00160  * Opens a UDP or a TCP socket with the given echo server and performs an echo
00161  * transaction retrieving current.
00162  */
00163 nsapi_error_t test_send_recv()
00164 {
00165     nsapi_size_or_error_t retcode;
00166 #if MBED_CONF_APP_SOCK_TYPE == TCP
00167     TCPSocket sock;
00168 #else
00169     UDPSocket sock;
00170 #endif
00171 
00172     retcode = sock.open(iface);
00173     if (retcode != NSAPI_ERROR_OK) {
00174 #if MBED_CONF_APP_SOCK_TYPE == TCP
00175         print_function("TCPSocket.open() fails, code: %d\n", retcode);
00176 #else
00177         print_function("UDPSocket.open() fails, code: %d\n", retcode);
00178 #endif
00179         return -1;
00180     }
00181 
00182     SocketAddress sock_addr;
00183     retcode = iface->gethostbyname(host_name, &sock_addr);
00184     if (retcode != NSAPI_ERROR_OK) {
00185         print_function("Couldn't resolve remote host: %s, code: %d\n", host_name, retcode);
00186         return -1;
00187     }
00188 
00189     sock_addr.set_port(port);
00190 
00191     sock.set_timeout(15000);
00192     int n = 0;
00193     const char *echo_string = "TEST";
00194     char recv_buf[4];
00195 #if MBED_CONF_APP_SOCK_TYPE == TCP
00196     retcode = sock.connect(sock_addr);
00197     if (retcode < 0) {
00198         print_function("TCPSocket.connect() fails, code: %d\n", retcode);
00199         return -1;
00200     } else {
00201         print_function("TCP: connected with %s server\n", host_name);
00202     }
00203     retcode = sock.send((void*) echo_string, sizeof(echo_string));
00204     if (retcode < 0) {
00205         print_function("TCPSocket.send() fails, code: %d\n", retcode);
00206         return -1;
00207     } else {
00208         print_function("TCP: Sent %d Bytes to %s\n", retcode, host_name);
00209     }
00210 
00211     n = sock.recv((void*) recv_buf, sizeof(recv_buf));
00212 #else
00213 
00214     retcode = sock.sendto(sock_addr, (void*) echo_string, sizeof(echo_string));
00215     if (retcode < 0) {
00216         print_function("UDPSocket.sendto() fails, code: %d\n", retcode);
00217         return -1;
00218     } else {
00219         print_function("UDP: Sent %d Bytes to %s\n", retcode, host_name);
00220     }
00221 
00222     n = sock.recvfrom(&sock_addr, (void*) recv_buf, sizeof(recv_buf));
00223 #endif
00224 
00225     sock.close();
00226 
00227     if (n > 0) {
00228         print_function("Received from echo server %d Bytes\n", n);
00229         return 0;
00230     }
00231 
00232     return -1;
00233 }
00234 
00235 int main()
00236 {
00237     print_function("\n\nmbed-os-example-cellular\n");
00238     print_function("\n\nBuilt: %s, %s\n", __DATE__, __TIME__);
00239 #ifdef MBED_CONF_NSAPI_DEFAULT_CELLULAR_PLMN
00240     print_function("\n\n[MAIN], plmn: %s\n", MBED_CONF_NSAPI_DEFAULT_CELLULAR_PLMN);
00241 #endif
00242 
00243     // Cat.M1 module init: Hardware reset and power on
00244     print_function("WIZnet's BG96 Modem power on\n");
00245     iotshield_modem_init();
00246 
00247     print_function("Establishing connection\n");
00248 #if MBED_CONF_MBED_TRACE_ENABLE
00249     trace_open();
00250 #else
00251     dot_thread.start(dot_event);
00252 #endif // #if MBED_CONF_MBED_TRACE_ENABLE
00253 
00254     // sim pin, apn, credentials and possible plmn are taken atuomtically from json when using get_default_instance()
00255     iface = NetworkInterface::get_default_instance();
00256     MBED_ASSERT(iface);
00257 
00258     nsapi_error_t retcode = NSAPI_ERROR_NO_CONNECTION;
00259 
00260     /* Attempt to connect to a cellular network */
00261     if (do_connect() == NSAPI_ERROR_OK) {
00262         retcode = test_send_recv();
00263     }
00264 
00265     if (iface->disconnect() != NSAPI_ERROR_OK) {
00266         print_function("\n\n disconnect failed.\n\n");
00267     }
00268 
00269     if (retcode == NSAPI_ERROR_OK) {
00270         print_function("\n\nSuccess. Exiting \n\n");
00271     } else {
00272         print_function("\n\nFailure. Exiting \n\n");
00273     }
00274 
00275 #if MBED_CONF_MBED_TRACE_ENABLE
00276     trace_close();
00277 #else
00278     dot_thread.terminate();
00279 #endif // #if MBED_CONF_MBED_TRACE_ENABLE
00280 
00281     return 0;
00282 }
00283 // EOF