Skip to content

Commit

Permalink
Merged in antmerlino/apps/i8sak_daemon (pull request apache#151)
Browse files Browse the repository at this point in the history
i8sak: i8sak daemon now gets shutdown if not in use.

Previously, once the i8sak daemon was started, by running any command, it would stay running. This means that if you want to use i8sak to setup your network, but then want exclusive access to the char device, or network device, you have to manually shutdown the i8sak daemon. Now the daemon stays active as long as required to finish any commands, or stays open if a new command keeps it on, but when all work is finished, it shuts down.

Approved-by: GregoryN <gnutt@nuttx.org>
  • Loading branch information
antmerlino authored and gregory-nutt committed Aug 19, 2018
1 parent 8e249eb commit 162fb66
Show file tree
Hide file tree
Showing 9 changed files with 136 additions and 54 deletions.
18 changes: 12 additions & 6 deletions wireless/ieee802154/i8sak/i8sak.h
Original file line number Diff line number Diff line change
Expand Up @@ -124,13 +124,16 @@ struct i8sak_s
pid_t daemon_pid;
FAR char ifname[I8SAK_MAX_IFNAME];
int result;
int fd; /* File/Socket descriptor. Only to be used by operations
* occuring within the Daemon TCB
*/
int fd; /* File/Socket descriptor. Only to be used by operations
* occuring within the Daemon TCB
*/

sem_t exclsem; /* For synchronizing access to the signaling semaphore */
sem_t sigsem; /* For signaling various tasks */
sem_t updatesem; /* For signaling the daemon that it's settings have changed */
sem_t exclsem; /* For synchronizing access to the signaling semaphore */
sem_t sigsem; /* For signaling various tasks */
sem_t updatesem; /* For signaling the daemon that it's settings have changed */
sem_t daemonlock; /* For synchronizing access to managing the daemon */

int daemonusers;

/* Fields related to event listener */

Expand Down Expand Up @@ -202,6 +205,9 @@ struct i8sak_s
* Public Function Prototypes
****************************************************************************/

int i8sak_requestdaemon(FAR struct i8sak_s *i8sak);
int i8sak_releasedaemon(FAR struct i8sak_s *i8sak);

uint8_t i8sak_char2nibble (char ch);
long i8sak_str2long (FAR const char *str);
uint8_t i8sak_str2luint8 (FAR const char *str);
Expand Down
2 changes: 2 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_acceptassoc.c
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,8 @@ void i8sak_acceptassoc_cmd(FAR struct i8sak_s *i8sak, int argc,
printf("i8sak: accepting all assoc requests\n");
}

i8sak_requestdaemon(i8sak);

/* Register new callback for receiving the association notifications */

memset(&filter, 0, sizeof(struct i8sak_eventfilter_s));
Expand Down
4 changes: 3 additions & 1 deletion wireless/ieee802154/i8sak/i8sak_assoc.c
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,8 @@ void i8sak_assoc_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
}
#endif

i8sak_requestdaemon(i8sak);

/* Register new callback for receiving the association notifications. */

memset(&filter, 0, sizeof(struct i8sak_eventfilter_s));
Expand Down Expand Up @@ -260,7 +262,6 @@ void i8sak_assoc_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
i8sak->result = -EBUSY;

ret = sem_wait(&i8sak->sigsem);
sem_post(&i8sak->exclsem);
if (ret != OK)
{
i8sak->assoc = false;
Expand Down Expand Up @@ -311,6 +312,7 @@ void i8sak_assoc_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
/* Clean up and return */

(void)i8sak_eventlistener_removereceiver(i8sak, assoc_eventcb);
i8sak_releasedaemon(i8sak);
close(fd);
}

