get-databasehash is now encrypted

This commit is contained in:
varjolintu 2017-06-27 10:26:48 +03:00
parent 50aca6a250
commit 686e98495f
4 changed files with 77 additions and 41 deletions

View file

@ -1,3 +1,7 @@
0.2.1 (2017-06-27)
=========================
- get-databasehash request/response is now encrypted
0.2.0 (2017-06-26)
=========================
- Added JSON install files and script for Windows

View file

@ -24,7 +24,7 @@ Now the requests are encrypted by [TweetNaCl.js](https://github.com/dchest/tweet
1. keepassxc-browser generates a key pair (with public and secret key) and transfers the public key to KeePassXC
2. When KeePassXC receives the public key it generates its own key pair and transfers the public key to keepassxc-browser
3. All messages (excluding get-databasehash) are now encrypted.
3. All messages between the browser extension and KeePassXC are now encrypted.
4. When keepassxc-browser sends a message it is encrypted with KeePassXC's public key, a random generated nonce and keepassxc-browser's secret key.
5. When KeePassXC sends a message it is encrypted with keepassxc-browser's public key etc.
6. Databases are stored based on the current public key used with `associate`. A new key pair for data transfer is generated each time keepassxc-browser is launched.
@ -48,7 +48,7 @@ Response (success):
```javascript
{
"action": "change-public-keys",
"version": "2.1.2",
"version": "2.2.0",
"publicKey": "<host public key>",
"success": "true"
}
@ -62,12 +62,12 @@ Request:
}
```
Response (success):
Response message data (success, decrypted):
```javascript
{
"action": "hash",
"hash": "29234e32274a32276e25666a42",
"version": "2.1.2"
"version": "2.2.0"
}
```
@ -93,7 +93,7 @@ Response message data (success, decrypted):
```javascript
{
"hash": "29234e32274a32276e25666a42",
"version": "2.1.2",
"version": "2.2.0",
"success": "true",
"id": "testclient",
"nonce": "tZvLrBzkQ9GxXq9PvKJj4iAnfPT0VZ3Q"
@ -122,7 +122,7 @@ Request:
Response message data (success, decrypted):
```javascript
{
"version": "2.1.2",
"version": "2.2.0",
"nonce": "tZvLrBzkQ9GxXq9PvKJj4iAnfPT0VZ3Q",
"hash": "29234e32274a32276e25666a42",
"id": "testclient",
@ -142,7 +142,7 @@ Request:
Response message data (success, decrypted):
```javascript
{
"version": "2.1.2",
"version": "2.2.0",
"entries": [
{
"login": 144,
@ -191,7 +191,7 @@ Response message data (success, decrypted):
"nonce": "tZvLrBzkQ9GxXq9PvKJj4iAnfPT0VZ3Q",
"success": "true",
"hash": "29234e32274a32276e25666a42",
"version": "2.1.2"
"version": "2.2.0"
}
```
@ -227,7 +227,7 @@ Response message data (success, decrypted):
"nonce": "tZvLrBzkQ9GxXq9PvKJj4iAnfPT0VZ3Q",
"success": "true",
"hash": "29234e32274a32276e25666a42",
"version": "2.1.2"
"version": "2.2.0"
}
```

View file

@ -31,7 +31,6 @@ keepass.addCredentials = function(callback, tab, username, password, url) {
keepass.updateCredentials(callback, tab, null, username, password, url);
}
// Not tested
keepass.updateCredentials = function(callback, tab, entryId, username, password, url) {
page.debug("keepass.updateCredentials(callback, {1}, {2}, {3}, [password], {4})", tab.id, entryId, username, url);
@ -191,7 +190,7 @@ keepass.retrieveCredentials = function (callback, tab, url, submiturl, forceCall
keepass.callbackOnId = function (ev, id, callback) {
var listener = ( function(port, id) {
var handler = function(msg) {
if(msg.action == id) {
if (msg && msg.action == id) {
ev.removeListener(handler);
callback(msg);
}
@ -465,32 +464,61 @@ keepass.getDatabaseHash = function (callback, tab, triggerUnlock) {
keepass.changePublicKeys(tab, function(res) {});
}
var message = { "action": "get-databasehash" };
var key = keepass.b64e(keepass.keyPair.publicKey);
var nonce = nacl.randomBytes(keepass.keySize);
var messageData = {
action: "get-databasehash"
};
var request = {
action: "get-databasehash",
message: keepass.encrypt(messageData, nonce),
nonce: keepass.b64e(nonce)
};
//var message = { "action": "get-databasehash" };
keepass.callbackOnId(keepass.nativePort.onMessage, "get-databasehash", function(response) {
if (response.hash)
{
console.log("hash reply received: "+ response.hash);
var oldDatabaseHash = keepass.databaseHash;
keepass.setcurrentKeePassXCVersion(response.version);
keepass.databaseHash = response.hash || "no-hash";
if (oldDatabaseHash && oldDatabaseHash != keepass.databaseHash) {
keepass.associated.value = false;
keepass.associated.hash = null;
if (response.message && response.nonce) {
var res = keepass.decrypt(response.message, response.nonce);
if (!res)
{
console.log("Failed to decrypt message");
}
else
{
var message = nacl.util.encodeUTF8(res);
var parsed = JSON.parse(message);
statusOK();
callback(response.hash);
if (parsed.hash)
{
console.log("hash reply received: "+ parsed.hash);
var oldDatabaseHash = keepass.databaseHash;
keepass.setcurrentKeePassXCVersion(parsed.version);
keepass.databaseHash = parsed.hash || "no-hash";
if (oldDatabaseHash && oldDatabaseHash != keepass.databaseHash) {
keepass.associated.value = false;
keepass.associated.hash = null;
}
statusOK();
callback(parsed.hash);
}
else if (parsed.errorCode)
{
keepass.databaseHash = "no-hash";
keepass.isDatabaseClosed = true;
console.log("Error: KeePass database is not opened.");
if (tab && page.tabs[tab.id]) {
page.tabs[tab.id].errorMessage = "KeePass database is not opened.";
}
callback(keepass.databaseHash);
}
}
}
else if (response.errorCode)
{
keepass.databaseHash = "no-hash";
keepass.isDatabaseClosed = true;
console.log("Error: KeePass database is not opened.");
if (tab && page.tabs[tab.id]) {
page.tabs[tab.id].errorMessage = "KeePass database is not opened.";
}
callback(keepass.databaseHash);
else if (response.error && response.errorCode) {
keepass.handleError(tab.id, response.error, response.errorCode);
}
else
{
@ -499,9 +527,9 @@ keepass.getDatabaseHash = function (callback, tab, triggerUnlock) {
page.tabs[tab.id].errorMessage = "Database hash not received.";
}
callback(keepass.databaseHash);
}
}
});
keepass.nativePort.postMessage(message);
keepass.nativePort.postMessage(request);
}
keepass.changePublicKeys = function(tab, callback) {
@ -776,11 +804,15 @@ keepass.setCryptoKey = function(id, key) {
keepass.encrypt = function(input, nonce) {
var messageData = nacl.util.decodeUTF8(JSON.stringify(input));
var message = nacl.box(messageData, nonce, keepass.serverPublicKey, keepass.keyPair.secretKey);
if (!message) {
return "";
if (keepass.serverPublicKey) {
var message = nacl.box(messageData, nonce, keepass.serverPublicKey, keepass.keyPair.secretKey);
if (message) {
return keepass.b64e(message);
}
}
return keepass.b64e(message);
console.log("Cannot encrypt message! Server public key needed.");
return "";
}
keepass.decrypt = function(input, nonce, toStr) {

View file

@ -1,7 +1,7 @@
{
"manifest_version": 2,
"name": "keepassxc-browser",
"version": "0.2.0",
"version": "0.2.1",
"description": "KeePassXC integration for modern web browsers",
"author": "Sami Vänttinen",
"icons": {
@ -70,7 +70,7 @@
"tabs",
"webRequest",
"webRequestBlocking",
"https://raw.github.com/"
"https://api.github.com/"
],
"applications": {
"gecko": {