mbed OS V5 BLE UARTService to USB/UART PassThru Example

Moxon Design : mbed OS V5 BLE UartService to USBUART passthru example

This example will advertise on BLE as "BLART" and allow BLE serial echo to the USB Serial port. Open a Bluetooth terminal application, like Nordic "nRF UART" and connect to "BLART", open a terminal emulator program, like "TeraTERM", and connect to the USB COM Port (like JLink CDC UART Port), and echo characters back and forth. Set UART_LoopBack = 1 for local loopback (e.g. BLE to BLE, USB-UART to USB-UART)

Revision:
1:5b50f5283781
Parent:
0:2d1d68397ff7
--- a/main.cpp	Fri Apr 28 20:51:34 2017 +0000
+++ b/main.cpp	Sat Apr 29 01:27:04 2017 +0000
@@ -1,4 +1,4 @@
-/* mbed BLE Library - UART Serial Pass-thru Example
+/* mbed BLE Library - USB/UART Serial Pass-thru Example
  *
  * author    : Moxon Design
  * date      : 4/27/2017
@@ -8,17 +8,16 @@
  * Overview: 
  * 
  * Employs the mBed platform ble/services/UARTService for UART emulation,
- * as well as exposing the phyical UART device providing a transparent bridge 
- * between the two interfaces. By default, 
- * UART_TX on pin P0_12,  and UART-RX on pin P0_11 
- * "Serial dev(P0_12, P0_11); // TX,RX  
+ * as well as exposing the phyical UART device connected to the USB host,
+ * providing a transparent bridge between the two interfaces. By default, 
+ * Serial dev(USBTX, USBRX);
  *
  * Set "UART_LoopBack" to enable local loopback test instead of pass-thru.
  * 
  * Notes : 
- * 1) Advertises as "BLART" for BLe-uART
+ * 1) Advertises as "BLART" for BLe-usbUART
  * 2) ble/services/UARTService is 20 byte max packets or about 4800 Baud (be patient)
- * 3) transparent bridge (add command interpretor, etc.)
+ * 3) transparent bridge
  *
  * License :
  *
@@ -53,22 +52,28 @@
 /* instantiate BLE services and softUART service */
 BLEDevice  ble;
 UARTService *uartServicePtr;
-
+int UART_LoopBack = 0;
+ 
 /* instantiate hardware UART devices                */
 /* devicename(TXD, RXD);                            */
 /* for "JLink CDC UART Port" use the define below : */
-/* Serial uart1(USBTX, USBRX);                      */
+/* Serial dev(USBTX, USBRX);                      */
 /* otherwise use the hardware UART on 0.12 & 0.11   */
 /* (a.k.a. d1 & D1 in Arduino parlance...           */
- Serial uart1(P0_12, P0_11);
- 
+ //Serial dev(P0_12, P0_11);
+ Serial dev(USBTX, USBRX);
+ static uint8_t rx_buf[32];
+ static uint8_t rx_len=0;
+ int tx_buf;
+ static uint8_t tx_len=0;
+
 /* define some blinky LED fun */
 DigitalOut led1(LED1);
 //DigitalOut led2(LED2);
 //DigitalOut led3(LED3);
 //DigitalOut led4(LED4);
 
-void disconnectionCallback(const Gap::DisconnectionCallbackParams_t *params)
+void theBLEdisconnectionCallback(const Gap::DisconnectionCallbackParams_t *params)
 {
     #if DEBUG_OUTPUT
       DEBUG("Disconnected!\n\r");
@@ -77,18 +82,48 @@
     ble.startAdvertising();
 }
 
-void onDataWritten(const GattWriteCallbackParams *params)
+void theBLEonDataWritten(const GattWriteCallbackParams *params)
 {
     if ((uartServicePtr != NULL) && (params->handle == uartServicePtr->getTXCharacteristicHandle())) {
         uint16_t bytesRead = params->len;
+        uint8_t byteCnt;
         
         #if DEBUG_OUTPUT
-          DEBUG("BLART received %u bytes\n\r", bytesRead);
+          DEBUG("BLART BLE received %u bytes\n\r", bytesRead);
         #endif
-        ble.updateCharacteristicValue(uartServicePtr->getRXCharacteristicHandle(), params->data, bytesRead);
+        
+        if (UART_LoopBack == 0) {
+          /* pass thru BLE UART data to UART1 */
+          for (byteCnt = 0; byteCnt < bytesRead; byteCnt++) {
+              dev.putc(params->data[byteCnt]);
+          } 
+        } else {
+          /* otherwise, loopback BLE UART data to itself */    
+          ble.updateCharacteristicValue(uartServicePtr->getRXCharacteristicHandle(), params->data, bytesRead);
+        }
     }
 }
 
+void theUARTonDataWritten(void) {
+    while(dev.readable())    
+    {
+        rx_buf[rx_len++] = dev.getc();
+        #if DEBUG_OUTPUT
+          DEBUG("BLART BLE received %u \n\r", rx_buf[rx_len]);
+        #endif    
+             if (UART_LoopBack == 0) {
+              ble.updateCharacteristicValue(uartServicePtr->getRXCharacteristicHandle(), rx_buf, rx_len);
+              rx_len = 0;
+            } else {
+                for (tx_len = 0; tx_len < rx_len; tx_len++) {
+                  tx_buf = rx_buf[tx_len];  
+                  dev.putc(tx_buf);
+                }
+                rx_len = 0;
+            } 
+    }            
+}
+
 void theTickCallback(void)
 {
     /* toggle the LED each timer tick (1 sec) */
@@ -102,13 +137,16 @@
     Ticker ticker;
     ticker.attach(theTickCallback, 1);
 
+    /* attach the hardwate UART1 data received callback */
+    dev.attach( &theUARTonDataWritten , dev.RxIrq);
+    
     /* initialze the BLE services */
     #if DEBUG_OUTPUT
       DEBUG("Initialising the nRF5x\n\r");
     #endif
     ble.init();
-    ble.onDisconnection(disconnectionCallback);
-    ble.onDataWritten(onDataWritten);
+    ble.onDisconnection(theBLEdisconnectionCallback);
+    ble.onDataWritten(theBLEonDataWritten);
 
     /* setup the BLE advertising */
     ble.accumulateAdvertisingPayload(GapAdvertisingData::BREDR_NOT_SUPPORTED);
@@ -130,7 +168,10 @@
     UARTService uartService(ble);
     uartServicePtr = &uartService;
 
-    /* main */
+    /* start the hardware UART1 */
+    //uart1.printf("Hello! My name is BLART, what's yours?\n");
+    
+    /* main loop */
     while (true) {
         /* call wait to give other threads a chance to run */
         ble.waitForEvent();