Lines Matching +full:iommu +full:- +full:secure +full:- +full:id
21 #include "hw/misc/tz-mpc.h"
22 #include "hw/qdev-properties.h"
24 /* Our IOMMU has two IOMMU indexes, one for secure transactions and one for
25 * non-secure transactions.
76 qemu_set_irq(s->irq, s->int_stat && s->int_en); in tz_mpc_irq_update()
83 * must call the IOMMU notifiers for the changed blocks. in tz_mpc_iommu_notify()
87 .addr_mask = s->blocksize - 1, in tz_mpc_iommu_notify()
90 hwaddr addr = lutidx * s->blocksize * 32; in tz_mpc_iommu_notify()
93 for (i = 0; i < 32; i++, addr += s->blocksize) { in tz_mpc_iommu_notify()
110 memory_region_notify_iommu(&s->upstream, IOMMU_IDX_S, event); in tz_mpc_iommu_notify()
111 memory_region_notify_iommu(&s->upstream, IOMMU_IDX_NS, event); in tz_mpc_iommu_notify()
116 event.entry.target_as = &s->blocked_io_as; in tz_mpc_iommu_notify()
118 event.entry.target_as = &s->downstream_as; in tz_mpc_iommu_notify()
120 memory_region_notify_iommu(&s->upstream, IOMMU_IDX_S, event); in tz_mpc_iommu_notify()
122 event.entry.target_as = &s->downstream_as; in tz_mpc_iommu_notify()
124 event.entry.target_as = &s->blocked_io_as; in tz_mpc_iommu_notify()
126 memory_region_notify_iommu(&s->upstream, IOMMU_IDX_NS, event); in tz_mpc_iommu_notify()
132 /* Auto-increment BLK_IDX if necessary */ in tz_mpc_autoinc_idx()
133 if (access_size == 4 && (s->ctrl & R_CTRL_AUTOINC_MASK)) { in tz_mpc_autoinc_idx()
134 s->blk_idx++; in tz_mpc_autoinc_idx()
135 s->blk_idx %= s->blk_max; in tz_mpc_autoinc_idx()
147 if (!attrs.secure && offset < A_PIDR4) { in tz_mpc_reg_read()
148 /* NS accesses can only see the ID registers */ in tz_mpc_reg_read()
158 r = s->ctrl; in tz_mpc_reg_read()
161 r = s->blk_max - 1; in tz_mpc_reg_read()
165 * the block size. s->blocksize == (1 << BLK_CFG + 5), so in tz_mpc_reg_read()
166 * BLK_CFG == ctz32(s->blocksize) - 5 in tz_mpc_reg_read()
168 r = ctz32(s->blocksize) - 5; in tz_mpc_reg_read()
171 r = s->blk_idx; in tz_mpc_reg_read()
174 r = s->blk_lut[s->blk_idx]; in tz_mpc_reg_read()
178 r = s->int_stat; in tz_mpc_reg_read()
181 r = s->int_en; in tz_mpc_reg_read()
184 r = s->int_info1; in tz_mpc_reg_read()
187 r = s->int_info2; in tz_mpc_reg_read()
201 r = tz_mpc_idregs[(offset - A_PIDR4) / 4]; in tz_mpc_reg_read()
206 "TZ MPC register read: write-only offset 0x%x\n", in tz_mpc_reg_read()
218 /* None of our registers are read-sensitive (except BLK_LUT, in tz_mpc_reg_read()
240 if (!attrs.secure && offset < A_PIDR4) { in tz_mpc_reg_write()
241 /* NS accesses can only see the ID registers */ in tz_mpc_reg_write()
257 oldval = s->ctrl; in tz_mpc_reg_write()
260 oldval = s->blk_idx; in tz_mpc_reg_write()
263 oldval = s->blk_lut[s->blk_idx]; in tz_mpc_reg_write()
272 if ((s->ctrl & R_CTRL_LOCKDOWN_MASK) && in tz_mpc_reg_write()
274 /* Lockdown mode makes these three registers read-only, and in tz_mpc_reg_write()
287 s->ctrl = value & (R_CTRL_SEC_RESP_MASK | in tz_mpc_reg_write()
292 s->blk_idx = value % s->blk_max; in tz_mpc_reg_write()
295 tz_mpc_iommu_notify(s, s->blk_idx, s->blk_lut[s->blk_idx], value); in tz_mpc_reg_write()
296 s->blk_lut[s->blk_idx] = value; in tz_mpc_reg_write()
301 s->int_stat = 0; in tz_mpc_reg_write()
306 s->int_en = value & R_INT_EN_IRQ_MASK; in tz_mpc_reg_write()
311 s->int_stat = R_INT_STAT_IRQ_MASK; in tz_mpc_reg_write()
328 "TZ MPC register write: read-only offset 0x%x\n", offset); in tz_mpc_reg_write()
352 hwaddr blknum = addr / s->blocksize; in tz_mpc_cfg_ns()
359 assert(blkword < s->blk_max); in tz_mpc_cfg_ns()
360 return s->blk_lut[blkword] & blkbit; in tz_mpc_cfg_ns()
366 if (!s->int_stat) { in tz_mpc_handle_block()
372 s->int_info1 = addr; in tz_mpc_handle_block()
373 s->int_info2 = 0; in tz_mpc_handle_block()
374 s->int_info2 = FIELD_DP32(s->int_info2, INT_INFO2, HMASTER, in tz_mpc_handle_block()
376 s->int_info2 = FIELD_DP32(s->int_info2, INT_INFO2, HNONSEC, in tz_mpc_handle_block()
377 ~attrs.secure); in tz_mpc_handle_block()
378 s->int_info2 = FIELD_DP32(s->int_info2, INT_INFO2, CFG_NS, in tz_mpc_handle_block()
380 s->int_stat |= R_INT_STAT_IRQ_MASK; in tz_mpc_handle_block()
385 return (s->ctrl & R_CTRL_SEC_RESP_MASK) ? MEMTX_ERROR : MEMTX_OK; in tz_mpc_handle_block()
389 * blocking them; non-blocked accesses go directly to the downstream
398 trace_tz_mpc_mem_blocked_read(addr, size, attrs.secure); in tz_mpc_mem_blocked_read()
410 trace_tz_mpc_mem_blocked_write(addr, value, size, attrs.secure); in tz_mpc_mem_blocked_write()
425 static IOMMUTLBEntry tz_mpc_translate(IOMMUMemoryRegion *iommu, in tz_mpc_translate() argument
429 TZMPC *s = TZ_MPC(container_of(iommu, TZMPC, upstream)); in tz_mpc_translate()
433 .iova = addr & ~(s->blocksize - 1), in tz_mpc_translate()
434 .translated_addr = addr & ~(s->blocksize - 1), in tz_mpc_translate()
435 .addr_mask = s->blocksize - 1, in tz_mpc_translate()
439 /* Look at the per-block configuration for this address, and in tz_mpc_translate()
442 * If the LUT cfg_ns bit is 1, only non-secure transactions in tz_mpc_translate()
443 * may pass. If the bit is 0, only secure transactions may pass. in tz_mpc_translate()
451 ret.target_as = ok ? &s->downstream_as : &s->blocked_io_as; in tz_mpc_translate()
455 static int tz_mpc_attrs_to_index(IOMMUMemoryRegion *iommu, MemTxAttrs attrs) in tz_mpc_attrs_to_index() argument
457 /* We treat unspecified attributes like secure. Transactions with in tz_mpc_attrs_to_index()
460 * those to pass through the from-reset "everything is secure" config. in tz_mpc_attrs_to_index()
461 * All the real during-emulation transactions from the CPU will in tz_mpc_attrs_to_index()
464 return (attrs.unspecified || attrs.secure) ? IOMMU_IDX_S : IOMMU_IDX_NS; in tz_mpc_attrs_to_index()
467 static int tz_mpc_num_indexes(IOMMUMemoryRegion *iommu) in tz_mpc_num_indexes() argument
476 s->ctrl = 0x00000100; in tz_mpc_reset()
477 s->blk_idx = 0; in tz_mpc_reset()
478 s->int_stat = 0; in tz_mpc_reset()
479 s->int_en = 1; in tz_mpc_reset()
480 s->int_info1 = 0; in tz_mpc_reset()
481 s->int_info2 = 0; in tz_mpc_reset()
483 memset(s->blk_lut, 0, s->blk_max * sizeof(uint32_t)); in tz_mpc_reset()
491 qdev_init_gpio_out_named(dev, &s->irq, "irq", 1); in tz_mpc_init()
508 if (!s->downstream) { in tz_mpc_realize()
513 size = memory_region_size(s->downstream); in tz_mpc_realize()
515 memory_region_init_iommu(&s->upstream, sizeof(s->upstream), in tz_mpc_realize()
517 obj, "tz-mpc-upstream", size); in tz_mpc_realize()
525 s->blocksize = memory_region_iommu_get_min_page_size(&s->upstream); in tz_mpc_realize()
526 if (size % s->blocksize != 0) { in tz_mpc_realize()
530 size, s->blocksize); in tz_mpc_realize()
531 object_unref(OBJECT(&s->upstream)); in tz_mpc_realize()
535 /* BLK_MAX is the max value of BLK_IDX, which indexes an array of 32-bit in tz_mpc_realize()
538 s->blk_max = DIV_ROUND_UP(size / s->blocksize, 32); in tz_mpc_realize()
540 memory_region_init_io(&s->regmr, obj, &tz_mpc_reg_ops, in tz_mpc_realize()
541 s, "tz-mpc-regs", 0x1000); in tz_mpc_realize()
542 sysbus_init_mmio(sbd, &s->regmr); in tz_mpc_realize()
544 sysbus_init_mmio(sbd, MEMORY_REGION(&s->upstream)); in tz_mpc_realize()
548 * that our IOMMU translate function might direct accesses to. in tz_mpc_realize()
550 memory_region_init_io(&s->blocked_io, obj, &tz_mpc_mem_blocked_ops, in tz_mpc_realize()
551 s, "tz-mpc-blocked-io", size); in tz_mpc_realize()
553 address_space_init(&s->downstream_as, s->downstream, in tz_mpc_realize()
554 "tz-mpc-downstream"); in tz_mpc_realize()
555 address_space_init(&s->blocked_io_as, &s->blocked_io, in tz_mpc_realize()
556 "tz-mpc-blocked-io"); in tz_mpc_realize()
558 s->blk_lut = g_new0(uint32_t, s->blk_max); in tz_mpc_realize()
566 if (s->blk_idx >= s->blk_max) { in tz_mpc_post_load()
567 return -1; in tz_mpc_post_load()
573 .name = "tz-mpc",
600 dc->realize = tz_mpc_realize; in tz_mpc_class_init()
601 dc->vmsd = &tz_mpc_vmstate; in tz_mpc_class_init()
619 imrc->translate = tz_mpc_translate; in tz_mpc_iommu_memory_region_class_init()
620 imrc->attrs_to_index = tz_mpc_attrs_to_index; in tz_mpc_iommu_memory_region_class_init()
621 imrc->num_indexes = tz_mpc_num_indexes; in tz_mpc_iommu_memory_region_class_init()