1c5475b3fSJoel Stanley /* 2c5475b3fSJoel Stanley * ASPEED Hash and Crypto Engine 3c5475b3fSJoel Stanley * 4c5475b3fSJoel Stanley * Copyright (C) 2021 IBM Corp. 5c5475b3fSJoel Stanley * 6c5475b3fSJoel Stanley * Joel Stanley <joel@jms.id.au> 7c5475b3fSJoel Stanley * 8c5475b3fSJoel Stanley * SPDX-License-Identifier: GPL-2.0-or-later 9c5475b3fSJoel Stanley */ 10c5475b3fSJoel Stanley 11c5475b3fSJoel Stanley #include "qemu/osdep.h" 12c5475b3fSJoel Stanley #include "qemu/log.h" 13c5475b3fSJoel Stanley #include "qemu/error-report.h" 14c5475b3fSJoel Stanley #include "hw/misc/aspeed_hace.h" 15c5475b3fSJoel Stanley #include "qapi/error.h" 16c5475b3fSJoel Stanley #include "migration/vmstate.h" 17c5475b3fSJoel Stanley #include "crypto/hash.h" 18c5475b3fSJoel Stanley #include "hw/qdev-properties.h" 19c5475b3fSJoel Stanley #include "hw/irq.h" 20c5475b3fSJoel Stanley 21c5475b3fSJoel Stanley #define R_CRYPT_CMD (0x10 / 4) 22c5475b3fSJoel Stanley 23c5475b3fSJoel Stanley #define R_STATUS (0x1c / 4) 24c5475b3fSJoel Stanley #define HASH_IRQ BIT(9) 25c5475b3fSJoel Stanley #define CRYPT_IRQ BIT(12) 26c5475b3fSJoel Stanley #define TAG_IRQ BIT(15) 27c5475b3fSJoel Stanley 28c5475b3fSJoel Stanley #define R_HASH_SRC (0x20 / 4) 29c5475b3fSJoel Stanley #define R_HASH_DEST (0x24 / 4) 30*1877069cSSteven Lee #define R_HASH_KEY_BUFF (0x28 / 4) 31c5475b3fSJoel Stanley #define R_HASH_SRC_LEN (0x2c / 4) 32c5475b3fSJoel Stanley 33c5475b3fSJoel Stanley #define R_HASH_CMD (0x30 / 4) 34c5475b3fSJoel Stanley /* Hash algorithm selection */ 35c5475b3fSJoel Stanley #define HASH_ALGO_MASK (BIT(4) | BIT(5) | BIT(6)) 36c5475b3fSJoel Stanley #define HASH_ALGO_MD5 0 37c5475b3fSJoel Stanley #define HASH_ALGO_SHA1 BIT(5) 38c5475b3fSJoel Stanley #define HASH_ALGO_SHA224 BIT(6) 39c5475b3fSJoel Stanley #define HASH_ALGO_SHA256 (BIT(4) | BIT(6)) 40c5475b3fSJoel Stanley #define HASH_ALGO_SHA512_SERIES (BIT(5) | BIT(6)) 41c5475b3fSJoel Stanley /* SHA512 algorithm selection */ 42c5475b3fSJoel Stanley #define SHA512_HASH_ALGO_MASK (BIT(10) | BIT(11) | BIT(12)) 43c5475b3fSJoel Stanley #define HASH_ALGO_SHA512_SHA512 0 44c5475b3fSJoel Stanley #define HASH_ALGO_SHA512_SHA384 BIT(10) 45c5475b3fSJoel Stanley #define HASH_ALGO_SHA512_SHA256 BIT(11) 46c5475b3fSJoel Stanley #define HASH_ALGO_SHA512_SHA224 (BIT(10) | BIT(11)) 47c5475b3fSJoel Stanley /* HMAC modes */ 48c5475b3fSJoel Stanley #define HASH_HMAC_MASK (BIT(7) | BIT(8)) 49c5475b3fSJoel Stanley #define HASH_DIGEST 0 50c5475b3fSJoel Stanley #define HASH_DIGEST_HMAC BIT(7) 51c5475b3fSJoel Stanley #define HASH_DIGEST_ACCUM BIT(8) 52c5475b3fSJoel Stanley #define HASH_HMAC_KEY (BIT(7) | BIT(8)) 53c5475b3fSJoel Stanley /* Cascaded operation modes */ 54c5475b3fSJoel Stanley #define HASH_ONLY 0 55c5475b3fSJoel Stanley #define HASH_ONLY2 BIT(0) 56c5475b3fSJoel Stanley #define HASH_CRYPT_THEN_HASH BIT(1) 57c5475b3fSJoel Stanley #define HASH_HASH_THEN_CRYPT (BIT(0) | BIT(1)) 58c5475b3fSJoel Stanley /* Other cmd bits */ 59c5475b3fSJoel Stanley #define HASH_IRQ_EN BIT(9) 60c5475b3fSJoel Stanley #define HASH_SG_EN BIT(18) 61c5475b3fSJoel Stanley /* Scatter-gather data list */ 62c5475b3fSJoel Stanley #define SG_LIST_LEN_SIZE 4 63c5475b3fSJoel Stanley #define SG_LIST_LEN_MASK 0x0FFFFFFF 64c5475b3fSJoel Stanley #define SG_LIST_LEN_LAST BIT(31) 65c5475b3fSJoel Stanley #define SG_LIST_ADDR_SIZE 4 66c5475b3fSJoel Stanley #define SG_LIST_ADDR_MASK 0x7FFFFFFF 67c5475b3fSJoel Stanley #define SG_LIST_ENTRY_SIZE (SG_LIST_LEN_SIZE + SG_LIST_ADDR_SIZE) 68c5475b3fSJoel Stanley #define ASPEED_HACE_MAX_SG 256 /* max number of entries */ 69c5475b3fSJoel Stanley 70c5475b3fSJoel Stanley static const struct { 71c5475b3fSJoel Stanley uint32_t mask; 72c5475b3fSJoel Stanley QCryptoHashAlgorithm algo; 73c5475b3fSJoel Stanley } hash_algo_map[] = { 74c5475b3fSJoel Stanley { HASH_ALGO_MD5, QCRYPTO_HASH_ALG_MD5 }, 75c5475b3fSJoel Stanley { HASH_ALGO_SHA1, QCRYPTO_HASH_ALG_SHA1 }, 76c5475b3fSJoel Stanley { HASH_ALGO_SHA224, QCRYPTO_HASH_ALG_SHA224 }, 77c5475b3fSJoel Stanley { HASH_ALGO_SHA256, QCRYPTO_HASH_ALG_SHA256 }, 78c5475b3fSJoel Stanley { HASH_ALGO_SHA512_SERIES | HASH_ALGO_SHA512_SHA512, QCRYPTO_HASH_ALG_SHA512 }, 79c5475b3fSJoel Stanley { HASH_ALGO_SHA512_SERIES | HASH_ALGO_SHA512_SHA384, QCRYPTO_HASH_ALG_SHA384 }, 80c5475b3fSJoel Stanley { HASH_ALGO_SHA512_SERIES | HASH_ALGO_SHA512_SHA256, QCRYPTO_HASH_ALG_SHA256 }, 81c5475b3fSJoel Stanley }; 82c5475b3fSJoel Stanley 83c5475b3fSJoel Stanley static int hash_algo_lookup(uint32_t reg) 84c5475b3fSJoel Stanley { 85c5475b3fSJoel Stanley int i; 86c5475b3fSJoel Stanley 87c5475b3fSJoel Stanley reg &= HASH_ALGO_MASK | SHA512_HASH_ALGO_MASK; 88c5475b3fSJoel Stanley 89c5475b3fSJoel Stanley for (i = 0; i < ARRAY_SIZE(hash_algo_map); i++) { 90c5475b3fSJoel Stanley if (reg == hash_algo_map[i].mask) { 91c5475b3fSJoel Stanley return hash_algo_map[i].algo; 92c5475b3fSJoel Stanley } 93c5475b3fSJoel Stanley } 94c5475b3fSJoel Stanley 95c5475b3fSJoel Stanley return -1; 96c5475b3fSJoel Stanley } 97c5475b3fSJoel Stanley 98c5475b3fSJoel Stanley static void do_hash_operation(AspeedHACEState *s, int algo, bool sg_mode) 99c5475b3fSJoel Stanley { 100c5475b3fSJoel Stanley struct iovec iov[ASPEED_HACE_MAX_SG]; 101c5475b3fSJoel Stanley g_autofree uint8_t *digest_buf; 102c5475b3fSJoel Stanley size_t digest_len = 0; 103c5475b3fSJoel Stanley int i; 104c5475b3fSJoel Stanley 105c5475b3fSJoel Stanley if (sg_mode) { 106c5475b3fSJoel Stanley uint32_t len = 0; 107c5475b3fSJoel Stanley 108c5475b3fSJoel Stanley for (i = 0; !(len & SG_LIST_LEN_LAST); i++) { 109c5475b3fSJoel Stanley uint32_t addr, src; 110c5475b3fSJoel Stanley hwaddr plen; 111c5475b3fSJoel Stanley 112c5475b3fSJoel Stanley if (i == ASPEED_HACE_MAX_SG) { 113c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, 114c5475b3fSJoel Stanley "aspeed_hace: guest failed to set end of sg list marker\n"); 115c5475b3fSJoel Stanley break; 116c5475b3fSJoel Stanley } 117c5475b3fSJoel Stanley 118c5475b3fSJoel Stanley src = s->regs[R_HASH_SRC] + (i * SG_LIST_ENTRY_SIZE); 119c5475b3fSJoel Stanley 120c5475b3fSJoel Stanley len = address_space_ldl_le(&s->dram_as, src, 121c5475b3fSJoel Stanley MEMTXATTRS_UNSPECIFIED, NULL); 122c5475b3fSJoel Stanley 123c5475b3fSJoel Stanley addr = address_space_ldl_le(&s->dram_as, src + SG_LIST_LEN_SIZE, 124c5475b3fSJoel Stanley MEMTXATTRS_UNSPECIFIED, NULL); 125c5475b3fSJoel Stanley addr &= SG_LIST_ADDR_MASK; 126c5475b3fSJoel Stanley 127c5475b3fSJoel Stanley iov[i].iov_len = len & SG_LIST_LEN_MASK; 128c5475b3fSJoel Stanley plen = iov[i].iov_len; 129c5475b3fSJoel Stanley iov[i].iov_base = address_space_map(&s->dram_as, addr, &plen, false, 130c5475b3fSJoel Stanley MEMTXATTRS_UNSPECIFIED); 131c5475b3fSJoel Stanley } 132c5475b3fSJoel Stanley } else { 133c5475b3fSJoel Stanley hwaddr len = s->regs[R_HASH_SRC_LEN]; 134c5475b3fSJoel Stanley 135c5475b3fSJoel Stanley iov[0].iov_len = len; 136c5475b3fSJoel Stanley iov[0].iov_base = address_space_map(&s->dram_as, s->regs[R_HASH_SRC], 137c5475b3fSJoel Stanley &len, false, 138c5475b3fSJoel Stanley MEMTXATTRS_UNSPECIFIED); 139c5475b3fSJoel Stanley i = 1; 140c5475b3fSJoel Stanley } 141c5475b3fSJoel Stanley 142c5475b3fSJoel Stanley if (qcrypto_hash_bytesv(algo, iov, i, &digest_buf, &digest_len, NULL) < 0) { 143c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, "%s: qcrypto failed\n", __func__); 144c5475b3fSJoel Stanley return; 145c5475b3fSJoel Stanley } 146c5475b3fSJoel Stanley 147c5475b3fSJoel Stanley if (address_space_write(&s->dram_as, s->regs[R_HASH_DEST], 148c5475b3fSJoel Stanley MEMTXATTRS_UNSPECIFIED, 149c5475b3fSJoel Stanley digest_buf, digest_len)) { 150c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, 151c5475b3fSJoel Stanley "aspeed_hace: address space write failed\n"); 152c5475b3fSJoel Stanley } 153c5475b3fSJoel Stanley 154c5475b3fSJoel Stanley for (; i > 0; i--) { 155c5475b3fSJoel Stanley address_space_unmap(&s->dram_as, iov[i - 1].iov_base, 156c5475b3fSJoel Stanley iov[i - 1].iov_len, false, 157c5475b3fSJoel Stanley iov[i - 1].iov_len); 158c5475b3fSJoel Stanley } 159c5475b3fSJoel Stanley 160c5475b3fSJoel Stanley /* 161c5475b3fSJoel Stanley * Set status bits to indicate completion. Testing shows hardware sets 162c5475b3fSJoel Stanley * these irrespective of HASH_IRQ_EN. 163c5475b3fSJoel Stanley */ 164c5475b3fSJoel Stanley s->regs[R_STATUS] |= HASH_IRQ; 165c5475b3fSJoel Stanley } 166c5475b3fSJoel Stanley 167c5475b3fSJoel Stanley static uint64_t aspeed_hace_read(void *opaque, hwaddr addr, unsigned int size) 168c5475b3fSJoel Stanley { 169c5475b3fSJoel Stanley AspeedHACEState *s = ASPEED_HACE(opaque); 170c5475b3fSJoel Stanley 171c5475b3fSJoel Stanley addr >>= 2; 172c5475b3fSJoel Stanley 173c5475b3fSJoel Stanley if (addr >= ASPEED_HACE_NR_REGS) { 174c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, 175c5475b3fSJoel Stanley "%s: Out-of-bounds read at offset 0x%" HWADDR_PRIx "\n", 176c5475b3fSJoel Stanley __func__, addr << 2); 177c5475b3fSJoel Stanley return 0; 178c5475b3fSJoel Stanley } 179c5475b3fSJoel Stanley 180c5475b3fSJoel Stanley return s->regs[addr]; 181c5475b3fSJoel Stanley } 182c5475b3fSJoel Stanley 183c5475b3fSJoel Stanley static void aspeed_hace_write(void *opaque, hwaddr addr, uint64_t data, 184c5475b3fSJoel Stanley unsigned int size) 185c5475b3fSJoel Stanley { 186c5475b3fSJoel Stanley AspeedHACEState *s = ASPEED_HACE(opaque); 187c5475b3fSJoel Stanley AspeedHACEClass *ahc = ASPEED_HACE_GET_CLASS(s); 188c5475b3fSJoel Stanley 189c5475b3fSJoel Stanley addr >>= 2; 190c5475b3fSJoel Stanley 191c5475b3fSJoel Stanley if (addr >= ASPEED_HACE_NR_REGS) { 192c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, 193c5475b3fSJoel Stanley "%s: Out-of-bounds write at offset 0x%" HWADDR_PRIx "\n", 194c5475b3fSJoel Stanley __func__, addr << 2); 195c5475b3fSJoel Stanley return; 196c5475b3fSJoel Stanley } 197c5475b3fSJoel Stanley 198c5475b3fSJoel Stanley switch (addr) { 199c5475b3fSJoel Stanley case R_STATUS: 200c5475b3fSJoel Stanley if (data & HASH_IRQ) { 201c5475b3fSJoel Stanley data &= ~HASH_IRQ; 202c5475b3fSJoel Stanley 203c5475b3fSJoel Stanley if (s->regs[addr] & HASH_IRQ) { 204c5475b3fSJoel Stanley qemu_irq_lower(s->irq); 205c5475b3fSJoel Stanley } 206c5475b3fSJoel Stanley } 207c5475b3fSJoel Stanley break; 208c5475b3fSJoel Stanley case R_HASH_SRC: 209c5475b3fSJoel Stanley data &= ahc->src_mask; 210c5475b3fSJoel Stanley break; 211c5475b3fSJoel Stanley case R_HASH_DEST: 212c5475b3fSJoel Stanley data &= ahc->dest_mask; 213c5475b3fSJoel Stanley break; 214*1877069cSSteven Lee case R_HASH_KEY_BUFF: 215*1877069cSSteven Lee data &= ahc->key_mask; 216*1877069cSSteven Lee break; 217c5475b3fSJoel Stanley case R_HASH_SRC_LEN: 218c5475b3fSJoel Stanley data &= 0x0FFFFFFF; 219c5475b3fSJoel Stanley break; 220c5475b3fSJoel Stanley case R_HASH_CMD: { 221c5475b3fSJoel Stanley int algo; 222c5475b3fSJoel Stanley data &= ahc->hash_mask; 223c5475b3fSJoel Stanley 224c5475b3fSJoel Stanley if ((data & HASH_HMAC_MASK)) { 225c5475b3fSJoel Stanley qemu_log_mask(LOG_UNIMP, 226c5475b3fSJoel Stanley "%s: HMAC engine command mode %"PRIx64" not implemented", 227c5475b3fSJoel Stanley __func__, (data & HASH_HMAC_MASK) >> 8); 228c5475b3fSJoel Stanley } 229c5475b3fSJoel Stanley if (data & BIT(1)) { 230c5475b3fSJoel Stanley qemu_log_mask(LOG_UNIMP, 231c5475b3fSJoel Stanley "%s: Cascaded mode not implemented", 232c5475b3fSJoel Stanley __func__); 233c5475b3fSJoel Stanley } 234c5475b3fSJoel Stanley algo = hash_algo_lookup(data); 235c5475b3fSJoel Stanley if (algo < 0) { 236c5475b3fSJoel Stanley qemu_log_mask(LOG_GUEST_ERROR, 237c5475b3fSJoel Stanley "%s: Invalid hash algorithm selection 0x%"PRIx64"\n", 238c5475b3fSJoel Stanley __func__, data & ahc->hash_mask); 239c5475b3fSJoel Stanley break; 240c5475b3fSJoel Stanley } 241c5475b3fSJoel Stanley do_hash_operation(s, algo, data & HASH_SG_EN); 242c5475b3fSJoel Stanley 243c5475b3fSJoel Stanley if (data & HASH_IRQ_EN) { 244c5475b3fSJoel Stanley qemu_irq_raise(s->irq); 245c5475b3fSJoel Stanley } 246c5475b3fSJoel Stanley break; 247c5475b3fSJoel Stanley } 248c5475b3fSJoel Stanley case R_CRYPT_CMD: 249c5475b3fSJoel Stanley qemu_log_mask(LOG_UNIMP, "%s: Crypt commands not implemented\n", 250c5475b3fSJoel Stanley __func__); 251c5475b3fSJoel Stanley break; 252c5475b3fSJoel Stanley default: 253c5475b3fSJoel Stanley break; 254c5475b3fSJoel Stanley } 255c5475b3fSJoel Stanley 256c5475b3fSJoel Stanley s->regs[addr] = data; 257c5475b3fSJoel Stanley } 258c5475b3fSJoel Stanley 259c5475b3fSJoel Stanley static const MemoryRegionOps aspeed_hace_ops = { 260c5475b3fSJoel Stanley .read = aspeed_hace_read, 261c5475b3fSJoel Stanley .write = aspeed_hace_write, 262c5475b3fSJoel Stanley .endianness = DEVICE_LITTLE_ENDIAN, 263c5475b3fSJoel Stanley .valid = { 264c5475b3fSJoel Stanley .min_access_size = 1, 265c5475b3fSJoel Stanley .max_access_size = 4, 266c5475b3fSJoel Stanley }, 267c5475b3fSJoel Stanley }; 268c5475b3fSJoel Stanley 269c5475b3fSJoel Stanley static void aspeed_hace_reset(DeviceState *dev) 270c5475b3fSJoel Stanley { 271c5475b3fSJoel Stanley struct AspeedHACEState *s = ASPEED_HACE(dev); 272c5475b3fSJoel Stanley 273c5475b3fSJoel Stanley memset(s->regs, 0, sizeof(s->regs)); 274c5475b3fSJoel Stanley } 275c5475b3fSJoel Stanley 276c5475b3fSJoel Stanley static void aspeed_hace_realize(DeviceState *dev, Error **errp) 277c5475b3fSJoel Stanley { 278c5475b3fSJoel Stanley AspeedHACEState *s = ASPEED_HACE(dev); 279c5475b3fSJoel Stanley SysBusDevice *sbd = SYS_BUS_DEVICE(dev); 280c5475b3fSJoel Stanley 281c5475b3fSJoel Stanley sysbus_init_irq(sbd, &s->irq); 282c5475b3fSJoel Stanley 283c5475b3fSJoel Stanley memory_region_init_io(&s->iomem, OBJECT(s), &aspeed_hace_ops, s, 284c5475b3fSJoel Stanley TYPE_ASPEED_HACE, 0x1000); 285c5475b3fSJoel Stanley 286c5475b3fSJoel Stanley if (!s->dram_mr) { 287c5475b3fSJoel Stanley error_setg(errp, TYPE_ASPEED_HACE ": 'dram' link not set"); 288c5475b3fSJoel Stanley return; 289c5475b3fSJoel Stanley } 290c5475b3fSJoel Stanley 291c5475b3fSJoel Stanley address_space_init(&s->dram_as, s->dram_mr, "dram"); 292c5475b3fSJoel Stanley 293c5475b3fSJoel Stanley sysbus_init_mmio(sbd, &s->iomem); 294c5475b3fSJoel Stanley } 295c5475b3fSJoel Stanley 296c5475b3fSJoel Stanley static Property aspeed_hace_properties[] = { 297c5475b3fSJoel Stanley DEFINE_PROP_LINK("dram", AspeedHACEState, dram_mr, 298c5475b3fSJoel Stanley TYPE_MEMORY_REGION, MemoryRegion *), 299c5475b3fSJoel Stanley DEFINE_PROP_END_OF_LIST(), 300c5475b3fSJoel Stanley }; 301c5475b3fSJoel Stanley 302c5475b3fSJoel Stanley 303c5475b3fSJoel Stanley static const VMStateDescription vmstate_aspeed_hace = { 304c5475b3fSJoel Stanley .name = TYPE_ASPEED_HACE, 305c5475b3fSJoel Stanley .version_id = 1, 306c5475b3fSJoel Stanley .minimum_version_id = 1, 307c5475b3fSJoel Stanley .fields = (VMStateField[]) { 308c5475b3fSJoel Stanley VMSTATE_UINT32_ARRAY(regs, AspeedHACEState, ASPEED_HACE_NR_REGS), 309c5475b3fSJoel Stanley VMSTATE_END_OF_LIST(), 310c5475b3fSJoel Stanley } 311c5475b3fSJoel Stanley }; 312c5475b3fSJoel Stanley 313c5475b3fSJoel Stanley static void aspeed_hace_class_init(ObjectClass *klass, void *data) 314c5475b3fSJoel Stanley { 315c5475b3fSJoel Stanley DeviceClass *dc = DEVICE_CLASS(klass); 316c5475b3fSJoel Stanley 317c5475b3fSJoel Stanley dc->realize = aspeed_hace_realize; 318c5475b3fSJoel Stanley dc->reset = aspeed_hace_reset; 319c5475b3fSJoel Stanley device_class_set_props(dc, aspeed_hace_properties); 320c5475b3fSJoel Stanley dc->vmsd = &vmstate_aspeed_hace; 321c5475b3fSJoel Stanley } 322c5475b3fSJoel Stanley 323c5475b3fSJoel Stanley static const TypeInfo aspeed_hace_info = { 324c5475b3fSJoel Stanley .name = TYPE_ASPEED_HACE, 325c5475b3fSJoel Stanley .parent = TYPE_SYS_BUS_DEVICE, 326c5475b3fSJoel Stanley .instance_size = sizeof(AspeedHACEState), 327c5475b3fSJoel Stanley .class_init = aspeed_hace_class_init, 328c5475b3fSJoel Stanley .class_size = sizeof(AspeedHACEClass) 329c5475b3fSJoel Stanley }; 330c5475b3fSJoel Stanley 331c5475b3fSJoel Stanley static void aspeed_ast2400_hace_class_init(ObjectClass *klass, void *data) 332c5475b3fSJoel Stanley { 333c5475b3fSJoel Stanley DeviceClass *dc = DEVICE_CLASS(klass); 334c5475b3fSJoel Stanley AspeedHACEClass *ahc = ASPEED_HACE_CLASS(klass); 335c5475b3fSJoel Stanley 336c5475b3fSJoel Stanley dc->desc = "AST2400 Hash and Crypto Engine"; 337c5475b3fSJoel Stanley 338c5475b3fSJoel Stanley ahc->src_mask = 0x0FFFFFFF; 339c5475b3fSJoel Stanley ahc->dest_mask = 0x0FFFFFF8; 340*1877069cSSteven Lee ahc->key_mask = 0x0FFFFFC0; 341c5475b3fSJoel Stanley ahc->hash_mask = 0x000003ff; /* No SG or SHA512 modes */ 342c5475b3fSJoel Stanley } 343c5475b3fSJoel Stanley 344c5475b3fSJoel Stanley static const TypeInfo aspeed_ast2400_hace_info = { 345c5475b3fSJoel Stanley .name = TYPE_ASPEED_AST2400_HACE, 346c5475b3fSJoel Stanley .parent = TYPE_ASPEED_HACE, 347c5475b3fSJoel Stanley .class_init = aspeed_ast2400_hace_class_init, 348c5475b3fSJoel Stanley }; 349c5475b3fSJoel Stanley 350c5475b3fSJoel Stanley static void aspeed_ast2500_hace_class_init(ObjectClass *klass, void *data) 351c5475b3fSJoel Stanley { 352c5475b3fSJoel Stanley DeviceClass *dc = DEVICE_CLASS(klass); 353c5475b3fSJoel Stanley AspeedHACEClass *ahc = ASPEED_HACE_CLASS(klass); 354c5475b3fSJoel Stanley 355c5475b3fSJoel Stanley dc->desc = "AST2500 Hash and Crypto Engine"; 356c5475b3fSJoel Stanley 357c5475b3fSJoel Stanley ahc->src_mask = 0x3fffffff; 358c5475b3fSJoel Stanley ahc->dest_mask = 0x3ffffff8; 359*1877069cSSteven Lee ahc->key_mask = 0x3FFFFFC0; 360c5475b3fSJoel Stanley ahc->hash_mask = 0x000003ff; /* No SG or SHA512 modes */ 361c5475b3fSJoel Stanley } 362c5475b3fSJoel Stanley 363c5475b3fSJoel Stanley static const TypeInfo aspeed_ast2500_hace_info = { 364c5475b3fSJoel Stanley .name = TYPE_ASPEED_AST2500_HACE, 365c5475b3fSJoel Stanley .parent = TYPE_ASPEED_HACE, 366c5475b3fSJoel Stanley .class_init = aspeed_ast2500_hace_class_init, 367c5475b3fSJoel Stanley }; 368c5475b3fSJoel Stanley 369c5475b3fSJoel Stanley static void aspeed_ast2600_hace_class_init(ObjectClass *klass, void *data) 370c5475b3fSJoel Stanley { 371c5475b3fSJoel Stanley DeviceClass *dc = DEVICE_CLASS(klass); 372c5475b3fSJoel Stanley AspeedHACEClass *ahc = ASPEED_HACE_CLASS(klass); 373c5475b3fSJoel Stanley 374c5475b3fSJoel Stanley dc->desc = "AST2600 Hash and Crypto Engine"; 375c5475b3fSJoel Stanley 376c5475b3fSJoel Stanley ahc->src_mask = 0x7FFFFFFF; 377c5475b3fSJoel Stanley ahc->dest_mask = 0x7FFFFFF8; 378*1877069cSSteven Lee ahc->key_mask = 0x7FFFFFF8; 379c5475b3fSJoel Stanley ahc->hash_mask = 0x00147FFF; 380c5475b3fSJoel Stanley } 381c5475b3fSJoel Stanley 382c5475b3fSJoel Stanley static const TypeInfo aspeed_ast2600_hace_info = { 383c5475b3fSJoel Stanley .name = TYPE_ASPEED_AST2600_HACE, 384c5475b3fSJoel Stanley .parent = TYPE_ASPEED_HACE, 385c5475b3fSJoel Stanley .class_init = aspeed_ast2600_hace_class_init, 386c5475b3fSJoel Stanley }; 387c5475b3fSJoel Stanley 388c5475b3fSJoel Stanley static void aspeed_hace_register_types(void) 389c5475b3fSJoel Stanley { 390c5475b3fSJoel Stanley type_register_static(&aspeed_ast2400_hace_info); 391c5475b3fSJoel Stanley type_register_static(&aspeed_ast2500_hace_info); 392c5475b3fSJoel Stanley type_register_static(&aspeed_ast2600_hace_info); 393c5475b3fSJoel Stanley type_register_static(&aspeed_hace_info); 394c5475b3fSJoel Stanley } 395c5475b3fSJoel Stanley 396c5475b3fSJoel Stanley type_init(aspeed_hace_register_types); 397