Expand Down
2 changes: 2 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_blaster.c
Original file line number Diff line number Diff line change
Expand Up @@ -98,6 +98,8 @@ void i8sak_blaster_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
{
int option;

i8sak_requestdaemon(i8sak);

if (argc < 2)
{
i8sak_blaster_start(i8sak);
Expand Down
150 changes: 103 additions & 47 deletions wireless/ieee802154/i8sak/i8sak_main.c
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,100 @@ static void i8sak_switch_instance(FAR char *ifname);
* Public Functions
****************************************************************************/

/****************************************************************************
* Name : i8sak_requestdaemon
*
* Description :
*
****************************************************************************/

int i8sak_requestdaemon(FAR struct i8sak_s *i8sak)
{
char daemonname[I8SAK_MAX_DAEMONNAME];
int ret;
int len;

ret = sem_wait(&i8sak->daemonlock);
if (ret < 0)
{
DEBUGASSERT(ret == EINTR);
return ret;
}

if (++i8sak->daemonusers == 1)
{
/* Create strings for task based on device. i.e. i8_ieee0 */

if (i8sak->mode == I8SAK_MODE_CHAR)
{
len = strlen(i8sak->ifname);
snprintf(daemonname, I8SAK_DAEMONNAME_PREFIX_LEN + (len - 5),
I8SAK_DAEMONNAME_FMT, &i8sak->ifname[5]);
}
#ifdef CONFIG_NET_6LOWPAN
else if (i8sak->mode == I8SAK_MODE_NETIF)
{
len = strlen(i8sak->ifname);
snprintf(daemonname, I8SAK_DAEMONNAME_PREFIX_LEN + len,
I8SAK_DAEMONNAME_FMT, i8sak->ifname);
}
#endif

i8sak->daemon_started = true;
i8sak->daemon_pid = task_create(daemonname, CONFIG_IEEE802154_I8SAK_PRIORITY,
CONFIG_IEEE802154_I8SAK_STACKSIZE, i8sak_daemon,
NULL);
if (i8sak->daemon_pid < 0)
{
fprintf(stderr, "failed to start daemon\n");
sem_post(&i8sak->daemonlock);
return ERROR;
}

/* Use the signal semaphore to wait for daemon to start before returning */

ret = sem_wait(&i8sak->sigsem);
if (ret < 0)
{
fprintf(stderr, "i8sak:interrupted while daemon starting\n");
sem_post(&i8sak->daemonlock);
return ret;
}
}

sem_post(&i8sak->daemonlock);
return 0;
}

/****************************************************************************
* Name : i8sak_releasedaemon
*
* Description :
*
****************************************************************************/

int i8sak_releasedaemon(FAR struct i8sak_s *i8sak)
{
int ret;

ret = sem_wait(&i8sak->daemonlock);
if (ret < 0)
{
DEBUGASSERT(ret == EINTR);
return ret;
}

/* If this was the last user, signal the daemon to shutdown */

if (--i8sak->daemonusers == 0)
{
i8sak->daemon_shutdown = true;
sem_post(&i8sak->updatesem);
}

return 0;
}

/****************************************************************************
* Name : i8sak_str2payload
*
Expand Down Expand Up @@ -496,34 +590,29 @@ static void i8sak_switch_instance(FAR char *ifname)

static int i8sak_setup(FAR struct i8sak_s *i8sak, FAR const char *ifname)
{
char daemonname[I8SAK_MAX_DAEMONNAME];
int i;
int ret;
int len;
int fd = 0;

if (i8sak->initialized)
{
return OK;
}

i8sak->chan = 11;
i8sak->chpage = 0;

if (strlen(ifname) > I8SAK_MAX_IFNAME)
{
fprintf(stderr, "ERROR: ifname too long\n");
return ERROR;
}

strcpy(&i8sak->ifname[0], ifname);

i8sak->chan = 11;
i8sak->chpage = 0;
i8sak->addrmode = IEEE802154_ADDRMODE_SHORT;

/* Initialize the default remote endpoint address */

i8sak->ep_addr.mode = IEEE802154_ADDRMODE_SHORT;

/* Initialize the default remote endpoint address */

for (i = 0; i < IEEE802154_EADDRSIZE; i++)
{
i8sak->ep_addr.eaddr[i] =
Expand Down Expand Up @@ -610,8 +699,11 @@ static int i8sak_setup(FAR struct i8sak_s *i8sak, FAR const char *ifname)

sem_init(&i8sak->eventsem, 0, 1);

sem_init(&i8sak->daemonlock, 0, 1);

i8sak->daemon_started = false;
i8sak->daemon_shutdown = false;
i8sak->daemonusers = 0;

i8sak->eventlistener_run = false;
sq_init(&i8sak->eventreceivers);
Expand All @@ -623,41 +715,6 @@ static int i8sak_setup(FAR struct i8sak_s *i8sak, FAR const char *ifname)

i8sak->blasterperiod = 1000;

/* Create strings for task based on device. i.e. i8_ieee0 */

if (i8sak->mode == I8SAK_MODE_CHAR)
{
len = strlen(ifname);
snprintf(daemonname, I8SAK_DAEMONNAME_PREFIX_LEN + (len - 5),
I8SAK_DAEMONNAME_FMT, &ifname[5]);
}
#ifdef CONFIG_NET_6LOWPAN
else if (i8sak->mode == I8SAK_MODE_NETIF)
{
len = strlen(ifname);
snprintf(daemonname, I8SAK_DAEMONNAME_PREFIX_LEN + len,
I8SAK_DAEMONNAME_FMT, ifname);
}
#endif

i8sak->daemon_pid = task_create(daemonname, CONFIG_IEEE802154_I8SAK_PRIORITY,
CONFIG_IEEE802154_I8SAK_STACKSIZE, i8sak_daemon,
NULL);
if (i8sak->daemon_pid < 0)
{
fprintf(stderr, "failed to start daemon\n");
return ERROR;
}

/* Use the signal semaphore to wait for daemon to start before returning */

ret = sem_wait(&i8sak->sigsem);
if (ret < 0)
{
fprintf(stderr, "i8sak:interrupted while daemon starting\n");
return ERROR;
}

i8sak->initialized = true;
return OK;
}
Expand All @@ -675,7 +732,6 @@ static int i8sak_daemon(int argc, FAR char *argv[])
int ret;

fprintf(stderr, "i8sak: daemon started\n");
i8sak->daemon_started = true;

if (i8sak->mode == I8SAK_MODE_CHAR)
{
Expand Down Expand Up @@ -766,12 +822,12 @@ static int i8sak_showusage(FAR const char *progname, int exitcode)
" acceptassoc [-h|e]\n"
" assoc [-h|p|e|s|w|r|t]\n"
" blaster [-h|q|f|p]\n"
" get [-h] parameter"
" get [-h] parameter\n"
" poll [-h]\n"
" regdump [-h]\n"
" reset [-h]\n"
" scan [-h|p|a|e] minch-maxch\n"
" set [-h] param val"
" set [-h] param val\n"
" sniffer [-h|d]\n"
" startpan [-h|b|s] xx:xx\n"
" tx [-h|d|m] <hex-payload>\n"
Expand Down
4 changes: 4 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_poll.c
Original file line number Diff line number Diff line change
Expand Up @@ -110,6 +110,8 @@ void i8sak_poll_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
}
}

i8sak_requestdaemon(i8sak);

/* Register new oneshot callback for receiving the association notifications */

memset(&eventfilter, 0, sizeof(struct i8sak_eventfilter_s));
Expand Down Expand Up @@ -163,6 +165,8 @@ void i8sak_poll_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
printf("i8sak: poll cancelled\n");
i8sak_cmd_error(i8sak);
}

