static int mov_read_trun(MOVContext *c, ByteIOContext *pb, MOVAtom atom)

{

    MOVFragment *frag = &c->fragment;

    AVStream *st = NULL;

    MOVStreamContext *sc;

    uint64_t offset;

    int64_t dts;

    int data_offset = 0;

    unsigned entries, first_sample_flags = frag->flags;

    int flags, distance, i;

    for (i = 0; i < c->fc->nb_streams; i++) {

        if (c->fc->streams[i]->id == frag->track_id) {

            st = c->fc->streams[i];

            break;

        }

    }

    if (!st) {

        av_log(c->fc, AV_LOG_ERROR, "could not find corresponding track id %d\n", frag->track_id);

        return -1;

    }

    sc = st->priv_data;

    if (sc->pseudo_stream_id+1 != frag->stsd_id)

        return 0;

    get_byte(pb); /* version */

    flags = get_be24(pb);

    entries = get_be32(pb);

    dprintf(c->fc, "flags 0x%x entries %d\n", flags, entries);

    if (flags & 0x001) data_offset        = get_be32(pb);

    if (flags & 0x004) first_sample_flags = get_be32(pb);

    if (flags & 0x800) {

        MOVStts *ctts_data;

        if ((uint64_t)entries+sc->ctts_count >= UINT_MAX/sizeof(*sc->ctts_data))

            return -1;

        ctts_data = av_realloc(sc->ctts_data,

                               (entries+sc->ctts_count)*sizeof(*sc->ctts_data));

        if (!ctts_data)

            return AVERROR(ENOMEM);

        sc->ctts_data = ctts_data;

    }

    dts = st->duration;

    offset = frag->base_data_offset + data_offset;

    distance = 0;

    dprintf(c->fc, "first sample flags 0x%x\n", first_sample_flags);

    for (i = 0; i < entries; i++) {

        unsigned sample_size = frag->size;

        int sample_flags = i ? frag->flags : first_sample_flags;

        unsigned sample_duration = frag->duration;

        int keyframe;

        if (flags & 0x100) sample_duration = get_be32(pb);

        if (flags & 0x200) sample_size     = get_be32(pb);

        if (flags & 0x400) sample_flags    = get_be32(pb);

        if (flags & 0x800) {

            sc->ctts_data[sc->ctts_count].count = 1;

            sc->ctts_data[sc->ctts_count].duration = get_be32(pb);

            sc->ctts_count++;

        }

        if ((keyframe = st->codec->codec_type == CODEC_TYPE_AUDIO ||

             (flags & 0x004 && !i && !sample_flags) || sample_flags & 0x2000000))

            distance = 0;

        av_add_index_entry(st, offset, dts, sample_size, distance,

                           keyframe ? AVINDEX_KEYFRAME : 0);

        dprintf(c->fc, "AVIndex stream %d, sample %d, offset %"PRIx64", dts %"PRId64", "

                "size %d, distance %d, keyframe %d\n", st->index, sc->sample_count+i,

                offset, dts, sample_size, distance, keyframe);

        distance++;

        assert(sample_duration % sc->time_rate == 0);

        dts += sample_duration / sc->time_rate;

        offset += sample_size;

    }

    frag->moof_offset = offset;

    sc->sample_count = st->nb_index_entries;

    st->duration = dts;

    return 0;

}


void dsputil_init_ppc(DSPContext* c, AVCodecContext *avctx)

{

    // Common optimizations whether Altivec is available or not

  switch (check_dcbzl_effect()) {

  case 32:

    c->clear_blocks = clear_blocks_dcbz32_ppc;

    break;

  case 128:

    c->clear_blocks = clear_blocks_dcbz128_ppc;

    break;

  default:

    break;

  }

#if HAVE_ALTIVEC

    if (has_altivec()) {

        mm_flags |= MM_ALTIVEC;

        // Altivec specific optimisations

        c->pix_abs16x16_x2 = pix_abs16x16_x2_altivec;

        c->pix_abs16x16_y2 = pix_abs16x16_y2_altivec;

        c->pix_abs16x16_xy2 = pix_abs16x16_xy2_altivec;

        c->pix_abs16x16 = pix_abs16x16_altivec;

        c->pix_abs8x8 = pix_abs8x8_altivec;

        c->sad[0]= sad16x16_altivec;

        c->sad[1]= sad8x8_altivec;

        c->pix_norm1 = pix_norm1_altivec;

        c->sse[1]= sse8_altivec;

        c->sse[0]= sse16_altivec;

        c->pix_sum = pix_sum_altivec;

        c->diff_pixels = diff_pixels_altivec;

        c->get_pixels = get_pixels_altivec;

// next one disabled as it's untested.

#if 0

        c->add_bytes= add_bytes_altivec;

#endif /* 0 */

        c->put_pixels_tab[0][0] = put_pixels16_altivec;

        c->avg_pixels_tab[0][0] = avg_pixels16_altivec;

// next one disabled as it's untested.

#if 0

        c->avg_pixels_tab[1][0] = avg_pixels8_altivec;

#endif /* 0 */

        c->put_pixels_tab[1][3] = put_pixels8_xy2_altivec;

        c->put_no_rnd_pixels_tab[1][3] = put_no_rnd_pixels8_xy2_altivec;

        c->put_pixels_tab[0][3] = put_pixels16_xy2_altivec;

        c->put_no_rnd_pixels_tab[0][3] = put_no_rnd_pixels16_xy2_altivec;

	c->gmc1 = gmc1_altivec;

        if ((avctx->idct_algo == FF_IDCT_AUTO) ||

                (avctx->idct_algo == FF_IDCT_ALTIVEC))

        {

            c->idct_put = idct_put_altivec;

            c->idct_add = idct_add_altivec;

#ifndef ALTIVEC_USE_REFERENCE_C_CODE

            c->idct_permutation_type = FF_TRANSPOSE_IDCT_PERM;

#else /* ALTIVEC_USE_REFERENCE_C_CODE */

            c->idct_permutation_type = FF_NO_IDCT_PERM;

#endif /* ALTIVEC_USE_REFERENCE_C_CODE */

        }

#ifdef POWERPC_TBL_PERFORMANCE_REPORT

        {

          int i;

          for (i = 0 ; i < powerpc_perf_total ; i++)

          {

            perfdata[i][powerpc_data_min] = 0xFFFFFFFFFFFFFFFF;

            perfdata[i][powerpc_data_max] = 0x0000000000000000;

            perfdata[i][powerpc_data_sum] = 0x0000000000000000;

            perfdata[i][powerpc_data_num] = 0x0000000000000000;

#ifdef POWERPC_PERF_USE_PMC

            perfdata_pmc2[i][powerpc_data_min] = 0xFFFFFFFFFFFFFFFF;

            perfdata_pmc2[i][powerpc_data_max] = 0x0000000000000000;

            perfdata_pmc2[i][powerpc_data_sum] = 0x0000000000000000;

            perfdata_pmc2[i][powerpc_data_num] = 0x0000000000000000;

            perfdata_pmc3[i][powerpc_data_min] = 0xFFFFFFFFFFFFFFFF;

            perfdata_pmc3[i][powerpc_data_max] = 0x0000000000000000;

            perfdata_pmc3[i][powerpc_data_sum] = 0x0000000000000000;

            perfdata_pmc3[i][powerpc_data_num] = 0x0000000000000000;

#endif /* POWERPC_PERF_USE_PMC */

          }

        }

#endif /* POWERPC_TBL_PERFORMANCE_REPORT */

    } else

#endif /* HAVE_ALTIVEC */

    {

        // Non-AltiVec PPC optimisations

        // ... pending ...

    }

}


static inline void RENAME(rgb24tobgr15)(const uint8_t *src, uint8_t *dst, long src_size)

{

    const uint8_t *s = src;

    const uint8_t *end;

#if COMPILE_TEMPLATE_MMX

    const uint8_t *mm_end;

#endif

    uint16_t *d = (uint16_t *)dst;

    end = s + src_size;

#if COMPILE_TEMPLATE_MMX

    __asm__ volatile(PREFETCH"    %0"::"m"(*src):"memory");

    __asm__ volatile(

        "movq          %0, %%mm7    \n\t"

        "movq          %1, %%mm6    \n\t"

        ::"m"(red_15mask),"m"(green_15mask));

    mm_end = end - 11;

    while (s < mm_end) {

        __asm__ volatile(

            PREFETCH"    32%1           \n\t"

            "movd          %1, %%mm0    \n\t"

            "movd         3%1, %%mm3    \n\t"

            "punpckldq    6%1, %%mm0    \n\t"

            "punpckldq    9%1, %%mm3    \n\t"

            "movq       %%mm0, %%mm1    \n\t"

            "movq       %%mm0, %%mm2    \n\t"

            "movq       %%mm3, %%mm4    \n\t"

            "movq       %%mm3, %%mm5    \n\t"

            "psrlq         $3, %%mm0    \n\t"

            "psrlq         $3, %%mm3    \n\t"

            "pand          %2, %%mm0    \n\t"

            "pand          %2, %%mm3    \n\t"

            "psrlq         $6, %%mm1    \n\t"

            "psrlq         $6, %%mm4    \n\t"

            "pand       %%mm6, %%mm1    \n\t"

            "pand       %%mm6, %%mm4    \n\t"

            "psrlq         $9, %%mm2    \n\t"

            "psrlq         $9, %%mm5    \n\t"

            "pand       %%mm7, %%mm2    \n\t"

            "pand       %%mm7, %%mm5    \n\t"

            "por        %%mm1, %%mm0    \n\t"

            "por        %%mm4, %%mm3    \n\t"

            "por        %%mm2, %%mm0    \n\t"

            "por        %%mm5, %%mm3    \n\t"

            "psllq        $16, %%mm3    \n\t"

            "por        %%mm3, %%mm0    \n\t"

            MOVNTQ"     %%mm0, %0       \n\t"

            :"=m"(*d):"m"(*s),"m"(blue_15mask):"memory");

        d += 4;

        s += 12;

    }

    __asm__ volatile(SFENCE:::"memory");

    __asm__ volatile(EMMS:::"memory");

#endif

    while (s < end) {

        const int b = *s++;

        const int g = *s++;

        const int r = *s++;

        *d++ = (b>>3) | ((g&0xF8)<<2) | ((r&0xF8)<<7);

    }

}


static double compute_target_delay(double delay, VideoState *is)

{

    double sync_threshold, diff;

    /* update delay to follow master synchronisation source */

    if (get_master_sync_type(is) != AV_SYNC_VIDEO_MASTER) {

        /* if video is slave, we try to correct big delays by

           duplicating or deleting a frame */

        diff = get_video_clock(is) - get_master_clock(is);

        /* skip or repeat frame. We take into account the

           delay to compute the threshold. I still don't know

           if it is the best guess */

        sync_threshold = FFMAX(AV_SYNC_THRESHOLD, delay);

        if (fabs(diff) < AV_NOSYNC_THRESHOLD) {

            if (diff <= -sync_threshold)

                delay = 0;

            else if (diff >= sync_threshold)

                delay = 2 * delay;

        }

    }

    av_dlog(NULL, "video: delay=%0.3f A-V=%f\n",

            delay, -diff);

    return delay;

}


static OutputStream *new_output_stream(OptionsContext *o, AVFormatContext *oc, enum AVMediaType type)

{

    OutputStream *ost;

    AVStream *st = avformat_new_stream(oc, NULL);

    int idx      = oc->nb_streams - 1, ret = 0;

    int64_t max_frames = INT64_MAX;

    char *bsf = NULL, *next, *codec_tag = NULL;

    AVBitStreamFilterContext *bsfc, *bsfc_prev = NULL;

    double qscale = -1;

    char *buf = NULL, *arg = NULL, *preset = NULL;

    AVIOContext *s = NULL;

    if (!st) {

        av_log(NULL, AV_LOG_FATAL, "Could not alloc stream.\n");

        exit_program(1);

    }

    if (oc->nb_streams - 1 < o->nb_streamid_map)

        st->id = o->streamid_map[oc->nb_streams - 1];

    output_streams = grow_array(output_streams, sizeof(*output_streams), &nb_output_streams,

                                nb_output_streams + 1);

    ost = &output_streams[nb_output_streams - 1];

    ost->file_index = nb_output_files;

    ost->index = idx;

    ost->st    = st;

    st->codec->codec_type = type;

    ost->enc = choose_codec(o, oc, st, type);

    if (ost->enc) {

        ost->opts  = filter_codec_opts(codec_opts, ost->enc->id, oc, st);

    }

    avcodec_get_context_defaults3(st->codec, ost->enc);

    st->codec->codec_type = type; // XXX hack, avcodec_get_context_defaults2() sets type to unknown for stream copy

    MATCH_PER_STREAM_OPT(presets, str, preset, oc, st);

    if (preset && (!(ret = get_preset_file_2(preset, ost->enc->name, &s)))) {

        do  {

            buf = get_line(s);

            if (!buf[0] || buf[0] == '#') {

                av_free(buf);

                continue;

            }

            if (!(arg = strchr(buf, '='))) {

                av_log(NULL, AV_LOG_FATAL, "Invalid line found in the preset file.\n");

                exit_program(1);

            }

            *arg++ = 0;

            av_dict_set(&ost->opts, buf, arg, AV_DICT_DONT_OVERWRITE);

            av_free(buf);

        } while (!s->eof_reached);

        avio_close(s);

    }

    if (ret) {

        av_log(NULL, AV_LOG_FATAL,

               "Preset %s specified for stream %d:%d, but could not be opened.\n",

               preset, ost->file_index, ost->index);

        exit_program(1);

    }

    MATCH_PER_STREAM_OPT(max_frames, i64, max_frames, oc, st);

    ost->max_frames = max_frames;

    MATCH_PER_STREAM_OPT(bitstream_filters, str, bsf, oc, st);

    while (bsf) {

        if (next = strchr(bsf, ','))

            *next++ = 0;

        if (!(bsfc = av_bitstream_filter_init(bsf))) {

            av_log(NULL, AV_LOG_FATAL, "Unknown bitstream filter %s\n", bsf);

            exit_program(1);

        }

        if (bsfc_prev)

            bsfc_prev->next = bsfc;

        else

            ost->bitstream_filters = bsfc;

        bsfc_prev = bsfc;

        bsf       = next;

    }

    MATCH_PER_STREAM_OPT(codec_tags, str, codec_tag, oc, st);

    if (codec_tag) {

        uint32_t tag = strtol(codec_tag, &next, 0);

        if (*next)

            tag = AV_RL32(codec_tag);

        st->codec->codec_tag = tag;

    }

    MATCH_PER_STREAM_OPT(qscale, dbl, qscale, oc, st);

    if (qscale >= 0 || same_quant) {

        st->codec->flags |= CODEC_FLAG_QSCALE;

        st->codec->global_quality = FF_QP2LAMBDA * qscale;

    }

    if (oc->oformat->flags & AVFMT_GLOBALHEADER)

        st->codec->flags |= CODEC_FLAG_GLOBAL_HEADER;

    av_opt_get_int(sws_opts, "sws_flags", 0, &ost->sws_flags);

    return ost;

}


