static int set_sps(HEVCContext *s, const HEVCSPS *sps)

{

    int ret;

    int num = 0, den = 0;

    pic_arrays_free(s);

    ret = pic_arrays_init(s, sps);

    if (ret < 0)

        goto fail;

    s->avctx->coded_width         = sps->width;

    s->avctx->coded_height        = sps->height;

    s->avctx->width               = sps->output_width;

    s->avctx->height              = sps->output_height;

    s->avctx->pix_fmt             = sps->pix_fmt;

    s->avctx->sample_aspect_ratio = sps->vui.sar;

    s->avctx->has_b_frames        = sps->temporal_layer[sps->max_sub_layers - 1].num_reorder_pics;

    if (sps->vui.video_signal_type_present_flag)

        s->avctx->color_range = sps->vui.video_full_range_flag ? AVCOL_RANGE_JPEG

                                                               : AVCOL_RANGE_MPEG;

    else

        s->avctx->color_range = AVCOL_RANGE_MPEG;

    if (sps->vui.colour_description_present_flag) {

        s->avctx->color_primaries = sps->vui.colour_primaries;

        s->avctx->color_trc       = sps->vui.transfer_characteristic;

        s->avctx->colorspace      = sps->vui.matrix_coeffs;

    } else {

        s->avctx->color_primaries = AVCOL_PRI_UNSPECIFIED;

        s->avctx->color_trc       = AVCOL_TRC_UNSPECIFIED;

        s->avctx->colorspace      = AVCOL_SPC_UNSPECIFIED;

    }

    ff_hevc_pred_init(&s->hpc,     sps->bit_depth);

    ff_hevc_dsp_init (&s->hevcdsp, sps->bit_depth);

    ff_videodsp_init (&s->vdsp,    sps->bit_depth);

    if (sps->sao_enabled) {

        av_frame_unref(s->tmp_frame);

        ret = ff_get_buffer(s->avctx, s->tmp_frame, AV_GET_BUFFER_FLAG_REF);

        if (ret < 0)

            goto fail;

        s->frame = s->tmp_frame;

    }

    s->sps = sps;

    s->vps = (HEVCVPS*) s->vps_list[s->sps->vps_id]->data;

    if (s->vps->vps_timing_info_present_flag) {

        num = s->vps->vps_num_units_in_tick;

        den = s->vps->vps_time_scale;

    } else if (sps->vui.vui_timing_info_present_flag) {

        num = sps->vui.vui_num_units_in_tick;

        den = sps->vui.vui_time_scale;

    }

    if (num != 0 && den != 0)

        av_reduce(&s->avctx->time_base.num, &s->avctx->time_base.den,

                  num, den, 1 << 30);

    return 0;

fail:

    pic_arrays_free(s);

    s->sps = NULL;

    return ret;

}


yuv2mono_2_c_template(SwsContext *c, const int16_t *buf[2],

                      const int16_t *ubuf[2], const int16_t *vbuf[2],

                      const int16_t *abuf[2], uint8_t *dest, int dstW,

                      int yalpha, int uvalpha, int y,

                      enum AVPixelFormat target)

{

    const int16_t *buf0  = buf[0],  *buf1  = buf[1];

    const uint8_t * const d128 = dither_8x8_220[y & 7];

    int  yalpha1 = 4096 - yalpha;

    int i;

    if (c->flags & SWS_ERROR_DIFFUSION) {

        int err = 0;

        int acc = 0;

        for (i = 0; i < dstW; i +=2) {

            int Y;

            Y = (buf0[i + 0] * yalpha1 + buf1[i + 0] * yalpha) >> 19;

            Y += (7*err + 1*c->dither_error[0][i] + 5*c->dither_error[0][i+1] + 3*c->dither_error[0][i+2] + 8 - 256)>>4;

            c->dither_error[0][i] = err;

            acc = 2*acc + (Y >= 128);

            Y -= 220*(acc&1);

            err = (buf0[i + 1] * yalpha1 + buf1[i + 1] * yalpha) >> 19;

            err += (7*Y + 1*c->dither_error[0][i+1] + 5*c->dither_error[0][i+2] + 3*c->dither_error[0][i+3] + 8 - 256)>>4;

            c->dither_error[0][i+1] = Y;

            acc = 2*acc + (err >= 128);

            err -= 220*(acc&1);

            if ((i & 7) == 6)

                output_pixel(*dest++, acc);

        }

        c->dither_error[0][i] = err;

    } else {

    for (i = 0; i < dstW; i += 8) {

        int Y, acc = 0;

        Y = (buf0[i + 0] * yalpha1 + buf1[i + 0] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[0]);

        Y = (buf0[i + 1] * yalpha1 + buf1[i + 1] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[1]);

        Y = (buf0[i + 2] * yalpha1 + buf1[i + 2] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[2]);

        Y = (buf0[i + 3] * yalpha1 + buf1[i + 3] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[3]);

        Y = (buf0[i + 4] * yalpha1 + buf1[i + 4] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[4]);

        Y = (buf0[i + 5] * yalpha1 + buf1[i + 5] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[5]);

        Y = (buf0[i + 6] * yalpha1 + buf1[i + 6] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[6]);

        Y = (buf0[i + 7] * yalpha1 + buf1[i + 7] * yalpha) >> 19;

        accumulate_bit(acc, Y + d128[7]);

        output_pixel(*dest++, acc);

    }

    }

}


static double eval_expr(Parser * p, AVEvalExpr * e) {

    switch (e->type) {

        case e_value:  return e->value;

        case e_const:  return e->value * p->const_value[e->a.const_index];

        case e_func0:  return e->value * e->a.func0(eval_expr(p, e->param[0]));

        case e_func1:  return e->value * e->a.func1(p->opaque, eval_expr(p, e->param[0]));

        case e_func2:  return e->value * e->a.func2(p->opaque, eval_expr(p, e->param[0]), eval_expr(p, e->param[1]));

        case e_squish: return 1/(1+exp(4*eval_expr(p, e->param[0])));

        case e_gauss: { double d = eval_expr(p, e->param[0]); return exp(-d*d/2)/sqrt(2*M_PI); }

        case e_ld:     return e->value * p->var[clip(eval_expr(p, e->param[0]), 0, VARS-1)];

        case e_while: {

            double d;

            while(eval_expr(p, e->param[0]))

                d=eval_expr(p, e->param[1]);

            return d;

        }

        default: {

            double d = eval_expr(p, e->param[0]);

            double d2 = eval_expr(p, e->param[1]);

            switch (e->type) {

                case e_mod: return e->value * (d - floor(d/d2)*d2);

                case e_max: return e->value * (d >  d2 ?   d : d2);

                case e_min: return e->value * (d <  d2 ?   d : d2);

                case e_eq:  return e->value * (d == d2 ? 1.0 : 0.0);

                case e_gt:  return e->value * (d >  d2 ? 1.0 : 0.0);

                case e_gte: return e->value * (d >= d2 ? 1.0 : 0.0);

                case e_pow: return e->value * pow(d, d2);

                case e_mul: return e->value * (d * d2);

                case e_div: return e->value * (d / d2);

                case e_add: return e->value * (d + d2);

                case e_last:return d2;

                case e_st : return e->value * (p->var[clip(d, 0, VARS-1)]= d2);

            }

        }

    }

    return NAN;

}


static int build_filter(ResampleContext *c, void *filter, double factor, int tap_count, int alloc, int phase_count, int scale,

                        int filter_type, int kaiser_beta){

    int ph, i;

    double x, y, w;

    double *tab = av_malloc_array(tap_count,  sizeof(*tab));

    const int center= (tap_count-1)/2;

    if (!tab)

        return AVERROR(ENOMEM);

    /* if upsampling, only need to interpolate, no filter */

    if (factor > 1.0)

        factor = 1.0;

    for(ph=0;ph<phase_count;ph++) {

        double norm = 0;

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

            x = M_PI * ((double)(i - center) - (double)ph / phase_count) * factor;

            if (x == 0) y = 1.0;

            else        y = sin(x) / x;

            switch(filter_type){

            case SWR_FILTER_TYPE_CUBIC:{

                const float d= -0.5; //first order derivative = -0.5

                x = fabs(((double)(i - center) - (double)ph / phase_count) * factor);

                if(x<1.0) y= 1 - 3*x*x + 2*x*x*x + d*(            -x*x + x*x*x);

                else      y=                       d*(-4 + 8*x - 5*x*x + x*x*x);

                break;}

            case SWR_FILTER_TYPE_BLACKMAN_NUTTALL:

                w = 2.0*x / (factor*tap_count) + M_PI;

                y *= 0.3635819 - 0.4891775 * cos(w) + 0.1365995 * cos(2*w) - 0.0106411 * cos(3*w);

                break;

            case SWR_FILTER_TYPE_KAISER:

                w = 2.0*x / (factor*tap_count*M_PI);

                y *= bessel(kaiser_beta*sqrt(FFMAX(1-w*w, 0)));

                break;

            default:

                av_assert0(0);

            }

            tab[i] = y;

            norm += y;

        }

        /* normalize so that an uniform color remains the same */

        switch(c->format){

        case AV_SAMPLE_FMT_S16P:

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

                ((int16_t*)filter)[ph * alloc + i] = av_clip(lrintf(tab[i] * scale / norm), INT16_MIN, INT16_MAX);

            break;

        case AV_SAMPLE_FMT_S32P:

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

                ((int32_t*)filter)[ph * alloc + i] = av_clipl_int32(llrint(tab[i] * scale / norm));

            break;

        case AV_SAMPLE_FMT_FLTP:

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

                ((float*)filter)[ph * alloc + i] = tab[i] * scale / norm;

            break;

        case AV_SAMPLE_FMT_DBLP:

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

                ((double*)filter)[ph * alloc + i] = tab[i] * scale / norm;

            break;

        }

    }

#if 0

    {

#define LEN 1024

        int j,k;

        double sine[LEN + tap_count];

        double filtered[LEN];

        double maxff=-2, minff=2, maxsf=-2, minsf=2;

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

            double ss=0, sf=0, ff=0;

            for(j=0; j<LEN+tap_count; j++)

                sine[j]= cos(i*j*M_PI/LEN);

            for(j=0; j<LEN; j++){

                double sum=0;

                ph=0;

                for(k=0; k<tap_count; k++)

                    sum += filter[ph * tap_count + k] * sine[k+j];

                filtered[j]= sum / (1<<FILTER_SHIFT);

                ss+= sine[j + center] * sine[j + center];

                ff+= filtered[j] * filtered[j];

                sf+= sine[j + center] * filtered[j];

            }

            ss= sqrt(2*ss/LEN);

            ff= sqrt(2*ff/LEN);

            sf= 2*sf/LEN;

            maxff= FFMAX(maxff, ff);

            minff= FFMIN(minff, ff);

            maxsf= FFMAX(maxsf, sf);

            minsf= FFMIN(minsf, sf);

            if(i%11==0){

                av_log(NULL, AV_LOG_ERROR, "i:%4d ss:%f ff:%13.6e-%13.6e sf:%13.6e-%13.6e\n", i, ss, maxff, minff, maxsf, minsf);

                minff=minsf= 2;

                maxff=maxsf= -2;

            }

        }

    }

#endif

    av_free(tab);

    return 0;

}


void avcodec_get_context_defaults2(AVCodecContext *s, enum CodecType codec_type){

    int flags=0;

    memset(s, 0, sizeof(AVCodecContext));

    s->av_class= &av_codec_context_class;

    s->codec_type = codec_type;

    if(codec_type == CODEC_TYPE_AUDIO)

        flags= AV_OPT_FLAG_AUDIO_PARAM;

    else if(codec_type == CODEC_TYPE_VIDEO)

        flags= AV_OPT_FLAG_VIDEO_PARAM;

    else if(codec_type == CODEC_TYPE_SUBTITLE)

        flags= AV_OPT_FLAG_SUBTITLE_PARAM;

    av_opt_set_defaults2(s, flags, flags);

    s->rc_eq= av_strdup("tex^qComp");

    s->time_base= (AVRational){0,1};

    s->get_buffer= avcodec_default_get_buffer;

    s->release_buffer= avcodec_default_release_buffer;

    s->get_format= avcodec_default_get_format;

    s->execute= avcodec_default_execute;

    s->sample_aspect_ratio= (AVRational){0,1};

    s->pix_fmt= PIX_FMT_NONE;

    s->sample_fmt= SAMPLE_FMT_S16; // FIXME: set to NONE

    s->palctrl = NULL;

    s->reget_buffer= avcodec_default_reget_buffer;

}


static void dec_float(DisasContext *dc, uint32_t insn)

