7 #define S390_PPNO_SHA512_BLOCK_SIZE (240 / 8)
8 static uint64_t block
[S390_PPNO_SHA512_BLOCK_SIZE
];
9 #define HASH_COUNT 2 /* exactly two hashes for generate */
10 static uint64_t hash
[HASH_COUNT
];
12 static void print_sha512_block()
14 printf("Current block state:\n");
15 for(size_t elem
= 0; elem
< S390_PPNO_SHA512_BLOCK_SIZE
; elem
++)
17 print_uint64_t(block
[elem
]);
20 printf("end of block.\n");
23 static void print_sha512_hash()
25 printf("Current hash:\n");
26 for(size_t index
= 0; index
< HASH_COUNT
; index
++)
27 print_uint64_t(hash
[index
]);
29 printf("end of hash\n");
32 /* The problem with this test is different results on different architectures.
33 E.g. z13 will return (1 << 0)|(1 << 3) value while more recent versions of CPU
34 can (and will!) add their own operations here. Anyway z13 or any later arch will
35 have "SHA-512-DRNG" (3-rd bit of result) and "Query" (0-th bit) functions
36 so we test only this bits and ignore others.
38 static bool test_ppno_query()
41 register uint64_t functionCode
__asm__("0") = 0ULL;
42 register uint64_t paramBlock
__asm__("1") = (uint64_t) &output
;
45 ".insn rre, 0xb93c0000, %%r2, %%r4 \n" // GPR's are ignored here
46 : "+d"(functionCode
), "+d"(paramBlock
)
51 /* 0x9 = (1 << 0)|(1 << 3), see explanation above */
52 uint32_t expected
= 0x90000000U
;
53 uint32_t after
= output
[0];
55 bool result
= expected
== after
;
57 printf("ERROR: basic ppno functions are not supported : %d\n", after
);
62 static void test_ppno_sha512_seed()
64 /* Important! The program should zero paramBlock for seeding. */
65 memset(block
, 0, sizeof(block
));
68 for(size_t index
= 0; index
< 512; index
++)
69 seed
[index
] = random_element();
71 const uint64_t seedLength
= strlen((char*)seed
);
73 register uint64_t functionCode
__asm__("0") = 0x83ULL
;
74 register uint64_t paramBlock
__asm__("1") = (uint64_t) &block
;
75 register uint64_t gpr2
__asm__("2") = (uint64_t) &seed
;
76 register uint64_t gpr3
__asm__("3") = seedLength
;
78 ".insn rre, 0xb93c0000, %%r4, %%r2 \n"
80 : "d"(functionCode
), "d"(paramBlock
), "d"(gpr2
), "d"(gpr3
)
84 printf("seedLength = %ld\n", seedLength
);
88 static void test_ppno_sha512_gen()
90 register uint64_t functionCode
__asm__("0") = 0x3ULL
;
91 register uint64_t paramBlock
__asm__("1") = (uint64_t) &block
;
92 register uint64_t gpr2
__asm__("2") = (uint64_t) &hash
;
93 register uint64_t gpr3
__asm__("3") = HASH_COUNT
;
96 "0: .insn rre, 0xb93c0000, %%r2, %%r4 \n"
97 " brc 1, 0 \n" /* handle partial completion */
99 : "d"(functionCode
), "d"(paramBlock
), "d"(gpr2
), "d"(gpr3
)
104 print_sha512_block();
107 static void test_ppno_sha512()
109 printf(" === sha512_seed: ===\n");
110 test_ppno_sha512_seed();
112 printf(" === sha512_gen: ===\n");
113 test_ppno_sha512_gen();
115 memset(hash
, 0, sizeof(hash
));
121 if(!test_ppno_query())