2016-04-26 02:42:17 +02:00
# include <gtest/gtest.h>
# include "testutils/CryTestBase.h"
2019-01-26 08:38:34 +01:00
# include <cryfs/impl/filesystem/CryDir.h>
# include <cryfs/impl/filesystem/CryFile.h>
# include <cryfs/impl/filesystem/CryOpenFile.h>
2016-04-26 02:42:17 +02:00
using cpputils : : unique_ref ;
using cpputils : : dynamic_pointer_move ;
using namespace cryfs ;
namespace bf = boost : : filesystem ;
// Many generic (black box) test cases for FsppNode are covered in Fspp fstest.
// This class adds some tests that need insight into how CryFS works.
class CryNodeTest : public : : testing : : Test , public CryTestBase {
public :
2018-09-14 11:34:11 +02:00
static constexpr fspp : : mode_t MODE_PUBLIC = fspp : : mode_t ( )
. addUserReadFlag ( ) . addUserWriteFlag ( ) . addUserExecFlag ( )
. addGroupReadFlag ( ) . addGroupWriteFlag ( ) . addGroupExecFlag ( )
. addOtherReadFlag ( ) . addOtherWriteFlag ( ) . addOtherExecFlag ( ) ;
2016-04-26 02:42:17 +02:00
unique_ref < CryNode > CreateFile ( const bf : : path & path ) {
2017-01-21 20:16:35 +01:00
auto parentDir = device ( ) . LoadDir ( path . parent_path ( ) ) . value ( ) ;
2018-09-14 11:34:11 +02:00
parentDir - > createAndOpenFile ( path . filename ( ) . string ( ) , MODE_PUBLIC , fspp : : uid_t ( 0 ) , fspp : : gid_t ( 0 ) ) ;
2017-01-21 20:16:35 +01:00
auto file = device ( ) . Load ( path ) . value ( ) ;
return dynamic_pointer_move < CryNode > ( file ) . value ( ) ;
2016-04-26 02:42:17 +02:00
}
2016-06-28 03:22:13 +02:00
unique_ref < CryNode > CreateDir ( const bf : : path & path ) {
auto _parentDir = device ( ) . Load ( path . parent_path ( ) ) . value ( ) ;
auto parentDir = dynamic_pointer_move < CryDir > ( _parentDir ) . value ( ) ;
2018-09-14 11:34:11 +02:00
parentDir - > createDir ( path . filename ( ) . string ( ) , MODE_PUBLIC , fspp : : uid_t ( 0 ) , fspp : : gid_t ( 0 ) ) ;
2016-06-28 03:22:13 +02:00
auto createdDir = device ( ) . Load ( path ) . value ( ) ;
return dynamic_pointer_move < CryNode > ( createdDir ) . value ( ) ;
}
unique_ref < CryNode > CreateSymlink ( const bf : : path & path ) {
auto _parentDir = device ( ) . Load ( path . parent_path ( ) ) . value ( ) ;
auto parentDir = dynamic_pointer_move < CryDir > ( _parentDir ) . value ( ) ;
2018-09-14 11:34:11 +02:00
parentDir - > createSymlink ( path . filename ( ) . string ( ) , " /target " , fspp : : uid_t ( 0 ) , fspp : : gid_t ( 0 ) ) ;
2016-06-28 03:22:13 +02:00
auto createdSymlink = device ( ) . Load ( path ) . value ( ) ;
return dynamic_pointer_move < CryNode > ( createdSymlink ) . value ( ) ;
}
2016-04-26 02:42:17 +02:00
} ;
2018-09-14 11:34:11 +02:00
constexpr fspp : : mode_t CryNodeTest : : MODE_PUBLIC ;
2016-04-26 02:42:17 +02:00
TEST_F ( CryNodeTest , Rename_DoesntLeaveBlocksOver ) {
auto node = CreateFile ( " /oldname " ) ;
EXPECT_EQ ( 2u , device ( ) . numBlocks ( ) ) ; // In the beginning, there is two blocks (the root block and the created file). If that is not true anymore, we'll have to adapt the test case.
node - > rename ( " /newname " ) ;
EXPECT_EQ ( 2u , device ( ) . numBlocks ( ) ) ; // Still same number of blocks
}
// TODO Add similar test cases (i.e. checking number of blocks) for other situations in rename, and also for other operations (e.g. deleting files).
TEST_F ( CryNodeTest , Rename_Overwrite_DoesntLeaveBlocksOver ) {
auto node = CreateFile ( " /oldname " ) ;
CreateFile ( " /newexistingname " ) ;
EXPECT_EQ ( 3u , device ( ) . numBlocks ( ) ) ; // In the beginning, there is three blocks (the root block and the two created files). If that is not true anymore, we'll have to adapt the test case.
node - > rename ( " /newexistingname " ) ;
EXPECT_EQ ( 2u , device ( ) . numBlocks ( ) ) ; // Only the blocks of one file are left
}
2016-06-28 03:22:13 +02:00
TEST_F ( CryNodeTest , Rename_UpdatesParentPointers_File ) {
this - > CreateDir ( " /mydir " ) ;
auto node = this - > CreateFile ( " /oldname " ) ;
node - > rename ( " /mydir/newname " ) ;
EXPECT_TRUE ( node - > checkParentPointer ( ) ) ;
}
TEST_F ( CryNodeTest , Rename_UpdatesParentPointers_Dir ) {
this - > CreateDir ( " /mydir " ) ;
auto node = this - > CreateDir ( " /oldname " ) ;
node - > rename ( " /mydir/newname " ) ;
EXPECT_TRUE ( node - > checkParentPointer ( ) ) ;
}
TEST_F ( CryNodeTest , Rename_UpdatesParentPointers_Symlink ) {
this - > CreateDir ( " /mydir " ) ;
auto node = this - > CreateSymlink ( " /oldname " ) ;
node - > rename ( " /mydir/newname " ) ;
EXPECT_TRUE ( node - > checkParentPointer ( ) ) ;
}