Data encryption
This topic discusses the encryption of data at the application level. For information about encrypting data transferred over a network, see the bulleted links on Data Security and Encryption. |
Synergy DBL enables you to encrypt and decrypt sensitive data using industry standard cipher techniques. This is accomplished on an on-demand basis using a set of Synergy subroutines that encrypt and decrypt a specified data region. You determine which data is encrypted as well as how it is encrypted.
On Windows, as of Synergy/DE 12, the Synergy data encryption feature uses Microsoft’s Cryptography API: Next Generation (CNG). On UNIX and OpenVMS, the Synergy data encryption feature interfaces with a third-party library, OpenSSL. We use PKCS #5 (Public Key Cryptography Standards) in conjunction with PBKDF2 (Password-Based Key Derivation Function); both are from RSA Security. To learn more about PKCS, visit tools.ietf.org/html/rfc2898.
Setting up your system for encryption (UNIX and OpenVMS)
On UNIX and OpenVMS, the vendor-supplied OpenSSL libraries are installed in a default location determined by the operating system. You do not need to set the library path. See OpenSSL requirements (UNIX and OpenVMS) for details on supported OpenSSL versions.
Encrypting and decrypting data
The DATA_ENCRYPT and DATA_DECRYPT routines encrypt and decrypt data using the data and password buffers that you pass to them. Optionally and recommended, the salt and iv arguments can be used to further enhance security. You can use the DATA_SALTIV routine to generate pseudorandom values that are appropriate for use.
As with the password, the same salt and IV (initialization vector) used to encrypt the data is required to decrypt it, so these values must be saved off. However, the salt and IV don’t need to be kept secret. |
The salt is used to derive the encryption key from the password, whereas the IV is used to randomize the resulting encrypted data. The encryption key used to encrypt/decrypt the data is immediately discarded by OpenSSL. Changing the keys that are used can be accomplished by altering either the password or the salt before encrypting. Additional key derivation parameters (iteration and key length) are kept internal and are set appropriately for the requested encryption algorithm. Supported encryption routines include 3DES-CBC (Triple DES) and AES-CBC.
Ciphers process data in blocks. If the length of the data isn’t a multiple of the cipher block size, DATA_ENCRYPT and DATA_DECRYPT use PKCS padding to pad it. Bytes of padding (between 1 byte and the number of bytes in a cipher block) are always added to the data when it is encrypted and then removed when it is decrypted. When using PKCS padding, the unencrypted data can be any size, but the encrypted data is always a multiple of cipher block size; PKCS padding does not allow in-place encryption even when the data is a multiple of the cipher block size.
To encrypt and decrypt data without changing its size (or for in-place encryption), you can suppress padding, but the data must be a multiple of cipher block size (which is 16 for AES encryption). To suppress padding, pass a 0 value to the DATA_ENCRYPT and DATA_DECRYPT routine’s pad argument. If you suppress padding to encrypt a piece of data, you must also suppress padding when you decrypt that same piece of data, or the decryption will fail with an “Argument specified with wrong size” error ($ERR_ARGSIZ).
To use in-place encryption, you must explicitly suppress padding. |
To determine the size of the encrypted data, pass the len argument to DATA_ENCRYPT with no destination argument. This will apply a formula based on the cipher block size and the padding (which is either 1 or 0). For example, for AES, the formula is
16 * (%TRUNC(data_size / 16) + padding)
Index data should be encrypted only if it is used for lookup only (READ with MATCH:Q_EQ) and not for index sequences (READS) and made into an alpha field of the size of the encrypted region. The key used for the lookup would be encrypted on the client first before being passed to a READ or FIND statement. Any file that uses encryption contains binary data and can only be unloaded/reloaded from a counted file. Access to encrypted data in a Synergy file is not supported by xfODBC. Make sure you mark encrypted fields as “Excluded by ReportWriter” in the repository. |
To implement Synergy data encryption,
1. | Decide what type of encryption you want to use and which fields should be encrypted. For example, you might choose to use AES-256 encryption to encrypt a field in your customer master record. You can allow for padding by inserting a “pad” field directly after the field and then declaring an overlay field to encompass both the original field and the pad field. Make sure when encrypting that the source doesn’t include the pad field. If the field is a multiple of the cipher block size, you may also suppress padding. |
2. | If you want to maximize the effectiveness of the cipher by including a random salt and/or IV, call the DATA_SALTIV routine and save the resulting value(s). |
3. | Before writing data to your master file using the STORE and WRITE statements, call the DATA_ENCRYPT routine with a user password and the salt and/or IV you generated in step 2, if applicable. |
4. | After reading data from your master file using the READ and READS statements, call the DATA_DECRYPT routine with the same user password, salt, and/or IV that you used to encrypt the data. |
5. | Convert your master file (if one existed before) to the new record structure. (Note that you must construct a program or routine to perform this conversion; no utility exists to convert the file automatically.) |
Examples
For an example of a traditional Synergy application that uses the DATA_ENCRYPT and DATA_DECRYPT routines see https://github.com/SteveIves/DataEncryptionDemo.
For a UI Toolkit application that uses data encryption, see CCtest, available from Synergy CodeExchange in the Synergex Resource Center.
Data at rest encryption
Synergy allows you to perform data at rest encryption for protected data (for example, credit card, Social Security, NHI, and bank account numbers) as long as you have the following:
- A relative file or an ISAM file
- Access to some encrypted key store service (there are many, including Azure) to access the original encryption keys and decrypt them in an industry-secure way
For ISAM files, key data encryption is possible where the keys provide direct keyed access (rather than ordered retrieval). Keep the following rules in mind when using data at rest encryption:
- Each key must be separately encrypted, with the key size being the encryption boundary. (When updating an application to use this feature, it's likely that you'll need to change key size.)
- Keys should be located together to allow the remaining non-key data to be encrypted as a single entity.
- Encrypted keys should be defined as alpha keys.
- Data at rest encryption must occur before any I/O statements. (To update an application to use this feature, consider using Synergex.SynergyDE.IOExtensions.IOHooks.)
- You must encrypt data before writing to a file (STORE, WRITE, or WRITES), and you must decrypt after reading from a file (READ or READS). If keys are encrypted, you must encrypt the key used for a read or find before executing the statement.
- Encrypted data is binary. To load or unload an encrypted file, you must use the COUNTED option for isload.