static unsigned int dec_lz_r(DisasContext *dc)

{

	TCGv t0;

	DIS(fprintf (logfile, "lz $r%u, $r%u\n",

		    dc->op1, dc->op2));

	cris_cc_mask(dc, CC_MASK_NZ);

	t0 = tcg_temp_new(TCG_TYPE_TL);

	dec_prep_alu_r(dc, dc->op1, dc->op2, 4, 0, cpu_R[dc->op2], t0);

	cris_alu(dc, CC_OP_LZ, cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);

	tcg_temp_free(t0);

	return 2;

}


int av_picture_pad(AVPicture *dst, const AVPicture *src, int height, int width,

                   enum PixelFormat pix_fmt, int padtop, int padbottom, int padleft, int padright,

            int *color)

{

    uint8_t *optr;

    int y_shift;

    int x_shift;

    int yheight;

    int i, y;

    if (pix_fmt < 0 || pix_fmt >= PIX_FMT_NB ||

        !is_yuv_planar(&pix_fmt_info[pix_fmt])) return -1;

    for (i = 0; i < 3; i++) {

        x_shift = i ? av_pix_fmt_descriptors[pix_fmt].log2_chroma_w : 0;

        y_shift = i ? av_pix_fmt_descriptors[pix_fmt].log2_chroma_h : 0;

        if (padtop || padleft) {

            memset(dst->data[i], color[i],

                dst->linesize[i] * (padtop >> y_shift) + (padleft >> x_shift));

        }

        if (padleft || padright) {

            optr = dst->data[i] + dst->linesize[i] * (padtop >> y_shift) +

                (dst->linesize[i] - (padright >> x_shift));

            yheight = (height - 1 - (padtop + padbottom)) >> y_shift;

            for (y = 0; y < yheight; y++) {

                memset(optr, color[i], (padleft + padright) >> x_shift);

                optr += dst->linesize[i];

            }

        }

        if (src) { /* first line */

            uint8_t *iptr = src->data[i];

            optr = dst->data[i] + dst->linesize[i] * (padtop >> y_shift) +

                    (padleft >> x_shift);

            memcpy(optr, iptr, (width - padleft - padright) >> x_shift);

            iptr += src->linesize[i];

            optr = dst->data[i] + dst->linesize[i] * (padtop >> y_shift) +

                (dst->linesize[i] - (padright >> x_shift));

            yheight = (height - 1 - (padtop + padbottom)) >> y_shift;

            for (y = 0; y < yheight; y++) {

                memset(optr, color[i], (padleft + padright) >> x_shift);

                memcpy(optr + ((padleft + padright) >> x_shift), iptr,

                       (width - padleft - padright) >> x_shift);

                iptr += src->linesize[i];

                optr += dst->linesize[i];

            }

        }

        if (padbottom || padright) {

            optr = dst->data[i] + dst->linesize[i] *

                ((height - padbottom) >> y_shift) - (padright >> x_shift);

            memset(optr, color[i],dst->linesize[i] *

                (padbottom >> y_shift) + (padright >> x_shift));

        }

    }

    return 0;

}


void ppc_hash64_stop_access(uint64_t token)

{

    if (kvmppc_kern_htab) {

        kvmppc_hash64_free_pteg(token);

    }

}


void helper_sysret(CPUX86State *env, int dflag)

{

    int cpl, selector;

    if (!(env->efer & MSR_EFER_SCE)) {

        raise_exception_err(env, EXCP06_ILLOP, 0);

    }

    cpl = env->hflags & HF_CPL_MASK;

    if (!(env->cr[0] & CR0_PE_MASK) || cpl != 0) {

        raise_exception_err(env, EXCP0D_GPF, 0);

    }

    selector = (env->star >> 48) & 0xffff;

    if (env->hflags & HF_LMA_MASK) {

        cpu_load_eflags(env, (uint32_t)(env->regs[11]), TF_MASK | AC_MASK

                        | ID_MASK | IF_MASK | IOPL_MASK | VM_MASK | RF_MASK |

                        NT_MASK);

        if (dflag == 2) {

            cpu_x86_load_seg_cache(env, R_CS, (selector + 16) | 3,

                                   0, 0xffffffff,

                                   DESC_G_MASK | DESC_P_MASK |

                                   DESC_S_MASK | (3 << DESC_DPL_SHIFT) |

                                   DESC_CS_MASK | DESC_R_MASK | DESC_A_MASK |

                                   DESC_L_MASK);

            env->eip = env->regs[R_ECX];

        } else {

            cpu_x86_load_seg_cache(env, R_CS, selector | 3,

                                   0, 0xffffffff,

                                   DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                                   DESC_S_MASK | (3 << DESC_DPL_SHIFT) |

                                   DESC_CS_MASK | DESC_R_MASK | DESC_A_MASK);

            env->eip = (uint32_t)env->regs[R_ECX];

        }

        cpu_x86_load_seg_cache(env, R_SS, selector + 8,

                               0, 0xffffffff,

                               DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                               DESC_S_MASK | (3 << DESC_DPL_SHIFT) |

                               DESC_W_MASK | DESC_A_MASK);

        cpu_x86_set_cpl(env, 3);

    } else {

        env->eflags |= IF_MASK;

        cpu_x86_load_seg_cache(env, R_CS, selector | 3,

                               0, 0xffffffff,

                               DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                               DESC_S_MASK | (3 << DESC_DPL_SHIFT) |

                               DESC_CS_MASK | DESC_R_MASK | DESC_A_MASK);

        env->eip = (uint32_t)env->regs[R_ECX];

        cpu_x86_load_seg_cache(env, R_SS, selector + 8,

                               0, 0xffffffff,

                               DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                               DESC_S_MASK | (3 << DESC_DPL_SHIFT) |

                               DESC_W_MASK | DESC_A_MASK);

        cpu_x86_set_cpl(env, 3);

    }

}


static int handle_sigp(S390CPU *cpu, struct kvm_run *run, uint8_t ipa1)

{

    CPUS390XState *env = &cpu->env;

    uint8_t order_code;

    uint16_t cpu_addr;

    int r = -1;

    S390CPU *target_cpu;

    cpu_synchronize_state(CPU(cpu));

    /* get order code */

    order_code = decode_basedisp_rs(env, run->s390_sieic.ipb) & SIGP_ORDER_MASK;

    cpu_addr = env->regs[ipa1 & 0x0f];

    target_cpu = s390_cpu_addr2state(cpu_addr);

    if (target_cpu == NULL) {

        goto out;

    }

    switch (order_code) {

    case SIGP_START:

        r = kvm_s390_cpu_start(target_cpu);

        break;

    case SIGP_RESTART:

        r = kvm_s390_cpu_restart(target_cpu);

        break;

    case SIGP_SET_ARCH:

        /* make the caller panic */

        return -1;

    case SIGP_INITIAL_CPU_RESET:

        r = s390_cpu_initial_reset(target_cpu);

        break;

    default:

        fprintf(stderr, "KVM: unknown SIGP: 0x%x\n", order_code);

        break;

    }

out:

    setcc(cpu, r ? 3 : 0);

    return 0;

}


static void dump_ops(const uint16_t *opc_buf)

{

    const uint16_t *opc_ptr;

    int c;

    opc_ptr = opc_buf;

    for(;;) {

        c = *opc_ptr++;

        fprintf(logfile, "0x%04x: %s\n", opc_ptr - opc_buf - 1, op_str[c]);

        if (c == INDEX_op_end)

            break;

    }

}


static int tap_set_sndbuf(TAPState *s, const char *sndbuf_str)

{

    int sndbuf = TAP_DEFAULT_SNDBUF;

    if (sndbuf_str) {

        sndbuf = atoi(sndbuf_str);

    }

    if (!sndbuf) {

        sndbuf = INT_MAX;

    }

    if (ioctl(s->fd, TUNSETSNDBUF, &sndbuf) == -1 && sndbuf_str) {

        qemu_error("TUNSETSNDBUF ioctl failed: %s\n", strerror(errno));

        return -1;

    }

    return 0;

}


static void virtex_init(MachineState *machine)

{

    ram_addr_t ram_size = machine->ram_size;

    const char *cpu_model = machine->cpu_model;

    const char *kernel_filename = machine->kernel_filename;

    const char *kernel_cmdline = machine->kernel_cmdline;

    hwaddr initrd_base = 0;

    int initrd_size = 0;

    MemoryRegion *address_space_mem = get_system_memory();

    DeviceState *dev;

    PowerPCCPU *cpu;

    CPUPPCState *env;

    hwaddr ram_base = 0;

    DriveInfo *dinfo;

    MemoryRegion *phys_ram = g_new(MemoryRegion, 1);

    qemu_irq irq[32], *cpu_irq;

    int kernel_size;

    int i;

    /* init CPUs */

    if (cpu_model == NULL) {

        cpu_model = "440-Xilinx";

    }

    cpu = ppc440_init_xilinx(&ram_size, 1, cpu_model, 400000000);

    env = &cpu->env;

    qemu_register_reset(main_cpu_reset, cpu);

    memory_region_allocate_system_memory(phys_ram, NULL, "ram", ram_size);

    memory_region_add_subregion(address_space_mem, ram_base, phys_ram);

    dinfo = drive_get(IF_PFLASH, 0, 0);

    pflash_cfi01_register(PFLASH_BASEADDR, NULL, "virtex.flash", FLASH_SIZE,

                          dinfo ? blk_bs(blk_by_legacy_dinfo(dinfo)) : NULL,

                          (64 * 1024), FLASH_SIZE >> 16,

                          1, 0x89, 0x18, 0x0000, 0x0, 1);

    cpu_irq = (qemu_irq *) &env->irq_inputs[PPC40x_INPUT_INT];

    dev = qdev_create(NULL, "xlnx.xps-intc");

    qdev_prop_set_uint32(dev, "kind-of-intr", 0);

    qdev_init_nofail(dev);

    sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, INTC_BASEADDR);

    sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, cpu_irq[0]);

    for (i = 0; i < 32; i++) {

        irq[i] = qdev_get_gpio_in(dev, i);

    }

    serial_mm_init(address_space_mem, UART16550_BASEADDR, 2, irq[UART16550_IRQ],

                   115200, serial_hds[0], DEVICE_LITTLE_ENDIAN);

    /* 2 timers at irq 2 @ 62 Mhz.  */

    dev = qdev_create(NULL, "xlnx.xps-timer");

    qdev_prop_set_uint32(dev, "one-timer-only", 0);

    qdev_prop_set_uint32(dev, "clock-frequency", 62 * 1000000);

    qdev_init_nofail(dev);

    sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, TIMER_BASEADDR);

    sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, irq[TIMER_IRQ]);

    if (kernel_filename) {

        uint64_t entry, low, high;

        hwaddr boot_offset;

        /* Boots a kernel elf binary.  */

        kernel_size = load_elf(kernel_filename, NULL, NULL,

                               &entry, &low, &high, 1, ELF_MACHINE, 0);

        boot_info.bootstrap_pc = entry & 0x00ffffff;

        if (kernel_size < 0) {

            boot_offset = 0x1200000;

            /* If we failed loading ELF's try a raw image.  */

            kernel_size = load_image_targphys(kernel_filename,

                                              boot_offset,

                                              ram_size);

            boot_info.bootstrap_pc = boot_offset;

            high = boot_info.bootstrap_pc + kernel_size + 8192;

        }

        boot_info.ima_size = kernel_size;

        /* Load initrd. */

        if (machine->initrd_filename) {

            initrd_base = high = ROUND_UP(high, 4);

            initrd_size = load_image_targphys(machine->initrd_filename,

                                              high, ram_size - high);

            if (initrd_size < 0) {

                error_report("couldn't load ram disk '%s'",

                             machine->initrd_filename);

                exit(1);

            }

            high = ROUND_UP(high + initrd_size, 4);

        }

        /* Provide a device-tree.  */

        boot_info.fdt = high + (8192 * 2);

        boot_info.fdt &= ~8191;

        xilinx_load_device_tree(boot_info.fdt, ram_size,

                                initrd_base, initrd_size,

                                kernel_cmdline);

    }

    env->load_info = &boot_info;

}


