static int kvm_get_msrs(X86CPU *cpu) { CPUX86State *env = &cpu->env; struct kvm_msr_entry *msrs = cpu->kvm_msr_buf->entries; int ret, i; uint64_t mtrr_top_bits; kvm_msr_buf_reset(cpu); kvm_msr_entry_add(cpu, MSR_IA32_SYSENTER_CS, 0); kvm_msr_entry_add(cpu, MSR_IA32_SYSENTER_ESP, 0); kvm_msr_entry_add(cpu, MSR_IA32_SYSENTER_EIP, 0); kvm_msr_entry_add(cpu, MSR_PAT, 0); if (has_msr_star) { kvm_msr_entry_add(cpu, MSR_STAR, 0); } if (has_msr_hsave_pa) { kvm_msr_entry_add(cpu, MSR_VM_HSAVE_PA, 0); } if (has_msr_tsc_aux) { kvm_msr_entry_add(cpu, MSR_TSC_AUX, 0); } if (has_msr_tsc_adjust) { kvm_msr_entry_add(cpu, MSR_TSC_ADJUST, 0); } if (has_msr_tsc_deadline) { kvm_msr_entry_add(cpu, MSR_IA32_TSCDEADLINE, 0); } if (has_msr_misc_enable) { kvm_msr_entry_add(cpu, MSR_IA32_MISC_ENABLE, 0); } if (has_msr_smbase) { kvm_msr_entry_add(cpu, MSR_IA32_SMBASE, 0); } if (has_msr_feature_control) { kvm_msr_entry_add(cpu, MSR_IA32_FEATURE_CONTROL, 0); } if (has_msr_bndcfgs) { kvm_msr_entry_add(cpu, MSR_IA32_BNDCFGS, 0); } if (has_msr_xss) { kvm_msr_entry_add(cpu, MSR_IA32_XSS, 0); } if (!env->tsc_valid) { kvm_msr_entry_add(cpu, MSR_IA32_TSC, 0); env->tsc_valid = !runstate_is_running(); } #ifdef TARGET_X86_64 if (lm_capable_kernel) { kvm_msr_entry_add(cpu, MSR_CSTAR, 0); kvm_msr_entry_add(cpu, MSR_KERNELGSBASE, 0); kvm_msr_entry_add(cpu, MSR_FMASK, 0); kvm_msr_entry_add(cpu, MSR_LSTAR, 0); } #endif kvm_msr_entry_add(cpu, MSR_KVM_SYSTEM_TIME, 0); kvm_msr_entry_add(cpu, MSR_KVM_WALL_CLOCK, 0); if (env->features[FEAT_KVM] & (1 << KVM_FEATURE_ASYNC_PF)) { kvm_msr_entry_add(cpu, MSR_KVM_ASYNC_PF_EN, 0); } if (env->features[FEAT_KVM] & (1 << KVM_FEATURE_PV_EOI)) { kvm_msr_entry_add(cpu, MSR_KVM_PV_EOI_EN, 0); } if (env->features[FEAT_KVM] & (1 << KVM_FEATURE_STEAL_TIME)) { kvm_msr_entry_add(cpu, MSR_KVM_STEAL_TIME, 0); } if (has_msr_architectural_pmu) { kvm_msr_entry_add(cpu, MSR_CORE_PERF_FIXED_CTR_CTRL, 0); kvm_msr_entry_add(cpu, MSR_CORE_PERF_GLOBAL_CTRL, 0); kvm_msr_entry_add(cpu, MSR_CORE_PERF_GLOBAL_STATUS, 0); kvm_msr_entry_add(cpu, MSR_CORE_PERF_GLOBAL_OVF_CTRL, 0); for (i = 0; i < MAX_FIXED_COUNTERS; i++) { kvm_msr_entry_add(cpu, MSR_CORE_PERF_FIXED_CTR0 + i, 0); } for (i = 0; i < num_architectural_pmu_counters; i++) { kvm_msr_entry_add(cpu, MSR_P6_PERFCTR0 + i, 0); kvm_msr_entry_add(cpu, MSR_P6_EVNTSEL0 + i, 0); } } if (env->mcg_cap) { kvm_msr_entry_add(cpu, MSR_MCG_STATUS, 0); kvm_msr_entry_add(cpu, MSR_MCG_CTL, 0); if (has_msr_mcg_ext_ctl) { kvm_msr_entry_add(cpu, MSR_MCG_EXT_CTL, 0); } for (i = 0; i < (env->mcg_cap & 0xff) * 4; i++) { kvm_msr_entry_add(cpu, MSR_MC0_CTL + i, 0); } } if (has_msr_hv_hypercall) { kvm_msr_entry_add(cpu, HV_X64_MSR_HYPERCALL, 0); kvm_msr_entry_add(cpu, HV_X64_MSR_GUEST_OS_ID, 0); } if (cpu->hyperv_vapic) { kvm_msr_entry_add(cpu, HV_X64_MSR_APIC_ASSIST_PAGE, 0); } if (cpu->hyperv_time) { kvm_msr_entry_add(cpu, HV_X64_MSR_REFERENCE_TSC, 0); } if (has_msr_hv_crash) { int j; for (j = 0; j < HV_CRASH_PARAMS; j++) { kvm_msr_entry_add(cpu, HV_X64_MSR_CRASH_P0 + j, 0); } } if (has_msr_hv_runtime) { kvm_msr_entry_add(cpu, HV_X64_MSR_VP_RUNTIME, 0); } if (cpu->hyperv_synic) { uint32_t msr; kvm_msr_entry_add(cpu, HV_X64_MSR_SCONTROL, 0); kvm_msr_entry_add(cpu, HV_X64_MSR_SIEFP, 0); kvm_msr_entry_add(cpu, HV_X64_MSR_SIMP, 0); for (msr = HV_X64_MSR_SINT0; msr <= HV_X64_MSR_SINT15; msr++) { kvm_msr_entry_add(cpu, msr, 0); } } if (has_msr_hv_stimer) { uint32_t msr; for (msr = HV_X64_MSR_STIMER0_CONFIG; msr <= HV_X64_MSR_STIMER3_COUNT; msr++) { kvm_msr_entry_add(cpu, msr, 0); } } if (env->features[FEAT_1_EDX] & CPUID_MTRR) { kvm_msr_entry_add(cpu, MSR_MTRRdefType, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix64K_00000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix16K_80000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix16K_A0000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_C0000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_C8000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_D0000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_D8000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_E0000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_E8000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_F0000, 0); kvm_msr_entry_add(cpu, MSR_MTRRfix4K_F8000, 0); for (i = 0; i < MSR_MTRRcap_VCNT; i++) { kvm_msr_entry_add(cpu, MSR_MTRRphysBase(i), 0); kvm_msr_entry_add(cpu, MSR_MTRRphysMask(i), 0); } } ret = kvm_vcpu_ioctl(CPU(cpu), KVM_GET_MSRS, cpu->kvm_msr_buf); if (ret < 0) { return ret; } if (ret < cpu->kvm_msr_buf->nmsrs) { struct kvm_msr_entry *e = &cpu->kvm_msr_buf->entries[ret]; error_report("error: failed to get MSR 0x%" PRIx32, (uint32_t)e->index); } assert(ret == cpu->kvm_msr_buf->nmsrs); /* * MTRR masks: Each mask consists of 5 parts * a 10..0: must be zero * b 11 : valid bit * c n-1.12: actual mask bits * d 51..n: reserved must be zero * e 63.52: reserved must be zero * * 'n' is the number of physical bits supported by the CPU and is * apparently always <= 52. We know our 'n' but don't know what * the destinations 'n' is; it might be smaller, in which case * it masks (c) on loading. It might be larger, in which case * we fill 'd' so that d..c is consistent irrespetive of the 'n' * we're migrating to. */ if (cpu->fill_mtrr_mask) { QEMU_BUILD_BUG_ON(TARGET_PHYS_ADDR_SPACE_BITS > 52); assert(cpu->phys_bits <= TARGET_PHYS_ADDR_SPACE_BITS); mtrr_top_bits = MAKE_64BIT_MASK(cpu->phys_bits, 52 - cpu->phys_bits); } else { mtrr_top_bits = 0; } for (i = 0; i < ret; i++) { uint32_t index = msrs[i].index; switch (index) { case MSR_IA32_SYSENTER_CS: env->sysenter_cs = msrs[i].data; break; case MSR_IA32_SYSENTER_ESP: env->sysenter_esp = msrs[i].data; break; case MSR_IA32_SYSENTER_EIP: env->sysenter_eip = msrs[i].data; break; case MSR_PAT: env->pat = msrs[i].data; break; case MSR_STAR: env->star = msrs[i].data; break; #ifdef TARGET_X86_64 case MSR_CSTAR: env->cstar = msrs[i].data; break; case MSR_KERNELGSBASE: env->kernelgsbase = msrs[i].data; break; case MSR_FMASK: env->fmask = msrs[i].data; break; case MSR_LSTAR: env->lstar = msrs[i].data; break; #endif case MSR_IA32_TSC: env->tsc = msrs[i].data; break; case MSR_TSC_AUX: env->tsc_aux = msrs[i].data; break; case MSR_TSC_ADJUST: env->tsc_adjust = msrs[i].data; break; case MSR_IA32_TSCDEADLINE: env->tsc_deadline = msrs[i].data; break; case MSR_VM_HSAVE_PA: env->vm_hsave = msrs[i].data; break; case MSR_KVM_SYSTEM_TIME: env->system_time_msr = msrs[i].data; break; case MSR_KVM_WALL_CLOCK: env->wall_clock_msr = msrs[i].data; break; case MSR_MCG_STATUS: env->mcg_status = msrs[i].data; break; case MSR_MCG_CTL: env->mcg_ctl = msrs[i].data; break; case MSR_MCG_EXT_CTL: env->mcg_ext_ctl = msrs[i].data; break; case MSR_IA32_MISC_ENABLE: env->msr_ia32_misc_enable = msrs[i].data; break; case MSR_IA32_SMBASE: env->smbase = msrs[i].data; break; case MSR_IA32_FEATURE_CONTROL: env->msr_ia32_feature_control = msrs[i].data; break; case MSR_IA32_BNDCFGS: env->msr_bndcfgs = msrs[i].data; break; case MSR_IA32_XSS: env->xss = msrs[i].data; break; default: if (msrs[i].index >= MSR_MC0_CTL && msrs[i].index < MSR_MC0_CTL + (env->mcg_cap & 0xff) * 4) { env->mce_banks[msrs[i].index - MSR_MC0_CTL] = msrs[i].data; } break; case MSR_KVM_ASYNC_PF_EN: env->async_pf_en_msr = msrs[i].data; break; case MSR_KVM_PV_EOI_EN: env->pv_eoi_en_msr = msrs[i].data; break; case MSR_KVM_STEAL_TIME: env->steal_time_msr = msrs[i].data; break; case MSR_CORE_PERF_FIXED_CTR_CTRL: env->msr_fixed_ctr_ctrl = msrs[i].data; break; case MSR_CORE_PERF_GLOBAL_CTRL: env->msr_global_ctrl = msrs[i].data; break; case MSR_CORE_PERF_GLOBAL_STATUS: env->msr_global_status = msrs[i].data; break; case MSR_CORE_PERF_GLOBAL_OVF_CTRL: env->msr_global_ovf_ctrl = msrs[i].data; break; case MSR_CORE_PERF_FIXED_CTR0 ... MSR_CORE_PERF_FIXED_CTR0 + MAX_FIXED_COUNTERS - 1: env->msr_fixed_counters[index - MSR_CORE_PERF_FIXED_CTR0] = msrs[i].data; break; case MSR_P6_PERFCTR0 ... MSR_P6_PERFCTR0 + MAX_GP_COUNTERS - 1: env->msr_gp_counters[index - MSR_P6_PERFCTR0] = msrs[i].data; break; case MSR_P6_EVNTSEL0 ... MSR_P6_EVNTSEL0 + MAX_GP_COUNTERS - 1: env->msr_gp_evtsel[index - MSR_P6_EVNTSEL0] = msrs[i].data; break; case HV_X64_MSR_HYPERCALL: env->msr_hv_hypercall = msrs[i].data; break; case HV_X64_MSR_GUEST_OS_ID: env->msr_hv_guest_os_id = msrs[i].data; break; case HV_X64_MSR_APIC_ASSIST_PAGE: env->msr_hv_vapic = msrs[i].data; break; case HV_X64_MSR_REFERENCE_TSC: env->msr_hv_tsc = msrs[i].data; break; case HV_X64_MSR_CRASH_P0 ... HV_X64_MSR_CRASH_P4: env->msr_hv_crash_params[index - HV_X64_MSR_CRASH_P0] = msrs[i].data; break; case HV_X64_MSR_VP_RUNTIME: env->msr_hv_runtime = msrs[i].data; break; case HV_X64_MSR_SCONTROL: env->msr_hv_synic_control = msrs[i].data; break; case HV_X64_MSR_SIEFP: env->msr_hv_synic_evt_page = msrs[i].data; break; case HV_X64_MSR_SIMP: env->msr_hv_synic_msg_page = msrs[i].data; break; case HV_X64_MSR_SINT0 ... HV_X64_MSR_SINT15: env->msr_hv_synic_sint[index - HV_X64_MSR_SINT0] = msrs[i].data; break; case HV_X64_MSR_STIMER0_CONFIG: case HV_X64_MSR_STIMER1_CONFIG: case HV_X64_MSR_STIMER2_CONFIG: case HV_X64_MSR_STIMER3_CONFIG: env->msr_hv_stimer_config[(index - HV_X64_MSR_STIMER0_CONFIG)/2] = msrs[i].data; break; case HV_X64_MSR_STIMER0_COUNT: case HV_X64_MSR_STIMER1_COUNT: case HV_X64_MSR_STIMER2_COUNT: case HV_X64_MSR_STIMER3_COUNT: env->msr_hv_stimer_count[(index - HV_X64_MSR_STIMER0_COUNT)/2] = msrs[i].data; break; case MSR_MTRRdefType: env->mtrr_deftype = msrs[i].data; break; case MSR_MTRRfix64K_00000: env->mtrr_fixed[0] = msrs[i].data; break; case MSR_MTRRfix16K_80000: env->mtrr_fixed[1] = msrs[i].data; break; case MSR_MTRRfix16K_A0000: env->mtrr_fixed[2] = msrs[i].data; break; case MSR_MTRRfix4K_C0000: env->mtrr_fixed[3] = msrs[i].data; break; case MSR_MTRRfix4K_C8000: env->mtrr_fixed[4] = msrs[i].data; break; case MSR_MTRRfix4K_D0000: env->mtrr_fixed[5] = msrs[i].data; break; case MSR_MTRRfix4K_D8000: env->mtrr_fixed[6] = msrs[i].data; break; case MSR_MTRRfix4K_E0000: env->mtrr_fixed[7] = msrs[i].data; break; case MSR_MTRRfix4K_E8000: env->mtrr_fixed[8] = msrs[i].data; break; case MSR_MTRRfix4K_F0000: env->mtrr_fixed[9] = msrs[i].data; break; case MSR_MTRRfix4K_F8000: env->mtrr_fixed[10] = msrs[i].data; break; case MSR_MTRRphysBase(0) ... MSR_MTRRphysMask(MSR_MTRRcap_VCNT - 1): if (index & 1) { env->mtrr_var[MSR_MTRRphysIndex(index)].mask = msrs[i].data | mtrr_top_bits; } else { env->mtrr_var[MSR_MTRRphysIndex(index)].base = msrs[i].data; } break; } } return 0; }


static void blk_mig_unlock(void) { qemu_mutex_unlock(&block_mig_state.lock); }


static void do_tb_flush(CPUState *cpu, void *data) { unsigned tb_flush_req = (unsigned) (uintptr_t) data; tb_lock(); /* If it's already been done on request of another CPU, * just retry. */ if (tcg_ctx.tb_ctx.tb_flush_count != tb_flush_req) { goto done; } #if defined(DEBUG_FLUSH) printf("qemu: flush code_size=%ld nb_tbs=%d avg_tb_size=%ld\n", (unsigned long)(tcg_ctx.code_gen_ptr - tcg_ctx.code_gen_buffer), tcg_ctx.tb_ctx.nb_tbs, tcg_ctx.tb_ctx.nb_tbs > 0 ? ((unsigned long)(tcg_ctx.code_gen_ptr - tcg_ctx.code_gen_buffer)) / tcg_ctx.tb_ctx.nb_tbs : 0); #endif if ((unsigned long)(tcg_ctx.code_gen_ptr - tcg_ctx.code_gen_buffer) > tcg_ctx.code_gen_buffer_size) { cpu_abort(cpu, "Internal error: code buffer overflow\n"); } CPU_FOREACH(cpu) { int i; for (i = 0; i < TB_JMP_CACHE_SIZE; ++i) { atomic_set(&cpu->tb_jmp_cache[i], NULL); } } tcg_ctx.tb_ctx.nb_tbs = 0; qht_reset_size(&tcg_ctx.tb_ctx.htable, CODE_GEN_HTABLE_SIZE); page_flush_tb(); tcg_ctx.code_gen_ptr = tcg_ctx.code_gen_buffer; /* XXX: flush processor icache at this point if cache flush is expensive */ atomic_mb_set(&tcg_ctx.tb_ctx.tb_flush_count, tcg_ctx.tb_ctx.tb_flush_count + 1); done: tb_unlock(); }


static int decode_gusa(DisasContext *ctx, CPUSH4State *env, int *pmax_insns) { uint16_t insns[5]; int ld_adr, ld_dst, ld_mop; int op_dst, op_src, op_opc; int mv_src, mt_dst, st_src, st_mop; TCGv op_arg; uint32_t pc = ctx->pc; uint32_t pc_end = ctx->tb->cs_base; int backup = sextract32(ctx->tbflags, GUSA_SHIFT, 8); int max_insns = (pc_end - pc) / 2; int i; if (pc != pc_end + backup || max_insns < 2) { /* This is a malformed gUSA region. Don't do anything special, since the interpreter is likely to get confused. */ ctx->envflags &= ~GUSA_MASK; return 0; } if (ctx->tbflags & GUSA_EXCLUSIVE) { /* Regardless of single-stepping or the end of the page, we must complete execution of the gUSA region while holding the exclusive lock. */ *pmax_insns = max_insns; return 0; } /* The state machine below will consume only a few insns. If there are more than that in a region, fail now. */ if (max_insns > ARRAY_SIZE(insns)) { goto fail; } /* Read all of the insns for the region. */ for (i = 0; i < max_insns; ++i) { insns[i] = cpu_lduw_code(env, pc + i * 2); } ld_adr = ld_dst = ld_mop = -1; mv_src = -1; op_dst = op_src = op_opc = -1; mt_dst = -1; st_src = st_mop = -1; TCGV_UNUSED(op_arg); i = 0; #define NEXT_INSN \ do { if (i >= max_insns) goto fail; ctx->opcode = insns[i++]; } while (0) /* * Expect a load to begin the region. */ NEXT_INSN; switch (ctx->opcode & 0xf00f) { case 0x6000: /* mov.b @Rm,Rn */ ld_mop = MO_SB; break; case 0x6001: /* mov.w @Rm,Rn */ ld_mop = MO_TESW; break; case 0x6002: /* mov.l @Rm,Rn */ ld_mop = MO_TESL; break; default: goto fail; } ld_adr = B7_4; ld_dst = B11_8; if (ld_adr == ld_dst) { goto fail; } /* Unless we see a mov, any two-operand operation must use ld_dst. */ op_dst = ld_dst; /* * Expect an optional register move. */ NEXT_INSN; switch (ctx->opcode & 0xf00f) { case 0x6003: /* mov Rm,Rn */ /* Here we want to recognize ld_dst being saved for later consumtion, or for another input register being copied so that ld_dst need not be clobbered during the operation. */ op_dst = B11_8; mv_src = B7_4; if (op_dst == ld_dst) { /* Overwriting the load output. */ goto fail; } if (mv_src != ld_dst) { /* Copying a new input; constrain op_src to match the load. */ op_src = ld_dst; } break; default: /* Put back and re-examine as operation. */ --i; } /* * Expect the operation. */ NEXT_INSN; switch (ctx->opcode & 0xf00f) { case 0x300c: /* add Rm,Rn */ op_opc = INDEX_op_add_i32; goto do_reg_op; case 0x2009: /* and Rm,Rn */ op_opc = INDEX_op_and_i32; goto do_reg_op; case 0x200a: /* xor Rm,Rn */ op_opc = INDEX_op_xor_i32; goto do_reg_op; case 0x200b: /* or Rm,Rn */ op_opc = INDEX_op_or_i32; do_reg_op: /* The operation register should be as expected, and the other input cannot depend on the load. */ if (op_dst != B11_8) { goto fail; } if (op_src < 0) { /* Unconstrainted input. */ op_src = B7_4; } else if (op_src == B7_4) { /* Constrained input matched load. All operations are commutative; "swap" them by "moving" the load output to the (implicit) first argument and the move source to the (explicit) second argument. */ op_src = mv_src; } else { goto fail; } op_arg = REG(op_src); break; case 0x6007: /* not Rm,Rn */ if (ld_dst != B7_4 || mv_src >= 0) { goto fail; } op_dst = B11_8; op_opc = INDEX_op_xor_i32; op_arg = tcg_const_i32(-1); break; case 0x7000 ... 0x700f: /* add #imm,Rn */ if (op_dst != B11_8 || mv_src >= 0) { goto fail; } op_opc = INDEX_op_add_i32; op_arg = tcg_const_i32(B7_0s); break; case 0x3000: /* cmp/eq Rm,Rn */ /* Looking for the middle of a compare-and-swap sequence, beginning with the compare. Operands can be either order, but with only one overlapping the load. */ if ((ld_dst == B11_8) + (ld_dst == B7_4) != 1 || mv_src >= 0) { goto fail; } op_opc = INDEX_op_setcond_i32; /* placeholder */ op_src = (ld_dst == B11_8 ? B7_4 : B11_8); op_arg = REG(op_src); NEXT_INSN; switch (ctx->opcode & 0xff00) { case 0x8b00: /* bf label */ case 0x8f00: /* bf/s label */ if (pc + (i + 1 + B7_0s) * 2 != pc_end) { goto fail; } if ((ctx->opcode & 0xff00) == 0x8b00) { /* bf label */ break; } /* We're looking to unconditionally modify Rn with the result of the comparison, within the delay slot of the branch. This is used by older gcc. */ NEXT_INSN; if ((ctx->opcode & 0xf0ff) == 0x0029) { /* movt Rn */ mt_dst = B11_8; } else { goto fail; } break; default: goto fail; } break; case 0x2008: /* tst Rm,Rn */ /* Looking for a compare-and-swap against zero. */ if (ld_dst != B11_8 || ld_dst != B7_4 || mv_src >= 0) { goto fail; } op_opc = INDEX_op_setcond_i32; op_arg = tcg_const_i32(0); NEXT_INSN; if ((ctx->opcode & 0xff00) != 0x8900 /* bt label */ || pc + (i + 1 + B7_0s) * 2 != pc_end) { goto fail; } break; default: /* Put back and re-examine as store. */ --i; } /* * Expect the store. */ /* The store must be the last insn. */ if (i != max_insns - 1) { goto fail; } NEXT_INSN; switch (ctx->opcode & 0xf00f) { case 0x2000: /* mov.b Rm,@Rn */ st_mop = MO_UB; break; case 0x2001: /* mov.w Rm,@Rn */ st_mop = MO_UW; break; case 0x2002: /* mov.l Rm,@Rn */ st_mop = MO_UL; break; default: goto fail; } /* The store must match the load. */ if (ld_adr != B11_8 || st_mop != (ld_mop & MO_SIZE)) { goto fail; } st_src = B7_4; #undef NEXT_INSN /* * Emit the operation. */ tcg_gen_insn_start(pc, ctx->envflags); switch (op_opc) { case -1: /* No operation found. Look for exchange pattern. */ if (st_src == ld_dst || mv_src >= 0) { goto fail; } tcg_gen_atomic_xchg_i32(REG(ld_dst), REG(ld_adr), REG(st_src), ctx->memidx, ld_mop); break; case INDEX_op_add_i32: if (op_dst != st_src) { goto fail; } if (op_dst == ld_dst && st_mop == MO_UL) { tcg_gen_atomic_add_fetch_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); } else { tcg_gen_atomic_fetch_add_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); if (op_dst != ld_dst) { /* Note that mop sizes < 4 cannot use add_fetch because it won't carry into the higher bits. */ tcg_gen_add_i32(REG(op_dst), REG(ld_dst), op_arg); } } break; case INDEX_op_and_i32: if (op_dst != st_src) { goto fail; } if (op_dst == ld_dst) { tcg_gen_atomic_and_fetch_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); } else { tcg_gen_atomic_fetch_and_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); tcg_gen_and_i32(REG(op_dst), REG(ld_dst), op_arg); } break; case INDEX_op_or_i32: if (op_dst != st_src) { goto fail; } if (op_dst == ld_dst) { tcg_gen_atomic_or_fetch_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); } else { tcg_gen_atomic_fetch_or_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); tcg_gen_or_i32(REG(op_dst), REG(ld_dst), op_arg); } break; case INDEX_op_xor_i32: if (op_dst != st_src) { goto fail; } if (op_dst == ld_dst) { tcg_gen_atomic_xor_fetch_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); } else { tcg_gen_atomic_fetch_xor_i32(REG(ld_dst), REG(ld_adr), op_arg, ctx->memidx, ld_mop); tcg_gen_xor_i32(REG(op_dst), REG(ld_dst), op_arg); } break; case INDEX_op_setcond_i32: if (st_src == ld_dst) { goto fail; } tcg_gen_atomic_cmpxchg_i32(REG(ld_dst), REG(ld_adr), op_arg, REG(st_src), ctx->memidx, ld_mop); tcg_gen_setcond_i32(TCG_COND_EQ, cpu_sr_t, REG(ld_dst), op_arg); if (mt_dst >= 0) { tcg_gen_mov_i32(REG(mt_dst), cpu_sr_t); } break; default: g_assert_not_reached(); } /* If op_src is not a valid register, then op_arg was a constant. */ if (op_src < 0) { tcg_temp_free_i32(op_arg); } /* The entire region has been translated. */ ctx->envflags &= ~GUSA_MASK; ctx->pc = pc_end; return max_insns; fail: qemu_log_mask(LOG_UNIMP, "Unrecognized gUSA sequence %08x-%08x\n", pc, pc_end); /* Restart with the EXCLUSIVE bit set, within a TB run via cpu_exec_step_atomic holding the exclusive lock. */ tcg_gen_insn_start(pc, ctx->envflags); ctx->envflags |= GUSA_EXCLUSIVE; gen_save_cpu_state(ctx, false); gen_helper_exclusive(cpu_env); ctx->bstate = BS_EXCP; /* We're not executing an instruction, but we must report one for the purposes of accounting within the TB. We might as well report the entire region consumed via ctx->pc so that it's immediately available in the disassembly dump. */ ctx->pc = pc_end; return 1; }


static int yop_read_header(AVFormatContext *s) { YopDecContext *yop = s->priv_data; AVIOContext *pb = s->pb; AVCodecContext *audio_dec, *video_dec; AVStream *audio_stream, *video_stream; int frame_rate, ret; audio_stream = avformat_new_stream(s, NULL); video_stream = avformat_new_stream(s, NULL); // Extra data that will be passed to the decoder video_stream->codec->extradata_size = 8; video_stream->codec->extradata = av_mallocz(video_stream->codec->extradata_size + FF_INPUT_BUFFER_PADDING_SIZE); if (!video_stream->codec->extradata) // Audio audio_dec = audio_stream->codec; audio_dec->codec_type = AVMEDIA_TYPE_AUDIO; audio_dec->codec_id = AV_CODEC_ID_ADPCM_IMA_APC; audio_dec->channels = 1; audio_dec->sample_rate = 22050; // Video video_dec = video_stream->codec; video_dec->codec_type = AVMEDIA_TYPE_VIDEO; video_dec->codec_id = AV_CODEC_ID_YOP; avio_skip(pb, 6); frame_rate = avio_r8(pb); yop->frame_size = avio_r8(pb) * 2048; video_dec->width = avio_rl16(pb); video_dec->height = avio_rl16(pb); video_stream->sample_aspect_ratio = (AVRational){1, 2}; ret = avio_read(pb, video_dec->extradata, 8); if (ret < 8) return ret < 0 ? ret : AVERROR_EOF; yop->palette_size = video_dec->extradata[0] * 3 + 4; yop->audio_block_length = AV_RL16(video_dec->extradata + 6); // 1840 samples per frame, 1 nibble per sample; hence 1840/2 = 920 if (yop->audio_block_length < 920 || yop->audio_block_length + yop->palette_size >= yop->frame_size) { av_log(s, AV_LOG_ERROR, "YOP has invalid header\n"); return AVERROR_INVALIDDATA; } avio_seek(pb, 2048, SEEK_SET); avpriv_set_pts_info(video_stream, 32, 1, frame_rate); return 0; }


int64_t bdrv_get_block_status_above(BlockDriverState *bs, BlockDriverState *base, int64_t sector_num, int nb_sectors, int *pnum, BlockDriverState **file) { Coroutine *co; BdrvCoGetBlockStatusData data = { .bs = bs, .base = base, .file = file, .sector_num = sector_num, .nb_sectors = nb_sectors, .pnum = pnum, .done = false, }; if (qemu_in_coroutine()) { /* Fast-path if already in coroutine context */ bdrv_get_block_status_above_co_entry(&data); } else { AioContext *aio_context = bdrv_get_aio_context(bs); co = qemu_coroutine_create(bdrv_get_block_status_above_co_entry); qemu_coroutine_enter(co, &data); while (!data.done) { aio_poll(aio_context, true); } } return data.ret; }


static int add_string_metadata(int count, const char *name, TiffContext *s) { char *value; if (bytestream2_get_bytes_left(&s->gb) < count || count < 0) return AVERROR_INVALIDDATA; value = av_malloc(count + 1); if (!value) return AVERROR(ENOMEM); bytestream2_get_bufferu(&s->gb, value, count); value[count] = 0; av_dict_set(avpriv_frame_get_metadatap(&s->picture), name, value, AV_DICT_DONT_STRDUP_VAL); return 0; }


static void pc_q35_init_1_6(QEMUMachineInitArgs *args) { has_pci_info = false; pc_q35_init(args); }


static void dvbsub_parse_clut_segment(AVCodecContext *avctx, const uint8_t *buf, int buf_size) { DVBSubContext *ctx = avctx->priv_data; const uint8_t *buf_end = buf + buf_size; int i, clut_id; DVBSubCLUT *clut; int entry_id, depth , full_range; int y, cr, cb, alpha; int r, g, b, r_add, g_add, b_add; av_dlog(avctx, "DVB clut packet:\n"); for (i=0; i < buf_size; i++) { av_dlog(avctx, "%02x ", buf[i]); if (i % 16 == 15) av_dlog(avctx, "\n"); } if (i % 16) av_dlog(avctx, "\n"); clut_id = *buf++; buf += 1; clut = get_clut(ctx, clut_id); if (!clut) { clut = av_malloc(sizeof(DVBSubCLUT)); memcpy(clut, &default_clut, sizeof(DVBSubCLUT)); clut->id = clut_id; clut->next = ctx->clut_list; ctx->clut_list = clut; } while (buf + 4 < buf_end) { entry_id = *buf++; depth = (*buf) & 0xe0; if (depth == 0) { av_log(avctx, AV_LOG_ERROR, "Invalid clut depth 0x%x!\n", *buf); return; } full_range = (*buf++) & 1; if (full_range) { y = *buf++; cr = *buf++; cb = *buf++; alpha = *buf++; } else { y = buf[0] & 0xfc; cr = (((buf[0] & 3) << 2) | ((buf[1] >> 6) & 3)) << 4; cb = (buf[1] << 2) & 0xf0; alpha = (buf[1] << 6) & 0xc0; buf += 2; } if (y == 0) alpha = 0xff; YUV_TO_RGB1_CCIR(cb, cr); YUV_TO_RGB2_CCIR(r, g, b, y); av_dlog(avctx, "clut %d := (%d,%d,%d,%d)\n", entry_id, r, g, b, alpha); if (depth & 0x80) clut->clut4[entry_id] = RGBA(r,g,b,255 - alpha); if (depth & 0x40) clut->clut16[entry_id] = RGBA(r,g,b,255 - alpha); if (depth & 0x20) clut->clut256[entry_id] = RGBA(r,g,b,255 - alpha); } }


static void intra_predict_mad_cow_dc_l0t_8x8_msa(uint8_t *src, int32_t stride) { uint8_t lp_cnt; uint32_t src0, src1, src2 = 0; uint32_t out0, out1, out2; v16u8 src_top; v8u16 add; v4u32 sum; src_top = LD_UB(src - stride); add = __msa_hadd_u_h(src_top, src_top); sum = __msa_hadd_u_w(add, add); src0 = __msa_copy_u_w((v4i32) sum, 0); src1 = __msa_copy_u_w((v4i32) sum, 1); for (lp_cnt = 0; lp_cnt < 4; lp_cnt++) { src2 += src[lp_cnt * stride - 1]; } src2 = (src0 + src2 + 4) >> 3; src0 = (src0 + 2) >> 2; src1 = (src1 + 2) >> 2; out0 = src0 * 0x01010101; out1 = src1 * 0x01010101; out2 = src2 * 0x01010101; for (lp_cnt = 4; lp_cnt--;) { SW(out2, src); SW(out1, src + 4); SW(out0, src + stride * 4); SW(out1, src + stride * 4 + 4); src += stride; } }


static int write_streamheader(AVFormatContext *avctx, AVIOContext *bc, AVStream *st, int i){ NUTContext *nut = avctx->priv_data; AVCodecContext *codec = st->codec; unsigned codec_tag = av_codec_get_tag(ff_nut_codec_tags, codec->codec_id); ff_put_v(bc, i); switch(codec->codec_type){ case AVMEDIA_TYPE_VIDEO: ff_put_v(bc, 0); break; case AVMEDIA_TYPE_AUDIO: ff_put_v(bc, 1); break; case AVMEDIA_TYPE_SUBTITLE: ff_put_v(bc, 2); break; default : ff_put_v(bc, 3); break; } ff_put_v(bc, 4); if (!codec_tag) codec_tag = codec->codec_tag; if (codec_tag) { avio_wl32(bc, codec_tag); } else { av_log(avctx, AV_LOG_ERROR, "No codec tag defined for stream %d\n", i); return AVERROR(EINVAL); } ff_put_v(bc, nut->stream[i].time_base - nut->time_base); ff_put_v(bc, nut->stream[i].msb_pts_shift); ff_put_v(bc, nut->stream[i].max_pts_distance); ff_put_v(bc, codec->has_b_frames); avio_w8(bc, 0); /* flags: 0x1 - fixed_fps, 0x2 - index_present */ ff_put_v(bc, codec->extradata_size); avio_write(bc, codec->extradata, codec->extradata_size); switch(codec->codec_type){ case AVMEDIA_TYPE_AUDIO: ff_put_v(bc, codec->sample_rate); ff_put_v(bc, 1); ff_put_v(bc, codec->channels); break; case AVMEDIA_TYPE_VIDEO: ff_put_v(bc, codec->width); ff_put_v(bc, codec->height); if(st->sample_aspect_ratio.num<=0 || st->sample_aspect_ratio.den<=0){ ff_put_v(bc, 0); ff_put_v(bc, 0); }else{ ff_put_v(bc, st->sample_aspect_ratio.num); ff_put_v(bc, st->sample_aspect_ratio.den); } ff_put_v(bc, 0); /* csp type -- unknown */ break; default: break; } return 0; }


SYNTH_FILTER_FUNC(sse2) SYNTH_FILTER_FUNC(avx) SYNTH_FILTER_FUNC(fma3) #endif /* HAVE_YASM */ av_cold void ff_synth_filter_init_x86(SynthFilterContext *s) { #if HAVE_YASM int cpu_flags = av_get_cpu_flags(); #if ARCH_X86_32 if (EXTERNAL_SSE(cpu_flags)) { s->synth_filter_float = synth_filter_sse; } #endif if (EXTERNAL_SSE2(cpu_flags)) { s->synth_filter_float = synth_filter_sse2; } if (EXTERNAL_AVX(cpu_flags)) { s->synth_filter_float = synth_filter_avx; } if (EXTERNAL_FMA3(cpu_flags)) { s->synth_filter_float = synth_filter_fma3; } #endif /* HAVE_YASM */ }


static BlockDriverAIOCB *iscsi_aio_ioctl(BlockDriverState *bs, unsigned long int req, void *buf, BlockDriverCompletionFunc *cb, void *opaque) { IscsiLun *iscsilun = bs->opaque; struct iscsi_context *iscsi = iscsilun->iscsi; struct iscsi_data data; IscsiAIOCB *acb; assert(req == SG_IO); acb = qemu_aio_get(&iscsi_aiocb_info, bs, cb, opaque); acb->iscsilun = iscsilun; acb->canceled = 0; acb->bh = NULL; acb->status = -EINPROGRESS; acb->buf = NULL; acb->ioh = buf; acb->task = malloc(sizeof(struct scsi_task)); if (acb->task == NULL) { error_report("iSCSI: Failed to allocate task for scsi command. %s", iscsi_get_error(iscsi)); qemu_aio_release(acb); return NULL; } memset(acb->task, 0, sizeof(struct scsi_task)); switch (acb->ioh->dxfer_direction) { case SG_DXFER_TO_DEV: acb->task->xfer_dir = SCSI_XFER_WRITE; break; case SG_DXFER_FROM_DEV: acb->task->xfer_dir = SCSI_XFER_READ; break; default: acb->task->xfer_dir = SCSI_XFER_NONE; break; } acb->task->cdb_size = acb->ioh->cmd_len; memcpy(&acb->task->cdb[0], acb->ioh->cmdp, acb->ioh->cmd_len); acb->task->expxferlen = acb->ioh->dxfer_len; data.size = 0; if (acb->task->xfer_dir == SCSI_XFER_WRITE) { if (acb->ioh->iovec_count == 0) { data.data = acb->ioh->dxferp; data.size = acb->ioh->dxfer_len; } else { #if defined(LIBISCSI_FEATURE_IOVECTOR) scsi_task_set_iov_out(acb->task, (struct scsi_iovec *) acb->ioh->dxferp, acb->ioh->iovec_count); #else struct iovec *iov = (struct iovec *)acb->ioh->dxferp; acb->buf = g_malloc(acb->ioh->dxfer_len); data.data = acb->buf; data.size = iov_to_buf(iov, acb->ioh->iovec_count, 0, acb->buf, acb->ioh->dxfer_len); #endif } } if (iscsi_scsi_command_async(iscsi, iscsilun->lun, acb->task, iscsi_aio_ioctl_cb, (data.size > 0) ? &data : NULL, acb) != 0) { scsi_free_scsi_task(acb->task); qemu_aio_release(acb); return NULL; } /* tell libiscsi to read straight into the buffer we got from ioctl */ if (acb->task->xfer_dir == SCSI_XFER_READ) { if (acb->ioh->iovec_count == 0) { scsi_task_add_data_in_buffer(acb->task, acb->ioh->dxfer_len, acb->ioh->dxferp); } else { #if defined(LIBISCSI_FEATURE_IOVECTOR) scsi_task_set_iov_in(acb->task, (struct scsi_iovec *) acb->ioh->dxferp, acb->ioh->iovec_count); #else int i; for (i = 0; i < acb->ioh->iovec_count; i++) { struct iovec *iov = (struct iovec *)acb->ioh->dxferp; scsi_task_add_data_in_buffer(acb->task, iov[i].iov_len, iov[i].iov_base); } #endif } } iscsi_set_events(iscsilun); return &acb->common; }


static void esp_pci_dma_memory_rw(PCIESPState *pci, uint8_t *buf, int len, DMADirection dir) { dma_addr_t addr; DMADirection expected_dir; if (pci->dma_regs[DMA_CMD] & DMA_CMD_DIR) { expected_dir = DMA_DIRECTION_FROM_DEVICE; } else { expected_dir = DMA_DIRECTION_TO_DEVICE; } if (dir != expected_dir) { trace_esp_pci_error_invalid_dma_direction(); return; } if (pci->dma_regs[DMA_STAT] & DMA_CMD_MDL) { qemu_log_mask(LOG_UNIMP, "am53c974: MDL transfer not implemented\n"); } addr = pci->dma_regs[DMA_SPA]; if (pci->dma_regs[DMA_WBC] < len) { len = pci->dma_regs[DMA_WBC]; } pci_dma_rw(PCI_DEVICE(pci), addr, buf, len, dir); /* update status registers */ pci->dma_regs[DMA_WBC] -= len; pci->dma_regs[DMA_WAC] += len; }


void qemu_fflush(QEMUFile *f) { ssize_t ret = 0; if (!qemu_file_is_writable(f)) { return; } if (f->ops->writev_buffer) { if (f->iovcnt > 0) { ret = f->ops->writev_buffer(f->opaque, f->iov, f->iovcnt, f->pos); } } else { if (f->buf_index > 0) { ret = f->ops->put_buffer(f->opaque, f->buf, f->pos, f->buf_index); } } if (ret >= 0) { f->pos += ret; } f->buf_index = 0; f->iovcnt = 0; if (ret < 0) { qemu_file_set_error(f, ret); } }


int64_t avio_seek(AVIOContext *s, int64_t offset, int whence) { int64_t offset1; int64_t pos; int force = whence & AVSEEK_FORCE; int buffer_size; int short_seek; whence &= ~AVSEEK_FORCE; if(!s) buffer_size = s->buf_end - s->buffer; // pos is the absolute position that the beginning of s->buffer corresponds to in the file pos = s->pos - (s->write_flag ? 0 : buffer_size); if (whence != SEEK_CUR && whence != SEEK_SET) if (whence == SEEK_CUR) { offset1 = pos + (s->buf_ptr - s->buffer); if (offset == 0) return offset1; offset += offset1; } if (offset < 0) if (s->short_seek_get) { short_seek = s->short_seek_get(s->opaque); /* fallback to default short seek */ if (short_seek <= 0) short_seek = s->short_seek_threshold; } else short_seek = s->short_seek_threshold; offset1 = offset - pos; // "offset1" is the relative offset from the beginning of s->buffer s->buf_ptr_max = FFMAX(s->buf_ptr_max, s->buf_ptr); if ((!s->direct || !s->seek) && offset1 >= 0 && offset1 <= (s->write_flag ? s->buf_ptr_max - s->buffer : buffer_size)) { /* can do the seek inside the buffer */ s->buf_ptr = s->buffer + offset1; } else if ((!(s->seekable & AVIO_SEEKABLE_NORMAL) || offset1 <= buffer_size + short_seek) && !s->write_flag && offset1 >= 0 && (!s->direct || !s->seek) && (whence != SEEK_END || force)) { while(s->pos < offset && !s->eof_reached) fill_buffer(s); if (s->eof_reached) return AVERROR_EOF; s->buf_ptr = s->buf_end - (s->pos - offset); } else if(!s->write_flag && offset1 < 0 && -offset1 < buffer_size>>1 && s->seek && offset > 0) { int64_t res; pos -= FFMIN(buffer_size>>1, pos); if ((res = s->seek(s->opaque, pos, SEEK_SET)) < 0) return res; s->buf_end = s->buf_ptr = s->buffer; s->pos = pos; s->eof_reached = 0; fill_buffer(s); return avio_seek(s, offset, SEEK_SET | force); } else { int64_t res; if (s->write_flag) { flush_buffer(s); } if (!s->seek) return AVERROR(EPIPE); if ((res = s->seek(s->opaque, offset, SEEK_SET)) < 0) return res; s->seek_count ++; if (!s->write_flag) s->buf_end = s->buffer; s->buf_ptr = s->buf_ptr_max = s->buffer; s->pos = offset; } s->eof_reached = 0; return offset; }


static void coroutine_fn v9fs_rename(void *opaque) { int32_t fid; ssize_t err = 0; size_t offset = 7; V9fsString name; int32_t newdirfid; V9fsFidState *fidp; V9fsPDU *pdu = opaque; V9fsState *s = pdu->s; v9fs_string_init(&name); err = pdu_unmarshal(pdu, offset, "dds", &fid, &newdirfid, &name); if (err < 0) { goto out_nofid; } if (name_is_illegal(name.data)) { err = -ENOENT; goto out_nofid; } if (!strcmp(".", name.data) || !strcmp("..", name.data)) { err = -EISDIR; goto out_nofid; } fidp = get_fid(pdu, fid); if (fidp == NULL) { err = -ENOENT; goto out_nofid; } BUG_ON(fidp->fid_type != P9_FID_NONE); /* if fs driver is not path based, return EOPNOTSUPP */ if (!(pdu->s->ctx.export_flags & V9FS_PATHNAME_FSCONTEXT)) { err = -EOPNOTSUPP; goto out; } v9fs_path_write_lock(s); err = v9fs_complete_rename(pdu, fidp, newdirfid, &name); v9fs_path_unlock(s); if (!err) { err = offset; } out: put_fid(pdu, fidp); out_nofid: pdu_complete(pdu, err); v9fs_string_free(&name); }


AVVDPAUContext *av_vdpau_alloc_context(void) { return av_mallocz(sizeof(AVVDPAUContext)); }


static AVBufferRef *pool_alloc_buffer(AVBufferPool *pool) { BufferPoolEntry *buf; AVBufferRef *ret; ret = pool->alloc(pool->size); if (!ret) return NULL; buf = av_mallocz(sizeof(*buf)); if (!buf) { av_buffer_unref(&ret); return NULL; } buf->data = ret->buffer->data; buf->opaque = ret->buffer->opaque; buf->free = ret->buffer->free; buf->pool = pool; ret->buffer->opaque = buf; ret->buffer->free = pool_release_buffer; avpriv_atomic_int_add_and_fetch(&pool->refcount, 1); return ret; }


static void compute_frame_duration(int *pnum, int *pden, AVStream *st, AVCodecParserContext *pc, AVPacket *pkt) { int frame_size; *pnum = 0; *pden = 0; switch(st->codec.codec_type) { case CODEC_TYPE_VIDEO: if(st->time_base.num*1000 > st->time_base.den){ *pnum = st->time_base.num; *pden = st->time_base.den; }else if(st->codec.time_base.num*1000 > st->codec.time_base.den){ *pnum = st->codec.time_base.num; *pden = st->codec.time_base.den; if (pc && pc->repeat_pict) { *pden *= 2; *pnum = (*pnum) * (2 + pc->repeat_pict); } } break; case CODEC_TYPE_AUDIO: frame_size = get_audio_frame_size(&st->codec, pkt->size); if (frame_size < 0) break; *pnum = frame_size; *pden = st->codec.sample_rate; break; default: break; } }


static int vdi_check(BlockDriverState *bs) { /* TODO: additional checks possible. */ BDRVVdiState *s = (BDRVVdiState *)bs->opaque; int n_errors = 0; uint32_t blocks_allocated = 0; uint32_t block; uint32_t *bmap; logout("\n"); bmap = qemu_malloc(s->header.blocks_in_image * sizeof(uint32_t)); memset(bmap, 0xff, s->header.blocks_in_image * sizeof(uint32_t)); /* Check block map and value of blocks_allocated. */ for (block = 0; block < s->header.blocks_in_image; block++) { uint32_t bmap_entry = le32_to_cpu(s->bmap[block]); if (bmap_entry != VDI_UNALLOCATED) { if (bmap_entry < s->header.blocks_in_image) { blocks_allocated++; if (bmap[bmap_entry] == VDI_UNALLOCATED) { bmap[bmap_entry] = bmap_entry; } else { fprintf(stderr, "ERROR: block index %" PRIu32 " also used by %" PRIu32 "\n", bmap[bmap_entry], bmap_entry); } } else { fprintf(stderr, "ERROR: block index %" PRIu32 " too large, is %" PRIu32 "\n", block, bmap_entry); n_errors++; } } } if (blocks_allocated != s->header.blocks_allocated) { fprintf(stderr, "ERROR: allocated blocks mismatch, is %" PRIu32 ", should be %" PRIu32 "\n", blocks_allocated, s->header.blocks_allocated); n_errors++; } qemu_free(bmap); return n_errors; }


static void submit_pdu(V9fsState *s, V9fsPDU *pdu) { pdu_handler_t *handler; if (debug_9p_pdu) { pprint_pdu(pdu); } BUG_ON(pdu->id >= ARRAY_SIZE(pdu_handlers)); handler = pdu_handlers[pdu->id]; BUG_ON(handler == NULL); handler(s, pdu); }


uint64_t helper_addqv (uint64_t op1, uint64_t op2) { uint64_t tmp = op1; op1 += op2; if (unlikely((tmp ^ op2 ^ (-1ULL)) & (tmp ^ op1) & (1ULL << 63))) { arith_excp(env, GETPC(), EXC_M_IOV, 0); } return op1; }


static void cirrus_mem_writeb_mode4and5_8bpp(CirrusVGAState * s, unsigned mode, unsigned offset, uint32_t mem_value) { int x; unsigned val = mem_value; uint8_t *dst; dst = s->vram_ptr + offset; for (x = 0; x < 8; x++) { if (val & 0x80) { *dst = s->cirrus_shadow_gr1; } else if (mode == 5) { *dst = s->cirrus_shadow_gr0; } val <<= 1; dst++; } cpu_physical_memory_set_dirty(s->vram_offset + offset); cpu_physical_memory_set_dirty(s->vram_offset + offset + 7); }


void translator_loop(const TranslatorOps *ops, DisasContextBase *db, CPUState *cpu, TranslationBlock *tb) { int max_insns; /* Initialize DisasContext */ db->tb = tb; db->pc_first = tb->pc; db->pc_next = db->pc_first; db->is_jmp = DISAS_NEXT; db->num_insns = 0; db->singlestep_enabled = cpu->singlestep_enabled; /* Instruction counting */ max_insns = db->tb->cflags & CF_COUNT_MASK; if (max_insns == 0) { max_insns = CF_COUNT_MASK; } if (max_insns > TCG_MAX_INSNS) { max_insns = TCG_MAX_INSNS; } if (db->singlestep_enabled || singlestep) { max_insns = 1; } max_insns = ops->init_disas_context(db, cpu, max_insns); tcg_debug_assert(db->is_jmp == DISAS_NEXT); /* no early exit */ /* Reset the temp count so that we can identify leaks */ tcg_clear_temp_count(); /* Start translating. */ gen_tb_start(db->tb); ops->tb_start(db, cpu); tcg_debug_assert(db->is_jmp == DISAS_NEXT); /* no early exit */ while (true) { db->num_insns++; ops->insn_start(db, cpu); tcg_debug_assert(db->is_jmp == DISAS_NEXT); /* no early exit */ /* Pass breakpoint hits to target for further processing */ if (unlikely(!QTAILQ_EMPTY(&cpu->breakpoints))) { CPUBreakpoint *bp; QTAILQ_FOREACH(bp, &cpu->breakpoints, entry) { if (bp->pc == db->pc_next) { if (ops->breakpoint_check(db, cpu, bp)) { break; } } } /* The breakpoint_check hook may use DISAS_TOO_MANY to indicate that only one more instruction is to be executed. Otherwise it should use DISAS_NORETURN when generating an exception, but may use a DISAS_TARGET_* value for Something Else. */ if (db->is_jmp > DISAS_TOO_MANY) { break; } } /* Disassemble one instruction. The translate_insn hook should update db->pc_next and db->is_jmp to indicate what should be done next -- either exiting this loop or locate the start of the next instruction. */ if (db->num_insns == max_insns && (db->tb->cflags & CF_LAST_IO)) { /* Accept I/O on the last instruction. */ gen_io_start(); ops->translate_insn(db, cpu); gen_io_end(); } else { ops->translate_insn(db, cpu); } /* Stop translation if translate_insn so indicated. */ if (db->is_jmp != DISAS_NEXT) { break; } /* Stop translation if the output buffer is full, or we have executed all of the allowed instructions. */ if (tcg_op_buf_full() || db->num_insns >= max_insns) { db->is_jmp = DISAS_TOO_MANY; break; } } /* Emit code to exit the TB, as indicated by db->is_jmp. */ ops->tb_stop(db, cpu); gen_tb_end(db->tb, db->num_insns); /* The disas_log hook may use these values rather than recompute. */ db->tb->size = db->pc_next - db->pc_first; db->tb->icount = db->num_insns; #ifdef DEBUG_DISAS if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM) && qemu_log_in_addr_range(db->pc_first)) { qemu_log_lock(); qemu_log("----------------\n"); ops->disas_log(db, cpu); qemu_log("\n"); qemu_log_unlock(); } #endif }


static int load_apply_palette(FFFrameSync *fs) { AVFilterContext *ctx = fs->parent; AVFilterLink *inlink = ctx->inputs[0]; PaletteUseContext *s = ctx->priv; AVFrame *master, *second, *out = NULL; int ret; // writable for error diffusal dithering ret = ff_framesync_dualinput_get_writable(fs, &master, &second); if (ret < 0) return ret; if (!master || !second) { ret = AVERROR_BUG; goto error; } if (!s->palette_loaded) { load_palette(s, second); } ret = apply_palette(inlink, master, &out); if (ret < 0) goto error; return ff_filter_frame(ctx->outputs[0], out); error: av_frame_free(&master); av_frame_free(&second); return ret; }


void avfilter_uninit(void) { memset(registered_avfilters, 0, sizeof(registered_avfilters)); next_registered_avfilter_idx = 0; }


int pcm_read_seek(AVFormatContext *s, int stream_index, int64_t timestamp, int flags) { AVStream *st; int block_align, byte_rate; int64_t pos; st = s->streams[0]; block_align = st->codec->block_align ? st->codec->block_align : (av_get_bits_per_sample(st->codec->codec_id) * st->codec->channels) >> 3; byte_rate = st->codec->bit_rate ? st->codec->bit_rate >> 3 : block_align * st->codec->sample_rate; if (block_align <= 0 || byte_rate <= 0) return -1; /* compute the position by aligning it to block_align */ pos = av_rescale_rnd(timestamp * byte_rate, st->time_base.num, st->time_base.den * (int64_t)block_align, (flags & AVSEEK_FLAG_BACKWARD) ? AV_ROUND_DOWN : AV_ROUND_UP); pos *= block_align; /* recompute exact position */ st->cur_dts = av_rescale(pos, st->time_base.den, byte_rate * (int64_t)st->time_base.num); url_fseek(s->pb, pos + s->data_offset, SEEK_SET); return 0; }


void show_pix_fmts(void) { list_fmts(avcodec_pix_fmt_string, PIX_FMT_NB); }


static int spdif_get_offset_and_codec(AVFormatContext *s, enum IEC61937DataType data_type, const char *buf, int *offset, enum AVCodecID *codec) { AACADTSHeaderInfo aac_hdr; GetBitContext gbc; switch (data_type & 0xff) { case IEC61937_AC3: *offset = AC3_FRAME_SIZE << 2; *codec = AV_CODEC_ID_AC3; break; case IEC61937_MPEG1_LAYER1: *offset = spdif_mpeg_pkt_offset[1][0]; *codec = AV_CODEC_ID_MP1; break; case IEC61937_MPEG1_LAYER23: *offset = spdif_mpeg_pkt_offset[1][0]; *codec = AV_CODEC_ID_MP3; break; case IEC61937_MPEG2_EXT: *offset = 4608; *codec = AV_CODEC_ID_MP3; break; case IEC61937_MPEG2_AAC: init_get_bits(&gbc, buf, AAC_ADTS_HEADER_SIZE * 8); if (avpriv_aac_parse_header(&gbc, &aac_hdr)) { if (s) /* be silent during a probe */ av_log(s, AV_LOG_ERROR, "Invalid AAC packet in IEC 61937\n"); return AVERROR_INVALIDDATA; } *offset = aac_hdr.samples << 2; *codec = AV_CODEC_ID_AAC; break; case IEC61937_MPEG2_LAYER1_LSF: *offset = spdif_mpeg_pkt_offset[0][0]; *codec = AV_CODEC_ID_MP1; break; case IEC61937_MPEG2_LAYER2_LSF: *offset = spdif_mpeg_pkt_offset[0][1]; *codec = AV_CODEC_ID_MP2; break; case IEC61937_MPEG2_LAYER3_LSF: *offset = spdif_mpeg_pkt_offset[0][2]; *codec = AV_CODEC_ID_MP3; break; case IEC61937_DTS1: *offset = 2048; *codec = AV_CODEC_ID_DTS; break; case IEC61937_DTS2: *offset = 4096; *codec = AV_CODEC_ID_DTS; break; case IEC61937_DTS3: *offset = 8192; *codec = AV_CODEC_ID_DTS; break; default: if (s) { /* be silent during a probe */ avpriv_request_sample(s, "Data type 0x%04x in IEC 61937", data_type); } return AVERROR_PATCHWELCOME; } return 0; }


static av_cold int seqvideo_decode_init(AVCodecContext *avctx) { SeqVideoContext *seq = avctx->priv_data; seq->avctx = avctx; avctx->pix_fmt = AV_PIX_FMT_PAL8; seq->frame.data[0] = NULL; return 0; }


void set_context_opts(void *ctx, void *opts_ctx, int flags, AVCodec *codec) { int i; void *priv_ctx=NULL; if(!strcmp("AVCodecContext", (*(AVClass**)ctx)->class_name)){ AVCodecContext *avctx= ctx; if(codec && codec->priv_class && avctx->priv_data){ priv_ctx= avctx->priv_data; } } else if (!strcmp("AVFormatContext", (*(AVClass**)ctx)->class_name)) { AVFormatContext *avctx = ctx; if (avctx->oformat && avctx->oformat->priv_class) { priv_ctx = avctx->priv_data; } } for(i=0; i<opt_name_count; i++){ char buf[256]; const AVOption *opt; const char *str= av_get_string(opts_ctx, opt_names[i], &opt, buf, sizeof(buf)); /* if an option with name opt_names[i] is present in opts_ctx then str is non-NULL */ if(str && ((opt->flags & flags) == flags)) av_set_string3(ctx, opt_names[i], str, 1, NULL); /* We need to use a differnt system to pass options to the private context because it is not known which codec and thus context kind that will be when parsing options we thus use opt_values directly instead of opts_ctx */ if(!str && priv_ctx) { if (av_find_opt(priv_ctx, opt_names[i], NULL, flags, flags)) av_set_string3(priv_ctx, opt_names[i], opt_values[i], 0, NULL); } } }


int av_vsrc_buffer_add_frame(AVFilterContext *buffer_filter, AVFrame *frame, int64_t pts, AVRational pixel_aspect) { BufferSourceContext *c = buffer_filter->priv; AVFilterBufferRef *buf; int ret; if (!buf) { c->eof = 1; return 0; } else if (c->eof) return AVERROR(EINVAL); if (!av_fifo_space(c->fifo) && (ret = av_fifo_realloc2(c->fifo, av_fifo_size(c->fifo) + sizeof(buf))) < 0) return ret; CHECK_PARAM_CHANGE(buffer_filter, c, frame->width, frame->height, frame->format); buf = avfilter_get_video_buffer(buffer_filter->outputs[0], AV_PERM_WRITE, c->w, c->h); av_image_copy(buf->data, buf->linesize, frame->data, frame->linesize, c->pix_fmt, c->w, c->h); avfilter_copy_frame_props(buf, frame); buf->pts = pts; buf->video->pixel_aspect = pixel_aspect; if ((ret = av_fifo_generic_write(c->fifo, &buf, sizeof(buf), NULL)) < 0) { avfilter_unref_buffer(buf); return ret; } return 0; }


static int decode_byterun(uint8_t *dst, int dst_size, const uint8_t *buf, const uint8_t *const buf_end) { const uint8_t *const buf_start = buf; unsigned x; for (x = 0; x < dst_size && buf < buf_end;) { unsigned length; const int8_t value = *buf++; if (value >= 0) { length = value + 1; memcpy(dst + x, buf, FFMIN3(length, dst_size - x, buf_end - buf)); buf += length; } else if (value > -128) { length = -value + 1; memset(dst + x, *buf++, FFMIN(length, dst_size - x)); } else { // noop continue; } x += length; } if (x < dst_size) { av_log(NULL, AV_LOG_WARNING, "decode_byterun ended before plane size\n"); memset(dst+x, 0, dst_size - x); } return buf - buf_start; }


uint64_t blk_mig_bytes_total(void) { BlkMigDevState *bmds; uint64_t sum = 0; QSIMPLEQ_FOREACH(bmds, &block_mig_state.bmds_list, entry) { sum += bmds->total_sectors; } return sum << BDRV_SECTOR_BITS; }


theora_header (AVFormatContext * s, int idx) { struct ogg *ogg = s->priv_data; struct ogg_stream *os = ogg->streams + idx; AVStream *st = s->streams[idx]; struct theora_params *thp = os->private; int cds = st->codec->extradata_size + os->psize + 2; uint8_t *cdp; if(!(os->buf[os->pstart] & 0x80)) return 0; if(!thp){ thp = av_mallocz(sizeof(*thp)); os->private = thp; if (os->buf[os->pstart] == 0x80) { GetBitContext gb; int width, height; init_get_bits(&gb, os->buf + os->pstart, os->psize*8); skip_bits_long(&gb, 7*8); /* 0x80"theora" */ thp->version = get_bits_long(&gb, 24); if (thp->version < 0x030100) { av_log(s, AV_LOG_ERROR, "Too old or unsupported Theora (%x)\n", thp->version); return -1; width = get_bits(&gb, 16) << 4; height = get_bits(&gb, 16) << 4; avcodec_set_dimensions(st->codec, width, height); if (thp->version >= 0x030400) skip_bits(&gb, 100); if (thp->version >= 0x030200) { width = get_bits_long(&gb, 24); height = get_bits_long(&gb, 24); if ( width <= st->codec->width && width > st->codec->width-16 && height <= st->codec->height && height > st->codec->height-16) avcodec_set_dimensions(st->codec, width, height); skip_bits(&gb, 16); st->codec->time_base.den = get_bits_long(&gb, 32); st->codec->time_base.num = get_bits_long(&gb, 32); st->time_base = st->codec->time_base; st->sample_aspect_ratio.num = get_bits_long(&gb, 24); st->sample_aspect_ratio.den = get_bits_long(&gb, 24); if (thp->version >= 0x030200) skip_bits_long(&gb, 38); if (thp->version >= 0x304000) skip_bits(&gb, 2); thp->gpshift = get_bits(&gb, 5); thp->gpmask = (1 << thp->gpshift) - 1; st->codec->codec_type = CODEC_TYPE_VIDEO; st->codec->codec_id = CODEC_ID_THEORA; } else if (os->buf[os->pstart] == 0x83) { vorbis_comment (s, os->buf + os->pstart + 7, os->psize - 8); st->codec->extradata = av_realloc (st->codec->extradata, cds + FF_INPUT_BUFFER_PADDING_SIZE); cdp = st->codec->extradata + st->codec->extradata_size; *cdp++ = os->psize >> 8; *cdp++ = os->psize & 0xff; memcpy (cdp, os->buf + os->pstart, os->psize); st->codec->extradata_size = cds; return 1;


static TAPState *net_tap_fd_init(VLANState *vlan, const char *model, const char *name, int fd) { TAPState *s; s = qemu_mallocz(sizeof(TAPState)); s->fd = fd; s->vc = qemu_new_vlan_client(vlan, model, name, tap_receive, NULL, s); s->vc->fd_readv = tap_receive_iov; qemu_set_fd_handler(s->fd, tap_send, NULL, s); snprintf(s->vc->info_str, sizeof(s->vc->info_str), "fd=%d", fd); return s; }


static int write_refcount_block_entries(BlockDriverState *bs, int64_t refcount_block_offset, int first_index, int last_index) { BDRVQcowState *s = bs->opaque; size_t size; int ret; if (cache_refcount_updates) { return 0; } if (first_index < 0) { return 0; } first_index &= ~(REFCOUNTS_PER_SECTOR - 1); last_index = (last_index + REFCOUNTS_PER_SECTOR) & ~(REFCOUNTS_PER_SECTOR - 1); size = (last_index - first_index) << REFCOUNT_SHIFT; BLKDBG_EVENT(bs->file, BLKDBG_REFBLOCK_UPDATE_PART); ret = bdrv_pwrite(bs->file, refcount_block_offset + (first_index << REFCOUNT_SHIFT), &s->refcount_block_cache[first_index], size); if (ret < 0) { return ret; } return 0; }


static int t15(InterplayACMContext *s, unsigned ind, unsigned col) { GetBitContext *gb = &s->gb; unsigned i, b; int n1, n2, n3; for (i = 0; i < s->rows; i++) { /* b = (x1) + (x2 * 3) + (x3 * 9) */ b = get_bits(gb, 5); n1 = (mul_3x3[b] & 0x0F) - 1; n2 = ((mul_3x3[b] >> 4) & 0x0F) - 1; n3 = ((mul_3x3[b] >> 8) & 0x0F) - 1; set_pos(s, i++, col, n1); if (i >= s->rows) break; set_pos(s, i++, col, n2); if (i >= s->rows) break; set_pos(s, i, col, n3); return 0;


void do_load_6xx_tlb (int is_code) { target_ulong RPN, CMP, EPN; int way; RPN = env->spr[SPR_RPA]; if (is_code) { CMP = env->spr[SPR_ICMP]; EPN = env->spr[SPR_IMISS]; } else { CMP = env->spr[SPR_DCMP]; EPN = env->spr[SPR_DMISS]; } way = (env->spr[SPR_SRR1] >> 17) & 1; #if defined (DEBUG_SOFTWARE_TLB) if (loglevel != 0) { fprintf(logfile, "%s: EPN %08lx %08lx PTE0 %08lx PTE1 %08lx way %d\n", __func__, (unsigned long)T0, (unsigned long)EPN, (unsigned long)CMP, (unsigned long)RPN, way); } #endif /* Store this TLB */ ppc6xx_tlb_store(env, T0 & TARGET_PAGE_MASK, way, is_code, CMP, RPN); }


void helper_dcbz(CPUPPCState *env, target_ulong addr, uint32_t is_dcbzl) { int dcbz_size = env->dcache_line_size; #if defined(TARGET_PPC64) if (!is_dcbzl && (env->excp_model == POWERPC_EXCP_970) && ((env->spr[SPR_970_HID5] >> 7) & 0x3) == 1) { dcbz_size = 32; } #endif /* XXX add e500mc support */ do_dcbz(env, addr, dcbz_size, GETPC()); }


envlist_create(void) { envlist_t *envlist; if ((envlist = malloc(sizeof (*envlist))) == NULL) return (NULL); QLIST_INIT(&envlist->el_entries); envlist->el_count = 0; return (envlist); }


static void gen_ori(DisasContext *ctx) { target_ulong uimm = UIMM(ctx->opcode); if (rS(ctx->opcode) == rA(ctx->opcode) && uimm == 0) { /* NOP */ /* XXX: should handle special NOPs for POWER series */ return; } tcg_gen_ori_tl(cpu_gpr[rA(ctx->opcode)], cpu_gpr[rS(ctx->opcode)], uimm); }


static void close(AVCodecParserContext *s) { H264Context *h = s->priv_data; ParseContext *pc = &h->s.parse_context; av_free(pc->buffer); }


static void sch_handle_start_func(SubchDev *sch, ORB *orb) { PMCW *p = &sch->curr_status.pmcw; SCSW *s = &sch->curr_status.scsw; int path; int ret; /* Path management: In our simple css, we always choose the only path. */ path = 0x80; if (!(s->ctrl & SCSW_ACTL_SUSP)) { /* Look at the orb and try to execute the channel program. */ assert(orb != NULL); /* resume does not pass an orb */ p->intparm = orb->intparm; if (!(orb->lpm & path)) { /* Generate a deferred cc 3 condition. */ s->flags |= SCSW_FLAGS_MASK_CC; s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= (SCSW_STCTL_ALERT | SCSW_STCTL_STATUS_PEND); return; } sch->ccw_fmt_1 = !!(orb->ctrl0 & ORB_CTRL0_MASK_FMT); sch->ccw_no_data_cnt = 0; } else { s->ctrl &= ~(SCSW_ACTL_SUSP | SCSW_ACTL_RESUME_PEND); } sch->last_cmd_valid = false; do { ret = css_interpret_ccw(sch, sch->channel_prog); switch (ret) { case -EAGAIN: /* ccw chain, continue processing */ break; case 0: /* success */ s->ctrl &= ~SCSW_ACTL_START_PEND; s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= SCSW_STCTL_PRIMARY | SCSW_STCTL_SECONDARY | SCSW_STCTL_STATUS_PEND; s->dstat = SCSW_DSTAT_CHANNEL_END | SCSW_DSTAT_DEVICE_END; s->cpa = sch->channel_prog + 8; break; case -ENOSYS: /* unsupported command, generate unit check (command reject) */ s->ctrl &= ~SCSW_ACTL_START_PEND; s->dstat = SCSW_DSTAT_UNIT_CHECK; /* Set sense bit 0 in ecw0. */ sch->sense_data[0] = 0x80; s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= SCSW_STCTL_PRIMARY | SCSW_STCTL_SECONDARY | SCSW_STCTL_ALERT | SCSW_STCTL_STATUS_PEND; s->cpa = sch->channel_prog + 8; break; case -EFAULT: /* memory problem, generate channel data check */ s->ctrl &= ~SCSW_ACTL_START_PEND; s->cstat = SCSW_CSTAT_DATA_CHECK; s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= SCSW_STCTL_PRIMARY | SCSW_STCTL_SECONDARY | SCSW_STCTL_ALERT | SCSW_STCTL_STATUS_PEND; s->cpa = sch->channel_prog + 8; break; case -EBUSY: /* subchannel busy, generate deferred cc 1 */ s->flags &= ~SCSW_FLAGS_MASK_CC; s->flags |= (1 << 8); s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= SCSW_STCTL_ALERT | SCSW_STCTL_STATUS_PEND; break; case -EINPROGRESS: /* channel program has been suspended */ s->ctrl &= ~SCSW_ACTL_START_PEND; s->ctrl |= SCSW_ACTL_SUSP; break; default: /* error, generate channel program check */ s->ctrl &= ~SCSW_ACTL_START_PEND; s->cstat = SCSW_CSTAT_PROG_CHECK; s->ctrl &= ~SCSW_CTRL_MASK_STCTL; s->ctrl |= SCSW_STCTL_PRIMARY | SCSW_STCTL_SECONDARY | SCSW_STCTL_ALERT | SCSW_STCTL_STATUS_PEND; s->cpa = sch->channel_prog + 8; break; } } while (ret == -EAGAIN); }


static int net_vhost_chardev_opts(void *opaque, const char *name, const char *value, Error **errp) { VhostUserChardevProps *props = opaque; if (strcmp(name, "backend") == 0 && strcmp(value, "socket") == 0) { props->is_socket = true; } else if (strcmp(name, "path") == 0) { props->is_unix = true; } else if (strcmp(name, "server") == 0) { } else { error_setg(errp, "vhost-user does not support a chardev with option %s=%s", name, value); return -1; } return 0; }


static int decode_frame(AVCodecContext *avctx, void *data, int *data_size, AVPacket *avpkt) { const uint8_t *buf = avpkt->data; const uint8_t *buf_end = avpkt->data + avpkt->size; int buf_size = avpkt->size; DPXContext *const s = avctx->priv_data; AVFrame *picture = data; AVFrame *const p = &s->picture; uint8_t *ptr; int magic_num, offset, endian; int x, y; int w, h, stride, bits_per_color, descriptor, elements, target_packet_size, source_packet_size; unsigned int rgbBuffer; magic_num = AV_RB32(buf); buf += 4; /* Check if the files "magic number" is "SDPX" which means it uses * big-endian or XPDS which is for little-endian files */ if (magic_num == AV_RL32("SDPX")) { endian = 0; } else if (magic_num == AV_RB32("SDPX")) { endian = 1; } else { av_log(avctx, AV_LOG_ERROR, "DPX marker not found\n"); offset = read32(&buf, endian); // Need to end in 0x304 offset from start of file buf = avpkt->data + 0x304; w = read32(&buf, endian); h = read32(&buf, endian); // Need to end in 0x320 to read the descriptor buf += 20; descriptor = buf[0]; // Need to end in 0x323 to read the bits per color buf += 3; avctx->bits_per_raw_sample = bits_per_color = buf[0]; switch (descriptor) { case 51: // RGBA elements = 4; break; case 50: // RGB elements = 3; break; default: av_log(avctx, AV_LOG_ERROR, "Unsupported descriptor %d\n", descriptor); switch (bits_per_color) { case 8: if (elements == 4) { avctx->pix_fmt = PIX_FMT_RGBA; } else { avctx->pix_fmt = PIX_FMT_RGB24; source_packet_size = elements; target_packet_size = elements; break; case 10: avctx->pix_fmt = PIX_FMT_RGB48; target_packet_size = 6; source_packet_size = elements * 2; break; case 12: case 16: if (endian) { avctx->pix_fmt = PIX_FMT_RGB48BE; } else { avctx->pix_fmt = PIX_FMT_RGB48LE; target_packet_size = 6; source_packet_size = elements * 2; break; default: av_log(avctx, AV_LOG_ERROR, "Unsupported color depth : %d\n", bits_per_color); if (s->picture.data[0]) avctx->release_buffer(avctx, &s->picture); if (av_image_check_size(w, h, 0, avctx)) if (w != avctx->width || h != avctx->height) avcodec_set_dimensions(avctx, w, h); if (avctx->get_buffer(avctx, p) < 0) { av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n"); // Move pointer to offset from start of file buf = avpkt->data + offset; ptr = p->data[0]; stride = p->linesize[0]; switch (bits_per_color) { case 10: for (x = 0; x < avctx->height; x++) { uint16_t *dst = (uint16_t*)ptr; for (y = 0; y < avctx->width; y++) { rgbBuffer = read32(&buf, endian); // Read out the 10-bit colors and convert to 16-bit *dst++ = make_16bit(rgbBuffer >> 16); *dst++ = make_16bit(rgbBuffer >> 6); *dst++ = make_16bit(rgbBuffer << 4); ptr += stride; break; case 8: case 12: // Treat 12-bit as 16-bit case 16: if (source_packet_size == target_packet_size) { for (x = 0; x < avctx->height; x++) { memcpy(ptr, buf, target_packet_size*avctx->width); ptr += stride; buf += source_packet_size*avctx->width; } else { for (x = 0; x < avctx->height; x++) { uint8_t *dst = ptr; for (y = 0; y < avctx->width; y++) { memcpy(dst, buf, target_packet_size); dst += target_packet_size; buf += source_packet_size; ptr += stride; break; *picture = s->picture; *data_size = sizeof(AVPicture); return buf_size;


static int mpeg_decode_mb(MpegEncContext *s, DCTELEM block[12][64]) { int i, j, k, cbp, val, mb_type, motion_type; const int mb_block_count = 4 + (1<< s->chroma_format) dprintf("decode_mb: x=%d y=%d\n", s->mb_x, s->mb_y); assert(s->mb_skiped==0); if (s->mb_skip_run-- != 0) { if(s->pict_type == I_TYPE){ av_log(s->avctx, AV_LOG_ERROR, "skiped MB in I frame at %d %d\n", s->mb_x, s->mb_y); return -1; } /* skip mb */ s->mb_intra = 0; for(i=0;i<12;i++) s->block_last_index[i] = -1; if(s->picture_structure == PICT_FRAME) s->mv_type = MV_TYPE_16X16; else s->mv_type = MV_TYPE_FIELD; if (s->pict_type == P_TYPE) { /* if P type, zero motion vector is implied */ s->mv_dir = MV_DIR_FORWARD; s->mv[0][0][0] = s->mv[0][0][1] = 0; s->last_mv[0][0][0] = s->last_mv[0][0][1] = 0; s->last_mv[0][1][0] = s->last_mv[0][1][1] = 0; s->field_select[0][0]= s->picture_structure - 1; s->mb_skiped = 1; s->current_picture.mb_type[ s->mb_x + s->mb_y*s->mb_stride ]= MB_TYPE_SKIP | MB_TYPE_L0 | MB_TYPE_16x16; } else { /* if B type, reuse previous vectors and directions */ s->mv[0][0][0] = s->last_mv[0][0][0]; s->mv[0][0][1] = s->last_mv[0][0][1]; s->mv[1][0][0] = s->last_mv[1][0][0]; s->mv[1][0][1] = s->last_mv[1][0][1]; s->current_picture.mb_type[ s->mb_x + s->mb_y*s->mb_stride ]= s->current_picture.mb_type[ s->mb_x + s->mb_y*s->mb_stride - 1] | MB_TYPE_SKIP; // assert(s->current_picture.mb_type[ s->mb_x + s->mb_y*s->mb_stride - 1]&(MB_TYPE_16x16|MB_TYPE_16x8)); if((s->mv[0][0][0]|s->mv[0][0][1]|s->mv[1][0][0]|s->mv[1][0][1])==0) s->mb_skiped = 1; } return 0; } switch(s->pict_type) { default: case I_TYPE: if (get_bits1(&s->gb) == 0) { if (get_bits1(&s->gb) == 0){ av_log(s->avctx, AV_LOG_ERROR, "invalid mb type in I Frame at %d %d\n", s->mb_x, s->mb_y); return -1; } mb_type = MB_TYPE_QUANT | MB_TYPE_INTRA; } else { mb_type = MB_TYPE_INTRA; } break; case P_TYPE: mb_type = get_vlc2(&s->gb, mb_ptype_vlc.table, MB_PTYPE_VLC_BITS, 1); if (mb_type < 0){ av_log(s->avctx, AV_LOG_ERROR, "invalid mb type in P Frame at %d %d\n", s->mb_x, s->mb_y); return -1; } mb_type = ptype2mb_type[ mb_type ]; break; case B_TYPE: mb_type = get_vlc2(&s->gb, mb_btype_vlc.table, MB_BTYPE_VLC_BITS, 1); if (mb_type < 0){ av_log(s->avctx, AV_LOG_ERROR, "invalid mb type in B Frame at %d %d\n", s->mb_x, s->mb_y); return -1; } mb_type = btype2mb_type[ mb_type ]; break; } dprintf("mb_type=%x\n", mb_type); // motion_type = 0; /* avoid warning */ if (IS_INTRA(mb_type)) { /* compute dct type */ if (s->picture_structure == PICT_FRAME && //FIXME add a interlaced_dct coded var? !s->frame_pred_frame_dct) { s->interlaced_dct = get_bits1(&s->gb); } if (IS_QUANT(mb_type)) s->qscale = get_qscale(s); if (s->concealment_motion_vectors) { /* just parse them */ if (s->picture_structure != PICT_FRAME) skip_bits1(&s->gb); /* field select */ s->mv[0][0][0]= s->last_mv[0][0][0]= s->last_mv[0][1][0] = mpeg_decode_motion(s, s->mpeg_f_code[0][0], s->last_mv[0][0][0]); s->mv[0][0][1]= s->last_mv[0][0][1]= s->last_mv[0][1][1] = mpeg_decode_motion(s, s->mpeg_f_code[0][1], s->last_mv[0][0][1]); skip_bits1(&s->gb); /* marker */ }else memset(s->last_mv, 0, sizeof(s->last_mv)); /* reset mv prediction */ s->mb_intra = 1; #ifdef HAVE_XVMC //one 1 we memcpy blocks in xvmcvideo if(s->avctx->xvmc_acceleration > 1){ XVMC_pack_pblocks(s,-1);//inter are always full blocks if(s->swap_uv){ exchange_uv(s); } } #endif if (s->codec_id == CODEC_ID_MPEG2VIDEO) { for(i=0;i<mb_block_count;i++) { if (mpeg2_decode_block_intra(s, s->pblocks[i], i) < 0) return -1; } } else { for(i=0;i<6;i++) { if (mpeg1_decode_block_intra(s, s->pblocks[i], i) < 0) return -1; } } } else { if (mb_type & MB_TYPE_ZERO_MV){ assert(mb_type & MB_TYPE_CBP); /* compute dct type */ if (s->picture_structure == PICT_FRAME && //FIXME add a interlaced_dct coded var? !s->frame_pred_frame_dct) { s->interlaced_dct = get_bits1(&s->gb); } if (IS_QUANT(mb_type)) s->qscale = get_qscale(s); s->mv_dir = MV_DIR_FORWARD; if(s->picture_structure == PICT_FRAME) s->mv_type = MV_TYPE_16X16; else{ s->mv_type = MV_TYPE_FIELD; mb_type |= MB_TYPE_INTERLACED; s->field_select[0][0]= s->picture_structure - 1; } s->last_mv[0][0][0] = 0; s->last_mv[0][0][1] = 0; s->last_mv[0][1][0] = 0; s->last_mv[0][1][1] = 0; s->mv[0][0][0] = 0; s->mv[0][0][1] = 0; }else{ assert(mb_type & MB_TYPE_L0L1); //FIXME decide if MBs in field pictures are MB_TYPE_INTERLACED /* get additionnal motion vector type */ if (s->frame_pred_frame_dct) motion_type = MT_FRAME; else{ motion_type = get_bits(&s->gb, 2); } /* compute dct type */ if (s->picture_structure == PICT_FRAME && //FIXME add a interlaced_dct coded var? !s->frame_pred_frame_dct && HAS_CBP(mb_type)) { s->interlaced_dct = get_bits1(&s->gb); } if (IS_QUANT(mb_type)) s->qscale = get_qscale(s); /* motion vectors */ s->mv_dir = 0; for(i=0;i<2;i++) { if (USES_LIST(mb_type, i)) { s->mv_dir |= (MV_DIR_FORWARD >> i); dprintf("motion_type=%d\n", motion_type); switch(motion_type) { case MT_FRAME: /* or MT_16X8 */ if (s->picture_structure == PICT_FRAME) { /* MT_FRAME */ mb_type |= MB_TYPE_16x16; s->mv_type = MV_TYPE_16X16; s->mv[i][0][0]= s->last_mv[i][0][0]= s->last_mv[i][1][0] = mpeg_decode_motion(s, s->mpeg_f_code[i][0], s->last_mv[i][0][0]); s->mv[i][0][1]= s->last_mv[i][0][1]= s->last_mv[i][1][1] = mpeg_decode_motion(s, s->mpeg_f_code[i][1], s->last_mv[i][0][1]); /* full_pel: only for mpeg1 */ if (s->full_pel[i]){ s->mv[i][0][0] <<= 1; s->mv[i][0][1] <<= 1; } } else { /* MT_16X8 */ mb_type |= MB_TYPE_16x8 | MB_TYPE_INTERLACED; s->mv_type = MV_TYPE_16X8; for(j=0;j<2;j++) { s->field_select[i][j] = get_bits1(&s->gb); for(k=0;k<2;k++) { val = mpeg_decode_motion(s, s->mpeg_f_code[i][k], s->last_mv[i][j][k]); s->last_mv[i][j][k] = val; s->mv[i][j][k] = val; } } } break; case MT_FIELD: s->mv_type = MV_TYPE_FIELD; if (s->picture_structure == PICT_FRAME) { mb_type |= MB_TYPE_16x8 | MB_TYPE_INTERLACED; for(j=0;j<2;j++) { s->field_select[i][j] = get_bits1(&s->gb); val = mpeg_decode_motion(s, s->mpeg_f_code[i][0], s->last_mv[i][j][0]); s->last_mv[i][j][0] = val; s->mv[i][j][0] = val; dprintf("fmx=%d\n", val); val = mpeg_decode_motion(s, s->mpeg_f_code[i][1], s->last_mv[i][j][1] >> 1); s->last_mv[i][j][1] = val << 1; s->mv[i][j][1] = val; dprintf("fmy=%d\n", val); } } else { mb_type |= MB_TYPE_16x16 | MB_TYPE_INTERLACED; s->field_select[i][0] = get_bits1(&s->gb); for(k=0;k<2;k++) { val = mpeg_decode_motion(s, s->mpeg_f_code[i][k], s->last_mv[i][0][k]); s->last_mv[i][0][k] = val; s->last_mv[i][1][k] = val; s->mv[i][0][k] = val; } } break; case MT_DMV: { int dmx, dmy, mx, my, m; mx = mpeg_decode_motion(s, s->mpeg_f_code[i][0], s->last_mv[i][0][0]); s->last_mv[i][0][0] = mx; s->last_mv[i][1][0] = mx; dmx = get_dmv(s); my = mpeg_decode_motion(s, s->mpeg_f_code[i][1], s->last_mv[i][0][1] >> 1); dmy = get_dmv(s); s->mv_type = MV_TYPE_DMV; s->last_mv[i][0][1] = my<<1; s->last_mv[i][1][1] = my<<1; s->mv[i][0][0] = mx; s->mv[i][0][1] = my; s->mv[i][1][0] = mx;//not used s->mv[i][1][1] = my;//not used if (s->picture_structure == PICT_FRAME) { mb_type |= MB_TYPE_16x16 | MB_TYPE_INTERLACED; //m = 1 + 2 * s->top_field_first; m = s->top_field_first ? 1 : 3; /* top -> top pred */ s->mv[i][2][0] = ((mx * m + (mx > 0)) >> 1) + dmx; s->mv[i][2][1] = ((my * m + (my > 0)) >> 1) + dmy - 1; m = 4 - m; s->mv[i][3][0] = ((mx * m + (mx > 0)) >> 1) + dmx; s->mv[i][3][1] = ((my * m + (my > 0)) >> 1) + dmy + 1; } else { mb_type |= MB_TYPE_16x16; s->mv[i][2][0] = ((mx + (mx > 0)) >> 1) + dmx; s->mv[i][2][1] = ((my + (my > 0)) >> 1) + dmy; if(s->picture_structure == PICT_TOP_FIELD) s->mv[i][2][1]--; else s->mv[i][2][1]++; } } break; default: av_log(s->avctx, AV_LOG_ERROR, "00 motion_type at %d %d\n", s->mb_x, s->mb_y); return -1; } } } } s->mb_intra = 0; if (HAS_CBP(mb_type)) { cbp = get_vlc2(&s->gb, mb_pat_vlc.table, MB_PAT_VLC_BITS, 1); if (cbp < 0 || ((cbp == 0) && (s->chroma_format < 2)) ){ av_log(s->avctx, AV_LOG_ERROR, "invalid cbp at %d %d\n", s->mb_x, s->mb_y); return -1; } if(mb_block_count > 6){ cbp<<= mb_block_count-6; cbp |= get_bits(&s->gb, mb_block_count-6); } #ifdef HAVE_XVMC //on 1 we memcpy blocks in xvmcvideo if(s->avctx->xvmc_acceleration > 1){ XVMC_pack_pblocks(s,cbp); if(s->swap_uv){ exchange_uv(s); } } #endif if (s->codec_id == CODEC_ID_MPEG2VIDEO) { if(s->flags2 & CODEC_FLAG2_FAST){ for(i=0;i<6;i++) { if(cbp & 32) { mpeg2_fast_decode_block_non_intra(s, s->pblocks[i], i); } else { s->block_last_index[i] = -1; } cbp+=cbp; } }else{ cbp<<= 12-mb_block_count; for(i=0;i<mb_block_count;i++) { if ( cbp & (1<<11) ) { if (mpeg2_decode_block_non_intra(s, s->pblocks[i], i) < 0) return -1; } else { s->block_last_index[i] = -1; } cbp+=cbp; } } } else { if(s->flags2 & CODEC_FLAG2_FAST){ for(i=0;i<6;i++) { if (cbp & 32) { mpeg1_fast_decode_block_inter(s, s->pblocks[i], i); } else { s->block_last_index[i] = -1; } cbp+=cbp; } }else{ for(i=0;i<6;i++) { if (cbp & 32) { if (mpeg1_decode_block_inter(s, s->pblocks[i], i) < 0) return -1; } else { s->block_last_index[i] = -1; } cbp+=cbp; } } } }else{ for(i=0;i<6;i++) s->block_last_index[i] = -1; } } s->current_picture.mb_type[ s->mb_x + s->mb_y*s->mb_stride ]= mb_type; return 0; }


void op_subo (void) { target_ulong tmp; tmp = T0; T0 = (int32_t)T0 - (int32_t)T1; if (!((T0 >> 31) ^ (T1 >> 31) ^ (tmp >> 31))) { CALL_FROM_TB1(do_raise_exception_direct, EXCP_OVERFLOW); } RETURN(); }


int get_physical_address (CPUState *env, mmu_ctx_t *ctx, target_ulong eaddr, int rw, int access_type, int check_BATs) { int ret; #if 0 if (loglevel != 0) { fprintf(logfile, "%s\n", __func__); } #endif if ((access_type == ACCESS_CODE && msr_ir == 0) || (access_type != ACCESS_CODE && msr_dr == 0)) { /* No address translation */ ret = check_physical(env, ctx, eaddr, rw); } else { ret = -1; switch (env->mmu_model) { case POWERPC_MMU_32B: case POWERPC_MMU_SOFT_6xx: case POWERPC_MMU_SOFT_74xx: /* Try to find a BAT */ if (check_BATs) ret = get_bat(env, ctx, eaddr, rw, access_type); /* No break here */ #if defined(TARGET_PPC64) case POWERPC_MMU_64B: case POWERPC_MMU_64BRIDGE: #endif if (ret < 0) { /* We didn't match any BAT entry or don't have BATs */ ret = get_segment(env, ctx, eaddr, rw, access_type); } break; case POWERPC_MMU_SOFT_4xx: case POWERPC_MMU_SOFT_4xx_Z: ret = mmu40x_get_physical_address(env, ctx, eaddr, rw, access_type); break; case POWERPC_MMU_601: /* XXX: TODO */ cpu_abort(env, "601 MMU model not implemented\n"); return -1; case POWERPC_MMU_BOOKE: ret = mmubooke_get_physical_address(env, ctx, eaddr, rw, access_type); break; case POWERPC_MMU_BOOKE_FSL: /* XXX: TODO */ cpu_abort(env, "BookE FSL MMU model not implemented\n"); return -1; case POWERPC_MMU_REAL_4xx: cpu_abort(env, "PowerPC 401 does not do any translation\n"); return -1; default: cpu_abort(env, "Unknown or invalid MMU model\n"); return -1; } } #if 0 if (loglevel != 0) { fprintf(logfile, "%s address " ADDRX " => %d " PADDRX "\n", __func__, eaddr, ret, ctx->raddr); } #endif return ret; }


uint32_t HELPER(neon_min_f32)(uint32_t a, uint32_t b) { float32 f0 = make_float32(a); float32 f1 = make_float32(b); return (float32_compare_quiet(f0, f1, NFS) == -1) ? a : b; }


static void test_primitive_lists(gconstpointer opaque) { TestArgs *args = (TestArgs *) opaque; const SerializeOps *ops = args->ops; PrimitiveType *pt = args->test_data; PrimitiveList pl = { .value = { NULL } }; PrimitiveList pl_copy = { .value = { NULL } }; PrimitiveList *pl_copy_ptr = &pl_copy; Error *err = NULL; void *serialize_data; void *cur_head = NULL; int i; pl.type = pl_copy.type = pt->type; /* build up our list of primitive types */ for (i = 0; i < 32; i++) { switch (pl.type) { case PTYPE_STRING: { strList *tmp = g_new0(strList, 1); tmp->value = g_strdup(pt->value.string); if (pl.value.strings == NULL) { pl.value.strings = tmp; } else { tmp->next = pl.value.strings; pl.value.strings = tmp; } break; } case PTYPE_INTEGER: { intList *tmp = g_new0(intList, 1); tmp->value = pt->value.integer; if (pl.value.integers == NULL) { pl.value.integers = tmp; } else { tmp->next = pl.value.integers; pl.value.integers = tmp; } break; } case PTYPE_S8: { int8List *tmp = g_new0(int8List, 1); tmp->value = pt->value.s8; if (pl.value.s8_integers == NULL) { pl.value.s8_integers = tmp; } else { tmp->next = pl.value.s8_integers; pl.value.s8_integers = tmp; } break; } case PTYPE_S16: { int16List *tmp = g_new0(int16List, 1); tmp->value = pt->value.s16; if (pl.value.s16_integers == NULL) { pl.value.s16_integers = tmp; } else { tmp->next = pl.value.s16_integers; pl.value.s16_integers = tmp; } break; } case PTYPE_S32: { int32List *tmp = g_new0(int32List, 1); tmp->value = pt->value.s32; if (pl.value.s32_integers == NULL) { pl.value.s32_integers = tmp; } else { tmp->next = pl.value.s32_integers; pl.value.s32_integers = tmp; } break; } case PTYPE_S64: { int64List *tmp = g_new0(int64List, 1); tmp->value = pt->value.s64; if (pl.value.s64_integers == NULL) { pl.value.s64_integers = tmp; } else { tmp->next = pl.value.s64_integers; pl.value.s64_integers = tmp; } break; } case PTYPE_U8: { uint8List *tmp = g_new0(uint8List, 1); tmp->value = pt->value.u8; if (pl.value.u8_integers == NULL) { pl.value.u8_integers = tmp; } else { tmp->next = pl.value.u8_integers; pl.value.u8_integers = tmp; } break; } case PTYPE_U16: { uint16List *tmp = g_new0(uint16List, 1); tmp->value = pt->value.u16; if (pl.value.u16_integers == NULL) { pl.value.u16_integers = tmp; } else { tmp->next = pl.value.u16_integers; pl.value.u16_integers = tmp; } break; } case PTYPE_U32: { uint32List *tmp = g_new0(uint32List, 1); tmp->value = pt->value.u32; if (pl.value.u32_integers == NULL) { pl.value.u32_integers = tmp; } else { tmp->next = pl.value.u32_integers; pl.value.u32_integers = tmp; } break; } case PTYPE_U64: { uint64List *tmp = g_new0(uint64List, 1); tmp->value = pt->value.u64; if (pl.value.u64_integers == NULL) { pl.value.u64_integers = tmp; } else { tmp->next = pl.value.u64_integers; pl.value.u64_integers = tmp; } break; } case PTYPE_NUMBER: { numberList *tmp = g_new0(numberList, 1); tmp->value = pt->value.number; if (pl.value.numbers == NULL) { pl.value.numbers = tmp; } else { tmp->next = pl.value.numbers; pl.value.numbers = tmp; } break; } case PTYPE_BOOLEAN: { boolList *tmp = g_new0(boolList, 1); tmp->value = pt->value.boolean; if (pl.value.booleans == NULL) { pl.value.booleans = tmp; } else { tmp->next = pl.value.booleans; pl.value.booleans = tmp; } break; } default: g_assert_not_reached(); } } ops->serialize((void **)&pl, &serialize_data, visit_primitive_list, &err); ops->deserialize((void **)&pl_copy_ptr, serialize_data, visit_primitive_list, &err); g_assert(err == NULL); i = 0; /* compare our deserialized list of primitives to the original */ do { switch (pl_copy.type) { case PTYPE_STRING: { strList *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.strings; } g_assert_cmpstr(pt->value.string, ==, ptr->value); break; } case PTYPE_INTEGER: { intList *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.integers; } g_assert_cmpint(pt->value.integer, ==, ptr->value); break; } case PTYPE_S8: { int8List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.s8_integers; } g_assert_cmpint(pt->value.s8, ==, ptr->value); break; } case PTYPE_S16: { int16List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.s16_integers; } g_assert_cmpint(pt->value.s16, ==, ptr->value); break; } case PTYPE_S32: { int32List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.s32_integers; } g_assert_cmpint(pt->value.s32, ==, ptr->value); break; } case PTYPE_S64: { int64List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.s64_integers; } g_assert_cmpint(pt->value.s64, ==, ptr->value); break; } case PTYPE_U8: { uint8List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.u8_integers; } g_assert_cmpint(pt->value.u8, ==, ptr->value); break; } case PTYPE_U16: { uint16List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.u16_integers; } g_assert_cmpint(pt->value.u16, ==, ptr->value); break; } case PTYPE_U32: { uint32List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.u32_integers; } g_assert_cmpint(pt->value.u32, ==, ptr->value); break; } case PTYPE_U64: { uint64List *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.u64_integers; } g_assert_cmpint(pt->value.u64, ==, ptr->value); break; } case PTYPE_NUMBER: { numberList *ptr; GString *double_expected = g_string_new(""); GString *double_actual = g_string_new(""); if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.numbers; } /* we serialize with %f for our reference visitors, so rather than * fuzzy floating math to test "equality", just compare the * formatted values */ g_string_printf(double_expected, "%.6f", pt->value.number); g_string_printf(double_actual, "%.6f", ptr->value); g_assert_cmpstr(double_actual->str, ==, double_expected->str); g_string_free(double_expected, true); g_string_free(double_actual, true); break; } case PTYPE_BOOLEAN: { boolList *ptr; if (cur_head) { ptr = cur_head; cur_head = ptr->next; } else { cur_head = ptr = pl_copy.value.booleans; } g_assert_cmpint(!!pt->value.boolean, ==, !!ptr->value); break; } default: g_assert_not_reached(); } i++; } while (cur_head); g_assert_cmpint(i, ==, 33); ops->cleanup(serialize_data); dealloc_helper(&pl, visit_primitive_list, &err); g_assert(!err); dealloc_helper(&pl_copy, visit_primitive_list, &err); g_assert(!err); g_free(args); }


static struct omap_pwl_s *omap_pwl_init(MemoryRegion *system_memory, target_phys_addr_t base, omap_clk clk) { struct omap_pwl_s *s = g_malloc0(sizeof(*s)); omap_pwl_reset(s); memory_region_init_io(&s->iomem, &omap_pwl_ops, s, "omap-pwl", 0x800); memory_region_add_subregion(system_memory, base, &s->iomem); omap_clk_adduser(clk, qemu_allocate_irqs(omap_pwl_clk_update, s, 1)[0]); return s; }


static void gem_transmit(GemState *s) { unsigned desc[2]; target_phys_addr_t packet_desc_addr; uint8_t tx_packet[2048]; uint8_t *p; unsigned total_bytes; /* Do nothing if transmit is not enabled. */ if (!(s->regs[GEM_NWCTRL] & GEM_NWCTRL_TXENA)) { return; } DB_PRINT("\n"); /* The packet we will hand off to qemu. * Packets scattered across multiple descriptors are gathered to this * one contiguous buffer first. */ p = tx_packet; total_bytes = 0; /* read current descriptor */ packet_desc_addr = s->tx_desc_addr; cpu_physical_memory_read(packet_desc_addr, (uint8_t *)&desc[0], sizeof(desc)); /* Handle all descriptors owned by hardware */ while (tx_desc_get_used(desc) == 0) { /* Do nothing if transmit is not enabled. */ if (!(s->regs[GEM_NWCTRL] & GEM_NWCTRL_TXENA)) { return; } print_gem_tx_desc(desc); /* The real hardware would eat this (and possibly crash). * For QEMU let's lend a helping hand. */ if ((tx_desc_get_buffer(desc) == 0) || (tx_desc_get_length(desc) == 0)) { DB_PRINT("Invalid TX descriptor @ 0x%x\n", packet_desc_addr); break; } /* Gather this fragment of the packet from "dma memory" to our contig. * buffer. */ cpu_physical_memory_read(tx_desc_get_buffer(desc), p, tx_desc_get_length(desc)); p += tx_desc_get_length(desc); total_bytes += tx_desc_get_length(desc); /* Last descriptor for this packet; hand the whole thing off */ if (tx_desc_get_last(desc)) { /* Modify the 1st descriptor of this packet to be owned by * the processor. */ cpu_physical_memory_read(s->tx_desc_addr, (uint8_t *)&desc[0], sizeof(desc)); tx_desc_set_used(desc); cpu_physical_memory_write(s->tx_desc_addr, (uint8_t *)&desc[0], sizeof(desc)); /* Advance the hardare current descriptor past this packet */ if (tx_desc_get_wrap(desc)) { s->tx_desc_addr = s->regs[GEM_TXQBASE]; } else { s->tx_desc_addr = packet_desc_addr + 8; } DB_PRINT("TX descriptor next: 0x%08x\n", s->tx_desc_addr); s->regs[GEM_TXSTATUS] |= GEM_TXSTATUS_TXCMPL; /* Handle interrupt consequences */ gem_update_int_status(s); /* Is checksum offload enabled? */ if (s->regs[GEM_DMACFG] & GEM_DMACFG_TXCSUM_OFFL) { net_checksum_calculate(tx_packet, total_bytes); } /* Update MAC statistics */ gem_transmit_updatestats(s, tx_packet, total_bytes); /* Send the packet somewhere */ if (s->phy_loop) { gem_receive(&s->nic->nc, tx_packet, total_bytes); } else { qemu_send_packet(&s->nic->nc, tx_packet, total_bytes); } /* Prepare for next packet */ p = tx_packet; total_bytes = 0; } /* read next descriptor */ if (tx_desc_get_wrap(desc)) { packet_desc_addr = s->regs[GEM_TXQBASE]; } else { packet_desc_addr += 8; } cpu_physical_memory_read(packet_desc_addr, (uint8_t *)&desc[0], sizeof(desc)); } if (tx_desc_get_used(desc)) { s->regs[GEM_TXSTATUS] |= GEM_TXSTATUS_USED; gem_update_int_status(s); } }


static void rx_init_frame(eTSEC *etsec, const uint8_t *buf, size_t size) { uint32_t fcb_size = 0; uint8_t prsdep = (etsec->regs[RCTRL].value >> RCTRL_PRSDEP_OFFSET) & RCTRL_PRSDEP_MASK; if (prsdep != 0) { /* Prepend FCB (FCB size + RCTRL[PAL]) */ fcb_size = 8 + ((etsec->regs[RCTRL].value >> 16) & 0x1F); etsec->rx_fcb_size = fcb_size; /* TODO: fill_FCB(etsec); */ memset(etsec->rx_fcb, 0x0, sizeof(etsec->rx_fcb)); } else { etsec->rx_fcb_size = 0; } if (etsec->rx_buffer != NULL) { g_free(etsec->rx_buffer); } /* Do not copy the frame for now */ etsec->rx_buffer = (uint8_t *)buf; etsec->rx_buffer_len = size; /* CRC padding (We don't have to compute the CRC) */ etsec->rx_padding = 4; etsec->rx_first_in_frame = 1; etsec->rx_remaining_data = etsec->rx_buffer_len; RING_DEBUG("%s: rx_buffer_len:%u rx_padding+crc:%u\n", __func__, etsec->rx_buffer_len, etsec->rx_padding); }


static uint32_t qpci_spapr_io_readl(QPCIBus *bus, void *addr) { QPCIBusSPAPR *s = container_of(bus, QPCIBusSPAPR, bus); uint64_t port = (uintptr_t)addr; uint32_t v; if (port < s->pio.size) { v = readl(s->pio_cpu_base + port); } else { v = readl(s->mmio_cpu_base + port); } return bswap32(v); }


void cpu_io_recompile(CPUState *cpu, uintptr_t retaddr) { #if defined(TARGET_MIPS) || defined(TARGET_SH4) CPUArchState *env = cpu->env_ptr; #endif TranslationBlock *tb; uint32_t n, cflags; target_ulong pc, cs_base; uint32_t flags; tb_lock(); tb = tb_find_pc(retaddr); if (!tb) { cpu_abort(cpu, "cpu_io_recompile: could not find TB for pc=%p", (void *)retaddr); } n = cpu->icount_decr.u16.low + tb->icount; cpu_restore_state_from_tb(cpu, tb, retaddr); /* Calculate how many instructions had been executed before the fault occurred. */ n = n - cpu->icount_decr.u16.low; /* Generate a new TB ending on the I/O insn. */ n++; /* On MIPS and SH, delay slot instructions can only be restarted if they were already the first instruction in the TB. If this is not the first instruction in a TB then re-execute the preceding branch. */ #if defined(TARGET_MIPS) if ((env->hflags & MIPS_HFLAG_BMASK) != 0 && n > 1) { env->active_tc.PC -= (env->hflags & MIPS_HFLAG_B16 ? 2 : 4); cpu->icount_decr.u16.low++; env->hflags &= ~MIPS_HFLAG_BMASK; } #elif defined(TARGET_SH4) if ((env->flags & ((DELAY_SLOT | DELAY_SLOT_CONDITIONAL))) != 0 && n > 1) { env->pc -= 2; cpu->icount_decr.u16.low++; env->flags &= ~(DELAY_SLOT | DELAY_SLOT_CONDITIONAL); } #endif /* This should never happen. */ if (n > CF_COUNT_MASK) { cpu_abort(cpu, "TB too big during recompile"); } cflags = n | CF_LAST_IO; cflags |= curr_cflags(); pc = tb->pc; cs_base = tb->cs_base; flags = tb->flags; tb_phys_invalidate(tb, -1); if (tb->cflags & CF_NOCACHE) { if (tb->orig_tb) { /* Invalidate original TB if this TB was generated in * cpu_exec_nocache() */ tb_phys_invalidate(tb->orig_tb, -1); } tb_free(tb); } /* FIXME: In theory this could raise an exception. In practice we have already translated the block once so it's probably ok. */ tb_gen_code(cpu, pc, cs_base, flags, cflags); /* TODO: If env->pc != tb->pc (i.e. the faulting instruction was not * the first in the TB) then we end up generating a whole new TB and * repeating the fault, which is horribly inefficient. * Better would be to execute just this insn uncached, or generate a * second new TB. * * cpu_loop_exit_noexc will longjmp back to cpu_exec where the * tb_lock gets reset. */ cpu_loop_exit_noexc(cpu); }


START_TEST(unterminated_array) { QObject *obj = qobject_from_json("[32"); fail_unless(obj == NULL); }


static void imx_fec_reset(DeviceState *d) { IMXFECState *s = IMX_FEC(d); /* Reset the FEC */ s->eir = 0; s->eimr = 0; s->rx_enabled = 0; s->ecr = 0; s->mscr = 0; s->mibc = 0xc0000000; s->rcr = 0x05ee0001; s->tcr = 0; s->tfwr = 0; s->frsr = 0x500; s->miigsk_cfgr = 0; s->miigsk_enr = 0x6; /* We also reset the PHY */ phy_reset(s); }


struct omap_mmc_s *omap2_mmc_init(struct omap_target_agent_s *ta, BlockDriverState *bd, qemu_irq irq, qemu_irq dma[], omap_clk fclk, omap_clk iclk) { struct omap_mmc_s *s = (struct omap_mmc_s *) g_malloc0(sizeof(struct omap_mmc_s)); s->irq = irq; s->dma = dma; s->clk = fclk; s->lines = 4; s->rev = 2; omap_mmc_reset(s); memory_region_init_io(&s->iomem, NULL, &omap_mmc_ops, s, "omap.mmc", omap_l4_region_size(ta, 0)); omap_l4_attach(ta, 0, &s->iomem); /* Instantiate the storage */ s->card = sd_init(bd, false); if (s->card == NULL) { exit(1); } s->cdet = qemu_allocate_irq(omap_mmc_cover_cb, s, 0); sd_set_cb(s->card, NULL, s->cdet); return s; }


int vmstate_register(int instance_id, const VMStateDescription *vmsd, void *opaque) { SaveStateEntry *se; se = qemu_malloc(sizeof(SaveStateEntry)); pstrcpy(se->idstr, sizeof(se->idstr), vmsd->name); se->version_id = vmsd->version_id; se->section_id = global_section_id++; se->save_live_state = NULL; se->save_state = NULL; se->load_state = NULL; se->opaque = opaque; se->vmsd = vmsd; if (instance_id == -1) { se->instance_id = calculate_new_instance_id(vmsd->name); } else { se->instance_id = instance_id; } /* add at the end of list */ TAILQ_INSERT_TAIL(&savevm_handlers, se, entry); return 0; }


bool qemu_clock_expired(QEMUClockType type) { return timerlist_expired( main_loop_tlg.tl[type]); }


static int proxy_opendir(FsContext *ctx, V9fsPath *fs_path, V9fsFidOpenState *fs) { int serrno, fd; fs->dir = NULL; fd = v9fs_request(ctx->private, T_OPEN, NULL, "sd", fs_path, O_DIRECTORY); if (fd < 0) { errno = -fd; return -1; } fs->dir = fdopendir(fd); if (!fs->dir) { serrno = errno; close(fd); errno = serrno; return -1; } return 0; }


static sd_rsp_type_t sd_normal_command(SDState *sd, SDRequest req) { uint32_t rca = 0x0000; uint64_t addr = (sd->ocr & (1 << 30)) ? (uint64_t) req.arg << 9 : req.arg; /* Not interpreting this as an app command */ sd->card_status &= ~APP_CMD; if (sd_cmd_type[req.cmd] == sd_ac || sd_cmd_type[req.cmd] == sd_adtc) rca = req.arg >> 16; DPRINTF("CMD%d 0x%08x state %d\n", req.cmd, req.arg, sd->state); switch (req.cmd) { /* Basic commands (Class 0 and Class 1) */ case 0: /* CMD0: GO_IDLE_STATE */ switch (sd->state) { case sd_inactive_state: return sd->spi ? sd_r1 : sd_r0; default: sd->state = sd_idle_state; sd_reset(sd, sd->bdrv); return sd->spi ? sd_r1 : sd_r0; } break; case 1: /* CMD1: SEND_OP_CMD */ if (!sd->spi) goto bad_cmd; sd->state = sd_transfer_state; return sd_r1; case 2: /* CMD2: ALL_SEND_CID */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_ready_state: sd->state = sd_identification_state; return sd_r2_i; default: break; } break; case 3: /* CMD3: SEND_RELATIVE_ADDR */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_identification_state: case sd_standby_state: sd->state = sd_standby_state; sd_set_rca(sd); return sd_r6; default: break; } break; case 4: /* CMD4: SEND_DSR */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_standby_state: break; default: break; } break; case 5: /* CMD5: reserved for SDIO cards */ return sd_illegal; case 6: /* CMD6: SWITCH_FUNCTION */ if (sd->spi) goto bad_cmd; switch (sd->mode) { case sd_data_transfer_mode: sd_function_switch(sd, req.arg); sd->state = sd_sendingdata_state; sd->data_start = 0; sd->data_offset = 0; return sd_r1; default: break; } break; case 7: /* CMD7: SELECT/DESELECT_CARD */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_standby_state: if (sd->rca != rca) return sd_r0; sd->state = sd_transfer_state; return sd_r1b; case sd_transfer_state: case sd_sendingdata_state: if (sd->rca == rca) break; sd->state = sd_standby_state; return sd_r1b; case sd_disconnect_state: if (sd->rca != rca) return sd_r0; sd->state = sd_programming_state; return sd_r1b; case sd_programming_state: if (sd->rca == rca) break; sd->state = sd_disconnect_state; return sd_r1b; default: break; } break; case 8: /* CMD8: SEND_IF_COND */ /* Physical Layer Specification Version 2.00 command */ switch (sd->state) { case sd_idle_state: sd->vhs = 0; /* No response if not exactly one VHS bit is set. */ if (!(req.arg >> 8) || (req.arg >> ffs(req.arg & ~0xff))) return sd->spi ? sd_r7 : sd_r0; /* Accept. */ sd->vhs = req.arg; return sd_r7; default: break; } break; case 9: /* CMD9: SEND_CSD */ switch (sd->state) { case sd_standby_state: if (sd->rca != rca) return sd_r0; return sd_r2_s; case sd_transfer_state: if (!sd->spi) break; sd->state = sd_sendingdata_state; memcpy(sd->data, sd->csd, 16); sd->data_start = addr; sd->data_offset = 0; return sd_r1; default: break; } break; case 10: /* CMD10: SEND_CID */ switch (sd->state) { case sd_standby_state: if (sd->rca != rca) return sd_r0; return sd_r2_i; case sd_transfer_state: if (!sd->spi) break; sd->state = sd_sendingdata_state; memcpy(sd->data, sd->cid, 16); sd->data_start = addr; sd->data_offset = 0; return sd_r1; default: break; } break; case 11: /* CMD11: READ_DAT_UNTIL_STOP */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_transfer_state: sd->state = sd_sendingdata_state; sd->data_start = req.arg; sd->data_offset = 0; if (sd->data_start + sd->blk_len > sd->size) sd->card_status |= ADDRESS_ERROR; return sd_r0; default: break; } break; case 12: /* CMD12: STOP_TRANSMISSION */ switch (sd->state) { case sd_sendingdata_state: sd->state = sd_transfer_state; return sd_r1b; case sd_receivingdata_state: sd->state = sd_programming_state; /* Bzzzzzzztt .... Operation complete. */ sd->state = sd_transfer_state; return sd_r1b; default: break; } break; case 13: /* CMD13: SEND_STATUS */ switch (sd->mode) { case sd_data_transfer_mode: if (sd->rca != rca) return sd_r0; return sd_r1; default: break; } break; case 15: /* CMD15: GO_INACTIVE_STATE */ if (sd->spi) goto bad_cmd; switch (sd->mode) { case sd_data_transfer_mode: if (sd->rca != rca) return sd_r0; sd->state = sd_inactive_state; return sd_r0; default: break; } break; /* Block read commands (Classs 2) */ case 16: /* CMD16: SET_BLOCKLEN */ switch (sd->state) { case sd_transfer_state: if (req.arg > (1 << HWBLOCK_SHIFT)) sd->card_status |= BLOCK_LEN_ERROR; else sd->blk_len = req.arg; return sd_r1; default: break; } break; case 17: /* CMD17: READ_SINGLE_BLOCK */ switch (sd->state) { case sd_transfer_state: sd->state = sd_sendingdata_state; sd->data_start = addr; sd->data_offset = 0; if (sd->data_start + sd->blk_len > sd->size) sd->card_status |= ADDRESS_ERROR; return sd_r1; default: break; } break; case 18: /* CMD18: READ_MULTIPLE_BLOCK */ switch (sd->state) { case sd_transfer_state: sd->state = sd_sendingdata_state; sd->data_start = addr; sd->data_offset = 0; if (sd->data_start + sd->blk_len > sd->size) sd->card_status |= ADDRESS_ERROR; return sd_r1; default: break; } break; /* Block write commands (Class 4) */ case 24: /* CMD24: WRITE_SINGLE_BLOCK */ if (sd->spi) goto unimplemented_cmd; switch (sd->state) { case sd_transfer_state: /* Writing in SPI mode not implemented. */ if (sd->spi) break; sd->state = sd_receivingdata_state; sd->data_start = addr; sd->data_offset = 0; sd->blk_written = 0; if (sd->data_start + sd->blk_len > sd->size) sd->card_status |= ADDRESS_ERROR; if (sd_wp_addr(sd, sd->data_start)) sd->card_status |= WP_VIOLATION; if (sd->csd[14] & 0x30) sd->card_status |= WP_VIOLATION; return sd_r1; default: break; } break; case 25: /* CMD25: WRITE_MULTIPLE_BLOCK */ if (sd->spi) goto unimplemented_cmd; switch (sd->state) { case sd_transfer_state: /* Writing in SPI mode not implemented. */ if (sd->spi) break; sd->state = sd_receivingdata_state; sd->data_start = addr; sd->data_offset = 0; sd->blk_written = 0; if (sd->data_start + sd->blk_len > sd->size) sd->card_status |= ADDRESS_ERROR; if (sd_wp_addr(sd, sd->data_start)) sd->card_status |= WP_VIOLATION; if (sd->csd[14] & 0x30) sd->card_status |= WP_VIOLATION; return sd_r1; default: break; } break; case 26: /* CMD26: PROGRAM_CID */ if (sd->spi) goto bad_cmd; switch (sd->state) { case sd_transfer_state: sd->state = sd_receivingdata_state; sd->data_start = 0; sd->data_offset = 0; return sd_r1; default: break; } break; case 27: /* CMD27: PROGRAM_CSD */ if (sd->spi) goto unimplemented_cmd; switch (sd->state) { case sd_transfer_state: sd->state = sd_receivingdata_state; sd->data_start = 0; sd->data_offset = 0; return sd_r1; default: break; } break; /* Write protection (Class 6) */ case 28: /* CMD28: SET_WRITE_PROT */ switch (sd->state) { case sd_transfer_state: if (addr >= sd->size) { sd->card_status |= ADDRESS_ERROR; return sd_r1b; } sd->state = sd_programming_state; set_bit(sd_addr_to_wpnum(addr), sd->wp_groups); /* Bzzzzzzztt .... Operation complete. */ sd->state = sd_transfer_state; return sd_r1b; default: break; } break; case 29: /* CMD29: CLR_WRITE_PROT */ switch (sd->state) { case sd_transfer_state: if (addr >= sd->size) { sd->card_status |= ADDRESS_ERROR; return sd_r1b; } sd->state = sd_programming_state; clear_bit(sd_addr_to_wpnum(addr), sd->wp_groups); /* Bzzzzzzztt .... Operation complete. */ sd->state = sd_transfer_state; return sd_r1b; default: break; } break; case 30: /* CMD30: SEND_WRITE_PROT */ switch (sd->state) { case sd_transfer_state: sd->state = sd_sendingdata_state; *(uint32_t *) sd->data = sd_wpbits(sd, req.arg); sd->data_start = addr; sd->data_offset = 0; return sd_r1b; default: break; } break; /* Erase commands (Class 5) */ case 32: /* CMD32: ERASE_WR_BLK_START */ switch (sd->state) { case sd_transfer_state: sd->erase_start = req.arg; return sd_r1; default: break; } break; case 33: /* CMD33: ERASE_WR_BLK_END */ switch (sd->state) { case sd_transfer_state: sd->erase_end = req.arg; return sd_r1; default: break; } break; case 38: /* CMD38: ERASE */ switch (sd->state) { case sd_transfer_state: if (sd->csd[14] & 0x30) { sd->card_status |= WP_VIOLATION; return sd_r1b; } sd->state = sd_programming_state; sd_erase(sd); /* Bzzzzzzztt .... Operation complete. */ sd->state = sd_transfer_state; return sd_r1b; default: break; } break; /* Lock card commands (Class 7) */ case 42: /* CMD42: LOCK_UNLOCK */ if (sd->spi) goto unimplemented_cmd; switch (sd->state) { case sd_transfer_state: sd->state = sd_receivingdata_state; sd->data_start = 0; sd->data_offset = 0; return sd_r1; default: break; } break; case 52: case 53: /* CMD52, CMD53: reserved for SDIO cards * (see the SDIO Simplified Specification V2.0) * Handle as illegal command but do not complain * on stderr, as some OSes may use these in their * probing for presence of an SDIO card. */ return sd_illegal; /* Application specific commands (Class 8) */ case 55: /* CMD55: APP_CMD */ if (sd->rca != rca) return sd_r0; sd->expecting_acmd = true; sd->card_status |= APP_CMD; return sd_r1; case 56: /* CMD56: GEN_CMD */ fprintf(stderr, "SD: GEN_CMD 0x%08x\n", req.arg); switch (sd->state) { case sd_transfer_state: sd->data_offset = 0; if (req.arg & 1) sd->state = sd_sendingdata_state; else sd->state = sd_receivingdata_state; return sd_r1; default: break; } break; default: bad_cmd: fprintf(stderr, "SD: Unknown CMD%i\n", req.cmd); return sd_illegal; unimplemented_cmd: /* Commands that are recognised but not yet implemented in SPI mode. */ fprintf(stderr, "SD: CMD%i not implemented in SPI mode\n", req.cmd); return sd_illegal; } fprintf(stderr, "SD: CMD%i in a wrong state\n", req.cmd); return sd_illegal; }


static void amdvi_mmio_trace(hwaddr addr, unsigned size) { uint8_t index = (addr & ~0x2000) / 8; if ((addr & 0x2000)) { /* high table */ index = index >= AMDVI_MMIO_REGS_HIGH ? AMDVI_MMIO_REGS_HIGH : index; trace_amdvi_mmio_read(amdvi_mmio_high[index], addr, size, addr & ~0x07); } else { index = index >= AMDVI_MMIO_REGS_LOW ? AMDVI_MMIO_REGS_LOW : index; trace_amdvi_mmio_read(amdvi_mmio_high[index], addr, size, addr & ~0x07); } }


void virtio_cleanup(VirtIODevice *vdev) { qemu_del_vm_change_state_handler(vdev->vmstate); g_free(vdev->config); g_free(vdev->vq); g_free(vdev->vector_queues); }