diff --git a/Makefile.in b/Makefile.in index a0e7aa4..87f2fd7 100644 --- a/Makefile.in +++ b/Makefile.in @@ -41,6 +41,7 @@ SOURCE=\ caching/cache_metadata_size.cc \ caching/cache_repair.cc \ caching/cache_restore.cc \ + caching/cache_writeback.cc \ caching/commands.cc \ caching/hint_array.cc \ caching/mapping_array.cc \ @@ -216,6 +217,7 @@ install: bin/pdata_tools ln -s -f pdata_tools $(BINDIR)/cache_metadata_size ln -s -f pdata_tools $(BINDIR)/cache_repair ln -s -f pdata_tools $(BINDIR)/cache_restore + ln -s -f pdata_tools $(BINDIR)/cache_writeback ln -s -f pdata_tools $(BINDIR)/thin_check ln -s -f pdata_tools $(BINDIR)/thin_delta ln -s -f pdata_tools $(BINDIR)/thin_dump @@ -235,6 +237,7 @@ install: bin/pdata_tools $(INSTALL_DATA) man8/cache_dump.8 $(MANPATH)/man8 $(INSTALL_DATA) man8/cache_repair.8 $(MANPATH)/man8 $(INSTALL_DATA) man8/cache_restore.8 $(MANPATH)/man8 + $(INSTALL_DATA) man8/cache_writeback.8 $(MANPATH)/man8 $(INSTALL_DATA) man8/thin_check.8 $(MANPATH)/man8 $(INSTALL_DATA) man8/thin_delta.8 $(MANPATH)/man8 $(INSTALL_DATA) man8/thin_dump.8 $(MANPATH)/man8 diff --git a/caching/cache_writeback.cc b/caching/cache_writeback.cc new file mode 100644 index 0000000..a3d27d1 --- /dev/null +++ b/caching/cache_writeback.cc @@ -0,0 +1,122 @@ +#ifndef CACHING_CACHE_WRITEBACK_H +#define CACHING_CACHE_WRITEBACK_H + +#include "caching/commands.h" +#include "version.h" + +#include +#include +#include + +using namespace caching; +using namespace boost; +using namespace std; + +//---------------------------------------------------------------- + +namespace { + struct flags { + using maybe_string = boost::optional; + + maybe_string metadata_dev; + maybe_string origin_dev; + maybe_string fast_dev; + }; + + int writeback(flags const &f) { + return 1; + } +} + +//---------------------------------------------------------------- + +cache_writeback_cmd::cache_writeback_cmd() + : command("cache_writeback") +{ +} + +void +cache_writeback_cmd::usage(std::ostream &out) const +{ + out << "Usage: " << get_name() << " [options]\n" + << "\t\t--metadata-device \n" + << "\t\t--origin-device \n" + << "\t\t--fast-device \n" + << "Options:\n" + << " {-h|--help}\n" + << " {-V|--version}" << endl; +} + +int +cache_writeback_cmd::run(int argc, char **argv) +{ + int c; + flags fs; + char const *short_opts = "hV"; + option const long_opts[] = { + { "metadata-device", required_argument, NULL, 0 }, + { "origin-device", required_argument, NULL, 1 }, + { "fast-device", required_argument, NULL, 2 }, + { "help", no_argument, NULL, 'h'}, + { "version", no_argument, NULL, 'V'}, + { NULL, no_argument, NULL, 0 } + }; + + while ((c = getopt_long(argc, argv, short_opts, long_opts, NULL)) != -1) { + switch(c) { + case 0: + fs.metadata_dev = optarg; + break; + + case 1: + fs.origin_dev = optarg; + break; + + case 2: + fs.fast_dev = optarg; + break; + + case 'h': + usage(cout); + return 0; + + case 'V': + cout << THIN_PROVISIONING_TOOLS_VERSION << endl; + return 0; + + default: + usage(cerr); + return 1; + } + } + + if (argc != optind) { + usage(cerr); + return 1; + } + + if (!fs.metadata_dev) { + cerr << "No metadata device provided.\n\n"; + usage(cerr); + return 1; + } + + if (!fs.origin_dev) { + cerr << "No origin device provided.\n\n"; + usage(cerr); + return 1; + } + + if (!fs.fast_dev) { + cerr << "No fast device provided.\n\n"; + usage(cerr); + return 1; + } + + return writeback(fs); + +} + +//---------------------------------------------------------------- + +#endif diff --git a/caching/commands.cc b/caching/commands.cc index 1ab79e6..b150a92 100644 --- a/caching/commands.cc +++ b/caching/commands.cc @@ -13,6 +13,7 @@ caching::register_cache_commands(application &app) app.add_cmd(command::ptr(new cache_metadata_size_cmd)); app.add_cmd(command::ptr(new cache_restore_cmd)); app.add_cmd(command::ptr(new cache_repair_cmd)); + app.add_cmd(command::ptr(new cache_writeback_cmd)); } //---------------------------------------------------------------- diff --git a/caching/commands.h b/caching/commands.h index 022ac06..b0546ab 100644 --- a/caching/commands.h +++ b/caching/commands.h @@ -63,6 +63,13 @@ namespace caching { virtual int run(int argc, char **argv); }; + class cache_writeback_cmd : public base::command { + public: + cache_writeback_cmd(); + virtual void usage(std::ostream &out) const; + virtual int run(int argc, char **argv); + }; + void register_cache_commands(base::application &app); } diff --git a/man8/cache_writeback.8 b/man8/cache_writeback.8 new file mode 100644 index 0000000..525b63a --- /dev/null +++ b/man8/cache_writeback.8 @@ -0,0 +1,53 @@ +.TH CACHE_WRITEBACK 8 "Thin Provisioning Tools" "Red Hat, Inc." \" -*- nroff -*- +.SH NAME +cache_writeback \- writeback dirty blocks to the origin device. + +.SH SYNOPSIS +.B cache_writeback +.RB [ options ] +.RB --metadata-device +.I {device|file} +.RB --origin-device +.I {device|file} +.RB --fast-device +.I {device|file} + +.SH DESCRIPTION +.B cache_writeback + +An offline tool that writesback dirty data to the data device +(origin). Intended for use in recovery scenarios when the SSD is +giving IO errors. + +This tool cannot be run on a live cache. + +.SH OPTIONS + +.IP "\fB\\-\-metadata\-device\fP \fI{device|file}\fP" +Location of cache metadata. + +.IP "\fB\-\-origin\-device\fP \fI{device|file}\fP" +Slow device being cached. + +.IP "\fB\-\-fast\-device\fP \fI{device|file}\fP" +Fast device containing the data that needs to be written back. + +.IP "\fB\-\-skip\-metadata\-update\fP" +Do not update the metadata to clear the dirty flags for written back +data. You may not want to do this if you're decommissioning the +cache. + +.IP "\fB\-h, \-\-help\fP" +Print help and exit. + +.IP "\fB\-V, \-\-version\fP" +Output version information and exit. + +.SH SEE ALSO +.B cache_dump(8) +.B cache_check(8) +.B cache_repair(8) +.B cache_restore(8) + +.SH AUTHOR +Joe Thornber diff --git a/thin-provisioning/commands.h b/thin-provisioning/commands.h index 1cff88f..927773c 100644 --- a/thin-provisioning/commands.h +++ b/thin-provisioning/commands.h @@ -77,17 +77,17 @@ namespace thin_provisioning { virtual int run(int argc, char **argv); }; -#ifdef DEV_TOOLS - class thin_scan_cmd : public base::command { + class thin_trim_cmd : public base::command { public: - thin_scan_cmd(); + thin_trim_cmd(); virtual void usage(std::ostream &out) const; virtual int run(int argc, char **argv); }; - class thin_trim_cmd : public base::command { +#ifdef DEV_TOOLS + class thin_scan_cmd : public base::command { public: - thin_trim_cmd(); + thin_scan_cmd(); virtual void usage(std::ostream &out) const; virtual int run(int argc, char **argv); };