static void pxa2xx_i2c_write(void *opaque, hwaddr addr,

                             uint64_t value64, unsigned size)

{

    PXA2xxI2CState *s = (PXA2xxI2CState *) opaque;

    uint32_t value = value64;

    int ack;

    addr -= s->offset;

    switch (addr) {

    case ICR:

        s->control = value & 0xfff7;

        if ((value & (1 << 3)) && (value & (1 << 6))) {	/* TB and IUE */

            /* TODO: slave mode */

            if (value & (1 << 0)) {			/* START condition */

                if (s->data & 1)

                    s->status |= 1 << 0;		/* set RWM */

                else

                    s->status &= ~(1 << 0);		/* clear RWM */

                ack = !i2c_start_transfer(s->bus, s->data >> 1, s->data & 1);

            } else {

                if (s->status & (1 << 0)) {		/* RWM */

                    s->data = i2c_recv(s->bus);

                    if (value & (1 << 2))		/* ACKNAK */

                        i2c_nack(s->bus);

                    ack = 1;

                } else

                    ack = !i2c_send(s->bus, s->data);

            }

            if (value & (1 << 1))			/* STOP condition */

                i2c_end_transfer(s->bus);

            if (ack) {

                if (value & (1 << 0))			/* START condition */

                    s->status |= 1 << 6;		/* set ITE */

                else

                    if (s->status & (1 << 0))		/* RWM */

                        s->status |= 1 << 7;		/* set IRF */

                    else

                        s->status |= 1 << 6;		/* set ITE */

                s->status &= ~(1 << 1);			/* clear ACKNAK */

            } else {

                s->status |= 1 << 6;			/* set ITE */

                s->status |= 1 << 10;			/* set BED */

                s->status |= 1 << 1;			/* set ACKNAK */

            }

        }

        if (!(value & (1 << 3)) && (value & (1 << 6)))	/* !TB and IUE */

            if (value & (1 << 4))			/* MA */

                i2c_end_transfer(s->bus);

        pxa2xx_i2c_update(s);

        break;

    case ISR:

        s->status &= ~(value & 0x07f0);

        pxa2xx_i2c_update(s);

        break;

    case ISAR:

        i2c_set_slave_address(I2C_SLAVE(s->slave), value & 0x7f);

        break;

    case IDBR:

        s->data = value & 0xff;

        break;

    default:

        printf("%s: Bad register " REG_FMT "\n", __FUNCTION__, addr);

    }

}


static void ptimer_trigger(ptimer_state *s)

{

    if (s->bh) {

        qemu_bh_schedule(s->bh);

    }

}


static int prepare_input_packet(AVFormatContext *s, AVPacket *pkt)

{

    int ret;

    ret = check_packet(s, pkt);

    if (ret < 0)

        return ret;

#if !FF_API_COMPUTE_PKT_FIELDS2

    /* sanitize the timestamps */

    if (!(s->oformat->flags & AVFMT_NOTIMESTAMPS)) {

        AVStream *st = s->streams[pkt->stream_index];

        /* when there is no reordering (so dts is equal to pts), but

         * only one of them is set, set the other as well */

        if (!st->internal->reorder) {

            if (pkt->pts == AV_NOPTS_VALUE && pkt->dts != AV_NOPTS_VALUE)

                pkt->pts = pkt->dts;

            if (pkt->dts == AV_NOPTS_VALUE && pkt->pts != AV_NOPTS_VALUE)

                pkt->dts = pkt->pts;

        }

        /* check that the timestamps are set */

        if (pkt->pts == AV_NOPTS_VALUE || pkt->dts == AV_NOPTS_VALUE) {

            av_log(s, AV_LOG_ERROR,

                   "Timestamps are unset in a packet for stream %d\n", st->index);

            return AVERROR(EINVAL);

        }

        /* check that the dts are increasing (or at least non-decreasing,

         * if the format allows it */

        if (st->cur_dts != AV_NOPTS_VALUE &&

            ((!(s->oformat->flags & AVFMT_TS_NONSTRICT) && st->cur_dts >= pkt->dts) ||

             st->cur_dts > pkt->dts)) {

            av_log(s, AV_LOG_ERROR,

                   "Application provided invalid, non monotonically increasing "

                   "dts to muxer in stream %d: %" PRId64 " >= %" PRId64 "\n",

                   st->index, st->cur_dts, pkt->dts);

            return AVERROR(EINVAL);

        }

        if (pkt->pts < pkt->dts) {

            av_log(s, AV_LOG_ERROR, "pts %" PRId64 " < dts %" PRId64 " in stream %d\n",

                   pkt->pts, pkt->dts, st->index);

            return AVERROR(EINVAL);

        }

    }

#endif

    return 0;

}


build_tpm2(GArray *table_data, GArray *linker)

{

    Acpi20TPM2 *tpm2_ptr;

    tpm2_ptr = acpi_data_push(table_data, sizeof *tpm2_ptr);

    tpm2_ptr->platform_class = cpu_to_le16(TPM2_ACPI_CLASS_CLIENT);

    tpm2_ptr->control_area_address = cpu_to_le64(0);

    tpm2_ptr->start_method = cpu_to_le32(TPM2_START_METHOD_MMIO);

    build_header(linker, table_data,

                 (void *)tpm2_ptr, "TPM2", sizeof(*tpm2_ptr), 4, NULL);

}


static int proxy_statfs(FsContext *s, V9fsPath *fs_path, struct statfs *stbuf)

{

    int retval;

    retval = v9fs_request(s->private, T_STATFS, stbuf, "s", fs_path);

    if (retval < 0) {

        errno = -retval;

        return -1;

    }

    return retval;

}


BusState *qbus_create(BusType type, size_t size,

                      DeviceState *parent, const char *name)

{

    BusState *bus;

    bus = qemu_mallocz(size);

    bus->type = type;

    bus->parent = parent;

    bus->name = qemu_strdup(name);

    LIST_INIT(&bus->children);

    if (parent) {

        LIST_INSERT_HEAD(&parent->child_bus, bus, sibling);

    }

    return bus;

}


static void update_sr (AC97LinkState *s, AC97BusMasterRegs *r, uint32_t new_sr)

{

    int event = 0;

    int level = 0;

    uint32_t new_mask = new_sr & SR_INT_MASK;

    uint32_t old_mask = r->sr & SR_INT_MASK;

    uint32_t masks[] = {GS_PIINT, GS_POINT, GS_MINT};

    if (new_mask ^ old_mask) {

        /** @todo is IRQ deasserted when only one of status bits is cleared? */

        if (!new_mask) {

            event = 1;

            level = 0;

        }

        else {

            if ((new_mask & SR_LVBCI) && (r->cr & CR_LVBIE)) {

                event = 1;

                level = 1;

            }

            if ((new_mask & SR_BCIS) && (r->cr & CR_IOCE)) {

                event = 1;

                level = 1;

            }

        }

    }

    r->sr = new_sr;

    dolog ("IOC%d LVB%d sr=%#x event=%d level=%d\n",

           r->sr & SR_BCIS, r->sr & SR_LVBCI,

           r->sr,

           event, level);

    if (!event)

        return;

    if (level) {

        s->glob_sta |= masks[r - s->bm_regs];

        dolog ("set irq level=1\n");

        qemu_set_irq (s->pci_dev->irq[0], 1);

    }

    else {

        s->glob_sta &= ~masks[r - s->bm_regs];

        dolog ("set irq level=0\n");

        qemu_set_irq (s->pci_dev->irq[0], 0);

    }

}


static unsigned int dec_subu_r(DisasContext *dc)

{

	TCGv t0;

	int size = memsize_z(dc);

	DIS(fprintf (logfile, "subu.%c $r%u, $r%u\n",

		    memsize_char(size),

		    dc->op1, dc->op2));

	cris_cc_mask(dc, CC_MASK_NZVC);

	t0 = tcg_temp_new(TCG_TYPE_TL);

	/* Size can only be qi or hi.  */

	t_gen_zext(t0, cpu_R[dc->op1], size);

	cris_alu(dc, CC_OP_SUB,

		    cpu_R[dc->op2], cpu_R[dc->op2], t0, 4);

	tcg_temp_free(t0);

	return 2;

}


bool cpu_physical_memory_is_io(hwaddr phys_addr)

{

    MemoryRegionSection *section;

    section = phys_page_find(address_space_memory.dispatch,

                             phys_addr >> TARGET_PAGE_BITS);

    return !(memory_region_is_ram(section->mr) ||

             memory_region_is_romd(section->mr));

}


int kvm_cpu_exec(CPUState *env)

{

    struct kvm_run *run = env->kvm_run;

    int ret;

    DPRINTF("kvm_cpu_exec()\n");

    if (kvm_arch_process_irqchip_events(env)) {

        env->exit_request = 0;

        env->exception_index = EXCP_HLT;

        return 0;

    }

    do {

        if (env->kvm_vcpu_dirty) {

            kvm_arch_put_registers(env, KVM_PUT_RUNTIME_STATE);

            env->kvm_vcpu_dirty = 0;

        }

        kvm_arch_pre_run(env, run);

        if (env->exit_request) {

            DPRINTF("interrupt exit requested\n");

            /*

             * KVM requires us to reenter the kernel after IO exits to complete

             * instruction emulation. This self-signal will ensure that we

             * leave ASAP again.

             */

            qemu_cpu_kick_self();

        }

        cpu_single_env = NULL;

        qemu_mutex_unlock_iothread();

        ret = kvm_vcpu_ioctl(env, KVM_RUN, 0);

        qemu_mutex_lock_iothread();

        cpu_single_env = env;

        kvm_arch_post_run(env, run);

        kvm_flush_coalesced_mmio_buffer();

        if (ret == -EINTR || ret == -EAGAIN) {

            cpu_exit(env);

            DPRINTF("io window exit\n");

            ret = 0;

            break;

        }

        if (ret < 0) {

            DPRINTF("kvm run failed %s\n", strerror(-ret));

            abort();

        }

        ret = 0; /* exit loop */

        switch (run->exit_reason) {

        case KVM_EXIT_IO:

            DPRINTF("handle_io\n");

            kvm_handle_io(run->io.port,

                          (uint8_t *)run + run->io.data_offset,

                          run->io.direction,

                          run->io.size,

                          run->io.count);

            ret = 1;

            break;

        case KVM_EXIT_MMIO:

            DPRINTF("handle_mmio\n");

            cpu_physical_memory_rw(run->mmio.phys_addr,

                                   run->mmio.data,

                                   run->mmio.len,

                                   run->mmio.is_write);

            ret = 1;

            break;

        case KVM_EXIT_IRQ_WINDOW_OPEN:

            DPRINTF("irq_window_open\n");

            break;

        case KVM_EXIT_SHUTDOWN:

            DPRINTF("shutdown\n");

            qemu_system_reset_request();

            ret = 1;

            break;

        case KVM_EXIT_UNKNOWN:

            fprintf(stderr, "KVM: unknown exit, hardware reason %" PRIx64 "\n",

                    (uint64_t)run->hw.hardware_exit_reason);

            ret = -1;

            break;

#ifdef KVM_CAP_INTERNAL_ERROR_DATA

        case KVM_EXIT_INTERNAL_ERROR:

            ret = kvm_handle_internal_error(env, run);

            break;

#endif

        case KVM_EXIT_DEBUG:

            DPRINTF("kvm_exit_debug\n");

#ifdef KVM_CAP_SET_GUEST_DEBUG

            if (kvm_arch_debug(&run->debug.arch)) {

                env->exception_index = EXCP_DEBUG;

                return 0;

            }

            /* re-enter, this exception was guest-internal */

            ret = 1;

#endif /* KVM_CAP_SET_GUEST_DEBUG */

            break;

        default:

            DPRINTF("kvm_arch_handle_exit\n");

            ret = kvm_arch_handle_exit(env, run);

            break;

        }

    } while (ret > 0);

    if (ret < 0) {

        cpu_dump_state(env, stderr, fprintf, CPU_DUMP_CODE);

        vm_stop(0);

        env->exit_request = 1;

    }

    if (env->exit_request) {

        env->exit_request = 0;

        env->exception_index = EXCP_INTERRUPT;

    }

    return ret;

}


static void rtsp_send_cmd(AVFormatContext *s,

                          const char *cmd, RTSPHeader *reply,

                          unsigned char **content_ptr)