{

    uint32_t op0;

    uint32_t ra, rb, rd;

    op0 = extract32(insn, 0, 8);

    ra = extract32(insn, 16, 5);

    rb = extract32(insn, 11, 5);

    rd = extract32(insn, 21, 5);

    switch (op0) {

    case 0x00:    /* lf.add.s */

        LOG_DIS("lf.add.s r%d, r%d, r%d\n", rd, ra, rb);

        gen_helper_float_add_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x01:    /* lf.sub.s */

        LOG_DIS("lf.sub.s r%d, r%d, r%d\n", rd, ra, rb);

        gen_helper_float_sub_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x02:    /* lf.mul.s */

        LOG_DIS("lf.mul.s r%d, r%d, r%d\n", rd, ra, rb);

        if (ra != 0 && rb != 0) {

            gen_helper_float_mul_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        } else {

            tcg_gen_ori_tl(fpcsr, fpcsr, FPCSR_ZF);

            tcg_gen_movi_i32(cpu_R[rd], 0x0);

        }

        break;

    case 0x03:    /* lf.div.s */

        LOG_DIS("lf.div.s r%d, r%d, r%d\n", rd, ra, rb);

        gen_helper_float_div_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x04:    /* lf.itof.s */

        LOG_DIS("lf.itof r%d, r%d\n", rd, ra);

        gen_helper_itofs(cpu_R[rd], cpu_env, cpu_R[ra]);

        break;

    case 0x05:    /* lf.ftoi.s */

        LOG_DIS("lf.ftoi r%d, r%d\n", rd, ra);

        gen_helper_ftois(cpu_R[rd], cpu_env, cpu_R[ra]);

        break;

    case 0x06:    /* lf.rem.s */

        LOG_DIS("lf.rem.s r%d, r%d, r%d\n", rd, ra, rb);

        gen_helper_float_rem_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x07:    /* lf.madd.s */

        LOG_DIS("lf.madd.s r%d, r%d, r%d\n", rd, ra, rb);

        gen_helper_float_madd_s(cpu_R[rd], cpu_env, cpu_R[rd],

                                cpu_R[ra], cpu_R[rb]);

        break;

    case 0x08:    /* lf.sfeq.s */

        LOG_DIS("lf.sfeq.s r%d, r%d\n", ra, rb);

        gen_helper_float_eq_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x09:    /* lf.sfne.s */

        LOG_DIS("lf.sfne.s r%d, r%d\n", ra, rb);

        gen_helper_float_ne_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x0a:    /* lf.sfgt.s */

        LOG_DIS("lf.sfgt.s r%d, r%d\n", ra, rb);

        gen_helper_float_gt_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x0b:    /* lf.sfge.s */

        LOG_DIS("lf.sfge.s r%d, r%d\n", ra, rb);

        gen_helper_float_ge_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x0c:    /* lf.sflt.s */

        LOG_DIS("lf.sflt.s r%d, r%d\n", ra, rb);

        gen_helper_float_lt_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x0d:    /* lf.sfle.s */

        LOG_DIS("lf.sfle.s r%d, r%d\n", ra, rb);

        gen_helper_float_le_s(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

/* not used yet, open it when we need or64.  */

/*#ifdef TARGET_OPENRISC64

    case 0x10:     lf.add.d

        LOG_DIS("lf.add.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        gen_helper_float_add_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x11:     lf.sub.d

        LOG_DIS("lf.sub.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        gen_helper_float_sub_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x12:     lf.mul.d

        LOG_DIS("lf.mul.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        if (ra != 0 && rb != 0) {

            gen_helper_float_mul_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        } else {

            tcg_gen_ori_tl(fpcsr, fpcsr, FPCSR_ZF);

            tcg_gen_movi_i64(cpu_R[rd], 0x0);

        }

        break;

    case 0x13:     lf.div.d

        LOG_DIS("lf.div.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        gen_helper_float_div_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x14:     lf.itof.d

        LOG_DIS("lf.itof r%d, r%d\n", rd, ra);

        check_of64s(dc);

        gen_helper_itofd(cpu_R[rd], cpu_env, cpu_R[ra]);

        break;

    case 0x15:     lf.ftoi.d

        LOG_DIS("lf.ftoi r%d, r%d\n", rd, ra);

        check_of64s(dc);

        gen_helper_ftoid(cpu_R[rd], cpu_env, cpu_R[ra]);

        break;

    case 0x16:     lf.rem.d

        LOG_DIS("lf.rem.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        gen_helper_float_rem_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x17:     lf.madd.d

        LOG_DIS("lf.madd.d r%d, r%d, r%d\n", rd, ra, rb);

        check_of64s(dc);

        gen_helper_float_madd_d(cpu_R[rd], cpu_env, cpu_R[rd],

                                cpu_R[ra], cpu_R[rb]);

        break;

    case 0x18:     lf.sfeq.d

        LOG_DIS("lf.sfeq.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_eq_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x1a:     lf.sfgt.d

        LOG_DIS("lf.sfgt.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_gt_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x1b:     lf.sfge.d

        LOG_DIS("lf.sfge.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_ge_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x19:     lf.sfne.d

        LOG_DIS("lf.sfne.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_ne_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x1c:     lf.sflt.d

        LOG_DIS("lf.sflt.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_lt_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

    case 0x1d:     lf.sfle.d

        LOG_DIS("lf.sfle.d r%d, r%d\n", ra, rb);

        check_of64s(dc);

        gen_helper_float_le_d(cpu_sr_f, cpu_env, cpu_R[ra], cpu_R[rb]);

        break;

#endif*/

    default:

        gen_illegal_exception(dc);

        break;

    }

}


void rng_backend_open(RngBackend *s, Error **errp)

{

    object_property_set_bool(OBJECT(s), true, "opened", errp);

}


static void encode_quant_matrix(VC2EncContext *s)

{

    int level, custom_quant_matrix = 0;

    if (s->wavelet_depth > 4 || s->quant_matrix != VC2_QM_DEF)

        custom_quant_matrix = 1;

    put_bits(&s->pb, 1, custom_quant_matrix);

    if (custom_quant_matrix) {

        init_custom_qm(s);

        put_vc2_ue_uint(&s->pb, s->quant[0][0]);

        for (level = 0; level < s->wavelet_depth; level++) {

            put_vc2_ue_uint(&s->pb, s->quant[level][1]);

            put_vc2_ue_uint(&s->pb, s->quant[level][2]);

            put_vc2_ue_uint(&s->pb, s->quant[level][3]);

        }

    } else {

        for (level = 0; level < s->wavelet_depth; level++) {

            s->quant[level][0] = ff_dirac_default_qmat[s->wavelet_idx][level][0];

            s->quant[level][1] = ff_dirac_default_qmat[s->wavelet_idx][level][1];

            s->quant[level][2] = ff_dirac_default_qmat[s->wavelet_idx][level][2];

            s->quant[level][3] = ff_dirac_default_qmat[s->wavelet_idx][level][3];

        }

    }

}


static void fix_bitshift(ShortenContext *s, int32_t *buffer)

{

    int i;

    if (s->bitshift != 0)

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

            buffer[s->nwrap + i] <<= s->bitshift;

}


static void wav_capture_destroy (void *opaque)

{

    WAVState *wav = opaque;

    AUD_del_capture (wav->cap, wav);

}


static uint32_t m5206_mbar_readw(void *opaque, target_phys_addr_t offset)

{

    m5206_mbar_state *s = (m5206_mbar_state *)opaque;

    int width;

    offset &= 0x3ff;

    if (offset > 0x200) {

        hw_error("Bad MBAR read offset 0x%x", (int)offset);

    }

    width = m5206_mbar_width[offset >> 2];

    if (width > 2) {

        uint32_t val;

        val = m5206_mbar_readl(opaque, offset & ~3);

        if ((offset & 3) == 0)

            val >>= 16;

        return val & 0xffff;

    } else if (width < 2) {

        uint16_t val;

        val = m5206_mbar_readb(opaque, offset) << 8;

        val |= m5206_mbar_readb(opaque, offset + 1);

        return val;

    }

    return m5206_mbar_read(s, offset, 2);

}


uint32_t pci_data_read(PCIBus *s, uint32_t addr, int len)

{

    PCIDevice *pci_dev = pci_dev_find_by_addr(s, addr);

    uint32_t config_addr = addr & (PCI_CONFIG_SPACE_SIZE - 1);

    uint32_t val;

    assert(len == 1 || len == 2 || len == 4);

    if (!pci_dev) {

        return ~0x0;

    }

    val = pci_dev->config_read(pci_dev, config_addr, len);

    PCI_DPRINTF("%s: %s: addr=%02"PRIx32" val=%08"PRIx32" len=%d\n",

                __func__, pci_dev->name, config_addr, val, len);

    return val;

}


static int decode_nal_units(H264Context *h, const uint8_t *buf, int buf_size){

    MpegEncContext * const s = &h->s;

    AVCodecContext * const avctx= s->avctx;

    int buf_index=0;

    H264Context *hx; ///< thread context

    int context_count = 0;

    int next_avc= h->is_avc ? 0 : buf_size;

    h->max_contexts = (HAVE_THREADS && (s->avctx->active_thread_type&FF_THREAD_SLICE)) ? avctx->thread_count : 1;

#if 0

    int i;

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

        av_log(NULL, AV_LOG_ERROR,"%02X ", buf[i]);

    }

#endif

    if(!(s->flags2 & CODEC_FLAG2_CHUNKS)){

        h->current_slice = 0;

        if (!s->first_field)

            s->current_picture_ptr= NULL;

        ff_h264_reset_sei(h);

    }

    for(;;){

        int consumed;

        int dst_length;

        int bit_length;

        const uint8_t *ptr;

        int i, nalsize = 0;

        int err;

        if(buf_index >= next_avc) {

            if(buf_index >= buf_size) break;

            nalsize = 0;

            for(i = 0; i < h->nal_length_size; i++)

                nalsize = (nalsize << 8) | buf[buf_index++];

            if(nalsize <= 0 || nalsize > buf_size - buf_index){

                av_log(h->s.avctx, AV_LOG_ERROR, "AVC: nal size %d\n", nalsize);

                break;

            }

            next_avc= buf_index + nalsize;

        } else {

            // start code prefix search

            for(; buf_index + 3 < next_avc; buf_index++){

                // This should always succeed in the first iteration.

                if(buf[buf_index] == 0 && buf[buf_index+1] == 0 && buf[buf_index+2] == 1)

                    break;

            }

            if(buf_index+3 >= buf_size) break;

            buf_index+=3;

            if(buf_index >= next_avc) continue;

        }

        hx = h->thread_context[context_count];

        ptr= ff_h264_decode_nal(hx, buf + buf_index, &dst_length, &consumed, next_avc - buf_index);

        if (ptr==NULL || dst_length < 0){

            return -1;

        }

        i= buf_index + consumed;

        if((s->workaround_bugs & FF_BUG_AUTODETECT) && i+3<next_avc &&

           buf[i]==0x00 && buf[i+1]==0x00 && buf[i+2]==0x01 && buf[i+3]==0xE0)

            s->workaround_bugs |= FF_BUG_TRUNCATED;

        if(!(s->workaround_bugs & FF_BUG_TRUNCATED)){

        while(ptr[dst_length - 1] == 0 && dst_length > 0)

            dst_length--;

        }

        bit_length= !dst_length ? 0 : (8*dst_length - ff_h264_decode_rbsp_trailing(h, ptr + dst_length - 1));

        if(s->avctx->debug&FF_DEBUG_STARTCODE){

            av_log(h->s.avctx, AV_LOG_DEBUG, "NAL %d/%d at %d/%d length %d\n", hx->nal_unit_type, hx->nal_ref_idc, buf_index, buf_size, dst_length);

        }

        if (h->is_avc && (nalsize != consumed) && nalsize){

            av_log(h->s.avctx, AV_LOG_DEBUG, "AVC: Consumed only %d bytes instead of %d\n", consumed, nalsize);

        }

        buf_index += consumed;

        //FIXME do not discard SEI id

        if(avctx->skip_frame >= AVDISCARD_NONREF && h->nal_ref_idc  == 0)

            continue;

      again:

        err = 0;

        switch(hx->nal_unit_type){

        case NAL_IDR_SLICE:

            if (h->nal_unit_type != NAL_IDR_SLICE) {

                av_log(h->s.avctx, AV_LOG_ERROR, "Invalid mix of idr and non-idr slices");

                return -1;

            }

            idr(h); //FIXME ensure we don't loose some frames if there is reordering

        case NAL_SLICE:

            init_get_bits(&hx->s.gb, ptr, bit_length);

            hx->intra_gb_ptr=

            hx->inter_gb_ptr= &hx->s.gb;

            hx->s.data_partitioning = 0;

            if((err = decode_slice_header(hx, h)))

               break;

            s->current_picture_ptr->key_frame |=

                    (hx->nal_unit_type == NAL_IDR_SLICE) ||

                    (h->sei_recovery_frame_cnt >= 0);

            if (h->current_slice == 1) {

                if(!(s->flags2 & CODEC_FLAG2_CHUNKS)) {

                    decode_postinit(h);

                }

                if (s->avctx->hwaccel && s->avctx->hwaccel->start_frame(s->avctx, NULL, 0) < 0)

                    return -1;

                if(CONFIG_H264_VDPAU_DECODER && s->avctx->codec->capabilities&CODEC_CAP_HWACCEL_VDPAU)

                    ff_vdpau_h264_picture_start(s);

            }

            if(hx->redundant_pic_count==0

               && (avctx->skip_frame < AVDISCARD_NONREF || hx->nal_ref_idc)

               && (avctx->skip_frame < AVDISCARD_BIDIR  || hx->slice_type_nos!=AV_PICTURE_TYPE_B)

               && (avctx->skip_frame < AVDISCARD_NONKEY || hx->slice_type_nos==AV_PICTURE_TYPE_I)

               && avctx->skip_frame < AVDISCARD_ALL){

                if(avctx->hwaccel) {

                    if (avctx->hwaccel->decode_slice(avctx, &buf[buf_index - consumed], consumed) < 0)

                        return -1;

                }else

                if(CONFIG_H264_VDPAU_DECODER && s->avctx->codec->capabilities&CODEC_CAP_HWACCEL_VDPAU){

                    static const uint8_t start_code[] = {0x00, 0x00, 0x01};

                    ff_vdpau_add_data_chunk(s, start_code, sizeof(start_code));

                    ff_vdpau_add_data_chunk(s, &buf[buf_index - consumed], consumed );

                }else

                    context_count++;

            }

            break;

        case NAL_DPA:

            init_get_bits(&hx->s.gb, ptr, bit_length);

            hx->intra_gb_ptr=

            hx->inter_gb_ptr= NULL;

            if ((err = decode_slice_header(hx, h)) < 0)

                break;

            hx->s.data_partitioning = 1;

            break;

        case NAL_DPB:

            init_get_bits(&hx->intra_gb, ptr, bit_length);

            hx->intra_gb_ptr= &hx->intra_gb;

            break;

        case NAL_DPC:

            init_get_bits(&hx->inter_gb, ptr, bit_length);

            hx->inter_gb_ptr= &hx->inter_gb;

            if(hx->redundant_pic_count==0 && hx->intra_gb_ptr && hx->s.data_partitioning

               && s->context_initialized

               && (avctx->skip_frame < AVDISCARD_NONREF || hx->nal_ref_idc)

               && (avctx->skip_frame < AVDISCARD_BIDIR  || hx->slice_type_nos!=AV_PICTURE_TYPE_B)

               && (avctx->skip_frame < AVDISCARD_NONKEY || hx->slice_type_nos==AV_PICTURE_TYPE_I)

               && avctx->skip_frame < AVDISCARD_ALL)

                context_count++;

            break;

        case NAL_SEI:

            init_get_bits(&s->gb, ptr, bit_length);

            ff_h264_decode_sei(h);

            break;

        case NAL_SPS:

            init_get_bits(&s->gb, ptr, bit_length);

            ff_h264_decode_seq_parameter_set(h);

            if(s->flags& CODEC_FLAG_LOW_DELAY ||

              (h->sps.bitstream_restriction_flag && !h->sps.num_reorder_frames))

                s->low_delay=1;

            if(avctx->has_b_frames < 2)

                avctx->has_b_frames= !s->low_delay;

            if (avctx->bits_per_raw_sample != h->sps.bit_depth_luma) {

                if (h->sps.bit_depth_luma >= 8 && h->sps.bit_depth_luma <= 10) {

                    avctx->bits_per_raw_sample = h->sps.bit_depth_luma;

                    h->pixel_shift = h->sps.bit_depth_luma > 8;

                    ff_h264dsp_init(&h->h264dsp, h->sps.bit_depth_luma);

                    ff_h264_pred_init(&h->hpc, s->codec_id, h->sps.bit_depth_luma);

                    dsputil_init(&s->dsp, s->avctx);

                } else {

                    av_log(avctx, AV_LOG_DEBUG, "Unsupported bit depth: %d\n", h->sps.bit_depth_luma);

                    return -1;

                }

            }

            break;

        case NAL_PPS:

            init_get_bits(&s->gb, ptr, bit_length);

            ff_h264_decode_picture_parameter_set(h, bit_length);

            break;

        case NAL_AUD:

        case NAL_END_SEQUENCE:

        case NAL_END_STREAM:

        case NAL_FILLER_DATA:

        case NAL_SPS_EXT:

        case NAL_AUXILIARY_SLICE:

            break;

        default:

            av_log(avctx, AV_LOG_DEBUG, "Unknown NAL code: %d (%d bits)\n", hx->nal_unit_type, bit_length);

        }

        if(context_count == h->max_contexts) {

            execute_decode_slices(h, context_count);

            context_count = 0;

        }

        if (err < 0)

            av_log(h->s.avctx, AV_LOG_ERROR, "decode_slice_header error\n");

        else if(err == 1) {

            /* Slice could not be decoded in parallel mode, copy down

             * NAL unit stuff to context 0 and restart. Note that

             * rbsp_buffer is not transferred, but since we no longer

             * run in parallel mode this should not be an issue. */

            h->nal_unit_type = hx->nal_unit_type;

            h->nal_ref_idc   = hx->nal_ref_idc;

            hx = h;

            goto again;

        }

    }

    if(context_count)

        execute_decode_slices(h, context_count);

    return buf_index;

}