i8sak_releasedaemon(i8sak);
}

/****************************************************************************
Expand Down
4 changes: 4 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_scan.c
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,8 @@ void i8sak_scan_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
scan.channels[i] = minchannel + i;
}

i8sak_requestdaemon(i8sak);

/* Register new callback for receiving the scan confirmation notification */

memset(&filter, 0, sizeof(struct i8sak_eventfilter_s));
Expand Down Expand Up @@ -257,4 +259,6 @@ static void scan_eventcb(FAR struct ieee802154_primitive_s *primitive, FAR void
PRINTF_FORMAT_EADDR(scan->pandescs[i].coordaddr.eaddr));
}
}

i8sak_requestdaemon(i8sak);
}
2 changes: 2 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_sniffer.c
Original file line number Diff line number Diff line change
Expand Up @@ -171,6 +171,8 @@ void i8sak_sniffer_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])

close(fd);

i8sak_requestdaemon(i8sak);

/* Start the sniffer thread. We use the existing daemon thread so that this
* thread belongs to the daemon task group.
*/
Expand Down
4 changes: 4 additions & 0 deletions wireless/ieee802154/i8sak/i8sak_tx.c
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,8 @@ void i8sak_tx_cmd(FAR struct i8sak_s *i8sak, int argc, FAR char *argv[])
tx.meta.flags.indirect = false;
}

i8sak_requestdaemon(i8sak);

/* Register new oneshot callback for receiving the association notifications */

memset(&eventfilter, 0, sizeof(struct i8sak_eventfilter_s));
Expand Down Expand Up @@ -296,4 +298,6 @@ static void tx_eventcb(FAR struct ieee802154_primitive_s *primitive, FAR void *a
}

sem_post(&i8sak->sigsem);

i8sak_requestdaemon(i8sak);
}

0 comments on commit 162fb66

Please sign in to comment.