{

    RTSPState *rt = s->priv_data;

    char buf[4096], buf1[1024], *q;

    unsigned char ch;

    const char *p;

    int content_length, line_count;

    unsigned char *content = NULL;

    memset(reply, 0, sizeof(RTSPHeader));

    rt->seq++;

    pstrcpy(buf, sizeof(buf), cmd);

    snprintf(buf1, sizeof(buf1), "CSeq: %d\r\n", rt->seq);

    pstrcat(buf, sizeof(buf), buf1);

    if (rt->session_id[0] != '\0' && !strstr(cmd, "\nIf-Match:")) {

        snprintf(buf1, sizeof(buf1), "Session: %s\r\n", rt->session_id);

        pstrcat(buf, sizeof(buf), buf1);

    }

    pstrcat(buf, sizeof(buf), "\r\n");

#ifdef DEBUG

    printf("Sending:\n%s--\n", buf);

#endif

    url_write(rt->rtsp_hd, buf, strlen(buf));

    /* parse reply (XXX: use buffers) */

    line_count = 0;

    rt->last_reply[0] = '\0';

    for(;;) {

        q = buf;

        for(;;) {

            if (url_read(rt->rtsp_hd, &ch, 1) == 0)

                break;

            if (ch == '\n')

                break;

            if (ch != '\r') {

                if ((q - buf) < sizeof(buf) - 1)

                    *q++ = ch;

            }

        }

        *q = '\0';

#ifdef DEBUG

        printf("line='%s'\n", buf);

#endif

        /* test if last line */

        if (buf[0] == '\0')

            break;

        p = buf;

        if (line_count == 0) {

            /* get reply code */

            get_word(buf1, sizeof(buf1), &p);

            get_word(buf1, sizeof(buf1), &p);

            reply->status_code = atoi(buf1);

        } else {

            rtsp_parse_line(reply, p);

            pstrcat(rt->last_reply, sizeof(rt->last_reply), p);

            pstrcat(rt->last_reply, sizeof(rt->last_reply), "\n");

        }

        line_count++;

    }

    if (rt->session_id[0] == '\0' && reply->session_id[0] != '\0')

        pstrcpy(rt->session_id, sizeof(rt->session_id), reply->session_id);

    content_length = reply->content_length;

    if (content_length > 0) {

        /* leave some room for a trailing '\0' (useful for simple parsing) */

        content = av_malloc(content_length + 1);

        url_read(rt->rtsp_hd, content, content_length);

        content[content_length] = '\0';

    }

    if (content_ptr)

        *content_ptr = content;

}


static void hb_regs_write(void *opaque, target_phys_addr_t offset,

                          uint64_t value, unsigned size)

{

    uint32_t *regs = opaque;

    if (offset == 0xf00) {

        if (value == 1 || value == 2) {

            qemu_system_reset_request();

        } else if (value == 3) {

            qemu_system_shutdown_request();

        }

    }

    regs[offset/4] = value;

}


static int print_size(DeviceState *dev, Property *prop, char *dest, size_t len)

{

    uint64_t *ptr = qdev_get_prop_ptr(dev, prop);

    char suffixes[] = {'T', 'G', 'M', 'K', 'B'};

    int i = 0;

    uint64_t div;

    for (div = 1ULL << 40; !(*ptr / div) ; div >>= 10) {

        i++;

    }

    return snprintf(dest, len, "%0.03f%c", (double)*ptr/div, suffixes[i]);

}


float64 HELPER(sub_cmp_f64)(CPUState *env, float64 a, float64 b)

{

    /* ??? This may incorrectly raise exceptions.  */

    /* ??? Should flush denormals to zero.  */

    float64 res;

    res = float64_sub(a, b, &env->fp_status);

    if (float64_is_nan(res)) {

        /* +/-inf compares equal against itself, but sub returns nan.  */

        if (!float64_is_nan(a)

            && !float64_is_nan(b)) {

            res = float64_zero;

            if (float64_lt_quiet(a, res, &env->fp_status))

                res = float64_chs(res);

        }

    }

    return res;

}


static void trim_aio_cancel(BlockAIOCB *acb)

{

    TrimAIOCB *iocb = container_of(acb, TrimAIOCB, common);

    /* Exit the loop so ide_issue_trim_cb will not continue  */

    iocb->j = iocb->qiov->niov - 1;

    iocb->i = (iocb->qiov->iov[iocb->j].iov_len / 8) - 1;

    iocb->ret = -ECANCELED;

    if (iocb->aiocb) {

        bdrv_aio_cancel_async(iocb->aiocb);

        iocb->aiocb = NULL;

    }

}


static uint64_t cadence_ttc_read(void *opaque, target_phys_addr_t offset,

    unsigned size)

{

    uint32_t ret = cadence_ttc_read_imp(opaque, offset);

    DB_PRINT("addr: %08x data: %08x\n", offset, ret);

    return ret;

}


static void scsi_do_read(void *opaque, int ret)

{

    SCSIDiskReq *r = opaque;

    SCSIDiskState *s = DO_UPCAST(SCSIDiskState, qdev, r->req.dev);

    uint32_t n;

    if (r->req.aiocb != NULL) {

        r->req.aiocb = NULL;

        bdrv_acct_done(s->qdev.conf.bs, &r->acct);

    }

    if (ret < 0) {

        if (scsi_handle_rw_error(r, -ret)) {

            goto done;

        }

    }

    if (r->req.io_canceled) {

        return;

    }

    /* The request is used as the AIO opaque value, so add a ref.  */

    scsi_req_ref(&r->req);

    if (r->req.sg) {

        dma_acct_start(s->qdev.conf.bs, &r->acct, r->req.sg, BDRV_ACCT_READ);

        r->req.resid -= r->req.sg->size;

        r->req.aiocb = dma_bdrv_read(s->qdev.conf.bs, r->req.sg, r->sector,

                                     scsi_dma_complete, r);

    } else {

        n = scsi_init_iovec(r, SCSI_DMA_BUF_SIZE);

        bdrv_acct_start(s->qdev.conf.bs, &r->acct, n * BDRV_SECTOR_SIZE, BDRV_ACCT_READ);

        r->req.aiocb = bdrv_aio_readv(s->qdev.conf.bs, r->sector, &r->qiov, n,

                                      scsi_read_complete, r);

    }

done:

    if (!r->req.io_canceled) {

        scsi_req_unref(&r->req);

    }

}


void *etraxfs_dmac_init(CPUState *env,

			target_phys_addr_t base, int nr_channels)

{

	struct fs_dma_ctrl *ctrl = NULL;

	int i;

	ctrl = qemu_mallocz(sizeof *ctrl);

	if (!ctrl)

		return NULL;

	ctrl->base = base;

	ctrl->env = env;

	ctrl->nr_channels = nr_channels;

	ctrl->channels = qemu_mallocz(sizeof ctrl->channels[0] * nr_channels);

	if (!ctrl->channels)

		goto err;

	for (i = 0; i < nr_channels; i++)

	{

		ctrl->channels[i].regmap = cpu_register_io_memory(0,

								  dma_read,

								  dma_write,

								  ctrl);

		cpu_register_physical_memory (base + i * 0x2000,

					      sizeof ctrl->channels[i].regs,

					      ctrl->channels[i].regmap);

	}

	/* Hax, we only support one DMA controller at a time.  */

	etraxfs_dmac = ctrl;

	return ctrl;

  err:

	qemu_free(ctrl->channels);

	qemu_free(ctrl);

	return NULL;

}


void lm4549_write(lm4549_state *s,

                  target_phys_addr_t offset, uint32_t value)

{

    uint16_t *regfile = s->regfile;

    assert(offset < 128);

    DPRINTF("write [0x%02x] = 0x%04x\n", offset, value);

    switch (offset) {

    case LM4549_Reset:

        lm4549_reset(s);

        break;

    case LM4549_PCM_Front_DAC_Rate:

        regfile[LM4549_PCM_Front_DAC_Rate] = value;

        DPRINTF("DAC rate change = %i\n", value);

        /* Re-open a voice with the new sample rate */

        struct audsettings as;

        as.freq = value;

        as.nchannels = 2;

        as.fmt = AUD_FMT_S16;

        as.endianness = 0;

        s->voice = AUD_open_out(

            &s->card,

            s->voice,

            "lm4549.out",

            s,

            lm4549_audio_out_callback,

            &as

        );

        break;

    case LM4549_Powerdown_Ctrl_Stat:

        value &= ~0xf;

        value |= regfile[LM4549_Powerdown_Ctrl_Stat] & 0xf;

        regfile[LM4549_Powerdown_Ctrl_Stat] = value;

        break;

    case LM4549_Ext_Audio_ID:

    case LM4549_Vendor_ID1:

    case LM4549_Vendor_ID2:

        DPRINTF("Write to read-only register 0x%x\n", (int)offset);

        break;

    default:

        /* Store the new value */

        regfile[offset] = value;

        break;

    }

}


static void gmc1_motion(MpegEncContext *s,

                        uint8_t *dest_y, uint8_t *dest_cb, uint8_t *dest_cr,

                        uint8_t **ref_picture)

{

    uint8_t *ptr;

    int offset, src_x, src_y, linesize, uvlinesize;

    int motion_x, motion_y;

    int emu=0;

    motion_x= s->sprite_offset[0][0];

    motion_y= s->sprite_offset[0][1];

    src_x = s->mb_x * 16 + (motion_x >> (s->sprite_warping_accuracy+1));

    src_y = s->mb_y * 16 + (motion_y >> (s->sprite_warping_accuracy+1));

    motion_x<<=(3-s->sprite_warping_accuracy);

    motion_y<<=(3-s->sprite_warping_accuracy);

    src_x = av_clip(src_x, -16, s->width);

    if (src_x == s->width)

        motion_x =0;

    src_y = av_clip(src_y, -16, s->height);

    if (src_y == s->height)

        motion_y =0;

    linesize = s->linesize;

    uvlinesize = s->uvlinesize;

    ptr = ref_picture[0] + (src_y * linesize) + src_x;

    if(s->flags&CODEC_FLAG_EMU_EDGE){

        if(   (unsigned)src_x >= FFMAX(s->h_edge_pos - 17, 0)

           || (unsigned)src_y >= FFMAX(s->v_edge_pos - 17, 0)){

            s->vdsp.emulated_edge_mc(s->edge_emu_buffer, ptr, linesize, 17, 17, src_x, src_y, s->h_edge_pos, s->v_edge_pos);

            ptr= s->edge_emu_buffer;

        }

    }

    if((motion_x|motion_y)&7){

        s->dsp.gmc1(dest_y  , ptr  , linesize, 16, motion_x&15, motion_y&15, 128 - s->no_rounding);

        s->dsp.gmc1(dest_y+8, ptr+8, linesize, 16, motion_x&15, motion_y&15, 128 - s->no_rounding);

    }else{

        int dxy;

        dxy= ((motion_x>>3)&1) | ((motion_y>>2)&2);

        if (s->no_rounding){

            s->hdsp.put_no_rnd_pixels_tab[0][dxy](dest_y, ptr, linesize, 16);

        }else{

            s->hdsp.put_pixels_tab       [0][dxy](dest_y, ptr, linesize, 16);

        }

    }

    if(CONFIG_GRAY && s->flags&CODEC_FLAG_GRAY) return;

    motion_x= s->sprite_offset[1][0];

    motion_y= s->sprite_offset[1][1];

    src_x = s->mb_x * 8 + (motion_x >> (s->sprite_warping_accuracy+1));

    src_y = s->mb_y * 8 + (motion_y >> (s->sprite_warping_accuracy+1));

    motion_x<<=(3-s->sprite_warping_accuracy);

    motion_y<<=(3-s->sprite_warping_accuracy);

    src_x = av_clip(src_x, -8, s->width>>1);

    if (src_x == s->width>>1)

        motion_x =0;

    src_y = av_clip(src_y, -8, s->height>>1);

    if (src_y == s->height>>1)

        motion_y =0;

    offset = (src_y * uvlinesize) + src_x;

    ptr = ref_picture[1] + offset;

    if(s->flags&CODEC_FLAG_EMU_EDGE){

        if(   (unsigned)src_x >= FFMAX((s->h_edge_pos>>1) - 9, 0)

           || (unsigned)src_y >= FFMAX((s->v_edge_pos>>1) - 9, 0)){

            s->vdsp.emulated_edge_mc(s->edge_emu_buffer, ptr, uvlinesize, 9, 9, src_x, src_y, s->h_edge_pos>>1, s->v_edge_pos>>1);

            ptr= s->edge_emu_buffer;

            emu=1;

        }

    }

    s->dsp.gmc1(dest_cb, ptr, uvlinesize, 8, motion_x&15, motion_y&15, 128 - s->no_rounding);

    ptr = ref_picture[2] + offset;

    if(emu){

        s->vdsp.emulated_edge_mc(s->edge_emu_buffer, ptr, uvlinesize, 9, 9, src_x, src_y, s->h_edge_pos>>1, s->v_edge_pos>>1);

        ptr= s->edge_emu_buffer;

    }

    s->dsp.gmc1(dest_cr, ptr, uvlinesize, 8, motion_x&15, motion_y&15, 128 - s->no_rounding);

    return;

}


static void mpcore_scu_write(void *opaque, target_phys_addr_t offset,

                             uint64_t value, unsigned size)

{

    mpcore_priv_state *s = (mpcore_priv_state *)opaque;

    /* SCU */

    switch (offset) {

    case 0: /* Control register.  */

        s->scu_control = value & 1;

        break;

    case 0x0c: /* Invalidate all.  */

        /* This is a no-op as cache is not emulated.  */

        break;

    default:

        hw_error("mpcore_priv_read: Bad offset %x\n", (int)offset);

    }

}


static void gen_imull(TCGv a, TCGv b)

{

    TCGv tmp1 = tcg_temp_new(TCG_TYPE_I64);

    TCGv tmp2 = tcg_temp_new(TCG_TYPE_I64);

    tcg_gen_ext_i32_i64(tmp1, a);

    tcg_gen_ext_i32_i64(tmp2, b);

    tcg_gen_mul_i64(tmp1, tmp1, tmp2);

    tcg_gen_trunc_i64_i32(a, tmp1);

    tcg_gen_shri_i64(tmp1, tmp1, 32);

    tcg_gen_trunc_i64_i32(b, tmp1);

}


void ppc40x_chip_reset (CPUState *env)