static int nvdec_vc1_decode_slice(AVCodecContext *avctx, const uint8_t *buffer, uint32_t size)

{

    NVDECContext *ctx = avctx->internal->hwaccel_priv_data;

    void *tmp;

    tmp = av_fast_realloc(ctx->slice_offsets, &ctx->slice_offsets_allocated,

                          (ctx->nb_slices + 1) * sizeof(*ctx->slice_offsets));

    if (!tmp)

        return AVERROR(ENOMEM);

    ctx->slice_offsets = tmp;

    if (!ctx->bitstream)

        ctx->bitstream = (uint8_t*)buffer;

    ctx->slice_offsets[ctx->nb_slices] = buffer - ctx->bitstream;

    ctx->bitstream_len += size;

    ctx->nb_slices++;

    return 0;

}


static void omap2_inth_write(void *opaque, target_phys_addr_t addr,

                             uint64_t value, unsigned size)

{

    struct omap_intr_handler_s *s = (struct omap_intr_handler_s *) opaque;

    int offset = addr;

    int bank_no, line_no;

    struct omap_intr_handler_bank_s *bank = NULL;

    if ((offset & 0xf80) == 0x80) {

        bank_no = (offset & 0x60) >> 5;

        if (bank_no < s->nbanks) {

            offset &= ~0x60;

            bank = &s->bank[bank_no];

        }

    }

    switch (offset) {

    case 0x10:	/* INTC_SYSCONFIG */

        s->autoidle &= 4;

        s->autoidle |= (value & 1) << 2;

        if (value & 2)						/* SOFTRESET */

            omap_inth_reset(s);

        return;

    case 0x48:	/* INTC_CONTROL */

        s->mask = (value & 4) ? 0 : ~0;				/* GLOBALMASK */

        if (value & 2) {					/* NEWFIQAGR */

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

            s->new_agr[1] = ~0;

            omap_inth_update(s, 1);

        }

        if (value & 1) {					/* NEWIRQAGR */

            qemu_set_irq(s->parent_intr[0], 0);

            s->new_agr[0] = ~0;

            omap_inth_update(s, 0);

        }

        return;

    case 0x4c:	/* INTC_PROTECTION */

        /* TODO: Make a bitmap (or sizeof(char)map) of access privileges

         * for every register, see Chapter 3 and 4 for privileged mode.  */

        if (value & 1)

            fprintf(stderr, "%s: protection mode enable attempt\n",

                            __FUNCTION__);

        return;

    case 0x50:	/* INTC_IDLE */

        s->autoidle &= ~3;

        s->autoidle |= value & 3;

        return;

    /* Per-bank registers */

    case 0x84:	/* INTC_MIR */

        bank->mask = value;

        omap_inth_update(s, 0);

        omap_inth_update(s, 1);

        return;

    case 0x88:	/* INTC_MIR_CLEAR */

        bank->mask &= ~value;

        omap_inth_update(s, 0);

        omap_inth_update(s, 1);

        return;

    case 0x8c:	/* INTC_MIR_SET */

        bank->mask |= value;

        return;

    case 0x90:	/* INTC_ISR_SET */

        bank->irqs |= bank->swi |= value;

        omap_inth_update(s, 0);

        omap_inth_update(s, 1);

        return;

    case 0x94:	/* INTC_ISR_CLEAR */

        bank->swi &= ~value;

        bank->irqs = bank->swi & bank->inputs;

        return;

    /* Per-line registers */

    case 0x100 ... 0x300:	/* INTC_ILR */

        bank_no = (offset - 0x100) >> 7;

        if (bank_no > s->nbanks)

            break;

        bank = &s->bank[bank_no];

        line_no = (offset & 0x7f) >> 2;

        bank->priority[line_no] = (value >> 2) & 0x3f;

        bank->fiq &= ~(1 << line_no);

        bank->fiq |= (value & 1) << line_no;

        return;

    case 0x00:	/* INTC_REVISION */

    case 0x14:	/* INTC_SYSSTATUS */

    case 0x40:	/* INTC_SIR_IRQ */

    case 0x44:	/* INTC_SIR_FIQ */

    case 0x80:	/* INTC_ITR */

    case 0x98:	/* INTC_PENDING_IRQ */

    case 0x9c:	/* INTC_PENDING_FIQ */

        OMAP_RO_REG(addr);

        return;

    }

    OMAP_BAD_REG(addr);

}


static bool pte32_match(target_ulong pte0, target_ulong pte1,

                        bool secondary, target_ulong ptem)

{

    return (pte0 & HPTE32_V_VALID)

        && (secondary == !!(pte0 & HPTE32_V_SECONDARY))

        && HPTE32_V_COMPARE(pte0, ptem);

}


static int hpet_init(SysBusDevice *dev)

{

    HPETState *s = FROM_SYSBUS(HPETState, dev);

    int i, iomemtype;

    HPETTimer *timer;

    if (hpet_cfg.count == UINT8_MAX) {

        /* first instance */

        hpet_cfg.count = 0;

    }

    if (hpet_cfg.count == 8) {

        fprintf(stderr, "Only 8 instances of HPET is allowed\n");

        return -1;

    }

    s->hpet_id = hpet_cfg.count++;

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

        sysbus_init_irq(dev, &s->irqs[i]);

    }

    if (s->num_timers < HPET_MIN_TIMERS) {

        s->num_timers = HPET_MIN_TIMERS;

    } else if (s->num_timers > HPET_MAX_TIMERS) {

        s->num_timers = HPET_MAX_TIMERS;

    }

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

        timer = &s->timer[i];

        timer->qemu_timer = qemu_new_timer(vm_clock, hpet_timer, timer);

        timer->tn = i;

        timer->state = s;

    }

    /* 64-bit main counter; LegacyReplacementRoute. */

    s->capability = 0x8086a001ULL;

    s->capability |= (s->num_timers - 1) << HPET_ID_NUM_TIM_SHIFT;

    s->capability |= ((HPET_CLK_PERIOD) << 32);

    isa_reserve_irq(RTC_ISA_IRQ);

    qdev_init_gpio_in(&dev->qdev, hpet_handle_rtc_irq, 1);

    /* HPET Area */

    iomemtype = cpu_register_io_memory(hpet_ram_read,

                                       hpet_ram_write, s,

                                       DEVICE_NATIVE_ENDIAN);

    sysbus_init_mmio(dev, 0x400, iomemtype);

    return 0;

}


static int send_png_rect(VncState *vs, int x, int y, int w, int h,

                         QDict *palette)

{

    png_byte color_type;

    png_structp png_ptr;

    png_infop info_ptr;

    png_colorp png_palette = NULL;

    size_t offset;

    int level = tight_conf[vs->tight_compression].raw_zlib_level;

    uint8_t *buf;

    int dy;

    png_ptr = png_create_write_struct_2(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL,

                                        NULL, vnc_png_malloc, vnc_png_free);

    if (png_ptr == NULL)

        return -1;

    info_ptr = png_create_info_struct(png_ptr);

    if (info_ptr == NULL) {

        png_destroy_write_struct(&png_ptr, NULL);

        return -1;

    }

    png_set_write_fn(png_ptr, (void *) vs, png_write_data, png_flush_data);

    png_set_compression_level(png_ptr, level);

    if (palette) {

        color_type = PNG_COLOR_TYPE_PALETTE;

    } else {

        color_type = PNG_COLOR_TYPE_RGB;

    }

    png_set_IHDR(png_ptr, info_ptr, w, h,

                 8, color_type, PNG_INTERLACE_NONE,

                 PNG_COMPRESSION_TYPE_DEFAULT, PNG_FILTER_TYPE_DEFAULT);

    if (color_type == PNG_COLOR_TYPE_PALETTE) {

        struct palette_cb_priv priv;

        png_palette = png_malloc(png_ptr, sizeof(*png_palette) *

                                 qdict_size(palette));

        priv.vs = vs;

        priv.png_palette = png_palette;

        qdict_iter(palette, write_png_palette, &priv);

        png_set_PLTE(png_ptr, info_ptr, png_palette, qdict_size(palette));

        offset = vs->tight.offset;

        if (vs->clientds.pf.bytes_per_pixel == 4) {

            tight_encode_indexed_rect32(vs->tight.buffer, w * h, palette);

        } else {

            tight_encode_indexed_rect16(vs->tight.buffer, w * h, palette);

        }

    }

    png_write_info(png_ptr, info_ptr);

    buffer_reserve(&vs->tight_png, 2048);

    buf = qemu_malloc(w * 3);

    for (dy = 0; dy < h; dy++)

    {

        if (color_type == PNG_COLOR_TYPE_PALETTE) {

            memcpy(buf, vs->tight.buffer + (dy * w), w);

        } else {

            rgb_prepare_row(vs, buf, x, y + dy, w);

        }

        png_write_row(png_ptr, buf);

    }

    qemu_free(buf);

    png_write_end(png_ptr, NULL);

    if (color_type == PNG_COLOR_TYPE_PALETTE) {

        png_free(png_ptr, png_palette);

    }

    png_destroy_write_struct(&png_ptr, &info_ptr);

    vnc_write_u8(vs, VNC_TIGHT_PNG << 4);

    tight_send_compact_size(vs, vs->tight_png.offset);

    vnc_write(vs, vs->tight_png.buffer, vs->tight_png.offset);

    buffer_reset(&vs->tight_png);

    return 1;

}


