1/* 2 * Power ISA decode for misc instructions 3 * 4 * Copyright (c) 2024, IBM Corporation. 5 * 6 * This library is free software; you can redistribute it and/or 7 * modify it under the terms of the GNU Lesser General Public 8 * License as published by the Free Software Foundation; either 9 * version 2.1 of the License, or (at your option) any later version. 10 * 11 * This library is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 * Lesser General Public License for more details. 15 * 16 * You should have received a copy of the GNU Lesser General Public 17 * License along with this library; if not, see <http://www.gnu.org/licenses/>. 18 */ 19 20/* 21 * Memory Barrier Instructions 22 */ 23 24static bool trans_SYNC(DisasContext *ctx, arg_X_sync *a) 25{ 26 TCGBar bar = TCG_MO_ALL; 27 uint32_t l = a->l; 28 29 /* 30 * BookE uses the msync mnemonic. This means hwsync, except in the 31 * 440, where it an execution serialisation point that requires all 32 * previous storage accesses to have been performed to memory (which 33 * doesn't matter for TCG). 34 */ 35 if (!(ctx->insns_flags & PPC_MEM_SYNC)) { 36 if (ctx->insns_flags & PPC_BOOKE) { 37 /* msync replaces sync on 440, interpreted as nop */ 38 /* XXX: this also catches e200 */ 39 return true; 40 } 41 42 return false; 43 } 44 45 if ((l == 1) && (ctx->insns_flags2 & PPC2_MEM_LWSYNC)) { 46 bar = TCG_MO_LD_LD | TCG_MO_LD_ST | TCG_MO_ST_ST; 47 } 48 49 /* 50 * We may need to check for a pending TLB flush. 51 * 52 * We do this on ptesync (l == 2) on ppc64 and any sync on ppc32. 53 * 54 * Additionally, this can only happen in kernel mode however so 55 * check MSR_PR as well. 56 */ 57 if (((l == 2) || !(ctx->insns_flags & PPC_64B)) && !ctx->pr) { 58 gen_check_tlb_flush(ctx, true); 59 } 60 61 tcg_gen_mb(bar | TCG_BAR_SC); 62 63 return true; 64} 65 66static bool trans_EIEIO(DisasContext *ctx, arg_EIEIO *a) 67{ 68 TCGBar bar = TCG_MO_ALL; 69 70 /* 71 * BookE uses the mbar instruction instead of eieio, which is basically 72 * full hwsync memory barrier, but is not execution synchronising. For 73 * the purpose of TCG the distinction is not relevant. 74 */ 75 if (!(ctx->insns_flags & PPC_MEM_EIEIO)) { 76 if ((ctx->insns_flags & PPC_BOOKE) || 77 (ctx->insns_flags2 & PPC2_BOOKE206)) { 78 return true; 79 } 80 return false; 81 } 82 83 /* 84 * eieio has complex semanitcs. It provides memory ordering between 85 * operations in the set: 86 * - loads from CI memory. 87 * - stores to CI memory. 88 * - stores to WT memory. 89 * 90 * It separately also orders memory for operations in the set: 91 * - stores to cacheble memory. 92 * 93 * It also serializes instructions: 94 * - dcbt and dcbst. 95 * 96 * It separately serializes: 97 * - tlbie and tlbsync. 98 * 99 * And separately serializes: 100 * - slbieg, slbiag, and slbsync. 101 * 102 * The end result is that CI memory ordering requires TCG_MO_ALL 103 * and it is not possible to special-case more relaxed ordering for 104 * cacheable accesses. TCG_BAR_SC is required to provide this 105 * serialization. 106 */ 107 108 /* 109 * POWER9 has a eieio instruction variant using bit 6 as a hint to 110 * tell the CPU it is a store-forwarding barrier. 111 */ 112 if (ctx->opcode & 0x2000000) { 113 /* 114 * ISA says that "Reserved fields in instructions are ignored 115 * by the processor". So ignore the bit 6 on non-POWER9 CPU but 116 * as this is not an instruction software should be using, 117 * complain to the user. 118 */ 119 if (!(ctx->insns_flags2 & PPC2_ISA300)) { 120 qemu_log_mask(LOG_GUEST_ERROR, "invalid eieio using bit 6 at @" 121 TARGET_FMT_lx "\n", ctx->cia); 122 } else { 123 bar = TCG_MO_ST_LD; 124 } 125 } 126 127 tcg_gen_mb(bar | TCG_BAR_SC); 128 129 return true; 130} 131