lib/thread: Add API spdk_poller_register_named() to set arbitrary name

Add an new API spdk_poller_register_named() to set arbitrary name
to the created poller. If NULL, the name is set to the pointer of
the poller function.

To set the name to the string of the poller function name conveniently,
add an new macro SPDK_POLLER_REGISTER() together in this patch.

All debug or error logs are changed to output poller name from pointer.

The added name will be used in the new RPC thread_get_pollers.

Signed-off-by: Shuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Change-Id: I3be558dd795252f797e3e81fa2db2e8b128cf004
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/506
Tested-by: SPDK CI Jenkins <sys_sgci@intel.com>
Reviewed-by: Maciej Szwed <maciej.szwed@intel.com>
Reviewed-by: Darek Stojaczyk <dariusz.stojaczyk@intel.com>
Reviewed-by: Aleksey Marchuk <alexeymar@mellanox.com>
This commit is contained in:
Shuhei Matsumoto 2020-02-10 20:16:35 -05:00 committed by Tomasz Zawadzki
parent cf669d0217
commit b992bb4e46
3 changed files with 71 additions and 17 deletions

View File

@ -511,6 +511,33 @@ struct spdk_poller *spdk_poller_register(spdk_poller_fn fn,
void *arg, void *arg,
uint64_t period_microseconds); uint64_t period_microseconds);
/**
* Register a poller on the current thread with arbitrary name.
*
* The poller can be unregistered by calling spdk_poller_unregister().
*
* \param fn This function will be called every `period_microseconds`.
* \param arg Argument passed to fn.
* \param period_microseconds How often to call `fn`. If 0, call `fn` as often
* as possible.
* \param name Human readable name for the poller. Pointer of the poller function
* name is set if NULL.
*
* \return a pointer to the poller registered on the current thread on success
* or NULL on failure.
*/
struct spdk_poller *spdk_poller_register_named(spdk_poller_fn fn,
void *arg,
uint64_t period_microseconds,
const char *name);
/*
* \brief Register a poller on the current thread with setting its name
* to the string of the poller function name.
*/
#define SPDK_POLLER_REGISTER(fn, arg, period_microseconds) \
spdk_poller_register_named(fn, arg, period_microseconds, #fn)
/** /**
* Unregister a poller on the current thread. * Unregister a poller on the current thread.
* *

View File

@ -37,6 +37,7 @@
#include "spdk/stdinc.h" #include "spdk/stdinc.h"
#include "spdk/thread.h" #include "spdk/thread.h"
#define SPDK_MAX_POLLER_NAME_LEN 256
#define SPDK_MAX_THREAD_NAME_LEN 256 #define SPDK_MAX_THREAD_NAME_LEN 256
enum spdk_poller_state { enum spdk_poller_state {
@ -71,6 +72,8 @@ struct spdk_poller {
spdk_poller_fn fn; spdk_poller_fn fn;
void *arg; void *arg;
struct spdk_thread *thread; struct spdk_thread *thread;
char name[SPDK_MAX_POLLER_NAME_LEN + 1];
}; };
struct spdk_thread { struct spdk_thread {

View File

@ -182,8 +182,8 @@ _free_thread(struct spdk_thread *thread)
TAILQ_FOREACH_SAFE(poller, &thread->active_pollers, tailq, ptmp) { TAILQ_FOREACH_SAFE(poller, &thread->active_pollers, tailq, ptmp) {
if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) { if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) {
SPDK_WARNLOG("poller %p still registered at thread exit\n", SPDK_WARNLOG("poller %s still registered at thread exit\n",
poller); poller->name);
} }
TAILQ_REMOVE(&thread->active_pollers, poller, tailq); TAILQ_REMOVE(&thread->active_pollers, poller, tailq);
free(poller); free(poller);
@ -191,15 +191,15 @@ _free_thread(struct spdk_thread *thread)
TAILQ_FOREACH_SAFE(poller, &thread->timed_pollers, tailq, ptmp) { TAILQ_FOREACH_SAFE(poller, &thread->timed_pollers, tailq, ptmp) {
if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) { if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) {
SPDK_WARNLOG("poller %p still registered at thread exit\n", SPDK_WARNLOG("poller %s still registered at thread exit\n",
poller); poller->name);
} }
TAILQ_REMOVE(&thread->timed_pollers, poller, tailq); TAILQ_REMOVE(&thread->timed_pollers, poller, tailq);
free(poller); free(poller);
} }
TAILQ_FOREACH_SAFE(poller, &thread->paused_pollers, tailq, ptmp) { TAILQ_FOREACH_SAFE(poller, &thread->paused_pollers, tailq, ptmp) {
SPDK_WARNLOG("poller %p still registered at thread exit\n", poller); SPDK_WARNLOG("poller %s still registered at thread exit\n", poller->name);
TAILQ_REMOVE(&thread->paused_pollers, poller, tailq); TAILQ_REMOVE(&thread->paused_pollers, poller, tailq);
free(poller); free(poller);
} }
@ -332,23 +332,23 @@ spdk_thread_exit(struct spdk_thread *thread)
TAILQ_FOREACH(poller, &thread->active_pollers, tailq) { TAILQ_FOREACH(poller, &thread->active_pollers, tailq) {
if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) { if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) {
SPDK_ERRLOG("thread %s still has active poller %p\n", SPDK_ERRLOG("thread %s still has active poller %s\n",
thread->name, poller); thread->name, poller->name);
return -EBUSY; return -EBUSY;
} }
} }
TAILQ_FOREACH(poller, &thread->timed_pollers, tailq) { TAILQ_FOREACH(poller, &thread->timed_pollers, tailq) {
if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) { if (poller->state != SPDK_POLLER_STATE_UNREGISTERED) {
SPDK_ERRLOG("thread %s still has active timed poller %p\n", SPDK_ERRLOG("thread %s still has active timed poller %s\n",
thread->name, poller); thread->name, poller->name);
return -EBUSY; return -EBUSY;
} }
} }
TAILQ_FOREACH(poller, &thread->paused_pollers, tailq) { TAILQ_FOREACH(poller, &thread->paused_pollers, tailq) {
SPDK_ERRLOG("thread %s still has paused poller %p\n", SPDK_ERRLOG("thread %s still has paused poller %s\n",
thread->name, poller); thread->name, poller->name);
return -EBUSY; return -EBUSY;
} }
@ -566,7 +566,7 @@ spdk_thread_poll(struct spdk_thread *thread, uint32_t max_msgs, uint64_t now)
#ifdef DEBUG #ifdef DEBUG
if (poller_rc == -1) { if (poller_rc == -1) {
SPDK_DEBUGLOG(SPDK_LOG_THREAD, "Poller %p returned -1\n", poller); SPDK_DEBUGLOG(SPDK_LOG_THREAD, "Poller %s returned -1\n", poller->name);
} }
#endif #endif
@ -605,7 +605,7 @@ spdk_thread_poll(struct spdk_thread *thread, uint32_t max_msgs, uint64_t now)
#ifdef DEBUG #ifdef DEBUG
if (timer_rc == -1) { if (timer_rc == -1) {
SPDK_DEBUGLOG(SPDK_LOG_THREAD, "Timed poller %p returned -1\n", poller); SPDK_DEBUGLOG(SPDK_LOG_THREAD, "Timed poller %s returned -1\n", poller->name);
} }
#endif #endif
@ -817,10 +817,11 @@ spdk_thread_send_critical_msg(struct spdk_thread *thread, spdk_msg_fn fn)
return -EIO; return -EIO;
} }
struct spdk_poller * static struct spdk_poller *
spdk_poller_register(spdk_poller_fn fn, _spdk_poller_register(spdk_poller_fn fn,
void *arg, void *arg,
uint64_t period_microseconds) uint64_t period_microseconds,
const char *name)
{ {
struct spdk_thread *thread; struct spdk_thread *thread;
struct spdk_poller *poller; struct spdk_poller *poller;
@ -843,6 +844,12 @@ spdk_poller_register(spdk_poller_fn fn,
return NULL; return NULL;
} }
if (name) {
snprintf(poller->name, sizeof(poller->name), "%s", name);
} else {
snprintf(poller->name, sizeof(poller->name), "%p", fn);
}
poller->state = SPDK_POLLER_STATE_WAITING; poller->state = SPDK_POLLER_STATE_WAITING;
poller->fn = fn; poller->fn = fn;
poller->arg = arg; poller->arg = arg;
@ -863,6 +870,23 @@ spdk_poller_register(spdk_poller_fn fn,
return poller; return poller;
} }
struct spdk_poller *
spdk_poller_register(spdk_poller_fn fn,
void *arg,
uint64_t period_microseconds)
{
return _spdk_poller_register(fn, arg, period_microseconds, NULL);
}
struct spdk_poller *
spdk_poller_register_named(spdk_poller_fn fn,
void *arg,
uint64_t period_microseconds,
const char *name)
{
return _spdk_poller_register(fn, arg, period_microseconds, name);
}
void void
spdk_poller_unregister(struct spdk_poller **ppoller) spdk_poller_unregister(struct spdk_poller **ppoller)
{ {