START_TEST(qdict_put_exists_test)

{

    int value;

    const char *key = "exists";

    qdict_put(tests_dict, key, qint_from_int(1));

    qdict_put(tests_dict, key, qint_from_int(2));

    value = qdict_get_int(tests_dict, key);

    fail_unless(value == 2);

    fail_unless(qdict_size(tests_dict) == 1);

}


static void gt64120_writel (void *opaque, target_phys_addr_t addr,

                            uint64_t val, unsigned size)

{

    GT64120State *s = opaque;

    PCIHostState *phb = PCI_HOST_BRIDGE(s);

    uint32_t saddr;

    if (!(s->regs[GT_CPU] & 0x00001000))

        val = bswap32(val);

    saddr = (addr & 0xfff) >> 2;

    switch (saddr) {

    /* CPU Configuration */

    case GT_CPU:

        s->regs[GT_CPU] = val;

        break;

    case GT_MULTI:

	/* Read-only register as only one GT64xxx is present on the CPU bus */

        break;

    /* CPU Address Decode */

    case GT_PCI0IOLD:

        s->regs[GT_PCI0IOLD]    = val & 0x00007fff;

        s->regs[GT_PCI0IOREMAP] = val & 0x000007ff;

        gt64120_pci_mapping(s);

        break;

    case GT_PCI0M0LD:

        s->regs[GT_PCI0M0LD]    = val & 0x00007fff;

        s->regs[GT_PCI0M0REMAP] = val & 0x000007ff;

        break;

    case GT_PCI0M1LD:

        s->regs[GT_PCI0M1LD]    = val & 0x00007fff;

        s->regs[GT_PCI0M1REMAP] = val & 0x000007ff;

        break;

    case GT_PCI1IOLD:

        s->regs[GT_PCI1IOLD]    = val & 0x00007fff;

        s->regs[GT_PCI1IOREMAP] = val & 0x000007ff;

        break;

    case GT_PCI1M0LD:

        s->regs[GT_PCI1M0LD]    = val & 0x00007fff;

        s->regs[GT_PCI1M0REMAP] = val & 0x000007ff;

        break;

    case GT_PCI1M1LD:

        s->regs[GT_PCI1M1LD]    = val & 0x00007fff;

        s->regs[GT_PCI1M1REMAP] = val & 0x000007ff;

        break;

    case GT_PCI0IOHD:

        s->regs[saddr] = val & 0x0000007f;

        gt64120_pci_mapping(s);

        break;

    case GT_PCI0M0HD:

    case GT_PCI0M1HD:

    case GT_PCI1IOHD:

    case GT_PCI1M0HD:

    case GT_PCI1M1HD:

        s->regs[saddr] = val & 0x0000007f;

        break;

    case GT_ISD:

        s->regs[saddr] = val & 0x00007fff;

        gt64120_isd_mapping(s);

        break;

    case GT_PCI0IOREMAP:

    case GT_PCI0M0REMAP:

    case GT_PCI0M1REMAP:

    case GT_PCI1IOREMAP:

    case GT_PCI1M0REMAP:

    case GT_PCI1M1REMAP:

        s->regs[saddr] = val & 0x000007ff;

        break;

    /* CPU Error Report */

    case GT_CPUERR_ADDRLO:

    case GT_CPUERR_ADDRHI:

    case GT_CPUERR_DATALO:

    case GT_CPUERR_DATAHI:

    case GT_CPUERR_PARITY:

	/* Read-only registers, do nothing */

        break;

    /* CPU Sync Barrier */

    case GT_PCI0SYNC:

    case GT_PCI1SYNC:

	/* Read-only registers, do nothing */

        break;

    /* SDRAM and Device Address Decode */

    case GT_SCS0LD:

    case GT_SCS0HD:

    case GT_SCS1LD:

    case GT_SCS1HD:

    case GT_SCS2LD:

    case GT_SCS2HD:

    case GT_SCS3LD:

    case GT_SCS3HD:

    case GT_CS0LD:

    case GT_CS0HD:

    case GT_CS1LD:

    case GT_CS1HD:

    case GT_CS2LD:

    case GT_CS2HD:

    case GT_CS3LD:

    case GT_CS3HD:

    case GT_BOOTLD:

    case GT_BOOTHD:

    case GT_ADERR:

    /* SDRAM Configuration */

    case GT_SDRAM_CFG:

    case GT_SDRAM_OPMODE:

    case GT_SDRAM_BM:

    case GT_SDRAM_ADDRDECODE:

        /* Accept and ignore SDRAM interleave configuration */

        s->regs[saddr] = val;

        break;

    /* Device Parameters */

    case GT_DEV_B0:

    case GT_DEV_B1:

    case GT_DEV_B2:

    case GT_DEV_B3:

    case GT_DEV_BOOT:

        /* Not implemented */

        DPRINTF ("Unimplemented device register offset 0x%x\n", saddr << 2);

        break;

    /* ECC */

    case GT_ECC_ERRDATALO:

    case GT_ECC_ERRDATAHI:

    case GT_ECC_MEM:

    case GT_ECC_CALC:

    case GT_ECC_ERRADDR:

        /* Read-only registers, do nothing */

        break;

    /* DMA Record */

    case GT_DMA0_CNT:

    case GT_DMA1_CNT:

    case GT_DMA2_CNT:

    case GT_DMA3_CNT:

    case GT_DMA0_SA:

    case GT_DMA1_SA:

    case GT_DMA2_SA:

    case GT_DMA3_SA:

    case GT_DMA0_DA:

    case GT_DMA1_DA:

    case GT_DMA2_DA:

    case GT_DMA3_DA:

    case GT_DMA0_NEXT:

    case GT_DMA1_NEXT:

    case GT_DMA2_NEXT:

    case GT_DMA3_NEXT:

    case GT_DMA0_CUR:

    case GT_DMA1_CUR:

    case GT_DMA2_CUR:

    case GT_DMA3_CUR:

        /* Not implemented */

        DPRINTF ("Unimplemented DMA register offset 0x%x\n", saddr << 2);

        break;

    /* DMA Channel Control */

    case GT_DMA0_CTRL:

    case GT_DMA1_CTRL:

    case GT_DMA2_CTRL:

    case GT_DMA3_CTRL:

        /* Not implemented */

        DPRINTF ("Unimplemented DMA register offset 0x%x\n", saddr << 2);

        break;

    /* DMA Arbiter */

    case GT_DMA_ARB:

        /* Not implemented */

        DPRINTF ("Unimplemented DMA register offset 0x%x\n", saddr << 2);

        break;

    /* Timer/Counter */

    case GT_TC0:

    case GT_TC1:

    case GT_TC2:

    case GT_TC3:

    case GT_TC_CONTROL:

        /* Not implemented */

        DPRINTF ("Unimplemented timer register offset 0x%x\n", saddr << 2);

        break;

    /* PCI Internal */

    case GT_PCI0_CMD:

    case GT_PCI1_CMD:

        s->regs[saddr] = val & 0x0401fc0f;

        break;

    case GT_PCI0_TOR:

    case GT_PCI0_BS_SCS10:

    case GT_PCI0_BS_SCS32:

    case GT_PCI0_BS_CS20:

    case GT_PCI0_BS_CS3BT:

    case GT_PCI1_IACK:

    case GT_PCI0_IACK:

    case GT_PCI0_BARE:

    case GT_PCI0_PREFMBR:

    case GT_PCI0_SCS10_BAR:

    case GT_PCI0_SCS32_BAR:

    case GT_PCI0_CS20_BAR:

    case GT_PCI0_CS3BT_BAR:

    case GT_PCI0_SSCS10_BAR:

    case GT_PCI0_SSCS32_BAR:

    case GT_PCI0_SCS3BT_BAR:

    case GT_PCI1_TOR:

    case GT_PCI1_BS_SCS10:

    case GT_PCI1_BS_SCS32:

    case GT_PCI1_BS_CS20:

    case GT_PCI1_BS_CS3BT:

    case GT_PCI1_BARE:

    case GT_PCI1_PREFMBR:

    case GT_PCI1_SCS10_BAR:

    case GT_PCI1_SCS32_BAR:

    case GT_PCI1_CS20_BAR:

    case GT_PCI1_CS3BT_BAR:

    case GT_PCI1_SSCS10_BAR:

    case GT_PCI1_SSCS32_BAR:

    case GT_PCI1_SCS3BT_BAR:

    case GT_PCI1_CFGADDR:

    case GT_PCI1_CFGDATA:

        /* not implemented */

        break;

    case GT_PCI0_CFGADDR:

        phb->config_reg = val & 0x80fffffc;

        break;

    case GT_PCI0_CFGDATA:

        if (!(s->regs[GT_PCI0_CMD] & 1) && (phb->config_reg & 0x00fff800)) {

            val = bswap32(val);

        }

        if (phb->config_reg & (1u << 31)) {

            pci_data_write(phb->bus, phb->config_reg, val, 4);

        }

        break;

    /* Interrupts */

    case GT_INTRCAUSE:

        /* not really implemented */

        s->regs[saddr] = ~(~(s->regs[saddr]) | ~(val & 0xfffffffe));

        s->regs[saddr] |= !!(s->regs[saddr] & 0xfffffffe);

        DPRINTF("INTRCAUSE %" PRIx64 "\n", val);

        break;

    case GT_INTRMASK:

        s->regs[saddr] = val & 0x3c3ffffe;

        DPRINTF("INTRMASK %" PRIx64 "\n", val);

        break;

    case GT_PCI0_ICMASK:

        s->regs[saddr] = val & 0x03fffffe;

        DPRINTF("ICMASK %" PRIx64 "\n", val);

        break;

    case GT_PCI0_SERR0MASK:

        s->regs[saddr] = val & 0x0000003f;

        DPRINTF("SERR0MASK %" PRIx64 "\n", val);

        break;

    /* Reserved when only PCI_0 is configured. */

    case GT_HINTRCAUSE:

    case GT_CPU_INTSEL:

    case GT_PCI0_INTSEL:

    case GT_HINTRMASK:

    case GT_PCI0_HICMASK:

    case GT_PCI1_SERR1MASK:

        /* not implemented */

        break;

    /* SDRAM Parameters */

    case GT_SDRAM_B0:

    case GT_SDRAM_B1:

    case GT_SDRAM_B2:

    case GT_SDRAM_B3:

        /* We don't simulate electrical parameters of the SDRAM.

           Accept, but ignore the values. */

        s->regs[saddr] = val;

        break;

    default:

        DPRINTF ("Bad register offset 0x%x\n", (int)addr);

        break;

    }

}


static void tcg_constant_folding(TCGContext *s)

