mirror of
https://github.com/vgough/encfs.git
synced 2025-06-15 01:16:52 +02:00
modernize: explicit conversions, braces around blocks
This commit is contained in:
parent
7a4e0c41db
commit
c37ab8e671
@ -67,8 +67,7 @@ ssize_t BlockFileIO::cacheReadOneBlock(const IORequest &req) const {
|
|||||||
* in the last block of a file, which may be smaller than the blocksize.
|
* in the last block of a file, which may be smaller than the blocksize.
|
||||||
* For reverse encryption, the cache must not be used at all, because
|
* For reverse encryption, the cache must not be used at all, because
|
||||||
* the lower file may have changed behind our back. */
|
* the lower file may have changed behind our back. */
|
||||||
if ((_noCache == false) && (req.offset == _cache.offset) &&
|
if ((!_noCache) && (req.offset == _cache.offset) && (_cache.dataLen != 0)) {
|
||||||
(_cache.dataLen != 0)) {
|
|
||||||
// satisfy request from cache
|
// satisfy request from cache
|
||||||
int len = req.dataLen;
|
int len = req.dataLen;
|
||||||
if (_cache.dataLen < len) len = _cache.dataLen; // Don't read past EOF
|
if (_cache.dataLen < len) len = _cache.dataLen; // Don't read past EOF
|
||||||
@ -86,8 +85,9 @@ ssize_t BlockFileIO::cacheReadOneBlock(const IORequest &req) const {
|
|||||||
if (result > 0) {
|
if (result > 0) {
|
||||||
_cache.offset = req.offset;
|
_cache.offset = req.offset;
|
||||||
_cache.dataLen = result; // the amount we really have
|
_cache.dataLen = result; // the amount we really have
|
||||||
if (result > req.dataLen)
|
if (result > req.dataLen) {
|
||||||
result = req.dataLen; // only as much as requested
|
result = req.dataLen; // only as much as requested
|
||||||
|
}
|
||||||
memcpy(req.data, _cache.data, result);
|
memcpy(req.data, _cache.data, result);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
@ -134,15 +134,15 @@ ssize_t BlockFileIO::read(const IORequest &req) const {
|
|||||||
blockReq.data = nullptr;
|
blockReq.data = nullptr;
|
||||||
|
|
||||||
unsigned char *out = req.data;
|
unsigned char *out = req.data;
|
||||||
while (size) {
|
while (size != 0u) {
|
||||||
blockReq.offset = blockNum * _blockSize;
|
blockReq.offset = blockNum * _blockSize;
|
||||||
|
|
||||||
// if we're reading a full block, then read directly into the
|
// if we're reading a full block, then read directly into the
|
||||||
// result buffer instead of using a temporary
|
// result buffer instead of using a temporary
|
||||||
if (partialOffset == 0 && size >= (size_t)_blockSize)
|
if (partialOffset == 0 && size >= (size_t)_blockSize) {
|
||||||
blockReq.data = out;
|
blockReq.data = out;
|
||||||
else {
|
} else {
|
||||||
if (!mb.data) mb = MemoryPool::allocate(_blockSize);
|
if (mb.data == nullptr) mb = MemoryPool::allocate(_blockSize);
|
||||||
blockReq.data = mb.data;
|
blockReq.data = mb.data;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -153,8 +153,9 @@ ssize_t BlockFileIO::read(const IORequest &req) const {
|
|||||||
CHECK(cpySize <= readSize);
|
CHECK(cpySize <= readSize);
|
||||||
|
|
||||||
// if we read to a temporary buffer, then move the data
|
// if we read to a temporary buffer, then move the data
|
||||||
if (blockReq.data != out)
|
if (blockReq.data != out) {
|
||||||
memcpy(out, blockReq.data + partialOffset, cpySize);
|
memcpy(out, blockReq.data + partialOffset, cpySize);
|
||||||
|
}
|
||||||
|
|
||||||
result += cpySize;
|
result += cpySize;
|
||||||
size -= cpySize;
|
size -= cpySize;
|
||||||
@ -165,7 +166,7 @@ ssize_t BlockFileIO::read(const IORequest &req) const {
|
|||||||
if (readSize < _blockSize) break;
|
if (readSize < _blockSize) break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mb.data) MemoryPool::release(mb);
|
if (mb.data != nullptr) MemoryPool::release(mb);
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
@ -202,9 +203,10 @@ bool BlockFileIO::write(const IORequest &req) {
|
|||||||
|
|
||||||
// if writing a partial block, but at least as much as what is
|
// if writing a partial block, but at least as much as what is
|
||||||
// already there..
|
// already there..
|
||||||
if (blockNum == lastFileBlock && req.dataLen >= lastBlockSize)
|
if (blockNum == lastFileBlock && req.dataLen >= lastBlockSize) {
|
||||||
return cacheWriteOneBlock(req);
|
return cacheWriteOneBlock(req);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// have to merge data with existing block(s)..
|
// have to merge data with existing block(s)..
|
||||||
MemBlock mb;
|
MemBlock mb;
|
||||||
@ -216,7 +218,7 @@ bool BlockFileIO::write(const IORequest &req) {
|
|||||||
bool ok = true;
|
bool ok = true;
|
||||||
size_t size = req.dataLen;
|
size_t size = req.dataLen;
|
||||||
unsigned char *inPtr = req.data;
|
unsigned char *inPtr = req.data;
|
||||||
while (size) {
|
while (size != 0u) {
|
||||||
blockReq.offset = blockNum * _blockSize;
|
blockReq.offset = blockNum * _blockSize;
|
||||||
int toCopy = min((size_t)(_blockSize - partialOffset), size);
|
int toCopy = min((size_t)(_blockSize - partialOffset), size);
|
||||||
|
|
||||||
@ -230,7 +232,7 @@ bool BlockFileIO::write(const IORequest &req) {
|
|||||||
} else {
|
} else {
|
||||||
// need a temporary buffer, since we have to either merge or pad
|
// need a temporary buffer, since we have to either merge or pad
|
||||||
// the data.
|
// the data.
|
||||||
if (!mb.data) mb = MemoryPool::allocate(_blockSize);
|
if (mb.data == nullptr) mb = MemoryPool::allocate(_blockSize);
|
||||||
memset(mb.data, 0, _blockSize);
|
memset(mb.data, 0, _blockSize);
|
||||||
blockReq.data = mb.data;
|
blockReq.data = mb.data;
|
||||||
|
|
||||||
@ -243,9 +245,10 @@ bool BlockFileIO::write(const IORequest &req) {
|
|||||||
blockReq.dataLen = cacheReadOneBlock(blockReq);
|
blockReq.dataLen = cacheReadOneBlock(blockReq);
|
||||||
|
|
||||||
// extend data if necessary..
|
// extend data if necessary..
|
||||||
if (partialOffset + toCopy > blockReq.dataLen)
|
if (partialOffset + toCopy > blockReq.dataLen) {
|
||||||
blockReq.dataLen = partialOffset + toCopy;
|
blockReq.dataLen = partialOffset + toCopy;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
// merge in the data to be written..
|
// merge in the data to be written..
|
||||||
memcpy(blockReq.data + partialOffset, inPtr, toCopy);
|
memcpy(blockReq.data + partialOffset, inPtr, toCopy);
|
||||||
}
|
}
|
||||||
@ -263,7 +266,7 @@ bool BlockFileIO::write(const IORequest &req) {
|
|||||||
partialOffset = 0;
|
partialOffset = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mb.data) MemoryPool::release(mb);
|
if (mb.data != nullptr) MemoryPool::release(mb);
|
||||||
|
|
||||||
return ok;
|
return ok;
|
||||||
}
|
}
|
||||||
@ -290,7 +293,7 @@ void BlockFileIO::padFile(off_t oldSize, off_t newSize, bool forceWrite) {
|
|||||||
req.dataLen = oldSize % _blockSize;
|
req.dataLen = oldSize % _blockSize;
|
||||||
int outSize = newSize % _blockSize; // outSize > req.dataLen
|
int outSize = newSize % _blockSize; // outSize > req.dataLen
|
||||||
|
|
||||||
if (outSize) {
|
if (outSize != 0) {
|
||||||
memset(mb.data, 0, outSize);
|
memset(mb.data, 0, outSize);
|
||||||
cacheReadOneBlock(req);
|
cacheReadOneBlock(req);
|
||||||
req.dataLen = outSize;
|
req.dataLen = outSize;
|
||||||
@ -331,7 +334,7 @@ void BlockFileIO::padFile(off_t oldSize, off_t newSize, bool forceWrite) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 3. only necessary if write is forced and block is non 0 length
|
// 3. only necessary if write is forced and block is non 0 length
|
||||||
if (forceWrite && newBlockSize) {
|
if (forceWrite && (newBlockSize != 0)) {
|
||||||
req.offset = newLastBlock * _blockSize;
|
req.offset = newLastBlock * _blockSize;
|
||||||
req.dataLen = newBlockSize;
|
req.dataLen = newBlockSize;
|
||||||
memset(mb.data, 0, req.dataLen);
|
memset(mb.data, 0, req.dataLen);
|
||||||
@ -339,7 +342,7 @@ void BlockFileIO::padFile(off_t oldSize, off_t newSize, bool forceWrite) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mb.data) MemoryPool::release(mb);
|
if (mb.data != nullptr) MemoryPool::release(mb);
|
||||||
}
|
}
|
||||||
|
|
||||||
int BlockFileIO::truncateBase(off_t size, FileIO *base) {
|
int BlockFileIO::truncateBase(off_t size, FileIO *base) {
|
||||||
@ -353,13 +356,13 @@ int BlockFileIO::truncateBase(off_t size, FileIO *base) {
|
|||||||
// states that it will pad with 0's.
|
// states that it will pad with 0's.
|
||||||
// do the truncate so that the underlying filesystem can allocate
|
// do the truncate so that the underlying filesystem can allocate
|
||||||
// the space, and then we'll fill it in padFile..
|
// the space, and then we'll fill it in padFile..
|
||||||
if (base) base->truncate(size);
|
if (base != nullptr) base->truncate(size);
|
||||||
|
|
||||||
const bool forceWrite = true;
|
const bool forceWrite = true;
|
||||||
padFile(oldSize, size, forceWrite);
|
padFile(oldSize, size, forceWrite);
|
||||||
} else if (size == oldSize) {
|
} else if (size == oldSize) {
|
||||||
// the easiest case, but least likely....
|
// the easiest case, but least likely....
|
||||||
} else if (partialBlock) {
|
} else if (partialBlock != 0) {
|
||||||
// partial block after truncate. Need to read in the block being
|
// partial block after truncate. Need to read in the block being
|
||||||
// truncated before the truncate. Then write it back out afterwards,
|
// truncated before the truncate. Then write it back out afterwards,
|
||||||
// since the encoding will change..
|
// since the encoding will change..
|
||||||
@ -374,7 +377,7 @@ int BlockFileIO::truncateBase(off_t size, FileIO *base) {
|
|||||||
ssize_t rdSz = cacheReadOneBlock(req);
|
ssize_t rdSz = cacheReadOneBlock(req);
|
||||||
|
|
||||||
// do the truncate
|
// do the truncate
|
||||||
if (base) res = base->truncate(size);
|
if (base != nullptr) res = base->truncate(size);
|
||||||
|
|
||||||
// write back out partial block
|
// write back out partial block
|
||||||
req.dataLen = partialBlock;
|
req.dataLen = partialBlock;
|
||||||
@ -390,7 +393,7 @@ int BlockFileIO::truncateBase(off_t size, FileIO *base) {
|
|||||||
} else {
|
} else {
|
||||||
// truncating on a block bounday. No need to re-encode the last
|
// truncating on a block bounday. No need to re-encode the last
|
||||||
// block..
|
// block..
|
||||||
if (base) res = base->truncate(size);
|
if (base != nullptr) res = base->truncate(size);
|
||||||
}
|
}
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
|
@ -89,11 +89,12 @@ static bool BlockIO32_registered = NameIO::Register(
|
|||||||
*/
|
*/
|
||||||
Interface BlockNameIO::CurrentInterface(bool caseInsensitive) {
|
Interface BlockNameIO::CurrentInterface(bool caseInsensitive) {
|
||||||
// implement major version 4 plus support for two prior versions
|
// implement major version 4 plus support for two prior versions
|
||||||
if (caseInsensitive)
|
if (caseInsensitive) {
|
||||||
return Interface("nameio/block32", 4, 0, 2);
|
return Interface("nameio/block32", 4, 0, 2);
|
||||||
else
|
} else {
|
||||||
return Interface("nameio/block", 4, 0, 2);
|
return Interface("nameio/block", 4, 0, 2);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
BlockNameIO::BlockNameIO(const Interface &iface, std::shared_ptr<Cipher> cipher,
|
BlockNameIO::BlockNameIO(const Interface &iface, std::shared_ptr<Cipher> cipher,
|
||||||
CipherKey key, int blockSize,
|
CipherKey key, int blockSize,
|
||||||
@ -118,11 +119,12 @@ int BlockNameIO::maxEncodedNameLen(int plaintextNameLen) const {
|
|||||||
// the size of too much space rather then too little.
|
// the size of too much space rather then too little.
|
||||||
int numBlocks = (plaintextNameLen + _bs) / _bs;
|
int numBlocks = (plaintextNameLen + _bs) / _bs;
|
||||||
int encodedNameLen = numBlocks * _bs + 2; // 2 checksum bytes
|
int encodedNameLen = numBlocks * _bs + 2; // 2 checksum bytes
|
||||||
if (_caseInsensitive)
|
if (_caseInsensitive) {
|
||||||
return B256ToB32Bytes(encodedNameLen);
|
return B256ToB32Bytes(encodedNameLen);
|
||||||
else
|
} else {
|
||||||
return B256ToB64Bytes(encodedNameLen);
|
return B256ToB64Bytes(encodedNameLen);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int BlockNameIO::maxDecodedNameLen(int encodedNameLen) const {
|
int BlockNameIO::maxDecodedNameLen(int encodedNameLen) const {
|
||||||
int decLen256 = _caseInsensitive ? B32ToB256Bytes(encodedNameLen)
|
int decLen256 = _caseInsensitive ? B32ToB256Bytes(encodedNameLen)
|
||||||
@ -145,7 +147,7 @@ int BlockNameIO::encodeName(const char *plaintextName, int length, uint64_t *iv,
|
|||||||
|
|
||||||
// store the IV before it is modified by the MAC call.
|
// store the IV before it is modified by the MAC call.
|
||||||
uint64_t tmpIV = 0;
|
uint64_t tmpIV = 0;
|
||||||
if (iv && _interface >= 3) tmpIV = *iv;
|
if ((iv != nullptr) && _interface >= 3) tmpIV = *iv;
|
||||||
|
|
||||||
// include padding in MAC computation
|
// include padding in MAC computation
|
||||||
unsigned int mac = _cipher->MAC_16((unsigned char *)encodedName + 2,
|
unsigned int mac = _cipher->MAC_16((unsigned char *)encodedName + 2,
|
||||||
@ -207,7 +209,7 @@ int BlockNameIO::decodeName(const char *encodedName, int length, uint64_t *iv,
|
|||||||
((unsigned int)((unsigned char)tmpBuf[1]));
|
((unsigned int)((unsigned char)tmpBuf[1]));
|
||||||
|
|
||||||
uint64_t tmpIV = 0;
|
uint64_t tmpIV = 0;
|
||||||
if (iv && _interface >= 3) tmpIV = *iv;
|
if ((iv != nullptr) && _interface >= 3) tmpIV = *iv;
|
||||||
|
|
||||||
_cipher->blockDecode((unsigned char *)tmpBuf + 2, decodedStreamLen,
|
_cipher->blockDecode((unsigned char *)tmpBuf + 2, decodedStreamLen,
|
||||||
(uint64_t)mac ^ tmpIV, _key);
|
(uint64_t)mac ^ tmpIV, _key);
|
||||||
|
@ -65,7 +65,7 @@ std::list<Cipher::CipherAlgorithm> Cipher::GetAlgorithmList(
|
|||||||
|
|
||||||
list<CipherAlgorithm> result;
|
list<CipherAlgorithm> result;
|
||||||
|
|
||||||
if (!gCipherMap) return result;
|
if (gCipherMap == nullptr) return result;
|
||||||
|
|
||||||
CipherMap_t::const_iterator it;
|
CipherMap_t::const_iterator it;
|
||||||
CipherMap_t::const_iterator mapEnd = gCipherMap->end();
|
CipherMap_t::const_iterator mapEnd = gCipherMap->end();
|
||||||
@ -98,7 +98,7 @@ bool Cipher::Register(const char *name, const char *description,
|
|||||||
const Interface &iface, const Range &keyLength,
|
const Interface &iface, const Range &keyLength,
|
||||||
const Range &blockSize, CipherConstructor fn,
|
const Range &blockSize, CipherConstructor fn,
|
||||||
bool hidden) {
|
bool hidden) {
|
||||||
if (!gCipherMap) gCipherMap = new CipherMap_t;
|
if (gCipherMap == nullptr) gCipherMap = new CipherMap_t;
|
||||||
|
|
||||||
CipherAlg ca;
|
CipherAlg ca;
|
||||||
ca.hidden = hidden;
|
ca.hidden = hidden;
|
||||||
@ -114,7 +114,7 @@ bool Cipher::Register(const char *name, const char *description,
|
|||||||
std::shared_ptr<Cipher> Cipher::New(const string &name, int keyLen) {
|
std::shared_ptr<Cipher> Cipher::New(const string &name, int keyLen) {
|
||||||
std::shared_ptr<Cipher> result;
|
std::shared_ptr<Cipher> result;
|
||||||
|
|
||||||
if (gCipherMap) {
|
if (gCipherMap != nullptr) {
|
||||||
CipherMap_t::const_iterator it = gCipherMap->find(name);
|
CipherMap_t::const_iterator it = gCipherMap->find(name);
|
||||||
if (it != gCipherMap->end()) {
|
if (it != gCipherMap->end()) {
|
||||||
CipherConstructor fn = it->second.constructor;
|
CipherConstructor fn = it->second.constructor;
|
||||||
@ -127,7 +127,7 @@ std::shared_ptr<Cipher> Cipher::New(const string &name, int keyLen) {
|
|||||||
}
|
}
|
||||||
std::shared_ptr<Cipher> Cipher::New(const Interface &iface, int keyLen) {
|
std::shared_ptr<Cipher> Cipher::New(const Interface &iface, int keyLen) {
|
||||||
std::shared_ptr<Cipher> result;
|
std::shared_ptr<Cipher> result;
|
||||||
if (gCipherMap) {
|
if (gCipherMap != nullptr) {
|
||||||
CipherMap_t::const_iterator it;
|
CipherMap_t::const_iterator it;
|
||||||
CipherMap_t::const_iterator mapEnd = gCipherMap->end();
|
CipherMap_t::const_iterator mapEnd = gCipherMap->end();
|
||||||
|
|
||||||
|
@ -197,14 +197,16 @@ void CipherFileIO::initHeader() {
|
|||||||
|
|
||||||
unsigned char buf[8] = {0};
|
unsigned char buf[8] = {0};
|
||||||
do {
|
do {
|
||||||
if (!cipher->randomize(buf, 8, false))
|
if (!cipher->randomize(buf, 8, false)) {
|
||||||
throw Error("Unable to generate a random file IV");
|
throw Error("Unable to generate a random file IV");
|
||||||
|
}
|
||||||
|
|
||||||
fileIV = 0;
|
fileIV = 0;
|
||||||
for (int i = 0; i < 8; ++i) fileIV = (fileIV << 8) | (uint64_t)buf[i];
|
for (int i = 0; i < 8; ++i) fileIV = (fileIV << 8) | (uint64_t)buf[i];
|
||||||
|
|
||||||
if (fileIV == 0)
|
if (fileIV == 0) {
|
||||||
RLOG(WARNING) << "Unexpected result: randomize returned 8 null bytes!";
|
RLOG(WARNING) << "Unexpected result: randomize returned 8 null bytes!";
|
||||||
|
}
|
||||||
} while (fileIV == 0); // don't accept 0 as an option..
|
} while (fileIV == 0); // don't accept 0 as an option..
|
||||||
|
|
||||||
if (base->isWritable()) {
|
if (base->isWritable()) {
|
||||||
@ -325,8 +327,9 @@ ssize_t CipherFileIO::readOneBlock(const IORequest &req) const {
|
|||||||
|
|
||||||
bool ok;
|
bool ok;
|
||||||
if (readSize > 0) {
|
if (readSize > 0) {
|
||||||
if (haveHeader && fileIV == 0)
|
if (haveHeader && fileIV == 0) {
|
||||||
const_cast<CipherFileIO *>(this)->initHeader();
|
const_cast<CipherFileIO *>(this)->initHeader();
|
||||||
|
}
|
||||||
|
|
||||||
if (readSize != bs) {
|
if (readSize != bs) {
|
||||||
VLOG(1) << "streamRead(data, " << readSize << ", IV)";
|
VLOG(1) << "streamRead(data, " << readSize << ", IV)";
|
||||||
@ -372,8 +375,9 @@ bool CipherFileIO::writeOneBlock(const IORequest &req) {
|
|||||||
IORequest tmpReq = req;
|
IORequest tmpReq = req;
|
||||||
tmpReq.offset += HEADER_SIZE;
|
tmpReq.offset += HEADER_SIZE;
|
||||||
ok = base->write(tmpReq);
|
ok = base->write(tmpReq);
|
||||||
} else
|
} else {
|
||||||
ok = base->write(req);
|
ok = base->write(req);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
VLOG(1) << "encodeBlock failed for block " << blockNum << ", size "
|
VLOG(1) << "encodeBlock failed for block " << blockNum << ", size "
|
||||||
<< req.dataLen;
|
<< req.dataLen;
|
||||||
@ -385,44 +389,49 @@ bool CipherFileIO::writeOneBlock(const IORequest &req) {
|
|||||||
bool CipherFileIO::blockWrite(unsigned char *buf, int size,
|
bool CipherFileIO::blockWrite(unsigned char *buf, int size,
|
||||||
uint64_t _iv64) const {
|
uint64_t _iv64) const {
|
||||||
VLOG(1) << "Called blockWrite";
|
VLOG(1) << "Called blockWrite";
|
||||||
if (!fsConfig->reverseEncryption)
|
if (!fsConfig->reverseEncryption) {
|
||||||
return cipher->blockEncode(buf, size, _iv64, key);
|
return cipher->blockEncode(buf, size, _iv64, key);
|
||||||
else
|
} else {
|
||||||
return cipher->blockDecode(buf, size, _iv64, key);
|
return cipher->blockDecode(buf, size, _iv64, key);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool CipherFileIO::streamWrite(unsigned char *buf, int size,
|
bool CipherFileIO::streamWrite(unsigned char *buf, int size,
|
||||||
uint64_t _iv64) const {
|
uint64_t _iv64) const {
|
||||||
VLOG(1) << "Called streamWrite";
|
VLOG(1) << "Called streamWrite";
|
||||||
if (!fsConfig->reverseEncryption)
|
if (!fsConfig->reverseEncryption) {
|
||||||
return cipher->streamEncode(buf, size, _iv64, key);
|
return cipher->streamEncode(buf, size, _iv64, key);
|
||||||
else
|
} else {
|
||||||
return cipher->streamDecode(buf, size, _iv64, key);
|
return cipher->streamDecode(buf, size, _iv64, key);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool CipherFileIO::blockRead(unsigned char *buf, int size,
|
bool CipherFileIO::blockRead(unsigned char *buf, int size,
|
||||||
uint64_t _iv64) const {
|
uint64_t _iv64) const {
|
||||||
if (fsConfig->reverseEncryption)
|
if (fsConfig->reverseEncryption) {
|
||||||
return cipher->blockEncode(buf, size, _iv64, key);
|
return cipher->blockEncode(buf, size, _iv64, key);
|
||||||
else {
|
} else {
|
||||||
if (_allowHoles) {
|
if (_allowHoles) {
|
||||||
// special case - leave all 0's alone
|
// special case - leave all 0's alone
|
||||||
for (int i = 0; i < size; ++i)
|
for (int i = 0; i < size; ++i) {
|
||||||
if (buf[i] != 0) return cipher->blockDecode(buf, size, _iv64, key);
|
if (buf[i] != 0) return cipher->blockDecode(buf, size, _iv64, key);
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
} else
|
} else {
|
||||||
return cipher->blockDecode(buf, size, _iv64, key);
|
return cipher->blockDecode(buf, size, _iv64, key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool CipherFileIO::streamRead(unsigned char *buf, int size,
|
bool CipherFileIO::streamRead(unsigned char *buf, int size,
|
||||||
uint64_t _iv64) const {
|
uint64_t _iv64) const {
|
||||||
if (fsConfig->reverseEncryption)
|
if (fsConfig->reverseEncryption) {
|
||||||
return cipher->streamEncode(buf, size, _iv64, key);
|
return cipher->streamEncode(buf, size, _iv64, key);
|
||||||
else
|
} else {
|
||||||
return cipher->streamDecode(buf, size, _iv64, key);
|
return cipher->streamDecode(buf, size, _iv64, key);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int CipherFileIO::truncate(off_t size) {
|
int CipherFileIO::truncate(off_t size) {
|
||||||
int res = 0;
|
int res = 0;
|
||||||
@ -434,9 +443,10 @@ int CipherFileIO::truncate(off_t size) {
|
|||||||
if (!base->isWritable()) {
|
if (!base->isWritable()) {
|
||||||
// open for write..
|
// open for write..
|
||||||
int newFlags = lastFlags | O_RDWR;
|
int newFlags = lastFlags | O_RDWR;
|
||||||
if (base->open(newFlags) < 0)
|
if (base->open(newFlags) < 0) {
|
||||||
VLOG(1) << "writeHeader failed to re-open for write";
|
VLOG(1) << "writeHeader failed to re-open for write";
|
||||||
}
|
}
|
||||||
|
}
|
||||||
initHeader();
|
initHeader();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -483,8 +493,9 @@ ssize_t CipherFileIO::read(const IORequest &origReq) const {
|
|||||||
* to the data. */
|
* to the data. */
|
||||||
if (req.offset < 0) {
|
if (req.offset < 0) {
|
||||||
headerBytes = -req.offset;
|
headerBytes = -req.offset;
|
||||||
if (req.dataLen < headerBytes)
|
if (req.dataLen < headerBytes) {
|
||||||
headerBytes = req.dataLen; // only up to the number of bytes requested
|
headerBytes = req.dataLen; // only up to the number of bytes requested
|
||||||
|
}
|
||||||
VLOG(1) << "Adding " << headerBytes << " header bytes";
|
VLOG(1) << "Adding " << headerBytes << " header bytes";
|
||||||
|
|
||||||
// copy the header bytes into the data
|
// copy the header bytes into the data
|
||||||
@ -506,9 +517,9 @@ ssize_t CipherFileIO::read(const IORequest &origReq) const {
|
|||||||
// read the payload
|
// read the payload
|
||||||
ssize_t readBytes = BlockFileIO::read(req);
|
ssize_t readBytes = BlockFileIO::read(req);
|
||||||
VLOG(1) << "read " << readBytes << " bytes from backing file";
|
VLOG(1) << "read " << readBytes << " bytes from backing file";
|
||||||
if (readBytes < 0)
|
if (readBytes < 0) {
|
||||||
return readBytes; // Return error code
|
return readBytes; // Return error code
|
||||||
else {
|
} else {
|
||||||
ssize_t sum = headerBytes + readBytes;
|
ssize_t sum = headerBytes + readBytes;
|
||||||
VLOG(1) << "returning sum=" << sum;
|
VLOG(1) << "returning sum=" << sum;
|
||||||
return sum;
|
return sum;
|
||||||
|
@ -127,11 +127,12 @@ ConfigVar ConfigReader::toVar() const {
|
|||||||
ConfigVar ConfigReader::operator[](const std::string &varName) const {
|
ConfigVar ConfigReader::operator[](const std::string &varName) const {
|
||||||
// read only
|
// read only
|
||||||
auto it = vars.find(varName);
|
auto it = vars.find(varName);
|
||||||
if (it == vars.end())
|
if (it == vars.end()) {
|
||||||
return ConfigVar();
|
return ConfigVar();
|
||||||
else
|
} else {
|
||||||
return it->second;
|
return it->second;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ConfigVar &ConfigReader::operator[](const std::string &varName) {
|
ConfigVar &ConfigReader::operator[](const std::string &varName) {
|
||||||
return vars[varName];
|
return vars[varName];
|
||||||
|
@ -43,10 +43,11 @@ ConfigVar::ConfigVar(const ConfigVar &src) { pd = src.pd; }
|
|||||||
ConfigVar::~ConfigVar() { pd.reset(); }
|
ConfigVar::~ConfigVar() { pd.reset(); }
|
||||||
|
|
||||||
ConfigVar &ConfigVar::operator=(const ConfigVar &src) {
|
ConfigVar &ConfigVar::operator=(const ConfigVar &src) {
|
||||||
if (src.pd == pd)
|
if (src.pd == pd) {
|
||||||
return *this;
|
return *this;
|
||||||
else
|
} else {
|
||||||
pd = src.pd;
|
pd = src.pd;
|
||||||
|
}
|
||||||
|
|
||||||
return *this;
|
return *this;
|
||||||
}
|
}
|
||||||
@ -122,7 +123,7 @@ int ConfigVar::readInt() const {
|
|||||||
|
|
||||||
do {
|
do {
|
||||||
unsigned char tmp = buf[offset++];
|
unsigned char tmp = buf[offset++];
|
||||||
highBitSet = tmp & 0x80;
|
highBitSet = ((tmp & 0x80) != 0);
|
||||||
|
|
||||||
value = (value << 7) | (int)(tmp & 0x7f);
|
value = (value << 7) | (int)(tmp & 0x7f);
|
||||||
} while (highBitSet && offset < bytes);
|
} while (highBitSet && offset < bytes);
|
||||||
@ -139,11 +140,12 @@ int ConfigVar::readInt(int defaultValue) const {
|
|||||||
int bytes = this->size();
|
int bytes = this->size();
|
||||||
int offset = at();
|
int offset = at();
|
||||||
|
|
||||||
if (offset >= bytes)
|
if (offset >= bytes) {
|
||||||
return defaultValue;
|
return defaultValue;
|
||||||
else
|
} else {
|
||||||
return readInt();
|
return readInt();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool ConfigVar::readBool(bool defaultValue) const {
|
bool ConfigVar::readBool(bool defaultValue) const {
|
||||||
int tmp = readInt(defaultValue ? 1 : 0);
|
int tmp = readInt(defaultValue ? 1 : 0);
|
||||||
|
@ -70,8 +70,8 @@ static bool _nextName(struct dirent *&de, const std::shared_ptr<DIR> &dir,
|
|||||||
int *fileType, ino_t *inode) {
|
int *fileType, ino_t *inode) {
|
||||||
de = ::readdir(dir.get());
|
de = ::readdir(dir.get());
|
||||||
|
|
||||||
if (de) {
|
if (de != nullptr) {
|
||||||
if (fileType) {
|
if (fileType != nullptr) {
|
||||||
#if defined(_DIRENT_HAVE_D_TYPE) || defined(__FreeBSD__) || defined(__APPLE__)
|
#if defined(_DIRENT_HAVE_D_TYPE) || defined(__FreeBSD__) || defined(__APPLE__)
|
||||||
*fileType = de->d_type;
|
*fileType = de->d_type;
|
||||||
#else
|
#else
|
||||||
@ -79,10 +79,10 @@ static bool _nextName(struct dirent *&de, const std::shared_ptr<DIR> &dir,
|
|||||||
*fileType = 0;
|
*fileType = 0;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
if (inode) *inode = de->d_ino;
|
if (inode != nullptr) *inode = de->d_ino;
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
if (fileType) *fileType = 0;
|
if (fileType != nullptr) *fileType = 0;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -477,9 +477,10 @@ std::shared_ptr<RenameOp> DirNode::newRenameOp(const char *fromP,
|
|||||||
if (!genRenameList(*renameList.get(), fromP, toP)) {
|
if (!genRenameList(*renameList.get(), fromP, toP)) {
|
||||||
RLOG(WARNING) << "Error during generation of recursive rename list";
|
RLOG(WARNING) << "Error during generation of recursive rename list";
|
||||||
return std::shared_ptr<RenameOp>();
|
return std::shared_ptr<RenameOp>();
|
||||||
} else
|
} else {
|
||||||
return std::make_shared<RenameOp>(this, renameList);
|
return std::make_shared<RenameOp>(this, renameList);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int DirNode::mkdir(const char *plaintextPath, mode_t mode, uid_t uid,
|
int DirNode::mkdir(const char *plaintextPath, mode_t mode, uid_t uid,
|
||||||
gid_t gid) {
|
gid_t gid) {
|
||||||
@ -504,8 +505,9 @@ int DirNode::mkdir(const char *plaintextPath, mode_t mode, uid_t uid,
|
|||||||
RLOG(WARNING) << "mkdir error on " << cyName << " mode " << mode << ": "
|
RLOG(WARNING) << "mkdir error on " << cyName << " mode " << mode << ": "
|
||||||
<< strerror(eno);
|
<< strerror(eno);
|
||||||
res = -eno;
|
res = -eno;
|
||||||
} else
|
} else {
|
||||||
res = 0;
|
res = 0;
|
||||||
|
}
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
@ -586,11 +588,12 @@ int DirNode::link(const char *from, const char *to) {
|
|||||||
VLOG(1) << "hard links not supported with external IV chaining!";
|
VLOG(1) << "hard links not supported with external IV chaining!";
|
||||||
} else {
|
} else {
|
||||||
res = ::link(fromCName.c_str(), toCName.c_str());
|
res = ::link(fromCName.c_str(), toCName.c_str());
|
||||||
if (res == -1)
|
if (res == -1) {
|
||||||
res = -errno;
|
res = -errno;
|
||||||
else
|
} else {
|
||||||
res = 0;
|
res = 0;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
@ -616,7 +619,7 @@ std::shared_ptr<FileNode> DirNode::renameNode(const char *from, const char *to,
|
|||||||
<< cname;
|
<< cname;
|
||||||
|
|
||||||
if (node->setName(to, cname.c_str(), newIV, forwardMode)) {
|
if (node->setName(to, cname.c_str(), newIV, forwardMode)) {
|
||||||
if (ctx) ctx->renameNode(from, to);
|
if (ctx != nullptr) ctx->renameNode(from, to);
|
||||||
} else {
|
} else {
|
||||||
// rename error! - put it back
|
// rename error! - put it back
|
||||||
RLOG(ERROR) << "renameNode failed";
|
RLOG(ERROR) << "renameNode failed";
|
||||||
@ -633,7 +636,7 @@ std::shared_ptr<FileNode> DirNode::findOrCreate(const char *plainName) {
|
|||||||
std::shared_ptr<FileNode> node;
|
std::shared_ptr<FileNode> node;
|
||||||
|
|
||||||
// See if we already have a FileNode for this path.
|
// See if we already have a FileNode for this path.
|
||||||
if (ctx) node = ctx->lookupNode(plainName);
|
if (ctx != nullptr) node = ctx->lookupNode(plainName);
|
||||||
|
|
||||||
// If we don't, create a new one.
|
// If we don't, create a new one.
|
||||||
if (!node) {
|
if (!node) {
|
||||||
@ -643,8 +646,9 @@ std::shared_ptr<FileNode> DirNode::findOrCreate(const char *plainName) {
|
|||||||
node.reset(new FileNode(this, fsConfig, plainName,
|
node.reset(new FileNode(this, fsConfig, plainName,
|
||||||
(rootDir + cipherName).c_str(), fuseFh));
|
(rootDir + cipherName).c_str(), fuseFh));
|
||||||
|
|
||||||
if (fsConfig->config->externalIVChaining)
|
if (fsConfig->config->externalIVChaining) {
|
||||||
node->setName(nullptr, nullptr, iv);
|
node->setName(nullptr, nullptr, iv);
|
||||||
|
}
|
||||||
|
|
||||||
VLOG(1) << "created FileNode for " << node->cipherName();
|
VLOG(1) << "created FileNode for " << node->cipherName();
|
||||||
}
|
}
|
||||||
@ -673,11 +677,12 @@ std::shared_ptr<FileNode> DirNode::openNode(const char *plainName,
|
|||||||
|
|
||||||
std::shared_ptr<FileNode> node = findOrCreate(plainName);
|
std::shared_ptr<FileNode> node = findOrCreate(plainName);
|
||||||
|
|
||||||
if (node && (*result = node->open(flags)) >= 0)
|
if (node && (*result = node->open(flags)) >= 0) {
|
||||||
return node;
|
return node;
|
||||||
else
|
} else {
|
||||||
return std::shared_ptr<FileNode>();
|
return std::shared_ptr<FileNode>();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int DirNode::unlink(const char *plaintextName) {
|
int DirNode::unlink(const char *plaintextName) {
|
||||||
string cyName = naming->encodePath(plaintextName);
|
string cyName = naming->encodePath(plaintextName);
|
||||||
@ -686,7 +691,7 @@ int DirNode::unlink(const char *plaintextName) {
|
|||||||
Lock _lock(mutex);
|
Lock _lock(mutex);
|
||||||
|
|
||||||
int res = 0;
|
int res = 0;
|
||||||
if (ctx && ctx->lookupNode(plaintextName)) {
|
if ((ctx != nullptr) && ctx->lookupNode(plaintextName)) {
|
||||||
// If FUSE is running with "hard_remove" option where it doesn't
|
// If FUSE is running with "hard_remove" option where it doesn't
|
||||||
// hide open files for us, then we can't allow an unlink of an open
|
// hide open files for us, then we can't allow an unlink of an open
|
||||||
// file..
|
// file..
|
||||||
|
@ -74,9 +74,11 @@ FileNode::FileNode(DirNode *parent_, const FSConfigPtr &cfg,
|
|||||||
std::shared_ptr<FileIO> rawIO(new RawFileIO(_cname));
|
std::shared_ptr<FileIO> rawIO(new RawFileIO(_cname));
|
||||||
io = std::shared_ptr<FileIO>(new CipherFileIO(rawIO, fsConfig));
|
io = std::shared_ptr<FileIO>(new CipherFileIO(rawIO, fsConfig));
|
||||||
|
|
||||||
if (cfg->config->blockMACBytes || cfg->config->blockMACRandBytes)
|
if ((cfg->config->blockMACBytes != 0) ||
|
||||||
|
(cfg->config->blockMACRandBytes != 0)) {
|
||||||
io = std::shared_ptr<FileIO>(new MACFileIO(io, fsConfig));
|
io = std::shared_ptr<FileIO>(new MACFileIO(io, fsConfig));
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
FileNode::~FileNode() {
|
FileNode::~FileNode() {
|
||||||
// FileNode mutex should be locked before the destructor is called
|
// FileNode mutex should be locked before the destructor is called
|
||||||
@ -98,23 +100,24 @@ string FileNode::plaintextParent() const { return parentDirectory(_pname); }
|
|||||||
|
|
||||||
static bool setIV(const std::shared_ptr<FileIO> &io, uint64_t iv) {
|
static bool setIV(const std::shared_ptr<FileIO> &io, uint64_t iv) {
|
||||||
struct stat stbuf;
|
struct stat stbuf;
|
||||||
if ((io->getAttr(&stbuf) < 0) || S_ISREG(stbuf.st_mode))
|
if ((io->getAttr(&stbuf) < 0) || S_ISREG(stbuf.st_mode)) {
|
||||||
return io->setIV(iv);
|
return io->setIV(iv);
|
||||||
else
|
} else {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool FileNode::setName(const char *plaintextName_, const char *cipherName_,
|
bool FileNode::setName(const char *plaintextName_, const char *cipherName_,
|
||||||
uint64_t iv, bool setIVFirst) {
|
uint64_t iv, bool setIVFirst) {
|
||||||
// Lock _lock( mutex );
|
// Lock _lock( mutex );
|
||||||
if (cipherName_) VLOG(1) << "calling setIV on " << cipherName_;
|
if (cipherName_ != nullptr) VLOG(1) << "calling setIV on " << cipherName_;
|
||||||
|
|
||||||
if (setIVFirst) {
|
if (setIVFirst) {
|
||||||
if (fsConfig->config->externalIVChaining && !setIV(io, iv)) return false;
|
if (fsConfig->config->externalIVChaining && !setIV(io, iv)) return false;
|
||||||
|
|
||||||
// now change the name..
|
// now change the name..
|
||||||
if (plaintextName_) this->_pname = plaintextName_;
|
if (plaintextName_ != nullptr) this->_pname = plaintextName_;
|
||||||
if (cipherName_) {
|
if (cipherName_ != nullptr) {
|
||||||
this->_cname = cipherName_;
|
this->_cname = cipherName_;
|
||||||
io->setFileName(cipherName_);
|
io->setFileName(cipherName_);
|
||||||
}
|
}
|
||||||
@ -122,8 +125,8 @@ bool FileNode::setName(const char *plaintextName_, const char *cipherName_,
|
|||||||
std::string oldPName = _pname;
|
std::string oldPName = _pname;
|
||||||
std::string oldCName = _cname;
|
std::string oldCName = _cname;
|
||||||
|
|
||||||
if (plaintextName_) this->_pname = plaintextName_;
|
if (plaintextName_ != nullptr) this->_pname = plaintextName_;
|
||||||
if (cipherName_) {
|
if (cipherName_ != nullptr) {
|
||||||
this->_cname = cipherName_;
|
this->_cname = cipherName_;
|
||||||
io->setFileName(cipherName_);
|
io->setFileName(cipherName_);
|
||||||
}
|
}
|
||||||
@ -167,10 +170,11 @@ int FileNode::mknod(mode_t mode, dev_t rdev, uid_t uid, gid_t gid) {
|
|||||||
if (S_ISREG(mode)) {
|
if (S_ISREG(mode)) {
|
||||||
res = ::open(_cname.c_str(), O_CREAT | O_EXCL | O_WRONLY, mode);
|
res = ::open(_cname.c_str(), O_CREAT | O_EXCL | O_WRONLY, mode);
|
||||||
if (res >= 0) res = ::close(res);
|
if (res >= 0) res = ::close(res);
|
||||||
} else if (S_ISFIFO(mode))
|
} else if (S_ISFIFO(mode)) {
|
||||||
res = ::mkfifo(_cname.c_str(), mode);
|
res = ::mkfifo(_cname.c_str(), mode);
|
||||||
else
|
} else {
|
||||||
res = ::mknod(_cname.c_str(), mode, rdev);
|
res = ::mknod(_cname.c_str(), mode, rdev);
|
||||||
|
}
|
||||||
|
|
||||||
if (olduid >= 0) setfsuid(olduid);
|
if (olduid >= 0) setfsuid(olduid);
|
||||||
if (oldgid >= 0) setfsgid(oldgid);
|
if (oldgid >= 0) setfsgid(oldgid);
|
||||||
@ -242,10 +246,11 @@ int FileNode::sync(bool datasync) {
|
|||||||
if (fh >= 0) {
|
if (fh >= 0) {
|
||||||
int res = -EIO;
|
int res = -EIO;
|
||||||
#ifdef linux
|
#ifdef linux
|
||||||
if (datasync)
|
if (datasync) {
|
||||||
res = fdatasync(fh);
|
res = fdatasync(fh);
|
||||||
else
|
} else {
|
||||||
res = fsync(fh);
|
res = fsync(fh);
|
||||||
|
}
|
||||||
#else
|
#else
|
||||||
(void)datasync;
|
(void)datasync;
|
||||||
// no fdatasync support
|
// no fdatasync support
|
||||||
@ -256,8 +261,9 @@ int FileNode::sync(bool datasync) {
|
|||||||
if (res == -1) res = -errno;
|
if (res == -1) res = -errno;
|
||||||
|
|
||||||
return res;
|
return res;
|
||||||
} else
|
} else {
|
||||||
return fh;
|
return fh;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace encfs
|
} // namespace encfs
|
||||||
|
@ -125,7 +125,7 @@ EncFS_Root::~EncFS_Root() = default;
|
|||||||
|
|
||||||
bool fileExists(const char *fileName) {
|
bool fileExists(const char *fileName) {
|
||||||
struct stat buf;
|
struct stat buf;
|
||||||
if (!lstat(fileName, &buf)) {
|
if (lstat(fileName, &buf) == 0) {
|
||||||
return true;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
// XXX show perror?
|
// XXX show perror?
|
||||||
@ -135,7 +135,7 @@ bool fileExists(const char *fileName) {
|
|||||||
|
|
||||||
bool isDirectory(const char *fileName) {
|
bool isDirectory(const char *fileName) {
|
||||||
struct stat buf;
|
struct stat buf;
|
||||||
if (!lstat(fileName, &buf)) {
|
if (lstat(fileName, &buf) == 0) {
|
||||||
return S_ISDIR(buf.st_mode);
|
return S_ISDIR(buf.st_mode);
|
||||||
} else {
|
} else {
|
||||||
return false;
|
return false;
|
||||||
@ -143,24 +143,26 @@ bool isDirectory(const char *fileName) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool isAbsolutePath(const char *fileName) {
|
bool isAbsolutePath(const char *fileName) {
|
||||||
if (fileName && fileName[0] != '\0' && fileName[0] == '/')
|
if ((fileName != nullptr) && fileName[0] != '\0' && fileName[0] == '/') {
|
||||||
return true;
|
return true;
|
||||||
else
|
} else {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const char *lastPathElement(const char *name) {
|
const char *lastPathElement(const char *name) {
|
||||||
const char *loc = strrchr(name, '/');
|
const char *loc = strrchr(name, '/');
|
||||||
return loc ? loc + 1 : name;
|
return loc != nullptr ? loc + 1 : name;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string parentDirectory(const std::string &path) {
|
std::string parentDirectory(const std::string &path) {
|
||||||
size_t last = path.find_last_of('/');
|
size_t last = path.find_last_of('/');
|
||||||
if (last == string::npos)
|
if (last == string::npos) {
|
||||||
return string("");
|
return string("");
|
||||||
else
|
} else {
|
||||||
return path.substr(0, last);
|
return path.substr(0, last);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool userAllowMkdir(const char *path, mode_t mode) {
|
bool userAllowMkdir(const char *path, mode_t mode) {
|
||||||
return userAllowMkdir(0, path, mode);
|
return userAllowMkdir(0, path, mode);
|
||||||
@ -194,8 +196,9 @@ bool userAllowMkdir(int promptno, const char *path, mode_t mode) {
|
|||||||
if (result < 0) {
|
if (result < 0) {
|
||||||
perror(_("Unable to create directory: "));
|
perror(_("Unable to create directory: "));
|
||||||
return false;
|
return false;
|
||||||
} else
|
} else {
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// Directory not created, by user request
|
// Directory not created, by user request
|
||||||
cerr << _("Directory not created.") << "\n";
|
cerr << _("Directory not created.") << "\n";
|
||||||
@ -208,7 +211,7 @@ bool userAllowMkdir(int promptno, const char *path, mode_t mode) {
|
|||||||
*/
|
*/
|
||||||
ConfigType readConfig_load(ConfigInfo *nm, const char *path,
|
ConfigType readConfig_load(ConfigInfo *nm, const char *path,
|
||||||
EncFSConfig *config) {
|
EncFSConfig *config) {
|
||||||
if (nm->loadFunc) {
|
if (nm->loadFunc != nullptr) {
|
||||||
try {
|
try {
|
||||||
if ((*nm->loadFunc)(path, config, nm)) {
|
if ((*nm->loadFunc)(path, config, nm)) {
|
||||||
config->cfgType = nm->type;
|
config->cfgType = nm->type;
|
||||||
@ -234,7 +237,7 @@ ConfigType readConfig_load(ConfigInfo *nm, const char *path,
|
|||||||
*/
|
*/
|
||||||
ConfigType readConfig(const string &rootDir, EncFSConfig *config) {
|
ConfigType readConfig(const string &rootDir, EncFSConfig *config) {
|
||||||
ConfigInfo *nm = ConfigFileMapping;
|
ConfigInfo *nm = ConfigFileMapping;
|
||||||
while (nm->fileName) {
|
while (nm->fileName != nullptr) {
|
||||||
// allow environment variable to override default config path
|
// allow environment variable to override default config path
|
||||||
if (nm->environmentOverride != nullptr) {
|
if (nm->environmentOverride != nullptr) {
|
||||||
char *envFile = getenv(nm->environmentOverride);
|
char *envFile = getenv(nm->environmentOverride);
|
||||||
@ -250,8 +253,9 @@ ConfigType readConfig(const string &rootDir, EncFSConfig *config) {
|
|||||||
}
|
}
|
||||||
// the standard place to look is in the root directory
|
// the standard place to look is in the root directory
|
||||||
string path = rootDir + nm->fileName;
|
string path = rootDir + nm->fileName;
|
||||||
if (fileExists(path.c_str()))
|
if (fileExists(path.c_str())) {
|
||||||
return readConfig_load(nm, path.c_str(), config);
|
return readConfig_load(nm, path.c_str(), config);
|
||||||
|
}
|
||||||
|
|
||||||
++nm;
|
++nm;
|
||||||
}
|
}
|
||||||
@ -446,8 +450,8 @@ bool saveConfig(ConfigType type, const string &rootDir,
|
|||||||
bool ok = false;
|
bool ok = false;
|
||||||
|
|
||||||
ConfigInfo *nm = ConfigFileMapping;
|
ConfigInfo *nm = ConfigFileMapping;
|
||||||
while (nm->fileName) {
|
while (nm->fileName != nullptr) {
|
||||||
if (nm->type == type && nm->saveFunc) {
|
if (nm->type == type && (nm->saveFunc != nullptr)) {
|
||||||
string path = rootDir + nm->fileName;
|
string path = rootDir + nm->fileName;
|
||||||
if (nm->environmentOverride != nullptr) {
|
if (nm->environmentOverride != nullptr) {
|
||||||
// use environment file if specified..
|
// use environment file if specified..
|
||||||
@ -593,7 +597,8 @@ static Cipher::CipherAlgorithm findCipherAlgorithm(const char *name,
|
|||||||
Cipher::AlgorithmList algorithms = Cipher::GetAlgorithmList();
|
Cipher::AlgorithmList algorithms = Cipher::GetAlgorithmList();
|
||||||
Cipher::AlgorithmList::const_iterator it;
|
Cipher::AlgorithmList::const_iterator it;
|
||||||
for (it = algorithms.begin(); it != algorithms.end(); ++it) {
|
for (it = algorithms.begin(); it != algorithms.end(); ++it) {
|
||||||
if (!strcmp(name, it->name.c_str()) && it->keyLength.allowed(keySize)) {
|
if ((strcmp(name, it->name.c_str()) == 0) &&
|
||||||
|
it->keyLength.allowed(keySize)) {
|
||||||
return *it;
|
return *it;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -659,8 +664,9 @@ static Cipher::CipherAlgorithm selectCipherAlgorithm() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
it = algorithms.begin();
|
it = algorithms.begin();
|
||||||
while (--cipherNum) // numbering starts at 1
|
while (--cipherNum != 0) { // numbering starts at 1
|
||||||
++it;
|
++it;
|
||||||
|
}
|
||||||
|
|
||||||
Cipher::CipherAlgorithm alg = *it;
|
Cipher::CipherAlgorithm alg = *it;
|
||||||
|
|
||||||
@ -702,8 +708,9 @@ static Interface selectNameCoding() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
it = algorithms.begin();
|
it = algorithms.begin();
|
||||||
while (--algNum) // numbering starts at 1
|
while (--algNum != 0) { // numbering starts at 1
|
||||||
++it;
|
++it;
|
||||||
|
}
|
||||||
|
|
||||||
// xgroup(setup)
|
// xgroup(setup)
|
||||||
cout << autosprintf(_("Selected algorithm \"%s\""), it->name.c_str())
|
cout << autosprintf(_("Selected algorithm \"%s\""), it->name.c_str())
|
||||||
@ -738,13 +745,13 @@ static int selectKeySize(const Cipher::CipherAlgorithm &alg) {
|
|||||||
if (numAvail < 5) {
|
if (numAvail < 5) {
|
||||||
// show them all
|
// show them all
|
||||||
for (int i = 0; i <= numAvail; ++i) {
|
for (int i = 0; i <= numAvail; ++i) {
|
||||||
if (i) cout << ", ";
|
if (i != 0) cout << ", ";
|
||||||
cout << alg.keyLength.min() + i * alg.keyLength.inc();
|
cout << alg.keyLength.min() + i * alg.keyLength.inc();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// partial
|
// partial
|
||||||
for (int i = 0; i < 3; ++i) {
|
for (int i = 0; i < 3; ++i) {
|
||||||
if (i) cout << ", ";
|
if (i != 0) cout << ", ";
|
||||||
cout << alg.keyLength.min() + i * alg.keyLength.inc();
|
cout << alg.keyLength.min() + i * alg.keyLength.inc();
|
||||||
}
|
}
|
||||||
cout << " ... " << alg.keyLength.max() - alg.keyLength.inc();
|
cout << " ... " << alg.keyLength.max() - alg.keyLength.inc();
|
||||||
@ -795,8 +802,9 @@ static int selectBlockSize(const Cipher::CipherAlgorithm &alg) {
|
|||||||
char *res = fgets(answer, sizeof(answer), stdin);
|
char *res = fgets(answer, sizeof(answer), stdin);
|
||||||
cout << "\n";
|
cout << "\n";
|
||||||
|
|
||||||
if (res != nullptr && atoi(answer) >= alg.blockSize.min())
|
if (res != nullptr && atoi(answer) >= alg.blockSize.min()) {
|
||||||
blockSize = atoi(answer);
|
blockSize = atoi(answer);
|
||||||
|
}
|
||||||
|
|
||||||
blockSize = alg.blockSize.closest(blockSize);
|
blockSize = alg.blockSize.closest(blockSize);
|
||||||
|
|
||||||
@ -818,10 +826,11 @@ static bool boolDefault(const char *prompt, bool defaultValue) {
|
|||||||
|
|
||||||
string yesno;
|
string yesno;
|
||||||
|
|
||||||
if (defaultValue == true)
|
if (defaultValue) {
|
||||||
yesno = "[y]/n: ";
|
yesno = "[y]/n: ";
|
||||||
else
|
} else {
|
||||||
yesno = "y/[n]: ";
|
yesno = "y/[n]: ";
|
||||||
|
}
|
||||||
|
|
||||||
string response;
|
string response;
|
||||||
bool value;
|
bool value;
|
||||||
@ -875,10 +884,11 @@ static void selectBlockMAC(int *macBytes, int *macRandBytes, bool forceMac) {
|
|||||||
addMAC = true;
|
addMAC = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (addMAC)
|
if (addMAC) {
|
||||||
*macBytes = 8;
|
*macBytes = 8;
|
||||||
else
|
} else {
|
||||||
*macBytes = 0;
|
*macBytes = 0;
|
||||||
|
}
|
||||||
|
|
||||||
// xgroup(setup)
|
// xgroup(setup)
|
||||||
cout << _(
|
cout << _(
|
||||||
@ -1057,7 +1067,7 @@ RootPtr createV6Config(EncFS_Context *ctx,
|
|||||||
/* Reverse mounts are read-only by default (set in main.cpp).
|
/* Reverse mounts are read-only by default (set in main.cpp).
|
||||||
* If uniqueIV is off, writing can be allowed, because there
|
* If uniqueIV is off, writing can be allowed, because there
|
||||||
* is no header that could be overwritten */
|
* is no header that could be overwritten */
|
||||||
if (uniqueIV == false) opts->readOnly = false;
|
if (!uniqueIV) opts->readOnly = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1085,13 +1095,13 @@ RootPtr createV6Config(EncFS_Context *ctx,
|
|||||||
/* Reverse mounts are read-only by default (set in main.cpp).
|
/* Reverse mounts are read-only by default (set in main.cpp).
|
||||||
* If uniqueIV is off, writing can be allowed, because there
|
* If uniqueIV is off, writing can be allowed, because there
|
||||||
* is no header that could be overwritten */
|
* is no header that could be overwritten */
|
||||||
if (uniqueIV == false) opts->readOnly = false;
|
if (!uniqueIV) opts->readOnly = false;
|
||||||
} else {
|
} else {
|
||||||
chainedIV = selectChainedIV();
|
chainedIV = selectChainedIV();
|
||||||
uniqueIV = selectUniqueIV(true);
|
uniqueIV = selectUniqueIV(true);
|
||||||
if (chainedIV && uniqueIV)
|
if (chainedIV && uniqueIV) {
|
||||||
externalIV = selectExternalChainedIV();
|
externalIV = selectExternalChainedIV();
|
||||||
else {
|
} else {
|
||||||
// xgroup(setup)
|
// xgroup(setup)
|
||||||
cout << _("External chained IV disabled, as both 'IV chaining'\n"
|
cout << _("External chained IV disabled, as both 'IV chaining'\n"
|
||||||
"and 'unique IV' features are required for this option.")
|
"and 'unique IV' features are required for this option.")
|
||||||
@ -1172,10 +1182,11 @@ RootPtr createV6Config(EncFS_Context *ctx,
|
|||||||
if (useStdin) {
|
if (useStdin) {
|
||||||
if (annotate) cerr << "$PROMPT$ new_passwd" << endl;
|
if (annotate) cerr << "$PROMPT$ new_passwd" << endl;
|
||||||
userKey = config->getUserKey(useStdin);
|
userKey = config->getUserKey(useStdin);
|
||||||
} else if (!passwordProgram.empty())
|
} else if (!passwordProgram.empty()) {
|
||||||
userKey = config->getUserKey(passwordProgram, rootDir);
|
userKey = config->getUserKey(passwordProgram, rootDir);
|
||||||
else
|
} else {
|
||||||
userKey = config->getNewUserKey();
|
userKey = config->getNewUserKey();
|
||||||
|
}
|
||||||
|
|
||||||
cipher->writeKey(volumeKey, encodedKey, userKey);
|
cipher->writeKey(volumeKey, encodedKey, userKey);
|
||||||
userKey.reset();
|
userKey.reset();
|
||||||
@ -1234,19 +1245,20 @@ void showFSInfo(const EncFSConfig *config) {
|
|||||||
config->cipherIface.name().c_str(), config->cipherIface.current(),
|
config->cipherIface.name().c_str(), config->cipherIface.current(),
|
||||||
config->cipherIface.revision(), config->cipherIface.age());
|
config->cipherIface.revision(), config->cipherIface.age());
|
||||||
// check if we support this interface..
|
// check if we support this interface..
|
||||||
if (!cipher)
|
if (!cipher) {
|
||||||
cout << _(" (NOT supported)\n");
|
cout << _(" (NOT supported)\n");
|
||||||
else {
|
} else {
|
||||||
// if we're using a newer interface, show the version number
|
// if we're using a newer interface, show the version number
|
||||||
if (config->cipherIface != cipher->interface()) {
|
if (config->cipherIface != cipher->interface()) {
|
||||||
Interface iface = cipher->interface();
|
Interface iface = cipher->interface();
|
||||||
// xgroup(diag)
|
// xgroup(diag)
|
||||||
cout << autosprintf(_(" (using %i:%i:%i)\n"), iface.current(),
|
cout << autosprintf(_(" (using %i:%i:%i)\n"), iface.current(),
|
||||||
iface.revision(), iface.age());
|
iface.revision(), iface.age());
|
||||||
} else
|
} else {
|
||||||
cout << "\n";
|
cout << "\n";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
{
|
{
|
||||||
// xgroup(diag)
|
// xgroup(diag)
|
||||||
cout << autosprintf(_("Filename encoding: \"%s\", version %i:%i:%i"),
|
cout << autosprintf(_("Filename encoding: \"%s\", version %i:%i:%i"),
|
||||||
@ -1266,19 +1278,21 @@ void showFSInfo(const EncFSConfig *config) {
|
|||||||
Interface iface = nameCoder->interface();
|
Interface iface = nameCoder->interface();
|
||||||
cout << autosprintf(_(" (using %i:%i:%i)\n"), iface.current(),
|
cout << autosprintf(_(" (using %i:%i:%i)\n"), iface.current(),
|
||||||
iface.revision(), iface.age());
|
iface.revision(), iface.age());
|
||||||
} else
|
} else {
|
||||||
cout << "\n";
|
cout << "\n";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
{
|
{
|
||||||
cout << autosprintf(_("Key Size: %i bits"), config->keySize);
|
cout << autosprintf(_("Key Size: %i bits"), config->keySize);
|
||||||
cipher = config->getCipher();
|
cipher = config->getCipher();
|
||||||
if (!cipher) {
|
if (!cipher) {
|
||||||
// xgroup(diag)
|
// xgroup(diag)
|
||||||
cout << _(" (NOT supported)\n");
|
cout << _(" (NOT supported)\n");
|
||||||
} else
|
} else {
|
||||||
cout << "\n";
|
cout << "\n";
|
||||||
}
|
}
|
||||||
|
}
|
||||||
if (config->kdfIterations > 0 && config->salt.size() > 0) {
|
if (config->kdfIterations > 0 && config->salt.size() > 0) {
|
||||||
cout << autosprintf(_("Using PBKDF2, with %i iterations"),
|
cout << autosprintf(_("Using PBKDF2, with %i iterations"),
|
||||||
config->kdfIterations)
|
config->kdfIterations)
|
||||||
@ -1286,7 +1300,7 @@ void showFSInfo(const EncFSConfig *config) {
|
|||||||
cout << autosprintf(_("Salt Size: %i bits"), (int)(8 * config->salt.size()))
|
cout << autosprintf(_("Salt Size: %i bits"), (int)(8 * config->salt.size()))
|
||||||
<< "\n";
|
<< "\n";
|
||||||
}
|
}
|
||||||
if (config->blockMACBytes || config->blockMACRandBytes) {
|
if ((config->blockMACBytes != 0) || (config->blockMACRandBytes != 0)) {
|
||||||
if (config->subVersion < 20040813) {
|
if (config->subVersion < 20040813) {
|
||||||
cout << autosprintf(
|
cout << autosprintf(
|
||||||
// xgroup(diag)
|
// xgroup(diag)
|
||||||
@ -1392,8 +1406,9 @@ CipherKey EncFSConfig::getUserKey(bool useStdin) {
|
|||||||
if (useStdin) {
|
if (useStdin) {
|
||||||
res = fgets(passBuf, sizeof(passBuf), stdin);
|
res = fgets(passBuf, sizeof(passBuf), stdin);
|
||||||
// Kill the trailing newline.
|
// Kill the trailing newline.
|
||||||
if (passBuf[strlen(passBuf) - 1] == '\n')
|
if (passBuf[strlen(passBuf) - 1] == '\n') {
|
||||||
passBuf[strlen(passBuf) - 1] = '\0';
|
passBuf[strlen(passBuf) - 1] = '\0';
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// xgroup(common)
|
// xgroup(common)
|
||||||
res = readpassphrase(_("EncFS Password: "), passBuf, sizeof(passBuf),
|
res = readpassphrase(_("EncFS Password: "), passBuf, sizeof(passBuf),
|
||||||
@ -1401,7 +1416,7 @@ CipherKey EncFSConfig::getUserKey(bool useStdin) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
CipherKey userKey;
|
CipherKey userKey;
|
||||||
if (!res) {
|
if (res == nullptr) {
|
||||||
cerr << _("fatal: error reading password\n");
|
cerr << _("fatal: error reading password\n");
|
||||||
exit(1);
|
exit(1);
|
||||||
} else {
|
} else {
|
||||||
@ -1423,15 +1438,17 @@ std::string readPassword(int FD) {
|
|||||||
if (rdSize > 0) {
|
if (rdSize > 0) {
|
||||||
result.append(buffer, rdSize);
|
result.append(buffer, rdSize);
|
||||||
memset(buffer, 0, sizeof(buffer));
|
memset(buffer, 0, sizeof(buffer));
|
||||||
} else
|
} else {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// chop off trailing "\n" if present..
|
// chop off trailing "\n" if present..
|
||||||
// This is done so that we can use standard programs like ssh-askpass
|
// This is done so that we can use standard programs like ssh-askpass
|
||||||
// without modification, as it returns trailing newline..
|
// without modification, as it returns trailing newline..
|
||||||
if (!result.empty() && result[result.length() - 1] == '\n')
|
if (!result.empty() && result[result.length() - 1] == '\n') {
|
||||||
result.resize(result.length() - 1);
|
result.resize(result.length() - 1);
|
||||||
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@ -1525,7 +1542,8 @@ CipherKey EncFSConfig::getNewUserKey() {
|
|||||||
char *res2 = readpassphrase(_("Verify Encfs Password: "), passBuf2,
|
char *res2 = readpassphrase(_("Verify Encfs Password: "), passBuf2,
|
||||||
sizeof(passBuf2) - 1, RPP_ECHO_OFF);
|
sizeof(passBuf2) - 1, RPP_ECHO_OFF);
|
||||||
|
|
||||||
if (res1 && res2 && !strcmp(passBuf, passBuf2)) {
|
if ((res1 != nullptr) && (res2 != nullptr) &&
|
||||||
|
(strcmp(passBuf, passBuf2) == 0)) {
|
||||||
userKey = makeKey(passBuf, strlen(passBuf));
|
userKey = makeKey(passBuf, strlen(passBuf));
|
||||||
} else {
|
} else {
|
||||||
// xgroup(common) -- probably not common, but group with the others
|
// xgroup(common) -- probably not common, but group with the others
|
||||||
@ -1560,7 +1578,7 @@ RootPtr initFS(EncFS_Context *ctx, const std::shared_ptr<EncFS_Opts> &opts) {
|
|||||||
/* Reverse mounts are read-only by default (set in main.cpp).
|
/* Reverse mounts are read-only by default (set in main.cpp).
|
||||||
* If uniqueIV is off, writing can be allowed, because there
|
* If uniqueIV is off, writing can be allowed, because there
|
||||||
* is no header that could be overwritten */
|
* is no header that could be overwritten */
|
||||||
if (config->uniqueIV == false) opts->readOnly = false;
|
if (!config->uniqueIV) opts->readOnly = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// first, instanciate the cipher.
|
// first, instanciate the cipher.
|
||||||
@ -1589,8 +1607,9 @@ RootPtr initFS(EncFS_Context *ctx, const std::shared_ptr<EncFS_Opts> &opts) {
|
|||||||
VLOG(1) << "useStdin: " << opts->useStdin;
|
VLOG(1) << "useStdin: " << opts->useStdin;
|
||||||
if (opts->annotate) cerr << "$PROMPT$ passwd" << endl;
|
if (opts->annotate) cerr << "$PROMPT$ passwd" << endl;
|
||||||
userKey = config->getUserKey(opts->useStdin);
|
userKey = config->getUserKey(opts->useStdin);
|
||||||
} else
|
} else {
|
||||||
userKey = config->getUserKey(opts->passwordProgram, opts->rootDir);
|
userKey = config->getUserKey(opts->passwordProgram, opts->rootDir);
|
||||||
|
}
|
||||||
|
|
||||||
if (!userKey) return rootInfo;
|
if (!userKey) return rootInfo;
|
||||||
|
|
||||||
|
@ -83,13 +83,14 @@ static int sign( int a, int b )
|
|||||||
#else
|
#else
|
||||||
// simple, easy to check, unlikely to break due to unforseen events..
|
// simple, easy to check, unlikely to break due to unforseen events..
|
||||||
static int sign(int a, int b) {
|
static int sign(int a, int b) {
|
||||||
if (a < b)
|
if (a < b) {
|
||||||
return 0;
|
return 0;
|
||||||
else if (a == b)
|
} else if (a == b) {
|
||||||
return 1;
|
return 1;
|
||||||
else
|
} else {
|
||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
static int diffSum(const Interface &A, const Interface &B) {
|
static int diffSum(const Interface &A, const Interface &B) {
|
||||||
@ -116,30 +117,34 @@ bool Interface::implements(const Interface &B) const {
|
|||||||
bool operator<(const Interface &A, const Interface &B) {
|
bool operator<(const Interface &A, const Interface &B) {
|
||||||
if (A.name() == B.name()) {
|
if (A.name() == B.name()) {
|
||||||
return (diffSum(A, B) < EqualVersion);
|
return (diffSum(A, B) < EqualVersion);
|
||||||
} else
|
} else {
|
||||||
return A.name() < B.name();
|
return A.name() < B.name();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool operator>(const Interface &A, const Interface &B) {
|
bool operator>(const Interface &A, const Interface &B) {
|
||||||
if (A.name() == B.name()) {
|
if (A.name() == B.name()) {
|
||||||
return (diffSum(A, B) > EqualVersion);
|
return (diffSum(A, B) > EqualVersion);
|
||||||
} else
|
} else {
|
||||||
return A.name() < B.name();
|
return A.name() < B.name();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool operator<=(const Interface &A, const Interface &B) {
|
bool operator<=(const Interface &A, const Interface &B) {
|
||||||
if (A.name() == B.name()) {
|
if (A.name() == B.name()) {
|
||||||
return (diffSum(A, B) <= EqualVersion);
|
return (diffSum(A, B) <= EqualVersion);
|
||||||
} else
|
} else {
|
||||||
return A.name() < B.name();
|
return A.name() < B.name();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bool operator>=(const Interface &A, const Interface &B) {
|
bool operator>=(const Interface &A, const Interface &B) {
|
||||||
if (A.name() == B.name()) {
|
if (A.name() == B.name()) {
|
||||||
return (diffSum(A, B) >= EqualVersion);
|
return (diffSum(A, B) >= EqualVersion);
|
||||||
} else
|
} else {
|
||||||
return A.name() < B.name();
|
return A.name() < B.name();
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
ConfigVar &operator<<(ConfigVar &dst, const Interface &iface) {
|
ConfigVar &operator<<(ConfigVar &dst, const Interface &iface) {
|
||||||
dst << iface.name() << iface.current() << iface.revision() << iface.age();
|
dst << iface.name() << iface.current() << iface.revision() << iface.age();
|
||||||
|
@ -160,13 +160,15 @@ ssize_t MACFileIO::readOneBlock(const IORequest &req) const {
|
|||||||
// don't store zeros if configured for zero-block pass-through
|
// don't store zeros if configured for zero-block pass-through
|
||||||
bool skipBlock = true;
|
bool skipBlock = true;
|
||||||
if (_allowHoles) {
|
if (_allowHoles) {
|
||||||
for (int i = 0; i < readSize; ++i)
|
for (int i = 0; i < readSize; ++i) {
|
||||||
if (tmp.data[i] != 0) {
|
if (tmp.data[i] != 0) {
|
||||||
skipBlock = false;
|
skipBlock = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
} else if (macBytes > 0)
|
}
|
||||||
|
} else if (macBytes > 0) {
|
||||||
skipBlock = false;
|
skipBlock = false;
|
||||||
|
}
|
||||||
|
|
||||||
if (readSize > headerSize) {
|
if (readSize > headerSize) {
|
||||||
if (!skipBlock) {
|
if (!skipBlock) {
|
||||||
@ -224,9 +226,10 @@ bool MACFileIO::writeOneBlock(const IORequest &req) {
|
|||||||
memset(newReq.data, 0, headerSize);
|
memset(newReq.data, 0, headerSize);
|
||||||
memcpy(newReq.data + headerSize, req.data, req.dataLen);
|
memcpy(newReq.data + headerSize, req.data, req.dataLen);
|
||||||
if (randBytes > 0) {
|
if (randBytes > 0) {
|
||||||
if (!cipher->randomize(newReq.data + macBytes, randBytes, false))
|
if (!cipher->randomize(newReq.data + macBytes, randBytes, false)) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (macBytes > 0) {
|
if (macBytes > 0) {
|
||||||
// compute the mac (which includes the random data) and fill it in
|
// compute the mac (which includes the random data) and fill it in
|
||||||
|
@ -75,15 +75,16 @@ MemBlock MemoryPool::allocate(int size) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unlink block from list
|
// unlink block from list
|
||||||
if (block) {
|
if (block != nullptr) {
|
||||||
if (!parent)
|
if (parent == nullptr) {
|
||||||
gMemPool = block->next;
|
gMemPool = block->next;
|
||||||
else
|
} else {
|
||||||
parent->next = block->next;
|
parent->next = block->next;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
pthread_mutex_unlock(&gMPoolMutex);
|
pthread_mutex_unlock(&gMPoolMutex);
|
||||||
|
|
||||||
if (!block) block = allocBlock(size);
|
if (block == nullptr) block = allocBlock(size);
|
||||||
block->next = nullptr;
|
block->next = nullptr;
|
||||||
|
|
||||||
MemBlock result;
|
MemBlock result;
|
||||||
|
@ -62,7 +62,7 @@ list<NameIO::Algorithm> NameIO::GetAlgorithmList(bool includeHidden) {
|
|||||||
AddSymbolReferences();
|
AddSymbolReferences();
|
||||||
|
|
||||||
list<Algorithm> result;
|
list<Algorithm> result;
|
||||||
if (gNameIOMap) {
|
if (gNameIOMap != nullptr) {
|
||||||
NameIOMap_t::const_iterator it;
|
NameIOMap_t::const_iterator it;
|
||||||
NameIOMap_t::const_iterator end = gNameIOMap->end();
|
NameIOMap_t::const_iterator end = gNameIOMap->end();
|
||||||
for (it = gNameIOMap->begin(); it != end; ++it) {
|
for (it = gNameIOMap->begin(); it != end; ++it) {
|
||||||
@ -83,7 +83,7 @@ list<NameIO::Algorithm> NameIO::GetAlgorithmList(bool includeHidden) {
|
|||||||
bool NameIO::Register(const char *name, const char *description,
|
bool NameIO::Register(const char *name, const char *description,
|
||||||
const Interface &iface, Constructor constructor,
|
const Interface &iface, Constructor constructor,
|
||||||
bool hidden) {
|
bool hidden) {
|
||||||
if (!gNameIOMap) gNameIOMap = new NameIOMap_t;
|
if (gNameIOMap == nullptr) gNameIOMap = new NameIOMap_t;
|
||||||
|
|
||||||
NameIOAlg alg;
|
NameIOAlg alg;
|
||||||
alg.hidden = hidden;
|
alg.hidden = hidden;
|
||||||
@ -98,7 +98,7 @@ std::shared_ptr<NameIO> NameIO::New(const string &name,
|
|||||||
const std::shared_ptr<Cipher> &cipher,
|
const std::shared_ptr<Cipher> &cipher,
|
||||||
const CipherKey &key) {
|
const CipherKey &key) {
|
||||||
std::shared_ptr<NameIO> result;
|
std::shared_ptr<NameIO> result;
|
||||||
if (gNameIOMap) {
|
if (gNameIOMap != nullptr) {
|
||||||
NameIOMap_t::const_iterator it = gNameIOMap->find(name);
|
NameIOMap_t::const_iterator it = gNameIOMap->find(name);
|
||||||
if (it != gNameIOMap->end()) {
|
if (it != gNameIOMap->end()) {
|
||||||
Constructor fn = it->second.constructor;
|
Constructor fn = it->second.constructor;
|
||||||
@ -111,7 +111,7 @@ std::shared_ptr<NameIO> NameIO::New(const Interface &iface,
|
|||||||
const std::shared_ptr<Cipher> &cipher,
|
const std::shared_ptr<Cipher> &cipher,
|
||||||
const CipherKey &key) {
|
const CipherKey &key) {
|
||||||
std::shared_ptr<NameIO> result;
|
std::shared_ptr<NameIO> result;
|
||||||
if (gNameIOMap) {
|
if (gNameIOMap != nullptr) {
|
||||||
NameIOMap_t::const_iterator it;
|
NameIOMap_t::const_iterator it;
|
||||||
NameIOMap_t::const_iterator end = gNameIOMap->end();
|
NameIOMap_t::const_iterator end = gNameIOMap->end();
|
||||||
for (it = gNameIOMap->begin(); it != end; ++it) {
|
for (it = gNameIOMap->begin(); it != end; ++it) {
|
||||||
@ -143,15 +143,16 @@ std::string NameIO::recodePath(
|
|||||||
uint64_t *iv) const {
|
uint64_t *iv) const {
|
||||||
string output;
|
string output;
|
||||||
|
|
||||||
while (*path) {
|
while (*path != 0) {
|
||||||
if (*path == '/') {
|
if (*path == '/') {
|
||||||
if (!output.empty()) // don't start the string with '/'
|
if (!output.empty()) { // don't start the string with '/'
|
||||||
output += '/';
|
output += '/';
|
||||||
|
}
|
||||||
++path;
|
++path;
|
||||||
} else {
|
} else {
|
||||||
bool isDotFile = (*path == '.');
|
bool isDotFile = (*path == '.');
|
||||||
const char *next = strchr(path, '/');
|
const char *next = strchr(path, '/');
|
||||||
int len = next ? next - path : strlen(path);
|
int len = next != nullptr ? next - path : strlen(path);
|
||||||
|
|
||||||
// at this point we know that len > 0
|
// at this point we know that len > 0
|
||||||
if (isDotFile && (path[len - 1] == '.') && (len <= 2)) {
|
if (isDotFile && (path[len - 1] == '.') && (len <= 2)) {
|
||||||
|
@ -113,7 +113,7 @@ static int open_readonly_workaround(const char *path, int flags) {
|
|||||||
it..
|
it..
|
||||||
*/
|
*/
|
||||||
int RawFileIO::open(int flags) {
|
int RawFileIO::open(int flags) {
|
||||||
bool requestWrite = ((flags & O_RDWR) || (flags & O_WRONLY));
|
bool requestWrite = (((flags & O_RDWR) != 0) || ((flags & O_WRONLY) != 0));
|
||||||
VLOG(1) << "open call, requestWrite = " << requestWrite;
|
VLOG(1) << "open call, requestWrite = " << requestWrite;
|
||||||
|
|
||||||
int result = 0;
|
int result = 0;
|
||||||
@ -126,7 +126,7 @@ int RawFileIO::open(int flags) {
|
|||||||
int finalFlags = requestWrite ? O_RDWR : O_RDONLY;
|
int finalFlags = requestWrite ? O_RDWR : O_RDONLY;
|
||||||
|
|
||||||
#if defined(O_LARGEFILE)
|
#if defined(O_LARGEFILE)
|
||||||
if (flags & O_LARGEFILE) finalFlags |= O_LARGEFILE;
|
if ((flags & O_LARGEFILE) != 0) finalFlags |= O_LARGEFILE;
|
||||||
#else
|
#else
|
||||||
#warning O_LARGEFILE not supported
|
#warning O_LARGEFILE not supported
|
||||||
#endif
|
#endif
|
||||||
@ -209,14 +209,14 @@ ssize_t RawFileIO::read(const IORequest &req) const {
|
|||||||
|
|
||||||
bool RawFileIO::write(const IORequest &req) {
|
bool RawFileIO::write(const IORequest &req) {
|
||||||
rAssert(fd >= 0);
|
rAssert(fd >= 0);
|
||||||
rAssert(true == canWrite);
|
rAssert(canWrite);
|
||||||
|
|
||||||
int retrys = 10;
|
int retrys = 10;
|
||||||
void *buf = req.data;
|
void *buf = req.data;
|
||||||
ssize_t bytes = req.dataLen;
|
ssize_t bytes = req.dataLen;
|
||||||
off_t offset = req.offset;
|
off_t offset = req.offset;
|
||||||
|
|
||||||
while (bytes && retrys > 0) {
|
while ((bytes != 0) && retrys > 0) {
|
||||||
ssize_t writeSize = ::pwrite(fd, buf, bytes, offset);
|
ssize_t writeSize = ::pwrite(fd, buf, bytes, offset);
|
||||||
|
|
||||||
if (writeSize < 0) {
|
if (writeSize < 0) {
|
||||||
@ -255,8 +255,9 @@ int RawFileIO::truncate(off_t size) {
|
|||||||
#if !defined(__FreeBSD__) && !defined(__APPLE__)
|
#if !defined(__FreeBSD__) && !defined(__APPLE__)
|
||||||
::fdatasync(fd);
|
::fdatasync(fd);
|
||||||
#endif
|
#endif
|
||||||
} else
|
} else {
|
||||||
res = ::truncate(name.c_str(), size);
|
res = ::truncate(name.c_str(), size);
|
||||||
|
}
|
||||||
|
|
||||||
if (res < 0) {
|
if (res < 0) {
|
||||||
int eno = errno;
|
int eno = errno;
|
||||||
|
@ -66,21 +66,22 @@ inline int MIN(int a, int b) { return (a < b) ? a : b; }
|
|||||||
int BytesToKey(int keyLen, int ivLen, const EVP_MD *md,
|
int BytesToKey(int keyLen, int ivLen, const EVP_MD *md,
|
||||||
const unsigned char *data, int dataLen, unsigned int rounds,
|
const unsigned char *data, int dataLen, unsigned int rounds,
|
||||||
unsigned char *key, unsigned char *iv) {
|
unsigned char *key, unsigned char *iv) {
|
||||||
if (data == nullptr || dataLen == 0)
|
if (data == nullptr || dataLen == 0) {
|
||||||
return 0; // OpenSSL returns nkey here, but why? It is a failure..
|
return 0; // OpenSSL returns nkey here, but why? It is a failure..
|
||||||
|
}
|
||||||
|
|
||||||
unsigned char mdBuf[EVP_MAX_MD_SIZE];
|
unsigned char mdBuf[EVP_MAX_MD_SIZE];
|
||||||
unsigned int mds = 0;
|
unsigned int mds = 0;
|
||||||
int addmd = 0;
|
int addmd = 0;
|
||||||
int nkey = key ? keyLen : 0;
|
int nkey = key != nullptr ? keyLen : 0;
|
||||||
int niv = iv ? ivLen : 0;
|
int niv = iv != nullptr ? ivLen : 0;
|
||||||
|
|
||||||
EVP_MD_CTX *cx = EVP_MD_CTX_new();
|
EVP_MD_CTX *cx = EVP_MD_CTX_new();
|
||||||
EVP_MD_CTX_init(cx);
|
EVP_MD_CTX_init(cx);
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
EVP_DigestInit_ex(cx, md, nullptr);
|
EVP_DigestInit_ex(cx, md, nullptr);
|
||||||
if (addmd++) EVP_DigestUpdate(cx, mdBuf, mds);
|
if ((addmd++) != 0) EVP_DigestUpdate(cx, mdBuf, mds);
|
||||||
EVP_DigestUpdate(cx, data, dataLen);
|
EVP_DigestUpdate(cx, data, dataLen);
|
||||||
EVP_DigestFinal_ex(cx, mdBuf, &mds);
|
EVP_DigestFinal_ex(cx, mdBuf, &mds);
|
||||||
|
|
||||||
@ -92,14 +93,14 @@ int BytesToKey(int keyLen, int ivLen, const EVP_MD *md,
|
|||||||
|
|
||||||
int offset = 0;
|
int offset = 0;
|
||||||
int toCopy = MIN(nkey, mds - offset);
|
int toCopy = MIN(nkey, mds - offset);
|
||||||
if (toCopy) {
|
if (toCopy != 0) {
|
||||||
memcpy(key, mdBuf + offset, toCopy);
|
memcpy(key, mdBuf + offset, toCopy);
|
||||||
key += toCopy;
|
key += toCopy;
|
||||||
nkey -= toCopy;
|
nkey -= toCopy;
|
||||||
offset += toCopy;
|
offset += toCopy;
|
||||||
}
|
}
|
||||||
toCopy = MIN(niv, mds - offset);
|
toCopy = MIN(niv, mds - offset);
|
||||||
if (toCopy) {
|
if (toCopy != 0) {
|
||||||
memcpy(iv, mdBuf + offset, toCopy);
|
memcpy(iv, mdBuf + offset, toCopy);
|
||||||
iv += toCopy;
|
iv += toCopy;
|
||||||
niv -= toCopy;
|
niv -= toCopy;
|
||||||
@ -139,10 +140,11 @@ int TimedPBKDF2(const char *pass, int passlen, const unsigned char *salt,
|
|||||||
} else if (delta < (5 * desiredPDFTime / 6)) {
|
} else if (delta < (5 * desiredPDFTime / 6)) {
|
||||||
// estimate number of iterations to get close to desired time
|
// estimate number of iterations to get close to desired time
|
||||||
iter = (int)((double)iter * (double)desiredPDFTime / (double)delta);
|
iter = (int)((double)iter * (double)desiredPDFTime / (double)delta);
|
||||||
} else
|
} else {
|
||||||
return iter;
|
return iter;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// - Version 1:0 used EVP_BytesToKey, which didn't do the right thing for
|
// - Version 1:0 used EVP_BytesToKey, which didn't do the right thing for
|
||||||
// Blowfish key lengths > 128 bit.
|
// Blowfish key lengths > 128 bit.
|
||||||
@ -366,8 +368,9 @@ CipherKey SSL_Cipher::newKey(const char *password, int passwdLength,
|
|||||||
if (res <= 0) {
|
if (res <= 0) {
|
||||||
RLOG(WARNING) << "openssl error, PBKDF2 failed";
|
RLOG(WARNING) << "openssl error, PBKDF2 failed";
|
||||||
return CipherKey();
|
return CipherKey();
|
||||||
} else
|
} else {
|
||||||
iterationCount = res;
|
iterationCount = res;
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
// known iteration length
|
// known iteration length
|
||||||
if (PKCS5_PBKDF2_HMAC_SHA1(
|
if (PKCS5_PBKDF2_HMAC_SHA1(
|
||||||
@ -425,8 +428,9 @@ CipherKey SSL_Cipher::newRandomKey() {
|
|||||||
int saltLen = 20;
|
int saltLen = 20;
|
||||||
unsigned char saltBuf[saltLen];
|
unsigned char saltBuf[saltLen];
|
||||||
|
|
||||||
if (!randomize(tmpBuf, bufLen, true) || !randomize(saltBuf, saltLen, true))
|
if (!randomize(tmpBuf, bufLen, true) || !randomize(saltBuf, saltLen, true)) {
|
||||||
return CipherKey();
|
return CipherKey();
|
||||||
|
}
|
||||||
|
|
||||||
std::shared_ptr<SSLKey> key(new SSLKey(_keySize, _ivLength));
|
std::shared_ptr<SSLKey> key(new SSLKey(_keySize, _ivLength));
|
||||||
|
|
||||||
@ -458,7 +462,7 @@ static uint64_t _checksum_64(SSLKey *key, const unsigned char *data,
|
|||||||
|
|
||||||
HMAC_Init_ex(key->mac_ctx, nullptr, 0, nullptr, nullptr);
|
HMAC_Init_ex(key->mac_ctx, nullptr, 0, nullptr, nullptr);
|
||||||
HMAC_Update(key->mac_ctx, data, dataLen);
|
HMAC_Update(key->mac_ctx, data, dataLen);
|
||||||
if (chainedIV) {
|
if (chainedIV != nullptr) {
|
||||||
// toss in the chained IV as well
|
// toss in the chained IV as well
|
||||||
uint64_t tmp = *chainedIV;
|
uint64_t tmp = *chainedIV;
|
||||||
unsigned char h[8];
|
unsigned char h[8];
|
||||||
@ -476,8 +480,9 @@ static uint64_t _checksum_64(SSLKey *key, const unsigned char *data,
|
|||||||
|
|
||||||
// chop this down to a 64bit value..
|
// chop this down to a 64bit value..
|
||||||
unsigned char h[8] = {0, 0, 0, 0, 0, 0, 0, 0};
|
unsigned char h[8] = {0, 0, 0, 0, 0, 0, 0, 0};
|
||||||
for (unsigned int i = 0; i < (mdLen - 1); ++i)
|
for (unsigned int i = 0; i < (mdLen - 1); ++i) {
|
||||||
h[i % 8] ^= (unsigned char)(md[i]);
|
h[i % 8] ^= (unsigned char)(md[i]);
|
||||||
|
}
|
||||||
|
|
||||||
auto value = (uint64_t)h[0];
|
auto value = (uint64_t)h[0];
|
||||||
for (int i = 1; i < 8; ++i) value = (value << 8) | (uint64_t)h[i];
|
for (int i = 1; i < 8; ++i) value = (value << 8) | (uint64_t)h[i];
|
||||||
@ -515,7 +520,7 @@ uint64_t SSL_Cipher::MAC_64(const unsigned char *data, int len,
|
|||||||
std::shared_ptr<SSLKey> mk = dynamic_pointer_cast<SSLKey>(key);
|
std::shared_ptr<SSLKey> mk = dynamic_pointer_cast<SSLKey>(key);
|
||||||
uint64_t tmp = _checksum_64(mk.get(), data, len, chainedIV);
|
uint64_t tmp = _checksum_64(mk.get(), data, len, chainedIV);
|
||||||
|
|
||||||
if (chainedIV) *chainedIV = tmp;
|
if (chainedIV != nullptr) *chainedIV = tmp;
|
||||||
|
|
||||||
return tmp;
|
return tmp;
|
||||||
}
|
}
|
||||||
@ -529,8 +534,9 @@ CipherKey SSL_Cipher::readKey(const unsigned char *data,
|
|||||||
|
|
||||||
// First N bytes are checksum bytes.
|
// First N bytes are checksum bytes.
|
||||||
unsigned int checksum = 0;
|
unsigned int checksum = 0;
|
||||||
for (int i = 0; i < KEY_CHECKSUM_BYTES; ++i)
|
for (int i = 0; i < KEY_CHECKSUM_BYTES; ++i) {
|
||||||
checksum = (checksum << 8) | (unsigned int)data[i];
|
checksum = (checksum << 8) | (unsigned int)data[i];
|
||||||
|
}
|
||||||
|
|
||||||
memcpy(tmpBuf, data + KEY_CHECKSUM_BYTES, _keySize + _ivLength);
|
memcpy(tmpBuf, data + KEY_CHECKSUM_BYTES, _keySize + _ivLength);
|
||||||
streamDecode(tmpBuf, _keySize + _ivLength, checksum, masterKey);
|
streamDecode(tmpBuf, _keySize + _ivLength, checksum, masterKey);
|
||||||
@ -591,11 +597,12 @@ bool SSL_Cipher::compareKey(const CipherKey &A, const CipherKey &B) const {
|
|||||||
rAssert(key1->keySize == _keySize);
|
rAssert(key1->keySize == _keySize);
|
||||||
rAssert(key2->keySize == _keySize);
|
rAssert(key2->keySize == _keySize);
|
||||||
|
|
||||||
if (memcmp(key1->buffer, key2->buffer, _keySize + _ivLength) != 0)
|
if (memcmp(key1->buffer, key2->buffer, _keySize + _ivLength) != 0) {
|
||||||
return false;
|
return false;
|
||||||
else
|
} else {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int SSL_Cipher::encodedKeySize() const {
|
int SSL_Cipher::encodedKeySize() const {
|
||||||
return _keySize + _ivLength + KEY_CHECKSUM_BYTES;
|
return _keySize + _ivLength + KEY_CHECKSUM_BYTES;
|
||||||
@ -694,7 +701,7 @@ static void flipBytes(unsigned char *buf, int size) {
|
|||||||
unsigned char revBuf[64];
|
unsigned char revBuf[64];
|
||||||
|
|
||||||
int bytesLeft = size;
|
int bytesLeft = size;
|
||||||
while (bytesLeft) {
|
while (bytesLeft != 0) {
|
||||||
int toFlip = MIN(sizeof(revBuf), bytesLeft);
|
int toFlip = MIN(sizeof(revBuf), bytesLeft);
|
||||||
|
|
||||||
for (int i = 0; i < toFlip; ++i) revBuf[i] = buf[toFlip - (i + 1)];
|
for (int i = 0; i < toFlip; ++i) revBuf[i] = buf[toFlip - (i + 1)];
|
||||||
@ -711,7 +718,7 @@ static void shuffleBytes(unsigned char *buf, int size) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void unshuffleBytes(unsigned char *buf, int size) {
|
static void unshuffleBytes(unsigned char *buf, int size) {
|
||||||
for (int i = size - 1; i; --i) buf[i] ^= buf[i - 1];
|
for (int i = size - 1; i != 0; --i) buf[i] ^= buf[i - 1];
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Partial blocks are encoded with a stream cipher. We make multiple passes on
|
/** Partial blocks are encoded with a stream cipher. We make multiple passes on
|
||||||
@ -798,8 +805,9 @@ bool SSL_Cipher::blockEncode(unsigned char *buf, int size, uint64_t iv64,
|
|||||||
|
|
||||||
// data must be integer number of blocks
|
// data must be integer number of blocks
|
||||||
const int blockMod = size % EVP_CIPHER_CTX_block_size(key->block_enc);
|
const int blockMod = size % EVP_CIPHER_CTX_block_size(key->block_enc);
|
||||||
if (blockMod != 0)
|
if (blockMod != 0) {
|
||||||
throw Error("Invalid data size, not multiple of block size");
|
throw Error("Invalid data size, not multiple of block size");
|
||||||
|
}
|
||||||
|
|
||||||
Lock lock(key->mutex);
|
Lock lock(key->mutex);
|
||||||
|
|
||||||
@ -830,8 +838,9 @@ bool SSL_Cipher::blockDecode(unsigned char *buf, int size, uint64_t iv64,
|
|||||||
|
|
||||||
// data must be integer number of blocks
|
// data must be integer number of blocks
|
||||||
const int blockMod = size % EVP_CIPHER_CTX_block_size(key->block_dec);
|
const int blockMod = size % EVP_CIPHER_CTX_block_size(key->block_dec);
|
||||||
if (blockMod != 0)
|
if (blockMod != 0) {
|
||||||
throw Error("Invalid data size, not multiple of block size");
|
throw Error("Invalid data size, not multiple of block size");
|
||||||
|
}
|
||||||
|
|
||||||
Lock lock(key->mutex);
|
Lock lock(key->mutex);
|
||||||
|
|
||||||
|
@ -96,7 +96,7 @@ int StreamNameIO::encodeName(const char *plaintextName, int length,
|
|||||||
uint64_t *iv, char *encodedName,
|
uint64_t *iv, char *encodedName,
|
||||||
int bufferLength) const {
|
int bufferLength) const {
|
||||||
uint64_t tmpIV = 0;
|
uint64_t tmpIV = 0;
|
||||||
if (iv && _interface >= 2) tmpIV = *iv;
|
if ((iv != nullptr) && _interface >= 2) tmpIV = *iv;
|
||||||
|
|
||||||
unsigned int mac =
|
unsigned int mac =
|
||||||
_cipher->MAC_16((const unsigned char *)plaintextName, length, _key, iv);
|
_cipher->MAC_16((const unsigned char *)plaintextName, length, _key, iv);
|
||||||
@ -155,7 +155,7 @@ int StreamNameIO::decodeName(const char *encodedName, int length, uint64_t *iv,
|
|||||||
((unsigned int)((unsigned char)tmpBuf[1]));
|
((unsigned int)((unsigned char)tmpBuf[1]));
|
||||||
|
|
||||||
// version 2 adds support for IV chaining..
|
// version 2 adds support for IV chaining..
|
||||||
if (iv && _interface >= 2) tmpIV = *iv;
|
if ((iv != nullptr) && _interface >= 2) tmpIV = *iv;
|
||||||
|
|
||||||
memcpy(plaintextName, tmpBuf + 2, decodedStreamLen);
|
memcpy(plaintextName, tmpBuf + 2, decodedStreamLen);
|
||||||
} else {
|
} else {
|
||||||
|
@ -80,7 +80,7 @@ bool XmlValue::read(const char *path, bool *out) const {
|
|||||||
XmlValuePtr value = find(path);
|
XmlValuePtr value = find(path);
|
||||||
if (!value) return false;
|
if (!value) return false;
|
||||||
|
|
||||||
*out = atoi(value->text().c_str());
|
*out = (atoi(value->text().c_str()) != 0);
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -124,9 +124,9 @@ std::string safeValueForNode(const tinyxml2::XMLElement *element) {
|
|||||||
if (element == nullptr) return value;
|
if (element == nullptr) return value;
|
||||||
|
|
||||||
const tinyxml2::XMLNode *child = element->FirstChild();
|
const tinyxml2::XMLNode *child = element->FirstChild();
|
||||||
if (child) {
|
if (child != nullptr) {
|
||||||
const tinyxml2::XMLText *childText = child->ToText();
|
const tinyxml2::XMLText *childText = child->ToText();
|
||||||
if (childText) value = childText->Value();
|
if (childText != nullptr) value = childText->Value();
|
||||||
}
|
}
|
||||||
|
|
||||||
return value;
|
return value;
|
||||||
@ -144,18 +144,20 @@ class XmlNode : virtual public XmlValue {
|
|||||||
XmlValuePtr find(const char *name) const override {
|
XmlValuePtr find(const char *name) const override {
|
||||||
if (name[0] == '@') {
|
if (name[0] == '@') {
|
||||||
const char *value = element->Attribute(name + 1);
|
const char *value = element->Attribute(name + 1);
|
||||||
if (value)
|
if (value != nullptr) {
|
||||||
return std::make_shared<encfs::XmlValue>(value);
|
return std::make_shared<encfs::XmlValue>(value);
|
||||||
else
|
} else {
|
||||||
return XmlValuePtr();
|
return XmlValuePtr();
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
const tinyxml2::XMLElement *el = element->FirstChildElement(name);
|
const tinyxml2::XMLElement *el = element->FirstChildElement(name);
|
||||||
if (el)
|
if (el != nullptr) {
|
||||||
return XmlValuePtr(new XmlNode(el));
|
return XmlValuePtr(new XmlNode(el));
|
||||||
else
|
} else {
|
||||||
return XmlValuePtr();
|
return XmlValuePtr();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct XmlReader::XmlReaderData {
|
struct XmlReader::XmlReaderData {
|
||||||
|
@ -57,10 +57,11 @@ autosprintf::operator char *() const {
|
|||||||
auto *copy = new char[length];
|
auto *copy = new char[length];
|
||||||
memcpy(copy, str, length);
|
memcpy(copy, str, length);
|
||||||
return copy;
|
return copy;
|
||||||
} else
|
} else {
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
autosprintf::operator std::string() const {
|
autosprintf::operator std::string() const {
|
||||||
return std::string(str ? str : "(error in autosprintf)");
|
return std::string(str != nullptr ? str : "(error in autosprintf)");
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
} // namespace gnu
|
||||||
|
@ -52,7 +52,7 @@ void changeBase2(unsigned char *src, int srcLen, int src2Pow,
|
|||||||
}
|
}
|
||||||
|
|
||||||
// now, we could have a partial value left in the work buffer..
|
// now, we could have a partial value left in the work buffer..
|
||||||
if (workBits && ((dst - origDst) < dstLen)) *dst++ = work & mask;
|
if ((workBits != 0) && ((dst - origDst) < dstLen)) *dst++ = work & mask;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -67,11 +67,11 @@ static void changeBase2Inline(unsigned char *src, int srcLen, int src2Pow,
|
|||||||
unsigned long work, int workBits,
|
unsigned long work, int workBits,
|
||||||
unsigned char *outLoc) {
|
unsigned char *outLoc) {
|
||||||
const int mask = (1 << dst2Pow) - 1;
|
const int mask = (1 << dst2Pow) - 1;
|
||||||
if (!outLoc) outLoc = src;
|
if (outLoc == nullptr) outLoc = src;
|
||||||
|
|
||||||
// copy the new bits onto the high bits of the stream.
|
// copy the new bits onto the high bits of the stream.
|
||||||
// The bits that fall off the low end are the output bits.
|
// The bits that fall off the low end are the output bits.
|
||||||
while (srcLen && workBits < dst2Pow) {
|
while ((srcLen != 0) && workBits < dst2Pow) {
|
||||||
work |= ((unsigned long)(*src++)) << workBits;
|
work |= ((unsigned long)(*src++)) << workBits;
|
||||||
workBits += src2Pow;
|
workBits += src2Pow;
|
||||||
--srcLen;
|
--srcLen;
|
||||||
@ -82,7 +82,7 @@ static void changeBase2Inline(unsigned char *src, int srcLen, int src2Pow,
|
|||||||
work >>= dst2Pow;
|
work >>= dst2Pow;
|
||||||
workBits -= dst2Pow;
|
workBits -= dst2Pow;
|
||||||
|
|
||||||
if (srcLen) {
|
if (srcLen != 0) {
|
||||||
// more input left, so recurse
|
// more input left, so recurse
|
||||||
changeBase2Inline(src, srcLen, src2Pow, dst2Pow, outputPartialLastByte,
|
changeBase2Inline(src, srcLen, src2Pow, dst2Pow, outputPartialLastByte,
|
||||||
work, workBits, outLoc + 1);
|
work, workBits, outLoc + 1);
|
||||||
@ -119,12 +119,14 @@ void B64ToAscii(unsigned char *in, int length) {
|
|||||||
for (int offset = 0; offset < length; ++offset) {
|
for (int offset = 0; offset < length; ++offset) {
|
||||||
int ch = in[offset];
|
int ch = in[offset];
|
||||||
if (ch > 11) {
|
if (ch > 11) {
|
||||||
if (ch > 37)
|
if (ch > 37) {
|
||||||
ch += 'a' - 38;
|
ch += 'a' - 38;
|
||||||
else
|
} else {
|
||||||
ch += 'A' - 12;
|
ch += 'A' - 12;
|
||||||
} else
|
}
|
||||||
|
} else {
|
||||||
ch = B642AsciiTable[ch];
|
ch = B642AsciiTable[ch];
|
||||||
|
}
|
||||||
|
|
||||||
in[offset] = ch;
|
in[offset] = ch;
|
||||||
}
|
}
|
||||||
@ -139,16 +141,17 @@ void AsciiToB64(unsigned char *in, int length) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void AsciiToB64(unsigned char *out, const unsigned char *in, int length) {
|
void AsciiToB64(unsigned char *out, const unsigned char *in, int length) {
|
||||||
while (length--) {
|
while ((length--) != 0) {
|
||||||
unsigned char ch = *in++;
|
unsigned char ch = *in++;
|
||||||
if (ch >= 'A') {
|
if (ch >= 'A') {
|
||||||
if (ch >= 'a')
|
if (ch >= 'a') {
|
||||||
ch += 38 - 'a';
|
ch += 38 - 'a';
|
||||||
else
|
} else {
|
||||||
ch += 12 - 'A';
|
ch += 12 - 'A';
|
||||||
} else
|
}
|
||||||
|
} else {
|
||||||
ch = Ascii2B64Table[ch] - '0';
|
ch = Ascii2B64Table[ch] - '0';
|
||||||
|
}
|
||||||
*out++ = ch;
|
*out++ = ch;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -156,10 +159,11 @@ void AsciiToB64(unsigned char *out, const unsigned char *in, int length) {
|
|||||||
void B32ToAscii(unsigned char *buf, int len) {
|
void B32ToAscii(unsigned char *buf, int len) {
|
||||||
for (int offset = 0; offset < len; ++offset) {
|
for (int offset = 0; offset < len; ++offset) {
|
||||||
int ch = buf[offset];
|
int ch = buf[offset];
|
||||||
if (ch >= 0 && ch < 26)
|
if (ch >= 0 && ch < 26) {
|
||||||
ch += 'A';
|
ch += 'A';
|
||||||
else
|
} else {
|
||||||
ch += '2' - 26;
|
ch += '2' - 26;
|
||||||
|
}
|
||||||
|
|
||||||
buf[offset] = ch;
|
buf[offset] = ch;
|
||||||
}
|
}
|
||||||
@ -170,14 +174,14 @@ void AsciiToB32(unsigned char *in, int length) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void AsciiToB32(unsigned char *out, const unsigned char *in, int length) {
|
void AsciiToB32(unsigned char *out, const unsigned char *in, int length) {
|
||||||
while (length--) {
|
while ((length--) != 0) {
|
||||||
unsigned char ch = *in++;
|
unsigned char ch = *in++;
|
||||||
int lch = toupper(ch);
|
int lch = toupper(ch);
|
||||||
if (lch >= 'A')
|
if (lch >= 'A') {
|
||||||
lch -= 'A';
|
lch -= 'A';
|
||||||
else
|
} else {
|
||||||
lch += 26 - '2';
|
lch += 26 - '2';
|
||||||
|
}
|
||||||
*out++ = (unsigned char)lch;
|
*out++ = (unsigned char)lch;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -221,7 +225,7 @@ bool B64StandardDecode(unsigned char *out, const unsigned char *in, int inLen) {
|
|||||||
buf = buf << 6 | c;
|
buf = buf << 6 | c;
|
||||||
|
|
||||||
/* If the buffer is full, split it into bytes */
|
/* If the buffer is full, split it into bytes */
|
||||||
if (buf & 0x1000000) {
|
if ((buf & 0x1000000) != 0u) {
|
||||||
*out++ = buf >> 16;
|
*out++ = buf >> 16;
|
||||||
*out++ = buf >> 8;
|
*out++ = buf >> 8;
|
||||||
*out++ = buf;
|
*out++ = buf;
|
||||||
@ -230,10 +234,10 @@ bool B64StandardDecode(unsigned char *out, const unsigned char *in, int inLen) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (buf & 0x40000) {
|
if ((buf & 0x40000) != 0u) {
|
||||||
*out++ = buf >> 10;
|
*out++ = buf >> 10;
|
||||||
*out++ = buf >> 2;
|
*out++ = buf >> 2;
|
||||||
} else if (buf & 0x1000) {
|
} else if ((buf & 0x1000) != 0u) {
|
||||||
*out++ = buf >> 4;
|
*out++ = buf >> 4;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -252,7 +252,7 @@ int encfs_readdir(const char *path, void *buf, fuse_fill_dir_t filler,
|
|||||||
#if defined(fuse_fill_dir_flags)
|
#if defined(fuse_fill_dir_flags)
|
||||||
if (filler(buf, name.c_str(), &st, 0, 0)) break;
|
if (filler(buf, name.c_str(), &st, 0, 0)) break;
|
||||||
#else
|
#else
|
||||||
if (filler(buf, name.c_str(), &st, 0)) break;
|
if (filler(buf, name.c_str(), &st, 0) != 0) break;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
name = dt.nextPlaintextName(&fileType, &inode);
|
name = dt.nextPlaintextName(&fileType, &inode);
|
||||||
@ -300,9 +300,10 @@ int encfs_mknod(const char *path, mode_t mode, dev_t rdev) {
|
|||||||
FSRoot->lookupNode(parent.c_str(), "mknod");
|
FSRoot->lookupNode(parent.c_str(), "mknod");
|
||||||
|
|
||||||
struct stat st;
|
struct stat st;
|
||||||
if (dnode->getAttr(&st) == 0)
|
if (dnode->getAttr(&st) == 0) {
|
||||||
res = fnode->mknod(mode, rdev, uid, st.st_gid);
|
res = fnode->mknod(mode, rdev, uid, st.st_gid);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} catch (encfs::Error &err) {
|
} catch (encfs::Error &err) {
|
||||||
RLOG(ERROR) << "error caught in mknod: " << err.what();
|
RLOG(ERROR) << "error caught in mknod: " << err.what();
|
||||||
}
|
}
|
||||||
@ -335,9 +336,10 @@ int encfs_mkdir(const char *path, mode_t mode) {
|
|||||||
FSRoot->lookupNode(parent.c_str(), "mkdir");
|
FSRoot->lookupNode(parent.c_str(), "mkdir");
|
||||||
|
|
||||||
struct stat st;
|
struct stat st;
|
||||||
if (dnode->getAttr(&st) == 0)
|
if (dnode->getAttr(&st) == 0) {
|
||||||
res = FSRoot->mkdir(path, mode, uid, st.st_gid);
|
res = FSRoot->mkdir(path, mode, uid, st.st_gid);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
} catch (encfs::Error &err) {
|
} catch (encfs::Error &err) {
|
||||||
RLOG(ERROR) << "error caught in mkdir: " << err.what();
|
RLOG(ERROR) << "error caught in mkdir: " << err.what();
|
||||||
}
|
}
|
||||||
@ -438,10 +440,11 @@ int encfs_symlink(const char *to, const char *from) {
|
|||||||
if (olduid >= 0) setfsuid(olduid);
|
if (olduid >= 0) setfsuid(olduid);
|
||||||
if (oldgid >= 0) setfsgid(oldgid);
|
if (oldgid >= 0) setfsgid(oldgid);
|
||||||
|
|
||||||
if (res == -1)
|
if (res == -1) {
|
||||||
res = -errno;
|
res = -errno;
|
||||||
else
|
} else {
|
||||||
res = ESUCCESS;
|
res = ESUCCESS;
|
||||||
|
}
|
||||||
} catch (encfs::Error &err) {
|
} catch (encfs::Error &err) {
|
||||||
RLOG(ERROR) << "error caught in symlink: " << err.what();
|
RLOG(ERROR) << "error caught in symlink: " << err.what();
|
||||||
}
|
}
|
||||||
@ -547,8 +550,10 @@ int encfs_utimens(const char *path, const struct timespec ts[2]) {
|
|||||||
int encfs_open(const char *path, struct fuse_file_info *file) {
|
int encfs_open(const char *path, struct fuse_file_info *file) {
|
||||||
EncFS_Context *ctx = context();
|
EncFS_Context *ctx = context();
|
||||||
|
|
||||||
if (isReadOnly(ctx) && (file->flags & O_WRONLY || file->flags & O_RDWR))
|
if (isReadOnly(ctx) &&
|
||||||
|
(((file->flags & O_WRONLY) != 0) || ((file->flags & O_RDWR) != 0))) {
|
||||||
return -EROFS;
|
return -EROFS;
|
||||||
|
}
|
||||||
|
|
||||||
int res = -EIO;
|
int res = -EIO;
|
||||||
std::shared_ptr<DirNode> FSRoot = ctx->getRoot(&res);
|
std::shared_ptr<DirNode> FSRoot = ctx->getRoot(&res);
|
||||||
@ -577,7 +582,7 @@ int encfs_open(const char *path, struct fuse_file_info *file) {
|
|||||||
|
|
||||||
int encfs_create(const char *path, mode_t mode, struct fuse_file_info *file) {
|
int encfs_create(const char *path, mode_t mode, struct fuse_file_info *file) {
|
||||||
int res = encfs_mknod(path, mode, 0);
|
int res = encfs_mknod(path, mode, 0);
|
||||||
if (res) {
|
if (res != 0) {
|
||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -648,11 +653,12 @@ int encfs_fsync(const char *path, int dataSync, struct fuse_file_info *file) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int _do_write(FileNode *fnode, unsigned char *ptr, size_t size, off_t offset) {
|
int _do_write(FileNode *fnode, unsigned char *ptr, size_t size, off_t offset) {
|
||||||
if (fnode->write(offset, ptr, size))
|
if (fnode->write(offset, ptr, size)) {
|
||||||
return size;
|
return size;
|
||||||
else
|
} else {
|
||||||
return -EIO;
|
return -EIO;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
int encfs_write(const char *path, const char *buf, size_t size, off_t offset,
|
int encfs_write(const char *path, const char *buf, size_t size, off_t offset,
|
||||||
struct fuse_file_info *file) {
|
struct fuse_file_info *file) {
|
||||||
@ -673,7 +679,7 @@ int encfs_statfs(const char *path, struct statvfs *st) {
|
|||||||
|
|
||||||
VLOG(1) << "doing statfs of " << cyName;
|
VLOG(1) << "doing statfs of " << cyName;
|
||||||
res = statvfs(cyName.c_str(), st);
|
res = statvfs(cyName.c_str(), st);
|
||||||
if (!res) {
|
if (res == 0) {
|
||||||
// adjust maximum name length..
|
// adjust maximum name length..
|
||||||
st->f_namemax = 6 * (st->f_namemax - 2) / 8; // approx..
|
st->f_namemax = 6 * (st->f_namemax - 2) / 8; // approx..
|
||||||
}
|
}
|
||||||
|
@ -94,8 +94,9 @@ struct EncFS_Args {
|
|||||||
if (opts->reverseEncryption) ss << "(reverseEncryption) ";
|
if (opts->reverseEncryption) ss << "(reverseEncryption) ";
|
||||||
if (opts->mountOnDemand) ss << "(mountOnDemand) ";
|
if (opts->mountOnDemand) ss << "(mountOnDemand) ";
|
||||||
if (opts->delayMount) ss << "(delayMount) ";
|
if (opts->delayMount) ss << "(delayMount) ";
|
||||||
for (int i = 0; i < fuseArgc; ++i) ss << fuseArgv[i] << ' ';
|
for (int i = 0; i < fuseArgc; ++i) {
|
||||||
|
ss << fuseArgv[i] << ' ';
|
||||||
|
}
|
||||||
return ss.str();
|
return ss.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -343,9 +344,9 @@ static bool processArgs(int argc, char *argv[],
|
|||||||
out->opts->passwordProgram.assign(optarg);
|
out->opts->passwordProgram.assign(optarg);
|
||||||
break;
|
break;
|
||||||
case 'P':
|
case 'P':
|
||||||
if (geteuid() != 0)
|
if (geteuid() != 0) {
|
||||||
RLOG(WARNING) << "option '--public' ignored for non-root user";
|
RLOG(WARNING) << "option '--public' ignored for non-root user";
|
||||||
else {
|
} else {
|
||||||
out->opts->ownerCreate = true;
|
out->opts->ownerCreate = true;
|
||||||
// add 'allow_other' option
|
// add 'allow_other' option
|
||||||
// add 'default_permissions' option (default)
|
// add 'default_permissions' option (default)
|
||||||
@ -496,7 +497,7 @@ void *encfs_init(fuse_conn_info *conn) {
|
|||||||
auto *ctx = (EncFS_Context *)fuse_get_context()->private_data;
|
auto *ctx = (EncFS_Context *)fuse_get_context()->private_data;
|
||||||
|
|
||||||
// set fuse connection options
|
// set fuse connection options
|
||||||
conn->async_read = true;
|
conn->async_read = 1u;
|
||||||
|
|
||||||
// if an idle timeout is specified, then setup a thread to monitor the
|
// if an idle timeout is specified, then setup a thread to monitor the
|
||||||
// filesystem.
|
// filesystem.
|
||||||
@ -534,8 +535,9 @@ int main(int argc, char *argv[]) {
|
|||||||
// anything that comes from the user should be considered tainted until
|
// anything that comes from the user should be considered tainted until
|
||||||
// we've processed it and only allowed through what we support.
|
// we've processed it and only allowed through what we support.
|
||||||
std::shared_ptr<EncFS_Args> encfsArgs(new EncFS_Args);
|
std::shared_ptr<EncFS_Args> encfsArgs(new EncFS_Args);
|
||||||
for (int i = 0; i < MaxFuseArgs; ++i)
|
for (int i = 0; i < MaxFuseArgs; ++i) {
|
||||||
encfsArgs->fuseArgv[i] = nullptr; // libfuse expects null args..
|
encfsArgs->fuseArgv[i] = nullptr; // libfuse expects null args..
|
||||||
|
}
|
||||||
|
|
||||||
if (argc == 1 || !processArgs(argc, argv, encfsArgs)) {
|
if (argc == 1 || !processArgs(argc, argv, encfsArgs)) {
|
||||||
usage(argv[0]);
|
usage(argv[0]);
|
||||||
@ -616,7 +618,7 @@ int main(int argc, char *argv[]) {
|
|||||||
ctx->args = encfsArgs;
|
ctx->args = encfsArgs;
|
||||||
ctx->opts = encfsArgs->opts;
|
ctx->opts = encfsArgs->opts;
|
||||||
|
|
||||||
if (encfsArgs->isThreaded == false && encfsArgs->idleTimeout > 0) {
|
if (!encfsArgs->isThreaded && encfsArgs->idleTimeout > 0) {
|
||||||
// xgroup(usage)
|
// xgroup(usage)
|
||||||
cerr << _("Note: requested single-threaded mode, but an idle\n"
|
cerr << _("Note: requested single-threaded mode, but an idle\n"
|
||||||
"timeout was specified. The filesystem will operate\n"
|
"timeout was specified. The filesystem will operate\n"
|
||||||
@ -727,12 +729,13 @@ static void *idleMonitor(void *_arg) {
|
|||||||
int usage, openCount;
|
int usage, openCount;
|
||||||
ctx->getAndResetUsageCounter(&usage, &openCount);
|
ctx->getAndResetUsageCounter(&usage, &openCount);
|
||||||
|
|
||||||
if (usage == 0 && ctx->isMounted())
|
if (usage == 0 && ctx->isMounted()) {
|
||||||
++idleCycles;
|
++idleCycles;
|
||||||
else {
|
} else {
|
||||||
if (idleCycles >= timeoutCycles)
|
if (idleCycles >= timeoutCycles) {
|
||||||
RLOG(INFO) << "Filesystem no longer inactive: "
|
RLOG(INFO) << "Filesystem no longer inactive: "
|
||||||
<< arg->opts->mountPoint;
|
<< arg->opts->mountPoint;
|
||||||
|
}
|
||||||
idleCycles = 0;
|
idleCycles = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -765,8 +768,9 @@ static void *idleMonitor(void *_arg) {
|
|||||||
|
|
||||||
// If we are here FS has been unmounted, so if we did not unmount ourselves
|
// If we are here FS has been unmounted, so if we did not unmount ourselves
|
||||||
// (manual, kill...), notify
|
// (manual, kill...), notify
|
||||||
if (!unmountres)
|
if (!unmountres) {
|
||||||
RLOG(INFO) << "Filesystem unmounted: " << arg->opts->mountPoint;
|
RLOG(INFO) << "Filesystem unmounted: " << arg->opts->mountPoint;
|
||||||
|
}
|
||||||
|
|
||||||
VLOG(1) << "Idle monitoring thread exiting";
|
VLOG(1) << "Idle monitoring thread exiting";
|
||||||
|
|
||||||
|
@ -43,14 +43,15 @@ void pthreads_locking_callback(int mode, int n, const char *caller_file,
|
|||||||
(void)caller_file;
|
(void)caller_file;
|
||||||
(void)caller_line;
|
(void)caller_line;
|
||||||
|
|
||||||
if (!crypto_locks) {
|
if (crypto_locks == nullptr) {
|
||||||
VLOG(1) << "Allocating " << CRYPTO_num_locks() << " locks for OpenSSL";
|
VLOG(1) << "Allocating " << CRYPTO_num_locks() << " locks for OpenSSL";
|
||||||
crypto_locks = new pthread_mutex_t[CRYPTO_num_locks()];
|
crypto_locks = new pthread_mutex_t[CRYPTO_num_locks()];
|
||||||
for (int i = 0; i < CRYPTO_num_locks(); ++i)
|
for (int i = 0; i < CRYPTO_num_locks(); ++i) {
|
||||||
pthread_mutex_init(crypto_locks + i, nullptr);
|
pthread_mutex_init(crypto_locks + i, nullptr);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (mode & CRYPTO_LOCK) {
|
if ((mode & CRYPTO_LOCK) != 0) {
|
||||||
pthread_mutex_lock(crypto_locks + n);
|
pthread_mutex_lock(crypto_locks + n);
|
||||||
} else {
|
} else {
|
||||||
pthread_mutex_unlock(crypto_locks + n);
|
pthread_mutex_unlock(crypto_locks + n);
|
||||||
@ -58,9 +59,10 @@ void pthreads_locking_callback(int mode, int n, const char *caller_file,
|
|||||||
}
|
}
|
||||||
|
|
||||||
void pthreads_locking_cleanup() {
|
void pthreads_locking_cleanup() {
|
||||||
if (crypto_locks) {
|
if (crypto_locks != nullptr) {
|
||||||
for (int i = 0; i < CRYPTO_num_locks(); ++i)
|
for (int i = 0; i < CRYPTO_num_locks(); ++i) {
|
||||||
pthread_mutex_destroy(crypto_locks + i);
|
pthread_mutex_destroy(crypto_locks + i);
|
||||||
|
}
|
||||||
delete[] crypto_locks;
|
delete[] crypto_locks;
|
||||||
crypto_locks = nullptr;
|
crypto_locks = nullptr;
|
||||||
}
|
}
|
||||||
|
@ -85,7 +85,7 @@ restart:
|
|||||||
* stdin and write to stderr unless a tty is required.
|
* stdin and write to stderr unless a tty is required.
|
||||||
*/
|
*/
|
||||||
if ((input = output = open(_PATH_TTY, O_RDWR)) == -1) {
|
if ((input = output = open(_PATH_TTY, O_RDWR)) == -1) {
|
||||||
if (flags & RPP_REQUIRE_TTY) {
|
if ((flags & RPP_REQUIRE_TTY) != 0) {
|
||||||
errno = ENOTTY;
|
errno = ENOTTY;
|
||||||
return (nullptr);
|
return (nullptr);
|
||||||
}
|
}
|
||||||
@ -112,7 +112,7 @@ restart:
|
|||||||
/* Turn off echo if possible. */
|
/* Turn off echo if possible. */
|
||||||
if (tcgetattr(input, &oterm) == 0) {
|
if (tcgetattr(input, &oterm) == 0) {
|
||||||
memcpy(&term, &oterm, sizeof(term));
|
memcpy(&term, &oterm, sizeof(term));
|
||||||
if (!(flags & RPP_ECHO_ON)) term.c_lflag &= ~(ECHO | ECHONL);
|
if ((flags & RPP_ECHO_ON) == 0) term.c_lflag &= ~(ECHO | ECHONL);
|
||||||
#ifdef VSTATUS
|
#ifdef VSTATUS
|
||||||
if (term.c_cc[VSTATUS] != _POSIX_VDISABLE)
|
if (term.c_cc[VSTATUS] != _POSIX_VDISABLE)
|
||||||
term.c_cc[VSTATUS] = _POSIX_VDISABLE;
|
term.c_cc[VSTATUS] = _POSIX_VDISABLE;
|
||||||
@ -127,21 +127,22 @@ restart:
|
|||||||
end = buf + bufsiz - 1;
|
end = buf + bufsiz - 1;
|
||||||
for (p = buf; (nr = read(input, &ch, 1)) == 1 && ch != '\n' && ch != '\r';) {
|
for (p = buf; (nr = read(input, &ch, 1)) == 1 && ch != '\n' && ch != '\r';) {
|
||||||
if (p < end) {
|
if (p < end) {
|
||||||
if ((flags & RPP_SEVENBIT)) ch &= 0x7f;
|
if ((flags & RPP_SEVENBIT) != 0) ch &= 0x7f;
|
||||||
if (isalpha(ch)) {
|
if (isalpha(ch) != 0) {
|
||||||
if ((flags & RPP_FORCELOWER)) ch = tolower(ch);
|
if ((flags & RPP_FORCELOWER) != 0) ch = tolower(ch);
|
||||||
if ((flags & RPP_FORCEUPPER)) ch = toupper(ch);
|
if ((flags & RPP_FORCEUPPER) != 0) ch = toupper(ch);
|
||||||
}
|
}
|
||||||
*p++ = ch;
|
*p++ = ch;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
*p = '\0';
|
*p = '\0';
|
||||||
save_errno = errno;
|
save_errno = errno;
|
||||||
if (!(term.c_lflag & ECHO)) (void)write(output, "\n", 1);
|
if ((term.c_lflag & ECHO) == 0u) (void)write(output, "\n", 1);
|
||||||
|
|
||||||
/* Restore old terminal settings and signals. */
|
/* Restore old terminal settings and signals. */
|
||||||
if (memcmp(&term, &oterm, sizeof(term)) != 0)
|
if (memcmp(&term, &oterm, sizeof(term)) != 0) {
|
||||||
(void)tcsetattr(input, _T_FLUSH, &oterm);
|
(void)tcsetattr(input, _T_FLUSH, &oterm);
|
||||||
|
}
|
||||||
(void)sigaction(SIGINT, &saveint, nullptr);
|
(void)sigaction(SIGINT, &saveint, nullptr);
|
||||||
(void)sigaction(SIGHUP, &savehup, nullptr);
|
(void)sigaction(SIGHUP, &savehup, nullptr);
|
||||||
(void)sigaction(SIGQUIT, &savequit, nullptr);
|
(void)sigaction(SIGQUIT, &savequit, nullptr);
|
||||||
@ -155,7 +156,7 @@ restart:
|
|||||||
* If we were interrupted by a signal, resend it to ourselves
|
* If we were interrupted by a signal, resend it to ourselves
|
||||||
* now that we have restored the signal handlers.
|
* now that we have restored the signal handlers.
|
||||||
*/
|
*/
|
||||||
if (signo) {
|
if (signo != 0) {
|
||||||
kill(getpid(), signo);
|
kill(getpid(), signo);
|
||||||
switch (signo) {
|
switch (signo) {
|
||||||
case SIGTSTP:
|
case SIGTSTP:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user