diff options
| author | haad <haad@NetBSD.org> | 2008-12-21 00:59:39 +0000 |
|---|---|---|
| committer | haad <haad@NetBSD.org> | 2008-12-21 00:59:39 +0000 |
| commit | cca8fb31f911820f397b9d96a25bdf445dcaa28b (patch) | |
| tree | 2a241827f48fd6b8d163de6d5f6d4c7bd4388c30 /sys/dev/dm/dm_target_snapshot.c | |
| parent | 38805eb14c9a24414515ec80d28fc16ff67c9c41 (diff) | |
Add support for loading dm targets as separate modules. All targets except
linear can be loaded as module. Module is not loaded when there is target
with similar name already. Zero and error targets aresimple examples how
can be all future targets written to support dynamic loading. Target can't
be unloaded until there is at least one user.
Diffstat (limited to 'sys/dev/dm/dm_target_snapshot.c')
| -rw-r--r-- | sys/dev/dm/dm_target_snapshot.c | 80 |
1 files changed, 79 insertions, 1 deletions
diff --git a/sys/dev/dm/dm_target_snapshot.c b/sys/dev/dm/dm_target_snapshot.c index 725d525ca63..f363f148db9 100644 --- a/sys/dev/dm/dm_target_snapshot.c +++ b/sys/dev/dm/dm_target_snapshot.c @@ -1,4 +1,4 @@ -/* $NetBSD: dm_target_snapshot.c,v 1.3 2008/12/19 16:30:41 haad Exp $ */ +/* $NetBSD: dm_target_snapshot.c,v 1.4 2008/12/21 00:59:39 haad Exp $ */ /* * Copyright (c) 2008 The NetBSD Foundation, Inc. @@ -72,6 +72,84 @@ #include "dm.h" +#ifdef DM_TARGET_MODULE +/* + * Every target can be compiled directly to dm driver or as a + * separate module this part of target is used for loading targets + * to dm driver. + * Target can be unloaded from kernel only if there are no users of + * it e.g. there are no devices which uses that target. + */ +#include <sys/kernel.h> +#include <sys/module.h> + +MODULE(MODULE_CLASS_MISC, dm_target_snapshot, NULL); + +static int +dm_target_snapshot_modcmd(modcmd_t cmd, void *arg) +{ + dm_target_t *dmt, *dmt1; + int r; + dmt = NULL; + + switch (cmd) { + case MODULE_CMD_INIT: + if (((dmt = dm_target_lookup("snapshot")) != NULL) || + (((dmt = dm_target_lookup("snapshot-origin")) != NULL))) + return EEXIST; + + dmt = dm_target_alloc("snapshot"); + dmt1 = dm_target_alloc("snapshot-origin"); + + dmt->version[0] = 1; + dmt->version[1] = 0; + dmt->version[2] = 5; + strlcpy(dmt->name, "snapshot", DM_MAX_TYPE_NAME); + dmt->init = &dm_target_snapshot_init; + dmt->status = &dm_target_snapshot_status; + dmt->strategy = &dm_target_snapshot_strategy; + dmt->deps = &dm_target_snapshot_deps; + dmt->destroy = &dm_target_snapshot_destroy; + dmt->upcall = &dm_target_snapshot_upcall; + + r = dm_target_insert(dmt); + + dmt1->version[0] = 1; + dmt1->version[1] = 0; + dmt1->version[2] = 5; + strlcpy(dmt1->name, "snapshot-origin", DM_MAX_TYPE_NAME); + dmt1->init = &dm_target_snapshot_orig_init; + dmt1->status = &dm_target_snapshot_orig_status; + dmt1->strategy = &dm_target_snapshot_orig_strategy; + dmt1->deps = &dm_target_snapshot_orig_deps; + dmt1->destroy = &dm_target_snapshot_orig_destroy; + dmt1->upcall = &dm_target_snapshot_orig_upcall; + + r = dm_target_insert(dmt1); + break; + + case MODULE_CMD_FINI: + /* + * Try to remove snapshot target if it works remove snap-origin + * it is not possible to remove snapshot and do not remove + * snap-origin because they are used together. + */ + if ((r = dm_target_rem("snapshot")) == 0) + r = dm_target_rem("snapshot-origin"); + break; + + case MODULE_CMD_STAT: + return ENOTTY; + + default: + return ENOTTY; + } + + return r; +} + +#endif + /* * Init function called from dm_table_load_ioctl. * argv: /dev/mapper/my_data_org /dev/mapper/tsc_cow_dev p 64 |
