0

Edit

I am trying to develop a password managing tool for companies. My idea is that the passwords in some kind of database are encrypted with a master password which only the admin has.

Per department in a company there should be an own password, which lets the users of that department only access their passwords.

Lets look at an example.

  • Department A
    • Billing system, Password: "Hello"
  • Department B
    • Mail, Password: "World"

The passwords are encrypted with the master password of the admin. Lets just assume it is 0000. So in the database there would be something like this

  • Department A
    • Billing system, Password: encrypt("Hello",0000,'A')
  • Department B
    • Mail, Password: encrypt("World",0000,'B')

Furthermore, the password of department A would be 9999 and of department B 7777. Now I am searching for a possibility to decrypt the password of the billing system with the password 9999 and decrypt the mail password with 7777. But it should not be possible to decrypt the mail password with 9999 and vice versa.

  • Billing system: decrypt(encrypt("Hello",0000,'A'), 9999) = "Hello"
  • Billing system: decrypt(encrypt("Hello",0000,'A'), 7777) != "Hello"
  • Mail: decrypt(encrypt("World",0000,'B'), 9999) != "World"
  • Mail: decrypt(encrypt("World",0000,'B'), 7777) = "World"

Not that this it hard enough, the admin user must have the possibility to decrypt any password with his master password 0000

  • Billing system: decrypt(encrypt("Hello",0000,'A'), 0000) = "Hello"
  • Mail: decrypt(encrypt("World",0000,'B'), 0000) = "World"

I hope that my ideas are getting clearer now...

Ph3n1x
  • 307
  • 7
  • 13
  • You always encrypt with the *public* key of the destination. Then only the private key owner can ever decrypt. Encrypting with private key is only done to *sign* documents, when the hash digest is encrypted with the private key and anyone can decrypt it using the public key, thus validating the signature. – Remus Rusanu Oct 23 '14 at 20:09
  • Well, yeah, you are right for the standard asymmetric cryptography. Maybe the use of private and public key is irritating here... Do you have a better idea of naming? – Ph3n1x Oct 23 '14 at 20:39
  • Absolutely unclear what you are trying to do and off topic as well as this doesn't evolve programming. You could post on crypto, but only if you can describe your protocol using some kind of standard notation, this one would be closed almost immediately. – Maarten Bodewes Oct 23 '14 at 22:02
  • Yeah, it is hard to describe my idea/problem without yelling out my idea to the world ;) But I guess otherwise nobody will understand what I am looking for. So I have rewritten the text... – Ph3n1x Oct 24 '14 at 00:12
  • 1
    What you want to achieve is already implemented as [key hierarchy](http://msdn.microsoft.com/en-us/library/ms189586.aspx). – Remus Rusanu Oct 24 '14 at 05:02

1 Answers1

1

Preface: you cannot design a cryptographic system without knowing its full intent and purpose, so me giving any snippet of advice may be wholly unsuitable for your eventual end goal. Also, you may rather want to ask the experts at http://security.stackexchange.com or http://crypto.stackexchange.com. Also, I have more of a general knowledge of cryptography and this is a general programming forum, so take the below with a grain of salt.


Having said that, the usual way to store one piece of information in an encrypted form but make it accessible to multiple parties using different passwords is to use intermediate encryption keys. You have your plaintext. You generate a random key and use that to encrypt the plaintext. You now encrypt the randomly generated key with the user's personal password and store the result.

plaintext  = 'Hello World'
key        = make_random_string(128)
ciphertext = encrypt(plaintext, key)
keys = {
    user1: encrypt(key, user1password),
    user2: encrypt(key, user2password),
    ...
}

To decrypt, you use the user's password to decrypt the key to then decrypt the actual information.

key       = decrypt(keys.user1, user1password)
plaintext = decrypt(ciphertext, key)

print plaintext

This indirection allows you to share the same piece of information among several users. In practice you'd probably use symmetric encryption to encrypt the plaintext with the random key, and asymmetric encryption to encrypt the random key with each user's public key. That means in practice, every time you generate a new random symmetric encryption key, the system needs to create a copy of it individually encrypted with each user's public key that should have access to it.

This also allows you to irretrievably revoke an individual user's access to a specific piece of information, simply by nuking that users version of the random encryption key.

deceze
  • 510,633
  • 85
  • 743
  • 889