{

    int oi, oi_next, nb_temps, nb_globals;

    /* Array VALS has an element for each temp.

       If this temp holds a constant then its value is kept in VALS' element.

       If this temp is a copy of other ones then the other copies are

       available through the doubly linked circular list. */

    nb_temps = s->nb_temps;

    nb_globals = s->nb_globals;

    reset_all_temps(nb_temps);

    for (oi = s->gen_first_op_idx; oi >= 0; oi = oi_next) {

        tcg_target_ulong mask, partmask, affected;

        int nb_oargs, nb_iargs, i;

        TCGArg tmp;

        TCGOp * const op = &s->gen_op_buf[oi];

        TCGArg * const args = &s->gen_opparam_buf[op->args];

        TCGOpcode opc = op->opc;

        const TCGOpDef *def = &tcg_op_defs[opc];

        oi_next = op->next;

        if (opc == INDEX_op_call) {

            nb_oargs = op->callo;

            nb_iargs = op->calli;

        } else {

            nb_oargs = def->nb_oargs;

            nb_iargs = def->nb_iargs;

        }

        /* Do copy propagation */

        for (i = nb_oargs; i < nb_oargs + nb_iargs; i++) {

            if (temps[args[i]].state == TCG_TEMP_COPY) {

                args[i] = find_better_copy(s, args[i]);

            }

        }

        /* For commutative operations make constant second argument */

        switch (opc) {

        CASE_OP_32_64(add):

        CASE_OP_32_64(mul):

        CASE_OP_32_64(and):

        CASE_OP_32_64(or):

        CASE_OP_32_64(xor):

        CASE_OP_32_64(eqv):

        CASE_OP_32_64(nand):

        CASE_OP_32_64(nor):

        CASE_OP_32_64(muluh):

        CASE_OP_32_64(mulsh):

            swap_commutative(args[0], &args[1], &args[2]);

            break;

        CASE_OP_32_64(brcond):

            if (swap_commutative(-1, &args[0], &args[1])) {

                args[2] = tcg_swap_cond(args[2]);

            }

            break;

        CASE_OP_32_64(setcond):

            if (swap_commutative(args[0], &args[1], &args[2])) {

                args[3] = tcg_swap_cond(args[3]);

            }

            break;

        CASE_OP_32_64(movcond):

            if (swap_commutative(-1, &args[1], &args[2])) {

                args[5] = tcg_swap_cond(args[5]);

            }

            /* For movcond, we canonicalize the "false" input reg to match

               the destination reg so that the tcg backend can implement

               a "move if true" operation.  */

            if (swap_commutative(args[0], &args[4], &args[3])) {

                args[5] = tcg_invert_cond(args[5]);

            }

            break;

        CASE_OP_32_64(add2):

            swap_commutative(args[0], &args[2], &args[4]);

            swap_commutative(args[1], &args[3], &args[5]);

            break;

        CASE_OP_32_64(mulu2):

        CASE_OP_32_64(muls2):

            swap_commutative(args[0], &args[2], &args[3]);

            break;

        case INDEX_op_brcond2_i32:

            if (swap_commutative2(&args[0], &args[2])) {

                args[4] = tcg_swap_cond(args[4]);

            }

            break;

        case INDEX_op_setcond2_i32:

            if (swap_commutative2(&args[1], &args[3])) {

                args[5] = tcg_swap_cond(args[5]);

            }

            break;

        default:

            break;

        }

        /* Simplify expressions for "shift/rot r, 0, a => movi r, 0",

           and "sub r, 0, a => neg r, a" case.  */

        switch (opc) {

        CASE_OP_32_64(shl):

        CASE_OP_32_64(shr):

        CASE_OP_32_64(sar):

        CASE_OP_32_64(rotl):

        CASE_OP_32_64(rotr):

            if (temps[args[1]].state == TCG_TEMP_CONST

                && temps[args[1]].val == 0) {

                tcg_opt_gen_movi(s, op, args, args[0], 0);

                continue;

            }

            break;

        CASE_OP_32_64(sub):

            {

                TCGOpcode neg_op;

                bool have_neg;

                if (temps[args[2]].state == TCG_TEMP_CONST) {

                    /* Proceed with possible constant folding. */

                    break;

                }

                if (opc == INDEX_op_sub_i32) {

                    neg_op = INDEX_op_neg_i32;

                    have_neg = TCG_TARGET_HAS_neg_i32;

                } else {

                    neg_op = INDEX_op_neg_i64;

                    have_neg = TCG_TARGET_HAS_neg_i64;

                }

                if (!have_neg) {

                    break;

                }

                if (temps[args[1]].state == TCG_TEMP_CONST

                    && temps[args[1]].val == 0) {

                    op->opc = neg_op;

                    reset_temp(args[0]);

                    args[1] = args[2];

                    continue;

                }

            }

            break;

        CASE_OP_32_64(xor):

        CASE_OP_32_64(nand):

            if (temps[args[1]].state != TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[2]].val == -1) {

                i = 1;

                goto try_not;

            }

            break;

        CASE_OP_32_64(nor):

            if (temps[args[1]].state != TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[2]].val == 0) {

                i = 1;

                goto try_not;

            }

            break;

        CASE_OP_32_64(andc):

            if (temps[args[2]].state != TCG_TEMP_CONST

                && temps[args[1]].state == TCG_TEMP_CONST

                && temps[args[1]].val == -1) {

                i = 2;

                goto try_not;

            }

            break;

        CASE_OP_32_64(orc):

        CASE_OP_32_64(eqv):

            if (temps[args[2]].state != TCG_TEMP_CONST

                && temps[args[1]].state == TCG_TEMP_CONST

                && temps[args[1]].val == 0) {

                i = 2;

                goto try_not;

            }

            break;

        try_not:

            {

                TCGOpcode not_op;

                bool have_not;

                if (def->flags & TCG_OPF_64BIT) {

                    not_op = INDEX_op_not_i64;

                    have_not = TCG_TARGET_HAS_not_i64;

                } else {

                    not_op = INDEX_op_not_i32;

                    have_not = TCG_TARGET_HAS_not_i32;

                }

                if (!have_not) {

                    break;

                }

                op->opc = not_op;

                reset_temp(args[0]);

                args[1] = args[i];

                continue;

            }

        default:

            break;

        }

        /* Simplify expression for "op r, a, const => mov r, a" cases */

        switch (opc) {

        CASE_OP_32_64(add):

        CASE_OP_32_64(sub):

        CASE_OP_32_64(shl):

        CASE_OP_32_64(shr):

        CASE_OP_32_64(sar):

        CASE_OP_32_64(rotl):

        CASE_OP_32_64(rotr):

        CASE_OP_32_64(or):

        CASE_OP_32_64(xor):

        CASE_OP_32_64(andc):

            if (temps[args[1]].state != TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[2]].val == 0) {

                tcg_opt_gen_mov(s, op, args, args[0], args[1]);

                continue;

            }

            break;

        CASE_OP_32_64(and):

        CASE_OP_32_64(orc):

        CASE_OP_32_64(eqv):

            if (temps[args[1]].state != TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[2]].val == -1) {

                tcg_opt_gen_mov(s, op, args, args[0], args[1]);

                continue;

            }

            break;

        default:

            break;

        }

        /* Simplify using known-zero bits. Currently only ops with a single

           output argument is supported. */

        mask = -1;

        affected = -1;

        switch (opc) {

        CASE_OP_32_64(ext8s):

            if ((temps[args[1]].mask & 0x80) != 0) {

                break;

            }

        CASE_OP_32_64(ext8u):

            mask = 0xff;

            goto and_const;

        CASE_OP_32_64(ext16s):

            if ((temps[args[1]].mask & 0x8000) != 0) {

                break;

            }

        CASE_OP_32_64(ext16u):

            mask = 0xffff;

            goto and_const;

        case INDEX_op_ext32s_i64:

            if ((temps[args[1]].mask & 0x80000000) != 0) {

                break;

            }

        case INDEX_op_ext32u_i64:

            mask = 0xffffffffU;

            goto and_const;

        CASE_OP_32_64(and):

            mask = temps[args[2]].mask;

            if (temps[args[2]].state == TCG_TEMP_CONST) {

        and_const:

                affected = temps[args[1]].mask & ~mask;

            }

            mask = temps[args[1]].mask & mask;

            break;

        CASE_OP_32_64(andc):

            /* Known-zeros does not imply known-ones.  Therefore unless

               args[2] is constant, we can't infer anything from it.  */

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                mask = ~temps[args[2]].mask;

                goto and_const;

            }

            /* But we certainly know nothing outside args[1] may be set. */

            mask = temps[args[1]].mask;

            break;

        case INDEX_op_sar_i32:

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = temps[args[2]].val & 31;

                mask = (int32_t)temps[args[1]].mask >> tmp;

            }

            break;

        case INDEX_op_sar_i64:

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = temps[args[2]].val & 63;

                mask = (int64_t)temps[args[1]].mask >> tmp;

            }

            break;

        case INDEX_op_shr_i32:

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = temps[args[2]].val & 31;

                mask = (uint32_t)temps[args[1]].mask >> tmp;

            }

            break;

        case INDEX_op_shr_i64:

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = temps[args[2]].val & 63;

                mask = (uint64_t)temps[args[1]].mask >> tmp;

            }

            break;

        case INDEX_op_trunc_shr_i32:

            mask = (uint64_t)temps[args[1]].mask >> args[2];

            break;

        CASE_OP_32_64(shl):

            if (temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = temps[args[2]].val & (TCG_TARGET_REG_BITS - 1);

                mask = temps[args[1]].mask << tmp;

            }

            break;

        CASE_OP_32_64(neg):

            /* Set to 1 all bits to the left of the rightmost.  */

            mask = -(temps[args[1]].mask & -temps[args[1]].mask);

            break;

        CASE_OP_32_64(deposit):

            mask = deposit64(temps[args[1]].mask, args[3], args[4],

                             temps[args[2]].mask);

            break;

        CASE_OP_32_64(or):

        CASE_OP_32_64(xor):

            mask = temps[args[1]].mask | temps[args[2]].mask;

            break;

        CASE_OP_32_64(setcond):

        case INDEX_op_setcond2_i32:

            mask = 1;

            break;

        CASE_OP_32_64(movcond):

            mask = temps[args[3]].mask | temps[args[4]].mask;

            break;

        CASE_OP_32_64(ld8u):

            mask = 0xff;

            break;

        CASE_OP_32_64(ld16u):

            mask = 0xffff;

            break;

        case INDEX_op_ld32u_i64:

            mask = 0xffffffffu;

            break;

        CASE_OP_32_64(qemu_ld):

            {

                TCGMemOpIdx oi = args[nb_oargs + nb_iargs];

                TCGMemOp mop = get_memop(oi);

                if (!(mop & MO_SIGN)) {

                    mask = (2ULL << ((8 << (mop & MO_SIZE)) - 1)) - 1;

                }

            }

            break;

        default:

            break;

        }

        /* 32-bit ops generate 32-bit results.  For the result is zero test

           below, we can ignore high bits, but for further optimizations we

           need to record that the high bits contain garbage.  */

        partmask = mask;

        if (!(def->flags & TCG_OPF_64BIT)) {

            mask |= ~(tcg_target_ulong)0xffffffffu;

            partmask &= 0xffffffffu;

            affected &= 0xffffffffu;

        }

        if (partmask == 0) {

            assert(nb_oargs == 1);

            tcg_opt_gen_movi(s, op, args, args[0], 0);

            continue;

        }

        if (affected == 0) {

            assert(nb_oargs == 1);

            tcg_opt_gen_mov(s, op, args, args[0], args[1]);

            continue;

        }

        /* Simplify expression for "op r, a, 0 => movi r, 0" cases */

        switch (opc) {

        CASE_OP_32_64(and):

        CASE_OP_32_64(mul):

        CASE_OP_32_64(muluh):

        CASE_OP_32_64(mulsh):

            if ((temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[2]].val == 0)) {

                tcg_opt_gen_movi(s, op, args, args[0], 0);

                continue;

            }

            break;

        default:

            break;

        }

        /* Simplify expression for "op r, a, a => mov r, a" cases */

        switch (opc) {

        CASE_OP_32_64(or):

        CASE_OP_32_64(and):

            if (temps_are_copies(args[1], args[2])) {

                tcg_opt_gen_mov(s, op, args, args[0], args[1]);

                continue;

            }

            break;

        default:

            break;

        }

        /* Simplify expression for "op r, a, a => movi r, 0" cases */

        switch (opc) {

        CASE_OP_32_64(andc):

        CASE_OP_32_64(sub):

        CASE_OP_32_64(xor):

            if (temps_are_copies(args[1], args[2])) {

                tcg_opt_gen_movi(s, op, args, args[0], 0);

                continue;

            }

            break;

        default:

            break;

        }

        /* Propagate constants through copy operations and do constant

           folding.  Constants will be substituted to arguments by register

           allocator where needed and possible.  Also detect copies. */

        switch (opc) {

        CASE_OP_32_64(mov):

            tcg_opt_gen_mov(s, op, args, args[0], args[1]);

            break;

        CASE_OP_32_64(movi):

            tcg_opt_gen_movi(s, op, args, args[0], args[1]);

            break;

        CASE_OP_32_64(not):

        CASE_OP_32_64(neg):

        CASE_OP_32_64(ext8s):

        CASE_OP_32_64(ext8u):

        CASE_OP_32_64(ext16s):

        CASE_OP_32_64(ext16u):

        case INDEX_op_ext32s_i64:

        case INDEX_op_ext32u_i64:

            if (temps[args[1]].state == TCG_TEMP_CONST) {

                tmp = do_constant_folding(opc, temps[args[1]].val, 0);

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

                break;

            }

            goto do_default;

        case INDEX_op_trunc_shr_i32:

            if (temps[args[1]].state == TCG_TEMP_CONST) {

                tmp = do_constant_folding(opc, temps[args[1]].val, args[2]);

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

                break;

            }

            goto do_default;

        CASE_OP_32_64(add):

        CASE_OP_32_64(sub):

        CASE_OP_32_64(mul):

        CASE_OP_32_64(or):

        CASE_OP_32_64(and):

        CASE_OP_32_64(xor):

        CASE_OP_32_64(shl):

        CASE_OP_32_64(shr):

        CASE_OP_32_64(sar):

        CASE_OP_32_64(rotl):

        CASE_OP_32_64(rotr):

        CASE_OP_32_64(andc):

        CASE_OP_32_64(orc):

        CASE_OP_32_64(eqv):

        CASE_OP_32_64(nand):

        CASE_OP_32_64(nor):

        CASE_OP_32_64(muluh):

        CASE_OP_32_64(mulsh):

        CASE_OP_32_64(div):

        CASE_OP_32_64(divu):

        CASE_OP_32_64(rem):

        CASE_OP_32_64(remu):

            if (temps[args[1]].state == TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = do_constant_folding(opc, temps[args[1]].val,

                                          temps[args[2]].val);

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

                break;

            }

            goto do_default;

        CASE_OP_32_64(deposit):

            if (temps[args[1]].state == TCG_TEMP_CONST

                && temps[args[2]].state == TCG_TEMP_CONST) {

                tmp = deposit64(temps[args[1]].val, args[3], args[4],

                                temps[args[2]].val);

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

                break;

            }

            goto do_default;

        CASE_OP_32_64(setcond):

            tmp = do_constant_folding_cond(opc, args[1], args[2], args[3]);

            if (tmp != 2) {

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

                break;

            }

            goto do_default;

        CASE_OP_32_64(brcond):

            tmp = do_constant_folding_cond(opc, args[0], args[1], args[2]);

            if (tmp != 2) {

                if (tmp) {

                    reset_all_temps(nb_temps);

                    op->opc = INDEX_op_br;

                    args[0] = args[3];

                } else {

                    tcg_op_remove(s, op);

                }

                break;

            }

            goto do_default;

        CASE_OP_32_64(movcond):

            tmp = do_constant_folding_cond(opc, args[1], args[2], args[5]);

            if (tmp != 2) {

                tcg_opt_gen_mov(s, op, args, args[0], args[4-tmp]);

                break;

            }

            goto do_default;

        case INDEX_op_add2_i32:

        case INDEX_op_sub2_i32:

            if (temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[3]].state == TCG_TEMP_CONST

                && temps[args[4]].state == TCG_TEMP_CONST

                && temps[args[5]].state == TCG_TEMP_CONST) {

                uint32_t al = temps[args[2]].val;

                uint32_t ah = temps[args[3]].val;

                uint32_t bl = temps[args[4]].val;

                uint32_t bh = temps[args[5]].val;

                uint64_t a = ((uint64_t)ah << 32) | al;

                uint64_t b = ((uint64_t)bh << 32) | bl;

                TCGArg rl, rh;

                TCGOp *op2 = insert_op_before(s, op, INDEX_op_movi_i32, 2);

                TCGArg *args2 = &s->gen_opparam_buf[op2->args];

                if (opc == INDEX_op_add2_i32) {

                    a += b;

                } else {

                    a -= b;

                }

                rl = args[0];

                rh = args[1];

                tcg_opt_gen_movi(s, op, args, rl, (uint32_t)a);

                tcg_opt_gen_movi(s, op2, args2, rh, (uint32_t)(a >> 32));

                /* We've done all we need to do with the movi.  Skip it.  */

                oi_next = op2->next;

                break;

            }

            goto do_default;

        case INDEX_op_mulu2_i32:

            if (temps[args[2]].state == TCG_TEMP_CONST

                && temps[args[3]].state == TCG_TEMP_CONST) {

                uint32_t a = temps[args[2]].val;

                uint32_t b = temps[args[3]].val;

                uint64_t r = (uint64_t)a * b;

                TCGArg rl, rh;

                TCGOp *op2 = insert_op_before(s, op, INDEX_op_movi_i32, 2);

                TCGArg *args2 = &s->gen_opparam_buf[op2->args];

                rl = args[0];

                rh = args[1];

                tcg_opt_gen_movi(s, op, args, rl, (uint32_t)r);

                tcg_opt_gen_movi(s, op2, args2, rh, (uint32_t)(r >> 32));

                /* We've done all we need to do with the movi.  Skip it.  */

                oi_next = op2->next;

                break;

            }

            goto do_default;

        case INDEX_op_brcond2_i32:

            tmp = do_constant_folding_cond2(&args[0], &args[2], args[4]);

            if (tmp != 2) {

                if (tmp) {

            do_brcond_true:

                    reset_all_temps(nb_temps);

                    op->opc = INDEX_op_br;

                    args[0] = args[5];

                } else {

            do_brcond_false:

                    tcg_op_remove(s, op);

                }

            } else if ((args[4] == TCG_COND_LT || args[4] == TCG_COND_GE)

                       && temps[args[2]].state == TCG_TEMP_CONST

                       && temps[args[3]].state == TCG_TEMP_CONST

                       && temps[args[2]].val == 0

                       && temps[args[3]].val == 0) {

                /* Simplify LT/GE comparisons vs zero to a single compare

                   vs the high word of the input.  */

            do_brcond_high:

                reset_all_temps(nb_temps);

                op->opc = INDEX_op_brcond_i32;

                args[0] = args[1];

                args[1] = args[3];

                args[2] = args[4];

                args[3] = args[5];

            } else if (args[4] == TCG_COND_EQ) {

                /* Simplify EQ comparisons where one of the pairs

                   can be simplified.  */

                tmp = do_constant_folding_cond(INDEX_op_brcond_i32,

                                               args[0], args[2], TCG_COND_EQ);

                if (tmp == 0) {

                    goto do_brcond_false;

                } else if (tmp == 1) {

                    goto do_brcond_high;

                }

                tmp = do_constant_folding_cond(INDEX_op_brcond_i32,

                                               args[1], args[3], TCG_COND_EQ);

                if (tmp == 0) {

                    goto do_brcond_false;

                } else if (tmp != 1) {

                    goto do_default;

                }

            do_brcond_low:

                reset_all_temps(nb_temps);

                op->opc = INDEX_op_brcond_i32;

                args[1] = args[2];

                args[2] = args[4];

                args[3] = args[5];

            } else if (args[4] == TCG_COND_NE) {

                /* Simplify NE comparisons where one of the pairs

                   can be simplified.  */

                tmp = do_constant_folding_cond(INDEX_op_brcond_i32,

                                               args[0], args[2], TCG_COND_NE);

                if (tmp == 0) {

                    goto do_brcond_high;

                } else if (tmp == 1) {

                    goto do_brcond_true;

                }

                tmp = do_constant_folding_cond(INDEX_op_brcond_i32,

                                               args[1], args[3], TCG_COND_NE);

                if (tmp == 0) {

                    goto do_brcond_low;

                } else if (tmp == 1) {

                    goto do_brcond_true;

                }

                goto do_default;

            } else {

                goto do_default;

            }

            break;

        case INDEX_op_setcond2_i32:

            tmp = do_constant_folding_cond2(&args[1], &args[3], args[5]);

            if (tmp != 2) {

            do_setcond_const:

                tcg_opt_gen_movi(s, op, args, args[0], tmp);

            } else if ((args[5] == TCG_COND_LT || args[5] == TCG_COND_GE)

                       && temps[args[3]].state == TCG_TEMP_CONST

                       && temps[args[4]].state == TCG_TEMP_CONST

                       && temps[args[3]].val == 0

                       && temps[args[4]].val == 0) {

                /* Simplify LT/GE comparisons vs zero to a single compare

                   vs the high word of the input.  */

            do_setcond_high:

                reset_temp(args[0]);

                temps[args[0]].mask = 1;

                op->opc = INDEX_op_setcond_i32;

                args[1] = args[2];

                args[2] = args[4];

                args[3] = args[5];

            } else if (args[5] == TCG_COND_EQ) {

                /* Simplify EQ comparisons where one of the pairs

                   can be simplified.  */

                tmp = do_constant_folding_cond(INDEX_op_setcond_i32,

                                               args[1], args[3], TCG_COND_EQ);

                if (tmp == 0) {

                    goto do_setcond_const;

                } else if (tmp == 1) {

                    goto do_setcond_high;

                }

                tmp = do_constant_folding_cond(INDEX_op_setcond_i32,

                                               args[2], args[4], TCG_COND_EQ);

                if (tmp == 0) {

                    goto do_setcond_high;

                } else if (tmp != 1) {

                    goto do_default;

                }

            do_setcond_low:

                reset_temp(args[0]);

                temps[args[0]].mask = 1;

                op->opc = INDEX_op_setcond_i32;

                args[2] = args[3];

                args[3] = args[5];

            } else if (args[5] == TCG_COND_NE) {

                /* Simplify NE comparisons where one of the pairs

                   can be simplified.  */

                tmp = do_constant_folding_cond(INDEX_op_setcond_i32,

                                               args[1], args[3], TCG_COND_NE);

                if (tmp == 0) {

                    goto do_setcond_high;

                } else if (tmp == 1) {

                    goto do_setcond_const;

                }

                tmp = do_constant_folding_cond(INDEX_op_setcond_i32,

                                               args[2], args[4], TCG_COND_NE);

                if (tmp == 0) {

                    goto do_setcond_low;

                } else if (tmp == 1) {

                    goto do_setcond_const;

                }

                goto do_default;

            } else {

                goto do_default;

            }

            break;

        case INDEX_op_call:

            if (!(args[nb_oargs + nb_iargs + 1]

                  & (TCG_CALL_NO_READ_GLOBALS | TCG_CALL_NO_WRITE_GLOBALS))) {

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

                    reset_temp(i);

                }

            }

            goto do_reset_output;

        default:

        do_default:

            /* Default case: we know nothing about operation (or were unable

               to compute the operation result) so no propagation is done.

               We trash everything if the operation is the end of a basic

               block, otherwise we only trash the output args.  "mask" is

               the non-zero bits mask for the first output arg.  */

            if (def->flags & TCG_OPF_BB_END) {

                reset_all_temps(nb_temps);

            } else {

        do_reset_output:

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

                    reset_temp(args[i]);

                    /* Save the corresponding known-zero bits mask for the

                       first output argument (only one supported so far). */

                    if (i == 0) {

                        temps[args[i]].mask = mask;

                    }

                }

            }

            break;

        }

    }

}


