Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/keepassxreboot/keepassxc.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorFelix Geyer <debfx@fobos.de>2010-09-16 20:20:46 +0400
committerFelix Geyer <debfx@fobos.de>2010-09-16 20:20:46 +0400
commitc2bdfab158da4be7d422a768a3d481cbbd814370 (patch)
tree77f792e6e8e322a4e149aacac9ed6caeaefce074 /src
parent49d64d81626adf3bdc427d9bcdf7dab486ac916a (diff)
Implement writing to the SymmetricCipherStream.
Diffstat (limited to 'src')
-rw-r--r--src/streams/SymmetricCipherStream.cpp87
-rw-r--r--src/streams/SymmetricCipherStream.h4
2 files changed, 77 insertions, 14 deletions
diff --git a/src/streams/SymmetricCipherStream.cpp b/src/streams/SymmetricCipherStream.cpp
index 483abefc3..30963bd7a 100644
--- a/src/streams/SymmetricCipherStream.cpp
+++ b/src/streams/SymmetricCipherStream.cpp
@@ -21,7 +21,8 @@ SymmetricCipherStream::SymmetricCipherStream(QIODevice* baseDevice, SymmetricCip
SymmetricCipher::Direction direction, const QByteArray& key, const QByteArray& iv)
: LayeredStream(baseDevice)
, m_bufferPos(0)
- , m_eof(false)
+ , m_bufferFilling(false)
+ , m_error(false)
{
m_cipher = new SymmetricCipher(algo, mode, direction, key, iv);
}
@@ -30,22 +31,30 @@ bool SymmetricCipherStream::reset()
{
m_buffer.clear();
m_bufferPos = 0;
+ m_bufferFilling = false;
+ m_error = false;
m_cipher->reset();
return true;
}
-qint64 SymmetricCipherStream::readData(char* data, qint64 maxSize)
+void SymmetricCipherStream::close()
{
- // TODO m_eof is probably wrong and should be removed
- if (m_eof) {
- return 0;
+ if (isWritable()) {
+ writeBlock();
}
+ LayeredStream::close();
+}
+
+qint64 SymmetricCipherStream::readData(char* data, qint64 maxSize)
+{
+ Q_ASSERT(maxSize >= 0);
+
qint64 bytesRemaining = maxSize;
qint64 offset = 0;
while (bytesRemaining > 0) {
- if (m_bufferPos == m_buffer.size()) {
+ if ((m_bufferPos == m_buffer.size()) || m_bufferFilling) {
if (!readBlock()) {
return maxSize - bytesRemaining;
}
@@ -65,28 +74,80 @@ qint64 SymmetricCipherStream::readData(char* data, qint64 maxSize)
bool SymmetricCipherStream::readBlock()
{
- m_buffer = m_baseDevice->read(m_cipher->blockSize());
+ if (m_bufferFilling) {
+ m_buffer.append(m_baseDevice->read(m_cipher->blockSize() - m_buffer.size()));
+ }
+ else {
+ m_buffer = m_baseDevice->read(m_cipher->blockSize());
+ }
if (m_buffer.size() != m_cipher->blockSize()) {
- m_eof = true;
- // TODO check if m_buffer.size()!=0
+ m_bufferFilling = true;
return false;
}
else {
m_cipher->processInPlace(m_buffer);
m_bufferPos = 0;
+ m_bufferFilling = false;
return true;
}
}
qint64 SymmetricCipherStream::writeData(const char* data, qint64 maxSize)
{
- // TODO implement
- return 0;
+ Q_ASSERT(maxSize >= 0);
+
+ if (m_error) {
+ return 0;
+ }
+
+ qint64 bytesRemaining = maxSize;
+ qint64 offset = 0;
+
+ while (bytesRemaining > 0) {
+ int bytesToCopy = qMin(bytesRemaining, static_cast<qint64>(m_cipher->blockSize() - m_buffer.size()));
+
+ m_buffer.append(data + offset, bytesToCopy);
+
+ offset += bytesToCopy;
+ bytesRemaining -= bytesToCopy;
+
+ if (m_buffer.size() == m_cipher->blockSize()) {
+ if (!writeBlock()) {
+ if (m_error) {
+ return -1;
+ }
+ else {
+ return maxSize - bytesRemaining;
+ }
+ }
+ }
+ }
+
+ return maxSize;
}
bool SymmetricCipherStream::writeBlock()
{
- // TODO implement
- return false;
+ if (m_buffer.isEmpty()) {
+ return true;
+ }
+ else if (m_buffer.size() != m_cipher->blockSize()) {
+ int padLen = m_cipher->blockSize() - m_buffer.size();
+ for (int i=m_buffer.size(); i<m_cipher->blockSize(); i++) {
+ m_buffer.append(static_cast<char>(padLen));
+ }
+ }
+
+ m_cipher->processInPlace(m_buffer);
+
+ if (m_baseDevice->write(m_buffer) != m_buffer.size()) {
+ m_error = true;
+ // TODO copy error string
+ return false;
+ }
+ else {
+ m_buffer.clear();
+ return true;
+ }
}
diff --git a/src/streams/SymmetricCipherStream.h b/src/streams/SymmetricCipherStream.h
index 1891f91c8..90bfc7257 100644
--- a/src/streams/SymmetricCipherStream.h
+++ b/src/streams/SymmetricCipherStream.h
@@ -31,6 +31,7 @@ public:
SymmetricCipherStream(QIODevice* baseDevice, SymmetricCipher::Algorithm algo, SymmetricCipher::Mode mode,
SymmetricCipher::Direction direction, const QByteArray& key, const QByteArray& iv);
bool reset();
+ void close();
protected:
qint64 readData(char* data, qint64 maxSize);
@@ -43,7 +44,8 @@ private:
SymmetricCipher* m_cipher;
QByteArray m_buffer;
int m_bufferPos;
- bool m_eof;
+ bool m_bufferFilling;
+ bool m_error;
};
#endif // KEEPASSX_SYMMETRICCIPHERSTREAM_H