Commit 7d5aca9ee6e92e3a746b9c7b59d31489f68a66f0
1 parent
72da4208
qemu: dynamic drive/drive_opt index allocation (Marcelo Tosatti)
Dynamically allocate drive options and drive table index, to reuse indexes when devices are removed. Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com> Signed-off-by: Anthony Liguori <aliguori@us.ibm.com> git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@6594 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
2 changed files
with
44 additions
and
11 deletions
sysemu.h
vl.c
... | ... | @@ -246,6 +246,7 @@ static int nb_drives_opt; |
246 | 246 | static struct drive_opt { |
247 | 247 | const char *file; |
248 | 248 | char opt[1024]; |
249 | + int used; | |
249 | 250 | } drives_opt[MAX_DRIVES]; |
250 | 251 | |
251 | 252 | static CPUState *cur_cpu; |
... | ... | @@ -2135,22 +2136,50 @@ static int bt_parse(const char *opt) |
2135 | 2136 | #define MTD_ALIAS "if=mtd" |
2136 | 2137 | #define SD_ALIAS "index=0,if=sd" |
2137 | 2138 | |
2139 | +static int drive_opt_get_free_idx(void) | |
2140 | +{ | |
2141 | + int index; | |
2142 | + | |
2143 | + for (index = 0; index < MAX_DRIVES; index++) | |
2144 | + if (!drives_opt[index].used) { | |
2145 | + drives_opt[index].used = 1; | |
2146 | + return index; | |
2147 | + } | |
2148 | + | |
2149 | + return -1; | |
2150 | +} | |
2151 | + | |
2152 | +static int drive_get_free_idx(void) | |
2153 | +{ | |
2154 | + int index; | |
2155 | + | |
2156 | + for (index = 0; index < MAX_DRIVES; index++) | |
2157 | + if (!drives_table[index].used) { | |
2158 | + drives_table[index].used = 1; | |
2159 | + return index; | |
2160 | + } | |
2161 | + | |
2162 | + return -1; | |
2163 | +} | |
2164 | + | |
2138 | 2165 | static int drive_add(const char *file, const char *fmt, ...) |
2139 | 2166 | { |
2140 | 2167 | va_list ap; |
2168 | + int index = drive_opt_get_free_idx(); | |
2141 | 2169 | |
2142 | - if (nb_drives_opt >= MAX_DRIVES) { | |
2170 | + if (nb_drives_opt >= MAX_DRIVES || index == -1) { | |
2143 | 2171 | fprintf(stderr, "qemu: too many drives\n"); |
2144 | 2172 | exit(1); |
2145 | 2173 | } |
2146 | 2174 | |
2147 | - drives_opt[nb_drives_opt].file = file; | |
2175 | + drives_opt[index].file = file; | |
2148 | 2176 | va_start(ap, fmt); |
2149 | - vsnprintf(drives_opt[nb_drives_opt].opt, | |
2177 | + vsnprintf(drives_opt[index].opt, | |
2150 | 2178 | sizeof(drives_opt[0].opt), fmt, ap); |
2151 | 2179 | va_end(ap); |
2152 | 2180 | |
2153 | - return nb_drives_opt++; | |
2181 | + nb_drives_opt++; | |
2182 | + return index; | |
2154 | 2183 | } |
2155 | 2184 | |
2156 | 2185 | int drive_get_index(BlockInterfaceType type, int bus, int unit) |
... | ... | @@ -2159,10 +2188,11 @@ int drive_get_index(BlockInterfaceType type, int bus, int unit) |
2159 | 2188 | |
2160 | 2189 | /* seek interface, bus and unit */ |
2161 | 2190 | |
2162 | - for (index = 0; index < nb_drives; index++) | |
2191 | + for (index = 0; index < MAX_DRIVES; index++) | |
2163 | 2192 | if (drives_table[index].type == type && |
2164 | 2193 | drives_table[index].bus == bus && |
2165 | - drives_table[index].unit == unit) | |
2194 | + drives_table[index].unit == unit && | |
2195 | + drives_table[index].used) | |
2166 | 2196 | return index; |
2167 | 2197 | |
2168 | 2198 | return -1; |
... | ... | @@ -2227,6 +2257,7 @@ static int drive_init(struct drive_opt *arg, int snapshot, |
2227 | 2257 | int index; |
2228 | 2258 | int cache; |
2229 | 2259 | int bdrv_flags, onerror; |
2260 | + int drives_table_idx; | |
2230 | 2261 | char *str = arg->opt; |
2231 | 2262 | static const char * const params[] = { "bus", "unit", "if", "index", |
2232 | 2263 | "cyls", "heads", "secs", "trans", |
... | ... | @@ -2501,11 +2532,12 @@ static int drive_init(struct drive_opt *arg, int snapshot, |
2501 | 2532 | snprintf(buf, sizeof(buf), "%s%s%i", |
2502 | 2533 | devname, mediastr, unit_id); |
2503 | 2534 | bdrv = bdrv_new(buf); |
2504 | - drives_table[nb_drives].bdrv = bdrv; | |
2505 | - drives_table[nb_drives].type = type; | |
2506 | - drives_table[nb_drives].bus = bus_id; | |
2507 | - drives_table[nb_drives].unit = unit_id; | |
2508 | - drives_table[nb_drives].onerror = onerror; | |
2535 | + drives_table_idx = drive_get_free_idx(); | |
2536 | + drives_table[drives_table_idx].bdrv = bdrv; | |
2537 | + drives_table[drives_table_idx].type = type; | |
2538 | + drives_table[drives_table_idx].bus = bus_id; | |
2539 | + drives_table[drives_table_idx].unit = unit_id; | |
2540 | + drives_table[drives_table_idx].onerror = onerror; | |
2509 | 2541 | strncpy(drives_table[nb_drives].serial, serial, sizeof(serial)); |
2510 | 2542 | nb_drives++; |
2511 | 2543 | ... | ... |