From 526b749d1da0c163ad04bf9dd9676cda5405167d Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Fri, 4 Mar 2016 23:12:41 +0100 Subject: [PATCH 1/6] Add a command line option for blocksize --- src/cryfs-cli/Cli.cpp | 8 ++-- src/cryfs-cli/Cli.h | 2 +- src/cryfs-cli/program_options/Parser.cpp | 9 ++++- .../program_options/ProgramOptions.cpp | 8 +++- .../program_options/ProgramOptions.h | 3 ++ src/cryfs/config/CryConfigCreator.cpp | 13 +++++-- src/cryfs/config/CryConfigCreator.h | 4 +- src/cryfs/config/CryConfigLoader.cpp | 6 +-- src/cryfs/config/CryConfigLoader.h | 3 +- .../program_options/ProgramOptionsTest.cpp | 38 ++++++++++++------- test/cryfs/config/CryConfigCreatorTest.cpp | 34 +++++++++++------ test/cryfs/config/CryConfigLoaderTest.cpp | 2 +- test/cryfs/filesystem/CryFsTest.cpp | 2 +- test/cryfs/filesystem/FileSystemTest.cpp | 2 +- 14 files changed, 87 insertions(+), 47 deletions(-) diff --git a/src/cryfs-cli/Cli.cpp b/src/cryfs-cli/Cli.cpp index 32998881..1a1adf4d 100644 --- a/src/cryfs-cli/Cli.cpp +++ b/src/cryfs-cli/Cli.cpp @@ -193,7 +193,7 @@ namespace cryfs { CryConfigFile Cli::_loadOrCreateConfig(const ProgramOptions &options) { try { auto configFile = _determineConfigFile(options); - auto config = _loadOrCreateConfigFile(configFile, options.cipher()); + auto config = _loadOrCreateConfigFile(configFile, options.cipher(), options.blocksizeBytes()); if (config == none) { std::cerr << "Could not load config file. Did you enter the correct password?" << std::endl; exit(1); @@ -205,17 +205,17 @@ namespace cryfs { } } - optional Cli::_loadOrCreateConfigFile(const bf::path &configFilePath, const optional &cipher) { + optional Cli::_loadOrCreateConfigFile(const bf::path &configFilePath, const optional &cipher, const optional &blocksizeBytes) { if (_noninteractive) { return CryConfigLoader(_console, _keyGenerator, _scryptSettings, &Cli::_askPasswordNoninteractive, &Cli::_askPasswordNoninteractive, - cipher, _noninteractive).loadOrCreate(configFilePath); + cipher, blocksizeBytes, _noninteractive).loadOrCreate(configFilePath); } else { return CryConfigLoader(_console, _keyGenerator, _scryptSettings, &Cli::_askPasswordForExistingFilesystem, &Cli::_askPasswordForNewFilesystem, - cipher, _noninteractive).loadOrCreate(configFilePath); + cipher, blocksizeBytes, _noninteractive).loadOrCreate(configFilePath); } } diff --git a/src/cryfs-cli/Cli.h b/src/cryfs-cli/Cli.h index ee9919a7..9a837a9d 100644 --- a/src/cryfs-cli/Cli.h +++ b/src/cryfs-cli/Cli.h @@ -22,7 +22,7 @@ namespace cryfs { void _checkForUpdates(); void _runFilesystem(const program_options::ProgramOptions &options); CryConfigFile _loadOrCreateConfig(const program_options::ProgramOptions &options); - boost::optional _loadOrCreateConfigFile(const boost::filesystem::path &configFilePath, const boost::optional &cipher); + boost::optional _loadOrCreateConfigFile(const boost::filesystem::path &configFilePath, const boost::optional &cipher, const boost::optional &blocksizeBytes); boost::filesystem::path _determineConfigFile(const program_options::ProgramOptions &options); static std::string _askPasswordForExistingFilesystem(); static std::string _askPasswordForNewFilesystem(); diff --git a/src/cryfs-cli/program_options/Parser.cpp b/src/cryfs-cli/program_options/Parser.cpp index 6a8dc999..8ca9c994 100644 --- a/src/cryfs-cli/program_options/Parser.cpp +++ b/src/cryfs-cli/program_options/Parser.cpp @@ -62,8 +62,12 @@ ProgramOptions Parser::parse(const vector &supportedCiphers) const { cipher = vm["cipher"].as(); _checkValidCipher(*cipher, supportedCiphers); } + optional blocksizeBytes = none; + if (vm.count("blocksize-bytes")) { + blocksizeBytes = vm["blocksize-bytes"].as(); + } - return ProgramOptions(baseDir, mountDir, configfile, foreground, unmountAfterIdleMinutes, logfile, cipher, options.second); + return ProgramOptions(baseDir, mountDir, configfile, foreground, unmountAfterIdleMinutes, logfile, cipher, blocksizeBytes, options.second); } void Parser::_checkValidCipher(const string &cipher, const vector &supportedCiphers) { @@ -108,7 +112,8 @@ void Parser::_addAllowedOptions(po::options_description *desc) { ("help,h", "show help message") ("config,c", po::value(), "Configuration file") ("foreground,f", "Run CryFS in foreground.") - ("cipher", po::value(), "Cipher to use for encryption. See possible values by calling cryfs with --show-ciphers") + ("cipher", po::value(), "Cipher to use for encryption. See possible values by calling cryfs with --show-ciphers.") + ("blocksize-bytes", po::value(), "The block size used when storing ciphertext blocks (in bytes).") ("show-ciphers", "Show list of supported ciphers.") ("unmount-idle", po::value(), "Automatically unmount after specified number of idle minutes.") ("logfile", po::value(), "Specify the file to write log messages to. If this is not specified, log messages will go to stdout, or syslog if CryFS is running in the background.") diff --git a/src/cryfs-cli/program_options/ProgramOptions.cpp b/src/cryfs-cli/program_options/ProgramOptions.cpp index 4f8c7107..ee9fdaf2 100644 --- a/src/cryfs-cli/program_options/ProgramOptions.cpp +++ b/src/cryfs-cli/program_options/ProgramOptions.cpp @@ -11,9 +11,11 @@ namespace bf = boost::filesystem; ProgramOptions::ProgramOptions(const bf::path &baseDir, const bf::path &mountDir, const optional &configFile, bool foreground, const optional &unmountAfterIdleMinutes, const optional &logFile, const optional &cipher, + const optional &blocksizeBytes, const vector &fuseOptions) :_baseDir(baseDir), _mountDir(nullptr), _configFile(configFile), _foreground(foreground), - _cipher(cipher), _unmountAfterIdleMinutes(unmountAfterIdleMinutes), _logFile(logFile), _fuseOptions(fuseOptions) { + _cipher(cipher), _blocksizeBytes(blocksizeBytes), _unmountAfterIdleMinutes(unmountAfterIdleMinutes), + _logFile(logFile), _fuseOptions(fuseOptions) { string mountDirStr = mountDir.native(); _mountDir = new char[mountDirStr.size()+1]; @@ -65,6 +67,10 @@ const optional &ProgramOptions::cipher() const { return _cipher; } +const optional &ProgramOptions::blocksizeBytes() const { + return _blocksizeBytes; +} + const vector &ProgramOptions::fuseOptions() const { return _fuseOptions; } diff --git a/src/cryfs-cli/program_options/ProgramOptions.h b/src/cryfs-cli/program_options/ProgramOptions.h index 910b608e..29dfbf53 100644 --- a/src/cryfs-cli/program_options/ProgramOptions.h +++ b/src/cryfs-cli/program_options/ProgramOptions.h @@ -17,6 +17,7 @@ namespace cryfs { bool foreground, const boost::optional &unmountAfterIdleMinutes, const boost::optional &logFile, const boost::optional &cipher, + const boost::optional &blocksizeBytes, const std::vector &fuseOptions); ProgramOptions(ProgramOptions &&rhs); ~ProgramOptions(); @@ -26,6 +27,7 @@ namespace cryfs { const boost::optional &configFile() const; bool foreground() const; const boost::optional &cipher() const; + const boost::optional &blocksizeBytes() const; const boost::optional &unmountAfterIdleMinutes() const; const boost::optional &logFile() const; const std::vector &fuseOptions() const; @@ -36,6 +38,7 @@ namespace cryfs { boost::optional _configFile; bool _foreground; boost::optional _cipher; + boost::optional _blocksizeBytes; boost::optional _unmountAfterIdleMinutes; boost::optional _logFile; std::vector _fuseOptions; diff --git a/src/cryfs/config/CryConfigCreator.cpp b/src/cryfs/config/CryConfigCreator.cpp index 34fa3041..6cf01867 100644 --- a/src/cryfs/config/CryConfigCreator.cpp +++ b/src/cryfs/config/CryConfigCreator.cpp @@ -17,18 +17,23 @@ namespace cryfs { :_console(console), _configConsole(console, noninteractive), _encryptionKeyGenerator(encryptionKeyGenerator) { } - CryConfig CryConfigCreator::create(const optional &cipherFromCommandLine) { + CryConfig CryConfigCreator::create(const optional &cipherFromCommandLine, const optional &blocksizeBytesFromCommandLine) { CryConfig config; config.SetCipher(_generateCipher(cipherFromCommandLine)); config.SetVersion(gitversion::VersionString()); - config.SetBlocksizeBytes(_generateBlocksizeBytes()); + config.SetBlocksizeBytes(_generateBlocksizeBytes(blocksizeBytesFromCommandLine)); config.SetRootBlob(_generateRootBlobKey()); config.SetEncryptionKey(_generateEncKey(config.Cipher())); return config; } - uint32_t CryConfigCreator::_generateBlocksizeBytes() { - return _configConsole.askBlocksizeBytes(); + uint32_t CryConfigCreator::_generateBlocksizeBytes(const optional &blocksizeBytesFromCommandLine) { + if (blocksizeBytesFromCommandLine != none) { + // TODO Check block size is valid (i.e. large enough) + return *blocksizeBytesFromCommandLine; + } else { + return _configConsole.askBlocksizeBytes(); + } } string CryConfigCreator::_generateCipher(const optional &cipherFromCommandLine) { diff --git a/src/cryfs/config/CryConfigCreator.h b/src/cryfs/config/CryConfigCreator.h index c3c57b27..867b9598 100644 --- a/src/cryfs/config/CryConfigCreator.h +++ b/src/cryfs/config/CryConfigCreator.h @@ -14,12 +14,12 @@ namespace cryfs { CryConfigCreator(std::shared_ptr console, cpputils::RandomGenerator &encryptionKeyGenerator, bool noninteractive); CryConfigCreator(CryConfigCreator &&rhs) = default; - CryConfig create(const boost::optional &cipherFromCommandLine); + CryConfig create(const boost::optional &cipherFromCommandLine, const boost::optional &blocksizeBytesFromCommandLine); private: std::string _generateCipher(const boost::optional &cipherFromCommandLine); std::string _generateEncKey(const std::string &cipher); std::string _generateRootBlobKey(); - uint32_t _generateBlocksizeBytes(); + uint32_t _generateBlocksizeBytes(const boost::optional &blocksizeBytesFromCommandLine); std::shared_ptr _console; CryConfigConsole _configConsole; diff --git a/src/cryfs/config/CryConfigLoader.cpp b/src/cryfs/config/CryConfigLoader.cpp index 6a3fc90b..819f0fbe 100644 --- a/src/cryfs/config/CryConfigLoader.cpp +++ b/src/cryfs/config/CryConfigLoader.cpp @@ -25,10 +25,10 @@ using namespace cpputils::logging; namespace cryfs { -CryConfigLoader::CryConfigLoader(shared_ptr console, RandomGenerator &keyGenerator, const SCryptSettings &scryptSettings, function askPasswordForExistingFilesystem, function askPasswordForNewFilesystem, const optional &cipherFromCommandLine, bool noninteractive) +CryConfigLoader::CryConfigLoader(shared_ptr console, RandomGenerator &keyGenerator, const SCryptSettings &scryptSettings, function askPasswordForExistingFilesystem, function askPasswordForNewFilesystem, const optional &cipherFromCommandLine, const boost::optional &blocksizeBytesFromCommandLine, bool noninteractive) : _creator(std::move(console), keyGenerator, noninteractive), _scryptSettings(scryptSettings), _askPasswordForExistingFilesystem(askPasswordForExistingFilesystem), _askPasswordForNewFilesystem(askPasswordForNewFilesystem), - _cipherFromCommandLine(cipherFromCommandLine) { + _cipherFromCommandLine(cipherFromCommandLine), _blocksizeBytesFromCommandLine(blocksizeBytesFromCommandLine) { } optional CryConfigLoader::_loadConfig(const bf::path &filename) { @@ -66,7 +66,7 @@ optional CryConfigLoader::loadOrCreate(const bf::path &filename) } CryConfigFile CryConfigLoader::_createConfig(const bf::path &filename) { - auto config = _creator.create(_cipherFromCommandLine); + auto config = _creator.create(_cipherFromCommandLine, _blocksizeBytesFromCommandLine); //TODO Ask confirmation if using insecure password (<8 characters) string password = _askPasswordForNewFilesystem(); std::cout << "Creating config file (this can take some time)..." << std::flush; diff --git a/src/cryfs/config/CryConfigLoader.h b/src/cryfs/config/CryConfigLoader.h index 4eb97450..4741d9e2 100644 --- a/src/cryfs/config/CryConfigLoader.h +++ b/src/cryfs/config/CryConfigLoader.h @@ -13,7 +13,7 @@ namespace cryfs { class CryConfigLoader final { public: - CryConfigLoader(std::shared_ptr console, cpputils::RandomGenerator &keyGenerator, const cpputils::SCryptSettings &scryptSettings, std::function askPasswordForExistingFilesystem, std::function askPasswordForNewFilesystem, const boost::optional &cipherFromCommandLine, bool noninteractive); + CryConfigLoader(std::shared_ptr console, cpputils::RandomGenerator &keyGenerator, const cpputils::SCryptSettings &scryptSettings, std::function askPasswordForExistingFilesystem, std::function askPasswordForNewFilesystem, const boost::optional &cipherFromCommandLine, const boost::optional &blocksizeBytesFromCommandLine, bool noninteractive); CryConfigLoader(CryConfigLoader &&rhs) = default; boost::optional loadOrCreate(const boost::filesystem::path &filename); @@ -29,6 +29,7 @@ private: std::function _askPasswordForExistingFilesystem; std::function _askPasswordForNewFilesystem; boost::optional _cipherFromCommandLine; + boost::optional _blocksizeBytesFromCommandLine; DISALLOW_COPY_AND_ASSIGN(CryConfigLoader); }; diff --git a/test/cryfs-cli/program_options/ProgramOptionsTest.cpp b/test/cryfs-cli/program_options/ProgramOptionsTest.cpp index d3cba542..3fbd58d5 100644 --- a/test/cryfs-cli/program_options/ProgramOptionsTest.cpp +++ b/test/cryfs-cli/program_options/ProgramOptionsTest.cpp @@ -23,73 +23,83 @@ namespace boost { class ProgramOptionsTest: public ProgramOptionsTestBase {}; TEST_F(ProgramOptionsTest, BaseDir) { - ProgramOptions testobj("/home/user/mydir", "", none, false, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("/home/user/mydir", "", none, false, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ("/home/user/mydir", testobj.baseDir()); } TEST_F(ProgramOptionsTest, MountDir) { - ProgramOptions testobj("", "/home/user/mydir", none, false, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "/home/user/mydir", none, false, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ("/home/user/mydir", testobj.mountDir()); } TEST_F(ProgramOptionsTest, ConfigfileNone) { - ProgramOptions testobj("", "", none, true, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ(none, testobj.configFile()); } TEST_F(ProgramOptionsTest, ConfigfileSome) { - ProgramOptions testobj("", "", bf::path("/home/user/configfile"), true, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", bf::path("/home/user/configfile"), true, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ("/home/user/configfile", testobj.configFile().get()); } TEST_F(ProgramOptionsTest, ForegroundFalse) { - ProgramOptions testobj("", "", none, false, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, false, none, none, none, none, options({"./myExecutable"})); EXPECT_FALSE(testobj.foreground()); } TEST_F(ProgramOptionsTest, ForegroundTrue) { - ProgramOptions testobj("", "", none, true, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); EXPECT_TRUE(testobj.foreground()); } TEST_F(ProgramOptionsTest, LogfileNone) { - ProgramOptions testobj("", "", none, true, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ(none, testobj.logFile()); } TEST_F(ProgramOptionsTest, LogfileSome) { - ProgramOptions testobj("", "", none, true, none, bf::path("logfile"), none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, bf::path("logfile"), none, none, options({"./myExecutable"})); EXPECT_EQ("logfile", testobj.logFile().get()); } TEST_F(ProgramOptionsTest, UnmountAfterIdleMinutesNone) { -ProgramOptions testobj("", "", none, true, none, none, none, options({"./myExecutable"})); +ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ(none, testobj.unmountAfterIdleMinutes()); } TEST_F(ProgramOptionsTest, UnmountAfterIdleMinutesSome) { - ProgramOptions testobj("", "", none, true, 10, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, 10, none, none, none, options({"./myExecutable"})); EXPECT_EQ(10, testobj.unmountAfterIdleMinutes().get()); } TEST_F(ProgramOptionsTest, CipherNone) { - ProgramOptions testobj("", "", none, true, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); EXPECT_EQ(none, testobj.cipher()); } TEST_F(ProgramOptionsTest, CipherSome) { - ProgramOptions testobj("", "", none, true, none, none, string("aes-256-gcm"), options({"./myExecutable"})); + ProgramOptions testobj("", "", none, true, none, none, string("aes-256-gcm"), none, options({"./myExecutable"})); EXPECT_EQ("aes-256-gcm", testobj.cipher().get()); } +TEST_F(ProgramOptionsTest, BlocksizeBytesNone) { + ProgramOptions testobj("", "", none, true, none, none, none, none, options({"./myExecutable"})); + EXPECT_EQ(none, testobj.blocksizeBytes()); +} + +TEST_F(ProgramOptionsTest, BlocksizeSome) { + ProgramOptions testobj("", "", none, true, none, none, none, 10*1024, options({"./myExecutable"})); + EXPECT_EQ(10*1024u, testobj.blocksizeBytes().get()); +} + TEST_F(ProgramOptionsTest, EmptyFuseOptions) { - ProgramOptions testobj("/rootDir", "/home/user/mydir", none, false, none, none, none, options({"./myExecutable"})); + ProgramOptions testobj("/rootDir", "/home/user/mydir", none, false, none, none, none, none, options({"./myExecutable"})); //Fuse should have the mount dir as first parameter EXPECT_VECTOR_EQ({"./myExecutable", "/home/user/mydir"}, testobj.fuseOptions()); } TEST_F(ProgramOptionsTest, SomeFuseOptions) { - ProgramOptions testobj("/rootDir", "/home/user/mydir", none, false, none, none, none, options({"./myExecutable", "-f", "--longoption"})); + ProgramOptions testobj("/rootDir", "/home/user/mydir", none, false, none, none, none, none, options({"./myExecutable", "-f", "--longoption"})); //Fuse should have the mount dir as first parameter EXPECT_VECTOR_EQ({"./myExecutable", "/home/user/mydir", "-f", "--longoption"}, testobj.fuseOptions()); } diff --git a/test/cryfs/config/CryConfigCreatorTest.cpp b/test/cryfs/config/CryConfigCreatorTest.cpp index b3a87a74..25f5ee9c 100644 --- a/test/cryfs/config/CryConfigCreatorTest.cpp +++ b/test/cryfs/config/CryConfigCreatorTest.cpp @@ -62,72 +62,82 @@ public: TEST_F(CryConfigCreatorTest, DoesAskForCipherIfNotSpecified) { AnswerNoToDefaultSettings(); EXPECT_ASK_FOR_CIPHER().WillOnce(ChooseAnyCipher()); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); } TEST_F(CryConfigCreatorTest, DoesNotAskForCipherIfSpecified) { AnswerNoToDefaultSettings(); EXPECT_DOES_NOT_ASK_FOR_CIPHER(); - CryConfig config = creator.create(string("aes-256-gcm")); + CryConfig config = creator.create(string("aes-256-gcm"), none); } TEST_F(CryConfigCreatorTest, DoesNotAskForCipherIfUsingDefaultSettings) { AnswerYesToDefaultSettings(); EXPECT_DOES_NOT_ASK_FOR_CIPHER(); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); } TEST_F(CryConfigCreatorTest, DoesNotAskForCipherIfNoninteractive) { EXPECT_DOES_NOT_ASK_TO_USE_DEFAULT_SETTINGS(); EXPECT_DOES_NOT_ASK_FOR_CIPHER(); - CryConfig config = noninteractiveCreator.create(none); + CryConfig config = noninteractiveCreator.create(none, none); } TEST_F(CryConfigCreatorTest, DoesAskForBlocksizeIfNotSpecified) { AnswerNoToDefaultSettings(); EXPECT_ASK_FOR_BLOCKSIZE().WillOnce(Return(1)); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); } -//TODO DoesNotAskForCipherIfSpecified +TEST_F(CryConfigCreatorTest, DoesNotAskForBlocksizeIfSpecified) { + AnswerNoToDefaultSettings(); + EXPECT_DOES_NOT_ASK_FOR_BLOCKSIZE(); + CryConfig config = creator.create(none, 10*1024u); +} TEST_F(CryConfigCreatorTest, DoesNotAskForBlocksizeIfNoninteractive) { EXPECT_DOES_NOT_ASK_TO_USE_DEFAULT_SETTINGS(); EXPECT_DOES_NOT_ASK_FOR_BLOCKSIZE(); - CryConfig config = noninteractiveCreator.create(none); + CryConfig config = noninteractiveCreator.create(none, none); } TEST_F(CryConfigCreatorTest, DoesNotAskForBlocksizeIfUsingDefaultSettings) { AnswerYesToDefaultSettings(); EXPECT_DOES_NOT_ASK_FOR_BLOCKSIZE(); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); } TEST_F(CryConfigCreatorTest, ChoosesEmptyRootBlobId) { AnswerNoToDefaultSettings(); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); EXPECT_EQ("", config.RootBlob()); // This tells CryFS to create a new root blob } TEST_F(CryConfigCreatorTest, ChoosesValidEncryptionKey_448) { AnswerNoToDefaultSettings(); EXPECT_ASK_FOR_CIPHER().WillOnce(ChooseCipher("mars-448-gcm")); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); cpputils::Mars448_GCM::EncryptionKey::FromString(config.EncryptionKey()); // This crashes if invalid } TEST_F(CryConfigCreatorTest, ChoosesValidEncryptionKey_256) { AnswerNoToDefaultSettings(); EXPECT_ASK_FOR_CIPHER().WillOnce(ChooseCipher("aes-256-gcm")); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); cpputils::AES256_GCM::EncryptionKey::FromString(config.EncryptionKey()); // This crashes if invalid } TEST_F(CryConfigCreatorTest, ChoosesValidEncryptionKey_128) { AnswerNoToDefaultSettings(); EXPECT_ASK_FOR_CIPHER().WillOnce(ChooseCipher("aes-128-gcm")); - CryConfig config = creator.create(none); + CryConfig config = creator.create(none, none); cpputils::AES128_GCM::EncryptionKey::FromString(config.EncryptionKey()); // This crashes if invalid } +TEST_F(CryConfigCreatorTest, DoesNotAskForAnythingIfEverythingIsSpecified) { + EXPECT_DOES_NOT_ASK_TO_USE_DEFAULT_SETTINGS(); + EXPECT_DOES_NOT_ASK_FOR_CIPHER(); + CryConfig config = noninteractiveCreator.create(string("aes-256-gcm"), 10*1024u); +} + //TODO Add test cases ensuring that the values entered are correctly taken diff --git a/test/cryfs/config/CryConfigLoaderTest.cpp b/test/cryfs/config/CryConfigLoaderTest.cpp index def88d5d..f3b4f92b 100644 --- a/test/cryfs/config/CryConfigLoaderTest.cpp +++ b/test/cryfs/config/CryConfigLoaderTest.cpp @@ -32,7 +32,7 @@ public: CryConfigLoader loader(const string &password, bool noninteractive, const optional &cipher = none) { auto askPassword = [password] { return password;}; - return CryConfigLoader(mockConsole(), cpputils::Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, cipher, noninteractive); + return CryConfigLoader(mockConsole(), cpputils::Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, cipher, none, noninteractive); } CryConfigFile Create(const string &password = "mypassword", const optional &cipher = none, bool noninteractive = false) { diff --git a/test/cryfs/filesystem/CryFsTest.cpp b/test/cryfs/filesystem/CryFsTest.cpp index 60e633e1..d80995e3 100644 --- a/test/cryfs/filesystem/CryFsTest.cpp +++ b/test/cryfs/filesystem/CryFsTest.cpp @@ -37,7 +37,7 @@ public: CryConfigFile loadOrCreateConfig() { auto askPassword = [] {return "mypassword";}; - return CryConfigLoader(mockConsole(), Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, none, true).loadOrCreate(config.path()).value(); + return CryConfigLoader(mockConsole(), Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, none, none, true).loadOrCreate(config.path()).value(); } unique_ref blockStore() { diff --git a/test/cryfs/filesystem/FileSystemTest.cpp b/test/cryfs/filesystem/FileSystemTest.cpp index 9ee176da..e4b0681d 100644 --- a/test/cryfs/filesystem/FileSystemTest.cpp +++ b/test/cryfs/filesystem/FileSystemTest.cpp @@ -28,7 +28,7 @@ public: unique_ref createDevice() override { auto blockStore = cpputils::make_unique_ref(); auto askPassword = [] {return "mypassword";}; - auto config = CryConfigLoader(mockConsole(), Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, none, true) + auto config = CryConfigLoader(mockConsole(), Random::PseudoRandom(), SCrypt::TestSettings, askPassword, askPassword, none, none, true) .loadOrCreate(configFile.path()).value(); return make_unique_ref(std::move(config), std::move(blockStore)); } From 4dbb380263544a8100cc327b760e8b17536495d1 Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Tue, 8 Mar 2016 23:47:31 +0100 Subject: [PATCH 2/6] Decouple DirBlob from CryDevice --- .../implementations/onblocks/BlobStoreOnBlocks.cpp | 6 +++++- .../implementations/onblocks/BlobStoreOnBlocks.h | 5 +++-- .../onblocks/datanodestore/DataNodeStore.cpp | 6 +++++- .../onblocks/datanodestore/DataNodeStore.h | 5 +++-- .../onblocks/datanodestore/DataNodeView.h | 9 ++++----- .../onblocks/datatreestore/DataTree.cpp | 4 ++-- .../onblocks/datatreestore/DataTreeStore.h | 7 ++++++- .../ParallelAccessDataTreeStore.h | 3 ++- src/blobstore/interface/BlobStore.h | 2 ++ src/cryfs/filesystem/CryDevice.h | 4 ++-- src/cryfs/filesystem/fsblobstore/DirBlob.cpp | 10 +++++----- src/cryfs/filesystem/fsblobstore/DirBlob.h | 5 +++-- src/cryfs/filesystem/fsblobstore/FsBlobStore.cpp | 2 +- src/cryfs/filesystem/fsblobstore/FsBlobStore.h | 8 +++++++- 14 files changed, 50 insertions(+), 26 deletions(-) diff --git a/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.cpp b/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.cpp index e8dce0f9..ea054728 100644 --- a/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.cpp +++ b/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.cpp @@ -27,7 +27,7 @@ using datanodestore::DataNodeStore; using datatreestore::DataTreeStore; using parallelaccessdatatreestore::ParallelAccessDataTreeStore; -BlobStoreOnBlocks::BlobStoreOnBlocks(unique_ref blockStore, uint32_t blocksizeBytes) +BlobStoreOnBlocks::BlobStoreOnBlocks(unique_ref blockStore, uint64_t blocksizeBytes) : _dataTreeStore(make_unique_ref(make_unique_ref(make_unique_ref(make_unique_ref(std::move(blockStore)), blocksizeBytes)))) { } @@ -52,6 +52,10 @@ void BlobStoreOnBlocks::remove(unique_ref blob) { _dataTreeStore->remove((*_blob)->releaseTree()); } +uint64_t BlobStoreOnBlocks::blocksizeBytes() const { + return _dataTreeStore->blocksizeBytes(); +} + uint64_t BlobStoreOnBlocks::numBlocks() const { return _dataTreeStore->numNodes(); } diff --git a/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.h b/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.h index 27e0935b..b915c95b 100644 --- a/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.h +++ b/src/blobstore/implementations/onblocks/BlobStoreOnBlocks.h @@ -16,7 +16,7 @@ class ParallelAccessDataTreeStore; class BlobStoreOnBlocks final: public BlobStore { public: - BlobStoreOnBlocks(cpputils::unique_ref blockStore, uint32_t blocksizeBytes); + BlobStoreOnBlocks(cpputils::unique_ref blockStore, uint64_t blocksizeBytes); ~BlobStoreOnBlocks(); cpputils::unique_ref create() override; @@ -24,7 +24,8 @@ public: void remove(cpputils::unique_ref blob) override; - //TODO Test numBlocks/estimateSpaceForNumBlocksLeft + //TODO Test blocksizeBytes/numBlocks/estimateSpaceForNumBlocksLeft + uint64_t blocksizeBytes() const override; uint64_t numBlocks() const override; uint64_t estimateSpaceForNumBlocksLeft() const override; diff --git a/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.cpp b/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.cpp index 74103e5d..c61a8be1 100644 --- a/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.cpp +++ b/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.cpp @@ -20,7 +20,7 @@ namespace blobstore { namespace onblocks { namespace datanodestore { -DataNodeStore::DataNodeStore(unique_ref blockstore, uint32_t blocksizeBytes) +DataNodeStore::DataNodeStore(unique_ref blockstore, uint64_t blocksizeBytes) : _blockstore(std::move(blockstore)), _layout(blocksizeBytes) { } @@ -96,6 +96,10 @@ uint64_t DataNodeStore::estimateSpaceForNumNodesLeft() const { return _blockstore->estimateNumFreeBytes() / _layout.blocksizeBytes(); } +uint64_t DataNodeStore::blocksizeBytes() const { + return _layout.blocksizeBytes(); +} + void DataNodeStore::removeSubtree(unique_ref node) { //TODO Make this faster by not loading the leaves but just deleting them. Can be recognized, because of the depth of their parents. DataInnerNode *inner = dynamic_cast(node.get()); diff --git a/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.h b/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.h index 88860ba7..4cbe2339 100644 --- a/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.h +++ b/src/blobstore/implementations/onblocks/datanodestore/DataNodeStore.h @@ -21,7 +21,7 @@ class DataInnerNode; class DataNodeStore final { public: - DataNodeStore(cpputils::unique_ref blockstore, uint32_t blocksizeBytes); + DataNodeStore(cpputils::unique_ref blockstore, uint64_t blocksizeBytes); ~DataNodeStore(); static constexpr uint8_t MAX_DEPTH = 10; @@ -41,7 +41,8 @@ public: void removeSubtree(cpputils::unique_ref node); - //TODO Test numBlocks/estimateSpaceForNumBlocksLeft + //TODO Test blocksizeBytes/numBlocks/estimateSpaceForNumBlocksLeft + uint64_t blocksizeBytes() const; uint64_t numNodes() const; uint64_t estimateSpaceForNumNodesLeft() const; //TODO Test overwriteNodeWith(), createNodeAsCopyFrom(), removeSubtree() diff --git a/src/blobstore/implementations/onblocks/datanodestore/DataNodeView.h b/src/blobstore/implementations/onblocks/datanodestore/DataNodeView.h index 834061b3..ab69bbfc 100644 --- a/src/blobstore/implementations/onblocks/datanodestore/DataNodeView.h +++ b/src/blobstore/implementations/onblocks/datanodestore/DataNodeView.h @@ -19,7 +19,7 @@ namespace datanodestore { //TODO Move DataNodeLayout into own file class DataNodeLayout final { public: - constexpr DataNodeLayout(uint32_t blocksizeBytes) + constexpr DataNodeLayout(uint64_t blocksizeBytes) :_blocksizeBytes( (HEADERSIZE_BYTES + 2*sizeof(DataInnerNode_ChildEntry) <= blocksizeBytes) ? blocksizeBytes @@ -37,22 +37,21 @@ public: //Size of a block (header + data region) - constexpr uint32_t blocksizeBytes() const { + constexpr uint64_t blocksizeBytes() const { return _blocksizeBytes; } //Number of bytes in the data region of a node - constexpr uint32_t datasizeBytes() const { + constexpr uint64_t datasizeBytes() const { return _blocksizeBytes - HEADERSIZE_BYTES; } //Maximum number of children an inner node can store - constexpr uint32_t maxChildrenPerInnerNode() const { + constexpr uint64_t maxChildrenPerInnerNode() const { return datasizeBytes() / sizeof(DataInnerNode_ChildEntry); } //Maximum number of bytes a leaf can store - //We are returning uint64_t here, because calculations involving maxBytesPerLeaf most probably should use 64bit integers to support blobs >4GB. constexpr uint64_t maxBytesPerLeaf() const { return datasizeBytes(); } diff --git a/src/blobstore/implementations/onblocks/datatreestore/DataTree.cpp b/src/blobstore/implementations/onblocks/datatreestore/DataTree.cpp index d2d87049..682ff062 100644 --- a/src/blobstore/implementations/onblocks/datatreestore/DataTree.cpp +++ b/src/blobstore/implementations/onblocks/datatreestore/DataTree.cpp @@ -166,7 +166,7 @@ void DataTree::traverseLeaves(uint32_t beginIndex, uint32_t endIndex, functionlayout().maxChildrenPerInnerNode(), endIndex); + uint8_t neededTreeDepth = utils::ceilLog(_nodeStore->layout().maxChildrenPerInnerNode(), (uint64_t)endIndex); uint32_t numLeaves = this->_numLeaves(*_rootNode); // TODO Querying the size causes a tree traversal down to the leaves. Possible without querying the size? if (_rootNode->depth() < neededTreeDepth) { //TODO Test cases that actually increase it here by 0 level / 1 level / more than 1 level @@ -250,7 +250,7 @@ unique_ref DataTree::addChildTo(DataInnerNode *node) { } uint32_t DataTree::leavesPerFullChild(const DataInnerNode &root) const { - return utils::intPow(_nodeStore->layout().maxChildrenPerInnerNode(), (uint32_t)root.depth()-1); + return utils::intPow(_nodeStore->layout().maxChildrenPerInnerNode(), (uint64_t)root.depth()-1); } uint64_t DataTree::numStoredBytes() const { diff --git a/src/blobstore/implementations/onblocks/datatreestore/DataTreeStore.h b/src/blobstore/implementations/onblocks/datatreestore/DataTreeStore.h index ebc5e06d..4e253728 100644 --- a/src/blobstore/implementations/onblocks/datatreestore/DataTreeStore.h +++ b/src/blobstore/implementations/onblocks/datatreestore/DataTreeStore.h @@ -25,7 +25,8 @@ public: void remove(cpputils::unique_ref tree); - //TODO Test numBlocks/estimateSpaceForNumBlocksLeft + //TODO Test blocksizeBytes/numBlocks/estimateSpaceForNumBlocksLeft + uint64_t blocksizeBytes() const; uint64_t numNodes() const; uint64_t estimateSpaceForNumNodesLeft() const; @@ -43,6 +44,10 @@ inline uint64_t DataTreeStore::estimateSpaceForNumNodesLeft() const { return _nodeStore->estimateSpaceForNumNodesLeft(); } +inline uint64_t DataTreeStore::blocksizeBytes() const { + return _nodeStore->blocksizeBytes(); +} + } } } diff --git a/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h b/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h index 2f65fb67..1ff4c069 100644 --- a/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h +++ b/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h @@ -26,7 +26,8 @@ public: void remove(cpputils::unique_ref tree); - //TODO Test numBlocks/estimateSpaceForNumBlocksLeft + //TODO Test blocksizeBytes/numBlocks/estimateSpaceForNumBlocksLeft + uint64_t blocksizeBytes() const; uint64_t numNodes() const; uint64_t estimateSpaceForNumNodesLeft() const; diff --git a/src/blobstore/interface/BlobStore.h b/src/blobstore/interface/BlobStore.h index 5cfe1a29..bf7c0653 100644 --- a/src/blobstore/interface/BlobStore.h +++ b/src/blobstore/interface/BlobStore.h @@ -11,6 +11,7 @@ namespace blobstore { +//TODO Remove this interface. We'll only use BlobStoreOnBlocks and never a different one. Rename BlobStoreOnBlocks to simply BlobStore. class BlobStore { public: virtual ~BlobStore() {} @@ -21,6 +22,7 @@ public: virtual uint64_t numBlocks() const = 0; virtual uint64_t estimateSpaceForNumBlocksLeft() const = 0; + virtual uint64_t blocksizeBytes() const = 0; }; } diff --git a/src/cryfs/filesystem/CryDevice.h b/src/cryfs/filesystem/CryDevice.h index 72123e8f..c448ef21 100644 --- a/src/cryfs/filesystem/CryDevice.h +++ b/src/cryfs/filesystem/CryDevice.h @@ -17,8 +17,6 @@ namespace cryfs { class CryDevice final: public fspp::Device { public: - static constexpr uint32_t BLOCKSIZE_BYTES = 32 * 1024; - CryDevice(CryConfigFile config, cpputils::unique_ref blockStore); void statfs(const boost::filesystem::path &path, struct ::statvfs *fsstat) override; @@ -39,6 +37,8 @@ public: private: + static constexpr uint32_t BLOCKSIZE_BYTES = 32 * 1024; + cpputils::unique_ref _fsBlobStore; blockstore::Key _rootKey; diff --git a/src/cryfs/filesystem/fsblobstore/DirBlob.cpp b/src/cryfs/filesystem/fsblobstore/DirBlob.cpp index 25d0c160..23101a2a 100644 --- a/src/cryfs/filesystem/fsblobstore/DirBlob.cpp +++ b/src/cryfs/filesystem/fsblobstore/DirBlob.cpp @@ -27,8 +27,8 @@ namespace fsblobstore { constexpr off_t DirBlob::DIR_LSTAT_SIZE; -DirBlob::DirBlob(unique_ref blob, std::function getLstatSize) : - FsBlob(std::move(blob)), _getLstatSize(getLstatSize), _entries(), _mutex(), _changed(false) { +DirBlob::DirBlob(FsBlobStore *fsBlobStore, unique_ref blob, std::function getLstatSize) : + FsBlob(std::move(blob)), _fsBlobStore(fsBlobStore), _getLstatSize(getLstatSize), _entries(), _mutex(), _changed(false) { ASSERT(baseBlob().blobType() == FsBlobView::BlobType::DIR, "Loaded blob is not a directory"); _readEntriesFromBlob(); } @@ -44,9 +44,9 @@ void DirBlob::flush() { baseBlob().flush(); } -unique_ref DirBlob::InitializeEmptyDir(unique_ref blob, std::function getLstatSize) { +unique_ref DirBlob::InitializeEmptyDir(FsBlobStore *fsBlobStore, unique_ref blob, std::function getLstatSize) { InitializeBlob(blob.get(), FsBlobView::BlobType::DIR); - return make_unique_ref(std::move(blob), getLstatSize); + return make_unique_ref(fsBlobStore, std::move(blob), getLstatSize); } void DirBlob::_writeEntriesToBlob() { @@ -136,7 +136,7 @@ void DirBlob::statChild(const Key &key, struct ::stat *result) const { result->st_size = _getLstatSize(key); //TODO Move ceilDivision to general utils which can be used by cryfs as well result->st_blocks = blobstore::onblocks::utils::ceilDivision(result->st_size, (off_t)512); - result->st_blksize = CryDevice::BLOCKSIZE_BYTES; //TODO FsBlobStore::BLOCKSIZE_BYTES would be cleaner + result->st_blksize = _fsBlobStore->blocksizeBytes(); } void DirBlob::chmodChild(const Key &key, mode_t mode) { diff --git a/src/cryfs/filesystem/fsblobstore/DirBlob.h b/src/cryfs/filesystem/fsblobstore/DirBlob.h index 6a32331f..92684a89 100644 --- a/src/cryfs/filesystem/fsblobstore/DirBlob.h +++ b/src/cryfs/filesystem/fsblobstore/DirBlob.h @@ -17,10 +17,10 @@ namespace cryfs { public: constexpr static off_t DIR_LSTAT_SIZE = 4096; - static cpputils::unique_ref InitializeEmptyDir(cpputils::unique_ref blob, + static cpputils::unique_ref InitializeEmptyDir(FsBlobStore *fsBlobStore, cpputils::unique_ref blob, std::function getLstatSize); - DirBlob(cpputils::unique_ref blob, std::function getLstatSize); + DirBlob(FsBlobStore *fsBlobStore, cpputils::unique_ref blob, std::function getLstatSize); ~DirBlob(); @@ -68,6 +68,7 @@ namespace cryfs { cpputils::unique_ref releaseBaseBlob() override; + FsBlobStore *_fsBlobStore; std::function _getLstatSize; DirEntryList _entries; mutable std::mutex _mutex; diff --git a/src/cryfs/filesystem/fsblobstore/FsBlobStore.cpp b/src/cryfs/filesystem/fsblobstore/FsBlobStore.cpp index 288f50ad..7200b0fc 100644 --- a/src/cryfs/filesystem/fsblobstore/FsBlobStore.cpp +++ b/src/cryfs/filesystem/fsblobstore/FsBlobStore.cpp @@ -23,7 +23,7 @@ boost::optional> FsBlobStore::load(const blockstore::Key &key if (blobType == FsBlobView::BlobType::FILE) { return unique_ref(make_unique_ref(std::move(*blob))); } else if (blobType == FsBlobView::BlobType::DIR) { - return unique_ref(make_unique_ref(std::move(*blob), _getLstatSize())); + return unique_ref(make_unique_ref(this, std::move(*blob), _getLstatSize())); } else if (blobType == FsBlobView::BlobType::SYMLINK) { return unique_ref(make_unique_ref(std::move(*blob))); } else { diff --git a/src/cryfs/filesystem/fsblobstore/FsBlobStore.h b/src/cryfs/filesystem/fsblobstore/FsBlobStore.h index 9dd5d589..583f56b0 100644 --- a/src/cryfs/filesystem/fsblobstore/FsBlobStore.h +++ b/src/cryfs/filesystem/fsblobstore/FsBlobStore.h @@ -25,6 +25,8 @@ namespace cryfs { uint64_t numBlocks() const; uint64_t estimateSpaceForNumBlocksLeft() const; + uint64_t blocksizeBytes() const; + private: std::function _getLstatSize(); @@ -45,7 +47,7 @@ namespace cryfs { inline cpputils::unique_ref FsBlobStore::createDirBlob() { auto blob = _baseBlobStore->create(); - return DirBlob::InitializeEmptyDir(std::move(blob), _getLstatSize()); + return DirBlob::InitializeEmptyDir(this, std::move(blob), _getLstatSize()); } inline cpputils::unique_ref FsBlobStore::createSymlinkBlob(const boost::filesystem::path &target) { @@ -72,6 +74,10 @@ namespace cryfs { return (*blob)->lstat_size(); }; } + + inline uint64_t FsBlobStore::blocksizeBytes() const { + return _baseBlobStore->blocksizeBytes(); + } } } From d7f34c0dfb1a965d65a813bb892d9d14f2f786a1 Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Tue, 8 Mar 2016 23:57:34 +0100 Subject: [PATCH 3/6] Make blocksize configurable --- src/cryfs/filesystem/CryDevice.cpp | 6 ++---- src/cryfs/filesystem/CryDevice.h | 2 -- .../filesystem/cachingfsblobstore/CachingFsBlobStore.h | 5 +++++ .../parallelaccessfsblobstore/ParallelAccessFsBlobStore.h | 5 +++++ 4 files changed, 12 insertions(+), 6 deletions(-) diff --git a/src/cryfs/filesystem/CryDevice.cpp b/src/cryfs/filesystem/CryDevice.cpp index 4b7b53c5..3fead795 100644 --- a/src/cryfs/filesystem/CryDevice.cpp +++ b/src/cryfs/filesystem/CryDevice.cpp @@ -45,8 +45,6 @@ namespace bf = boost::filesystem; namespace cryfs { -constexpr uint32_t CryDevice::BLOCKSIZE_BYTES; - CryDevice::CryDevice(CryConfigFile configFile, unique_ref blockStore) : _fsBlobStore( make_unique_ref( @@ -55,7 +53,7 @@ CryDevice::CryDevice(CryConfigFile configFile, unique_ref blockStore make_unique_ref( make_unique_ref( CreateEncryptedBlockStore(*configFile.config(), std::move(blockStore)) - ), BLOCKSIZE_BYTES))) + ), configFile.config()->BlocksizeBytes()))) ) ), _rootKey(GetOrCreateRootKey(&configFile)), @@ -140,7 +138,7 @@ void CryDevice::statfs(const bf::path &path, struct statvfs *fsstat) { callFsActionCallbacks(); uint64_t numUsedBlocks = _fsBlobStore->numBlocks(); uint64_t numFreeBlocks = _fsBlobStore->estimateSpaceForNumBlocksLeft(); - fsstat->f_bsize = BLOCKSIZE_BYTES; + fsstat->f_bsize = _fsBlobStore->blocksizeBytes(); fsstat->f_blocks = numUsedBlocks + numFreeBlocks; fsstat->f_bfree = numFreeBlocks; fsstat->f_bavail = numFreeBlocks; diff --git a/src/cryfs/filesystem/CryDevice.h b/src/cryfs/filesystem/CryDevice.h index c448ef21..ed2b22a5 100644 --- a/src/cryfs/filesystem/CryDevice.h +++ b/src/cryfs/filesystem/CryDevice.h @@ -37,8 +37,6 @@ public: private: - static constexpr uint32_t BLOCKSIZE_BYTES = 32 * 1024; - cpputils::unique_ref _fsBlobStore; blockstore::Key _rootKey; diff --git a/src/cryfs/filesystem/cachingfsblobstore/CachingFsBlobStore.h b/src/cryfs/filesystem/cachingfsblobstore/CachingFsBlobStore.h index ba7f6344..6915b03f 100644 --- a/src/cryfs/filesystem/cachingfsblobstore/CachingFsBlobStore.h +++ b/src/cryfs/filesystem/cachingfsblobstore/CachingFsBlobStore.h @@ -24,6 +24,7 @@ namespace cryfs { cpputils::unique_ref createSymlinkBlob(const boost::filesystem::path &target); boost::optional> load(const blockstore::Key &key); void remove(cpputils::unique_ref blob); + uint64_t blocksizeBytes() const; uint64_t numBlocks() const; uint64_t estimateSpaceForNumBlocksLeft() const; @@ -80,6 +81,10 @@ namespace cryfs { _cache.push(key, std::move(baseBlob)); } + inline uint64_t CachingFsBlobStore::blocksizeBytes() const { + return _baseBlobStore->blocksizeBytes(); + } + inline uint64_t CachingFsBlobStore::numBlocks() const { return _baseBlobStore->numBlocks(); } diff --git a/src/cryfs/filesystem/parallelaccessfsblobstore/ParallelAccessFsBlobStore.h b/src/cryfs/filesystem/parallelaccessfsblobstore/ParallelAccessFsBlobStore.h index 384eb2d3..cca1b3e4 100644 --- a/src/cryfs/filesystem/parallelaccessfsblobstore/ParallelAccessFsBlobStore.h +++ b/src/cryfs/filesystem/parallelaccessfsblobstore/ParallelAccessFsBlobStore.h @@ -26,6 +26,7 @@ namespace cryfs { cpputils::unique_ref createSymlinkBlob(const boost::filesystem::path &target); boost::optional> load(const blockstore::Key &key); void remove(cpputils::unique_ref blob); + uint64_t blocksizeBytes() const; uint64_t numBlocks() const; uint64_t estimateSpaceForNumBlocksLeft() const; @@ -57,6 +58,10 @@ namespace cryfs { }; } + inline uint64_t ParallelAccessFsBlobStore::blocksizeBytes() const { + return _baseBlobStore->blocksizeBytes(); + } + inline uint64_t ParallelAccessFsBlobStore::numBlocks() const { return _baseBlobStore->numBlocks(); } From fdd9c980bd6132438ad5778b9ac5973c4e94f895 Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Tue, 8 Mar 2016 23:58:51 +0100 Subject: [PATCH 4/6] Add configurable blocksize to ChangeLog --- ChangeLog.txt | 1 + 1 file changed, 1 insertion(+) diff --git a/ChangeLog.txt b/ChangeLog.txt index 490054cb..c6a11ae8 100644 --- a/ChangeLog.txt +++ b/ChangeLog.txt @@ -5,6 +5,7 @@ Version 0.9.3 (unreleased) Furthermore, we won't ask for password confirmation when creating a file system but the password only has to be sent once to stdin. * You can disable the automatic update check by setting CRYFS_NO_UPDATE_CHECK=true in your environment. * Building CryFS from the GitHub tarball (i.e. when there is no .git directory present) works. +* The ciphertext block size is configurable. You can use the "--blocksize-bytes" command line argument. If not specified, CryFS will ask you for a block size when creating a file system. Version 0.9.2 --------------- From 08c1d206af854c6e0eae0570d8b04a0409211e9d Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Wed, 9 Mar 2016 00:13:18 +0100 Subject: [PATCH 5/6] Fix compiler error --- .../parallelaccessdatatreestore/ParallelAccessDataTreeStore.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h b/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h index 1ff4c069..533a5146 100644 --- a/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h +++ b/src/blobstore/implementations/onblocks/parallelaccessdatatreestore/ParallelAccessDataTreeStore.h @@ -38,6 +38,10 @@ private: DISALLOW_COPY_AND_ASSIGN(ParallelAccessDataTreeStore); }; +inline uint64_t ParallelAccessDataTreeStore::blocksizeBytes() const { + return _dataTreeStore->blocksizeBytes(); +} + inline uint64_t ParallelAccessDataTreeStore::numNodes() const { return _dataTreeStore->numNodes(); } From 1ee3a8df868377ecf5b176c3c268d58f1461590d Mon Sep 17 00:00:00 2001 From: Sebastian Messmer Date: Wed, 9 Mar 2016 00:20:04 +0100 Subject: [PATCH 6/6] Use uint64_t for block size --- src/cryfs/config/CryConfig.cpp | 8 ++++---- src/cryfs/config/CryConfig.h | 6 +++--- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/src/cryfs/config/CryConfig.cpp b/src/cryfs/config/CryConfig.cpp index 45bec926..38e87e84 100644 --- a/src/cryfs/config/CryConfig.cpp +++ b/src/cryfs/config/CryConfig.cpp @@ -33,7 +33,7 @@ CryConfig CryConfig::load(const Data &data) { cfg._encKey = pt.get("cryfs.key", ""); cfg._cipher = pt.get("cryfs.cipher", ""); cfg._version = pt.get("cryfs.version", "0.8"); // CryFS 0.8 didn't specify this field, so if the field doesn't exist, it's 0.8. - cfg._blocksizeBytes = pt.get("cryfs.blocksizeBytes", 32 * 1024); // TODO Put here the actual block size value of earlier CryFS versions + cfg._blocksizeBytes = pt.get("cryfs.blocksizeBytes", 32 * 1024); // CryFS <= 0.9.1 used a 32KB block size. return cfg; } @@ -44,7 +44,7 @@ Data CryConfig::save() const { pt.put("cryfs.key", _encKey); pt.put("cryfs.cipher", _cipher); pt.put("cryfs.version", _version); - pt.put("cryfs.blocksizeBytes", _blocksizeBytes); + pt.put("cryfs.blocksizeBytes", _blocksizeBytes); stringstream stream; write_json(stream, pt); @@ -83,11 +83,11 @@ void CryConfig::SetVersion(const std::string &value) { _version = value; } -uint32_t CryConfig::BlocksizeBytes() const { +uint64_t CryConfig::BlocksizeBytes() const { return _blocksizeBytes; } -void CryConfig::SetBlocksizeBytes(uint32_t value) { +void CryConfig::SetBlocksizeBytes(uint64_t value) { _blocksizeBytes = value; } diff --git a/src/cryfs/config/CryConfig.h b/src/cryfs/config/CryConfig.h index c3a01f92..b970d38d 100644 --- a/src/cryfs/config/CryConfig.h +++ b/src/cryfs/config/CryConfig.h @@ -27,8 +27,8 @@ public: const std::string &Version() const; void SetVersion(const std::string &value); - uint32_t BlocksizeBytes() const; - void SetBlocksizeBytes(uint32_t value); + uint64_t BlocksizeBytes() const; + void SetBlocksizeBytes(uint64_t value); static CryConfig load(const cpputils::Data &data); cpputils::Data save() const; @@ -38,7 +38,7 @@ private: std::string _encKey; std::string _cipher; std::string _version; - uint32_t _blocksizeBytes; + uint64_t _blocksizeBytes; DISALLOW_COPY_AND_ASSIGN(CryConfig); };