{

    target_ulong dbsr;

    printf("Reset PowerPC chip\n");

    cpu_ppc_reset(env);

    /* XXX: TODO reset all internal peripherals */

    dbsr = env->spr[SPR_40x_DBSR];

    dbsr &= ~0x00000300;

    dbsr |= 0x00000200;

    env->spr[SPR_40x_DBSR] = dbsr;

    cpu_loop_exit();

}


static int thread_get_buffer_internal(AVCodecContext *avctx, ThreadFrame *f, int flags)

{

    PerThreadContext *p = avctx->internal->thread_ctx;

    int err;

    f->owner = avctx;

    ff_init_buffer_info(avctx, f->f);

    if (!(avctx->active_thread_type & FF_THREAD_FRAME))

        return ff_get_buffer(avctx, f->f, flags);

    if (atomic_load(&p->state) != STATE_SETTING_UP &&

        (avctx->codec->update_thread_context || !THREAD_SAFE_CALLBACKS(avctx))) {

        av_log(avctx, AV_LOG_ERROR, "get_buffer() cannot be called after ff_thread_finish_setup()\n");

        return -1;

    }

    if (avctx->internal->allocate_progress) {

        atomic_int *progress;

        f->progress = av_buffer_alloc(2 * sizeof(*progress));

        if (!f->progress) {

            return AVERROR(ENOMEM);

        }

        progress = (atomic_int*)f->progress->data;

        atomic_init(&progress[0], -1);

        atomic_init(&progress[1], -1);

    }

    pthread_mutex_lock(&p->parent->buffer_mutex);

    if (avctx->thread_safe_callbacks ||

        avctx->get_buffer2 == avcodec_default_get_buffer2) {

        err = ff_get_buffer(avctx, f->f, flags);

    } else {

        pthread_mutex_lock(&p->progress_mutex);

        p->requested_frame = f->f;

        p->requested_flags = flags;

        atomic_store_explicit(&p->state, STATE_GET_BUFFER, memory_order_release);

        pthread_cond_broadcast(&p->progress_cond);

        while (atomic_load(&p->state) != STATE_SETTING_UP)

            pthread_cond_wait(&p->progress_cond, &p->progress_mutex);

        err = p->result;

        pthread_mutex_unlock(&p->progress_mutex);

    }

    if (!THREAD_SAFE_CALLBACKS(avctx) && !avctx->codec->update_thread_context)

        ff_thread_finish_setup(avctx);

    if (err)

        av_buffer_unref(&f->progress);

    pthread_mutex_unlock(&p->parent->buffer_mutex);

    return err;

}


static void gen_spr_power5p_lpar(CPUPPCState *env)

{

#if !defined(CONFIG_USER_ONLY)

    /* Logical partitionning */

    spr_register_kvm(env, SPR_LPCR, "LPCR",

                     &spr_read_generic, &spr_write_lpcr,

                     KVM_REG_PPC_LPCR, LPCR_LPES0 | LPCR_LPES1);

#endif

}


int inet_connect_opts(QemuOpts *opts, bool block, bool *in_progress,

                      Error **errp)

{

    struct addrinfo *res, *e;

    int sock = -1;

    res = inet_parse_connect_opts(opts, errp);

    if (!res) {

        return -1;

    }

    if (in_progress) {

        *in_progress = false;

    }

    for (e = res; e != NULL; e = e->ai_next) {

        sock = inet_connect_addr(e, block, in_progress);

        if (sock >= 0) {

            break;

        }

    }

    if (sock < 0) {

        error_set(errp, QERR_SOCKET_CONNECT_FAILED);

    }

    freeaddrinfo(res);

    return sock;

}


static void via_class_init(ObjectClass *klass, void *data)

{

    DeviceClass *dc = DEVICE_CLASS(klass);

    PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);

    k->init = vt82c686b_initfn;

    k->config_write = vt82c686b_write_config;

    k->vendor_id = PCI_VENDOR_ID_VIA;

    k->device_id = PCI_DEVICE_ID_VIA_ISA_BRIDGE;

    k->class_id = PCI_CLASS_BRIDGE_ISA;

    k->revision = 0x40;

    dc->desc = "ISA bridge";

    dc->no_user = 1;

    dc->vmsd = &vmstate_via;

}


static int vhost_user_reset_device(struct vhost_dev *dev)

{

    VhostUserMsg msg = {

        .request = VHOST_USER_RESET_OWNER,

        .flags = VHOST_USER_VERSION,

    };

    vhost_user_write(dev, &msg, NULL, 0);

    return 0;

}


static int vp5_parse_header(VP56Context *s, const uint8_t *buf, int buf_size,

                            int *golden_frame)

