00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <config.h>
00021
00022 #include "schroot-listmounts-main.h"
00023
00024 #include <cerrno>
00025 #include <climits>
00026 #include <cstdio>
00027 #include <cstdlib>
00028 #include <ctime>
00029 #include <iostream>
00030 #include <locale>
00031
00032 #include <sys/types.h>
00033 #include <sys/stat.h>
00034 #include <unistd.h>
00035
00036 #include <boost/format.hpp>
00037
00038 #include <mntent.h>
00039
00040 #include <lockdev.h>
00041
00042 using std::endl;
00043 using boost::format;
00044 using sbuild::_;
00045 using sbuild::N_;
00046 using namespace schroot_listmounts;
00047
00048 namespace
00049 {
00050
00051 typedef std::pair<main::error_code,const char *> emap;
00052
00057 emap init_errors[] =
00058 {
00059
00060 emap(main::FIND, N_("Failed to find '%1%'")),
00061
00062 emap(main::OPEN, N_("Failed to open '%1%'")),
00063
00064 emap(main::CLOSE, N_("Failed to close '%1%'"))
00065 };
00066
00067 }
00068
00069 template<>
00070 sbuild::error<main::error_code>::map_type
00071 sbuild::error<main::error_code>::error_strings
00072 (init_errors,
00073 init_errors + (sizeof(init_errors) / sizeof(init_errors[0])));
00074
00075 main::main (options::ptr& options):
00076 schroot_base::main("schroot-listmounts",
00077
00078
00079 _("[OPTION...] - list mount points"),
00080 options,
00081 false),
00082 opts(options)
00083 {
00084 }
00085
00086 main::~main ()
00087 {
00088 }
00089
00090 sbuild::string_list
00091 main::list_mounts (std::string const& mountfile) const
00092 {
00093 sbuild::string_list ret;
00094
00095 std::string to_find = sbuild::normalname(this->opts->mountpoint);
00096
00097
00098 char *rpath = realpath(to_find.c_str(), NULL);
00099 if (rpath == 0)
00100 throw error(to_find, FIND, strerror(errno));
00101
00102 to_find = rpath;
00103 free(rpath);
00104 rpath = 0;
00105
00106 std::FILE *mntdb = std::fopen(mountfile.c_str(), "r");
00107 if (mntdb == 0)
00108 throw error(mountfile, OPEN, strerror(errno));
00109
00110 mntent *mount;
00111 while ((mount = getmntent(mntdb)) != 0)
00112 {
00113 std::string mount_dir(mount->mnt_dir);
00114 if (to_find == "/" ||
00115 (mount_dir.find(to_find) == 0 &&
00116 (
00117 mount_dir.size() == to_find.size() ||
00118
00119 (mount_dir.size() > to_find.size() &&
00120 mount_dir[to_find.size()] == '/'))))
00121 ret.push_back(mount_dir);
00122 }
00123
00124 std::cout << std::flush;
00125
00126 if (std::fclose(mntdb) == EOF)
00127 throw error(mountfile, CLOSE, strerror(errno));
00128
00129 return ret;
00130 }
00131
00132 void
00133 main::action_listmounts ()
00134 {
00135
00136 const sbuild::string_list mounts =
00137 list_mounts("/proc/mounts");
00138
00139 for (sbuild::string_list::const_reverse_iterator pos = mounts.rbegin();
00140 pos != mounts.rend();
00141 ++pos)
00142 std::cout << *pos << '\n';
00143 std::cout << std::flush;
00144 }
00145
00146 int
00147 main::run_impl ()
00148 {
00149 if (this->opts->action == options::ACTION_HELP)
00150 action_help(std::cerr);
00151 else if (this->opts->action == options::ACTION_VERSION)
00152 action_version(std::cerr);
00153 else if (this->opts->action == options::ACTION_LISTMOUNTS)
00154 action_listmounts();
00155 else
00156 assert(0);
00157
00158 return EXIT_SUCCESS;
00159 }