mirror of
git://sourceware.org/git/lvm2.git
synced 2024-12-21 13:34:40 +03:00
Speedup consequent activation calls
Stop calling fs_unlock() from lv_de/activate(). Start using internal lvm fs cookie for dm_tree. Stop directly calling dm_udev_wait() and dm_tree_set/get_cookie() from activate code - it's now called through fs_unlock() function. Add lvm_do_fs_unlock() Call fs_unlock() when unlocking vg where implicit unlock solves the problem also for cluster - thus no extra command for clustering environment is required - only lvm_do_fs_unlock() function is added to call lvm's fs_unlock() while holding lvm_lock mutex in clvmd. Add fs_unlock() also to set_lv() so the command waits until devices are ready for regular open (i.e. wiping its begining). Move fs_unlock() prototype to activation.h to keep fs.h private in lib/activate dir and not expose other functions from this header.
This commit is contained in:
parent
f6fdfd56e4
commit
937a21f0d2
@ -1,5 +1,6 @@
|
||||
Version 2.02.80 -
|
||||
====================================
|
||||
Speedup consequent activation calls by using internal cookie.
|
||||
Add internal lvm library cookie.
|
||||
Speedup command processing by caching resolved config tree.
|
||||
Pass config_tree to renamed function import_vg_from_config_tree().
|
||||
|
@ -214,6 +214,7 @@ static int lock_vg(struct local_client *client)
|
||||
if (lkid == 0)
|
||||
return EINVAL;
|
||||
|
||||
lvm_do_fs_unlock(); /* Wait for devices */
|
||||
status = sync_unlock(lockname, lkid);
|
||||
if (status)
|
||||
status = errno;
|
||||
|
@ -894,6 +894,13 @@ struct dm_hash_node *get_next_excl_lock(struct dm_hash_node *v, char **name)
|
||||
return v;
|
||||
}
|
||||
|
||||
void lvm_do_fs_unlock(void)
|
||||
{
|
||||
pthread_mutex_lock(&lvm_lock);
|
||||
fs_unlock();
|
||||
pthread_mutex_unlock(&lvm_lock);
|
||||
}
|
||||
|
||||
/* Called to initialise the LVM context of the daemon */
|
||||
int init_clvm(int using_gulm, char **argv)
|
||||
{
|
||||
|
@ -36,5 +36,6 @@ extern char *get_last_lvm_error(void);
|
||||
extern void do_lock_vg(unsigned char command, unsigned char lock_flags,
|
||||
char *resource);
|
||||
extern struct dm_hash_node *get_next_excl_lock(struct dm_hash_node *v, char **name);
|
||||
void lvm_do_fs_unlock(void);
|
||||
|
||||
#endif
|
||||
|
@ -1206,7 +1206,6 @@ int lv_deactivate(struct cmd_context *cmd, const char *lvid_s)
|
||||
memlock_inc(cmd);
|
||||
r = _lv_deactivate(lv);
|
||||
memlock_dec(cmd);
|
||||
fs_unlock();
|
||||
|
||||
if (!lv_info(cmd, lv, 0, &info, 1, 0) || info.exists)
|
||||
r = 0;
|
||||
@ -1305,7 +1304,6 @@ static int _lv_activate(struct cmd_context *cmd, const char *lvid_s,
|
||||
if (!(r = _lv_activate_lv(lv, 0)))
|
||||
stack;
|
||||
memlock_dec(cmd);
|
||||
fs_unlock();
|
||||
|
||||
if (r && !monitor_dev_for_events(cmd, lv, 0, 1))
|
||||
stack;
|
||||
|
@ -121,4 +121,9 @@ int pv_uses_vg(struct physical_volume *pv,
|
||||
*/
|
||||
int device_is_usable(struct device *dev);
|
||||
|
||||
/*
|
||||
* Declaration moved here from fs.h to keep header fs.h hidden
|
||||
*/
|
||||
void fs_unlock(void);
|
||||
|
||||
#endif
|
||||
|
@ -1622,7 +1622,6 @@ static int _clean_tree(struct dev_manager *dm, struct dm_tree_node *root, char *
|
||||
struct dm_tree_node *child;
|
||||
char *vgname, *lvname, *layer;
|
||||
const char *name, *uuid;
|
||||
int r;
|
||||
|
||||
while ((child = dm_tree_next_child(&handle, root, 0))) {
|
||||
if (!(name = dm_tree_node_get_name(child)))
|
||||
@ -1644,12 +1643,7 @@ static int _clean_tree(struct dev_manager *dm, struct dm_tree_node *root, char *
|
||||
if (non_toplevel_tree_dlid && !strcmp(non_toplevel_tree_dlid, uuid))
|
||||
continue;
|
||||
|
||||
dm_tree_set_cookie(root, 0);
|
||||
r = dm_tree_deactivate_children(root, uuid, strlen(uuid));
|
||||
if (!dm_udev_wait(dm_tree_get_cookie(root)))
|
||||
stack;
|
||||
|
||||
if (!r)
|
||||
if (!dm_tree_deactivate_children(root, uuid, strlen(uuid)))
|
||||
return_0;
|
||||
}
|
||||
|
||||
@ -1669,9 +1663,12 @@ static int _tree_action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
|
||||
if (!(root = dm_tree_find_node(dtree, 0, 0))) {
|
||||
log_error("Lost dependency tree root node");
|
||||
goto out;
|
||||
goto out_no_root;
|
||||
}
|
||||
|
||||
/* Restore fs cookie */
|
||||
dm_tree_set_cookie(root, fs_get_cookie());
|
||||
|
||||
if (!(dlid = build_dm_uuid(dm->mem, lv->lvid.s, origin_only ? "real" : NULL)))
|
||||
goto_out;
|
||||
|
||||
@ -1684,10 +1681,7 @@ static int _tree_action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
break;
|
||||
case DEACTIVATE:
|
||||
/* Deactivate LV and all devices it references that nothing else has open. */
|
||||
dm_tree_set_cookie(root, 0);
|
||||
r = dm_tree_deactivate_children(root, dlid, ID_LEN + sizeof(UUID_PREFIX) - 1);
|
||||
if (!dm_udev_wait(dm_tree_get_cookie(root)))
|
||||
stack;
|
||||
if (!r)
|
||||
goto_out;
|
||||
if (!_remove_lv_symlinks(dm, root))
|
||||
@ -1708,10 +1702,7 @@ static int _tree_action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
goto_out;
|
||||
|
||||
/* Preload any devices required before any suspensions */
|
||||
dm_tree_set_cookie(root, 0);
|
||||
r = dm_tree_preload_children(root, dlid, ID_LEN + sizeof(UUID_PREFIX) - 1);
|
||||
if (!dm_udev_wait(dm_tree_get_cookie(root)))
|
||||
stack;
|
||||
if (!r)
|
||||
goto_out;
|
||||
|
||||
@ -1719,10 +1710,7 @@ static int _tree_action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
dm->flush_required = 1;
|
||||
|
||||
if (action == ACTIVATE) {
|
||||
dm_tree_set_cookie(root, 0);
|
||||
r = dm_tree_activate_children(root, dlid, ID_LEN + sizeof(UUID_PREFIX) - 1);
|
||||
if (!dm_udev_wait(dm_tree_get_cookie(root)))
|
||||
stack;
|
||||
if (!r)
|
||||
goto_out;
|
||||
if (!_create_lv_symlinks(dm, root)) {
|
||||
@ -1740,6 +1728,9 @@ static int _tree_action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
r = 1;
|
||||
|
||||
out:
|
||||
/* Save fs cookie for udev settle, do not wait here */
|
||||
fs_set_cookie(dm_tree_get_cookie(root));
|
||||
out_no_root:
|
||||
dm_tree_free(dtree);
|
||||
|
||||
return r;
|
||||
|
@ -15,6 +15,7 @@
|
||||
|
||||
#include "lib.h"
|
||||
#include "fs.h"
|
||||
#include "activate.h"
|
||||
#include "toolcontext.h"
|
||||
#include "lvm-string.h"
|
||||
#include "lvm-file.h"
|
||||
|
@ -29,7 +29,7 @@ int fs_del_lv_byname(const char *dev_dir, const char *vg_name,
|
||||
const char *lv_name, int check_udev);
|
||||
int fs_rename_lv(struct logical_volume *lv, const char *dev,
|
||||
const char *old_vgname, const char *old_lvname);
|
||||
void fs_unlock(void);
|
||||
/* void fs_unlock(void); moved to activate.h */
|
||||
uint32_t fs_get_cookie(void);
|
||||
void fs_set_cookie(uint32_t cookie);
|
||||
|
||||
|
@ -215,6 +215,7 @@ static int _lock_file(const char *file, uint32_t flags)
|
||||
state = 'W';
|
||||
break;
|
||||
case LCK_UNLOCK:
|
||||
fs_unlock(); /* Wait until devices are available */
|
||||
return _release_lock(file, 1);
|
||||
default:
|
||||
log_error("Unrecognised lock type: %d", flags & LCK_TYPE_MASK);
|
||||
|
@ -3022,6 +3022,8 @@ int set_lv(struct cmd_context *cmd, struct logical_volume *lv,
|
||||
return 0;
|
||||
}
|
||||
|
||||
fs_unlock(); /* Wait until devices are available */
|
||||
|
||||
log_verbose("Clearing start of logical volume \"%s\"", lv->name);
|
||||
|
||||
if (!(dev = dev_cache_get(name, NULL))) {
|
||||
|
Loading…
Reference in New Issue
Block a user