author | ulf69 <ulf69> | 2004-11-07 02:10:50 (UTC) |
---|---|---|
committer | ulf69 <ulf69> | 2004-11-07 02:10:50 (UTC) |
commit | 31c3fc0e0673b9403fb4ef4a9836305d1d49ff83 (patch) (side-by-side diff) | |
tree | f5a44f4402294d6fd61e204489cdd776acb804aa | |
parent | 2b6072e39edbc8c9ab36e1e835b252a799db97a1 (diff) | |
download | kdepimpi-31c3fc0e0673b9403fb4ef4a9836305d1d49ff83.zip kdepimpi-31c3fc0e0673b9403fb4ef4a9836305d1d49ff83.tar.gz kdepimpi-31c3fc0e0673b9403fb4ef4a9836305d1d49ff83.tar.bz2 |
Fixed nasty PwM/Pi file reading bug, when
the used hash algo of file is different then the global
hash algo.
CVS ----------------------------------------------------------------------
-rw-r--r-- | pwmanager/pwmanager/libgcryptif.cpp | 25 | ||||
-rw-r--r-- | pwmanager/pwmanager/libgcryptif.h | 12 | ||||
-rw-r--r-- | pwmanager/pwmanager/pwmdoc.cpp | 20 | ||||
-rw-r--r-- | pwmanager/pwmanager/pwmdoc.h | 8 |
4 files changed, 46 insertions, 19 deletions
diff --git a/pwmanager/pwmanager/libgcryptif.cpp b/pwmanager/pwmanager/libgcryptif.cpp index ff94bf6..15f6cef 100644 --- a/pwmanager/pwmanager/libgcryptif.cpp +++ b/pwmanager/pwmanager/libgcryptif.cpp @@ -20,49 +20,51 @@ * * $Id$ **************************************************************************/ #include "libgcryptif.h" #ifdef CONFIG_PWMANAGER_GCRY #include "pwmdoc.h" #include "randomizer.h" #include <gcrypt.h> #ifdef PWM_EMBEDDED #include <pwmprefs.h> #endif PwMerror LibGCryptIf::encrypt(unsigned char **outBuf, size_t *outBufLen, unsigned char *inBuf, size_t inBufLen, const unsigned char *key, size_t keylen, - char _algo) + char _algo, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase + ) { PwMerror ret = e_success; gcry_error_t err; gcry_cipher_hd_t handle; size_t blklen; size_t unpaddedLen = inBufLen; size_t cipherKeylen; unsigned char *hashedKey; unsigned char salt[STRING2KEY_SALTLEN]; int algo = mapCipherId(_algo); if (!inBufLen || !keylen) return e_invalidArg; // test if algo is ready for encryption err = gcry_cipher_algo_info(algo, GCRYCTL_TEST_ALGO, 0, 0); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): GCRYCTL_TEST_ALGO failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } @@ -84,145 +86,147 @@ PwMerror LibGCryptIf::encrypt(unsigned char **outBuf, // get the algo key length err = gcry_cipher_algo_info(algo, GCRYCTL_GET_KEYLEN, 0, &cipherKeylen); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): GCRYCTL_GET_KEYLEN failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } // now open the algo and get a handle err = gcry_cipher_open(&handle, algo, GCRY_CIPHER_MODE_CBC, 0); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): gcry_cipher_open() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } // hash the "key" to a fixed size hash matching "cipherKeylen" hashedKey = new unsigned char[cipherKeylen]; - hashPassphrase(key, keylen, salt, hashedKey, cipherKeylen, true); + hashPassphrase(key, keylen, salt, hashedKey, cipherKeylen, true, _hashalgo); // so now set the hashed key err = gcry_cipher_setkey(handle, hashedKey, cipherKeylen); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): gcry_cipher_setkey() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; delete [] hashedKey; goto out_close; } delete [] hashedKey; /* allocate a buffer for the encrypted data. * The size of the buffer is the inBuf length, but blklen * aligned and plus the length of the salt, that is appended. */ *outBufLen = getBufLen(unpaddedLen, blklen) + STRING2KEY_SALTLEN; *outBuf = new unsigned char[*outBufLen]; padData(inBuf, unpaddedLen, blklen); // encrypt the padded data err = gcry_cipher_encrypt(handle, *outBuf, *outBufLen - STRING2KEY_SALTLEN, inBuf, *outBufLen - STRING2KEY_SALTLEN); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): gcry_cipher_encrypt() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out_delete; } // append the salt to the encrypted data memcpy(*outBuf + *outBufLen - STRING2KEY_SALTLEN, salt, STRING2KEY_SALTLEN); goto out_close; out_delete: delete [] *outBuf; out_close: gcry_cipher_close(handle); out: return ret; } PwMerror LibGCryptIf::decrypt(unsigned char **outBuf, size_t *outBufLen, const unsigned char *inBuf, size_t inBufLen, const unsigned char *key, size_t keylen, - char _algo) + char _algo, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +) { PwMerror ret = e_success; gcry_error_t err; gcry_cipher_hd_t handle; size_t cipherKeylen; unsigned char *hashedKey; unsigned char salt[STRING2KEY_SALTLEN]; int algo = mapCipherId(_algo); if (!inBufLen || !keylen) return e_invalidArg; // test if algo is ready for encryption err = gcry_cipher_algo_info(algo, GCRYCTL_TEST_ALGO, 0, 0); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doDecrypt(): GCRYCTL_TEST_ALGO failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } // get algo key length err = gcry_cipher_algo_info(algo, GCRYCTL_GET_KEYLEN, 0, &cipherKeylen); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doDecrypt(): GCRYCTL_GET_KEYLEN failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } // extract the salt of the encrypted data buffer memcpy(salt, inBuf + inBufLen - STRING2KEY_SALTLEN, STRING2KEY_SALTLEN); // open the algo and get a handle err = gcry_cipher_open(&handle, algo, GCRY_CIPHER_MODE_CBC, 0); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doDecrypt(): gcry_cipher_open() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out; } // hash the "key" to a fixed size hash matching "cipherKeylen" hashedKey = new unsigned char[cipherKeylen]; - hashPassphrase(key, keylen, salt, hashedKey, cipherKeylen, false); + hashPassphrase(key, keylen, salt, hashedKey, cipherKeylen, false, _hashalgo); // so now set the hashed key err = gcry_cipher_setkey(handle, hashedKey, cipherKeylen); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doDecrypt(): gcry_cipher_setkey() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; delete [] hashedKey; goto out_close; } delete [] hashedKey; *outBufLen = inBufLen - STRING2KEY_SALTLEN; *outBuf = new unsigned char[*outBufLen]; // decrypt the data err = gcry_cipher_decrypt(handle, *outBuf, *outBufLen, inBuf, *outBufLen); if (err != GPG_ERR_NO_ERROR) { printDebug(string("LibGCryptIf::doEncrypt(): gcry_cipher_encrypt() failed: ") + gcry_strerror(err)); ret = e_cryptNotImpl; goto out_delete; } @@ -293,57 +297,62 @@ int LibGCryptIf::mapHashId(char algo) return GCRY_MD_SHA1; case PWM_HASH_SHA256: return GCRY_MD_SHA256; case PWM_HASH_SHA384: return GCRY_MD_SHA384; case PWM_HASH_SHA512: return GCRY_MD_SHA512; case PWM_HASH_MD5: return GCRY_MD_MD5; case PWM_HASH_RMD160: return GCRY_MD_RMD160; case PWM_HASH_TIGER: return GCRY_MD_TIGER; default: BUG(); } return GCRY_MD_NONE; } bool LibGCryptIf::hashPassphrase(const unsigned char *pw, size_t pwlen, unsigned char *salt, unsigned char *key, size_t keylen, - bool create) + bool create, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +) { DEK dek; STRING2KEY s2k; bool ret; dek.keylen = keylen; s2k.mode = 1; - s2k.hash_algo = mapHashId(conf()->confGlobHashAlgo()); + //US bug: do not use the global hash algo here. Use the passed ago instead. The hashalgo stored in the file can + // be different from the one in the configuration. + s2k.hash_algo = mapHashId(_hashalgo //conf()->confGlobHashAlgo() + ); s2k.count = 0; if (!create) memcpy(s2k.salt, salt, STRING2KEY_SALTLEN); ret = doHashPassphrase(&dek, pw, pwlen, &s2k, create); if (!ret) goto out; memcpy(key, dek.key, dek.keylen); if (create) memcpy(salt, s2k.salt, STRING2KEY_SALTLEN); out: return ret; } bool LibGCryptIf::doHashPassphrase(DEK *dek, const unsigned char *pw, size_t pwlen, STRING2KEY *s2k, bool create) { @@ -418,37 +427,37 @@ void LibGCryptIf::padData(unsigned char *buf, { size_t numPadBytes = boundary - ((bufLen + 1) % boundary); buf[bufLen] = static_cast<char>(0x01); size_t i = 0; Randomizer *rnd = Randomizer::obj(); char c; unsigned char *b; while (i < numPadBytes) { c = rnd->genRndChar(); if (c == static_cast<char>(0x01)) continue; b = buf + bufLen + 1 + i; *b = c; ++i; } } void LibGCryptIf::unpadData(const unsigned char *buf, size_t *bufLen) { size_t pos; BUG_ON(*bufLen % 8); pos = *bufLen - 1; while (buf[pos] != static_cast<char>(0x01)) { - qDebug("pos %d %d %d", pos, buf[pos], static_cast<char>(0x01) ); + //qDebug("pos %d %d %d", pos, buf[pos], static_cast<char>(0x01) ); BUG_ON(!pos); //LR BUG we should terminte the loop if p == 0 if ( pos == 0 ) break; --pos; } *bufLen = pos; - qDebug("ente "); + //qDebug("ente "); } #endif // CONFIG_PWMANAGER_GCRY diff --git a/pwmanager/pwmanager/libgcryptif.h b/pwmanager/pwmanager/libgcryptif.h index 1a7b658..9a987a2 100644 --- a/pwmanager/pwmanager/libgcryptif.h +++ b/pwmanager/pwmanager/libgcryptif.h @@ -52,100 +52,106 @@ protected: int hash_algo; uint8_t salt[STRING2KEY_SALTLEN]; uint32_t count; }; struct DEK { size_t keylen; uint8_t key[32]; // this is the largest used keylen (256 bit) }; public: LibGCryptIf() { } /** is libgcrypt available? */ static bool available() { return true; } /** encrypt data. _algo is the PWM_CRYPT_* ID * of the algorithm. */ PwMerror encrypt(unsigned char **outBuf, size_t *outBufLen, unsigned char *inBuf, size_t inBufLen, const unsigned char *key, size_t keylen, - char _algo); + char _algo, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +); /** decrypt data. _algo is the PWM_CRYPT_* ID * of the algorithm. */ PwMerror decrypt(unsigned char **outBuf, size_t *outBufLen, const unsigned char *inBuf, size_t inBufLen, const unsigned char *key, size_t keylen, - char _algo); + char _algo, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +); /** hash data. _algo is the PWM_HASH_* ID of the hash */ PwMerror hash(unsigned char **outBuf, size_t *outBufLen, const unsigned char *inBuf, size_t inBufLen, char _algo); /** returns the length of the hash. _algo is the PWM_HASH_* * id of the hash. returns 0 on error. */ unsigned int hashLength(char _algo); protected: /** returns the total buffer length */ size_t getBufLen(size_t inBufLen, size_t boundary) { return ((boundary - (inBufLen % boundary)) + inBufLen); } /** pad the data up to the given boundary. * "buf" has to be big enough! */ void padData(unsigned char *buf, size_t bufLen, size_t boundary); /** unpad the data */ void unpadData(const unsigned char *buf, size_t *bufLen); /** maps the PWM_CRYPT_* ID of an algorithm * to the libgcrypt GCRY_CIPHER_* ID */ int mapCipherId(char algo); /** maps the PWM_HASH_* ID of an algorithm * to the libgcrypt GCRY_MD_* ID */ int mapHashId(char algo); /** hash a passphrase to a cipher key */ bool hashPassphrase(const unsigned char *pw, size_t pwlen, unsigned char *salt, unsigned char *key, size_t keylen, - bool create); + bool create, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +); /** hash a passphrase to a cipher key */ bool doHashPassphrase(DEK *dek, const unsigned char *pw, size_t pwlen, STRING2KEY *s2k, bool create); }; #else // CONFIG_PWMANAGER_GCRY /** libgcrypt is not installed. This is a NOP wrapper. */ class LibGCryptIf { public: LibGCryptIf() { } static bool available() { return false; } PwMerror encrypt(unsigned char **, size_t *, unsigned char *, size_t, const unsigned char *, size_t, char) diff --git a/pwmanager/pwmanager/pwmdoc.cpp b/pwmanager/pwmanager/pwmdoc.cpp index 17cb74a..a740d6d 100644 --- a/pwmanager/pwmanager/pwmdoc.cpp +++ b/pwmanager/pwmanager/pwmdoc.cpp @@ -466,49 +466,49 @@ PwMerror PwMDoc::saveDoc(char compress, const QString *file) if (!serializeDta(&serialized)) { printDebug("PwMDoc::saveDoc(): serializeDta() failed"); f.close(); ret = e_serializeDta; goto out_moveback; } e = writeDataHash(hashAlgo, &serialized, &f); if (e == e_hashNotImpl) { printDebug("PwMDoc::saveDoc(): writeDataHash() failed: e_hashNotImpl"); f.close(); ret = e_hashNotImpl; goto out_moveback; } else if (e != e_success) { printDebug("PwMDoc::saveDoc(): writeDataHash() failed"); f.close(); ret = e_writeHeader; goto out_moveback; } if (!compressDta(&serialized, compress)) { printDebug("PwMDoc::saveDoc(): compressDta() failed"); f.close(); ret = e_enc; goto out_moveback; } - e = encrypt(&serialized, ¤tPw, &f, cryptAlgo); + e = encrypt(&serialized, ¤tPw, &f, cryptAlgo, hashAlgo); if (e == e_weakPw) { printDebug("PwMDoc::saveDoc(): encrypt() failed: e_weakPw"); f.close(); ret = e_weakPw; goto out_moveback; } else if (e == e_cryptNotImpl) { printDebug("PwMDoc::saveDoc(): encrypt() failed: e_cryptNotImpl"); f.close(); ret = e_cryptNotImpl; goto out_moveback; } else if (e != e_success) { printDebug("PwMDoc::saveDoc(): encrypt() failed"); f.close(); ret = e_enc; goto out_moveback; } unsetDocStatFlag(DOC_STAT_DISK_DIRTY); f.close(); #ifndef _WIN32_ if (chmod(filename.latin1(), conf()->confGlobFilePermissions())) { printWarn(string("chmod failed: ") + strerror(errno)); } #endif @@ -586,49 +586,49 @@ PwMerror PwMDoc::openDoc(const QString *file, int openLocked) if (deepLock(true, false) != e_success) return e_openFile; goto out_success; } if (!f.open(IO_ReadOnly)) return e_openFile; ret = checkHeader(&cryptAlgo, ¤tPw, &compress, &headerLen, &dataHashType, &dataHash, &f); if (ret != e_success) { printDebug("PwMDoc::openDoc(): checkHeader() failed"); f.close(); if (ret == e_wrongPw) { wrongMpwMsgBox(getDocStatFlag(DOC_STAT_USE_CHIPCARD)); return ret; } else if (ret == e_noPw || ret == e_fileVer || ret == e_fileFormat || ret == e_hashNotImpl) { return ret; } else return e_readFile; } - ret = decrypt(&decrypted, headerLen, ¤tPw, cryptAlgo, &f); + ret = decrypt(&decrypted, headerLen, ¤tPw, cryptAlgo, dataHashType, &f); if (ret == e_cryptNotImpl) { printDebug("PwMDoc::openDoc(): decrypt() failed: e_cryptNotImpl"); f.close(); return e_cryptNotImpl; } else if (ret != e_success) { printDebug("PwMDoc::openDoc(): decrypt() failed"); f.close(); return e_readFile; } if (!decompressDta(&decrypted, compress)) { printDebug("PwMDoc::openDoc(): decompressDta() failed"); f.close(); return e_fileCorrupt; } ret = checkDataHash(dataHashType, &dataHash, &decrypted); if (ret == e_hashNotImpl) { printDebug("PwMDoc::openDoc(): checkDataHash() failed: e_hashNotImpl"); f.close(); return e_hashNotImpl; } else if (ret != e_success) { printDebug("PwMDoc::openDoc(): checkDataHash() failed"); f.close(); return e_fileCorrupt; } @@ -1286,113 +1286,119 @@ bool PwMDoc::compressDta(string *d, char algo) return false; } bool PwMDoc::decompressDta(string *d, char algo) { PWM_ASSERT(d); switch (algo) { case PWM_COMPRESS_GZIP: { CompressGzip comp; return comp.decompress(d); } #ifndef PWM_EMBEDDED case PWM_COMPRESS_BZIP2: { CompressBzip2 comp; return comp.decompress(d); } #endif case PWM_COMPRESS_NONE: { return true; } } return false; } -PwMerror PwMDoc::encrypt(string *d, const QString *pw, QFile *f, char algo) +PwMerror PwMDoc::encrypt(string *d, const QString *pw, QFile *f, char algo, + char hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +) { PWM_ASSERT(d); PWM_ASSERT(pw); PWM_ASSERT(f); size_t encSize; byte *encrypted = 0; switch (algo) { case PWM_CRYPT_BLOWFISH: { Blowfish::padNull(d); encSize = d->length(); encrypted = new byte[encSize]; Blowfish bf; if (bf.bf_setkey((byte *) pw->latin1(), pw->length())) { delete [] encrypted; return e_weakPw; } bf.bf_encrypt((byte *) encrypted, (byte *) d->c_str(), encSize); break; } case PWM_CRYPT_AES128: /*... fall through */ case PWM_CRYPT_AES192: case PWM_CRYPT_AES256: case PWM_CRYPT_3DES: case PWM_CRYPT_TWOFISH: case PWM_CRYPT_TWOFISH128: { if (!LibGCryptIf::available()) return e_cryptNotImpl; LibGCryptIf gc; PwMerror err; unsigned char *plain = new unsigned char[d->length() + 1024]; memcpy(plain, d->c_str(), d->length()); err = gc.encrypt(&encrypted, &encSize, plain, d->length(), reinterpret_cast<const unsigned char *>(pw->latin1()), pw->length(), - algo); + algo, + hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase + ); delete [] plain; if (err != e_success) return e_cryptNotImpl; break; } default: { delete_ifnot_null_array(encrypted); return e_cryptNotImpl; } } // write encrypted data to file if (f->writeBlock(reinterpret_cast<const char *>(encrypted), static_cast<Q_ULONG>(encSize)) != static_cast<Q_LONG>(encSize)) { delete_ifnot_null_array(encrypted); return e_writeFile; } delete_ifnot_null_array(encrypted); return e_success; } PwMerror PwMDoc::decrypt(string *d, unsigned int pos, const QString *pw, - char algo, QFile *f) + char algo, + char hashalgo, //US BUG: pass _hashalgo because we need it in hashPassphrase + QFile *f) { PWM_ASSERT(d); PWM_ASSERT(pw); PWM_ASSERT(f); unsigned int cryptLen = f->size() - pos; byte *encrypted = new byte[cryptLen]; byte *decrypted = new byte[cryptLen]; f->at(pos); #ifndef PWM_EMBEDDED if (f->readBlock(reinterpret_cast<char *>(encrypted), static_cast<Q_ULONG>(cryptLen)) != static_cast<Q_LONG>(cryptLen)) { delete [] encrypted; delete [] decrypted; return e_readFile; } #else if (f->readBlock((char *)(encrypted), (unsigned long)(cryptLen)) != (long)(cryptLen)) { delete [] encrypted; delete [] decrypted; @@ -1402,49 +1408,51 @@ PwMerror PwMDoc::decrypt(string *d, unsigned int pos, const QString *pw, switch (algo) { case PWM_CRYPT_BLOWFISH: { Blowfish bf; bf.bf_setkey((byte *) pw->latin1(), pw->length()); bf.bf_decrypt(decrypted, encrypted, cryptLen); break; } case PWM_CRYPT_AES128: /*... fall through */ case PWM_CRYPT_AES192: case PWM_CRYPT_AES256: case PWM_CRYPT_3DES: case PWM_CRYPT_TWOFISH: case PWM_CRYPT_TWOFISH128: { if (!LibGCryptIf::available()) return e_cryptNotImpl; LibGCryptIf gc; PwMerror err; err = gc.decrypt(&decrypted, &cryptLen, encrypted, cryptLen, reinterpret_cast<const unsigned char *>(pw->latin1()), pw->length(), - algo); + algo, + hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +); if (err != e_success) { delete [] encrypted; delete [] decrypted; return e_cryptNotImpl; } break; } default: { delete [] encrypted; delete [] decrypted; return e_cryptNotImpl; } } delete [] encrypted; #ifndef PWM_EMBEDDED d->assign(reinterpret_cast<const char *>(decrypted), static_cast<string::size_type>(cryptLen)); #else d->assign((const char *)(decrypted), (string::size_type)(cryptLen)); #endif delete [] decrypted; if (algo == PWM_CRYPT_BLOWFISH) { if (!Blowfish::unpadNull(d)) { BUG(); diff --git a/pwmanager/pwmanager/pwmdoc.h b/pwmanager/pwmanager/pwmdoc.h index 138dd3d..9fcdda7 100644 --- a/pwmanager/pwmanager/pwmdoc.h +++ b/pwmanager/pwmanager/pwmdoc.h @@ -715,51 +715,55 @@ protected: /** lock counter for the "dataChanged" signal */ unsigned int dataChangedLock; /** list of all open documents */ static PwMDocList openDocList; protected: /** serialize "dta" and return it in "d". */ bool serializeDta(string *d); /** de-serialize "d" and overwrite "dta" */ bool deSerializeDta(const string *d, bool entriesLocked); /** write header to file */ PwMerror writeFileHeader(char keyHash, char dataHash, char crypt, char compress, QString *pw, QFile *f); /** write data-hash to file */ PwMerror writeDataHash(char dataHash, string *d, QFile *f); /** check header. Read header info and verify key-hash and filever. * returns length of header in "headerLength" */ PwMerror checkHeader(char *cryptAlgo, QString *pw, char *compress, unsigned int *headerLength, char *dataHashType, string *dataHash, QFile *f); /** check the data-hash */ PwMerror checkDataHash(char dataHashType, const string *dataHash, const string *dataStream); /** encrypt data "d" and write to "filename" */ - PwMerror encrypt(string *d, const QString *pw, QFile *f, char algo); + PwMerror encrypt(string *d, const QString *pw, QFile *f, char algo, + char _hashalgo //US BUG: pass _hashalgo because we need it in hashPassphrase +); /** read data from file beginning at "pos", decrypt and return it */ - PwMerror decrypt(string *d, unsigned int pos, const QString *pw, char algo, QFile *f); + PwMerror decrypt(string *d, unsigned int pos, const QString *pw, char algo, + char _hashalgo, //US BUG: pass _hashalgo because we need it in hashPassphrase +QFile *f); /** compress the data */ bool compressDta(string *d, char algo); /** uncompress the data */ bool decompressDta(string *d, char algo); /** internal import function for a text-file generated by PwM. * If this is not a valid PwM-exported file, it returns e_fileFormat */ PwMerror importText_PwM(const QString *file); /** PwM-text-import helper function to extract the name/pw/comment out * of one entry-line */ bool textExtractEntry_PwM(const char *in, ssize_t in_size, string *out); /** compare two strings */ bool compareString(const string &s1, const string &s2, bool caseSensitive, bool exactWordMatch); /** clears all document-data */ void clearDoc(); /** delete all empty categories */ void delAllEmptyCat(bool dontFlagDirty); /** set a document status flag */ void setDocStatFlag(unsigned int statFlag) { curDocStat |= statFlag; } /** unset a document status flag */ void unsetDocStatFlag(unsigned int statFlag) { curDocStat &= ~statFlag; } /** get a document status flag */ |