[PATCH] Finding spare devices for grow - rework

[PATCH] Finding spare devices for grow - rework

am 13.12.2010 13:29:03 von krzysztof.wojcik

This patch introduces new method of finding spare devices
for grow (OnLine Capacity Expansion) operation.
The patch reuses code and procedures delivered
by the Array Auto Rebuild functionality hence it reduce
code redundancy.
The patch also introduces spare drive size verification
(missing in early implementation)

Signed-off-by: Krzysztof Wojcik
---
super-intel.c | 142 +++++++++++++++++++++++------------------------
sysfs.c | 174 ---------------------------------------------------------
2 files changed, 70 insertions(+), 246 deletions(-)

diff --git a/super-intel.c b/super-intel.c
index 626ecb6..c8d6382 100644
--- a/super-intel.c
+++ b/super-intel.c
@@ -7352,77 +7352,72 @@ exit_imsm_reshape_is_allowed_on_container:
return ret_val;
}

-struct mdinfo *get_spares_imsm(int devnum)
+/* Function: get_spares_for_grow
+ * Description: Allocates memory and creates list of spare devices
+ * avaliable in containter. Checks if spare drive size is acceptable.
+ * Parameters: Pointer to the supertype structure
+ * Returns: Pointer to the list of spare devices (mdinfo structure) on sucess,
+ * NULL if fail
+ */
+struct mdinfo *get_spares_for_grow(struct supertype *st)
{
+ int err;
+ char buf[PATH_MAX];
int fd = -1;
- struct mdinfo *info = NULL;
- struct mdinfo *ret_val = NULL;
- int cont_fd = -1;
- struct supertype *st = NULL;
- int find_result;
- struct intel_super *super = NULL;
-
- dprintf("imsm: get_spares_imsm for device: %i.\n", devnum);
+ dev_t dev = 0;
+ struct mdinfo *disks, *d, *ds;
+ struct mdinfo *spares = NULL;
+ unsigned long long min_size = min_acceptable_spare_size_imsm(st);

- cont_fd = open_dev(devnum);
- if (cont_fd < 0) {
- dprintf("imsm: ERROR: Cannot open container.\n");
- goto abort;
- }
+ sprintf(buf, "/dev/md%i", st->container_dev);
+ fd = open(buf, O_RDONLY);

- /* get first volume */
- st = super_by_fd(cont_fd, NULL);
- if (st == NULL) {
- dprintf("imsm: ERROR: Cannot load container information.\n");
- goto abort;
- }
- find_result = imsm_find_array_minor_by_subdev(0, devnum, &devnum);
- if (find_result < 0) {
- dprintf("imsm: ERROR: Cannot find array.\n");
- goto abort;
- }
- fd = open_dev(devnum);
- if (fd < 0) {
- dprintf("imsm: ERROR: Cannot open device.\n");
- goto abort;
- }
- st->ss->load_super(st, cont_fd, NULL);
- if (st->sb == NULL) {
- dprintf("imsm: ERROR: Cannot load array information.\n");
- goto abort;
- }
- info = sysfs_read(fd,
- 0,
- GET_LEVEL | GET_VERSION | GET_DEVS | GET_STATE);
- if (info == NULL) {
- dprintf("imsm: Cannot get device info.\n");
- goto abort;
- }
- super = st->sb;
- super->current_vol = 0;
- st->ss->getinfo_super(st, info, NULL);
- ret_val = sysfs_get_unused_spares(cont_fd, fd);
- if (ret_val == NULL) {
- dprintf("imsm: ERROR: Cannot get spare devices.\n");
- goto abort;
- }
- if (ret_val->array.spare_disks == 0) {
- dprintf("imsm: ERROR: No available spares.\n");
- free(ret_val);
- ret_val = NULL;
- goto abort;
- }
+ err = load_container_imsm(st, fd, NULL);
+ close(fd);
+ if (err)
+ return NULL;

-abort:
- if (st)
- st->ss->free_super(st);
- sysfs_free(info);
- if (fd > -1)
- close(fd);
- if (cont_fd > -1)
- close(cont_fd);
+ /* get list of alldisks in container */
+ disks = getinfo_super_disks_imsm(st);

- return ret_val;
+ if (!disks)
+ return NULL;
+ /* find spare devices on the list */
+ for (d = disks->devs ; d ; d = d->next) {
+ int found = 0;
+ if (d->disk.state == 0) {
+ /* check if size is acceptable */
+ unsigned long long dev_size;
+ dev = makedev(d->disk.major,d->disk.minor);
+ if (min_size &&
+ dev_size_from_id(dev, &dev_size) &&
+ dev_size >= min_size) {
+ dev = 0;
+ found = 1;
+ }
+ }
+ if (found) {
+ /* append spare to the list */
+ ds = malloc(sizeof(struct mdinfo));
+ if (ds == NULL)
+ goto exit_get_spares_for_grow;
+ memcpy(ds, d, sizeof(struct mdinfo));
+ ds->next = spares;
+ spares = ds;
+ disks->array.spare_disks++;
+ }
+ }
+exit_get_spares_for_grow:
+ /* free memory */
+ d = disks->devs;
+ while (d) {
+ struct mdinfo *tmp;
+ tmp = d->next;
+ free(d);
+ d = tmp;
+ }
+ disks->devs = spares;
+ return disks;
}

/*********************************************************** ******************
@@ -7707,7 +7702,7 @@ struct imsm_update_reshape *imsm_create_metadata_update_for_reshape(

/* now get spare disks list
*/
- spares = get_spares_imsm(st->container_dev);
+ spares = get_spares_for_grow(st);

