Skip to content

Commit bd6957f

Browse files
romanmichalvasko
authored andcommitted
session client REFACTOR monitoring use clocklock
1 parent 28628dc commit bd6957f

2 files changed

Lines changed: 85 additions & 13 deletions

File tree

src/session_client.c

Lines changed: 80 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -3272,15 +3272,57 @@ nc_client_monitoring_get_session_fd(struct nc_session *session)
32723272
return fd;
32733273
}
32743274

3275+
/**
3276+
* @brief Lock the client monitoring data.
3277+
*
3278+
* @param[in] timeout Timeout in msec to use.
3279+
*
3280+
* @return 1 on success;
3281+
* @return 0 on timeout;
3282+
* @return -1 on error.
3283+
*/
3284+
static int
3285+
nc_client_monitoring_lock(int timeout)
3286+
{
3287+
int r;
3288+
struct timespec ts;
3289+
3290+
if (timeout > 0) {
3291+
nc_timeouttime_get(&ts, timeout);
3292+
r = pthread_mutex_clocklock(&client_opts.monitoring_thread_data.lock, COMPAT_CLOCK_ID, &ts);
3293+
} else if (!timeout) {
3294+
r = pthread_mutex_trylock(&client_opts.monitoring_thread_data.lock);
3295+
} else {
3296+
r = pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3297+
}
3298+
3299+
if (r) {
3300+
ERR(NULL, "Failed to lock the client monitoring data lock (%s).", strerror(r));
3301+
3302+
if ((r == EBUSY) || (r == ETIMEDOUT)) {
3303+
/* timeout */
3304+
return 0;
3305+
}
3306+
3307+
/* error */
3308+
return -1;
3309+
}
3310+
3311+
return 1;
3312+
}
3313+
32753314
int
32763315
nc_client_monitoring_session_start(struct nc_session *session)
32773316
{
3278-
int ret = 0, fd;
3317+
int ret = 0, fd, r;
32793318
struct nc_client_monitoring_thread_arg *mtarg;
32803319
void *tmp, *tmp2;
32813320

32823321
/* LOCK */
3283-
pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3322+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3323+
if (r < 1) {
3324+
return 1;
3325+
}
32843326

32853327
/* check if the monitoring thread is running */
32863328
if (!client_opts.monitoring_thread_data.thread_running) {
@@ -3314,19 +3356,22 @@ nc_client_monitoring_session_start(struct nc_session *session)
33143356

33153357
cleanup:
33163358
/* UNLOCK */
3317-
pthread_mutex_unlock(&mtarg->lock);
3359+
pthread_mutex_unlock(&client_opts.monitoring_thread_data.lock);
33183360
return ret;
33193361
}
33203362

33213363
void
33223364
nc_client_monitoring_session_stop(struct nc_session *session, int lock)
33233365
{
3324-
int i;
3366+
int i, r;
33253367
struct nc_client_monitoring_thread_arg *mtarg;
33263368

33273369
if (lock) {
33283370
/* LOCK */
3329-
pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3371+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3372+
if (r < 1) {
3373+
return;
3374+
}
33303375
}
33313376

33323377
mtarg = &client_opts.monitoring_thread_data;
@@ -3379,7 +3424,7 @@ nc_client_monitoring_session_stop(struct nc_session *session, int lock)
33793424
static void *
33803425
nc_client_monitoring_thread(void *arg)
33813426
{
3382-
int r;
3427+
int r, locked = 0;
33833428
struct nc_client_monitoring_thread_arg *mtarg;
33843429
nfds_t i;
33853430
struct nc_session *session = NULL;
@@ -3388,7 +3433,11 @@ nc_client_monitoring_thread(void *arg)
33883433
nc_client_set_thread_context(arg);
33893434

33903435
/* LOCK */
3391-
pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3436+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3437+
if (r < 1) {
3438+
goto cleanup;
3439+
}
3440+
locked = 1;
33923441

33933442
mtarg = &client_opts.monitoring_thread_data;
33943443

@@ -3425,6 +3474,7 @@ nc_client_monitoring_thread(void *arg)
34253474
next_iter:
34263475
/* UNLOCK */
34273476
pthread_mutex_unlock(&mtarg->lock);
3477+
locked = 0;
34283478

34293479
/* if an event occurred, call the callback */
34303480
if (session) {
@@ -3435,12 +3485,18 @@ nc_client_monitoring_thread(void *arg)
34353485
usleep(NC_CLIENT_MONITORING_BACKOFF * 1000);
34363486

34373487
/* LOCK */
3438-
pthread_mutex_lock(&mtarg->lock);
3488+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3489+
if (r < 1) {
3490+
goto cleanup;
3491+
}
3492+
locked = 1;
34393493
}
34403494

34413495
cleanup:
3442-
/* UNLOCK */
3443-
pthread_mutex_unlock(&mtarg->lock);
3496+
if (locked) {
3497+
/* UNLOCK */
3498+
pthread_mutex_unlock(&mtarg->lock);
3499+
}
34443500
VRB(NULL, "Client monitoring thread exit.");
34453501
return NULL;
34463502
}
@@ -3454,7 +3510,11 @@ nc_client_monitoring_thread_start(nc_client_monitoring_clb monitoring_clb, void
34543510
NC_CHECK_ARG_RET(NULL, monitoring_clb, 1);
34553511

34563512
/* LOCK */
3457-
pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3513+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3514+
if (r < 1) {
3515+
return 1;
3516+
}
3517+
34583518
if (client_opts.monitoring_thread_data.thread_running) {
34593519
ERR(NULL, "Client monitoring thread is already running.");
34603520
ret = 1;
@@ -3497,7 +3557,11 @@ nc_client_monitoring_thread_stop(void)
34973557
struct nc_client_monitoring_thread_arg *mtarg;
34983558

34993559
/* LOCK */
3500-
pthread_mutex_lock(&client_opts.monitoring_thread_data.lock);
3560+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3561+
if (r < 1) {
3562+
return;
3563+
}
3564+
35013565
if (!client_opts.monitoring_thread_data.thread_running) {
35023566
ERR(NULL, "Client monitoring thread is not running.");
35033567

@@ -3525,7 +3589,10 @@ nc_client_monitoring_thread_stop(void)
35253589
}
35263590

35273591
/* LOCK */
3528-
pthread_mutex_lock(&mtarg->lock);
3592+
r = nc_client_monitoring_lock(NC_CLIENT_MONITORING_LOCK_TIMEOUT);
3593+
if (r < 1) {
3594+
return;
3595+
}
35293596

35303597
if (mtarg->clb_free_data) {
35313598
mtarg->clb_free_data(mtarg->clb_data);

src/session_p.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -678,6 +678,11 @@ struct nc_server_opts {
678678
*/
679679
#define NC_CLIENT_MONITORING_BACKOFF 200
680680

681+
/**
682+
* Timeout in msec for acquiring a lock of a client monitoring thread.
683+
*/
684+
#define NC_CLIENT_MONITORING_LOCK_TIMEOUT 500
685+
681686
/**
682687
* @brief Type of the session
683688
*/

0 commit comments

Comments
 (0)