On 21 Jan 2014, at 13:54, Bruno Oliveira <bruno@abstractj.org> wrote:


On January 20, 2014 at 3:00:54 PM, Tadeas Kriz (tkriz@redhat.com) wrote:


I know we’ve been discussing this before, but with no solution.  
I myself think, that the store should fail to open when the passphrase  
is wrong, because that’s where you’d like to have your “try ..  
catch ..” to handle the problem, not elsewhere, when you want  
to actually read/write/delete from the store, that’s just not  
very user friendly.
If the answer to that is YES, then the next question is, how to decide 
when the passphrase is right and when it isn’t. Again I’ll write 

Like I mentioned here (https://issues.jboss.org/browse/AGDROID-173), our goal to the very initial release was not to make anything perfect, but lay down the groundwork for encryption. So if you where you read “Experimental”, by that means, not perfect.

Offline authentication didn’t start yet, so that might happen. The API will be user friendly when become stable.

On one side, the API for DataManager is considered stable, because changing it is postponed for version 2.0.0, but on the other hand it’s not stable? I’m a bit confused right now. I completely agree with the decision to not change the DataManager API before 2.0.0, but that means the API should be almost perfect and the implementation might not be as good, because the implementation can be improved overtime.

more ways I’ve got on mind, that’d solve this. Important is, that  
none of them actually stores the passphrase!
On each call of ‘open()’:
1. do ‘readAll()’ to ensure the passphrase is right. Basically,  
that’s what user has to do now to find out if the passphrase is right.  

2. read the first row and if the read is successful, then the passphrase  
is right. In this case, we’d have to be 100% sure that there is no  
way to put data into the store with different key and thus all the  
rows are encrypted with the same passphrase.

We are aware of it, at the same time we didn’t add support for querying into the database. That’s planned, but not atm. Our focus was data encryption, optimizations will come with the next releases, for this reason a jiras like this existhttps://issues.jboss.org/browse/AGSEC-137 

I’m not talking about optimisations there. The whole problem is about developer’s experience. Like I wouldn’t like to have to add try .. catch .. everywhere I’d like to read/save/delete from encrypted database, that’s just not cool.

3. Save some metadata for each data model, that would be encrypted  
with the same passphrase and we’d read them and if successful,  
the passphrase is right. This has two possible implementations.  

a. The first row in the data model table would be reserved for the  
metadata, so the verification would work similarly to the option 

b. There would be separate table, in which we’d add a row for each  
data model table. Again, very similar to a. but without the pain  
of having different data in the same table. Also, if the implementation  
of SQLStore will become multi-table (instead of multi-database  
which is now), there would be only one table for all the metadata.  

So, what do you think?

Repeating what I said on that Jira, it seems too much. APIs like SQLCipher don’t do that.

You can’t compare EncryptedSQLStore with SQLCipher. Completely different way of encryption. SQLCipher encrypts the database page by page (mostly chunks of 1024 bytes), but EncryptedSQLStore encrypts only the data row by row individually (check [1] for very simple comparsion). That’s completely different approach. This way you can find out if the passphrase is right by calling basically any SQL command and an exception will be thrown if it won’t succeed. That’s something that cannot be achieved with current EncryptedSQLStore implementation. The EncryptedSQLStore already saves IV and Salt in separate table. It wouldn’t be a problem, performance issue or space issue to add one more row, which the EncryptedSQLStore would try to decrypt and if successful, that’d mean the passphrase is correct. The value of that row might be just an encrypted JSON with random key and value. That way, you’d check if the decrypted is valid JSON. There should be no security issue with that, or is there?

PS: For abstractj, I’ve been trying to find any library that would  
do the encryption on high-level, as AeroGear does, but couldn’t  
find any. There are many ways to encrypt SQLite database though  
they work on different approach of encrypting the whole database  
file, not just rows themselves.

That’s the reason why we’ve been working on it.

I’m not saying “don’t work on it”. I’m just trying to help, so it'll have added value for the user.

Tadeas Kriz

aerogear-dev mailing list

1 - http://i.imgur.com/u7WFNPJ.png