Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Prevent renaming files or swap content #72

Open
Gromolyak opened this issue Feb 21, 2020 · 12 comments
Open

Prevent renaming files or swap content #72

Gromolyak opened this issue Feb 21, 2020 · 12 comments

Comments

@Gromolyak
Copy link

Gromolyak commented Feb 21, 2020

Embed the product (hash) of the file encryption key into the encrypted file name (concat it after a zero byte in plain file name, for example), on open, just check it, that's all, folks!

@Gromolyak Gromolyak changed the title Disallow moving files or swap content Prevent renaming files or swap content Feb 21, 2020
@overheadhunter
Copy link
Member

If it was that simple, we would have done it already. This is a known issue for a long time, see cryptomator/cryptomator#119.

What you're suggesting would lead to a key-reuse in CTR mode, which is certainly not a good idea.

@Gromolyak
Copy link
Author

Gromolyak commented Feb 21, 2020

OK, you are right, but how about to put file encryption key hash together with the dir id (as AD)? The decoded value of the file name can be used without knowing the AD (that is, without getting file encryption key from file header) for dir listing purposes, just skip MAC checking after AES CTR decoding in SIV mode. That's all. :-)
P. S. in case of moving the file into another dir it will be listed anyway, but will not open, so what?

@overheadhunter
Copy link
Member

Any AD will change the filename. But we need deterministic filenames for a variety of reasons, among them the ability to utilize the file versioning in the cloud but also for not running into conflicts when different devices write to the same file concurrently.

Therefore AD can only contain data that doesn't change. The file encryption key on the other side must change on each write.

@Gromolyak
Copy link
Author

Gromolyak commented Feb 21, 2020

"32 bytes file content key" in file header as of https://docs.cryptomator.org/en/latest/security/architecture/. When does it change?
I can see I will have to implement it myself since you don't understand me. Alas, I dislike java, so I will have to reimplement the whole thing in C++.

@overheadhunter
Copy link
Member

overheadhunter commented Feb 21, 2020

wrong

The first 16 bytes of a SIV-encrypted ciphertext is the ... well... SIV. It is basically a CMAC over the cleartext + AD.

I.e. changing only one single bit in the AD will result in a completely different ciphertext filename.

I can see I will have to implement it myself since you don't understand me. Alas, I hate java, so I will have to reimplement the whole thing in C++.

feel free

@Gromolyak
Copy link
Author

Gromolyak commented Feb 21, 2020

"changing only one single bit in the AD will result in a completely different ciphertext filename". You will have to change it only to move the file to another dir or to rename the file. There is no difference between the already "embedded" dir id and the suggested hash to "embed" along with it. Each of both "link" the encrypted name to some data. It can not be explained simpler.

@overheadhunter
Copy link
Member

Well, the dir ID is per dir, while anything related to the file (which is the whole point of this issue) is per file. Therefore the AD stays the same.

@Gromolyak
Copy link
Author

Gromolyak commented Feb 21, 2020

I don't understand what you mean.
Now the AD stays the same per dir, right.
If we add one more AD, it will depend on the unique file content key as well:

The AD for a file name = AD1, AD2
AD1 = dir id
AD2 = file id (unique file content key)
The AD will not stay the same per dir because it will contain AD2 which will depend on file content key from the file header.

Of course this straight approach has a weakness - no check for valid file name will be possible before obtaining the AD2 from the file. That means a better solution is to keep a separate SIV for it (it will cost 16 extra raw bytes or 26 in Base32, 22 in Base64). That is calculated by the function s2v( .. ) in SivMode.java. This extra SIV will be checked only before opening the file.

@overheadhunter
Copy link
Member

overheadhunter commented Feb 22, 2020

  • The AD MUST NOT CHANGE
  • The file key MUST CAN CHANGE

You can not combine these two, if you put the file key (or a hash or anything derived from it) into the filename.

@Gromolyak
Copy link
Author

"The file key MUST CHANGE" - when? If it ever changes, each encrypted chunk should be reecrypted. A you sure you are talking about the "32 bytes file content key" from the file header?

@overheadhunter
Copy link
Member

overheadhunter commented Feb 24, 2020

Ok, to be more precise: The file key doesn't necesarrily change, but it must be able to change. Consider concurrent access by multiple devices or if the full file gets rewritten (which is btw always the case with WebDAV due to lacking client capabilities): There are many occasions where the existing file header gets discarded and a new file content key is created.

So from a cryptographic perspective it would indeed be possible to use the content key as AD, if it stayed the same forever.

That said, reading from each file during a directory listing is somewhere from impractical (on the desktop application) to impossible (on mobile apps - think of rate limiting, bandwidth, etc).

Skipping authentication during file name decryption and thus making the system vulnerable to CCAs isn't the right approach, either.

@Gromolyak
Copy link
Author

Gromolyak commented Mar 1, 2020

Oh, this WebDAV! I forgot about it... :-(

Let us imagine that the encoded file name contains some extra data, but the decoded name does not depend on this data.
That is, an encrypted directory can contain files with different encoded names which decode to the same visible name.
Whenever it happens, it means there is a version conflict, and the client (Cryptomator)
should keep only one file of those and delete the others. This decision can be made automatically depending on the modification date, or even some interaction with the user could be provided.
That extra data would contain whichever id of the file as described in the previous posts.
Keeping that data WOULD NOT lead to "Skipping authentication during file name decryption", that data is to be checked against the file header data ONLY WHEN there will be a request to read that file. Later I could describe one possible implementation based on the RFC 5297 and the existing Cryptomator code.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants