blob: ea35e101aa3560c686c41a1d7a010a7de8669297 [file] [log] [blame]
/*
* ======== talk.c ========
*/
#include <xdc/runtime/System.h>
#include "bsp.h"
#include "mrfi.h"
#include "nwk_types.h"
#include "nwk_api.h"
#include "bsp_leds.h"
#include "bsp_buttons.h"
static void linkTo(void);
static void toggleLED(uint8_t);
static uint8_t sTxTid = 0, sRxTid = 0;
static linkID_t sLinkID1;
/* application Rx frame handler. */
static uint8_t sRxCallback(linkID_t);
#define MINPERIOD 1
#define MAXPERIOD 1000
uint16_t msgPeriod = 100;
/*
* ======== main ========
*/
void main(void)
{
addr_t lAddr = {0x77, 0x56, 0x34, 0x12};
System_printf("before BSP_init ...\n");
BSP_Init();
System_printf("after BSP_init.\n");
SMPL_Ioctl(IOCTL_OBJ_ADDR, IOCTL_ACT_SET, &lAddr);
/* This call will fail because the join will fail since there is no Access
* Point in this scenario. But we don't care -- just use the default link
* token later.
*
* We supply a callback pointer to handle the message returned by the peer.
*/
SMPL_Init(sRxCallback);
/* turn on LEDs. */
if (!BSP_LED2_IS_ON()) {
toggleLED(2);
}
if (!BSP_LED1_IS_ON()) {
toggleLED(1);
}
/* wait for a button press... */
System_printf("waiting for a button ...\n");
for (;;) {
if (BSP_BUTTON1() || BSP_BUTTON2()) {
break;
}
}
/* never coming back... */
linkTo();
/* but in case we do... */
System_printf("oops!\n");
System_exit(1);
}
/*
* ======== linkTo ========
*/
static void linkTo()
{
uint8_t msg[2], delay = 0;
System_printf("linking ...\n");
while (SMPL_SUCCESS != SMPL_Link(&sLinkID1)) {
/* blink LEDs until we link successfully */
toggleLED(1);
toggleLED(2);
NWK_DELAY(1000);
}
/* we're linked. turn off red LED. received messages will toggle the
* green LED.
*/
System_printf("linked to %d.\n", sLinkID1);
if (BSP_LED2_IS_ON()) {
toggleLED(2);
}
/* turn on RX. default is RX off. */
SMPL_Ioctl(IOCTL_OBJ_RADIO, IOCTL_ACT_RADIO_RXON, 0);
/* put LED to toggle in the message */
msg[0] = 2; /* toggle red */
while (1) {
NWK_DELAY(msgPeriod + (delay * msgPeriod));
/* delay longer and longer -- then start over */
delay = (delay + 1) & 0x07;
/* put the sequence ID in the message */
msg[1] = ++sTxTid;
SMPL_Send(sLinkID1, msg, sizeof(msg));
}
}
/*
* ======== toggleLED ========
*/
static void toggleLED(uint8_t which)
{
if (1 == which) {
BSP_TOGGLE_LED1();
}
else if (2 == which) {
BSP_TOGGLE_LED2();
}
}
/*
* ======== sRxCallback ========
* handle received frames.
*/
static uint8_t sRxCallback(linkID_t port)
{
uint8_t msg[2], len, tid, delta;
/* is the callback for the link ID we want to handle? */
if (port == sLinkID1) {
/* yes. go get the frame. we know this call will succeed. */
if ((SMPL_SUCCESS == SMPL_Receive(sLinkID1, msg, &len)) && len) {
/* Check the application sequence number to detect
* late or missing frames...
*/
tid = msg[1];
delta = tid - sRxTid;
if (delta != 1) {
System_printf(
"frame error: prev = 0x%x, received = 0x%x, sent = 0x%x\n",
sRxTid, tid, sTxTid);
}
if (tid) {
if (tid > sRxTid) {
/* we're good. toggle LED in the message */
toggleLED(*msg);
sRxTid = tid;
}
}
else {
/* the wrap case... */
if (sRxTid) {
/* we're good. toggle LED in the message */
toggleLED(*msg);
sRxTid = tid;
}
}
/* drop frame. we're done with it. */
return (1);
}
else {
System_printf("receive from %d (len = %d) failed.\n",
sLinkID1, len);
}
}
/* keep frame for later handling. */
return (0);
}
/*
* ======== uartRxCallback ========
*/
void uartRxCallback(char *buf)
{
switch (buf[0]) {
case '-': {
msgPeriod -= 10;
break;
}
case '+': {
msgPeriod += 10;
break;
}
case '0': {
msgPeriod = 0;
break;
}
default: {
break;
}
}
if (msgPeriod < MINPERIOD) {
msgPeriod = MINPERIOD;
}
if (msgPeriod > MAXPERIOD) {
msgPeriod = MAXPERIOD;
}
}