static inline void qpel_motion(MpegEncContext *s,

                               uint8_t *dest_y,

                               uint8_t *dest_cb,

                               uint8_t *dest_cr,

                               int field_based, int bottom_field,

                               int field_select, uint8_t **ref_picture,

                               op_pixels_func (*pix_op)[4],

                               qpel_mc_func (*qpix_op)[16],

                               int motion_x, int motion_y, int h)

{

    uint8_t *ptr_y, *ptr_cb, *ptr_cr;

    int dxy, uvdxy, mx, my, src_x, src_y, uvsrc_x, uvsrc_y, v_edge_pos;

    ptrdiff_t linesize, uvlinesize;

    dxy   = ((motion_y & 3) << 2) | (motion_x & 3);

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

    src_y = s->mb_y * (16 >> field_based) + (motion_y >> 2);

    v_edge_pos = s->v_edge_pos >> field_based;

    linesize   = s->linesize   << field_based;

    uvlinesize = s->uvlinesize << field_based;

    if (field_based) {

        mx = motion_x / 2;

        my = motion_y >> 1;

    } else if (s->workaround_bugs & FF_BUG_QPEL_CHROMA2) {

        static const int rtab[8] = { 0, 0, 1, 1, 0, 0, 0, 1 };

        mx = (motion_x >> 1) + rtab[motion_x & 7];

        my = (motion_y >> 1) + rtab[motion_y & 7];

    } else if (s->workaround_bugs & FF_BUG_QPEL_CHROMA) {

        mx = (motion_x >> 1) | (motion_x & 1);

        my = (motion_y >> 1) | (motion_y & 1);

    } else {

        mx = motion_x / 2;

        my = motion_y / 2;

    }

    mx = (mx >> 1) | (mx & 1);

    my = (my >> 1) | (my & 1);

    uvdxy = (mx & 1) | ((my & 1) << 1);

    mx  >>= 1;

    my  >>= 1;

    uvsrc_x = s->mb_x *  8                 + mx;

    uvsrc_y = s->mb_y * (8 >> field_based) + my;

    ptr_y  = ref_picture[0] + src_y   * linesize   + src_x;

    ptr_cb = ref_picture[1] + uvsrc_y * uvlinesize + uvsrc_x;

    ptr_cr = ref_picture[2] + uvsrc_y * uvlinesize + uvsrc_x;

    if ((unsigned)src_x > FFMAX(s->h_edge_pos - (motion_x & 3) - 16, 0) ||

        (unsigned)src_y > FFMAX(v_edge_pos - (motion_y & 3) - h, 0)) {

        s->vdsp.emulated_edge_mc(s->sc.edge_emu_buffer, ptr_y,

                                 s->linesize, s->linesize,

                                 17, 17 + field_based,

                                 src_x, src_y << field_based,

                                 s->h_edge_pos, s->v_edge_pos);

        ptr_y = s->sc.edge_emu_buffer;

        if (!CONFIG_GRAY || !(s->avctx->flags & AV_CODEC_FLAG_GRAY)) {

            uint8_t *uvbuf = s->sc.edge_emu_buffer + 18 * s->linesize;

            s->vdsp.emulated_edge_mc(uvbuf, ptr_cb,

                                     s->uvlinesize, s->uvlinesize,

                                     9, 9 + field_based,

                                     uvsrc_x, uvsrc_y << field_based,

                                     s->h_edge_pos >> 1, s->v_edge_pos >> 1);

            s->vdsp.emulated_edge_mc(uvbuf + 16, ptr_cr,

                                     s->uvlinesize, s->uvlinesize,

                                     9, 9 + field_based,

                                     uvsrc_x, uvsrc_y << field_based,

                                     s->h_edge_pos >> 1, s->v_edge_pos >> 1);

            ptr_cb = uvbuf;

            ptr_cr = uvbuf + 16;

        }

    }

    if (!field_based)

        qpix_op[0][dxy](dest_y, ptr_y, linesize);

    else {

        if (bottom_field) {

            dest_y  += s->linesize;

            dest_cb += s->uvlinesize;

            dest_cr += s->uvlinesize;

        }

        if (field_select) {

            ptr_y  += s->linesize;

            ptr_cb += s->uvlinesize;

            ptr_cr += s->uvlinesize;

        }

        // damn interlaced mode

        // FIXME boundary mirroring is not exactly correct here

        qpix_op[1][dxy](dest_y, ptr_y, linesize);

        qpix_op[1][dxy](dest_y + 8, ptr_y + 8, linesize);

    }

    if (!CONFIG_GRAY || !(s->avctx->flags & AV_CODEC_FLAG_GRAY)) {

        pix_op[1][uvdxy](dest_cr, ptr_cr, uvlinesize, h >> 1);

        pix_op[1][uvdxy](dest_cb, ptr_cb, uvlinesize, h >> 1);

    }

}