{

    VP56RangeCoder *c = &s->c;

    int rows, cols;

    ff_vp56_init_range_decoder(&s->c, buf, buf_size);

    s->framep[VP56_FRAME_CURRENT]->key_frame = !vp56_rac_get(c);

    vp56_rac_get(c);

    ff_vp56_init_dequant(s, vp56_rac_gets(c, 6));

    if (s->framep[VP56_FRAME_CURRENT]->key_frame)

    {

        vp56_rac_gets(c, 8);

        if(vp56_rac_gets(c, 5) > 5)

        vp56_rac_gets(c, 2);

        if (vp56_rac_get(c)) {

            av_log(s->avctx, AV_LOG_ERROR, "interlacing not supported\n");

        rows = vp56_rac_gets(c, 8);  /* number of stored macroblock rows */

        cols = vp56_rac_gets(c, 8);  /* number of stored macroblock cols */

        vp56_rac_gets(c, 8);  /* number of displayed macroblock rows */

        vp56_rac_gets(c, 8);  /* number of displayed macroblock cols */

        vp56_rac_gets(c, 2);

        if (!s->macroblocks || /* first frame */

            16*cols != s->avctx->coded_width ||

            16*rows != s->avctx->coded_height) {

            avcodec_set_dimensions(s->avctx, 16*cols, 16*rows);

            return 2;

    } else if (!s->macroblocks)

    return 1;


static void spapr_finalize_fdt(sPAPRMachineState *spapr,

                               hwaddr fdt_addr,

                               hwaddr rtas_addr,

                               hwaddr rtas_size)

{

    MachineState *machine = MACHINE(qdev_get_machine());

    sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(machine);

    const char *boot_device = machine->boot_order;

    int ret, i;

    size_t cb = 0;

    char *bootlist;

    void *fdt;

    sPAPRPHBState *phb;

    fdt = g_malloc(FDT_MAX_SIZE);

    /* open out the base tree into a temp buffer for the final tweaks */

    _FDT((fdt_open_into(spapr->fdt_skel, fdt, FDT_MAX_SIZE)));

    ret = spapr_populate_memory(spapr, fdt);

    if (ret < 0) {

        fprintf(stderr, "couldn't setup memory nodes in fdt\n");

        exit(1);

    }

    ret = spapr_populate_vdevice(spapr->vio_bus, fdt);

    if (ret < 0) {

        fprintf(stderr, "couldn't setup vio devices in fdt\n");

        exit(1);

    }

    if (object_resolve_path_type("", TYPE_SPAPR_RNG, NULL)) {

        ret = spapr_rng_populate_dt(fdt);

        if (ret < 0) {

            fprintf(stderr, "could not set up rng device in the fdt\n");

            exit(1);

        }

    }

    QLIST_FOREACH(phb, &spapr->phbs, list) {

        ret = spapr_populate_pci_dt(phb, PHANDLE_XICP, fdt);

        if (ret < 0) {

            error_report("couldn't setup PCI devices in fdt");

            exit(1);

        }

    }

    /* RTAS */

    ret = spapr_rtas_device_tree_setup(fdt, rtas_addr, rtas_size);

    if (ret < 0) {

        fprintf(stderr, "Couldn't set up RTAS device tree properties\n");

    }

    /* cpus */

    spapr_populate_cpus_dt_node(fdt, spapr);

    bootlist = get_boot_devices_list(&cb, true);

    if (cb && bootlist) {

        int offset = fdt_path_offset(fdt, "/chosen");

        if (offset < 0) {

            exit(1);

        }

        for (i = 0; i < cb; i++) {

            if (bootlist[i] == '\n') {

                bootlist[i] = ' ';

            }

        }

        ret = fdt_setprop_string(fdt, offset, "qemu,boot-list", bootlist);

    }

    if (boot_device && strlen(boot_device)) {

        int offset = fdt_path_offset(fdt, "/chosen");

        if (offset < 0) {

            exit(1);

        }

        fdt_setprop_string(fdt, offset, "qemu,boot-device", boot_device);

    }

    if (!spapr->has_graphics) {

        spapr_populate_chosen_stdout(fdt, spapr->vio_bus);

    }

    if (smc->dr_lmb_enabled) {

        _FDT(spapr_drc_populate_dt(fdt, 0, NULL, SPAPR_DR_CONNECTOR_TYPE_LMB));

    }

    if (smc->dr_cpu_enabled) {

        int offset = fdt_path_offset(fdt, "/cpus");

        ret = spapr_drc_populate_dt(fdt, offset, NULL,

                                    SPAPR_DR_CONNECTOR_TYPE_CPU);

        if (ret < 0) {

            error_report("Couldn't set up CPU DR device tree properties");

            exit(1);

        }

    }

    _FDT((fdt_pack(fdt)));

    if (fdt_totalsize(fdt) > FDT_MAX_SIZE) {

        error_report("FDT too big ! 0x%x bytes (max is 0x%x)",

                     fdt_totalsize(fdt), FDT_MAX_SIZE);

        exit(1);

    }

    qemu_fdt_dumpdtb(fdt, fdt_totalsize(fdt));

    cpu_physical_memory_write(fdt_addr, fdt, fdt_totalsize(fdt));

    g_free(bootlist);

    g_free(fdt);

}


static av_cold int avs_decode_init(AVCodecContext * avctx)

{

    avctx->pix_fmt = PIX_FMT_PAL8;

    return 0;

}


CharDriverState *qemu_chr_alloc(ChardevCommon *backend, Error **errp)

{

    CharDriverState *chr = g_malloc0(sizeof(CharDriverState));

    qemu_mutex_init(&chr->chr_write_lock);

    chr->mux_idx = -1;

    if (backend->has_logfile) {

        int flags = O_WRONLY | O_CREAT;

        if (backend->has_logappend &&

            backend->logappend) {

            flags |= O_APPEND;

        } else {

            flags |= O_TRUNC;

        }

        chr->logfd = qemu_open(backend->logfile, flags, 0666);

        if (chr->logfd < 0) {

            error_setg_errno(errp, errno,

                             "Unable to open logfile %s",

                             backend->logfile);

            g_free(chr);

            return NULL;

        }

    } else {

        chr->logfd = -1;

    }

    return chr;

}


static int read_block(ALSDecContext *ctx, ALSBlockData *bd)

{

    GetBitContext *gb        = &ctx->gb;

    *bd->shift_lsbs = 0;

    // read block type flag and read the samples accordingly

    if (get_bits1(gb)) {

        if (read_var_block_data(ctx, bd))

            return -1;

    } else {

        read_const_block_data(ctx, bd);

    }

    return 0;

}


static bool get_phys_addr(CPUARMState *env, target_ulong address,

                          int access_type, ARMMMUIdx mmu_idx,

                          hwaddr *phys_ptr, MemTxAttrs *attrs, int *prot,

                          target_ulong *page_size, uint32_t *fsr,

                          ARMMMUFaultInfo *fi)

{

    if (mmu_idx == ARMMMUIdx_S12NSE0 || mmu_idx == ARMMMUIdx_S12NSE1) {

        /* Call ourselves recursively to do the stage 1 and then stage 2

         * translations.

         */

        if (arm_feature(env, ARM_FEATURE_EL2)) {

            hwaddr ipa;

            int s2_prot;

            int ret;

            ret = get_phys_addr(env, address, access_type,

                                stage_1_mmu_idx(mmu_idx), &ipa, attrs,

                                prot, page_size, fsr, fi);

            /* If S1 fails or S2 is disabled, return early.  */

            if (ret || regime_translation_disabled(env, ARMMMUIdx_S2NS)) {

                *phys_ptr = ipa;

                return ret;

            }

            /* S1 is done. Now do S2 translation.  */

            ret = get_phys_addr_lpae(env, ipa, access_type, ARMMMUIdx_S2NS,

                                     phys_ptr, attrs, &s2_prot,

                                     page_size, fsr, fi);

            fi->s2addr = ipa;

            /* Combine the S1 and S2 perms.  */

            *prot &= s2_prot;

            return ret;

        } else {

            /*

             * For non-EL2 CPUs a stage1+stage2 translation is just stage 1.

             */

            mmu_idx = stage_1_mmu_idx(mmu_idx);

        }

    }

    /* The page table entries may downgrade secure to non-secure, but

     * cannot upgrade an non-secure translation regime's attributes

     * to secure.

     */

    attrs->secure = regime_is_secure(env, mmu_idx);

    attrs->user = regime_is_user(env, mmu_idx);

    /* Fast Context Switch Extension. This doesn't exist at all in v8.

     * In v7 and earlier it affects all stage 1 translations.

     */

    if (address < 0x02000000 && mmu_idx != ARMMMUIdx_S2NS

        && !arm_feature(env, ARM_FEATURE_V8)) {

        if (regime_el(env, mmu_idx) == 3) {

            address += env->cp15.fcseidr_s;

        } else {

            address += env->cp15.fcseidr_ns;

        }

    }

    /* pmsav7 has special handling for when MPU is disabled so call it before

     * the common MMU/MPU disabled check below.

     */

    if (arm_feature(env, ARM_FEATURE_PMSA) &&

        arm_feature(env, ARM_FEATURE_V7)) {

        bool ret;

        *page_size = TARGET_PAGE_SIZE;

        ret = get_phys_addr_pmsav7(env, address, access_type, mmu_idx,

                                   phys_ptr, prot, fsr);

        qemu_log_mask(CPU_LOG_MMU, "PMSAv7 MPU lookup for %s at 0x%08" PRIx32

                      " mmu_idx %u -> %s (prot %c%c%c)\n",

                      access_type == 1 ? "reading" :

                      (access_type == 2 ? "writing" : "execute"),

                      (uint32_t)address, mmu_idx,

                      ret ? "Miss" : "Hit",

                      *prot & PAGE_READ ? 'r' : '-',

                      *prot & PAGE_WRITE ? 'w' : '-',

                      *prot & PAGE_EXEC ? 'x' : '-');

        return ret;

    }

    if (regime_translation_disabled(env, mmu_idx)) {

        /* MMU/MPU disabled.  */

        *phys_ptr = address;

        *prot = PAGE_READ | PAGE_WRITE | PAGE_EXEC;

        *page_size = TARGET_PAGE_SIZE;

        return 0;

    }

    if (arm_feature(env, ARM_FEATURE_PMSA)) {

        /* Pre-v7 MPU */

        *page_size = TARGET_PAGE_SIZE;

        return get_phys_addr_pmsav5(env, address, access_type, mmu_idx,

                                    phys_ptr, prot, fsr);

    }

    if (regime_using_lpae_format(env, mmu_idx)) {

        return get_phys_addr_lpae(env, address, access_type, mmu_idx, phys_ptr,

                                  attrs, prot, page_size, fsr, fi);

    } else if (regime_sctlr(env, mmu_idx) & SCTLR_XP) {

        return get_phys_addr_v6(env, address, access_type, mmu_idx, phys_ptr,

                                attrs, prot, page_size, fsr, fi);

    } else {

        return get_phys_addr_v5(env, address, access_type, mmu_idx, phys_ptr,

                                prot, page_size, fsr, fi);

    }

}


bool qpci_msix_masked(QPCIDevice *dev, uint16_t entry)

{

    uint8_t addr;

    uint16_t val;

    void *vector_addr = dev->msix_table + (entry * PCI_MSIX_ENTRY_SIZE);

    g_assert(dev->msix_enabled);

    addr = qpci_find_capability(dev, PCI_CAP_ID_MSIX);

    g_assert_cmphex(addr, !=, 0);

    val = qpci_config_readw(dev, addr + PCI_MSIX_FLAGS);

    if (val & PCI_MSIX_FLAGS_MASKALL) {

        return true;

    } else {

        return (qpci_io_readl(dev, vector_addr + PCI_MSIX_ENTRY_VECTOR_CTRL)

                                            & PCI_MSIX_ENTRY_CTRL_MASKBIT) != 0;

    }

}


static MegasasCmd *megasas_enqueue_frame(MegasasState *s,

    hwaddr frame, uint64_t context, int count)

{

    PCIDevice *pcid = PCI_DEVICE(s);

    MegasasCmd *cmd = NULL;

    int frame_size = MFI_FRAME_SIZE * 16;

    hwaddr frame_size_p = frame_size;

    cmd = megasas_next_frame(s, frame);

    /* All frames busy */

    if (!cmd) {

        return NULL;

    }

    if (!cmd->pa) {

        cmd->pa = frame;

        /* Map all possible frames */

        cmd->frame = pci_dma_map(pcid, frame, &frame_size_p, 0);

        if (frame_size_p != frame_size) {

            trace_megasas_qf_map_failed(cmd->index, (unsigned long)frame);

            if (cmd->frame) {

                pci_dma_unmap(pcid, cmd->frame, frame_size_p, 0, 0);

                cmd->frame = NULL;

                cmd->pa = 0;

            }

            s->event_count++;

            return NULL;

        }

        cmd->pa_size = frame_size_p;

        cmd->context = context;

        if (!megasas_use_queue64(s)) {

            cmd->context &= (uint64_t)0xFFFFFFFF;

        }

    }

    cmd->count = count;

    s->busy++;

    if (s->consumer_pa) {

        s->reply_queue_tail = ldl_le_phys(&address_space_memory,

                                          s->consumer_pa);

    }

    trace_megasas_qf_enqueue(cmd->index, cmd->count, cmd->context,

                             s->reply_queue_head, s->reply_queue_tail, s->busy);

    return cmd;

}


static int img_commit(int argc, char **argv)

{

    int c, ret, flags;

    const char *filename, *fmt, *cache, *base;

    BlockBackend *blk;

    BlockDriverState *bs, *base_bs;

    BlockJob *job;

    bool progress = false, quiet = false, drop = false;

    bool writethrough;

    Error *local_err = NULL;

    CommonBlockJobCBInfo cbi;

    bool image_opts = false;

    AioContext *aio_context;

    fmt = NULL;

    cache = BDRV_DEFAULT_CACHE;

    base = NULL;

    for(;;) {

        static const struct option long_options[] = {

            {"help", no_argument, 0, 'h'},

            {"object", required_argument, 0, OPTION_OBJECT},

            {"image-opts", no_argument, 0, OPTION_IMAGE_OPTS},

            {0, 0, 0, 0}

        };

        c = getopt_long(argc, argv, "f:ht:b:dpq",

                        long_options, NULL);

        if (c == -1) {

            break;

        }

        switch(c) {

        case '?':

        case 'h':

            help();

            break;

        case 'f':

            fmt = optarg;

            break;

        case 't':

            cache = optarg;

            break;

        case 'b':

            base = optarg;

            /* -b implies -d */

            drop = true;

            break;

        case 'd':

            drop = true;

            break;

        case 'p':

            progress = true;

            break;

        case 'q':

            quiet = true;

            break;

        case OPTION_OBJECT: {

            QemuOpts *opts;

            opts = qemu_opts_parse_noisily(&qemu_object_opts,

                                           optarg, true);

            if (!opts) {

                return 1;

            }

        }   break;

        case OPTION_IMAGE_OPTS:

            image_opts = true;

            break;

        }

    }

    /* Progress is not shown in Quiet mode */

    if (quiet) {

        progress = false;

    }

    if (optind != argc - 1) {

        error_exit("Expecting one image file name");

    }

    filename = argv[optind++];

    if (qemu_opts_foreach(&qemu_object_opts,

                          user_creatable_add_opts_foreach,

                          NULL, NULL)) {

        return 1;

    }

    flags = BDRV_O_RDWR | BDRV_O_UNMAP;

    ret = bdrv_parse_cache_mode(cache, &flags, &writethrough);

    if (ret < 0) {

        error_report("Invalid cache option: %s", cache);

        return 1;

    }

    blk = img_open(image_opts, filename, fmt, flags, writethrough, quiet);

    if (!blk) {

        return 1;

    }

    bs = blk_bs(blk);

    qemu_progress_init(progress, 1.f);

    qemu_progress_print(0.f, 100);

    if (base) {

        base_bs = bdrv_find_backing_image(bs, base);

        if (!base_bs) {

            error_setg(&local_err,

                       "Did not find '%s' in the backing chain of '%s'",

                       base, filename);

            goto done;

        }

    } else {

        /* This is different from QMP, which by default uses the deepest file in

         * the backing chain (i.e., the very base); however, the traditional

         * behavior of qemu-img commit is using the immediate backing file. */

        base_bs = backing_bs(bs);

        if (!base_bs) {

            error_setg(&local_err, "Image does not have a backing file");

            goto done;

        }

    }

    cbi = (CommonBlockJobCBInfo){

        .errp = &local_err,

        .bs   = bs,

    };

    aio_context = bdrv_get_aio_context(bs);

    aio_context_acquire(aio_context);

    commit_active_start("commit", bs, base_bs, BLOCK_JOB_DEFAULT, 0,

                        BLOCKDEV_ON_ERROR_REPORT, NULL, common_block_job_cb,

                        &cbi, &local_err, false);

    aio_context_release(aio_context);

    if (local_err) {

        goto done;

    }

    /* When the block job completes, the BlockBackend reference will point to

     * the old backing file. In order to avoid that the top image is already

     * deleted, so we can still empty it afterwards, increment the reference

     * counter here preemptively. */

    if (!drop) {

        bdrv_ref(bs);

    }

    job = block_job_get("commit");

    run_block_job(job, &local_err);

    if (local_err) {

        goto unref_backing;

    }

    if (!drop && bs->drv->bdrv_make_empty) {

        ret = bs->drv->bdrv_make_empty(bs);

        if (ret) {

            error_setg_errno(&local_err, -ret, "Could not empty %s",

                             filename);

            goto unref_backing;

        }

    }

unref_backing:

    if (!drop) {

        bdrv_unref(bs);

    }

done:

    qemu_progress_end();

    blk_unref(blk);

    if (local_err) {

        error_report_err(local_err);

        return 1;

    }

    qprintf(quiet, "Image committed.\n");

    return 0;

}


static int encode_superframe(AVCodecContext *avctx, AVPacket *avpkt,

                             const AVFrame *frame, int *got_packet_ptr)

{

    WMACodecContext *s = avctx->priv_data;

    int i, total_gain, ret, error;

    s->block_len_bits= s->frame_len_bits; //required by non variable block len

    s->block_len = 1 << s->block_len_bits;

    apply_window_and_mdct(avctx, frame);

    if (s->ms_stereo) {

        float a, b;

        int i;

        for(i = 0; i < s->block_len; i++) {

            a = s->coefs[0][i]*0.5;

            b = s->coefs[1][i]*0.5;

            s->coefs[0][i] = a + b;

            s->coefs[1][i] = a - b;

    if ((ret = ff_alloc_packet2(avctx, avpkt, 2 * MAX_CODED_SUPERFRAME_SIZE)) < 0)

        return ret;

    total_gain= 128;

    for(i=64; i; i>>=1){

        error = encode_frame(s, s->coefs, avpkt->data, avpkt->size,

                                 total_gain - i);

        if(error<=0)

            total_gain-= i;

    while(total_gain <= 128 && error > 0)

        error = encode_frame(s, s->coefs, avpkt->data, avpkt->size, total_gain++);

    av_assert0((put_bits_count(&s->pb) & 7) == 0);

    i= avctx->block_align - (put_bits_count(&s->pb)+7)/8;

    av_assert0(i>=0);

    while(i--)

        put_bits(&s->pb, 8, 'N');

    flush_put_bits(&s->pb);

    av_assert0(put_bits_ptr(&s->pb) - s->pb.buf == avctx->block_align);

    if (frame->pts != AV_NOPTS_VALUE)

        avpkt->pts = frame->pts - ff_samples_to_time_base(avctx, avctx->delay);

    avpkt->size = avctx->block_align;

    *got_packet_ptr = 1;

    return 0;


static int ftp_passive_mode(FTPContext *s)

{

    char *res = NULL, *start, *end;

    int i;

    const char *command = "PASV\r\n";

    const int pasv_codes[] = {227, 501, 0}; /* 501 is incorrect code */

    if (ftp_send_command(s, command, pasv_codes, &res) != 227 || !res)

        goto fail;

    start = NULL;

    for (i = 0; i < strlen(res); ++i) {

        if (res[i] == '(') {

            start = res + i + 1;

        } else if (res[i] == ')') {

            end = res + i;

            break;

        }

    }

    if (!start || !end)

        goto fail;

    *end  = '\0';

    /* skip ip */

    if (!av_strtok(start, ",", &end)) goto fail;

    if (!av_strtok(end, ",", &end)) goto fail;

    if (!av_strtok(end, ",", &end)) goto fail;

    if (!av_strtok(end, ",", &end)) goto fail;

    /* parse port number */

    start = av_strtok(end, ",", &end);

    if (!start) goto fail;

    s->server_data_port = atoi(start) * 256;

    start = av_strtok(end, ",", &end);

    if (!start) goto fail;

    s->server_data_port += atoi(start);

    av_dlog(s, "Server data port: %d\n", s->server_data_port);

    av_free(res);

    return 0;

  fail:

    av_free(res);

    s->server_data_port = -1;

    return AVERROR(EIO);

}


static int wavpack_decode_block(AVCodecContext *avctx, int block_no,

                                void *data, int *data_size,

                                const uint8_t *buf, int buf_size)

{

    WavpackContext *wc = avctx->priv_data;

    WavpackFrameContext *s;

    void *samples = data;

    int samplecount;

    int got_terms = 0, got_weights = 0, got_samples = 0, got_entropy = 0, got_bs = 0, got_float = 0;

    int got_hybrid = 0;

    const uint8_t* orig_buf = buf;

    const uint8_t* buf_end = buf + buf_size;

    int i, j, id, size, ssize, weights, t;

    int bpp, chan, chmask;

    if (buf_size == 0){

        *data_size = 0;

        return 0;

    }

    if(block_no >= wc->fdec_num && wv_alloc_frame_context(wc) < 0){

        av_log(avctx, AV_LOG_ERROR, "Error creating frame decode context\n");

        return -1;

    }

    s = wc->fdec[block_no];

    if(!s){

        av_log(avctx, AV_LOG_ERROR, "Context for block %d is not present\n", block_no);

        return -1;

    }

    if(!s->samples_left){

        memset(s->decorr, 0, MAX_TERMS * sizeof(Decorr));

        memset(s->ch, 0, sizeof(s->ch));

        s->extra_bits = 0;

        s->and = s->or = s->shift = 0;

        s->got_extra_bits = 0;

    }

    if(!wc->mkv_mode){

        s->samples = AV_RL32(buf); buf += 4;

        if(!s->samples){

            *data_size = 0;

            return 0;

        }

    }else{

        s->samples = wc->samples;

    }

    s->frame_flags = AV_RL32(buf); buf += 4;

    if(s->frame_flags&0x80){

        bpp = sizeof(float);

        avctx->sample_fmt = AV_SAMPLE_FMT_FLT;

    } else if((s->frame_flags&0x03) <= 1){

        bpp = 2;

        avctx->sample_fmt = AV_SAMPLE_FMT_S16;

    } else {

        bpp = 4;

        avctx->sample_fmt = AV_SAMPLE_FMT_S32;

    }

    samples = (uint8_t*)samples + bpp * wc->ch_offset;

    s->stereo = !(s->frame_flags & WV_MONO);

    s->stereo_in = (s->frame_flags & WV_FALSE_STEREO) ? 0 : s->stereo;

    s->joint = s->frame_flags & WV_JOINT_STEREO;

    s->hybrid = s->frame_flags & WV_HYBRID_MODE;

    s->hybrid_bitrate = s->frame_flags & WV_HYBRID_BITRATE;

    s->post_shift = 8 * (bpp-1-(s->frame_flags&0x03)) + ((s->frame_flags >> 13) & 0x1f);

    s->CRC = AV_RL32(buf); buf += 4;

    if(wc->mkv_mode)

        buf += 4; //skip block size;

    wc->ch_offset += 1 + s->stereo;

    s->max_samples = *data_size / (bpp * avctx->channels);

    s->max_samples = FFMIN(s->max_samples, s->samples);

    if(s->samples_left > 0){

        s->max_samples = FFMIN(s->max_samples, s->samples_left);

        buf = buf_end;

    }

    // parse metadata blocks

    while(buf < buf_end){

        id = *buf++;

        size = *buf++;

        if(id & WP_IDF_LONG) {

            size |= (*buf++) << 8;

            size |= (*buf++) << 16;

        }

        size <<= 1; // size is specified in words

        ssize = size;

        if(id & WP_IDF_ODD) size--;

        if(size < 0){

            av_log(avctx, AV_LOG_ERROR, "Got incorrect block %02X with size %i\n", id, size);

            break;

        }

        if(buf + ssize > buf_end){

            av_log(avctx, AV_LOG_ERROR, "Block size %i is out of bounds\n", size);

            break;

        }

        if(id & WP_IDF_IGNORE){

            buf += ssize;

            continue;

        }

        switch(id & WP_IDF_MASK){

        case WP_ID_DECTERMS:

            s->terms = size;

            if(s->terms > MAX_TERMS){

                av_log(avctx, AV_LOG_ERROR, "Too many decorrelation terms\n");

                buf += ssize;

                continue;

            }

            for(i = 0; i < s->terms; i++) {

                s->decorr[s->terms - i - 1].value = (*buf & 0x1F) - 5;

                s->decorr[s->terms - i - 1].delta = *buf >> 5;

                buf++;

            }

            got_terms = 1;

            break;

        case WP_ID_DECWEIGHTS:

            if(!got_terms){

                av_log(avctx, AV_LOG_ERROR, "No decorrelation terms met\n");

                continue;

            }

            weights = size >> s->stereo_in;

            if(weights > MAX_TERMS || weights > s->terms){

                av_log(avctx, AV_LOG_ERROR, "Too many decorrelation weights\n");

                buf += ssize;

                continue;

            }

            for(i = 0; i < weights; i++) {

                t = (int8_t)(*buf++);

                s->decorr[s->terms - i - 1].weightA = t << 3;

                if(s->decorr[s->terms - i - 1].weightA > 0)

                    s->decorr[s->terms - i - 1].weightA += (s->decorr[s->terms - i - 1].weightA + 64) >> 7;

                if(s->stereo_in){

                    t = (int8_t)(*buf++);

                    s->decorr[s->terms - i - 1].weightB = t << 3;

                    if(s->decorr[s->terms - i - 1].weightB > 0)

                        s->decorr[s->terms - i - 1].weightB += (s->decorr[s->terms - i - 1].weightB + 64) >> 7;

                }

            }

            got_weights = 1;

            break;

        case WP_ID_DECSAMPLES:

            if(!got_terms){

                av_log(avctx, AV_LOG_ERROR, "No decorrelation terms met\n");

                continue;

            }

            t = 0;

            for(i = s->terms - 1; (i >= 0) && (t < size); i--) {

                if(s->decorr[i].value > 8){

                    s->decorr[i].samplesA[0] = wp_exp2(AV_RL16(buf)); buf += 2;

                    s->decorr[i].samplesA[1] = wp_exp2(AV_RL16(buf)); buf += 2;

                    if(s->stereo_in){

                        s->decorr[i].samplesB[0] = wp_exp2(AV_RL16(buf)); buf += 2;

                        s->decorr[i].samplesB[1] = wp_exp2(AV_RL16(buf)); buf += 2;

                        t += 4;

                    }

                    t += 4;

                }else if(s->decorr[i].value < 0){

                    s->decorr[i].samplesA[0] = wp_exp2(AV_RL16(buf)); buf += 2;

                    s->decorr[i].samplesB[0] = wp_exp2(AV_RL16(buf)); buf += 2;

                    t += 4;

                }else{

                    for(j = 0; j < s->decorr[i].value; j++){

                        s->decorr[i].samplesA[j] = wp_exp2(AV_RL16(buf)); buf += 2;

                        if(s->stereo_in){

                            s->decorr[i].samplesB[j] = wp_exp2(AV_RL16(buf)); buf += 2;

                        }

                    }

                    t += s->decorr[i].value * 2 * (s->stereo_in + 1);

                }

            }

            got_samples = 1;

            break;

        case WP_ID_ENTROPY:

            if(size != 6 * (s->stereo_in + 1)){

                av_log(avctx, AV_LOG_ERROR, "Entropy vars size should be %i, got %i", 6 * (s->stereo_in + 1), size);

                buf += ssize;

                continue;

            }

            for(j = 0; j <= s->stereo_in; j++){

                for(i = 0; i < 3; i++){

                    s->ch[j].median[i] = wp_exp2(AV_RL16(buf));

                    buf += 2;

                }

            }

            got_entropy = 1;

            break;

        case WP_ID_HYBRID:

            if(s->hybrid_bitrate){

                for(i = 0; i <= s->stereo_in; i++){

                    s->ch[i].slow_level = wp_exp2(AV_RL16(buf));

                    buf += 2;

                    size -= 2;

                }

            }

            for(i = 0; i < (s->stereo_in + 1); i++){

                s->ch[i].bitrate_acc = AV_RL16(buf) << 16;

                buf += 2;

                size -= 2;

            }

            if(size > 0){

                for(i = 0; i < (s->stereo_in + 1); i++){

                    s->ch[i].bitrate_delta = wp_exp2((int16_t)AV_RL16(buf));

                    buf += 2;

                }

            }else{

                for(i = 0; i < (s->stereo_in + 1); i++)

                    s->ch[i].bitrate_delta = 0;

            }

            got_hybrid = 1;

            break;

        case WP_ID_INT32INFO:

            if(size != 4){

                av_log(avctx, AV_LOG_ERROR, "Invalid INT32INFO, size = %i, sent_bits = %i\n", size, *buf);

                buf += ssize;

                continue;

            }

            if(buf[0])

                s->extra_bits = buf[0];

            else if(buf[1])

                s->shift = buf[1];

            else if(buf[2]){

                s->and = s->or = 1;

                s->shift = buf[2];

            }else if(buf[3]){

                s->and = 1;

                s->shift = buf[3];

            }

            buf += 4;

            break;

        case WP_ID_FLOATINFO:

            if(size != 4){

                av_log(avctx, AV_LOG_ERROR, "Invalid FLOATINFO, size = %i\n", size);

                buf += ssize;

                continue;

            }

            s->float_flag = buf[0];

            s->float_shift = buf[1];

            s->float_max_exp = buf[2];

            buf += 4;

            got_float = 1;

            break;

        case WP_ID_DATA:

            s->sc.offset = buf - orig_buf;

            s->sc.size   = size * 8;

            init_get_bits(&s->gb, buf, size * 8);

            s->data_size = size * 8;

            buf += size;

            got_bs = 1;

            break;

        case WP_ID_EXTRABITS:

            if(size <= 4){

                av_log(avctx, AV_LOG_ERROR, "Invalid EXTRABITS, size = %i\n", size);

                buf += size;

                continue;

            }

            s->extra_sc.offset = buf - orig_buf;

            s->extra_sc.size   = size * 8;

            init_get_bits(&s->gb_extra_bits, buf, size * 8);

            s->crc_extra_bits = get_bits_long(&s->gb_extra_bits, 32);

            buf += size;

            s->got_extra_bits = 1;

            break;

        case WP_ID_CHANINFO:

            if(size <= 1){

                av_log(avctx, AV_LOG_ERROR, "Insufficient channel information\n");

                return -1;

            }

            chan = *buf++;

            switch(size - 2){

            case 0:

                chmask = *buf;

                break;

            case 1:

                chmask = AV_RL16(buf);

                break;

            case 2:

                chmask = AV_RL24(buf);

                break;

            case 3:

                chmask = AV_RL32(buf);

                break;

            case 5:

                chan |= (buf[1] & 0xF) << 8;

                chmask = AV_RL24(buf + 2);

                break;

            default:

                av_log(avctx, AV_LOG_ERROR, "Invalid channel info size %d\n", size);

                chan = avctx->channels;

                chmask = avctx->channel_layout;

            }

            if(chan != avctx->channels){

                av_log(avctx, AV_LOG_ERROR, "Block reports total %d channels, decoder believes it's %d channels\n",

                       chan, avctx->channels);

                return -1;

            }

            if(!avctx->channel_layout)

                avctx->channel_layout = chmask;

            buf += size - 1;

            break;

        default:

            buf += size;

        }

        if(id & WP_IDF_ODD) buf++;

    }

    if(!s->samples_left){

        if(!got_terms){

            av_log(avctx, AV_LOG_ERROR, "No block with decorrelation terms\n");

            return -1;

        }

        if(!got_weights){

            av_log(avctx, AV_LOG_ERROR, "No block with decorrelation weights\n");

            return -1;

        }

        if(!got_samples){

            av_log(avctx, AV_LOG_ERROR, "No block with decorrelation samples\n");

            return -1;

        }

        if(!got_entropy){

            av_log(avctx, AV_LOG_ERROR, "No block with entropy info\n");

            return -1;

        }

        if(s->hybrid && !got_hybrid){

            av_log(avctx, AV_LOG_ERROR, "Hybrid config not found\n");

            return -1;

        }

        if(!got_bs){

            av_log(avctx, AV_LOG_ERROR, "Packed samples not found\n");

            return -1;

        }

        if(!got_float && avctx->sample_fmt == AV_SAMPLE_FMT_FLT){

            av_log(avctx, AV_LOG_ERROR, "Float information not found\n");

            return -1;

        }

        if(s->got_extra_bits && avctx->sample_fmt != AV_SAMPLE_FMT_FLT){

            const int size = get_bits_left(&s->gb_extra_bits);

            const int wanted = s->samples * s->extra_bits << s->stereo_in;

            if(size < wanted){

                av_log(avctx, AV_LOG_ERROR, "Too small EXTRABITS\n");

                s->got_extra_bits = 0;

            }

        }

        s->samples_left = s->samples;

    }else{

        init_get_bits(&s->gb, orig_buf + s->sc.offset, s->sc.size);

        skip_bits_long(&s->gb, s->sc.bits_used);

        if(s->got_extra_bits){

            init_get_bits(&s->gb_extra_bits, orig_buf + s->extra_sc.offset,

                          s->extra_sc.size);

            skip_bits_long(&s->gb_extra_bits, s->extra_sc.bits_used);

        }

    }

    if(s->stereo_in){

        if(avctx->sample_fmt == AV_SAMPLE_FMT_S16)

            samplecount = wv_unpack_stereo(s, &s->gb, samples, AV_SAMPLE_FMT_S16);

        else if(avctx->sample_fmt == AV_SAMPLE_FMT_S32)

            samplecount = wv_unpack_stereo(s, &s->gb, samples, AV_SAMPLE_FMT_S32);

        else

            samplecount = wv_unpack_stereo(s, &s->gb, samples, AV_SAMPLE_FMT_FLT);

        samplecount >>= 1;

    }else{

        const int channel_stride = avctx->channels;

        if(avctx->sample_fmt == AV_SAMPLE_FMT_S16)

            samplecount = wv_unpack_mono(s, &s->gb, samples, AV_SAMPLE_FMT_S16);

        else if(avctx->sample_fmt == AV_SAMPLE_FMT_S32)

            samplecount = wv_unpack_mono(s, &s->gb, samples, AV_SAMPLE_FMT_S32);

        else

            samplecount = wv_unpack_mono(s, &s->gb, samples, AV_SAMPLE_FMT_FLT);

        if(s->stereo && avctx->sample_fmt == AV_SAMPLE_FMT_S16){

            int16_t *dst = (int16_t*)samples + 1;

            int16_t *src = (int16_t*)samples;

            int cnt = samplecount;

            while(cnt--){

                *dst = *src;

                src += channel_stride;

                dst += channel_stride;

            }

        }else if(s->stereo && avctx->sample_fmt == AV_SAMPLE_FMT_S32){

            int32_t *dst = (int32_t*)samples + 1;

            int32_t *src = (int32_t*)samples;

            int cnt = samplecount;

            while(cnt--){

                *dst = *src;

                src += channel_stride;

                dst += channel_stride;

            }

        }else if(s->stereo){

            float *dst = (float*)samples + 1;

            float *src = (float*)samples;

            int cnt = samplecount;

            while(cnt--){

                *dst = *src;

                src += channel_stride;

                dst += channel_stride;

            }

        }

    }

    wc->samples_left = s->samples_left;

    return samplecount * bpp;

}


void qemu_send_packet(VLANClientState *vc, const uint8_t *buf, int size)

{

    VLANState *vlan = vc->vlan;

    VLANPacket *packet;

    if (vc->link_down)

        return;

#ifdef DEBUG_NET

    printf("vlan %d send:\n", vlan->id);

    hex_dump(stdout, buf, size);

#endif

    if (vlan->delivering) {

        packet = qemu_malloc(sizeof(VLANPacket) + size);

        packet->next = vlan->send_queue;

        packet->sender = vc;

        packet->size = size;

        memcpy(packet->data, buf, size);

        vlan->send_queue = packet;

    } else {

        vlan->delivering = 1;

        qemu_deliver_packet(vc, buf, size);

        while ((packet = vlan->send_queue) != NULL) {

            qemu_deliver_packet(packet->sender, packet->data, packet->size);

            vlan->send_queue = packet->next;

            qemu_free(packet);

        }

        vlan->delivering = 0;

    }

}


static void test_bmdma_one_sector_short_prdt(void)

{

    QPCIDevice *dev;

    void *bmdma_base, *ide_base;

    uint8_t status;

    /* Read 2 sectors but only give 1 sector in PRDT */

    PrdtEntry prdt[] = {

        {

            .addr = 0,

            .size = cpu_to_le32(0x200 | PRDT_EOT),

        },

    };

    dev = get_pci_device(&bmdma_base, &ide_base);

    /* Normal request */

    status = send_dma_request(CMD_READ_DMA, 0, 2,

                              prdt, ARRAY_SIZE(prdt), NULL);

    g_assert_cmphex(status, ==, 0);

    assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR);

    /* Abort the request before it completes */

    status = send_dma_request(CMD_READ_DMA | CMDF_ABORT, 0, 2,

                              prdt, ARRAY_SIZE(prdt), NULL);

    g_assert_cmphex(status, ==, 0);

    assert_bit_clear(qpci_io_readb(dev, ide_base + reg_status), DF | ERR);

}


static uint32_t regtype_to_ss(uint8_t type)

{

    if (type & PCI_BASE_ADDRESS_MEM_TYPE_64) {

        return 3;

    }

    if (type == PCI_BASE_ADDRESS_SPACE_IO) {

        return 1;

    }

    return 2;

}


static int swf_read_header(AVFormatContext *s, AVFormatParameters *ap)

{

    ByteIOContext *pb = &s->pb;

    int nbits, len, frame_rate, tag, v;

    AVStream *st;

    if ((get_be32(pb) & 0xffffff00) != MKBETAG('F', 'W', 'S', 0))

        return -EIO;

    get_le32(pb);

    /* skip rectangle size */

    nbits = get_byte(pb) >> 3;

    len = (4 * nbits - 3 + 7) / 8;

    url_fskip(pb, len);

    frame_rate = get_le16(pb);

    get_le16(pb); /* frame count */

    for(;;) {

        tag = get_swf_tag(pb, &len);

        if (tag < 0) {

            fprintf(stderr, "No streaming found in SWF\n");

            return -EIO;

        }

        if (tag == TAG_STREAMHEAD) {

            /* streaming found */

            get_byte(pb);

            v = get_byte(pb);

            get_le16(pb);

            if (len!=4)

                url_fskip(pb,len-4);

            /* if mp3 streaming found, OK */

            if ((v & 0x20) != 0) {

                st = av_new_stream(s, 0);

                if (!st)

                    return -ENOMEM;

                if (v & 0x01)

                    st->codec.channels = 2;

                else

                    st->codec.channels = 1;

                switch((v>> 2) & 0x03) {

                case 1:

                    st->codec.sample_rate = 11025;

                    break;

                case 2:

                    st->codec.sample_rate = 22050;

                    break;

                case 3:

                    st->codec.sample_rate = 44100;

                    break;

                default:

                    av_free(st);

                    return -EIO;

                }

                st->codec.codec_type = CODEC_TYPE_AUDIO;

                st->codec.codec_id = CODEC_ID_MP2;

                break;

            }

        } else {

            url_fskip(pb, len);

        }

    }

    return 0;

}


static int crystalhd_receive_frame(AVCodecContext *avctx, AVFrame *frame)

{

    BC_STATUS bc_ret;

    BC_DTS_STATUS decoder_status = { 0, };

    CopyRet rec_ret;

    CHDContext *priv   = avctx->priv_data;

    HANDLE dev         = priv->dev;

    int got_frame = 0;

    av_log(avctx, AV_LOG_VERBOSE, "CrystalHD: receive_frame\n");

    bc_ret = DtsGetDriverStatus(dev, &decoder_status);

    if (bc_ret != BC_STS_SUCCESS) {

        av_log(avctx, AV_LOG_ERROR, "CrystalHD: GetDriverStatus failed\n");

        return -1;

    }

    if (decoder_status.ReadyListCount == 0) {

        av_log(avctx, AV_LOG_INFO, "CrystalHD: Insufficient frames ready. Returning\n");

        return AVERROR(EAGAIN);

    }

    rec_ret = receive_frame(avctx, frame, &got_frame);

    if (rec_ret == RET_ERROR) {

        return -1;

    } else if (got_frame == 0) {

        return AVERROR(EAGAIN);

    } else {

        return 0;

    }

}


av_cold int ff_opus_parse_extradata(AVCodecContext *avctx,

                                    OpusContext *s)

{

    static const uint8_t default_channel_map[2] = { 0, 1 };

    int (*channel_reorder)(int, int) = channel_reorder_unknown;

    const uint8_t *extradata, *channel_map;

    int extradata_size;

    int version, channels, map_type, streams, stereo_streams, i, j;

    uint64_t layout;

    if (!avctx->extradata) {

        if (avctx->channels > 2) {

            av_log(avctx, AV_LOG_ERROR,

                   "Multichannel configuration without extradata.\n");

            return AVERROR(EINVAL);

        }

        extradata      = opus_default_extradata;

        extradata_size = sizeof(opus_default_extradata);

    } else {

        extradata = avctx->extradata;

        extradata_size = avctx->extradata_size;

    }

    if (extradata_size < 19) {

        av_log(avctx, AV_LOG_ERROR, "Invalid extradata size: %d\n",

               extradata_size);

        return AVERROR_INVALIDDATA;

    }

    version = extradata[8];

    if (version > 15) {

        avpriv_request_sample(avctx, "Extradata version %d", version);

        return AVERROR_PATCHWELCOME;

    }

    avctx->delay = AV_RL16(extradata + 10);

    channels = avctx->extradata ? extradata[9] : (avctx->channels == 1) ? 1 : 2;

    if (!channels) {

        av_log(avctx, AV_LOG_ERROR, "Zero channel count specified in the extradata\n");

        return AVERROR_INVALIDDATA;

    }

    s->gain_i = AV_RL16(extradata + 16);

    if (s->gain_i)

        s->gain = ff_exp10(s->gain_i / (20.0 * 256));

    map_type = extradata[18];

    if (!map_type) {

        if (channels > 2) {

            av_log(avctx, AV_LOG_ERROR,

                   "Channel mapping 0 is only specified for up to 2 channels\n");

            return AVERROR_INVALIDDATA;

        }

        layout         = (channels == 1) ? AV_CH_LAYOUT_MONO : AV_CH_LAYOUT_STEREO;

        streams        = 1;

        stereo_streams = channels - 1;

        channel_map    = default_channel_map;

    } else if (map_type == 1 || map_type == 2 || map_type == 255) {

        if (extradata_size < 21 + channels) {

            av_log(avctx, AV_LOG_ERROR, "Invalid extradata size: %d\n",

                   extradata_size);

            return AVERROR_INVALIDDATA;

        }

        streams        = extradata[19];

        stereo_streams = extradata[20];

        if (!streams || stereo_streams > streams ||

            streams + stereo_streams > 255) {

            av_log(avctx, AV_LOG_ERROR,

                   "Invalid stream/stereo stream count: %d/%d\n", streams, stereo_streams);

            return AVERROR_INVALIDDATA;

        }

        if (map_type == 1) {

            if (channels > 8) {

                av_log(avctx, AV_LOG_ERROR,

                       "Channel mapping 1 is only specified for up to 8 channels\n");

                return AVERROR_INVALIDDATA;

            }

            layout = ff_vorbis_channel_layouts[channels - 1];

            channel_reorder = channel_reorder_vorbis;

        } else if (map_type == 2) {

            int ambisonic_order = ff_sqrt(channels) - 1;

            if (channels != (ambisonic_order + 1) * (ambisonic_order + 1)) {

                av_log(avctx, AV_LOG_ERROR,

                       "Channel mapping 2 is only specified for channel counts"

                       " which can be written as (n + 1)^2 for nonnegative integer n\n");

                return AVERROR_INVALIDDATA;

            }

            layout = 0;

        } else

            layout = 0;

        channel_map = extradata + 21;

    } else {

        avpriv_request_sample(avctx, "Mapping type %d", map_type);

        return AVERROR_PATCHWELCOME;

    }

    s->channel_maps = av_mallocz_array(channels, sizeof(*s->channel_maps));

    if (!s->channel_maps)

        return AVERROR(ENOMEM);

    for (i = 0; i < channels; i++) {

        ChannelMap *map = &s->channel_maps[i];

        uint8_t     idx = channel_map[channel_reorder(channels, i)];

        if (idx == 255) {

            map->silence = 1;

            continue;

        } else if (idx >= streams + stereo_streams) {

            av_log(avctx, AV_LOG_ERROR,

                   "Invalid channel map for output channel %d: %d\n", i, idx);

            return AVERROR_INVALIDDATA;

        }

        /* check that we did not see this index yet */

        map->copy = 0;

        for (j = 0; j < i; j++)

            if (channel_map[channel_reorder(channels, j)] == idx) {

                map->copy     = 1;

                map->copy_idx = j;

                break;

            }

        if (idx < 2 * stereo_streams) {

            map->stream_idx  = idx / 2;

            map->channel_idx = idx & 1;

        } else {

            map->stream_idx  = idx - stereo_streams;

            map->channel_idx = 0;

        }

    }

    avctx->channels       = channels;

    avctx->channel_layout = layout;

    s->nb_streams         = streams;

    s->nb_stereo_streams  = stereo_streams;

    return 0;

}


uint32 float32_to_uint32_round_to_zero( float32 a STATUS_PARAM )

{

    int64_t v;

    uint32 res;

    v = float32_to_int64_round_to_zero(a STATUS_VAR);

    if (v < 0) {

        res = 0;

        float_raise( float_flag_invalid STATUS_VAR);

    } else if (v > 0xffffffff) {

        res = 0xffffffff;

        float_raise( float_flag_invalid STATUS_VAR);

    } else {

        res = v;

    }

    return res;

}


static inline abi_long do_msgrcv(int msqid, abi_long msgp,

                                 unsigned int msgsz, abi_long msgtyp,

                                 int msgflg)

{

    struct target_msgbuf *target_mb;

    char *target_mtext;

    struct msgbuf *host_mb;

    abi_long ret = 0;

    if (!lock_user_struct(VERIFY_WRITE, target_mb, msgp, 0))

        return -TARGET_EFAULT;

    host_mb = malloc(msgsz+sizeof(long));

    ret = get_errno(msgrcv(msqid, host_mb, msgsz, tswapal(msgtyp), msgflg));

    if (ret > 0) {

        abi_ulong target_mtext_addr = msgp + sizeof(abi_ulong);

        target_mtext = lock_user(VERIFY_WRITE, target_mtext_addr, ret, 0);

        if (!target_mtext) {

            ret = -TARGET_EFAULT;

            goto end;

        }

        memcpy(target_mb->mtext, host_mb->mtext, ret);

        unlock_user(target_mtext, target_mtext_addr, ret);

    }

    target_mb->mtype = tswapal(host_mb->mtype);

    free(host_mb);

end:

    if (target_mb)

        unlock_user_struct(target_mb, msgp, 1);

    return ret;

}


restore_sigcontext(CPUM68KState *env, struct target_sigcontext *sc, int *pd0)

{

    int err = 0;

    int temp;

    __get_user(env->aregs[7], &sc->sc_usp);

    __get_user(env->dregs[1], &sc->sc_d1);

    __get_user(env->aregs[0], &sc->sc_a0);

    __get_user(env->aregs[1], &sc->sc_a1);

    __get_user(env->pc, &sc->sc_pc);

    __get_user(temp, &sc->sc_sr);

    env->sr = (env->sr & 0xff00) | (temp & 0xff);

    *pd0 = tswapl(sc->sc_d0);

    return err;

}


static ssize_t mp_pacl_getxattr(FsContext *ctx, const char *path,

                                const char *name, void *value, size_t size)

{

    char *buffer;

    ssize_t ret;

    buffer = rpath(ctx, path);

    ret = lgetxattr(buffer, MAP_ACL_ACCESS, value, size);

    g_free(buffer);

    return ret;

}