aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--util-linux/mdev.c154
1 files changed, 82 insertions, 72 deletions
diff --git a/util-linux/mdev.c b/util-linux/mdev.c
index 63b55536a..8205a260a 100644
--- a/util-linux/mdev.c
+++ b/util-linux/mdev.c
@@ -1047,6 +1047,86 @@ static void signal_mdevs(unsigned my_pid)
1047 } 1047 }
1048} 1048}
1049 1049
1050static void process_action(char *temp, unsigned my_pid)
1051{
1052 char *fw;
1053 char *seq;
1054 char *action;
1055 char *env_devname;
1056 char *env_devpath;
1057 unsigned seqnum = seqnum; /* for compiler */
1058 int seq_fd;
1059 smalluint op;
1060
1061 /* Hotplug:
1062 * env ACTION=... DEVPATH=... SUBSYSTEM=... [SEQNUM=...] mdev
1063 * ACTION can be "add", "remove", "change"
1064 * DEVPATH is like "/block/sda" or "/class/input/mice"
1065 */
1066 env_devname = getenv("DEVNAME"); /* can be NULL */
1067 G.subsystem = getenv("SUBSYSTEM");
1068 action = getenv("ACTION");
1069 env_devpath = getenv("DEVPATH");
1070 if (!action || !env_devpath /*|| !G.subsystem*/)
1071 bb_show_usage();
1072 fw = getenv("FIRMWARE");
1073 seq = getenv("SEQNUM");
1074 op = index_in_strings(keywords, action);
1075
1076 open_mdev_log(seq, my_pid);
1077
1078 seq_fd = -1;
1079 if (seq) {
1080 seqnum = atoll(seq);
1081 seq_fd = wait_for_seqfile(seqnum);
1082 }
1083
1084 dbg1("%s "
1085 "ACTION:%s SEQNUM:%s SUBSYSTEM:%s DEVNAME:%s DEVPATH:%s"
1086 "%s%s",
1087 curtime(),
1088 action, seq, G.subsystem, env_devname, env_devpath,
1089 fw ? " FW:" : "", fw ? fw : ""
1090 );
1091
1092 snprintf(temp, PATH_MAX, "/sys%s", env_devpath);
1093 if (op == OP_remove) {
1094 /* Ignoring "remove firmware". It was reported
1095 * to happen and to cause erroneous deletion
1096 * of device nodes. */
1097 if (!fw)
1098 make_device(env_devname, temp, op);
1099 }
1100 else {
1101 make_device(env_devname, temp, op);
1102 if (ENABLE_FEATURE_MDEV_LOAD_FIRMWARE) {
1103 if (op == OP_add && fw)
1104 load_firmware(fw, temp);
1105 }
1106 }
1107
1108 if (seq_fd >= 0) {
1109 xwrite_str(seq_fd, utoa(seqnum + 1));
1110 signal_mdevs(my_pid);
1111 }
1112}
1113
1114static void initial_scan(char *temp)
1115{
1116 struct stat st;
1117
1118 xstat("/", &st);
1119 G.root_major = major(st.st_dev);
1120 G.root_minor = minor(st.st_dev);
1121
1122 putenv((char*)"ACTION=add");
1123
1124 /* Create all devices from /sys/dev hierarchy */
1125 recursive_action("/sys/dev",
1126 ACTION_RECURSE | ACTION_FOLLOWLINKS,
1127 fileAction, dirAction, temp, 0);
1128}
1129
1050int mdev_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE; 1130int mdev_main(int argc, char **argv) MAIN_EXTERNALLY_VISIBLE;
1051int mdev_main(int argc UNUSED_PARAM, char **argv) 1131int mdev_main(int argc UNUSED_PARAM, char **argv)
1052{ 1132{
@@ -1071,86 +1151,16 @@ int mdev_main(int argc UNUSED_PARAM, char **argv)
1071 /* 1151 /*
1072 * Scan: mdev -s 1152 * Scan: mdev -s
1073 */ 1153 */
1074 struct stat st;
1075
1076#if ENABLE_FEATURE_MDEV_CONF 1154#if ENABLE_FEATURE_MDEV_CONF
1077 /* Same as xrealloc_vector(NULL, 4, 0): */ 1155 /* Same as xrealloc_vector(NULL, 4, 0): */
1078 G.rule_vec = xzalloc((1 << 4) * sizeof(*G.rule_vec)); 1156 G.rule_vec = xzalloc((1 << 4) * sizeof(*G.rule_vec));
1079#endif 1157#endif
1080 xstat("/", &st);
1081 G.root_major = major(st.st_dev);
1082 G.root_minor = minor(st.st_dev);
1083 1158
1084 putenv((char*)"ACTION=add"); 1159 initial_scan(temp);
1085
1086 /* Create all devices from /sys/dev hierarchy */
1087 recursive_action("/sys/dev",
1088 ACTION_RECURSE | ACTION_FOLLOWLINKS,
1089 fileAction, dirAction, temp, 0);
1090 } else { 1160 } else {
1091 char *fw; 1161 process_action(temp, getpid());
1092 char *seq;
1093 char *action;
1094 char *env_devname;
1095 char *env_devpath;
1096 unsigned my_pid;
1097 unsigned seqnum = seqnum; /* for compiler */
1098 int seq_fd;
1099 smalluint op;
1100
1101 /* Hotplug:
1102 * env ACTION=... DEVPATH=... SUBSYSTEM=... [SEQNUM=...] mdev
1103 * ACTION can be "add", "remove", "change"
1104 * DEVPATH is like "/block/sda" or "/class/input/mice"
1105 */
1106 env_devname = getenv("DEVNAME"); /* can be NULL */
1107 G.subsystem = getenv("SUBSYSTEM");
1108 action = getenv("ACTION");
1109 env_devpath = getenv("DEVPATH");
1110 if (!action || !env_devpath /*|| !G.subsystem*/)
1111 bb_show_usage();
1112 fw = getenv("FIRMWARE");
1113 seq = getenv("SEQNUM");
1114 op = index_in_strings(keywords, action);
1115
1116 my_pid = getpid();
1117 open_mdev_log(seq, my_pid);
1118
1119 seq_fd = -1;
1120 if (seq) {
1121 seqnum = atoll(seq);
1122 seq_fd = wait_for_seqfile(seqnum);
1123 }
1124
1125 dbg1("%s "
1126 "ACTION:%s SUBSYSTEM:%s DEVNAME:%s DEVPATH:%s"
1127 "%s%s",
1128 curtime(),
1129 action, G.subsystem, env_devname, env_devpath,
1130 fw ? " FW:" : "", fw ? fw : ""
1131 );
1132
1133 snprintf(temp, PATH_MAX, "/sys%s", env_devpath);
1134 if (op == OP_remove) {
1135 /* Ignoring "remove firmware". It was reported
1136 * to happen and to cause erroneous deletion
1137 * of device nodes. */
1138 if (!fw)
1139 make_device(env_devname, temp, op);
1140 }
1141 else {
1142 make_device(env_devname, temp, op);
1143 if (ENABLE_FEATURE_MDEV_LOAD_FIRMWARE) {
1144 if (op == OP_add && fw)
1145 load_firmware(fw, temp);
1146 }
1147 }
1148 1162
1149 dbg1("%s exiting", curtime()); 1163 dbg1("%s exiting", curtime());
1150 if (seq_fd >= 0) {
1151 xwrite_str(seq_fd, utoa(seqnum + 1));
1152 signal_mdevs(my_pid);
1153 }
1154 } 1164 }
1155 1165
1156 if (ENABLE_FEATURE_CLEAN_UP) 1166 if (ENABLE_FEATURE_CLEAN_UP)