s390/zcrypt: add display of ASYM master key verification pattern

This patch extends the sysfs attribute mkvps for CCA cards
to show the states and master key verification patterns for
the old, current and new ASYM master key registers.

With this patch now all relevant master key verification
patterns related to a CCA HSM are available with the mkvps
sysfs attribute. This is a requirement for some exploiters
like the kubernetes cex plugin or initrd code needing to
verify the master key verification patterns on HSMs before
use.

A sample output:
  cat /sys/devices/ap/card04/04.0005/mkvps
  AES NEW: empty 0x0000000000000000
  AES CUR: valid 0xe9a49a58cd039bed
  AES OLD: valid 0x7d10d17bc8a409c4
  APKA NEW: empty 0x0000000000000000
  APKA CUR: valid 0x5f2f27aaa2d59b4a
  APKA OLD: valid 0x82a5e2cd5030d5ec
  ASYM NEW: empty 0x00000000000000000000000000000000
  ASYM CUR: valid 0x650c25a89c27e716d0e692b6c83f10e5
  ASYM OLD: valid 0xf8ae2acf8bfc57f0a0957c732c16078b

Signed-off-by: Harald Freudenberger <freude@linux.ibm.com>
Reviewed-by: Jörg Schmidbauer <jschmidb@linux.ibm.com>
Signed-off-by: Heiko Carstens <hca@linux.ibm.com>
This commit is contained in:
Harald Freudenberger 2022-03-24 13:23:53 +01:00 committed by Heiko Carstens
parent 2ba24343bd
commit 28d3417a94
3 changed files with 47 additions and 4 deletions

View file

@ -1708,6 +1708,15 @@ static int fetch_cca_info(u16 cardnr, u16 domain, struct cca_info *ci)
rarray, &rlen, varray, &vlen);
if (rc == 0 && rlen >= 10*8 && vlen >= 204) {
memcpy(ci->serial, rarray, 8);
ci->new_asym_mk_state = (char) rarray[4*8];
ci->cur_asym_mk_state = (char) rarray[5*8];
ci->old_asym_mk_state = (char) rarray[6*8];
if (ci->old_asym_mk_state == '2')
memcpy(ci->old_asym_mkvp, varray + 64, 16);
if (ci->cur_asym_mk_state == '2')
memcpy(ci->cur_asym_mkvp, varray + 84, 16);
if (ci->new_asym_mk_state == '3')
memcpy(ci->new_asym_mkvp, varray + 104, 16);
ci->new_aes_mk_state = (char) rarray[7*8];
ci->cur_aes_mk_state = (char) rarray[8*8];
ci->old_aes_mk_state = (char) rarray[9*8];

View file

@ -251,12 +251,18 @@ struct cca_info {
char new_apka_mk_state; /* '1' empty, '2' partially full, '3' full */
char cur_apka_mk_state; /* '1' invalid, '2' valid */
char old_apka_mk_state; /* '1' invalid, '2' valid */
char new_asym_mk_state; /* '1' empty, '2' partially full, '3' full */
char cur_asym_mk_state; /* '1' invalid, '2' valid */
char old_asym_mk_state; /* '1' invalid, '2' valid */
u64 new_aes_mkvp; /* truncated sha256 of new aes master key */
u64 cur_aes_mkvp; /* truncated sha256 of current aes master key */
u64 old_aes_mkvp; /* truncated sha256 of old aes master key */
u64 new_apka_mkvp; /* truncated sha256 of new apka master key */
u64 cur_apka_mkvp; /* truncated sha256 of current apka mk */
u64 old_apka_mkvp; /* truncated sha256 of old apka mk */
u8 new_asym_mkvp[16]; /* verify pattern of new asym master key */
u8 cur_asym_mkvp[16]; /* verify pattern of current asym master key */
u8 old_asym_mkvp[16]; /* verify pattern of old asym master key */
char serial[9]; /* serial number (8 ascii numbers + 0x00) */
};

View file

@ -123,11 +123,12 @@ static ssize_t cca_mkvps_show(struct device *dev,
&ci, zq->online);
if (ci.new_aes_mk_state >= '1' && ci.new_aes_mk_state <= '3')
n = scnprintf(buf, PAGE_SIZE, "AES NEW: %s 0x%016llx\n",
new_state[ci.new_aes_mk_state - '1'],
ci.new_aes_mkvp);
n += scnprintf(buf + n, PAGE_SIZE,
"AES NEW: %s 0x%016llx\n",
new_state[ci.new_aes_mk_state - '1'],
ci.new_aes_mkvp);
else
n = scnprintf(buf, PAGE_SIZE, "AES NEW: - -\n");
n += scnprintf(buf + n, PAGE_SIZE, "AES NEW: - -\n");
if (ci.cur_aes_mk_state >= '1' && ci.cur_aes_mk_state <= '2')
n += scnprintf(buf + n, PAGE_SIZE - n,
@ -169,6 +170,33 @@ static ssize_t cca_mkvps_show(struct device *dev,
else
n += scnprintf(buf + n, PAGE_SIZE - n, "APKA OLD: - -\n");
if (ci.new_asym_mk_state >= '1' && ci.new_asym_mk_state <= '3')
n += scnprintf(buf + n, PAGE_SIZE,
"ASYM NEW: %s 0x%016llx%016llx\n",
new_state[ci.new_asym_mk_state - '1'],
*((u64 *)(ci.new_asym_mkvp)),
*((u64 *)(ci.new_asym_mkvp + sizeof(u64))));
else
n += scnprintf(buf + n, PAGE_SIZE, "ASYM NEW: - -\n");
if (ci.cur_asym_mk_state >= '1' && ci.cur_asym_mk_state <= '2')
n += scnprintf(buf + n, PAGE_SIZE - n,
"ASYM CUR: %s 0x%016llx%016llx\n",
cao_state[ci.cur_asym_mk_state - '1'],
*((u64 *)(ci.cur_asym_mkvp)),
*((u64 *)(ci.cur_asym_mkvp + sizeof(u64))));
else
n += scnprintf(buf + n, PAGE_SIZE - n, "ASYM CUR: - -\n");
if (ci.old_asym_mk_state >= '1' && ci.old_asym_mk_state <= '2')
n += scnprintf(buf + n, PAGE_SIZE - n,
"ASYM OLD: %s 0x%016llx%016llx\n",
cao_state[ci.old_asym_mk_state - '1'],
*((u64 *)(ci.old_asym_mkvp)),
*((u64 *)(ci.old_asym_mkvp + sizeof(u64))));
else
n += scnprintf(buf + n, PAGE_SIZE - n, "ASYM OLD: - -\n");
return n;
}