|
@@ -1,1658 +0,0 @@
|
|
-# 1 "kind.ag"
|
|
|
|
-#include <dirent.h>
|
|
|
|
-# 2 "kind.ag"
|
|
|
|
-#include <sys/stat.h>
|
|
|
|
-# 3 "kind.ag"
|
|
|
|
-#include <cstring>
|
|
|
|
-# 4 "kind.ag"
|
|
|
|
-#include <unistd.h>
|
|
|
|
-# 5 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 6 "kind.ag"
|
|
|
|
-#include <iostream>
|
|
|
|
-# 7 "kind.ag"
|
|
|
|
-#include <fstream>
|
|
|
|
-# 8 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 9 "kind.ag"
|
|
|
|
-#include <string>
|
|
|
|
-# 10 "kind.ag"
|
|
|
|
-#include <vector>
|
|
|
|
-# 11 "kind.ag"
|
|
|
|
-#include <set>
|
|
|
|
-# 12 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 13 "kind.ag"
|
|
|
|
-#include <algorithm>
|
|
|
|
-# 14 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 15 "kind.ag"
|
|
|
|
-#include "stringtools.h"
|
|
|
|
-# 16 "kind.ag"
|
|
|
|
-#include "Exception.h"
|
|
|
|
-# 17 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 18 "kind.ag"
|
|
|
|
-#include "DateTime.h"
|
|
|
|
-# 19 "kind.ag"
|
|
|
|
-#include "Strings.h"
|
|
|
|
-# 20 "kind.ag"
|
|
|
|
-#include "FileName.h"
|
|
|
|
-# 21 "kind.ag"
|
|
|
|
-#include "Image.h"
|
|
|
|
-# 22 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 23 "kind.ag"
|
|
|
|
-#include "KindConfig.h"
|
|
|
|
-# 24 "kind.ag"
|
|
|
|
-#include "filetools.h"
|
|
|
|
-# 25 "kind.ag"
|
|
|
|
-#include "Lexer.h"
|
|
|
|
-# 26 "kind.ag"
|
|
|
|
-#include "rulecomp.h"
|
|
|
|
-# 27 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 28 "kind.ag"
|
|
|
|
-#include "kind.h"
|
|
|
|
-# 29 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 30 "kind.ag"
|
|
|
|
-#include "expiretools.h"
|
|
|
|
-# 31 "kind.ag"
|
|
|
|
-#include "excludetools.h"
|
|
|
|
-# 32 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 33 "kind.ag"
|
|
|
|
-/*AppGen
|
|
|
|
-# 34 "kind.ag"
|
|
|
|
- %% Beschreibung des Programmes:
|
|
|
|
-# 35 "kind.ag"
|
|
|
|
- prog: archiving backup
|
|
|
|
-# 36 "kind.ag"
|
|
|
|
- %% Beschreibung Parameter
|
|
|
|
-# 37 "kind.ag"
|
|
|
|
- % symbolischerName, Art, Typ, Variablenname, Erklärung, Default-Wert
|
|
|
|
-# 38 "kind.ag"
|
|
|
|
- para: vault_or_group, required, string, vault, Vault to backup
|
|
|
|
-# 39 "kind.ag"
|
|
|
|
- %% Beschreibung der Optionen
|
|
|
|
-# 40 "kind.ag"
|
|
|
|
- % kurz-Option, lang-Option, Typ, Variablenname, Erklärung, Default-Wert
|
|
|
|
-# 41 "kind.ag"
|
|
|
|
- opt: c, masterconfig, string, masterConfig, Master config file, ""
|
|
|
|
-# 42 "kind.ag"
|
|
|
|
- opt2: if not given or empty kind looks for
|
|
|
|
-# 43 "kind.ag"
|
|
|
|
- opt2: /etc/kind/master.conf
|
|
|
|
-# 44 "kind.ag"
|
|
|
|
- opt2: /ffp/etc/kind/master.conf
|
|
|
|
-# 45 "kind.ag"
|
|
|
|
- opt: f, full, void, fullImage, Force full image == initial backup, false
|
|
|
|
-# 46 "kind.ag"
|
|
|
|
- opt: B, backup, void, doBackup, Backup, false
|
|
|
|
-# 47 "kind.ag"
|
|
|
|
- opt: E, expire, void, doExpire, Expire, false
|
|
|
|
-# 48 "kind.ag"
|
|
|
|
- opt: C, listconfig, void, listConfig, Show configuration, false
|
|
|
|
-# 49 "kind.ag"
|
|
|
|
- opt: I, listimages, void, listImages, List data of images, false
|
|
|
|
-# 50 "kind.ag"
|
|
|
|
- opt2: if none of backup, expire, listconfig and listimages is specified,
|
|
|
|
-# 51 "kind.ag"
|
|
|
|
- opt2: backup and expire is assumed.
|
|
|
|
-# 52 "kind.ag"
|
|
|
|
- opt2: listconfig and listimages cannot be combined with other actions
|
|
|
|
-# 53 "kind.ag"
|
|
|
|
- opt: D, dryrun, Void, dryRun, Dry run (no real backup), false
|
|
|
|
-# 54 "kind.ag"
|
|
|
|
- opt: F, forcebackup, string, forcedBackupSet, Create image for specified backup set, ""
|
|
|
|
-# 55 "kind.ag"
|
|
|
|
- opt: v, verbose, Void, verbose, Verbose, false
|
|
|
|
-# 56 "kind.ag"
|
|
|
|
- opt: d, debug, Void, debug, Debug output of many data, false
|
|
|
|
-# 57 "kind.ag"
|
|
|
|
- opt: q, quiet, Void, quiet, Be quiet - no messages, false
|
|
|
|
-# 58 "kind.ag"
|
|
|
|
- opt: h, help, usage, ignored , This help
|
|
|
|
-# 59 "kind.ag"
|
|
|
|
-AppGen*/
|
|
|
|
-# 60 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 61 "kind.ag"
|
|
|
|
-using namespace std;
|
|
|
|
-# 62 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 63 "kind.ag"
|
|
|
|
-/*AppGen:Global*/
|
|
|
|
-#include <getopt.h>
|
|
|
|
-#include <string>
|
|
|
|
-#include <string>
|
|
|
|
-#include <string>
|
|
|
|
-bool dryRun = false;
|
|
|
|
-bool verbose = false;
|
|
|
|
-bool debug = false;
|
|
|
|
-bool quiet = false;
|
|
|
|
-/*AppGen:GlobalEnd*/
|
|
|
|
-# 64 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 65 "kind.ag"
|
|
|
|
-Strings banks;
|
|
|
|
-# 66 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 67 "kind.ag"
|
|
|
|
-string findVault(const string& v);
|
|
|
|
-# 68 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 69 "kind.ag"
|
|
|
|
-// we use double for sizes (in byte) to avoid overflow
|
|
|
|
-# 70 "kind.ag"
|
|
|
|
-// on machines with small int types
|
|
|
|
-# 71 "kind.ag"
|
|
|
|
-typedef pair<double, double> Sizes;
|
|
|
|
-# 72 "kind.ag"
|
|
|
|
-map<string, Sizes> sizes;
|
|
|
|
-# 73 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 74 "kind.ag"
|
|
|
|
-void readSizes(const string& logSizeFile)
|
|
|
|
-# 75 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 76 "kind.ag"
|
|
|
|
- if (!logSizeFile.empty() && fileExists(logSizeFile))
|
|
|
|
-# 77 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 78 "kind.ag"
|
|
|
|
- vector<string> ss;
|
|
|
|
-# 79 "kind.ag"
|
|
|
|
- file2Strings(logSizeFile, ss);
|
|
|
|
-# 80 "kind.ag"
|
|
|
|
- for (const string& s : ss)
|
|
|
|
-# 81 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 82 "kind.ag"
|
|
|
|
- unsigned int i = 0;
|
|
|
|
-# 83 "kind.ag"
|
|
|
|
- string vault = getWord(s, i);
|
|
|
|
-# 84 "kind.ag"
|
|
|
|
- double s1 = getDouble(s, i);
|
|
|
|
-# 85 "kind.ag"
|
|
|
|
- double s2 = getDouble(s, i);
|
|
|
|
-# 86 "kind.ag"
|
|
|
|
- try
|
|
|
|
-# 87 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 88 "kind.ag"
|
|
|
|
- findVault(vault);
|
|
|
|
-# 89 "kind.ag"
|
|
|
|
- sizes[vault] = Sizes(s1, s2);
|
|
|
|
-# 90 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 91 "kind.ag"
|
|
|
|
- catch (...)
|
|
|
|
-# 92 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 93 "kind.ag"
|
|
|
|
- // ignore missing vaults
|
|
|
|
-# 94 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 95 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 96 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 97 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 98 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 99 "kind.ag"
|
|
|
|
-void writeSizes(const string logSizeFile)
|
|
|
|
-# 100 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 101 "kind.ag"
|
|
|
|
- if (!logSizeFile.empty())
|
|
|
|
-# 102 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 103 "kind.ag"
|
|
|
|
- Strings st;
|
|
|
|
-# 104 "kind.ag"
|
|
|
|
- for (auto s : sizes)
|
|
|
|
-# 105 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 106 "kind.ag"
|
|
|
|
- string h = s.first + " " + to_string(s.second.first) + " " + to_string(s.second.second);
|
|
|
|
-# 107 "kind.ag"
|
|
|
|
- st.push_back(h);
|
|
|
|
-# 108 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 109 "kind.ag"
|
|
|
|
- strings2File(st, logSizeFile);
|
|
|
|
-# 110 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 111 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 112 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 113 "kind.ag"
|
|
|
|
-void verbosePrint(const string& text)
|
|
|
|
-# 114 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 115 "kind.ag"
|
|
|
|
- if (verbose)
|
|
|
|
-# 116 "kind.ag"
|
|
|
|
- cout << " " << text << endl;
|
|
|
|
-# 117 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 118 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 119 "kind.ag"
|
|
|
|
-void debugPrint(const string& text)
|
|
|
|
-# 120 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 121 "kind.ag"
|
|
|
|
- if (debug)
|
|
|
|
-# 122 "kind.ag"
|
|
|
|
- cout << " " << text << endl;
|
|
|
|
-# 123 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 124 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 125 "kind.ag"
|
|
|
|
-void readMasterConfig1(const string& fn, KindConfig& conf)
|
|
|
|
-# 126 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 127 "kind.ag"
|
|
|
|
- verbosePrint("reading master config " + fn);
|
|
|
|
-# 128 "kind.ag"
|
|
|
|
- conf.addFile(fn);
|
|
|
|
-# 129 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 130 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 131 "kind.ag"
|
|
|
|
-void readMasterConfig(const string& fn, KindConfig& conf)
|
|
|
|
-# 132 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 133 "kind.ag"
|
|
|
|
- if (!fn.empty()) // master config given by user on commandline
|
|
|
|
-# 134 "kind.ag"
|
|
|
|
- readMasterConfig1(fn, conf);
|
|
|
|
-# 135 "kind.ag"
|
|
|
|
- else if (fileExists("/etc/kind/master.conf"))
|
|
|
|
-# 136 "kind.ag"
|
|
|
|
- readMasterConfig1("/etc/kind/master.conf", conf);
|
|
|
|
-# 137 "kind.ag"
|
|
|
|
- else if (fileExists("/ffp/etc/kind/master.conf"))
|
|
|
|
-# 138 "kind.ag"
|
|
|
|
- readMasterConfig1("/ffp/etc/kind/master.conf", conf);
|
|
|
|
-# 139 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 140 "kind.ag"
|
|
|
|
- throw Exception("MasterConfig", "no file");
|
|
|
|
-# 141 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 142 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 143 "kind.ag"
|
|
|
|
-string findVault(const string& v)
|
|
|
|
-# 144 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 145 "kind.ag"
|
|
|
|
- bool found = false;
|
|
|
|
-# 146 "kind.ag"
|
|
|
|
- FileName fn;
|
|
|
|
-# 147 "kind.ag"
|
|
|
|
- fn.setName(v);
|
|
|
|
-# 148 "kind.ag"
|
|
|
|
- for (unsigned int i = 0; !found && i < banks.size(); ++i)
|
|
|
|
-# 149 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 150 "kind.ag"
|
|
|
|
- fn.setPath(banks[i]);
|
|
|
|
-# 151 "kind.ag"
|
|
|
|
- if (dirExists(fn.getFileName()))
|
|
|
|
-# 152 "kind.ag"
|
|
|
|
- found = true;
|
|
|
|
-# 153 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 154 "kind.ag"
|
|
|
|
- if (!found)
|
|
|
|
-# 155 "kind.ag"
|
|
|
|
- throw Exception("find vault", v + " not found");
|
|
|
|
-# 156 "kind.ag"
|
|
|
|
- verbosePrint("using vault " + fn.getFileName());
|
|
|
|
-# 157 "kind.ag"
|
|
|
|
- return fn.getFileName();
|
|
|
|
-# 158 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 159 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 160 "kind.ag"
|
|
|
|
-void readVaultConfig(const string& vault, KindConfig& conf)
|
|
|
|
-# 161 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 162 "kind.ag"
|
|
|
|
- string vaultpath = findVault(vault);
|
|
|
|
-# 163 "kind.ag"
|
|
|
|
- const string& vaultConfigName = vaultpath + '/' + conf.getString("vaultConfigName");
|
|
|
|
-# 164 "kind.ag"
|
|
|
|
- verbosePrint("reading vault config:");
|
|
|
|
-# 165 "kind.ag"
|
|
|
|
- verbosePrint(" " + vaultConfigName);
|
|
|
|
-# 166 "kind.ag"
|
|
|
|
- conf.addFile(vaultConfigName);
|
|
|
|
-# 167 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 168 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 169 "kind.ag"
|
|
|
|
-string getImageName(const KindConfig& conf,
|
|
|
|
-# 170 "kind.ag"
|
|
|
|
- const string& vaultPath,
|
|
|
|
-# 171 "kind.ag"
|
|
|
|
- const DateTime& imageTime)
|
|
|
|
-# 172 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 173 "kind.ag"
|
|
|
|
- bool nonPortable = false;
|
|
|
|
-# 174 "kind.ag"
|
|
|
|
- string imageName = conf.getString("imageName");
|
|
|
|
-# 175 "kind.ag"
|
|
|
|
- for (unsigned int i = 0; !nonPortable && i < imageName.size(); ++i)
|
|
|
|
-# 176 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 177 "kind.ag"
|
|
|
|
- char c = imageName[i];
|
|
|
|
-# 178 "kind.ag"
|
|
|
|
- if (!isalnum(c) && c != '.' && c != '_')
|
|
|
|
-# 179 "kind.ag"
|
|
|
|
- nonPortable = true;
|
|
|
|
-# 180 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 181 "kind.ag"
|
|
|
|
- if (nonPortable)
|
|
|
|
-# 182 "kind.ag"
|
|
|
|
- throw Exception("getImageName", "Invalid character in image name " + imageName);
|
|
|
|
-# 183 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 184 "kind.ag"
|
|
|
|
- if (!imageName.empty())
|
|
|
|
-# 185 "kind.ag"
|
|
|
|
- imageName += '-';
|
|
|
|
-# 186 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 187 "kind.ag"
|
|
|
|
- string imageFullName = vaultPath + "/" + imageName ;
|
|
|
|
-# 188 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 189 "kind.ag"
|
|
|
|
- if (conf.getBool("longImageName"))
|
|
|
|
-# 190 "kind.ag"
|
|
|
|
- imageFullName += imageTime.getString('m');
|
|
|
|
-# 191 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 192 "kind.ag"
|
|
|
|
- imageFullName += imageTime.getString('s');
|
|
|
|
-# 193 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 194 "kind.ag"
|
|
|
|
- return imageFullName;
|
|
|
|
-# 195 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 196 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 197 "kind.ag"
|
|
|
|
-Images findImages(const string& vaultpath, const KindConfig& conf, bool all)
|
|
|
|
-# 198 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 199 "kind.ag"
|
|
|
|
- Strings dirs;
|
|
|
|
-# 200 "kind.ag"
|
|
|
|
- debugPrint("searching images in " + vaultpath);
|
|
|
|
-# 201 "kind.ag"
|
|
|
|
- dirList(vaultpath, dirs);
|
|
|
|
-# 202 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 203 "kind.ag"
|
|
|
|
- Images imageList;
|
|
|
|
-# 204 "kind.ag"
|
|
|
|
- for (string dir : dirs)
|
|
|
|
-# 205 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 206 "kind.ag"
|
|
|
|
- FileName fn(dir);
|
|
|
|
-# 207 "kind.ag"
|
|
|
|
- string imgname = conf.getString("imageName");
|
|
|
|
-# 208 "kind.ag"
|
|
|
|
- if (startsWith(fn.getName(), imgname))
|
|
|
|
-# 209 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 210 "kind.ag"
|
|
|
|
- debugPrint("Checking " + dir);
|
|
|
|
-# 211 "kind.ag"
|
|
|
|
- Image image(dir);
|
|
|
|
-# 212 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 213 "kind.ag"
|
|
|
|
- if (all || image.valid)
|
|
|
|
-# 214 "kind.ag"
|
|
|
|
- imageList.push_back(image);
|
|
|
|
-# 215 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 216 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 217 "kind.ag"
|
|
|
|
- if (imageList.size() > 1)
|
|
|
|
-# 218 "kind.ag"
|
|
|
|
- sort(imageList.begin(), imageList.end());
|
|
|
|
-# 219 "kind.ag"
|
|
|
|
- return imageList;
|
|
|
|
-# 220 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 221 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 222 "kind.ag"
|
|
|
|
-void listImageInfo(const string& vault,
|
|
|
|
-# 223 "kind.ag"
|
|
|
|
- KindConfig conf /*Copy!*/ ,
|
|
|
|
-# 224 "kind.ag"
|
|
|
|
- const DateTime& imageTime,
|
|
|
|
-# 225 "kind.ag"
|
|
|
|
- const string& backupSet)
|
|
|
|
-# 226 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 227 "kind.ag"
|
|
|
|
- readVaultConfig(vault, conf);
|
|
|
|
-# 228 "kind.ag"
|
|
|
|
- string vaultPath = findVault(vault);
|
|
|
|
-# 229 "kind.ag"
|
|
|
|
- Images imageList = findImages(vaultPath, conf, true);
|
|
|
|
-# 230 "kind.ag"
|
|
|
|
- cout << "---" << endl;
|
|
|
|
-# 231 "kind.ag"
|
|
|
|
- for (auto img : imageList)
|
|
|
|
-# 232 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 233 "kind.ag"
|
|
|
|
- if (img.series == backupSet || backupSet.empty())
|
|
|
|
-# 234 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 235 "kind.ag"
|
|
|
|
- img.printInfo();
|
|
|
|
-# 236 "kind.ag"
|
|
|
|
- cout << "---" << endl;
|
|
|
|
-# 237 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 238 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 239 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 240 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 241 "kind.ag"
|
|
|
|
-void doBackup(const string& vault,
|
|
|
|
-# 242 "kind.ag"
|
|
|
|
- const string& imageFullName,
|
|
|
|
-# 243 "kind.ag"
|
|
|
|
- const string& referenceImage,
|
|
|
|
-# 244 "kind.ag"
|
|
|
|
- const KindConfig& conf)
|
|
|
|
-# 245 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 246 "kind.ag"
|
|
|
|
- // create image path
|
|
|
|
-# 247 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 248 "kind.ag"
|
|
|
|
- bool shellMode = true;
|
|
|
|
-# 249 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 250 "kind.ag"
|
|
|
|
- // create source descriptor
|
|
|
|
-# 251 "kind.ag"
|
|
|
|
- string host;
|
|
|
|
-# 252 "kind.ag"
|
|
|
|
- if (conf.hasKey("host"))
|
|
|
|
-# 253 "kind.ag"
|
|
|
|
- host = conf.getString("host");
|
|
|
|
-# 254 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 255 "kind.ag"
|
|
|
|
- string server;
|
|
|
|
-# 256 "kind.ag"
|
|
|
|
- if (conf.hasKey("server"))
|
|
|
|
-# 257 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 258 "kind.ag"
|
|
|
|
- server = conf.getString("server");
|
|
|
|
-# 259 "kind.ag"
|
|
|
|
- shellMode = false;
|
|
|
|
-# 260 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 261 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 262 "kind.ag"
|
|
|
|
- if (!host.empty() && !server.empty())
|
|
|
|
-# 263 "kind.ag"
|
|
|
|
- throw Exception("backupVault", "Cannot have host and server");
|
|
|
|
-# 264 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 265 "kind.ag"
|
|
|
|
- if (host.empty() && server.empty())
|
|
|
|
-# 266 "kind.ag"
|
|
|
|
- throw Exception("backupVault", "No host or server specified");
|
|
|
|
-# 267 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 268 "kind.ag"
|
|
|
|
- // ping host / server
|
|
|
|
-# 269 "kind.ag"
|
|
|
|
- // ping -c 1 -W 5 -q $HOST
|
|
|
|
-# 270 "kind.ag"
|
|
|
|
- string pingCommand = conf.getString("ping");
|
|
|
|
-# 271 "kind.ag"
|
|
|
|
- debugPrint("PingCommand: " + pingCommand);
|
|
|
|
-# 272 "kind.ag"
|
|
|
|
- if (!pingCommand.empty())
|
|
|
|
-# 273 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 274 "kind.ag"
|
|
|
|
- if (!host.empty())
|
|
|
|
-# 275 "kind.ag"
|
|
|
|
- replacePlaceHolder(pingCommand, "%host", host);
|
|
|
|
-# 276 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 277 "kind.ag"
|
|
|
|
- replacePlaceHolder(pingCommand, "%host", server);
|
|
|
|
-# 278 "kind.ag"
|
|
|
|
- int rc = 0;
|
|
|
|
-# 279 "kind.ag"
|
|
|
|
- Strings pingResult = localExec(pingCommand, rc, debug);
|
|
|
|
-# 280 "kind.ag"
|
|
|
|
- if (rc != 0)
|
|
|
|
-# 281 "kind.ag"
|
|
|
|
- throw Exception("Host not available", pingCommand);
|
|
|
|
-# 282 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 283 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 284 "kind.ag"
|
|
|
|
- string path = conf.getString("path");
|
|
|
|
-# 285 "kind.ag"
|
|
|
|
- if (path.empty())
|
|
|
|
-# 286 "kind.ag"
|
|
|
|
- throw Exception("rsync", "empty source path");
|
|
|
|
-# 287 "kind.ag"
|
|
|
|
- if (path.back() != '/')
|
|
|
|
-# 288 "kind.ag"
|
|
|
|
- path += '/';
|
|
|
|
-# 289 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 290 "kind.ag"
|
|
|
|
- string rsyncCmd = "rsync -vrltH --delete --stats -D --numeric-ids ";
|
|
|
|
-# 291 "kind.ag"
|
|
|
|
- if (!conf.getBool("ignorePermission"))
|
|
|
|
-# 292 "kind.ag"
|
|
|
|
- rsyncCmd += "-pgo";
|
|
|
|
-# 293 "kind.ag"
|
|
|
|
- vector<string> rso = conf.getStrings("rsyncOption");
|
|
|
|
-# 294 "kind.ag"
|
|
|
|
- for (const string& opt : rso)
|
|
|
|
-# 295 "kind.ag"
|
|
|
|
- rsyncCmd += opt + " ";
|
|
|
|
-# 296 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 297 "kind.ag"
|
|
|
|
- // excludes
|
|
|
|
-# 298 "kind.ag"
|
|
|
|
- Strings excluded = getExclusions(conf, shellMode);
|
|
|
|
-# 299 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 300 "kind.ag"
|
|
|
|
- // create image path
|
|
|
|
-# 301 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 302 "kind.ag"
|
|
|
|
- if (mkdir(imageFullName.c_str(), S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) != 0)
|
|
|
|
-# 303 "kind.ag"
|
|
|
|
- throw Exception("Create image", "failed to create " + imageFullName);
|
|
|
|
-# 304 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 305 "kind.ag"
|
|
|
|
- // error message
|
|
|
|
-# 306 "kind.ag"
|
|
|
|
- // we write an generic error message to mark backup as unsuccessful
|
|
|
|
-# 307 "kind.ag"
|
|
|
|
- // will be deleted at successful end of rsync
|
|
|
|
-# 308 "kind.ag"
|
|
|
|
- string errorfile = imageFullName + "/error";
|
|
|
|
-# 309 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 310 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 311 "kind.ag"
|
|
|
|
- ofstream error(errorfile);
|
|
|
|
-# 312 "kind.ag"
|
|
|
|
- error << "failed" << endl;
|
|
|
|
-# 313 "kind.ag"
|
|
|
|
- error.close();
|
|
|
|
-# 314 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 315 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 316 "kind.ag"
|
|
|
|
- if (shellMode) // shell mode
|
|
|
|
-# 317 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 318 "kind.ag"
|
|
|
|
- // cout << "USING SHELLMODE '" << host << "'" << endl;
|
|
|
|
-# 319 "kind.ag"
|
|
|
|
- string remoteShell = conf.getString("remoteShell");
|
|
|
|
-# 320 "kind.ag"
|
|
|
|
- string userAtHost = conf.getString("user") + "@" + conf.getString("host");
|
|
|
|
-# 321 "kind.ag"
|
|
|
|
- string rshCommand = remoteShell;
|
|
|
|
-# 322 "kind.ag"
|
|
|
|
- if (remoteShell.empty())
|
|
|
|
-# 323 "kind.ag"
|
|
|
|
- rshCommand = "ssh";
|
|
|
|
-# 324 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 325 "kind.ag"
|
|
|
|
- rshCommand += " " + userAtHost;
|
|
|
|
-# 326 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 327 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 328 "kind.ag"
|
|
|
|
- strings2File(excluded, imageFullName + "/exclude");
|
|
|
|
-# 329 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 330 "kind.ag"
|
|
|
|
- // rsync image
|
|
|
|
-# 331 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 332 "kind.ag"
|
|
|
|
- if (!remoteShell.empty())
|
|
|
|
-# 333 "kind.ag"
|
|
|
|
- rsyncCmd += " -e \'" + remoteShell + "\' ";
|
|
|
|
-# 334 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 335 "kind.ag"
|
|
|
|
- rsyncCmd += "--exclude-from=" + imageFullName + "/exclude ";
|
|
|
|
-# 336 "kind.ag"
|
|
|
|
- if (!referenceImage.empty())
|
|
|
|
-# 337 "kind.ag"
|
|
|
|
- rsyncCmd += "--link-dest=" + referenceImage + "/tree ";
|
|
|
|
-# 338 "kind.ag"
|
|
|
|
- rsyncCmd += userAtHost + ":" + path + " ";
|
|
|
|
-# 339 "kind.ag"
|
|
|
|
- rsyncCmd += imageFullName + "/tree";
|
|
|
|
-# 340 "kind.ag"
|
|
|
|
- } // shell mode
|
|
|
|
-# 341 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 342 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 343 "kind.ag"
|
|
|
|
- // cout << "USING SERVERMODE" << endl;
|
|
|
|
-# 344 "kind.ag"
|
|
|
|
- // we cannot use find without shell access
|
|
|
|
-# 345 "kind.ag"
|
|
|
|
- // and do not read an exclude file on client side
|
|
|
|
-# 346 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 347 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 348 "kind.ag"
|
|
|
|
- strings2File(excluded, imageFullName + "/exclude");
|
|
|
|
-# 349 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 350 "kind.ag"
|
|
|
|
- rsyncCmd += "--exclude-from=" + imageFullName + "/exclude ";
|
|
|
|
-# 351 "kind.ag"
|
|
|
|
- if (!referenceImage.empty())
|
|
|
|
-# 352 "kind.ag"
|
|
|
|
- rsyncCmd += "--link-dest=" + referenceImage + "/tree ";
|
|
|
|
-# 353 "kind.ag"
|
|
|
|
- rsyncCmd += conf.getString("server") + "::" + path + " ";
|
|
|
|
-# 354 "kind.ag"
|
|
|
|
- rsyncCmd += imageFullName + "/tree";
|
|
|
|
-# 355 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 356 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 357 "kind.ag"
|
|
|
|
- debugPrint("Action: " + rsyncCmd);
|
|
|
|
-# 358 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 359 "kind.ag"
|
|
|
|
- vector<string> backupResult;
|
|
|
|
-# 360 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 361 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 362 "kind.ag"
|
|
|
|
- verbosePrint("syncing (" + rsyncCmd + ")");
|
|
|
|
-# 363 "kind.ag"
|
|
|
|
- int rc;
|
|
|
|
-# 364 "kind.ag"
|
|
|
|
- backupResult = localExec(rsyncCmd, rc, debug, imageFullName + "/rsync-log");
|
|
|
|
-# 365 "kind.ag"
|
|
|
|
- if (rc == 0 ||
|
|
|
|
-# 366 "kind.ag"
|
|
|
|
- rc == 24 || // "no error" or "vanished source files" (ignored)
|
|
|
|
-# 367 "kind.ag"
|
|
|
|
- rc == 6144) // workaround for wrong exit code ??!!
|
|
|
|
-# 368 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 369 "kind.ag"
|
|
|
|
- unlink(errorfile.c_str());
|
|
|
|
-# 370 "kind.ag"
|
|
|
|
- double st = 0;
|
|
|
|
-# 371 "kind.ag"
|
|
|
|
- double sc = 0;
|
|
|
|
-# 372 "kind.ag"
|
|
|
|
- for (auto bl : backupResult)
|
|
|
|
-# 373 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 374 "kind.ag"
|
|
|
|
- if (startsWith(bl, "Total file size"))
|
|
|
|
-# 375 "kind.ag"
|
|
|
|
- st = getNumber(bl);
|
|
|
|
-# 376 "kind.ag"
|
|
|
|
- else if (startsWith(bl, "Total transferred file size"))
|
|
|
|
-# 377 "kind.ag"
|
|
|
|
- sc = getNumber(bl);
|
|
|
|
-# 378 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 379 "kind.ag"
|
|
|
|
- // sizes[vault] = pair<long int, long int>(st, sc);
|
|
|
|
-# 380 "kind.ag"
|
|
|
|
- sizes[vault] = Sizes(st, sc);
|
|
|
|
-# 381 "kind.ag"
|
|
|
|
- // cout << vault << " " << st << " || " << sc << endl;
|
|
|
|
-# 382 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 383 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 384 "kind.ag"
|
|
|
|
- throw Exception("Backup", "Failed to execute rsync (result: " + to_string(rc) + ")");
|
|
|
|
-# 385 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 386 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 387 "kind.ag"
|
|
|
|
- cout << "Not executing " << rsyncCmd << endl;
|
|
|
|
-# 388 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 389 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 390 "kind.ag"
|
|
|
|
-bool backupVault(const string& vault,
|
|
|
|
-# 391 "kind.ag"
|
|
|
|
- KindConfig conf /*Copy!*/ ,
|
|
|
|
-# 392 "kind.ag"
|
|
|
|
- const DateTime& imageTime,
|
|
|
|
-# 393 "kind.ag"
|
|
|
|
- bool fullImage,
|
|
|
|
-# 394 "kind.ag"
|
|
|
|
- const string& forcedBackupSet)
|
|
|
|
-# 395 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 396 "kind.ag"
|
|
|
|
- if (!quiet)
|
|
|
|
-# 397 "kind.ag"
|
|
|
|
- cout << DateTime::now().getString('h') << ": Backup of vault " << vault << endl;
|
|
|
|
-# 398 "kind.ag"
|
|
|
|
- try
|
|
|
|
-# 399 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 400 "kind.ag"
|
|
|
|
- readVaultConfig(vault, conf);
|
|
|
|
-# 401 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 402 "kind.ag"
|
|
|
|
- // where to store
|
|
|
|
-# 403 "kind.ag"
|
|
|
|
- string vaultPath = findVault(vault);
|
|
|
|
-# 404 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 405 "kind.ag"
|
|
|
|
- // image path
|
|
|
|
-# 406 "kind.ag"
|
|
|
|
- string imageFullName = getImageName(conf, vaultPath, imageTime);
|
|
|
|
-# 407 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 408 "kind.ag"
|
|
|
|
- bool backupNow = true;
|
|
|
|
-# 409 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 410 "kind.ag"
|
|
|
|
- // existing images
|
|
|
|
-# 411 "kind.ag"
|
|
|
|
- Images validImageList = findImages(vaultPath, conf, false);
|
|
|
|
-# 412 "kind.ag"
|
|
|
|
- string currentSet = "expire"; // we are not using backupSets
|
|
|
|
-# 413 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 414 "kind.ag"
|
|
|
|
- // check if we are using backup sets
|
|
|
|
-# 415 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 416 "kind.ag"
|
|
|
|
- map<string, int> setIdx;
|
|
|
|
-# 417 "kind.ag"
|
|
|
|
- vector<SetRule> backupSetRule;
|
|
|
|
-# 418 "kind.ag"
|
|
|
|
- int setRuleIdx = -1;
|
|
|
|
-# 419 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 420 "kind.ag"
|
|
|
|
- if (conf.hasKey("setRule"))
|
|
|
|
-# 421 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 422 "kind.ag"
|
|
|
|
- readSetRules(conf, setIdx, backupSetRule);
|
|
|
|
-# 423 "kind.ag"
|
|
|
|
- if (!setIdx.empty())
|
|
|
|
-# 424 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 425 "kind.ag"
|
|
|
|
- if (forcedBackupSet.empty())
|
|
|
|
-# 426 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 427 "kind.ag"
|
|
|
|
- backupNow = false;
|
|
|
|
-# 428 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 429 "kind.ag"
|
|
|
|
- // find time for nextBackup for every backupSet
|
|
|
|
-# 430 "kind.ag"
|
|
|
|
- // defaults to now == imageTime;
|
|
|
|
-# 431 "kind.ag"
|
|
|
|
- vector<DateTime> nextBackup(backupSetRule.size(), imageTime);
|
|
|
|
-# 432 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 433 "kind.ag"
|
|
|
|
- // find time for next backup
|
|
|
|
-# 434 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 435 "kind.ag"
|
|
|
|
- for (const Image& image : validImageList)
|
|
|
|
-# 436 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 437 "kind.ag"
|
|
|
|
- if (image.series != "expire")
|
|
|
|
-# 438 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 439 "kind.ag"
|
|
|
|
- string s = image.series;
|
|
|
|
-# 440 "kind.ag"
|
|
|
|
- if (setIdx.count(s) > 0) // rule for set exists?
|
|
|
|
-# 441 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 442 "kind.ag"
|
|
|
|
- int rIdx = setIdx[s];
|
|
|
|
-# 443 "kind.ag"
|
|
|
|
- // image is valid for this and "lower level" backupSets
|
|
|
|
-# 444 "kind.ag"
|
|
|
|
- for (unsigned int i = rIdx; i < backupSetRule.size(); ++i)
|
|
|
|
-# 445 "kind.ag"
|
|
|
|
- if (nextBackup[i] < image.time + backupSetRule[i].distance)
|
|
|
|
-# 446 "kind.ag"
|
|
|
|
- nextBackup[i] = image.time + backupSetRule[i].distance;
|
|
|
|
-# 447 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 448 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 449 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 450 "kind.ag"
|
|
|
|
- if (debug)
|
|
|
|
-# 451 "kind.ag"
|
|
|
|
- for (unsigned int i = 0; i < backupSetRule.size(); ++i)
|
|
|
|
-# 452 "kind.ag"
|
|
|
|
- cout << " Next backup for " << backupSetRule[i].name << " at " << nextBackup[i].getString('h') << endl;
|
|
|
|
-# 453 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 454 "kind.ag"
|
|
|
|
- // find backupSet that
|
|
|
|
-# 455 "kind.ag"
|
|
|
|
- // - needs backup
|
|
|
|
-# 456 "kind.ag"
|
|
|
|
- // - has longest time to keep
|
|
|
|
-# 457 "kind.ag"
|
|
|
|
- // because of ordered list backupSetRule this is the first set, that need
|
|
|
|
-# 458 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 459 "kind.ag"
|
|
|
|
- currentSet = "";
|
|
|
|
-# 460 "kind.ag"
|
|
|
|
- for (unsigned int i = 0; i < backupSetRule.size() && currentSet.empty(); ++i)
|
|
|
|
-# 461 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 462 "kind.ag"
|
|
|
|
- string name = backupSetRule[i].name;
|
|
|
|
-# 463 "kind.ag"
|
|
|
|
- if (nextBackup[i] <= imageTime + 5) // small offset of 5s for "jitter"
|
|
|
|
-# 464 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 465 "kind.ag"
|
|
|
|
- backupNow = true;
|
|
|
|
-# 466 "kind.ag"
|
|
|
|
- currentSet = name;
|
|
|
|
-# 467 "kind.ag"
|
|
|
|
- setRuleIdx = i;
|
|
|
|
-# 468 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 469 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 470 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 471 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 472 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 473 "kind.ag"
|
|
|
|
- if (setIdx.count(forcedBackupSet) > 0)
|
|
|
|
-# 474 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 475 "kind.ag"
|
|
|
|
- currentSet = forcedBackupSet;
|
|
|
|
-# 476 "kind.ag"
|
|
|
|
- setRuleIdx = setIdx[forcedBackupSet];
|
|
|
|
-# 477 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 478 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 479 "kind.ag"
|
|
|
|
- throw Exception("force backup of set " + forcedBackupSet, " set not exists");
|
|
|
|
-# 480 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 481 "kind.ag"
|
|
|
|
- } // if (!setIdx.empty())
|
|
|
|
-# 482 "kind.ag"
|
|
|
|
- } // (conf.hasKey("setRule"))
|
|
|
|
-# 483 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 484 "kind.ag"
|
|
|
|
- if (backupNow)
|
|
|
|
-# 485 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 486 "kind.ag"
|
|
|
|
- verbosePrint("backup to \"" + imageFullName + "\"");
|
|
|
|
-# 487 "kind.ag"
|
|
|
|
- if (setRuleIdx >= 0 && !quiet)
|
|
|
|
-# 488 "kind.ag"
|
|
|
|
- cout << " backup set is \"" << currentSet << "\"" << endl;
|
|
|
|
-# 489 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 490 "kind.ag"
|
|
|
|
- else if (!quiet)
|
|
|
|
-# 491 "kind.ag"
|
|
|
|
- cout << " no backup set needs update" << endl;
|
|
|
|
-# 492 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 493 "kind.ag"
|
|
|
|
- if (backupNow)
|
|
|
|
-# 494 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 495 "kind.ag"
|
|
|
|
- // find reference image
|
|
|
|
-# 496 "kind.ag"
|
|
|
|
- string referenceImage;
|
|
|
|
-# 497 "kind.ag"
|
|
|
|
- if (!fullImage)
|
|
|
|
-# 498 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 499 "kind.ag"
|
|
|
|
- if (validImageList.empty())
|
|
|
|
-# 500 "kind.ag"
|
|
|
|
- throw Exception("backupVault", "no reference image found");
|
|
|
|
-# 501 "kind.ag"
|
|
|
|
- // last image is newest image
|
|
|
|
-# 502 "kind.ag"
|
|
|
|
- referenceImage = validImageList.back().name;
|
|
|
|
-# 503 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 504 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 505 "kind.ag"
|
|
|
|
- doBackup(vault, imageFullName, referenceImage, conf);
|
|
|
|
-# 506 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 507 "kind.ag"
|
|
|
|
- if (!dryRun)
|
|
|
|
-# 508 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 509 "kind.ag"
|
|
|
|
- string lastPath = vaultPath + "/last";
|
|
|
|
-# 510 "kind.ag"
|
|
|
|
- struct stat fstat;
|
|
|
|
-# 511 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 512 "kind.ag"
|
|
|
|
- // remove last (dir or symlink)
|
|
|
|
-# 513 "kind.ag"
|
|
|
|
- if (lstat(lastPath.c_str(), &fstat) == 0) // last exists
|
|
|
|
-# 514 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 515 "kind.ag"
|
|
|
|
- if (S_ISDIR(fstat.st_mode))
|
|
|
|
-# 516 "kind.ag"
|
|
|
|
- removeDir(lastPath);
|
|
|
|
-# 517 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 518 "kind.ag"
|
|
|
|
- unlink(lastPath.c_str());
|
|
|
|
-# 519 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 520 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 521 "kind.ag"
|
|
|
|
- string linkType = conf.getString("lastLink");
|
|
|
|
-# 522 "kind.ag"
|
|
|
|
- if (linkType == "hardLink")
|
|
|
|
-# 523 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 524 "kind.ag"
|
|
|
|
- int rc;
|
|
|
|
-# 525 "kind.ag"
|
|
|
|
- string hardLinkCommand = "cp -al " + imageFullName + " " + lastPath;
|
|
|
|
-# 526 "kind.ag"
|
|
|
|
- Strings res = localExec(hardLinkCommand, rc, debug);
|
|
|
|
-# 527 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 528 "kind.ag"
|
|
|
|
- else if (linkType == "symLink")
|
|
|
|
-# 529 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 530 "kind.ag"
|
|
|
|
- // set symlink to last image
|
|
|
|
-# 531 "kind.ag"
|
|
|
|
- symlink(imageFullName.c_str(), lastPath.c_str());
|
|
|
|
-# 532 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 533 "kind.ag"
|
|
|
|
- else if (linkType != "null")
|
|
|
|
-# 534 "kind.ag"
|
|
|
|
- cerr << "invalid Value in \"lastLink\"" << endl;
|
|
|
|
-# 535 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 536 "kind.ag"
|
|
|
|
- // write expire date to file
|
|
|
|
-# 537 "kind.ag"
|
|
|
|
- DateTime expireTime;
|
|
|
|
-# 538 "kind.ag"
|
|
|
|
- string rule;
|
|
|
|
-# 539 "kind.ag"
|
|
|
|
- if (setRuleIdx < 0) // not backup set based
|
|
|
|
-# 540 "kind.ag"
|
|
|
|
- expireTime = getExpireDate(imageTime, conf, rule);
|
|
|
|
-# 541 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 542 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 543 "kind.ag"
|
|
|
|
- expireTime = imageTime + backupSetRule[setRuleIdx].keep;
|
|
|
|
-# 544 "kind.ag"
|
|
|
|
- rule = backupSetRule[setRuleIdx].rule;
|
|
|
|
-# 545 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 546 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 547 "kind.ag"
|
|
|
|
- ofstream expireFile(imageFullName + "/expires");
|
|
|
|
-# 548 "kind.ag"
|
|
|
|
- expireFile << currentSet << "-" << expireTime.getString('m') << endl;
|
|
|
|
-# 549 "kind.ag"
|
|
|
|
- expireFile << rule << endl;
|
|
|
|
-# 550 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 551 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 552 "kind.ag"
|
|
|
|
- return backupNow;
|
|
|
|
-# 553 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 554 "kind.ag"
|
|
|
|
- catch (Exception ex)
|
|
|
|
-# 555 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 556 "kind.ag"
|
|
|
|
- cerr << "Exception in vault " << vault << ": " << ex.what() << endl;
|
|
|
|
-# 557 "kind.ag"
|
|
|
|
- return false;
|
|
|
|
-# 558 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 559 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 560 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 561 "kind.ag"
|
|
|
|
-void expireVault(const string& vault, KindConfig conf, DateTime now)
|
|
|
|
-# 562 "kind.ag"
|
|
|
|
-{
|
|
|
|
-# 563 "kind.ag"
|
|
|
|
- if (!quiet)
|
|
|
|
-# 564 "kind.ag"
|
|
|
|
- cout << DateTime::now().getString('h') << ": Expiring images in vault " << vault << endl;
|
|
|
|
-# 565 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 566 "kind.ag"
|
|
|
|
- readVaultConfig(vault, conf);
|
|
|
|
-# 567 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 568 "kind.ag"
|
|
|
|
- string vaultpath = findVault(vault);
|
|
|
|
-# 569 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 570 "kind.ag"
|
|
|
|
- Images imagelist = findImages(vaultpath, conf, true);
|
|
|
|
-# 571 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 572 "kind.ag"
|
|
|
|
- string lastValidImage;
|
|
|
|
-# 573 "kind.ag"
|
|
|
|
- for (Image image : imagelist)
|
|
|
|
-# 574 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 575 "kind.ag"
|
|
|
|
- if (image.valid)
|
|
|
|
-# 576 "kind.ag"
|
|
|
|
- lastValidImage = image.name;
|
|
|
|
-# 577 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 578 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 579 "kind.ag"
|
|
|
|
- for (Image image : imagelist)
|
|
|
|
-# 580 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 581 "kind.ag"
|
|
|
|
- if (debug)
|
|
|
|
-# 582 "kind.ag"
|
|
|
|
- image.printInfo();
|
|
|
|
-# 583 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 584 "kind.ag"
|
|
|
|
- DateTime imageTime = image.time;
|
|
|
|
-# 585 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 586 "kind.ag"
|
|
|
|
- if (imageTime != now && // ignore just created image
|
|
|
|
-# 587 "kind.ag"
|
|
|
|
- image.name != lastValidImage // ignore last valid image
|
|
|
|
-# 588 "kind.ag"
|
|
|
|
- )
|
|
|
|
-# 589 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 590 "kind.ag"
|
|
|
|
- DateTime expireTime;
|
|
|
|
-# 591 "kind.ag"
|
|
|
|
- string expireRule;
|
|
|
|
-# 592 "kind.ag"
|
|
|
|
- if (!image.valid) // invalid image?
|
|
|
|
-# 593 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 594 "kind.ag"
|
|
|
|
- time_t expPeriod = stot(conf.getString("expireFailedImage"));
|
|
|
|
-# 595 "kind.ag"
|
|
|
|
- if (expPeriod < 0)
|
|
|
|
-# 596 "kind.ag"
|
|
|
|
- throw Exception("expireFailedImage", "Time period must be positive");
|
|
|
|
-# 597 "kind.ag"
|
|
|
|
- expireTime = imageTime + stot(conf.getString("expireFailedImage"));
|
|
|
|
-# 598 "kind.ag"
|
|
|
|
- expireRule = "invalid image: " + conf.getString("expireFailedImage");
|
|
|
|
-# 599 "kind.ag"
|
|
|
|
- debugPrint("- invalid image");
|
|
|
|
-# 600 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 601 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 602 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 603 "kind.ag"
|
|
|
|
- debugPrint("- valid image");
|
|
|
|
-# 604 "kind.ag"
|
|
|
|
- expireTime = image.expire;
|
|
|
|
-# 605 "kind.ag"
|
|
|
|
- expireRule = image.expireRule;
|
|
|
|
-# 606 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 607 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 608 "kind.ag"
|
|
|
|
- if (expireTime < now)
|
|
|
|
-# 609 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 610 "kind.ag"
|
|
|
|
- if (!quiet)
|
|
|
|
-# 611 "kind.ag"
|
|
|
|
- cout << " removing image " << image.name << endl;
|
|
|
|
-# 612 "kind.ag"
|
|
|
|
- try
|
|
|
|
-# 613 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 614 "kind.ag"
|
|
|
|
- if (removeDir(image.name) != 0)
|
|
|
|
-# 615 "kind.ag"
|
|
|
|
- cout << "Error removing " << image.name << endl;
|
|
|
|
-# 616 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 617 "kind.ag"
|
|
|
|
- catch (Exception ex)
|
|
|
|
-# 618 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 619 "kind.ag"
|
|
|
|
- cerr << "Exception: " << ex.what() << endl;
|
|
|
|
-# 620 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 621 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 622 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 623 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 624 "kind.ag"
|
|
|
|
- debugPrint("- current image - ignored");
|
|
|
|
-# 625 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 626 "kind.ag"
|
|
|
|
-}
|
|
|
|
-# 627 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 628 "kind.ag"
|
|
|
|
-/*AppGen:Main*/
|
|
|
|
-string ag_programName;
|
|
|
|
-
|
|
|
|
-void usage()
|
|
|
|
-{
|
|
|
|
- cout << ag_programName << " - archiving backup" << endl;
|
|
|
|
- cout << "Usage:" << endl;
|
|
|
|
- cout << ag_programName << " [<options>] vault_or_group " << endl;
|
|
|
|
- cout << " vault_or_group - Vault to backup" << endl;
|
|
|
|
- cout << "Options:" << endl;
|
|
|
|
- cout << " -c <s> --masterconfig=<s>" << endl;
|
|
|
|
- cout << " Master config file (default: \"\")" << endl;
|
|
|
|
-
|
|
|
|
- cout << " if not given or empty kind looks for" << endl;
|
|
|
|
- cout << " /etc/kind/master.conf" << endl;
|
|
|
|
- cout << " /ffp/etc/kind/master.conf" << endl;
|
|
|
|
- cout << " -f --full= " << endl;
|
|
|
|
- cout << " Force full image == initial backup (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -B --backup= " << endl;
|
|
|
|
- cout << " Backup (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -E --expire= " << endl;
|
|
|
|
- cout << " Expire (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -C --listconfig= " << endl;
|
|
|
|
- cout << " Show configuration (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -I --listimages= " << endl;
|
|
|
|
- cout << " List data of images (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " if none of backup, expire, listconfig and listimages is specified," << endl;
|
|
|
|
- cout << " backup and expire is assumed." << endl;
|
|
|
|
- cout << " listconfig and listimages cannot be combined with other actions" << endl;
|
|
|
|
- cout << " -D --dryrun= " << endl;
|
|
|
|
- cout << " Dry run (no real backup) (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -F <s> --forcebackup=<s>" << endl;
|
|
|
|
- cout << " Create image for specified backup set (default: \"\")" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -v --verbose= " << endl;
|
|
|
|
- cout << " Verbose (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -d --debug= " << endl;
|
|
|
|
- cout << " Debug output of many data (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -q --quiet= " << endl;
|
|
|
|
- cout << " Be quiet - no messages (default: false)" << endl;
|
|
|
|
-
|
|
|
|
- cout << " -h --help= " << endl;
|
|
|
|
- cout << " This help" << endl;
|
|
|
|
-
|
|
|
|
- exit(1);
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-void error(const string &msg)
|
|
|
|
-{
|
|
|
|
- cout << endl << ag_programName << " - error: " << msg << endl << endl;
|
|
|
|
- usage();
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-int ptoi(const char *para)
|
|
|
|
-{
|
|
|
|
- char *end;
|
|
|
|
- int res = strtol(para, &end, 10);
|
|
|
|
- if (end == para)
|
|
|
|
- error(string("no int: ") + para);
|
|
|
|
- if (*end != 0)
|
|
|
|
- error(string("garbage in int: ") + para);
|
|
|
|
- return res;
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-double ptod(const char *para)
|
|
|
|
-{
|
|
|
|
- char *end;
|
|
|
|
- double res = strtod(para, &end);
|
|
|
|
- if (end == para)
|
|
|
|
- error(string("no double: ") + para);
|
|
|
|
- if (*end != 0)
|
|
|
|
- error(string("garbage in double: ") + para);
|
|
|
|
- return res;
|
|
|
|
-}
|
|
|
|
-
|
|
|
|
-int main(int argc, char **argv)
|
|
|
|
-{
|
|
|
|
-string masterConfig = "";
|
|
|
|
-bool fullImage = false;
|
|
|
|
-bool doBackup = false;
|
|
|
|
-bool doExpire = false;
|
|
|
|
-bool listConfig = false;
|
|
|
|
-bool listImages = false;
|
|
|
|
-string forcedBackupSet = "";
|
|
|
|
-
|
|
|
|
-string vault = "";
|
|
|
|
- static struct option ag_long_options[] =
|
|
|
|
- {
|
|
|
|
- {"masterconfig", required_argument, 0, 'c' },
|
|
|
|
- {"full", no_argument, 0, 'f' },
|
|
|
|
- {"backup", no_argument, 0, 'B' },
|
|
|
|
- {"expire", no_argument, 0, 'E' },
|
|
|
|
- {"listconfig", no_argument, 0, 'C' },
|
|
|
|
- {"listimages", no_argument, 0, 'I' },
|
|
|
|
- {"dryrun", no_argument, 0, 'D' },
|
|
|
|
- {"forcebackup", required_argument, 0, 'F' },
|
|
|
|
- {"verbose", no_argument, 0, 'v' },
|
|
|
|
- {"debug", no_argument, 0, 'd' },
|
|
|
|
- {"quiet", no_argument, 0, 'q' },
|
|
|
|
- {"help", no_argument, 0, 'h' },
|
|
|
|
- {0, 0, 0, 0 }
|
|
|
|
- };
|
|
|
|
- ag_programName = argv[0];
|
|
|
|
- int rc;
|
|
|
|
- opterr = 0;
|
|
|
|
- while ((rc = getopt_long(argc, argv, ":c:fBECIDF:vdqh", ag_long_options, NULL)) >= 0)
|
|
|
|
- {
|
|
|
|
- switch (rc)
|
|
|
|
- {
|
|
|
|
- case '?':
|
|
|
|
- error("Unknown option");
|
|
|
|
- break;
|
|
|
|
- case ':':
|
|
|
|
- error("Expecting option parameter");
|
|
|
|
- break;
|
|
|
|
- case 'c':
|
|
|
|
- masterConfig = optarg;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'f':
|
|
|
|
- fullImage = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'B':
|
|
|
|
- doBackup = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'E':
|
|
|
|
- doExpire = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'C':
|
|
|
|
- listConfig = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'I':
|
|
|
|
- listImages = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'D':
|
|
|
|
- dryRun = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'F':
|
|
|
|
- forcedBackupSet = optarg;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'v':
|
|
|
|
- verbose = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'd':
|
|
|
|
- debug = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'q':
|
|
|
|
- quiet = true;
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- case 'h':
|
|
|
|
- usage();
|
|
|
|
- break;
|
|
|
|
-
|
|
|
|
- default:
|
|
|
|
- error("error in options");
|
|
|
|
- }
|
|
|
|
- }
|
|
|
|
- if (optind < argc)
|
|
|
|
- vault = argv[optind++];
|
|
|
|
- else error("Parameter vault_or_group needed");
|
|
|
|
-
|
|
|
|
-/*AppGen:MainEnd*/
|
|
|
|
-# 632 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 633 "kind.ag"
|
|
|
|
- int exitCode = 0;
|
|
|
|
-# 634 "kind.ag"
|
|
|
|
- string lockFile;
|
|
|
|
-# 635 "kind.ag"
|
|
|
|
- try
|
|
|
|
-# 636 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 637 "kind.ag"
|
|
|
|
- // handling of parameters and switches
|
|
|
|
-# 638 "kind.ag"
|
|
|
|
- if (debug) // debug implies verbose
|
|
|
|
-# 639 "kind.ag"
|
|
|
|
- verbose = true;
|
|
|
|
-# 640 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 641 "kind.ag"
|
|
|
|
- if (!doBackup && !doExpire && !listConfig && !listImages)
|
|
|
|
-# 642 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 643 "kind.ag"
|
|
|
|
- doBackup = true;
|
|
|
|
-# 644 "kind.ag"
|
|
|
|
- doExpire = true;
|
|
|
|
-# 645 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 646 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 647 "kind.ag"
|
|
|
|
- KindConfig conf;
|
|
|
|
-# 648 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 649 "kind.ag"
|
|
|
|
- // default-values
|
|
|
|
-# 650 "kind.ag"
|
|
|
|
- conf.add("imageName", "image");
|
|
|
|
-# 651 "kind.ag"
|
|
|
|
- conf.add("vaultConfigName", "kind/vault.conf");
|
|
|
|
-# 652 "kind.ag"
|
|
|
|
- conf.add("expireFailedImage", "3 days");
|
|
|
|
-# 653 "kind.ag"
|
|
|
|
- conf.add("expireRule", "* * * * 1 month");
|
|
|
|
-# 654 "kind.ag"
|
|
|
|
- conf.add("ping", "ping -c 1 -W 5 %host");
|
|
|
|
-# 655 "kind.ag"
|
|
|
|
- conf.add("rsyncOption", ""); // no additional rsync option
|
|
|
|
-# 656 "kind.ag"
|
|
|
|
- conf.add("remoteShell", "");
|
|
|
|
-# 657 "kind.ag"
|
|
|
|
- conf.add("lockfile", "/var/lock/kind");
|
|
|
|
-# 658 "kind.ag"
|
|
|
|
- conf.add("userExcludeFile", "nobackup.list");
|
|
|
|
-# 659 "kind.ag"
|
|
|
|
- conf.add("userExcludeCommand",
|
|
|
|
-# 660 "kind.ag"
|
|
|
|
- "find %path -type f -iname '*nobackup' -printf '%P\\\\n'");
|
|
|
|
-# 661 "kind.ag"
|
|
|
|
- conf.add("logSize", "");
|
|
|
|
-# 662 "kind.ag"
|
|
|
|
- conf.add("lastLink", "symLink");
|
|
|
|
-# 663 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 664 "kind.ag"
|
|
|
|
- if (listConfig)
|
|
|
|
-# 665 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 666 "kind.ag"
|
|
|
|
- cout << "builtin config" << endl;
|
|
|
|
-# 667 "kind.ag"
|
|
|
|
- conf.print(". ");
|
|
|
|
-# 668 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 669 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 670 "kind.ag"
|
|
|
|
- readMasterConfig(masterConfig, conf);
|
|
|
|
-# 671 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 672 "kind.ag"
|
|
|
|
- banks = conf.getStrings("bank");
|
|
|
|
-# 673 "kind.ag"
|
|
|
|
- if (banks.empty())
|
|
|
|
-# 674 "kind.ag"
|
|
|
|
- throw Exception("read master configuration", "no banks defined");
|
|
|
|
-# 675 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 676 "kind.ag"
|
|
|
|
- if (listConfig)
|
|
|
|
-# 677 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 678 "kind.ag"
|
|
|
|
- cout << "global config:" << endl;
|
|
|
|
-# 679 "kind.ag"
|
|
|
|
- conf.print(". ");
|
|
|
|
-# 680 "kind.ag"
|
|
|
|
- readVaultConfig(vault, conf);
|
|
|
|
-# 681 "kind.ag"
|
|
|
|
- cout << "vault config:" << endl;
|
|
|
|
-# 682 "kind.ag"
|
|
|
|
- conf.print(". ");
|
|
|
|
-# 683 "kind.ag"
|
|
|
|
- exit(0);
|
|
|
|
-# 684 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 685 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 686 "kind.ag"
|
|
|
|
- DateTime imageTime = DateTime::now();
|
|
|
|
-# 687 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 688 "kind.ag"
|
|
|
|
- if (listImages)
|
|
|
|
-# 689 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 690 "kind.ag"
|
|
|
|
- listImageInfo(vault, conf, imageTime, forcedBackupSet);
|
|
|
|
-# 691 "kind.ag"
|
|
|
|
- exit(0);
|
|
|
|
-# 692 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 693 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 694 "kind.ag"
|
|
|
|
- lockFile = conf.getString("lockfile");
|
|
|
|
-# 695 "kind.ag"
|
|
|
|
- createLock(lockFile);
|
|
|
|
-# 696 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 697 "kind.ag"
|
|
|
|
- string logSizeFile = conf.getString("logSize");
|
|
|
|
-# 698 "kind.ag"
|
|
|
|
- readSizes(logSizeFile);
|
|
|
|
-# 699 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 700 "kind.ag"
|
|
|
|
- vector<string> vaults;
|
|
|
|
-# 701 "kind.ag"
|
|
|
|
- string groupname = "group_" + vault;
|
|
|
|
-# 702 "kind.ag"
|
|
|
|
- if (conf.hasKey(groupname))
|
|
|
|
-# 703 "kind.ag"
|
|
|
|
- vaults = conf.getStrings(groupname);
|
|
|
|
-# 704 "kind.ag"
|
|
|
|
- else
|
|
|
|
-# 705 "kind.ag"
|
|
|
|
- vaults.push_back(vault);
|
|
|
|
-# 706 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 707 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 708 "kind.ag"
|
|
|
|
- for (string vault : vaults)
|
|
|
|
-# 709 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 710 "kind.ag"
|
|
|
|
- if (doBackup)
|
|
|
|
-# 711 "kind.ag"
|
|
|
|
- if (backupVault(vault, conf, imageTime, fullImage, forcedBackupSet))
|
|
|
|
-# 712 "kind.ag"
|
|
|
|
- writeSizes(logSizeFile);
|
|
|
|
-# 713 "kind.ag"
|
|
|
|
- if (doExpire)
|
|
|
|
-# 714 "kind.ag"
|
|
|
|
- expireVault(vault, conf, imageTime);
|
|
|
|
-# 715 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 716 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 717 "kind.ag"
|
|
|
|
- if (!quiet)
|
|
|
|
-# 718 "kind.ag"
|
|
|
|
- cout << DateTime::now().getString('h') << ": finished" << endl;
|
|
|
|
-# 719 "kind.ag"
|
|
|
|
-
|
|
|
|
-# 720 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 721 "kind.ag"
|
|
|
|
- catch (const Exception& ex)
|
|
|
|
-# 722 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 723 "kind.ag"
|
|
|
|
- cerr << "Exception: " << ex.what() << endl;
|
|
|
|
-# 724 "kind.ag"
|
|
|
|
- exitCode = 1;
|
|
|
|
-# 725 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 726 "kind.ag"
|
|
|
|
- catch (const char* msg)
|
|
|
|
-# 727 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 728 "kind.ag"
|
|
|
|
- cerr << "Exception(char*): " << msg << endl;
|
|
|
|
-# 729 "kind.ag"
|
|
|
|
- exitCode = 1;
|
|
|
|
-# 730 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 731 "kind.ag"
|
|
|
|
- catch (const string& msg)
|
|
|
|
-# 732 "kind.ag"
|
|
|
|
- {
|
|
|
|
-# 733 "kind.ag"
|
|
|
|
- cerr << "Exception(string): " << msg << endl;
|
|
|
|
-# 734 "kind.ag"
|
|
|
|
- exitCode = 1;
|
|
|
|
-# 735 "kind.ag"
|
|
|
|
- }
|
|
|
|
-# 736 "kind.ag"
|
|
|
|
- removeLock(lockFile);
|
|
|
|
-# 737 "kind.ag"
|
|
|
|
- return exitCode;
|
|
|
|
-# 738 "kind.ag"
|
|
|
|
-}
|
|
|