mirror of
git://sourceware.org/git/lvm2.git
synced 2025-02-25 21:57:45 +03:00
scan: add a dev to bcache before each read to handle write path
This is a temporary hacky workaround to the problem of reads going through bcache and writes not using bcache. The write path wants to read parts of data that it is incrementally writing to disk, but the reads (using bcache) don't work because the writes are not in the bcache. For now, add a dev to bcache before each attempt to read it in case it's being used on the write path.
This commit is contained in:
parent
6c67c7557c
commit
9d2add1361
@ -320,6 +320,8 @@ static int _raw_read_mda_header(struct mda_header *mdah, struct device_area *dev
|
||||
log_debug_metadata("Reading mda header sector from %s at %llu",
|
||||
dev_name(dev_area->dev), (unsigned long long)dev_area->start);
|
||||
|
||||
label_scan_confirm(dev_area->dev); /* FIXME: remove this, ensures dev is in bcache */
|
||||
|
||||
if (!bcache_read_bytes(scan_bcache, dev_area->dev->bcache_fd, dev_area->start, MDA_HEADER_SIZE, mdah)) {
|
||||
log_error("Failed to read metadata area header on %s at %llu",
|
||||
dev_name(dev_area->dev), (unsigned long long)dev_area->start);
|
||||
@ -462,6 +464,8 @@ static struct raw_locn *_read_metadata_location_vg(struct device_area *dev_area,
|
||||
*/
|
||||
memset(vgnamebuf, 0, sizeof(vgnamebuf));
|
||||
|
||||
label_scan_confirm(dev_area->dev); /* FIXME: remove this, ensures dev is in bcache */
|
||||
|
||||
bcache_read_bytes(scan_bcache, dev_area->dev->bcache_fd, dev_area->start + rlocn->offset, NAME_LEN, vgnamebuf);
|
||||
|
||||
if (!strncmp(vgnamebuf, vgname, len = strlen(vgname)) &&
|
||||
@ -1209,6 +1213,8 @@ int read_metadata_location_summary(const struct format_type *fmt,
|
||||
return 0;
|
||||
}
|
||||
|
||||
label_scan_confirm(dev_area->dev); /* FIXME: remove this, ensures dev is in bcache */
|
||||
|
||||
bcache_read_bytes(scan_bcache, dev_area->dev->bcache_fd, dev_area->start + rlocn->offset, NAME_LEN, buf);
|
||||
|
||||
while (buf[len] && !isspace(buf[len]) && buf[len] != '{' &&
|
||||
|
@ -786,3 +786,21 @@ int label_read_sector(struct device *dev, struct label **labelp, uint64_t scan_s
|
||||
return label_read(dev, labelp, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
* FIXME: remove this. It should not be needed once writes are going through
|
||||
* bcache. As it is now, the write path involves multiple writes to a device,
|
||||
* and later writes want to read previous writes from disk. They do these
|
||||
* reads using the standard read paths which require the devs to be in bcache,
|
||||
* but the bcache reads do not find the dev because the writes have gone around
|
||||
* bcache. To work around this for now, check if each dev is in bcache before
|
||||
* reading it, and if not add it first.
|
||||
*/
|
||||
|
||||
void label_scan_confirm(struct device *dev)
|
||||
{
|
||||
if (!_in_bcache(dev)) {
|
||||
log_warn("add dev %s to bcache", dev_name(dev));
|
||||
label_read(dev, NULL, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -109,5 +109,6 @@ void label_scan_invalidate(struct device *dev);
|
||||
void label_scan_destroy(struct cmd_context *cmd);
|
||||
int label_read(struct device *dev, struct label **labelp, uint64_t unused_sector);
|
||||
int label_read_sector(struct device *dev, struct label **labelp, uint64_t scan_sector);
|
||||
void label_scan_confirm(struct device *dev);
|
||||
|
||||
#endif
|
||||
|
Loading…
x
Reference in New Issue
Block a user