embedded keys - there has to be a less vulnerable approach
From: Andrew Mayo (ajmayo_at_my-deja.com)
Date: 25 Jun 2003 09:36:18 -0700
A problem that seems to be increasingly common these days involves the
idea of protecting information in a source such as a relational
database, which by its nature is intended to facilitate the sharing
and retrieval of information.
Ideally, the database would be run on top of an encrypting file system
so that data would only be available in cleartext to the actual
requestor, but not by interrogating the database file (e.g SQL Server
.dat file) by other means.
This, however, is not practical in the majority of situations, and the
use of EFS, in any case, is an expensive solution in computational
terms as every access operation must be encrypted.
Since in most cases only a small subset of the data is actually
sensitive, most protection methods resort to encrypting only this
data, when it is stored or updated, and decrypting it as a batch
operation once the rowset has been returned to the client application.
The problem here, however, is that encrypting and decrypting the data
require either a single key in the case of symmetrical encryption
algorithms (e.g DES, Blowfish, etc), or a public/private keypair if
asymmetrical algorithms such as RSA are used.
This key (or keys) must be preserved as a secret, most usually by
embedding it within the application, ideally in such a way that the
key bytes are scattered randomly throughout the executable image.
The secrecy of this key is also the most vulnerable part of this
scheme. Because of distribution issues, an application with a large
fanout i.e large user base must use the same 'secret' key embedded in
each copy of the executable which will perform the encrypt/decrypt
Apart from obvious attack methods such as tracing API calls etc, a
hostile insider such as a previous employee of the company who
developed the software might use their knowledge of the key to access
information without due authorisation.
The use of an asymmetrical encryption algorithm does not seem to offer
any particular advantages here, because the encryption and decryption
processes must occur on the same machine. In normal use, asymmetrical
schemes solve the key distribution problem because the sender does not
need to know the receiver's private key. But in this case the two keys
must be known on the one system in order to encrypt and decrypt via
the application. This then reduces security to the same case as a
single key symmetrical algorithm; if you can reveal this key, the
system is broken.
Concealment of the encryption key is somewhat easier than concealment
of the decryption key (assuming they differ) because the encryption
process can be encapsulated into a component such as a DLL which
performs the encryption opaquely. Other than dictionary attacks, which
are pointless if the keyspace and messagespace are reasonably large,
there is then no easy way of determining the encryption key other than
single-stepping through the component with a debugger and hoping that
the code has not been too obfuscated.
By precompiling this component and restricting access to its source
code within an organisation, the spread of knowledge regarding the
encryption key can be controlled to a reasonable extent, provided that
a hostile attacker is not a member of that small knowledgeable elite.
However, concealment of the decryption key is more difficult. Since
application code will need to decrypt data in several places, the code
to perform the decryption must appear in-line with the key included.
It is clearly not possible to encapsulate the decryption process in a
component as was done with encryption because if this is done, anyone
calling the component can directly decrypt the data!.
This means that developers must have knowledge of the key in order to
write code, thus making it more difficult to restrict its
dissemination and increasing the pool of potential hostile attackers
(e.g a developer who has been laid off)
There must be a better way of managing this problem, but I cannot find
any research on this specific issue. Can anyone point me in the
direction of any useful material which might enable a stronger system
to be constructed?
You have a table with customer names and addresses. This information
is sensitive. If you can encrypt the customer names and addresses
only, then the remainder of the database is not directly useful; the
join out to the rest of the system is by customer ID number and this
is not directly meaningful.
So you batch encrypt these columns when storing customers and batch
decrypt them when retrieving customers, so that the only time this
information appears in cleartext is within your application, and in
We assume that users of the application have been duly authorised by
password control etc. and possibly operating system level security, so
the problem here is to protect the decryption process from attack by a
knowledgeable insider who knows the secret decryption key, which has
been embedded in the application code.
You might suppose that the encryption and decryption keys (or key, if
this is a symmetrical system) can be computed at installation time,
for example, by calculating a GUID. This is indeed feasible but now
this information must be stored somewhere. You might choose to update
a prearranged sequence of bytes within the install image (carefully
reserved as a buffer, and not sequential) but then the offset position
of each byte must be fixed at compile time and so THIS information
becomes effectively the decryption key and you are no more secure than
when you started.
Products such as PGP secure private keys on a keyring and use
passphrases to control access to them. This is practical if you are a
human being reading your email, but this decryption must be done under
program control and if you store the passphrase you are also back
where you started, security-wise.
So, any thoughts, folks?