1
0
mirror of git://sourceware.org/git/lvm2.git synced 2024-10-27 10:25:13 +03:00

Fix another bug in memlock handling, this time the "global" dmeventd memlock

was preventing device scans in lvconvert --repair running from inside dmeventd.
This commit is contained in:
Petr Rockai 2009-11-19 01:11:57 +00:00
parent c85222c461
commit 4514bdcfa2
3 changed files with 50 additions and 8 deletions

View File

@ -53,6 +53,7 @@ static size_t _size_malloc = 2000000;
static void *_malloc_mem = NULL;
static int _memlock_count = 0;
static int _memlock_count_daemon = 0;
static int _priority;
static int _default_priority;
@ -123,22 +124,61 @@ static void _unlock_mem(void)
strerror(errno));
}
static void _lock_mem_if_needed(void) {
if ((_memlock_count + _memlock_count_daemon) == 1)
_lock_mem();
}
static void _unlock_mem_if_possible(void) {
if ((_memlock_count + _memlock_count_daemon) == 0)
_unlock_mem();
}
void memlock_inc(void)
{
if (!_memlock_count++)
_lock_mem();
++_memlock_count;
_lock_mem_if_needed();
log_debug("memlock_count inc to %d", _memlock_count);
}
void memlock_dec(void)
{
if (_memlock_count && (!--_memlock_count))
_unlock_mem();
log_debug("memlock_count dec to %d", _memlock_count);
if (_memlock_count < 0)
if (!_memlock_count)
log_error("Internal error: _memlock_count has dropped below 0.");
--_memlock_count;
_unlock_mem_if_possible();
log_debug("memlock_count dec to %d", _memlock_count);
}
/*
* The memlock_*_daemon functions will force the mlockall() call that we need
* to stay in memory, but they will have no effect on device scans (unlike
* normal memlock_inc and memlock_dec). Memory is kept locked as long as either
* of memlock or memlock_daemon is in effect.
*/
void memlock_inc_daemon(void)
{
++_memlock_count_daemon;
_lock_mem_if_needed();
log_debug("memlock_count_daemon inc to %d", _memlock_count_daemon);
}
void memlock_dec_daemon(void)
{
if (!_memlock_count_daemon)
log_error("Internal error: _memlock_count_daemon has dropped below 0.");
--_memlock_count_daemon;
_unlock_mem_if_possible();
log_debug("memlock_count_daemon dec to %d", _memlock_count_daemon);
}
/*
* This disregards the daemon (dmeventd) locks, since we use memlock() to check
* whether it is safe to run a device scan, which would normally coincide with
* !memlock() -- but the daemon global memory lock breaks this assumption, so
* we do not take those into account here.
*/
int memlock(void)
{
return _memlock_count;

View File

@ -20,6 +20,8 @@ struct cmd_context;
void memlock_inc(void);
void memlock_dec(void);
void memlock_inc_daemon(void);
void memlock_dec_daemon(void);
int memlock(void);
void memlock_init(struct cmd_context *cmd);

View File

@ -82,9 +82,9 @@ int lvm2_run(void *handle, const char *cmdline)
/* FIXME Temporary - move to libdevmapper */
ret = ECMD_PROCESSED;
if (!strcmp(cmdline, "_memlock_inc"))
memlock_inc();
memlock_inc_daemon();
else if (!strcmp(cmdline, "_memlock_dec"))
memlock_dec();
memlock_dec_daemon();
else
ret = lvm_run_command(cmd, argc, argv);