void do_m68k_simcall(CPUM68KState *env, int nr)

{

    uint32_t *args;

    args = (uint32_t *)(env->aregs[7] + 4);

    switch (nr) {

    case SYS_EXIT:

        exit(ARG(0));

    case SYS_READ:

        check_err(env, read(ARG(0), (void *)ARG(1), ARG(2)));

        break;

    case SYS_WRITE:

        check_err(env, write(ARG(0), (void *)ARG(1), ARG(2)));

        break;

    case SYS_OPEN:

        check_err(env, open((char *)ARG(0), translate_openflags(ARG(1)),

                            ARG(2)));

        break;

    case SYS_CLOSE:

        {

            /* Ignore attempts to close stdin/out/err.  */

            int fd = ARG(0);

            if (fd > 2)

              check_err(env, close(fd));

            else

              check_err(env, 0);

            break;

        }

    case SYS_BRK:

        {

            int32_t ret;

            ret = do_brk((void *)ARG(0));

            if (ret == -ENOMEM)

                ret = -1;

            check_err(env, ret);

        }

        break;

    case SYS_FSTAT:

        {

            struct stat s;

            int rc;

            struct m86k_sim_stat *p;

            rc = check_err(env, fstat(ARG(0), &s));

            if (rc == 0) {

                p = (struct m86k_sim_stat *)ARG(1);

                p->sim_st_dev = tswap16(s.st_dev);

                p->sim_st_ino = tswap16(s.st_ino);

                p->sim_st_mode = tswap32(s.st_mode);

                p->sim_st_nlink = tswap16(s.st_nlink);

                p->sim_st_uid = tswap16(s.st_uid);

                p->sim_st_gid = tswap16(s.st_gid);

                p->sim_st_rdev = tswap16(s.st_rdev);

                p->sim_st_size = tswap32(s.st_size);

                p->sim_st_atime = tswap32(s.st_atime);

                p->sim_st_mtime = tswap32(s.st_mtime);

                p->sim_st_ctime = tswap32(s.st_ctime);

                p->sim_st_blksize = tswap32(s.st_blksize);

                p->sim_st_blocks = tswap32(s.st_blocks);

            }

        }

        break;

    case SYS_ISATTY:

        check_err(env, isatty(ARG(0)));

        break;

    case SYS_LSEEK:

        check_err(env, lseek(ARG(0), (int32_t)ARG(1), ARG(2)));

        break;

    default:

        cpu_abort(env, "Unsupported m68k sim syscall %d\n", nr);

    }

}


static void do_change(const char *device, const char *target, const char *fmt)

{

    if (strcmp(device, "vnc") == 0) {

	do_change_vnc(target);

    } else {

	do_change_block(device, target, fmt);

    }

}


aio_ctx_dispatch(GSource     *source,

                 GSourceFunc  callback,

                 gpointer     user_data)

{

    AioContext *ctx = (AioContext *) source;

    assert(callback == NULL);

    aio_dispatch(ctx, true);

    return true;

}


S390PCIBusDevice *s390_pci_find_dev_by_fid(uint32_t fid)

{

    S390PCIBusDevice *pbdev;

    int i;

    S390pciState *s = s390_get_phb();

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

        pbdev = s->pbdev[i];

        if (pbdev && pbdev->fid == fid) {

            return pbdev;

        }

    }

    return NULL;

}


int qcrypto_pbkdf2_count_iters(QCryptoHashAlgorithm hash,

                               const uint8_t *key, size_t nkey,

                               const uint8_t *salt, size_t nsalt,

                               Error **errp)

{

    uint8_t out[32];

    long long int iterations = (1 << 15);

    unsigned long long delta_ms, start_ms, end_ms;

    while (1) {

        if (qcrypto_pbkdf2_get_thread_cpu(&start_ms, errp) < 0) {

            return -1;

        }

        if (qcrypto_pbkdf2(hash,

                           key, nkey,

                           salt, nsalt,

                           iterations,

                           out, sizeof(out),

                           errp) < 0) {

            return -1;

        }

        if (qcrypto_pbkdf2_get_thread_cpu(&end_ms, errp) < 0) {

            return -1;

        }

        delta_ms = end_ms - start_ms;

        if (delta_ms > 500) {

            break;

        } else if (delta_ms < 100) {

            iterations = iterations * 10;

        } else {

            iterations = (iterations * 1000 / delta_ms);

        }

    }

    iterations = iterations * 1000 / delta_ms;

    if (iterations > INT32_MAX) {

        error_setg(errp, "Iterations %lld too large for a 32-bit int",

                   iterations);

        return -1;

    }

    return iterations;

}


bool write_cpustate_to_list(ARMCPU *cpu)

{

    /* Write the coprocessor state from cpu->env to the (index,value) list. */

    int i;

    bool ok = true;

    for (i = 0; i < cpu->cpreg_array_len; i++) {

        uint32_t regidx = kvm_to_cpreg_id(cpu->cpreg_indexes[i]);

        const ARMCPRegInfo *ri;

        ri = get_arm_cp_reginfo(cpu->cp_regs, regidx);

        if (!ri) {

            ok = false;

            continue;

        }

        if (ri->type & ARM_CP_NO_MIGRATE) {

            continue;

        }

        cpu->cpreg_values[i] = read_raw_cp_reg(&cpu->env, ri);

    }

    return ok;

}


void *qemu_malloc(size_t size)

{

    return malloc(size);

}


static void intra_predict_plane_16x16_msa(uint8_t *src, int32_t stride)

{

    uint8_t lpcnt;

    int32_t res0, res1, res2, res3;

    uint64_t load0, load1;

    v16i8 shf_mask = { 7, 8, 6, 9, 5, 10, 4, 11, 3, 12, 2, 13, 1, 14, 0, 15 };

    v8i16 short_multiplier = { 1, 2, 3, 4, 5, 6, 7, 8 };

    v4i32 int_multiplier = { 0, 1, 2, 3 };

    v16u8 src_top = { 0 };

    v8i16 vec9, vec10;

    v4i32 vec0, vec1, vec2, vec3, vec4, vec5, vec6, vec7, vec8, res_add;

    load0 = LD(src - (stride + 1));

    load1 = LD(src - (stride + 1) + 9);

    INSERT_D2_UB(load0, load1, src_top);

    src_top = (v16u8) __msa_vshf_b(shf_mask, (v16i8) src_top, (v16i8) src_top);

    vec9 = __msa_hsub_u_h(src_top, src_top);

    vec9 *= short_multiplier;

    vec8 = __msa_hadd_s_w(vec9, vec9);

    res_add = (v4i32) __msa_hadd_s_d(vec8, vec8);

    res0 = __msa_copy_s_w(res_add, 0) + __msa_copy_s_w(res_add, 2);

    res1 = (src[8 * stride - 1] - src[6 * stride - 1]) +

        2 * (src[9 * stride - 1] - src[5 * stride - 1]) +

        3 * (src[10 * stride - 1] - src[4 * stride - 1]) +

        4 * (src[11 * stride - 1] - src[3 * stride - 1]) +

        5 * (src[12 * stride - 1] - src[2 * stride - 1]) +

        6 * (src[13 * stride - 1] - src[stride - 1]) +

        7 * (src[14 * stride - 1] - src[-1]) +

        8 * (src[15 * stride - 1] - src[-1 * stride - 1]);

    res0 *= 5;

    res1 *= 5;

    res0 = (res0 + 32) >> 6;

    res1 = (res1 + 32) >> 6;

    res3 = 7 * (res0 + res1);

    res2 = 16 * (src[15 * stride - 1] + src[-stride + 15] + 1);

    res2 -= res3;

    vec8 = __msa_fill_w(res0);

    vec4 = __msa_fill_w(res2);

    vec5 = __msa_fill_w(res1);

    vec6 = vec8 * 4;

    vec7 = vec8 * int_multiplier;

    for (lpcnt = 16; lpcnt--;) {

        vec0 = vec7;

        vec0 += vec4;

        vec1 = vec0 + vec6;

        vec2 = vec1 + vec6;

        vec3 = vec2 + vec6;

        SRA_4V(vec0, vec1, vec2, vec3, 5);

        PCKEV_H2_SH(vec1, vec0, vec3, vec2, vec9, vec10);

        CLIP_SH2_0_255(vec9, vec10);

        PCKEV_ST_SB(vec9, vec10, src);

        src += stride;

        vec4 += vec5;

    }

}


static int ff_filter_frame_framed(AVFilterLink *link, AVFrame *frame)

{

    int (*filter_frame)(AVFilterLink *, AVFrame *);

    AVFilterContext *dstctx = link->dst;

    AVFilterPad *dst = link->dstpad;

    AVFrame *out = NULL;

    int ret;

    AVFilterCommand *cmd= link->dst->command_queue;

    int64_t pts;

    if (link->closed) {

        av_frame_free(&frame);

        return AVERROR_EOF;

    }

    if (!(filter_frame = dst->filter_frame))

        filter_frame = default_filter_frame;

    /* copy the frame if needed */

    if (dst->needs_writable && !av_frame_is_writable(frame)) {

        av_log(link->dst, AV_LOG_DEBUG, "Copying data in avfilter.\n");

        switch (link->type) {

        case AVMEDIA_TYPE_VIDEO:

            out = ff_get_video_buffer(link, link->w, link->h);

            break;

        case AVMEDIA_TYPE_AUDIO:

            out = ff_get_audio_buffer(link, frame->nb_samples);

            break;

        default:

            ret = AVERROR(EINVAL);

            goto fail;

        }

        if (!out) {

            ret = AVERROR(ENOMEM);

            goto fail;

        }

        ret = av_frame_copy_props(out, frame);

        if (ret < 0)

            goto fail;

        switch (link->type) {

        case AVMEDIA_TYPE_VIDEO:

            av_image_copy(out->data, out->linesize, (const uint8_t **)frame->data, frame->linesize,

                          frame->format, frame->width, frame->height);

            break;

        case AVMEDIA_TYPE_AUDIO:

            av_samples_copy(out->extended_data, frame->extended_data,

                            0, 0, frame->nb_samples,

                            av_get_channel_layout_nb_channels(frame->channel_layout),

                            frame->format);

            break;

        default:

            ret = AVERROR(EINVAL);

            goto fail;

        }

        av_frame_free(&frame);

    } else

        out = frame;

    while(cmd && cmd->time <= out->pts * av_q2d(link->time_base)){

        av_log(link->dst, AV_LOG_DEBUG,

               "Processing command time:%f command:%s arg:%s\n",

               cmd->time, cmd->command, cmd->arg);

        avfilter_process_command(link->dst, cmd->command, cmd->arg, 0, 0, cmd->flags);

        ff_command_queue_pop(link->dst);

        cmd= link->dst->command_queue;

    }

    pts = out->pts;

    if (dstctx->enable_str) {

        int64_t pos = av_frame_get_pkt_pos(out);

        dstctx->var_values[VAR_N] = link->frame_count;

        dstctx->var_values[VAR_T] = pts == AV_NOPTS_VALUE ? NAN : pts * av_q2d(link->time_base);

        dstctx->var_values[VAR_W] = link->w;

        dstctx->var_values[VAR_H] = link->h;

        dstctx->var_values[VAR_POS] = pos == -1 ? NAN : pos;

        dstctx->is_disabled = fabs(av_expr_eval(dstctx->enable, dstctx->var_values, NULL)) < 0.5;

        if (dstctx->is_disabled &&

            (dstctx->filter->flags & AVFILTER_FLAG_SUPPORT_TIMELINE_GENERIC))

            filter_frame = default_filter_frame;

    }

    ret = filter_frame(link, out);

    link->frame_count++;

    link->frame_requested = 0;

    ff_update_link_current_pts(link, pts);

    return ret;

fail:

    av_frame_free(&out);

    av_frame_free(&frame);

    return ret;

}


