Repository: incubator-mynewt-site Updated Branches: refs/heads/develop 4981e8644 -> c28a73bbe
added eddystone beacon tutorial Project: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/repo Commit: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/commit/c28a73bb Tree: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/tree/c28a73bb Diff: http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/diff/c28a73bb Branch: refs/heads/develop Commit: c28a73bbe5cc8ba430e566fd677a0d58f42d52a1 Parents: 4981e86 Author: aditihilbert <ad...@runtime.io> Authored: Wed Feb 15 00:29:29 2017 -0800 Committer: aditihilbert <ad...@runtime.io> Committed: Wed Feb 15 00:29:29 2017 -0800 ---------------------------------------------------------------------- docs/os/tutorials/eddystone.md | 197 ++++++++++++++++++++++++++++++++++++ docs/os/tutorials/ibeacon.md | 59 +++++++++-- mkdocs.yml | 1 + 3 files changed, 247 insertions(+), 10 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/blob/c28a73bb/docs/os/tutorials/eddystone.md ---------------------------------------------------------------------- diff --git a/docs/os/tutorials/eddystone.md b/docs/os/tutorials/eddystone.md new file mode 100644 index 0000000..53f188d --- /dev/null +++ b/docs/os/tutorials/eddystone.md @@ -0,0 +1,197 @@ +## BLE Eddystone + +<br> + +### Eddystone Beacon Protocol + +A beaconing device announces its presence to the world by broadcasting +advertisements. The Eddystone protocol is built on top of the standard BLE +advertisement specification. Eddystone supports multiple data packet types + +* Eddystone-UID: a unique, static ID with a 10-byte Namespace component and a 6-byte Instance component. +* Eddystone-URL: a compressed URL that, once parsed and decompressed, is directly usable by the client. +* Eddystone-TLM: "telemetry" packets that are broadcast alongside the Eddystone-UID or Eddystone-URL packets and contains beaconâs âhealth statusâ (e.g., battery life). +* Eddystone-EID to broadcast an ephemeral identifier that changes every few minutes and allow only parties that can resolve the identifier to use the beacon. + +[This page](https://developers.google.com/beacons/eddystone) describes the Eddystone open beacon format developed by Google. + +Apache Mynewt currently supports Eddystone-UID and Eddystone-URL formats only. This tutorial will explain how to get an Eddystone-URL beacon going on a peripheral device. + +<br> + +### Configuration + +Use the following function to configure your NimBLE device to send Eddystone-URL beacons: + +```c +int +ble_eddystone_set_adv_data_url(struct ble_hs_adv_fields *adv_fields, + uint8_t url_scheme, char *url_body, + uint8_t url_body_len, uint8_t url_suffix) +``` + +This function's parameters are documented below. + +| *Parameter* | *Purpose* | +| ----------- | --------- | +| adv_fields | The base advertisement fields to transform into an eddystone beacon. | +| url_scheme | The prefix of the URL; one of the BLE_EDDYSTONE_URL_SCHEME values from ble_eddystone.h | +| url_body | The middle of the url specified within "". | +| url_body_len | The string length of the url_body argument. | +| url_suffix | The suffix of the URL; one of the BLE_EDDYSTONE_URL_SUFFIX values from ble_eddystone.h | + +<br> + +### Modify bleprph + +To demonstrate how the above function is used, we will now modify the *bleprph* +example application to send Eddystone beacons. For some background behind the *bleprph* +app, we recommend you take a look at the [bleprph project +tutorial](bleprph/bleprph-intro/). If you plan on making these modifications +yourself, it might be a good idea to copy *bleprph* to your local repository +and work with the copy. In general, you should avoid changing a package that +newt downloads, as you will lose your changes the next time you upgrade the +package. + +*bleprph* sets its advertisement data and begins advertising as follows (*main.c*): + +```c +static void +bleprph_advertise(void) +{ + struct ble_gap_adv_params adv_params; + struct ble_hs_adv_fields fields; + const char *name; + int rc; + + /** + * Set the advertisement data included in our advertisements: + * o Flags (indicates advertisement type and other general info). + * o Advertising tx power. + * o Device name. + * o 16-bit service UUIDs (alert notifications). + */ + + memset(&fields, 0, sizeof fields); + + /* Advertise two flags: + * o Discoverability in forthcoming advertisement (general) + * o BLE-only (BR/EDR unsupported). + */ + fields.flags = BLE_HS_ADV_F_DISC_GEN | + BLE_HS_ADV_F_BREDR_UNSUP; + + /* Indicate that the TX power level field should be included; have the + * stack fill this value automatically. This is done by assiging the + * special value BLE_HS_ADV_TX_PWR_LVL_AUTO. + */ + fields.tx_pwr_lvl_is_present = 1; + fields.tx_pwr_lvl = BLE_HS_ADV_TX_PWR_LVL_AUTO; + + name = ble_svc_gap_device_name(); + fields.name = (uint8_t *)name; + fields.name_len = strlen(name); + fields.name_is_complete = 1; + + fields.uuids16 = (ble_uuid16_t[]){ + BLE_UUID16_INIT(GATT_SVR_SVC_ALERT_UUID) + }; + fields.num_uuids16 = 1; + fields.uuids16_is_complete = 1; + + rc = ble_gap_adv_set_fields(&fields); + if (rc != 0) { + BLEPRPH_LOG(ERROR, "error setting advertisement data; rc=%d\n", rc); + return; + } + + /* Begin advertising. */ + memset(&adv_params, 0, sizeof adv_params); + adv_params.conn_mode = BLE_GAP_CONN_MODE_UND; + adv_params.disc_mode = BLE_GAP_DISC_MODE_GEN; + rc = ble_gap_adv_start(BLE_OWN_ADDR_PUBLIC, NULL, BLE_HS_FOREVER, + &adv_params, bleprph_gap_event, NULL); + if (rc != 0) { + BLEPRPH_LOG(ERROR, "error enabling advertisement; rc=%d\n", rc); + return; + } +} +``` + +The call to `ble_gap_adv_set_fields()` configures the device with normal +(non-Eddystone) advertisements; the call to `ble_gap_adv_start()` tells the +NimBLE stack to start broadcasting. We are now going to create an Eddystone app +by making the following changes: + +* Call `ble_eddystone_set_adv_data()` instead of `ble_gap_adv_set_fields()`. The tutorial shows how to emit "`https://mynewt.apache.org". +* Remove advertisement data such as device name, flags, tx levels etc. that are not required. +* Remove unnecessary local variables e.g. `name` pointer. +* Modify the call to `ble_gap_adv_start()` such that the device is non-discoverable and non-connectable. + +<br> + +```c hl_lines="9 18 20 29 30" +static void +bleprph_advertise(void) +{ + struct ble_gap_adv_params adv_params; + struct ble_hs_adv_fields fields; + int rc; + + /** + * Remove the advertisement data typically included in our advertisements: + * o Flags (indicates advertisement type and other general info). + * o Advertising tx power. + * o Device name. + * o 16-bit service UUIDs (alert notifications). + */ + + memset(&fields, 0, sizeof fields); + + /* No flags are needed for Eddystone URL. Remove all from default app.*/ + + rc = ble_eddystone_set_adv_data_url(&fields, BLE_EDDYSTONE_URL_SCHEME_HTTPS, "mynewt.apache", + 13, BLE_EDDYSTONE_URL_SUFFIX_ORG); + if (rc != 0) { + BLEPRPH_LOG(ERROR, "error setting eddystone advertisement data; rc=%d\n", rc); + return; + } + + /* Begin advertising. */ + memset(&adv_params, 0, sizeof adv_params); + adv_params.conn_mode = BLE_GAP_CONN_MODE_NON; + adv_params.disc_mode = BLE_GAP_DISC_MODE_NON; + rc = ble_gap_adv_start(BLE_OWN_ADDR_PUBLIC, NULL, BLE_HS_FOREVER, + &adv_params, bleprph_gap_event, NULL); + if (rc != 0) { + BLEPRPH_LOG(ERROR, "error enabling advertisement; rc=%d\n", rc); + return; + } +} + +``` + +Also include the header file for the eddystone beacon `ble_eddystone.h` in the app's main.c file. + +```c +#include "host/ble_eddystone.h" +``` + +If you have copied the bleprph app into your local repository then make sure that the pkg.yml for the app has the `@apache-mynewt-core/` prefix; otherwise the package dependencies will not be resolved correctly. + +``` +pkg.deps: + - "@apache-mynewt-core/boot/split" + - "@apache-mynewt-core/kernel/os" +<snip> +``` + +Finally, enable the `BLE_EDDYSTONE` sysconfig in the syscfg.yml of either your target or your app. +``` +syscfg.vals: + <snip> + BLE_EDDYSTONE: 1 +``` + +Now when you run this app on your board, you should be able to see it with all +your Eddystone-aware devices. http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/blob/c28a73bb/docs/os/tutorials/ibeacon.md ---------------------------------------------------------------------- diff --git a/docs/os/tutorials/ibeacon.md b/docs/os/tutorials/ibeacon.md index 3b4fa4e..83182b2 100644 --- a/docs/os/tutorials/ibeacon.md +++ b/docs/os/tutorials/ibeacon.md @@ -49,14 +49,46 @@ package. static void bleprph_advertise(void) { + struct ble_gap_adv_params adv_params; struct ble_hs_adv_fields fields; + const char *name; int rc; - /* Set the advertisement data included in our advertisements. */ + /** + * Set the advertisement data included in our advertisements: + * o Flags (indicates advertisement type and other general info). + * o Advertising tx power. + * o Device name. + * o 16-bit service UUIDs (alert notifications). + */ + memset(&fields, 0, sizeof fields); - fields.name = (uint8_t *)bleprph_device_name; - fields.name_len = strlen(bleprph_device_name); + + /* Advertise two flags: + * o Discoverability in forthcoming advertisement (general) + * o BLE-only (BR/EDR unsupported). + */ + fields.flags = BLE_HS_ADV_F_DISC_GEN | + BLE_HS_ADV_F_BREDR_UNSUP; + + /* Indicate that the TX power level field should be included; have the + * stack fill this value automatically. This is done by assiging the + * special value BLE_HS_ADV_TX_PWR_LVL_AUTO. + */ + fields.tx_pwr_lvl_is_present = 1; + fields.tx_pwr_lvl = BLE_HS_ADV_TX_PWR_LVL_AUTO; + + name = ble_svc_gap_device_name(); + fields.name = (uint8_t *)name; + fields.name_len = strlen(name); fields.name_is_complete = 1; + + fields.uuids16 = (ble_uuid16_t[]){ + BLE_UUID16_INIT(GATT_SVR_SVC_ALERT_UUID) + }; + fields.num_uuids16 = 1; + fields.uuids16_is_complete = 1; + rc = ble_gap_adv_set_fields(&fields); if (rc != 0) { BLEPRPH_LOG(ERROR, "error setting advertisement data; rc=%d\n", rc); @@ -64,8 +96,11 @@ bleprph_advertise(void) } /* Begin advertising. */ - rc = ble_gap_adv_start(BLE_GAP_DISC_MODE_GEN, BLE_GAP_CONN_MODE_UND, - NULL, 0, NULL, bleprph_on_connect, NULL); + memset(&adv_params, 0, sizeof adv_params); + adv_params.conn_mode = BLE_GAP_CONN_MODE_UND; + adv_params.disc_mode = BLE_GAP_DISC_MODE_GEN; + rc = ble_gap_adv_start(BLE_OWN_ADDR_PUBLIC, NULL, BLE_HS_FOREVER, + &adv_params, bleprph_gap_event, NULL); if (rc != 0) { BLEPRPH_LOG(ERROR, "error enabling advertisement; rc=%d\n", rc); return; @@ -76,21 +111,22 @@ bleprph_advertise(void) The call to `ble_gap_adv_set_fields()` configures the device with normal (non-iBeacon) advertisements; the call to `ble_gap_adv_start()` tells the NimBLE stack to start broadcasting. We are now going to create an iBeacon app -by making the following to changes: +by making the following two changes: * Call `ble_ibeacon_set_adv_data()` instead of `ble_gap_adv_set_fields()`. * Modify the call to `ble_gap_adv_start()` such that the device is non-discoverable and non-connectable. <br> -```c hl_lines="4 7 8 10 11 19" +```c hl_lines="4 5 7 8 9 11 12 21 22" static void bleprph_advertise(void) { + struct ble_gap_adv_params adv_params; uint8_t uuid128[16]; int rc; - /* Arbitrarily et the UUID to a string of 0x11 bytes. */ + /* Arbitrarily set the UUID to a string of 0x11 bytes. */ memset(uuid128, 0x11, sizeof uuid128); /* Major version=2; minor version=10. */ @@ -102,8 +138,11 @@ bleprph_advertise(void) } /* Begin advertising. */ - rc = ble_gap_adv_start(BLE_GAP_DISC_MODE_NON, BLE_GAP_CONN_MODE_NON, - NULL, 0, NULL, bleprph_on_connect, NULL); + memset(&adv_params, 0, sizeof adv_params); + adv_params.conn_mode = BLE_GAP_CONN_MODE_NON; + adv_params.disc_mode = BLE_GAP_DISC_MODE_NON; + rc = ble_gap_adv_start(BLE_OWN_ADDR_PUBLIC, NULL, BLE_HS_FOREVER, + &adv_params, bleprph_gap_event, NULL); if (rc != 0) { BLEPRPH_LOG(ERROR, "error enabling advertisement; rc=%d\n", rc); return; http://git-wip-us.apache.org/repos/asf/incubator-mynewt-site/blob/c28a73bb/mkdocs.yml ---------------------------------------------------------------------- diff --git a/mkdocs.yml b/mkdocs.yml index eb13a8a..e55efcc 100644 --- a/mkdocs.yml +++ b/mkdocs.yml @@ -64,6 +64,7 @@ pages: - 'GAP Event Callbacks': 'os/tutorials/bleprph/bleprph-gap-event.md' - 'BLE Peripheral App' : 'os/tutorials/bleprph/bleprph-app.md' - 'BLE iBeacon': 'os/tutorials/ibeacon.md' + - 'BLE Eddystone': 'os/tutorials/eddystone.md' - 'BLE HCI interface': 'os/tutorials/blehci_project.md' - OS User Guide: - toc: 'os/os_user_guide.md'