1 From ac3447ab680ef5319717fc6b85a4c5b22e652e5e Mon Sep 17 00:00:00 2001
2 From: Chris Leech <cleech@redhat.com>
3 Date: Fri, 7 Dec 2012 17:01:42 -0800
4 Subject: iscsiadm, iscsid: newroot command to survive switch_root
6 When started from initramfs, iscsid needs to be able to chroot itself
7 to the runtime filesystem before the switch_root occurs. In the
8 initramfs "iscsiadm --newroot {root fs mount before switch}" should be
9 called before the switch_root.
11 Signed-off-by: Chris Leech <cleech@redhat.com>
13 usr/iscsiadm.c | 30 ++++++++++++++++++++++++++++++
14 usr/mgmt_ipc.c | 11 +++++++++++
15 usr/mgmt_ipc.h | 6 +++++-
16 3 files changed, 46 insertions(+), 1 deletion(-)
18 diff --git a/usr/iscsiadm.c b/usr/iscsiadm.c
19 index 8f9de05..323d0a8 100644
22 @@ -111,6 +111,7 @@ static struct option const long_options[] =
23 {"packetsize", required_argument, NULL, 'b'},
24 {"count", required_argument, NULL, 'c'},
25 {"interval", required_argument, NULL, 'i'},
26 + {"newroot", required_argument, NULL, 0},
29 static char *short_options = "RlDVhm:a:b:c:C:p:P:T:H:i:I:U:k:L:d:r:n:v:o:sSt:u";
30 @@ -131,6 +132,7 @@ iscsiadm -m session [ -hV ] [ -d debug_level ] [ -P printlevel] [ -r sessionid
31 iscsiadm -m iface [ -hV ] [ -d debug_level ] [ -P printlevel ] [ -I ifacename | -H hostno|MAC ] [ [ -o operation ] [ -n name ] [ -v value ] ] [ -C ping [ -a ip ] [ -b packetsize ] [ -c count ] [ -i interval ] ]\n\
32 iscsiadm -m fw [ -l ]\n\
33 iscsiadm -m host [ -P printlevel ] [ -H hostno|MAC ] [ -C chap [ -o operation ] [ -v chap_tbl_idx ] ]\n\
34 +iscsiadm --newroot switch_root_path\n\
35 iscsiadm -k priority\n");
38 @@ -251,6 +253,22 @@ static void kill_iscsid(int priority)
42 +static void do_newroot(char *newroot)
48 + memset(&req, 0, sizeof(req));
49 + req.command = MGMT_IPC_NEWROOT;
50 + strncpy(req.u.newroot.path, newroot, PATH_MAX);
51 + rc = iscsid_exec_req(&req, &rsp, 0);
53 + iscsi_err_print_msg(rc);
54 + log_error("Could not send NEWROOT command");
59 * TODO: we can display how the ifaces are related to node records.
60 * And we can add a scsi_host mode which would display how
61 @@ -2397,6 +2415,7 @@ main(int argc, char **argv)
63 char *ip = NULL, *name = NULL, *value = NULL;
64 char *targetname = NULL, *group_session_mgmt_mode = NULL;
65 + char *newroot = NULL;
66 int ch, longindex, mode=-1, port=-1, do_login=0, do_rescan=0;
67 int rc=0, sid=-1, op=OP_NOOP, type=-1, do_logout=0, do_stats=0;
68 int do_login_all=0, do_logout_all=0, info_level=-1, num_ifaces = 0;
69 @@ -2433,6 +2452,12 @@ main(int argc, char **argv)
70 while ((ch = getopt_long(argc, argv, short_options,
71 long_options, &longindex)) >= 0) {
74 + if (long_options[longindex].flag != 0)
76 + if (!strcmp(long_options[longindex].name, "newroot"))
80 killiscsid = atoi(optarg);
82 @@ -2579,6 +2604,11 @@ main(int argc, char **argv)
87 + do_newroot(newroot);
92 usage(ISCSI_ERR_INVAL);
94 diff --git a/usr/mgmt_ipc.c b/usr/mgmt_ipc.c
95 index 87bd346..5cb7143 100644
98 @@ -226,6 +226,16 @@ mgmt_ipc_immediate_stop(queue_task_t *qtask)
102 +mgmt_ipc_newroot(queue_task_t *qtask)
104 + char *newroot = qtask->req.u.newroot.path;
105 + if (chdir(newroot) || chroot(".") || chdir("/"))
107 + mgmt_ipc_write_rsp(qtask, ISCSI_SUCCESS);
108 + return ISCSI_SUCCESS;
112 mgmt_ipc_conn_remove(queue_task_t *qtask)
115 @@ -534,6 +544,7 @@ static mgmt_ipc_fn_t * mgmt_ipc_functions[__MGMT_IPC_MAX_COMMAND] = {
116 [MGMT_IPC_NOTIFY_DEL_NODE] = mgmt_ipc_notify_del_node,
117 [MGMT_IPC_NOTIFY_ADD_PORTAL] = mgmt_ipc_notify_add_portal,
118 [MGMT_IPC_NOTIFY_DEL_PORTAL] = mgmt_ipc_notify_del_portal,
119 +[MGMT_IPC_NEWROOT] = mgmt_ipc_newroot,
122 void mgmt_ipc_handle(int accept_fd)
123 diff --git a/usr/mgmt_ipc.h b/usr/mgmt_ipc.h
124 index 55972ed..102ffff 100644
129 #include "iscsi_if.h"
133 #define ISCSIADM_NAMESPACE "ISCSIADM_ABSTRACT_NAMESPACE"
134 #define PEERUSER_MAX 64
135 @@ -46,6 +47,7 @@ typedef enum iscsiadm_cmd {
136 MGMT_IPC_NOTIFY_DEL_NODE = 17,
137 MGMT_IPC_NOTIFY_ADD_PORTAL = 18,
138 MGMT_IPC_NOTIFY_DEL_PORTAL = 19,
139 + MGMT_IPC_NEWROOT = 20,
141 __MGMT_IPC_MAX_COMMAND
143 @@ -75,8 +77,10 @@ typedef struct iscsiadm_req {
145 /* TODO: make this variable len to support */
146 char value[IFNAMSIZ + 1];
149 + struct ipc_msg_newroot {
150 + char path[PATH_MAX + 1];