static void predict_plane(SnowContext *s, DWTELEM *buf, int plane_index, int add){

    Plane *p= &s->plane[plane_index];

    const int mb_w= s->mb_band.width;

    const int mb_h= s->mb_band.height;

    const int mb_stride= s->mb_band.stride;

    int x, y, mb_x, mb_y;

    int scale      = plane_index ?  s->mv_scale : 2*s->mv_scale;

    int block_w    = plane_index ?  8 : 16;

    uint8_t *obmc  = plane_index ? obmc16 : obmc32;

    int obmc_stride= plane_index ? 16 : 32;

    int ref_stride= s->last_picture.linesize[plane_index];

    uint8_t *ref  = s->last_picture.data[plane_index];

    int w= p->width;

    int h= p->height;

if(s->avctx->debug&512){

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

        for(x=0; x<w; x++){

            if(add) buf[x + y*w]+= 128*256;

            else    buf[x + y*w]-= 128*256;

        }

    }

    return;

}

    for(mb_y=-1; mb_y<=mb_h; mb_y++){

        for(mb_x=-1; mb_x<=mb_w; mb_x++){

            int index= clip(mb_x, 0, mb_w-1) + clip(mb_y, 0, mb_h-1)*mb_stride;

            add_xblock(buf, ref, obmc,

                       block_w*mb_x - block_w/2,

                       block_w*mb_y - block_w/2,

                       2*block_w, 2*block_w,

                       s->mv_band[0].buf[index]*scale, s->mv_band[1].buf[index]*scale,

                       w, h,

                       w, ref_stride, obmc_stride,

                       s->mb_band.buf[index], add);

        }

    }

}


static void rocker_test_dma_ctrl(Rocker *r, uint32_t val)

{

    PCIDevice *dev = PCI_DEVICE(r);

    char *buf;

    int i;

    buf = g_malloc(r->test_dma_size);

    if (!buf) {

        DPRINTF("test dma buffer alloc failed");

        return;

    }

    switch (val) {

    case ROCKER_TEST_DMA_CTRL_CLEAR:

        memset(buf, 0, r->test_dma_size);

        break;

    case ROCKER_TEST_DMA_CTRL_FILL:

        memset(buf, 0x96, r->test_dma_size);

        break;

    case ROCKER_TEST_DMA_CTRL_INVERT:

        pci_dma_read(dev, r->test_dma_addr, buf, r->test_dma_size);

        for (i = 0; i < r->test_dma_size; i++) {

            buf[i] = ~buf[i];

        }

        break;

    default:

        DPRINTF("not test dma control val=0x%08x\n", val);

        goto err_out;

    }

    pci_dma_write(dev, r->test_dma_addr, buf, r->test_dma_size);

    rocker_msix_irq(r, ROCKER_MSIX_VEC_TEST);

err_out:

    g_free(buf);

}


xilinx_pcie_init(MemoryRegion *sys_mem, uint32_t bus_nr,

                 hwaddr cfg_base, uint64_t cfg_size,

                 hwaddr mmio_base, uint64_t mmio_size,

                 qemu_irq irq, bool link_up)

{

    DeviceState *dev;

    MemoryRegion *cfg, *mmio;

    dev = qdev_create(NULL, TYPE_XILINX_PCIE_HOST);

    qdev_prop_set_uint32(dev, "bus_nr", bus_nr);

    qdev_prop_set_uint64(dev, "cfg_base", cfg_base);

    qdev_prop_set_uint64(dev, "cfg_size", cfg_size);

    qdev_prop_set_uint64(dev, "mmio_base", mmio_base);

    qdev_prop_set_uint64(dev, "mmio_size", mmio_size);

    qdev_prop_set_bit(dev, "link_up", link_up);

    qdev_init_nofail(dev);

    cfg = sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 0);

    memory_region_add_subregion_overlap(sys_mem, cfg_base, cfg, 0);

    mmio = sysbus_mmio_get_region(SYS_BUS_DEVICE(dev), 1);

    memory_region_add_subregion_overlap(sys_mem, 0, mmio, 0);

    qdev_connect_gpio_out_named(dev, "interrupt_out", 0, irq);

    return XILINX_PCIE_HOST(dev);

}


long do_sigreturn(CPUMIPSState *regs)

{

    struct sigframe *frame;

    abi_ulong frame_addr;

    sigset_t blocked;

    target_sigset_t target_set;

    int i;

#if defined(DEBUG_SIGNAL)

    fprintf(stderr, "do_sigreturn\n");

#endif

    frame_addr = regs->active_tc.gpr[29];

    if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1))

   	goto badframe;

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

   	if(__get_user(target_set.sig[i], &frame->sf_mask.sig[i]))

	    goto badframe;

    }

    target_to_host_sigset_internal(&blocked, &target_set);

    do_sigprocmask(SIG_SETMASK, &blocked, NULL);

    restore_sigcontext(regs, &frame->sf_sc);

#if 0

    /*

     * Don't let your children do this ...

     */

    __asm__ __volatile__(

   	"move\t$29, %0\n\t"

   	"j\tsyscall_exit"

   	:/* no outputs */

   	:"r" (&regs));

    /* Unreached */

#endif

    regs->active_tc.PC = regs->CP0_EPC;

    mips_set_hflags_isa_mode_from_pc(regs);

    /* I am not sure this is right, but it seems to work

    * maybe a problem with nested signals ? */

    regs->CP0_EPC = 0;

    return -TARGET_QEMU_ESIGRETURN;

badframe:

    force_sig(TARGET_SIGSEGV/*, current*/);

    return 0;

}


static void pmac_dma_read(BlockBackend *blk,

                          int64_t offset, unsigned int bytes,

                          void (*cb)(void *opaque, int ret), void *opaque)

{

    DBDMA_io *io = opaque;

    MACIOIDEState *m = io->opaque;

    IDEState *s = idebus_active_if(&m->bus);

    dma_addr_t dma_addr, dma_len;

    void *mem;

    int64_t sector_num;

    int nsector;

    uint64_t align = BDRV_SECTOR_SIZE;

    size_t head_bytes, tail_bytes;

    qemu_iovec_destroy(&io->iov);

    qemu_iovec_init(&io->iov, io->len / MACIO_PAGE_SIZE + 1);

    sector_num = (offset >> 9);

    nsector = (io->len >> 9);

    MACIO_DPRINTF("--- DMA read transfer (0x%" HWADDR_PRIx ",0x%x): "

                  "sector_num: %" PRId64 ", nsector: %d\n", io->addr, io->len,

                  sector_num, nsector);

    dma_addr = io->addr;

    dma_len = io->len;

    mem = dma_memory_map(&address_space_memory, dma_addr, &dma_len,

                         DMA_DIRECTION_FROM_DEVICE);

    if (offset & (align - 1)) {

        head_bytes = offset & (align - 1);

        MACIO_DPRINTF("--- DMA unaligned head: sector %" PRId64 ", "

                      "discarding %zu bytes\n", sector_num, head_bytes);

        qemu_iovec_add(&io->iov, &io->remainder, head_bytes);

        bytes += offset & (align - 1);

        offset = offset & ~(align - 1);

    }

    qemu_iovec_add(&io->iov, mem, io->len);

    if ((offset + bytes) & (align - 1)) {

        tail_bytes = (offset + bytes) & (align - 1);

        MACIO_DPRINTF("--- DMA unaligned tail: sector %" PRId64 ", "

                      "discarding bytes %zu\n", sector_num, tail_bytes);

        qemu_iovec_add(&io->iov, &io->remainder, align - tail_bytes);

        bytes = ROUND_UP(bytes, align);

    }

    s->io_buffer_size -= io->len;

    s->io_buffer_index += io->len;

    io->len = 0;

    MACIO_DPRINTF("--- Block read transfer - sector_num: %" PRIx64 "  "

                  "nsector: %x\n", (offset >> 9), (bytes >> 9));

    m->aiocb = blk_aio_readv(blk, (offset >> 9), &io->iov, (bytes >> 9),

                             cb, io);

}


static void sbr_qmf_analysis(AVFixedDSPContext *dsp, FFTContext *mdct,

#else

static void sbr_qmf_analysis(AVFloatDSPContext *dsp, FFTContext *mdct,

#endif /* USE_FIXED */

                             SBRDSPContext *sbrdsp, const INTFLOAT *in, INTFLOAT *x,

                             INTFLOAT z[320], INTFLOAT W[2][32][32][2], int buf_idx)

{

    int i;

    int j;

    memcpy(x    , x+1024, (320-32)*sizeof(x[0]));

    memcpy(x+288, in,         1024*sizeof(x[0]));

    for (i = 0; i < 32; i++) { // numTimeSlots*RATE = 16*2 as 960 sample frames

                               // are not supported

        dsp->vector_fmul_reverse(z, sbr_qmf_window_ds, x, 320);

        sbrdsp->sum64x5(z);

        sbrdsp->qmf_pre_shuffle(z);

        mdct->imdct_half(mdct, z, z+64);

        sbrdsp->qmf_post_shuffle(W[buf_idx][i], z);

        x += 32;


static CPUArchState *find_cpu(uint32_t thread_id)

{

    CPUState *cpu;

    cpu = qemu_get_cpu(thread_id);

    if (cpu == NULL) {

        return NULL;

    }

    return cpu->env_ptr;

}


static void find_block_motion(DeshakeContext *deshake, uint8_t *src1,

                              uint8_t *src2, int cx, int cy, int stride,

                              MotionVector *mv)

{

    int x, y;

    int diff;

    int smallest = INT_MAX;

    int tmp, tmp2;

    #define CMP(i, j) deshake->c.sad[0](deshake, src1 + cy * stride + cx, \

                                        src2 + (j) * stride + (i), stride, \

                                        deshake->blocksize)

    if (deshake->search == EXHAUSTIVE) {

        // Compare every possible position - this is sloooow!

        for (y = -deshake->ry; y <= deshake->ry; y++) {

            for (x = -deshake->rx; x <= deshake->rx; x++) {

                diff = CMP(cx - x, cy - y);

                if (diff < smallest) {

                    smallest = diff;

                    mv->x = x;

                    mv->y = y;

                }

            }

        }

    } else if (deshake->search == SMART_EXHAUSTIVE) {

        // Compare every other possible position and find the best match

        for (y = -deshake->ry + 1; y < deshake->ry - 2; y += 2) {

            for (x = -deshake->rx + 1; x < deshake->rx - 2; x += 2) {

                diff = CMP(cx - x, cy - y);

                if (diff < smallest) {

                    smallest = diff;

                    mv->x = x;

                    mv->y = y;

                }

            }

        }

        // Hone in on the specific best match around the match we found above

        tmp = mv->x;

        tmp2 = mv->y;

        for (y = tmp2 - 1; y <= tmp2 + 1; y++) {

            for (x = tmp - 1; x <= tmp + 1; x++) {

                if (x == tmp && y == tmp2)

                    continue;

                diff = CMP(cx - x, cy - y);

                if (diff < smallest) {

                    smallest = diff;

                    mv->x = x;

                    mv->y = y;

                }

            }

        }

    }

    if (smallest > 512) {

        mv->x = -1;

        mv->y = -1;

    }

    emms_c();

    //av_log(NULL, AV_LOG_ERROR, "%d\n", smallest);

    //av_log(NULL, AV_LOG_ERROR, "Final: (%d, %d) = %d x %d\n", cx, cy, mv->x, mv->y);

}


static void replication_close(BlockDriverState *bs)

{

    BDRVReplicationState *s = bs->opaque;

    if (s->replication_state == BLOCK_REPLICATION_RUNNING) {

        replication_stop(s->rs, false, NULL);

    if (s->mode == REPLICATION_MODE_SECONDARY) {

        g_free(s->top_id);

    replication_remove(s->rs);


static int kvm_irqchip_create(KVMState *s)

{

    QemuOptsList *list = qemu_find_opts("machine");

    int ret;

    if (QTAILQ_EMPTY(&list->head) ||

        !qemu_opt_get_bool(QTAILQ_FIRST(&list->head),

                           "kernel_irqchip", true) ||

        !kvm_check_extension(s, KVM_CAP_IRQCHIP)) {

        return 0;

    }

    ret = kvm_vm_ioctl(s, KVM_CREATE_IRQCHIP);

    if (ret < 0) {

        fprintf(stderr, "Create kernel irqchip failed\n");

        return ret;

    }

    kvm_kernel_irqchip = true;

    /* If we have an in-kernel IRQ chip then we must have asynchronous

     * interrupt delivery (though the reverse is not necessarily true)

     */

    kvm_async_interrupts_allowed = true;

    kvm_halt_in_kernel_allowed = true;

    kvm_init_irq_routing(s);

    return 0;

}


uint32_t qpci_io_readl(QPCIDevice *dev, void *data)

{

    uintptr_t addr = (uintptr_t)data;

    if (addr < QPCI_PIO_LIMIT) {

        return dev->bus->pio_readl(dev->bus, addr);

    } else {

        uint32_t val;

        dev->bus->memread(dev->bus, addr, &val, sizeof(val));

        return le32_to_cpu(val);

    }

}