if (spares == NULL) {
dprintf("imsm: ERROR: Cannot get spare devices.\n");
@@ -8133,6 +8128,7 @@ static int imsm_reshape_array_manage_new_slots(struct intel_super *super,
int fd2;
int rv;

+ /* skip not configured disks */
if (dl->index < 0)
continue;

@@ -8189,10 +8185,11 @@ struct mdinfo *imsm_grow_array(struct active_array *a)
int inst = a->info.container_member;
struct imsm_dev *dev = get_imsm_dev(super, inst);
struct imsm_map *map = get_imsm_map(dev, 0);
+ struct imsm_map *map_2 = get_imsm_map(dev, 1);
struct mdinfo *di;
struct dl *dl;
int i;
- int prev_raid_disks = a->info.array.raid_disks;
+ int prev_raid_disks = map_2->num_members;
int new_raid_disks = prev_raid_disks + a->reshape_delta_disks;
struct mdinfo *vol = NULL;
int fd;
@@ -8221,12 +8218,13 @@ struct mdinfo *imsm_grow_array(struct active_array *a)
for (i = prev_raid_disks; i < new_raid_disks; i++) {
/* OK, this device can be added. Try to add.
*/
- dl = imsm_add_spare(super, i, a, 0, rv);
- if (!dl)
- continue;
+ dl = super->disks;
+ while (dl) {
+ if (dl->index == i)
+ break;
+ dl = dl->next;
+ }

- if (dl->index < 0)
- dl->index = i;
/* found a usable disk with enough space */
di = malloc(sizeof(*di));
if (!di)
diff --git a/sysfs.c b/sysfs.c
index ca29aab..7a0403d 100644
--- a/sysfs.c
+++ b/sysfs.c
@@ -801,180 +801,6 @@ int sysfs_unique_holder(int devnum, long rdev)
return found;
}

-int sysfs_is_spare_device_belongs_to(int fd, char *devname)
-{
- int ret_val = -1;
- char fname[PATH_MAX];
- char *base;
- char *dbase;
- struct mdinfo *sra;
- DIR *dir = NULL;
- struct dirent *de;
-
- sra = malloc(sizeof(*sra));
- if (sra == NULL)
- goto abort;
- memset(sra, 0, sizeof(*sra));
- sysfs_init(sra, fd, -1);
- if (sra->sys_name[0] == 0)
- goto abort;
-
- memset(fname, PATH_MAX, 0);
- sprintf(fname, "/sys/block/%s/md/", sra->sys_name);
- base = fname + strlen(fname);
-
- /* Get all the devices as well */
- *base = 0;
- dir = opendir(fname);
- if (!dir)
- goto abort;
- while ((de = readdir(dir)) != NULL) {
- if (de->d_ino == 0 ||
- strncmp(de->d_name, "dev-", 4) != 0)
- continue;
- strcpy(base, de->d_name);
- dbase = base + strlen(base);
- *dbase = '\0';
- dbase = strstr(fname, "/md/");
- if (dbase && strcmp(devname, dbase) == 0) {
- ret_val = 1;
- goto abort;
- }
- }
-abort:
- if (dir)
- closedir(dir);
- sysfs_free(sra);
-
- return ret_val;
-}
-
-struct mdinfo *sysfs_get_unused_spares(int container_fd, int fd)
-{
- char fname[PATH_MAX];
- char buf[PATH_MAX];
- char *base;
- char *dbase;
- struct mdinfo *ret_val;
- struct mdinfo *dev;
- DIR *dir = NULL;
- struct dirent *de;
- int is_in;
- char *to_check;
-
- ret_val = malloc(sizeof(*ret_val));
- if (ret_val == NULL)
- goto abort;
- memset(ret_val, 0, sizeof(*ret_val));
- sysfs_init(ret_val, container_fd, -1);
- if (ret_val->sys_name[0] == 0)
- goto abort;
-
- sprintf(fname, "/sys/block/%s/md/", ret_val->sys_name);
- base = fname + strlen(fname);
-
- strcpy(base, "raid_disks");
- if (load_sys(fname, buf))
- goto abort;
- ret_val->array.raid_disks = strtoul(buf, NULL, 0);
-
- /* Get all the devices as well */
- *base = 0;
- dir = opendir(fname);
- if (!dir)
- goto abort;
- ret_val->array.spare_disks = 0;
- while ((de = readdir(dir)) != NULL) {
- char *ep;
- if (de->d_ino == 0 ||
- strncmp(de->d_name, "dev-", 4) != 0)
- continue;
- strcpy(base, de->d_name);
- dbase = base + strlen(base);
- *dbase = '\0';
-
- to_check = strstr(fname, "/md/");
- is_in = sysfs_is_spare_device_belongs_to(fd, to_check);
- if (is_in == -1) {
- char *p;
- struct stat stb;
- char stb_name[PATH_MAX];
-
- dev = malloc(sizeof(*dev));
- if (!dev)
- goto abort;
- strncpy(dev->text_version, fname, 50);
-
- *dbase++ = '/';
-
- dev->disk.raid_disk = strtoul(buf, &ep, 10);
- dev->disk.raid_disk = -1;
-
- strcpy(dbase, "block/dev");
- if (load_sys(fname, buf)) {
- free(dev);
- continue;
- }
- /* check first if we are working on block device
- * if not, we cannot check it
- */
- p = strchr(dev->text_version, '-');
- if (p)
- p++;
- sprintf(stb_name, "/dev/%s", p);
- if (stat(stb_name, &stb) < 0) {
- dprintf(Name ": stat failed for %s: %s.\n",
- stb_name, strerror(errno));
- free(dev);
- continue;
- }
- if (!S_ISBLK(stb.st_mode)) {
- dprintf(Name\
- ": %s is not a block device."\
- " Skip checking.\n",
- stb_name);
- goto skip;
- }
- dprintf(Name": %s seams to a be block device\n",
- stb_name);
- sscanf(buf, "%d:%d",
- &dev->disk.major,
- &dev->disk.minor);
- strcpy(dbase, "block/device/state");
- if (load_sys(fname, buf) != 0) {
- free(dev);
- continue;
- }
- if (strncmp(buf, "offline", 7) == 0) {
- free(dev);
- continue;
- }
- if (strncmp(buf, "failed", 6) == 0) {
- free(dev);
- continue;
- }
-
-skip:
- /* add this disk to spares list */
- dev->next = ret_val->devs;
- ret_val->devs = dev;
- ret_val->array.spare_disks++;
- *(dbase-1) = '\0';
- dprintf("sysfs: found spare: %s [%d:%d]\n",
- fname, dev->disk.major, dev->disk.minor);
- }
- }
- closedir(dir);
- return ret_val;
-
-abort:
- if (dir)
- closedir(dir);
- sysfs_free(ret_val);
-
- return NULL;
-}
-
int sysfs_freeze_array(struct mdinfo *sra)
{
/* Try to freeze resync/rebuild on this array/container.

--
To unsubscribe from this list: send the line "unsubscribe linux-raid" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html

RE: [PATCH] Finding spare devices for grow - rework

am 14.12.2010 18:23:14 von Marcin.Labun

SSB3b3VsZCB0cnkgdG8gYXZvaWQgZG91YmxlIG1lbW9yeSBhbGxvY2F0aW9u IGJ5IG9uZSBvZjoN
Ci0gbW9kaWZ5IGdldGluZm9fc3VwZXJfZGlza3NfaW1zbSB0byBsZXQgdGhl IGNhbGxlciBzcGVj
aWZ5IHN0YXRlIG9mIGRpc2tzIHRoYXQgaXMgaW50ZXJlc3RlZCBpbi4gIA0K SW4geW91ciBjYXNl
LCBpdCB3b3VsZCBiZSAwIC0gZm9yIHNwYXJlIGRpc2suIA0KDQotIG9yIGlu dHJvZHVjZSBhIG5l
dyBzdXBlci1pbnRlbC5jIGZ1bmN0aW9uIHRoYXQgYWxsb3dzIHRvIGNvbnN0 cmFpbiBkaXNrcyBs
aXN0IHRoYXQgaXMgcmV0dXJuZWQuIFRoZSBmdW5jdGlvbiBzaGFsbCBjb250 YWluIHRoZSBjdXJy
ZW50IA0KYm9keSBvZiBnZXRpbmZvX3N1cGVyX2Rpc2tzX2ltc20gYW5kIGlu c3RydW1lbnRhdGlv
biB0aGF0IHlvdXIgY29kZSByZXF1aXJlcyAoaS5lLiBkaXNrIHN0YXRlIGFu ZCBkaXNrIHNpemUg
dmVyaWZpY2F0aW9uKS4NCmdldGluZm9fc3VwZXJfZGlza3NfaW1zbSB3b3Vs ZCBjYWxsIHRoaXMg
bmV3IGZ1bmN0aW9uIHdpdGggYXBwcm9wcmlhdGUgcGFyYW1ldGVycy4NCg0K TWFyY2luDQoNCj4g
LS0tLS1PcmlnaW5hbCBNZXNzYWdlLS0tLS0NCj4gRnJvbTogbGludXgtcmFp ZC1vd25lckB2Z2Vy
Lmtlcm5lbC5vcmcgW21haWx0bzpsaW51eC1yYWlkLQ0KPiBvd25lckB2Z2Vy Lmtlcm5lbC5vcmdd
IE9uIEJlaGFsZiBPZiBLcnp5c3p0b2YgV29qY2lrDQo+IFNlbnQ6IE1vbmRh eSwgRGVjZW1iZXIg
MTMsIDIwMTAgMToyOSBQTQ0KPiBUbzogbmVpbGJAc3VzZS5kZQ0KPiBDYzog bGludXgtcmFpZEB2
Z2VyLmtlcm5lbC5vcmc7IE5ldWJhdWVyLCBXb2pjaWVjaDsgS3dvbGVrLCBB ZGFtOw0KPiBXaWxs
aWFtcywgRGFuIEo7IENpZWNoYW5vd3NraSwgRWQNCj4gU3ViamVjdDogW1BB VENIXSBGaW5kaW5n
IHNwYXJlIGRldmljZXMgZm9yIGdyb3cgLSByZXdvcmsNCj4gDQo+IFRoaXMg cGF0Y2ggaW50cm9k
dWNlcyBuZXcgbWV0aG9kIG9mIGZpbmRpbmcgc3BhcmUgZGV2aWNlcw0KPiBm b3IgZ3JvdyAoT25M
aW5lIENhcGFjaXR5IEV4cGFuc2lvbikgb3BlcmF0aW9uLg0KPiBUaGUgcGF0 Y2ggcmV1c2VzIGNv
ZGUgYW5kIHByb2NlZHVyZXMgZGVsaXZlcmVkDQo+IGJ5IHRoZSBBcnJheSBB dXRvIFJlYnVpbGQg
ZnVuY3Rpb25hbGl0eSBoZW5jZSBpdCByZWR1Y2UNCj4gY29kZSByZWR1bmRh bmN5Lg0KPiBUaGUg
cGF0Y2ggYWxzbyBpbnRyb2R1Y2VzIHNwYXJlIGRyaXZlIHNpemUgdmVyaWZp Y2F0aW9uDQo+ICht
aXNzaW5nIGluIGVhcmx5IGltcGxlbWVudGF0aW9uKQ0KPiANCj4gU2lnbmVk LW9mZi1ieTogS3J6
eXN6dG9mIFdvamNpayA8a3J6eXN6dG9mLndvamNpa0BpbnRlbC5jb20+DQo+ IC0tLQ0KPiAgc3Vw
ZXItaW50ZWwuYyB8ICAxNDIgKysrKysrKysrKysrKysrKysrKysrKystLS0t LS0tLS0tLS0tLS0t
LS0tLS0tLS0NCj4gIHN5c2ZzLmMgICAgICAgfCAgMTc0IC0tLS0tLS0tLS0t LS0tLS0tLS0tLS0t
LS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0tLS0NCj4gLS0tLS0tLS0NCj4gIDIg ZmlsZXMgY2hhbmdl
ZCwgNzAgaW5zZXJ0aW9ucygrKSwgMjQ2IGRlbGV0aW9ucygtKQ0KPiANCj4g ZGlmZiAtLWdpdCBh
L3N1cGVyLWludGVsLmMgYi9zdXBlci1pbnRlbC5jDQo+IGluZGV4IDYyNmVj YjYuLmM4ZDYzODIg
MTAwNjQ0DQo+IC0tLSBhL3N1cGVyLWludGVsLmMNCj4gKysrIGIvc3VwZXIt aW50ZWwuYw0KPiBA
QCAtNzM1Miw3NyArNzM1Miw3MiBAQCBleGl0X2ltc21fcmVzaGFwZV9pc19h bGxvd2VkX29uX2Nv
bnRhaW5lcjoNCj4gIAlyZXR1cm4gcmV0X3ZhbDsNCj4gIH0NCj4gDQo+IC1z dHJ1Y3QgbWRpbmZv
ICpnZXRfc3BhcmVzX2ltc20oaW50IGRldm51bSkNCj4gKy8qIEZ1bmN0aW9u OiBnZXRfc3BhcmVz
X2Zvcl9ncm93DQo+ICsgKiBEZXNjcmlwdGlvbjogQWxsb2NhdGVzIG1lbW9y eSBhbmQgY3JlYXRl
cyBsaXN0IG9mIHNwYXJlIGRldmljZXMNCj4gKyAqIAkJYXZhbGlhYmxlIGlu IGNvbnRhaW50ZXIu
IENoZWNrcyBpZiBzcGFyZSBkcml2ZSBzaXplIGlzDQo+IGFjY2VwdGFibGUu DQo+ICsgKiBQYXJh
bWV0ZXJzOiBQb2ludGVyIHRvIHRoZSBzdXBlcnR5cGUgc3RydWN0dXJlDQo+ ICsgKiBSZXR1cm5z
OiBQb2ludGVyIHRvIHRoZSBsaXN0IG9mIHNwYXJlIGRldmljZXMgKG1kaW5m byBzdHJ1Y3R1cmUp
IG9uDQo+IHN1Y2VzcywNCj4gKyAqIAkJTlVMTCBpZiBmYWlsDQo+ICsgKi8N Cj4gK3N0cnVjdCBt
ZGluZm8gKmdldF9zcGFyZXNfZm9yX2dyb3coc3RydWN0IHN1cGVydHlwZSAq c3QpDQo+ICB7DQo+
ICsJaW50IGVycjsNCj4gKwljaGFyIGJ1ZltQQVRIX01BWF07DQo+ICAJaW50 IGZkID0gLTE7DQo+
IC0Jc3RydWN0IG1kaW5mbyAqaW5mbyA9IE5VTEw7DQo+IC0Jc3RydWN0IG1k aW5mbyAqcmV0X3Zh
bCA9IE5VTEw7DQo+IC0JaW50IGNvbnRfZmQgPSAtMTsNCj4gLQlzdHJ1Y3Qg c3VwZXJ0eXBlICpz
dCA9IE5VTEw7DQo+IC0JaW50IGZpbmRfcmVzdWx0Ow0KPiAtCXN0cnVjdCBp bnRlbF9zdXBlciAq
c3VwZXIgPSBOVUxMOw0KPiAtDQo+IC0JZHByaW50ZigiaW1zbTogZ2V0X3Nw YXJlc19pbXNtIGZv
ciBkZXZpY2U6ICVpLlxuIiwgZGV2bnVtKTsNCj4gKwlkZXZfdCBkZXYgPSAw Ow0KPiArCXN0cnVj
dCBtZGluZm8gKmRpc2tzLCAqZCwgKmRzOw0KPiArCXN0cnVjdCBtZGluZm8g KnNwYXJlcyA9IE5V
TEw7DQo+ICsJdW5zaWduZWQgbG9uZyBsb25nIG1pbl9zaXplID0gbWluX2Fj Y2VwdGFibGVfc3Bh
cmVfc2l6ZV9pbXNtKHN0KTsNCj4gDQo+IC0JY29udF9mZCA9IG9wZW5fZGV2 KGRldm51bSk7DQo+
IC0JaWYgKGNvbnRfZmQgPCAwKSB7DQo+IC0JCWRwcmludGYoImltc206IEVS Uk9SOiBDYW5ub3Qg
b3BlbiBjb250YWluZXIuXG4iKTsNCj4gLQkJZ290byBhYm9ydDsNCj4gLQl9 DQo+ICsJc3ByaW50
ZihidWYsICIvZGV2L21kJWkiLCBzdC0+Y29udGFpbmVyX2Rldik7DQo+ICsJ ZmQgPSBvcGVuKGJ1
ZiwgT19SRE9OTFkpOw0KPiANCj4gLQkvKiBnZXQgZmlyc3Qgdm9sdW1lICov DQo+IC0Jc3QgPSBz
dXBlcl9ieV9mZChjb250X2ZkLCBOVUxMKTsNCj4gLQlpZiAoc3QgPT0gTlVM TCkgew0KPiAtCQlk
cHJpbnRmKCJpbXNtOiBFUlJPUjogQ2Fubm90IGxvYWQgY29udGFpbmVyDQo+ IGluZm9ybWF0aW9u
LlxuIik7DQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0JfQ0KPiAtCWZpbmRfcmVz dWx0ID0gaW1zbV9m
aW5kX2FycmF5X21pbm9yX2J5X3N1YmRldigwLCBkZXZudW0sDQo+ICZkZXZu dW0pOw0KPiAtCWlm
IChmaW5kX3Jlc3VsdCA8IDApIHsNCj4gLQkJZHByaW50ZigiaW1zbTogRVJS T1I6IENhbm5vdCBm
aW5kIGFycmF5LlxuIik7DQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0JfQ0KPiAt CWZkID0gb3Blbl9k
ZXYoZGV2bnVtKTsNCj4gLQlpZiAoZmQgPCAwKSB7DQo+IC0JCWRwcmludGYo Imltc206IEVSUk9S
OiBDYW5ub3Qgb3BlbiBkZXZpY2UuXG4iKTsNCj4gLQkJZ290byBhYm9ydDsN Cj4gLQl9DQo+IC0J
c3QtPnNzLT5sb2FkX3N1cGVyKHN0LCBjb250X2ZkLCBOVUxMKTsNCj4gLQlp ZiAoc3QtPnNiID09
IE5VTEwpIHsNCj4gLQkJZHByaW50ZigiaW1zbTogRVJST1I6IENhbm5vdCBs b2FkIGFycmF5IGlu
Zm9ybWF0aW9uLlxuIik7DQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0JfQ0KPiAt CWluZm8gPSBzeXNm
c19yZWFkKGZkLA0KPiAtCQkJICAwLA0KPiAtCQkJICBHRVRfTEVWRUwgfCBH RVRfVkVSU0lPTiB8
IEdFVF9ERVZTIHwgR0VUX1NUQVRFKTsNCj4gLQlpZiAoaW5mbyA9PSBOVUxM KSB7DQo+IC0JCWRw
cmludGYoImltc206IENhbm5vdCBnZXQgZGV2aWNlIGluZm8uXG4iKTsNCj4g LQkJZ290byBhYm9y
dDsNCj4gLQl9DQo+IC0Jc3VwZXIgPSBzdC0+c2I7DQo+IC0Jc3VwZXItPmN1 cnJlbnRfdm9sID0g
MDsNCj4gLQlzdC0+c3MtPmdldGluZm9fc3VwZXIoc3QsIGluZm8sIE5VTEwp Ow0KPiAtCXJldF92
YWwgPSBzeXNmc19nZXRfdW51c2VkX3NwYXJlcyhjb250X2ZkLCBmZCk7DQo+ IC0JaWYgKHJldF92
YWwgPT0gTlVMTCkgew0KPiAtCQlkcHJpbnRmKCJpbXNtOiBFUlJPUjogQ2Fu bm90IGdldCBzcGFy
ZSBkZXZpY2VzLlxuIik7DQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0JfQ0KPiAt CWlmIChyZXRfdmFs
LT5hcnJheS5zcGFyZV9kaXNrcyA9PSAwKSB7DQo+IC0JCWRwcmludGYoImlt c206IEVSUk9SOiBO
byBhdmFpbGFibGUgc3BhcmVzLlxuIik7DQo+IC0JCWZyZWUocmV0X3ZhbCk7 DQo+IC0JCXJldF92
YWwgPSBOVUxMOw0KPiAtCQlnb3RvIGFib3J0Ow0KPiAtCX0NCj4gKwllcnIg PSBsb2FkX2NvbnRh
aW5lcl9pbXNtKHN0LCBmZCwgTlVMTCk7DQo+ICsJY2xvc2UoZmQpOw0KPiAr CWlmIChlcnIpDQo+
ICsJCXJldHVybiBOVUxMOw0KPiANCj4gLWFib3J0Og0KPiAtCWlmIChzdCkN Cj4gLQkJc3QtPnNz
LT5mcmVlX3N1cGVyKHN0KTsNCj4gLQlzeXNmc19mcmVlKGluZm8pOw0KPiAt CWlmIChmZCA+IC0x
KQ0KPiAtCQljbG9zZShmZCk7DQo+IC0JaWYgKGNvbnRfZmQgPiAtMSkNCj4g LQkJY2xvc2UoY29u
dF9mZCk7DQo+ICsJLyogZ2V0IGxpc3Qgb2YgYWxsZGlza3MgaW4gY29udGFp bmVyICovDQo+ICsJ
ZGlza3MgPSBnZXRpbmZvX3N1cGVyX2Rpc2tzX2ltc20oc3QpOw0KPiANCj4g LQlyZXR1cm4gcmV0
X3ZhbDsNCj4gKwlpZiAoIWRpc2tzKQ0KPiArCQlyZXR1cm4gTlVMTDsNCj4g KwkvKiBmaW5kIHNw
YXJlIGRldmljZXMgb24gdGhlIGxpc3QgKi8NCj4gKwlmb3IgKGQgPSBkaXNr cy0+ZGV2cyA7IGQg
OyBkID0gZC0+bmV4dCkgew0KPiArCQlpbnQgZm91bmQgPSAwOw0KPiArCQlp ZiAoZC0+ZGlzay5z
dGF0ZSA9PSAwKSB7DQo+ICsJCQkvKiBjaGVjayBpZiBzaXplIGlzIGFjY2Vw dGFibGUgKi8NCj4g
KwkJCXVuc2lnbmVkIGxvbmcgbG9uZyBkZXZfc2l6ZTsNCj4gKwkJCWRldiA9 IG1ha2VkZXYoZC0+
ZGlzay5tYWpvcixkLT5kaXNrLm1pbm9yKTsNCj4gKwkJCWlmIChtaW5fc2l6 ZSAmJg0KPiArCQkJ
ICAgIGRldl9zaXplX2Zyb21faWQoZGV2LCAgJmRldl9zaXplKSAmJg0KPiAr CQkJICAgIGRldl9z
aXplID49IG1pbl9zaXplKSB7DQo+ICsJCQkJZGV2ID0gMDsNCj4gKwkJCQlm b3VuZCA9IDE7DQo+
ICsJCQl9DQo+ICsJCX0NCj4gKwkJaWYgKGZvdW5kKSB7DQo+ICsJCQkvKiBh cHBlbmQgc3BhcmUg
dG8gdGhlIGxpc3QgKi8NCj4gKwkJCWRzID0gbWFsbG9jKHNpemVvZihzdHJ1 Y3QgbWRpbmZvKSk7
DQo+ICsJCQlpZiAoZHMgPT0gTlVMTCkNCj4gKwkJCQlnb3RvIGV4aXRfZ2V0 X3NwYXJlc19mb3Jf
Z3JvdzsNCj4gKwkJCW1lbWNweShkcywgZCwgc2l6ZW9mKHN0cnVjdCBtZGlu Zm8pKTsNCj4gKwkJ
CWRzLT5uZXh0ID0gc3BhcmVzOw0KPiArCQkJc3BhcmVzID0gZHM7DQo+ICsJ CQlkaXNrcy0+YXJy
YXkuc3BhcmVfZGlza3MrKzsNCj4gKwkJfQ0KPiArCX0NCj4gK2V4aXRfZ2V0 X3NwYXJlc19mb3Jf
Z3JvdzoNCj4gKwkvKiBmcmVlIG1lbW9yeSAqLw0KPiArCWQgPSBkaXNrcy0+ ZGV2czsNCj4gKwl3
aGlsZSAoZCkgew0KPiArCQlzdHJ1Y3QgbWRpbmZvICp0bXA7DQo+ICsJCXRt cCA9IGQtPm5leHQ7
DQo+ICsJCWZyZWUoZCk7DQo+ICsJCWQgPSB0bXA7DQo+ICsJfQ0KPiArCWRp c2tzLT5kZXZzID0g
c3BhcmVzOw0KPiArCXJldHVybiBkaXNrczsNCj4gIH0NCj4gDQo+IA0KPiAv KioqKioqKioqKioq
KioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioqKioq KioqKioqKioqKioq
Kg0KPiAqKioqKioqDQo+IEBAIC03NzA3LDcgKzc3MDIsNyBAQCBzdHJ1Y3Qg aW1zbV91cGRhdGVf
cmVzaGFwZQ0KPiAqaW1zbV9jcmVhdGVfbWV0YWRhdGFfdXBkYXRlX2Zvcl9y ZXNoYXBlKA0KPiAN
Cj4gIAkvKiBub3cgZ2V0IHNwYXJlIGRpc2tzIGxpc3QNCj4gIAkgKi8NCj4g LQlzcGFyZXMgPSBn
ZXRfc3BhcmVzX2ltc20oc3QtPmNvbnRhaW5lcl9kZXYpOw0KPiArCXNwYXJl cyA9IGdldF9zcGFy
ZXNfZm9yX2dyb3coc3QpOw0KPiANCj4gIAlpZiAoc3BhcmVzID09IE5VTEwp IHsNCj4gIAkJZHBy
aW50ZigiaW1zbTogRVJST1I6IENhbm5vdCBnZXQgc3BhcmUgZGV2aWNlcy5c biIpOw0KPiBAQCAt
ODEzMyw2ICs4MTI4LDcgQEAgc3RhdGljIGludA0KPiBpbXNtX3Jlc2hhcGVf YXJyYXlfbWFuYWdl
X25ld19zbG90cyhzdHJ1Y3QgaW50ZWxfc3VwZXIgKnN1cGVyLA0KPiAgCQlp bnQgZmQyOw0KPiAg
CQlpbnQgcnY7DQo+IA0KPiArCQkvKiBza2lwIG5vdCBjb25maWd1cmVkIGRp c2tzICovDQo+ICAJ
CWlmIChkbC0+aW5kZXggPCAwKQ0KPiAgCQkJY29udGludWU7DQo+IA0KPiBA QCAtODE4OSwxMCAr
ODE4NSwxMSBAQCBzdHJ1Y3QgbWRpbmZvICppbXNtX2dyb3dfYXJyYXkoc3Ry dWN0DQo+IGFjdGl2
ZV9hcnJheSAqYSkNCj4gIAlpbnQgaW5zdCA9IGEtPmluZm8uY29udGFpbmVy X21lbWJlcjsNCj4g
IAlzdHJ1Y3QgaW1zbV9kZXYgKmRldiA9IGdldF9pbXNtX2RldihzdXBlciwg aW5zdCk7DQo+ICAJ
c3RydWN0IGltc21fbWFwICptYXAgPSBnZXRfaW1zbV9tYXAoZGV2LCAwKTsN Cj4gKwlzdHJ1Y3Qg
aW1zbV9tYXAgKm1hcF8yID0gZ2V0X2ltc21fbWFwKGRldiwgMSk7DQo+ICAJ c3RydWN0IG1kaW5m
byAqZGk7DQo+ICAJc3RydWN0IGRsICpkbDsNCj4gIAlpbnQgaTsNCj4gLQlp bnQgcHJldl9yYWlk
X2Rpc2tzID0gYS0+aW5mby5hcnJheS5yYWlkX2Rpc2tzOw0KPiArCWludCBw cmV2X3JhaWRfZGlz
a3MgPSBtYXBfMi0+bnVtX21lbWJlcnM7DQo+ICAJaW50IG5ld19yYWlkX2Rp c2tzID0gcHJldl9y
YWlkX2Rpc2tzICsgYS0+cmVzaGFwZV9kZWx0YV9kaXNrczsNCj4gIAlzdHJ1 Y3QgbWRpbmZvICp2
b2wgPSBOVUxMOw0KPiAgCWludCBmZDsNCj4gQEAgLTgyMjEsMTIgKzgyMTgs MTMgQEAgc3RydWN0
IG1kaW5mbyAqaW1zbV9ncm93X2FycmF5KHN0cnVjdA0KPiBhY3RpdmVfYXJy YXkgKmEpDQo+ICAJ
Zm9yIChpID0gcHJldl9yYWlkX2Rpc2tzOyBpIDwgbmV3X3JhaWRfZGlza3M7 IGkrKykgew0KPiAg
CQkvKiBPSywgdGhpcyBkZXZpY2UgY2FuIGJlIGFkZGVkLiAgVHJ5IHRvIGFk ZC4NCj4gIAkJICov
DQo+IC0JCWRsID0gaW1zbV9hZGRfc3BhcmUoc3VwZXIsIGksIGEsIDAsIHJ2 KTsNCj4gLQkJaWYg
KCFkbCkNCj4gLQkJCWNvbnRpbnVlOw0KPiArCQlkbCA9IHN1cGVyLT5kaXNr czsNCj4gKwkJd2hp
bGUgKGRsKSB7DQo+ICsJCQlpZiAoZGwtPmluZGV4ID09IGkpDQo+ICsJCQkJ YnJlYWs7DQo+ICsJ
CQlkbCA9IGRsLT5uZXh0Ow0KPiArCQl9DQo+IA0KPiAtCQlpZiAoZGwtPmlu ZGV4IDwgMCkNCj4g
LQkJCWRsLT5pbmRleCA9IGk7DQo+ICAJCS8qIGZvdW5kIGEgdXNhYmxlIGRp c2sgd2l0aCBlbm91
Z2ggc3BhY2UgKi8NCj4gIAkJZGkgPSBtYWxsb2Moc2l6ZW9mKCpkaSkpOw0K PiAgCQlpZiAoIWRp
KQ0KPiBkaWZmIC0tZ2l0IGEvc3lzZnMuYyBiL3N5c2ZzLmMNCj4gaW5kZXgg Y2EyOWFhYi4uN2Ew
NDAzZCAxMDA2NDQNCj4gLS0tIGEvc3lzZnMuYw0KPiArKysgYi9zeXNmcy5j DQo+IEBAIC04MDEs
MTgwICs4MDEsNiBAQCBpbnQgc3lzZnNfdW5pcXVlX2hvbGRlcihpbnQgZGV2 bnVtLCBsb25nIHJk
ZXYpDQo+ICAJCXJldHVybiBmb3VuZDsNCj4gIH0NCj4gDQo+IC1pbnQgc3lz ZnNfaXNfc3BhcmVf
ZGV2aWNlX2JlbG9uZ3NfdG8oaW50IGZkLCBjaGFyICpkZXZuYW1lKQ0KPiAt ew0KPiAtCWludCBy
ZXRfdmFsID0gLTE7DQo+IC0JY2hhciBmbmFtZVtQQVRIX01BWF07DQo+IC0J Y2hhciAqYmFzZTsN
Cj4gLQljaGFyICpkYmFzZTsNCj4gLQlzdHJ1Y3QgbWRpbmZvICpzcmE7DQo+ IC0JRElSICpkaXIg
PSBOVUxMOw0KPiAtCXN0cnVjdCBkaXJlbnQgKmRlOw0KPiAtDQo+IC0Jc3Jh ID0gbWFsbG9jKHNp
emVvZigqc3JhKSk7DQo+IC0JaWYgKHNyYSA9PSBOVUxMKQ0KPiAtCQlnb3Rv IGFib3J0Ow0KPiAt
CW1lbXNldChzcmEsIDAsIHNpemVvZigqc3JhKSk7DQo+IC0Jc3lzZnNfaW5p dChzcmEsIGZkLCAt
MSk7DQo+IC0JaWYgKHNyYS0+c3lzX25hbWVbMF0gPT0gMCkNCj4gLQkJZ290 byBhYm9ydDsNCj4g
LQ0KPiAtCW1lbXNldChmbmFtZSwgUEFUSF9NQVgsIDApOw0KPiAtCXNwcmlu dGYoZm5hbWUsICIv
c3lzL2Jsb2NrLyVzL21kLyIsIHNyYS0+c3lzX25hbWUpOw0KPiAtCWJhc2Ug PSBmbmFtZSArIHN0
cmxlbihmbmFtZSk7DQo+IC0NCj4gLQkvKiBHZXQgYWxsIHRoZSBkZXZpY2Vz IGFzIHdlbGwgKi8N
Cj4gLQkqYmFzZSA9IDA7DQo+IC0JZGlyID0gb3BlbmRpcihmbmFtZSk7DQo+ IC0JaWYgKCFkaXIp
DQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0Jd2hpbGUgKChkZSA9IHJlYWRkaXIo ZGlyKSkgIT0gTlVM
TCkgew0KPiAtCQlpZiAoZGUtPmRfaW5vID09IDAgfHwNCj4gLQkJICAgIHN0 cm5jbXAoZGUtPmRf
bmFtZSwgImRldi0iLCA0KSAhPSAwKQ0KPiAtCQkJY29udGludWU7DQo+IC0J CXN0cmNweShiYXNl
LCBkZS0+ZF9uYW1lKTsNCj4gLQkJZGJhc2UgPSBiYXNlICsgc3RybGVuKGJh c2UpOw0KPiAtCQkq
ZGJhc2UgPSAnXDAnOw0KPiAtCQlkYmFzZSA9IHN0cnN0cihmbmFtZSwgIi9t ZC8iKTsNCj4gLQkJ
aWYgKGRiYXNlICYmIHN0cmNtcChkZXZuYW1lLCBkYmFzZSkgPT0gMCkgew0K PiAtCQkJcmV0X3Zh
bCA9IDE7DQo+IC0JCQlnb3RvIGFib3J0Ow0KPiAtCQl9DQo+IC0JfQ0KPiAt YWJvcnQ6DQo+IC0J
aWYgKGRpcikNCj4gLQkJY2xvc2VkaXIoZGlyKTsNCj4gLQlzeXNmc19mcmVl KHNyYSk7DQo+IC0N
Cj4gLQlyZXR1cm4gcmV0X3ZhbDsNCj4gLX0NCj4gLQ0KPiAtc3RydWN0IG1k aW5mbyAqc3lzZnNf
Z2V0X3VudXNlZF9zcGFyZXMoaW50IGNvbnRhaW5lcl9mZCwgaW50IGZkKQ0K PiAtew0KPiAtCWNo
YXIgZm5hbWVbUEFUSF9NQVhdOw0KPiAtCWNoYXIgYnVmW1BBVEhfTUFYXTsN Cj4gLQljaGFyICpi
YXNlOw0KPiAtCWNoYXIgKmRiYXNlOw0KPiAtCXN0cnVjdCBtZGluZm8gKnJl dF92YWw7DQo+IC0J
c3RydWN0IG1kaW5mbyAqZGV2Ow0KPiAtCURJUiAqZGlyID0gTlVMTDsNCj4g LQlzdHJ1Y3QgZGly
ZW50ICpkZTsNCj4gLQlpbnQgaXNfaW47DQo+IC0JY2hhciAqdG9fY2hlY2s7 DQo+IC0NCj4gLQly
ZXRfdmFsID0gbWFsbG9jKHNpemVvZigqcmV0X3ZhbCkpOw0KPiAtCWlmIChy ZXRfdmFsID09IE5V
TEwpDQo+IC0JCWdvdG8gYWJvcnQ7DQo+IC0JbWVtc2V0KHJldF92YWwsIDAs IHNpemVvZigqcmV0
X3ZhbCkpOw0KPiAtCXN5c2ZzX2luaXQocmV0X3ZhbCwgY29udGFpbmVyX2Zk LCAtMSk7DQo+IC0J
aWYgKHJldF92YWwtPnN5c19uYW1lWzBdID09IDApDQo+IC0JCWdvdG8gYWJv cnQ7DQo+IC0NCj4g
LQlzcHJpbnRmKGZuYW1lLCAiL3N5cy9ibG9jay8lcy9tZC8iLCByZXRfdmFs LT5zeXNfbmFtZSk7
DQo+IC0JYmFzZSA9IGZuYW1lICsgc3RybGVuKGZuYW1lKTsNCj4gLQ0KPiAt CXN0cmNweShiYXNl
LCAicmFpZF9kaXNrcyIpOw0KPiAtCWlmIChsb2FkX3N5cyhmbmFtZSwgYnVm KSkNCj4gLQkJZ290
byBhYm9ydDsNCj4gLQlyZXRfdmFsLT5hcnJheS5yYWlkX2Rpc2tzID0gc3Ry dG91bChidWYsIE5V
TEwsIDApOw0KPiAtDQo+IC0JLyogR2V0IGFsbCB0aGUgZGV2aWNlcyBhcyB3 ZWxsICovDQo+IC0J
KmJhc2UgPSAwOw0KPiAtCWRpciA9IG9wZW5kaXIoZm5hbWUpOw0KPiAtCWlm ICghZGlyKQ0KPiAt
CQlnb3RvIGFib3J0Ow0KPiAtCXJldF92YWwtPmFycmF5LnNwYXJlX2Rpc2tz ID0gMDsNCj4gLQl3
aGlsZSAoKGRlID0gcmVhZGRpcihkaXIpKSAhPSBOVUxMKSB7DQo+IC0JCWNo YXIgKmVwOw0KPiAt
CQlpZiAoZGUtPmRfaW5vID09IDAgfHwNCj4gLQkJICAgIHN0cm5jbXAoZGUt PmRfbmFtZSwgImRl
di0iLCA0KSAhPSAwKQ0KPiAtCQkJY29udGludWU7DQo+IC0JCXN0cmNweShi YXNlLCBkZS0+ZF9u
YW1lKTsNCj4gLQkJZGJhc2UgPSBiYXNlICsgc3RybGVuKGJhc2UpOw0KPiAt CQkqZGJhc2UgPSAn
XDAnOw0KPiAtDQo+IC0JCXRvX2NoZWNrID0gc3Ryc3RyKGZuYW1lLCAiL21k LyIpOw0KPiAtCQlp
c19pbiA9IHN5c2ZzX2lzX3NwYXJlX2RldmljZV9iZWxvbmdzX3RvKGZkLCB0 b19jaGVjayk7DQo+
IC0JCWlmIChpc19pbiA9PSAtMSkgew0KPiAtCQkJY2hhciAqcDsNCj4gLQkJ CXN0cnVjdCBzdGF0
IHN0YjsNCj4gLQkJCWNoYXIgc3RiX25hbWVbUEFUSF9NQVhdOw0KPiAtDQo+ IC0JCQlkZXYgPSBt
YWxsb2Moc2l6ZW9mKCpkZXYpKTsNCj4gLQkJCWlmICghZGV2KQ0KPiAtCQkJ CWdvdG8gYWJvcnQ7
DQo+IC0JCQlzdHJuY3B5KGRldi0+dGV4dF92ZXJzaW9uLCBmbmFtZSwgNTAp Ow0KPiAtDQo+IC0J
CQkqZGJhc2UrKyA9ICcvJzsNCj4gLQ0KPiAtCQkJZGV2LT5kaXNrLnJhaWRf ZGlzayA9IHN0cnRv
dWwoYnVmLCAmZXAsIDEwKTsNCj4gLQkJCWRldi0+ZGlzay5yYWlkX2Rpc2sg PSAtMTsNCj4gLQ0K
PiAtCQkJc3RyY3B5KGRiYXNlLCAiYmxvY2svZGV2Iik7DQo+IC0JCQlpZiAo bG9hZF9zeXMoZm5h
bWUsIGJ1ZikpIHsNCj4gLQkJCQlmcmVlKGRldik7DQo+IC0JCQkJY29udGlu dWU7DQo+IC0JCQl9
DQo+IC0JCQkvKiBjaGVjayBmaXJzdCBpZiB3ZSBhcmUgd29ya2luZyBvbiBi bG9jayBkZXZpY2UN
Cj4gLQkJCSAqIGlmIG5vdCwgd2UgY2Fubm90IGNoZWNrIGl0DQo+IC0JCQkg Ki8NCj4gLQkJCXAg
PSBzdHJjaHIoZGV2LT50ZXh0X3ZlcnNpb24sICctJyk7DQo+IC0JCQlpZiAo cCkNCj4gLQkJCQlw
Kys7DQo+IC0JCQlzcHJpbnRmKHN0Yl9uYW1lLCAiL2Rldi8lcyIsIHApOw0K PiAtCQkJaWYgKHN0
YXQoc3RiX25hbWUsICZzdGIpIDwgMCkgew0KPiAtCQkJCWRwcmludGYoTmFt ZSAiOiBzdGF0IGZh
aWxlZCBmb3IgJXM6ICVzLlxuIiwNCj4gLQkJCQkJc3RiX25hbWUsIHN0cmVy cm9yKGVycm5vKSk7
DQo+IC0JCQkJZnJlZShkZXYpOw0KPiAtCQkJCWNvbnRpbnVlOw0KPiAtCQkJ fQ0KPiAtCQkJaWYg
KCFTX0lTQkxLKHN0Yi5zdF9tb2RlKSkgew0KPiAtCQkJCWRwcmludGYoTmFt ZVwNCj4gLQkJCQkJ
IjogJXMgaXMgbm90IGEgYmxvY2sgZGV2aWNlLiJcDQo+IC0JCQkJCSIgU2tp cCBjaGVja2luZy5c
biIsDQo+IC0JCQkJCXN0Yl9uYW1lKTsNCj4gLQkJCQlnb3RvIHNraXA7DQo+ IC0JCQl9DQo+IC0J
CQlkcHJpbnRmKE5hbWUiOiAlcyBzZWFtcyB0byBhIGJlIGJsb2NrIGRldmlj ZVxuIiwNCj4gLQkJ
CQlzdGJfbmFtZSk7DQo+IC0JCQlzc2NhbmYoYnVmLCAiJWQ6JWQiLA0KPiAt CQkJICAgICAgICZk
ZXYtPmRpc2subWFqb3IsDQo+IC0JCQkgICAgICAgJmRldi0+ZGlzay5taW5v cik7DQo+IC0JCQlz
dHJjcHkoZGJhc2UsICJibG9jay9kZXZpY2Uvc3RhdGUiKTsNCj4gLQkJCWlm IChsb2FkX3N5cyhm
bmFtZSwgYnVmKSAhPSAwKSB7DQo+IC0JCQkJZnJlZShkZXYpOw0KPiAtCQkJ CWNvbnRpbnVlOw0K
PiAtCQkJfQ0KPiAtCQkJaWYgKHN0cm5jbXAoYnVmLCAib2ZmbGluZSIsIDcp ID09IDApIHsNCj4g
LQkJCQlmcmVlKGRldik7DQo+IC0JCQkJY29udGludWU7DQo+IC0JCQl9DQo+ IC0JCQlpZiAoc3Ry
bmNtcChidWYsICJmYWlsZWQiLCA2KSA9PSAwKSB7DQo+IC0JCQkJZnJlZShk ZXYpOw0KPiAtCQkJ
CWNvbnRpbnVlOw0KPiAtCQkJfQ0KPiAtDQo+IC1za2lwOg0KPiAtCQkJLyog YWRkIHRoaXMgZGlz
ayB0byBzcGFyZXMgbGlzdCAqLw0KPiAtCQkJZGV2LT5uZXh0ID0gcmV0X3Zh bC0+ZGV2czsNCj4g
LQkJCXJldF92YWwtPmRldnMgPSBkZXY7DQo+IC0JCQlyZXRfdmFsLT5hcnJh eS5zcGFyZV9kaXNr
cysrOw0KPiAtCQkJKihkYmFzZS0xKSA9ICdcMCc7DQo+IC0JCQlkcHJpbnRm KCJzeXNmczogZm91
bmQgc3BhcmU6ICVzIFslZDolZF1cbiIsDQo+IC0JCQkJZm5hbWUsIGRldi0+ ZGlzay5tYWpvciwg
ZGV2LT5kaXNrLm1pbm9yKTsNCj4gLQkJfQ0KPiAtCX0NCj4gLQljbG9zZWRp cihkaXIpOw0KPiAt
CXJldHVybiByZXRfdmFsOw0KPiAtDQo+IC1hYm9ydDoNCj4gLQlpZiAoZGly KQ0KPiAtCQljbG9z
ZWRpcihkaXIpOw0KPiAtCXN5c2ZzX2ZyZWUocmV0X3ZhbCk7DQo+IC0NCj4g LQlyZXR1cm4gTlVM
TDsNCj4gLX0NCj4gLQ0KPiAgaW50IHN5c2ZzX2ZyZWV6ZV9hcnJheShzdHJ1 Y3QgbWRpbmZvICpz
cmEpDQo+ICB7DQo+ICAJLyogVHJ5IHRvIGZyZWV6ZSByZXN5bmMvcmVidWls ZCBvbiB0aGlzIGFy
cmF5L2NvbnRhaW5lci4NCj4gDQo+IC0tDQo+IFRvIHVuc3Vic2NyaWJlIGZy b20gdGhpcyBsaXN0
OiBzZW5kIHRoZSBsaW5lICJ1bnN1YnNjcmliZSBsaW51eC1yYWlkIg0KPiBp bg0KPiB0aGUgYm9k
eSBvZiBhIG1lc3NhZ2UgdG8gbWFqb3Jkb21vQHZnZXIua2VybmVsLm9yZw0K PiBNb3JlIG1ham9y
ZG9tbyBpbmZvIGF0ICBodHRwOi8vdmdlci5rZXJuZWwub3JnL21ham9yZG9t by1pbmZvLmh0bWwN
Cg==
--
To unsubscribe from this list: send the line "unsubscribe linux-raid" in
the body of a message to majordomo@vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html