static int mov_write_trailer(AVFormatContext *s)

{

    MOVMuxContext *mov = s->priv_data;

    AVIOContext *pb = s->pb;

    int res = 0;

    int i;

    int64_t moov_pos = avio_tell(pb);

    if (!(mov->flags & FF_MOV_FLAG_FRAGMENT)) {

        /* Write size of mdat tag */

        if (mov->mdat_size + 8 <= UINT32_MAX) {

            avio_seek(pb, mov->mdat_pos, SEEK_SET);

            avio_wb32(pb, mov->mdat_size + 8);

        } else {

            /* overwrite 'wide' placeholder atom */

            avio_seek(pb, mov->mdat_pos - 8, SEEK_SET);

            /* special value: real atom size will be 64 bit value after

             * tag field */

            avio_wb32(pb, 1);

            ffio_wfourcc(pb, "mdat");

            avio_wb64(pb, mov->mdat_size + 16);

        }

        avio_seek(pb, mov->reserved_moov_size ? mov->reserved_moov_pos : moov_pos, SEEK_SET);

        mov_write_moov_tag(pb, mov, s);

        if(mov->reserved_moov_size){

            int64_t size=  mov->reserved_moov_size - (avio_tell(pb) - mov->reserved_moov_pos);

            if(size < 8){

                av_log(s, AV_LOG_ERROR, "reserved_moov_size is too small, needed %"PRId64" additional\n", 8-size);

                return -1;

            }

            avio_wb32(pb, size);

            ffio_wfourcc(pb, "free");

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

                avio_w8(pb, 0);

            avio_seek(pb, moov_pos, SEEK_SET);

        }

    } else {

        mov_flush_fragment(s);

        mov_write_mfra_tag(pb, mov);

    }

    if (mov->chapter_track)

        av_freep(&mov->tracks[mov->chapter_track].enc);

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

        if (mov->tracks[i].tag == MKTAG('r','t','p',' '))

            ff_mov_close_hinting(&mov->tracks[i]);

        else if (mov->tracks[i].tag == MKTAG('t','m','c','d'))

            av_freep(&mov->tracks[i].enc);

        if (mov->flags & FF_MOV_FLAG_FRAGMENT &&

            mov->tracks[i].vc1_info.struct_offset && s->pb->seekable) {

            int64_t off = avio_tell(pb);

            uint8_t buf[7];

            if (mov_write_dvc1_structs(&mov->tracks[i], buf) >= 0) {

                avio_seek(pb, mov->tracks[i].vc1_info.struct_offset, SEEK_SET);

                avio_write(pb, buf, 7);

                avio_seek(pb, off, SEEK_SET);

            }

        }

        av_freep(&mov->tracks[i].cluster);

        av_freep(&mov->tracks[i].frag_info);

        if (mov->tracks[i].vos_len)

            av_free(mov->tracks[i].vos_data);

    }

    avio_flush(pb);

    av_freep(&mov->tracks);

    return res;

}


static void dvbsub_parse_region_segment(AVCodecContext *avctx,

                                        const uint8_t *buf, int buf_size)

{

    DVBSubContext *ctx = avctx->priv_data;

    const uint8_t *buf_end = buf + buf_size;

    int region_id, object_id;

    int av_unused version;

    DVBSubRegion *region;

    DVBSubObject *object;

    DVBSubObjectDisplay *display;

    int fill;

    if (buf_size < 10)

    region_id = *buf++;

    region = get_region(ctx, region_id);

    if (!region) {

        region = av_mallocz(sizeof(DVBSubRegion));

        region->id = region_id;

        region->version = -1;

        region->next = ctx->region_list;

        ctx->region_list = region;

    }

    version = ((*buf)>>4) & 15;

    fill = ((*buf++) >> 3) & 1;

    region->width = AV_RB16(buf);

    buf += 2;

    region->height = AV_RB16(buf);

    buf += 2;

    if (region->width * region->height != region->buf_size) {

        av_free(region->pbuf);

        region->buf_size = region->width * region->height;

        region->pbuf = av_malloc(region->buf_size);

        fill = 1;

        region->dirty = 0;

    }

    region->depth = 1 << (((*buf++) >> 2) & 7);

    if(region->depth<2 || region->depth>8){

        av_log(avctx, AV_LOG_ERROR, "region depth %d is invalid\n", region->depth);

        region->depth= 4;

    }

    region->clut = *buf++;

    if (region->depth == 8) {

        region->bgcolor = *buf++;

        buf += 1;

    } else {

        buf += 1;

        if (region->depth == 4)

            region->bgcolor = (((*buf++) >> 4) & 15);

        else

            region->bgcolor = (((*buf++) >> 2) & 3);

    }

    av_dlog(avctx, "Region %d, (%dx%d)\n", region_id, region->width, region->height);

    if (fill) {

        memset(region->pbuf, region->bgcolor, region->buf_size);

        av_dlog(avctx, "Fill region (%d)\n", region->bgcolor);

    }

    delete_region_display_list(ctx, region);

    while (buf + 5 < buf_end) {

        object_id = AV_RB16(buf);

        buf += 2;

        object = get_object(ctx, object_id);

        if (!object) {

            object = av_mallocz(sizeof(DVBSubObject));

            object->id = object_id;

            object->next = ctx->object_list;

            ctx->object_list = object;

        }

        object->type = (*buf) >> 6;

        display = av_mallocz(sizeof(DVBSubObjectDisplay));

        display->object_id = object_id;

        display->region_id = region_id;

        display->x_pos = AV_RB16(buf) & 0xfff;

        buf += 2;

        display->y_pos = AV_RB16(buf) & 0xfff;

        buf += 2;

        if ((object->type == 1 || object->type == 2) && buf+1 < buf_end) {

            display->fgcolor = *buf++;

            display->bgcolor = *buf++;

        }

        display->region_list_next = region->display_list;

        region->display_list = display;

        display->object_list_next = object->display_list;

        object->display_list = display;

    }

}


static int local_link(FsContext *ctx, V9fsPath *oldpath,

                      V9fsPath *dirpath, const char *name)

{

    int ret;

    V9fsString newpath;

    char *buffer, *buffer1;

    int serrno;

    v9fs_string_init(&newpath);

    v9fs_string_sprintf(&newpath, "%s/%s", dirpath->data, name);

    buffer = rpath(ctx, oldpath->data);

    buffer1 = rpath(ctx, newpath.data);

    ret = link(buffer, buffer1);

    g_free(buffer);

    if (ret < 0) {

        goto out;

    }

    /* now link the virtfs_metadata files */

    if (ctx->export_flags & V9FS_SM_MAPPED_FILE) {

        char *vbuffer, *vbuffer1;

        /* Link the .virtfs_metadata files. Create the metada directory */

        ret = local_create_mapped_attr_dir(ctx, newpath.data);

        if (ret < 0) {

            goto err_out;

        }

        vbuffer = local_mapped_attr_path(ctx, oldpath->data);

        vbuffer1 = local_mapped_attr_path(ctx, newpath.data);

        ret = link(vbuffer, vbuffer1);

        g_free(vbuffer);

        g_free(vbuffer1);

        if (ret < 0 && errno != ENOENT) {

            goto err_out;

        }

    }

    goto out;

err_out:

    serrno = errno;

    remove(buffer1);

    errno = serrno;

out:

    g_free(buffer1);

    v9fs_string_free(&newpath);

    return ret;

}


static int parse_str(StringInputVisitor *siv, const char *name, Error **errp)

{

    char *str = (char *) siv->string;

    long long start, end;

    Range *cur;

    char *endptr;

    if (siv->ranges) {

        return 0;

    }

    do {

        errno = 0;

        start = strtoll(str, &endptr, 0);

        if (errno == 0 && endptr > str) {

            if (*endptr == '\0') {

                cur = g_malloc0(sizeof(*cur));

                cur->begin = start;

                cur->end = start + 1;

                siv->ranges = g_list_insert_sorted_merged(siv->ranges, cur,

                                                          range_compare);

                cur = NULL;

                str = NULL;

            } else if (*endptr == '-') {

                str = endptr + 1;

                errno = 0;

                end = strtoll(str, &endptr, 0);

                if (errno == 0 && endptr > str && start <= end &&

                    (start > INT64_MAX - 65536 ||

                     end < start + 65536)) {

                    if (*endptr == '\0') {

                        cur = g_malloc0(sizeof(*cur));

                        cur->begin = start;

                        cur->end = end + 1;

                        siv->ranges =

                            g_list_insert_sorted_merged(siv->ranges,

                                                        cur,

                                                        range_compare);

                        cur = NULL;

                        str = NULL;

                    } else if (*endptr == ',') {

                        str = endptr + 1;

                        cur = g_malloc0(sizeof(*cur));

                        cur->begin = start;

                        cur->end = end + 1;

                        siv->ranges =

                            g_list_insert_sorted_merged(siv->ranges,

                                                        cur,

                                                        range_compare);

                        cur = NULL;

                    } else {

                        goto error;

                    }

                } else {

                    goto error;

                }

            } else if (*endptr == ',') {

                str = endptr + 1;

                cur = g_malloc0(sizeof(*cur));

                cur->begin = start;

                cur->end = start + 1;

                siv->ranges = g_list_insert_sorted_merged(siv->ranges,

                                                          cur,

                                                          range_compare);

                cur = NULL;

            } else {

                goto error;

            }

        } else {

            goto error;

        }

    } while (str);

    return 0;

error:

    g_list_foreach(siv->ranges, free_range, NULL);

    g_list_free(siv->ranges);

    siv->ranges = NULL;

    error_setg(errp, QERR_INVALID_PARAMETER_VALUE, name ? name : "null",

               "an int64 value or range");

    return -1;

}


static av_cold int adpcm_encode_init(AVCodecContext *avctx)

{

    ADPCMEncodeContext *s = avctx->priv_data;

    uint8_t *extradata;

    int i;

    if (avctx->channels > 2)

        return -1; /* only stereo or mono =) */

    if (avctx->trellis && (unsigned)avctx->trellis > 16U) {

        av_log(avctx, AV_LOG_ERROR, "invalid trellis size\n");

        return -1;

    }

    if (avctx->trellis) {

        int frontier  = 1 << avctx->trellis;

        int max_paths =  frontier * FREEZE_INTERVAL;

        FF_ALLOC_OR_GOTO(avctx, s->paths,

                         max_paths * sizeof(*s->paths), error);

        FF_ALLOC_OR_GOTO(avctx, s->node_buf,

                         2 * frontier * sizeof(*s->node_buf),  error);

        FF_ALLOC_OR_GOTO(avctx, s->nodep_buf,

                         2 * frontier * sizeof(*s->nodep_buf), error);

        FF_ALLOC_OR_GOTO(avctx, s->trellis_hash,

                         65536 * sizeof(*s->trellis_hash), error);

    }

    avctx->bits_per_coded_sample = av_get_bits_per_sample(avctx->codec->id);

    switch (avctx->codec->id) {

    case CODEC_ID_ADPCM_IMA_WAV:

        /* each 16 bits sample gives one nibble

           and we have 4 bytes per channel overhead */

        avctx->frame_size = (BLKSIZE - 4 * avctx->channels) * 8 /

                            (4 * avctx->channels) + 1;

        /* seems frame_size isn't taken into account...

           have to buffer the samples :-( */

        avctx->block_align = BLKSIZE;

        avctx->bits_per_coded_sample = 4;

        break;

    case CODEC_ID_ADPCM_IMA_QT:

        avctx->frame_size  = 64;

        avctx->block_align = 34 * avctx->channels;

        break;

    case CODEC_ID_ADPCM_MS:

        /* each 16 bits sample gives one nibble

           and we have 7 bytes per channel overhead */

        avctx->frame_size = (BLKSIZE - 7 * avctx->channels) * 2 / avctx->channels + 2;

        avctx->block_align = BLKSIZE;

        avctx->bits_per_coded_sample = 4;

        avctx->extradata_size = 32;

        extradata = avctx->extradata = av_malloc(avctx->extradata_size);

        if (!extradata)

            return AVERROR(ENOMEM);

        bytestream_put_le16(&extradata, avctx->frame_size);

        bytestream_put_le16(&extradata, 7); /* wNumCoef */

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

            bytestream_put_le16(&extradata, ff_adpcm_AdaptCoeff1[i] * 4);

            bytestream_put_le16(&extradata, ff_adpcm_AdaptCoeff2[i] * 4);

        }

        break;

    case CODEC_ID_ADPCM_YAMAHA:

        avctx->frame_size  = BLKSIZE * avctx->channels;

        avctx->block_align = BLKSIZE;

        break;

    case CODEC_ID_ADPCM_SWF:

        if (avctx->sample_rate != 11025 &&

            avctx->sample_rate != 22050 &&

            avctx->sample_rate != 44100) {

            av_log(avctx, AV_LOG_ERROR, "Sample rate must be 11025, "

                   "22050 or 44100\n");

            goto error;

        }

        avctx->frame_size = 512 * (avctx->sample_rate / 11025);

        break;

    default:

        goto error;

    }

    avctx->coded_frame = avcodec_alloc_frame();

    avctx->coded_frame->key_frame= 1;

    return 0;

error:

    av_freep(&s->paths);

    av_freep(&s->node_buf);

    av_freep(&s->nodep_buf);

    av_freep(&s->trellis_hash);

    return -1;

}


void *etraxfs_dmac_init(target_phys_addr_t base, int nr_channels)

{

	struct fs_dma_ctrl *ctrl = NULL;

	ctrl = g_malloc0(sizeof *ctrl);

        ctrl->bh = qemu_bh_new(DMA_run, ctrl);

	ctrl->nr_channels = nr_channels;

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

	memory_region_init_io(&ctrl->mmio, &dma_ops, ctrl, "etraxfs-dma",

			      nr_channels * 0x2000);

	memory_region_add_subregion(get_system_memory(), base, &ctrl->mmio);

	return ctrl;

}


static inline void gen_cond_branch(DisasContext *dc, int cond)

{

    int l1;

    l1 = gen_new_label();

    tcg_gen_brcond_tl(cond, cpu_R[dc->r0], cpu_R[dc->r1], l1);

    gen_goto_tb(dc, 0, dc->pc + 4);

    gen_set_label(l1);

    gen_goto_tb(dc, 1, dc->pc + (sign_extend(dc->imm16 << 2, 16)));

    dc->is_jmp = DISAS_TB_JUMP;

}


static void RENAME(sws_init_swScale)(SwsContext *c)

{

    enum PixelFormat srcFormat = c->srcFormat;

    if (!(c->flags & SWS_BITEXACT)) {

        if (c->flags & SWS_ACCURATE_RND) {

            c->yuv2yuv1     = RENAME(yuv2yuv1_ar    );

            c->yuv2yuvX     = RENAME(yuv2yuvX_ar    );

            switch (c->dstFormat) {

            case PIX_FMT_RGB32:   c->yuv2packedX = RENAME(yuv2rgb32_X_ar);   break;

            case PIX_FMT_BGR24:   c->yuv2packedX = RENAME(yuv2bgr24_X_ar);   break;

            case PIX_FMT_RGB555:  c->yuv2packedX = RENAME(yuv2rgb555_X_ar);  break;

            case PIX_FMT_RGB565:  c->yuv2packedX = RENAME(yuv2rgb565_X_ar);  break;

            case PIX_FMT_YUYV422: c->yuv2packedX = RENAME(yuv2yuyv422_X_ar); break;

            default: break;

            }

        } else {

            c->yuv2yuv1     = RENAME(yuv2yuv1    );

            c->yuv2yuvX     = RENAME(yuv2yuvX    );

            switch (c->dstFormat) {

            case PIX_FMT_RGB32:   c->yuv2packedX = RENAME(yuv2rgb32_X);   break;

            case PIX_FMT_BGR24:   c->yuv2packedX = RENAME(yuv2bgr24_X);   break;

            case PIX_FMT_RGB555:  c->yuv2packedX = RENAME(yuv2rgb555_X);  break;

            case PIX_FMT_RGB565:  c->yuv2packedX = RENAME(yuv2rgb565_X);  break;

            case PIX_FMT_YUYV422: c->yuv2packedX = RENAME(yuv2yuyv422_X); break;

            default: break;

            }

        }

        switch (c->dstFormat) {

        case PIX_FMT_RGB32:

                c->yuv2packed1 = RENAME(yuv2rgb32_1);

                c->yuv2packed2 = RENAME(yuv2rgb32_2);

                break;

        case PIX_FMT_BGR24:

                c->yuv2packed1 = RENAME(yuv2bgr24_1);

                c->yuv2packed2 = RENAME(yuv2bgr24_2);

                break;

        case PIX_FMT_RGB555:

                c->yuv2packed1 = RENAME(yuv2rgb555_1);

                c->yuv2packed2 = RENAME(yuv2rgb555_2);

                break;

        case PIX_FMT_RGB565:

                c->yuv2packed1 = RENAME(yuv2rgb565_1);

                c->yuv2packed2 = RENAME(yuv2rgb565_2);

                break;

        case PIX_FMT_YUYV422:

                c->yuv2packed1 = RENAME(yuv2yuyv422_1);

                c->yuv2packed2 = RENAME(yuv2yuyv422_2);

                break;

        default:

                break;

        }

    }

#if !COMPILE_TEMPLATE_MMX2

    c->hScale       = RENAME(hScale      );

#endif /* !COMPILE_TEMPLATE_MMX2 */

    // Use the new MMX scaler if the MMX2 one can't be used (it is faster than the x86 ASM one).

#if COMPILE_TEMPLATE_MMX2

    if (c->flags & SWS_FAST_BILINEAR && c->canMMX2BeUsed)

    {

        c->hyscale_fast = RENAME(hyscale_fast);

        c->hcscale_fast = RENAME(hcscale_fast);

    } else {

#endif /* COMPILE_TEMPLATE_MMX2 */

        c->hyscale_fast = NULL;

        c->hcscale_fast = NULL;

#if COMPILE_TEMPLATE_MMX2

    }

#endif /* COMPILE_TEMPLATE_MMX2 */

#if !COMPILE_TEMPLATE_MMX2

    switch(srcFormat) {

        case PIX_FMT_YUYV422  : c->chrToYV12 = RENAME(yuy2ToUV); break;

        case PIX_FMT_UYVY422  : c->chrToYV12 = RENAME(uyvyToUV); break;

        case PIX_FMT_NV12     : c->chrToYV12 = RENAME(nv12ToUV); break;

        case PIX_FMT_NV21     : c->chrToYV12 = RENAME(nv21ToUV); break;

        case PIX_FMT_GRAY16LE :

        case PIX_FMT_YUV420P9LE:

        case PIX_FMT_YUV422P10LE:

        case PIX_FMT_YUV420P10LE:

        case PIX_FMT_YUV420P16LE:

        case PIX_FMT_YUV422P16LE:

        case PIX_FMT_YUV444P16LE: c->hScale16= RENAME(hScale16); break;

    }

#endif /* !COMPILE_TEMPLATE_MMX2 */

    if (!c->chrSrcHSubSample) {

        switch(srcFormat) {

        case PIX_FMT_BGR24  : c->chrToYV12 = RENAME(bgr24ToUV); break;

        case PIX_FMT_RGB24  : c->chrToYV12 = RENAME(rgb24ToUV); break;

        default: break;

        }

    }

    switch (srcFormat) {

#if !COMPILE_TEMPLATE_MMX2

    case PIX_FMT_YUYV422  :

    case PIX_FMT_Y400A    :

                            c->lumToYV12 = RENAME(yuy2ToY); break;

    case PIX_FMT_UYVY422  :

                            c->lumToYV12 = RENAME(uyvyToY); break;

#endif /* !COMPILE_TEMPLATE_MMX2 */

    case PIX_FMT_BGR24    : c->lumToYV12 = RENAME(bgr24ToY); break;

    case PIX_FMT_RGB24    : c->lumToYV12 = RENAME(rgb24ToY); break;

    default: break;

    }

#if !COMPILE_TEMPLATE_MMX2

    if (c->alpPixBuf) {

        switch (srcFormat) {

        case PIX_FMT_Y400A  : c->alpToYV12 = RENAME(yuy2ToY); break;

        default: break;

        }

    }

#endif /* !COMPILE_TEMPLATE_MMX2 */

    if(isAnyRGB(c->srcFormat))

        c->hScale16= RENAME(hScale16);

}


static void tftp_handle_rrq(struct tftp_t *tp, int pktlen)

{

  struct tftp_session *spt;

  int s, k, n;

  u_int8_t *src, *dst;

  s = tftp_session_allocate(tp);

  if (s < 0) {

    return;

  }

  spt = &tftp_sessions[s];

  src = tp->x.tp_buf;

  dst = spt->filename;

  n = pktlen - ((uint8_t *)&tp->x.tp_buf[0] - (uint8_t *)tp);

  /* get name */

  for (k = 0; k < n; k++) {

    if (k < TFTP_FILENAME_MAX) {

      dst[k] = src[k];

    }

    else {

      return;

    }

    if (src[k] == '\0') {

      break;

    }

  }

  if (k >= n) {

    return;

  }

  k++;

  /* check mode */

  if ((n - k) < 6) {

    return;

  }

  if (memcmp(&src[k], "octet\0", 6) != 0) {

      tftp_send_error(spt, 4, "Unsupported transfer mode", tp);

      return;

  }

  k += 6; /* skipping octet */

  /* do sanity checks on the filename */

  if ((spt->filename[0] != '/')

      || (spt->filename[strlen((char *)spt->filename) - 1] == '/')

      ||  strstr((char *)spt->filename, "/../")) {

      tftp_send_error(spt, 2, "Access violation", tp);

      return;

  }

  /* only allow exported prefixes */

  if (!tftp_prefix) {

      tftp_send_error(spt, 2, "Access violation", tp);

      return;

  }

  /* check if the file exists */

  if (tftp_read_data(spt, 0, spt->filename, 0) < 0) {

      tftp_send_error(spt, 1, "File not found", tp);

      return;

  }

  if (src[n - 1] != 0) {

      tftp_send_error(spt, 2, "Access violation", tp);

      return;

  }

  while (k < n) {

      const char *key, *value;

      key = (char *)src + k;

      k += strlen(key) + 1;

      if (k >= n) {

	  tftp_send_error(spt, 2, "Access violation", tp);

	  return;

      }

      value = (char *)src + k;

      k += strlen(value) + 1;

      if (strcmp(key, "tsize") == 0) {

	  int tsize = atoi(value);

	  struct stat stat_p;

	  if (tsize == 0 && tftp_prefix) {

	      char buffer[1024];

	      int len;

	      len = snprintf(buffer, sizeof(buffer), "%s/%s",

			     tftp_prefix, spt->filename);

	      if (stat(buffer, &stat_p) == 0)

		  tsize = stat_p.st_size;

	      else {

		  tftp_send_error(spt, 1, "File not found", tp);

		  return;

	      }

	  }

	  tftp_send_oack(spt, "tsize", tsize, tp);

      }

  }

  tftp_send_data(spt, 1, tp);

}


static int waveformat_to_audio_settings (WAVEFORMATEX *wfx, audsettings_t *as)

{

    if (wfx->wFormatTag != WAVE_FORMAT_PCM) {

        dolog ("Invalid wave format, tag is not PCM, but %d\n",

               wfx->wFormatTag);

        return -1;

    }

    if (!wfx->nSamplesPerSec) {

        dolog ("Invalid wave format, frequency is zero\n");

        return -1;

    }

    as->freq = wfx->nSamplesPerSec;

    switch (wfx->nChannels) {

    case 1:

        as->nchannels = 1;

        break;

    case 2:

        as->nchannels = 2;

        break;

    default:

        dolog (

            "Invalid wave format, number of channels is not 1 or 2, but %d\n",

            wfx->nChannels

            );

        return -1;

    }

    switch (wfx->wBitsPerSample) {

    case 8:

        as->fmt = AUD_FMT_U8;

        break;

    case 16:

        as->fmt = AUD_FMT_S16;

        break;

    case 32:

        as->fmt = AUD_FMT_S32;

        break;

    default:

        dolog ("Invalid wave format, bits per sample is not "

               "8, 16 or 32, but %d\n",

               wfx->wBitsPerSample);

        return -1;

    }

    return 0;

}


void css_queue_crw(uint8_t rsc, uint8_t erc, int chain, uint16_t rsid)

{

    CrwContainer *crw_cont;

    trace_css_crw(rsc, erc, rsid, chain ? "(chained)" : "");

    /* TODO: Maybe use a static crw pool? */

    crw_cont = g_try_malloc0(sizeof(CrwContainer));

    if (!crw_cont) {

        channel_subsys.crws_lost = true;

        return;

    }

    crw_cont->crw.flags = (rsc << 8) | erc;

    if (chain) {

        crw_cont->crw.flags |= CRW_FLAGS_MASK_C;

    }

    crw_cont->crw.rsid = rsid;

    if (channel_subsys.crws_lost) {

        crw_cont->crw.flags |= CRW_FLAGS_MASK_R;

        channel_subsys.crws_lost = false;

    }

    QTAILQ_INSERT_TAIL(&channel_subsys.pending_crws, crw_cont, sibling);

    if (channel_subsys.do_crw_mchk) {

        channel_subsys.do_crw_mchk = false;

        /* Inject crw pending machine check. */

        s390_crw_mchk();

    }

}


static int buffered_get_fd(void *opaque)

{

    QEMUFileBuffered *s = opaque;

    return qemu_get_fd(s->file);

}


size_t qemu_file_get_rate_limit(QEMUFile *f)

{

    if (f->get_rate_limit)

        return f->get_rate_limit(f->opaque);

    return 0;

}


static uint8_t *csrhci_out_packet(struct csrhci_s *s, int len)

{

    int off = s->out_start + s->out_len;

    /* TODO: do the padding here, i.e. align len */

    s->out_len += len;

    if (off < FIFO_LEN) {

        if (off + len > FIFO_LEN && (s->out_size = off + len) > FIFO_LEN * 2) {

            fprintf(stderr, "%s: can't alloc %i bytes\n", __func__, len);

            exit(-1);

        }

        return s->outfifo + off;

    }

    if (s->out_len > s->out_size) {

        fprintf(stderr, "%s: can't alloc %i bytes\n", __func__, len);

        exit(-1);

    }

    return s->outfifo + off - s->out_size;

}


static void test_dummy_createcmdl(void)

{

    QemuOpts *opts;

    DummyObject *dobj;

    Error *err = NULL;

    const char *params = TYPE_DUMMY \

                         ",id=dev0," \

                         "bv=yes,sv=Hiss hiss hiss,av=platypus";

    qemu_add_opts(&qemu_object_opts);

    opts = qemu_opts_parse(&qemu_object_opts, params, true, &err);

    g_assert(err == NULL);

    g_assert(opts);

    dobj = DUMMY_OBJECT(user_creatable_add_opts(opts, &err));

    g_assert(err == NULL);

    g_assert(dobj);

    g_assert_cmpstr(dobj->sv, ==, "Hiss hiss hiss");

    g_assert(dobj->bv == true);

    g_assert(dobj->av == DUMMY_PLATYPUS);

    user_creatable_del("dev0", &err);

    g_assert(err == NULL);

    error_free(err);

    /*

     * cmdline-parsing via qemu_opts_parse() results in a QemuOpts entry

     * corresponding to the Object's ID to be added to the QemuOptsList

     * for objects. To avoid having this entry conflict with future

     * Objects using the same ID (which can happen in cases where

     * qemu_opts_parse() is used to parse the object params, such as

     * with hmp_object_add() at the time of this comment), we need to

     * check for this in user_creatable_del() and remove the QemuOpts if

     * it is present.

     *

     * FIXME: add an assert to verify that the QemuOpts is cleaned up

     * once the corresponding cleanup code is added.

     */

}


static void musicpal_init(ram_addr_t ram_size, int vga_ram_size,

               const char *boot_device, DisplayState *ds,

               const char *kernel_filename, const char *kernel_cmdline,

               const char *initrd_filename, const char *cpu_model)

{

    CPUState *env;

    qemu_irq *pic;

    int index;

    int iomemtype;

    unsigned long flash_size;

    if (!cpu_model)

        cpu_model = "arm926";

    env = cpu_init(cpu_model);

    if (!env) {

        fprintf(stderr, "Unable to find CPU definition\n");

        exit(1);

    }

    pic = arm_pic_init_cpu(env);

    /* For now we use a fixed - the original - RAM size */

    cpu_register_physical_memory(0, MP_RAM_DEFAULT_SIZE,

                                 qemu_ram_alloc(MP_RAM_DEFAULT_SIZE));

    sram_off = qemu_ram_alloc(MP_SRAM_SIZE);

    cpu_register_physical_memory(MP_SRAM_BASE, MP_SRAM_SIZE, sram_off);

    /* Catch various stuff not handled by separate subsystems */

    iomemtype = cpu_register_io_memory(0, musicpal_readfn,

                                       musicpal_writefn, env);

    cpu_register_physical_memory(0x80000000, 0x10000, iomemtype);

    pic = mv88w8618_pic_init(MP_PIC_BASE, pic[ARM_PIC_CPU_IRQ]);

    mv88w8618_pit_init(MP_PIT_BASE, pic, MP_TIMER1_IRQ);

    if (serial_hds[0])

        serial_mm_init(MP_UART1_BASE, 2, pic[MP_UART1_IRQ], 1825000,

                   serial_hds[0], 1);

    if (serial_hds[1])

        serial_mm_init(MP_UART2_BASE, 2, pic[MP_UART2_IRQ], 1825000,

                   serial_hds[1], 1);

    /* Register flash */

    index = drive_get_index(IF_PFLASH, 0, 0);

    if (index != -1) {

        flash_size = bdrv_getlength(drives_table[index].bdrv);

        if (flash_size != 8*1024*1024 && flash_size != 16*1024*1024 &&

            flash_size != 32*1024*1024) {

            fprintf(stderr, "Invalid flash image size\n");

            exit(1);

        }

        /*

         * The original U-Boot accesses the flash at 0xFE000000 instead of

         * 0xFF800000 (if there is 8 MB flash). So remap flash access if the

         * image is smaller than 32 MB.

         */

        pflash_cfi02_register(0-MP_FLASH_SIZE_MAX, qemu_ram_alloc(flash_size),

                              drives_table[index].bdrv, 0x10000,

                              (flash_size + 0xffff) >> 16,

                              MP_FLASH_SIZE_MAX / flash_size,

                              2, 0x00BF, 0x236D, 0x0000, 0x0000,

                              0x5555, 0x2AAA);

    }

    mv88w8618_flashcfg_init(MP_FLASHCFG_BASE);

    musicpal_lcd_init(ds, MP_LCD_BASE);

    qemu_add_kbd_event_handler(musicpal_key_event, pic[MP_GPIO_IRQ]);

    /*

     * Wait a bit to catch menu button during U-Boot start-up

     * (to trigger emergency update).

     */

    sleep(1);

    mv88w8618_eth_init(&nd_table[0], MP_ETH_BASE, pic[MP_ETH_IRQ]);

    mixer_i2c = musicpal_audio_init(MP_AUDIO_BASE, pic[MP_AUDIO_IRQ]);

    musicpal_binfo.ram_size = MP_RAM_DEFAULT_SIZE;

    musicpal_binfo.kernel_filename = kernel_filename;

    musicpal_binfo.kernel_cmdline = kernel_cmdline;

    musicpal_binfo.initrd_filename = initrd_filename;

    arm_load_kernel(env, &musicpal_binfo);

}


void helper_sysenter(CPUX86State *env)

{

    if (env->sysenter_cs == 0) {

        raise_exception_err(env, EXCP0D_GPF, 0);

    }

    env->eflags &= ~(VM_MASK | IF_MASK | RF_MASK);

    cpu_x86_set_cpl(env, 0);

#ifdef TARGET_X86_64

    if (env->hflags & HF_LMA_MASK) {

        cpu_x86_load_seg_cache(env, R_CS, env->sysenter_cs & 0xfffc,

                               0, 0xffffffff,

                               DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                               DESC_S_MASK |

                               DESC_CS_MASK | DESC_R_MASK | DESC_A_MASK |

                               DESC_L_MASK);

    } else

#endif

    {

        cpu_x86_load_seg_cache(env, R_CS, env->sysenter_cs & 0xfffc,

                               0, 0xffffffff,

                               DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                               DESC_S_MASK |

                               DESC_CS_MASK | DESC_R_MASK | DESC_A_MASK);

    }

    cpu_x86_load_seg_cache(env, R_SS, (env->sysenter_cs + 8) & 0xfffc,

                           0, 0xffffffff,

                           DESC_G_MASK | DESC_B_MASK | DESC_P_MASK |

                           DESC_S_MASK |

                           DESC_W_MASK | DESC_A_MASK);

    env->regs[R_ESP] = env->sysenter_esp;

    env->eip = env->sysenter_eip;

}


int bdrv_snapshot_load_tmp_by_id_or_name(BlockDriverState *bs,

                                         const char *id_or_name,

                                         Error **errp)

{

    int ret;

    Error *local_err = NULL;

    ret = bdrv_snapshot_load_tmp(bs, id_or_name, NULL, &local_err);

    if (ret == -ENOENT || ret == -EINVAL) {

        error_free(local_err);

        local_err = NULL;

        ret = bdrv_snapshot_load_tmp(bs, NULL, id_or_name, &local_err);

    }

    if (local_err) {

        error_propagate(errp, local_err);

    }

    return ret;

}


void vnc_init_state(VncState *vs)

{

    vs->initialized = true;

    VncDisplay *vd = vs->vd;

    bool first_client = QTAILQ_EMPTY(&vd->clients);

    vs->last_x = -1;

    vs->last_y = -1;

    vs->as.freq = 44100;

    vs->as.nchannels = 2;

    vs->as.fmt = AUD_FMT_S16;

    vs->as.endianness = 0;

    qemu_mutex_init(&vs->output_mutex);

    vs->bh = qemu_bh_new(vnc_jobs_bh, vs);

    QTAILQ_INSERT_TAIL(&vd->clients, vs, next);

    if (first_client) {

        vnc_update_server_surface(vd);

    }

    graphic_hw_update(vd->dcl.con);

    vnc_write(vs, "RFB 003.008\n", 12);

    vnc_flush(vs);

    vnc_read_when(vs, protocol_version, 12);

    reset_keys(vs);

    if (vs->vd->lock_key_sync)

        vs->led = qemu_add_led_event_handler(kbd_leds, vs);

    vs->mouse_mode_notifier.notify = check_pointer_type_change;

    qemu_add_mouse_mode_change_notifier(&vs->mouse_mode_notifier);

}


void migrate_fd_error(MigrationState *s, const Error *error)

{

    trace_migrate_fd_error(error ? error_get_pretty(error) : "");

    assert(s->to_dst_file == NULL);

    migrate_set_state(&s->state, MIGRATION_STATUS_SETUP,

                      MIGRATION_STATUS_FAILED);

    if (!s->error) {

        s->error = error_copy(error);

    }

    notifier_list_notify(&migration_state_notifiers, s);

}


get_field (const unsigned char *data, enum floatformat_byteorders order,

           unsigned int total_len, unsigned int start, unsigned int len)

{

  unsigned long result;

  unsigned int cur_byte;

  int cur_bitshift;

  /* Start at the least significant part of the field.  */

  cur_byte = (start + len) / FLOATFORMAT_CHAR_BIT;

  if (order == floatformat_little)

    cur_byte = (total_len / FLOATFORMAT_CHAR_BIT) - cur_byte - 1;

  cur_bitshift =

    ((start + len) % FLOATFORMAT_CHAR_BIT) - FLOATFORMAT_CHAR_BIT;

  result = *(data + cur_byte) >> (-cur_bitshift);

  cur_bitshift += FLOATFORMAT_CHAR_BIT;

  if (order == floatformat_little)

    ++cur_byte;

  else

    --cur_byte;

  /* Move towards the most significant part of the field.  */

  while ((unsigned int) cur_bitshift < len)

    {

      if (len - cur_bitshift < FLOATFORMAT_CHAR_BIT)

	/* This is the last byte; zero out the bits which are not part of

	   this field.  */

	result |=

	  (*(data + cur_byte) & ((1 << (len - cur_bitshift)) - 1))

	    << cur_bitshift;

      else

	result |= *(data + cur_byte) << cur_bitshift;

      cur_bitshift += FLOATFORMAT_CHAR_BIT;

      if (order == floatformat_little)

	++cur_byte;

      else

	--cur_byte;

    }

  return result;

}


static int coroutine_fn blkreplay_co_discard(BlockDriverState *bs,

    int64_t sector_num, int nb_sectors)

{

    uint64_t reqid = request_id++;

    int ret = bdrv_co_discard(bs->file->bs, sector_num, nb_sectors);

    block_request_create(reqid, bs, qemu_coroutine_self());

    qemu_coroutine_yield();

    return ret;

}


static inline uint32_t ldl_phys_internal(hwaddr addr,

                                         enum device_endian endian)

{

    uint8_t *ptr;

    uint32_t val;

    MemoryRegionSection *section;

    section = phys_page_find(address_space_memory.dispatch, addr >> TARGET_PAGE_BITS);

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

          memory_region_is_romd(section->mr))) {

        /* I/O case */

        addr = memory_region_section_addr(section, addr);

        val = io_mem_read(section->mr, addr, 4);

#if defined(TARGET_WORDS_BIGENDIAN)

        if (endian == DEVICE_LITTLE_ENDIAN) {

            val = bswap32(val);

        }

#else

        if (endian == DEVICE_BIG_ENDIAN) {

            val = bswap32(val);

        }

#endif

    } else {

        /* RAM case */

        ptr = qemu_get_ram_ptr((memory_region_get_ram_addr(section->mr)

                                & TARGET_PAGE_MASK)

                               + memory_region_section_addr(section, addr));

        switch (endian) {

        case DEVICE_LITTLE_ENDIAN:

            val = ldl_le_p(ptr);

            break;

        case DEVICE_BIG_ENDIAN:

            val = ldl_be_p(ptr);

            break;

        default:

            val = ldl_p(ptr);

            break;

        }

    }

    return val;

}


int ne2000_can_receive(NetClientState *nc)

{

    NE2000State *s = qemu_get_nic_opaque(nc);

    if (s->cmd & E8390_STOP)

        return 1;

    return !ne2000_buffer_full(s);

}


static int encode_frame(AVCodecContext *avctx, AVPacket *pkt,

                        const AVFrame *pic, int *got_packet)

{

    ProresContext *ctx = avctx->priv_data;

    uint8_t *orig_buf, *buf, *slice_hdr, *slice_sizes, *tmp;

    uint8_t *picture_size_pos;

    PutBitContext pb;

    int x, y, i, mb, q = 0;

    int sizes[4] = { 0 };

    int slice_hdr_size = 2 + 2 * (ctx->num_planes - 1);

    int frame_size, picture_size, slice_size;

    int mbs_per_slice = ctx->mbs_per_slice;

    int pkt_size, ret;

    *avctx->coded_frame           = *pic;

    avctx->coded_frame->pict_type = AV_PICTURE_TYPE_I;

    avctx->coded_frame->key_frame = 1;

    pkt_size = ctx->mb_width * ctx->mb_height * 64 * 3 * 12

               + ctx->num_slices * 2 + 200 + FF_MIN_BUFFER_SIZE;

    if ((ret = ff_alloc_packet(pkt, pkt_size)) < 0) {

        av_log(avctx, AV_LOG_ERROR, "Error getting output packet.\n");

        return ret;

    }

    orig_buf = pkt->data;

    // frame atom

    orig_buf += 4;                              // frame size

    bytestream_put_be32  (&orig_buf, FRAME_ID); // frame container ID

    buf = orig_buf;

    // frame header

    tmp = buf;

    buf += 2;                                   // frame header size will be stored here

    bytestream_put_be16  (&buf, 0);             // version 1

    bytestream_put_buffer(&buf, "Lavc", 4);     // creator

    bytestream_put_be16  (&buf, avctx->width);

    bytestream_put_be16  (&buf, avctx->height);

    bytestream_put_byte  (&buf, ctx->chroma_factor << 6); // frame flags

    bytestream_put_byte  (&buf, 0);             // reserved

    bytestream_put_byte  (&buf, 0);             // primaries

    bytestream_put_byte  (&buf, 0);             // transfer function

    bytestream_put_byte  (&buf, 6);             // colour matrix - ITU-R BT.601-4

    bytestream_put_byte  (&buf, 0x40);          // source format and alpha information

    bytestream_put_byte  (&buf, 0);             // reserved

    bytestream_put_byte  (&buf, 0x03);          // matrix flags - both matrices are present

    // luma quantisation matrix

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

        bytestream_put_byte(&buf, ctx->profile_info->quant[i]);

    // chroma quantisation matrix

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

        bytestream_put_byte(&buf, ctx->profile_info->quant[i]);

    bytestream_put_be16  (&tmp, buf - orig_buf); // write back frame header size

    // picture header

    picture_size_pos = buf + 1;

    bytestream_put_byte  (&buf, 0x40);          // picture header size (in bits)

    buf += 4;                                   // picture data size will be stored here

    bytestream_put_be16  (&buf, ctx->num_slices); // total number of slices

    bytestream_put_byte  (&buf, av_log2(ctx->mbs_per_slice) << 4); // slice width and height in MBs

    // seek table - will be filled during slice encoding

    slice_sizes = buf;

    buf += ctx->num_slices * 2;

    // slices

    for (y = 0; y < ctx->mb_height; y++) {

        mbs_per_slice = ctx->mbs_per_slice;

        for (x = mb = 0; x < ctx->mb_width; x += mbs_per_slice, mb++) {

            while (ctx->mb_width - x < mbs_per_slice)

                mbs_per_slice >>= 1;

            q = find_slice_quant(avctx, pic, (mb + 1) * TRELLIS_WIDTH, x, y,

                                 mbs_per_slice);

        }

        for (x = ctx->slices_width - 1; x >= 0; x--) {

            ctx->slice_q[x] = ctx->nodes[q].quant;

            q = ctx->nodes[q].prev_node;

        }

        mbs_per_slice = ctx->mbs_per_slice;

        for (x = mb = 0; x < ctx->mb_width; x += mbs_per_slice, mb++) {

            q = ctx->slice_q[mb];

            while (ctx->mb_width - x < mbs_per_slice)

                mbs_per_slice >>= 1;

            bytestream_put_byte(&buf, slice_hdr_size << 3);

            slice_hdr = buf;

            buf += slice_hdr_size - 1;

            init_put_bits(&pb, buf, (pkt_size - (buf - orig_buf)) * 8);

            encode_slice(avctx, pic, &pb, sizes, x, y, q, mbs_per_slice);

            bytestream_put_byte(&slice_hdr, q);

            slice_size = slice_hdr_size + sizes[ctx->num_planes - 1];

            for (i = 0; i < ctx->num_planes - 1; i++) {

                bytestream_put_be16(&slice_hdr, sizes[i]);

                slice_size += sizes[i];

            }

            bytestream_put_be16(&slice_sizes, slice_size);

            buf += slice_size - slice_hdr_size;

        }

    }

    orig_buf -= 8;

    frame_size = buf - orig_buf;

    picture_size = buf - picture_size_pos - 6;

    bytestream_put_be32(&orig_buf, frame_size);

    bytestream_put_be32(&picture_size_pos, picture_size);

    pkt->size   = frame_size;

    pkt->flags |= AV_PKT_FLAG_KEY;

    *got_packet = 1;

    return 0;

}


static int epzs_motion_search4(MpegEncContext * s, int block,

                             int *mx_ptr, int *my_ptr,

                             int P[6][2], int pred_x, int pred_y,

                             int xmin, int ymin, int xmax, int ymax, uint8_t *ref_picture)

{

    int best[2]={0, 0};

    int d, dmin;

    UINT8 *new_pic, *old_pic;

    const int pic_stride= s->linesize;

    const int pic_xy= ((s->mb_y*2 + (block>>1))*pic_stride + s->mb_x*2 + (block&1))*8;

    UINT16 *mv_penalty= s->mv_penalty[s->f_code] + MAX_MV; // f_code of the prev frame

    int quant= s->qscale; // qscale of the prev frame

    const int shift= 1+s->quarter_sample;

    new_pic = s->new_picture[0] + pic_xy;

    old_pic = ref_picture + pic_xy;

    dmin = pix_abs8x8(new_pic, old_pic, pic_stride);

    /* first line */

    if ((s->mb_y == 0 || s->first_slice_line || s->first_gob_line) && block<2) {

        CHECK_MV4(P[1][0]>>shift, P[1][1]>>shift)

    }else{

        CHECK_MV4(P[4][0]>>shift, P[4][1]>>shift)

        if(dmin<Z_THRESHOLD){

            *mx_ptr= P[4][0]>>shift;

            *my_ptr= P[4][1]>>shift;

//printf("M\n");

            return dmin;

        }

        CHECK_MV4(P[1][0]>>shift, P[1][1]>>shift)

        CHECK_MV4(P[2][0]>>shift, P[2][1]>>shift)

        CHECK_MV4(P[3][0]>>shift, P[3][1]>>shift)

    }

    CHECK_MV4(P[0][0]>>shift, P[0][1]>>shift)

    CHECK_MV4(P[5][0]>>shift, P[5][1]>>shift)

//check(best[0],best[1],0, b0)

    dmin= small_diamond_search4MV(s, best, dmin, new_pic, old_pic, pic_stride,

                                   pred_x, pred_y, mv_penalty, quant, xmin, ymin, xmax, ymax, shift);

//check(best[0],best[1],0, b1)

    *mx_ptr= best[0];

    *my_ptr= best[1];

//    printf("%d %d %d \n", best[0], best[1], dmin);

    return dmin;

}


static int ffm_write_write_index(int fd, int64_t pos)

{

    uint8_t buf[8];

    int i;

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

        buf[i] = (pos >> (56 - i * 8)) & 0xff;

    lseek(fd, 8, SEEK_SET);

    if (write(fd, buf, 8) != 8)

        return AVERROR(EIO);

    return 8;

}


static void rv34_output_i16x16(RV34DecContext *r, int8_t *intra_types, int cbp)

{

    LOCAL_ALIGNED_16(DCTELEM, block16, [16]);

    MpegEncContext *s    = &r->s;

    GetBitContext  *gb   = &s->gb;

    int             q_dc = rv34_qscale_tab[ r->luma_dc_quant_i[s->qscale] ],

                    q_ac = rv34_qscale_tab[s->qscale];

    uint8_t        *dst  = s->dest[0];

    DCTELEM        *ptr  = s->block[0];

    int       avail[6*8] = {0};

    int i, j, itype, has_ac;

    memset(block16, 0, 16 * sizeof(*block16));

    // Set neighbour information.

    if(r->avail_cache[1])

        avail[0] = 1;

    if(r->avail_cache[2])

        avail[1] = avail[2] = 1;

    if(r->avail_cache[3])

        avail[3] = avail[4] = 1;

    if(r->avail_cache[4])

        avail[5] = 1;

    if(r->avail_cache[5])

        avail[8] = avail[16] = 1;

    if(r->avail_cache[9])

        avail[24] = avail[32] = 1;

    has_ac = rv34_decode_block(block16, gb, r->cur_vlcs, 3, 0, q_dc, q_dc, q_ac);

    if(has_ac)

        r->rdsp.rv34_inv_transform(block16);

    else

        r->rdsp.rv34_inv_transform_dc(block16);

    itype = ittrans16[intra_types[0]];

    itype = adjust_pred16(itype, r->avail_cache[6-4], r->avail_cache[6-1]);

    r->h.pred16x16[itype](dst, s->linesize);

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

        for(i = 0; i < 4; i++, cbp >>= 1){

            int dc = block16[i + j*4];

            if(cbp & 1){

                has_ac = rv34_decode_block(ptr, gb, r->cur_vlcs, r->luma_vlc, 0, q_ac, q_ac, q_ac);

            }else

                has_ac = 0;

            if(has_ac){

                ptr[0] = dc;

                r->rdsp.rv34_idct_add(dst+4*i, s->linesize, ptr);

            }else

                r->rdsp.rv34_idct_dc_add(dst+4*i, s->linesize, dc);

        }

        dst += 4*s->linesize;

    }

    itype = ittrans16[intra_types[0]];

    if(itype == PLANE_PRED8x8) itype = DC_PRED8x8;

    itype = adjust_pred16(itype, r->avail_cache[6-4], r->avail_cache[6-1]);

    q_dc = rv34_qscale_tab[rv34_chroma_quant[1][s->qscale]];

    q_ac = rv34_qscale_tab[rv34_chroma_quant[0][s->qscale]];

    for(j = 1; j < 3; j++){

        dst = s->dest[j];

        r->h.pred8x8[itype](dst, s->uvlinesize);

        for(i = 0; i < 4; i++, cbp >>= 1){

            uint8_t *pdst;

            if(!(cbp & 1)) continue;

            pdst   = dst + (i&1)*4 + (i&2)*2*s->uvlinesize;

            rv34_process_block(r, pdst, s->uvlinesize,

                               r->chroma_vlc, 1, q_dc, q_ac);

        }

    }

}


STATIC void DEF(put, pixels8_xy2)(uint8_t *block, const uint8_t *pixels,

                                  ptrdiff_t line_size, int h)

{

    MOVQ_ZERO(mm7);

    SET_RND(mm6); // =2 for rnd  and  =1 for no_rnd version

    __asm__ volatile(

        "movq   (%1), %%mm0             \n\t"

        "movq   1(%1), %%mm4            \n\t"

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

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

        "punpcklbw %%mm7, %%mm0         \n\t"

        "punpcklbw %%mm7, %%mm4         \n\t"

        "punpckhbw %%mm7, %%mm1         \n\t"

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

        "paddusw %%mm0, %%mm4           \n\t"

        "paddusw %%mm1, %%mm5           \n\t"

        "xor    %%"REG_a", %%"REG_a"    \n\t"

        "add    %3, %1                  \n\t"

        ".p2align 3                     \n\t"

        "1:                             \n\t"

        "movq   (%1, %%"REG_a"), %%mm0  \n\t"

        "movq   1(%1, %%"REG_a"), %%mm2 \n\t"

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

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

        "punpcklbw %%mm7, %%mm0         \n\t"

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

        "punpckhbw %%mm7, %%mm1         \n\t"

        "punpckhbw %%mm7, %%mm3         \n\t"

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

        "paddusw %%mm3, %%mm1           \n\t"

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

        "paddusw %%mm6, %%mm5           \n\t"

        "paddusw %%mm0, %%mm4           \n\t"

        "paddusw %%mm1, %%mm5           \n\t"

        "psrlw  $2, %%mm4               \n\t"

        "psrlw  $2, %%mm5               \n\t"

        "packuswb  %%mm5, %%mm4         \n\t"

        "movq   %%mm4, (%2, %%"REG_a")  \n\t"

        "add    %3, %%"REG_a"           \n\t"

        "movq   (%1, %%"REG_a"), %%mm2  \n\t" // 0 <-> 2   1 <-> 3

        "movq   1(%1, %%"REG_a"), %%mm4 \n\t"

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

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

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

        "punpcklbw %%mm7, %%mm4         \n\t"

        "punpckhbw %%mm7, %%mm3         \n\t"

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

        "paddusw %%mm2, %%mm4           \n\t"

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

        "paddusw %%mm6, %%mm0           \n\t"

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

        "paddusw %%mm4, %%mm0           \n\t"

        "paddusw %%mm5, %%mm1           \n\t"

        "psrlw  $2, %%mm0               \n\t"

        "psrlw  $2, %%mm1               \n\t"

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

        "movq   %%mm0, (%2, %%"REG_a")  \n\t"

        "add    %3, %%"REG_a"           \n\t"

        "subl   $2, %0                  \n\t"

        "jnz    1b                      \n\t"

        :"+g"(h), "+S"(pixels)

        :"D"(block), "r"((x86_reg)line_size)

        :REG_a, "memory");

}


static int atrac1_decode_frame(AVCodecContext *avctx, void *data,

                               int *data_size, AVPacket *avpkt)

{

    const uint8_t *buf = avpkt->data;

    int buf_size       = avpkt->size;

    AT1Ctx *q          = avctx->priv_data;

    int ch, ret, i;

    GetBitContext gb;

    float* samples = data;

    if (buf_size < 212 * q->channels) {

        av_log(q,AV_LOG_ERROR,"Not enought data to decode!\n");

        return -1;

    }

    for (ch = 0; ch < q->channels; ch++) {

        AT1SUCtx* su = &q->SUs[ch];

        init_get_bits(&gb, &buf[212 * ch], 212 * 8);

        /* parse block_size_mode, 1st byte */

        ret = at1_parse_bsm(&gb, su->log2_block_count);

        if (ret < 0)

            return ret;

        ret = at1_unpack_dequant(&gb, su, q->spec);

        if (ret < 0)

            return ret;

        ret = at1_imdct_block(su, q);

        if (ret < 0)

            return ret;

        at1_subband_synthesis(q, su, q->out_samples[ch]);

    }

    /* interleave; FIXME, should create/use a DSP function */

    if (q->channels == 1) {

        /* mono */

        memcpy(samples, q->out_samples[0], AT1_SU_SAMPLES * 4);

    } else {

        /* stereo */

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

            samples[i * 2]     = q->out_samples[0][i];

            samples[i * 2 + 1] = q->out_samples[1][i];

        }

    }

    *data_size = q->channels * AT1_SU_SAMPLES * sizeof(*samples);

    return avctx->block_align;

}


static void virgl_cmd_submit_3d(VirtIOGPU *g,

                                struct virtio_gpu_ctrl_command *cmd)

{

    struct virtio_gpu_cmd_submit cs;

    void *buf;

    size_t s;

    VIRTIO_GPU_FILL_CMD(cs);

    trace_virtio_gpu_cmd_ctx_submit(cs.hdr.ctx_id, cs.size);

    buf = g_malloc(cs.size);

    s = iov_to_buf(cmd->elem.out_sg, cmd->elem.out_num,

                   sizeof(cs), buf, cs.size);

    if (s != cs.size) {

        qemu_log_mask(LOG_GUEST_ERROR, "%s: size mismatch (%zd/%d)",

                      __func__, s, cs.size);

        cmd->error = VIRTIO_GPU_RESP_ERR_INVALID_PARAMETER;

        return;

    }

    if (virtio_gpu_stats_enabled(g->conf)) {

        g->stats.req_3d++;

        g->stats.bytes_3d += cs.size;

    }

    virgl_renderer_submit_cmd(buf, cs.hdr.ctx_id, cs.size / 4);

    g_free(buf);

}


static int scsi_write_data(SCSIRequest *req)

{

    SCSIDiskReq *r = DO_UPCAST(SCSIDiskReq, req, req);

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

    uint32_t n;

    /* No data transfer may already be in progress */

    assert(r->req.aiocb == NULL);

    n = r->iov.iov_len / 512;

    if (n) {

        qemu_iovec_init_external(&r->qiov, &r->iov, 1);

        r->req.aiocb = bdrv_aio_writev(s->bs, r->sector, &r->qiov, n,

                                   scsi_write_complete, r);

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

            scsi_write_complete(r, -EIO);

        }

    } else {

        /* Invoke completion routine to fetch data from host.  */

        scsi_write_complete(r, 0);

    }

    return 0;

}


static int create_dynamic_disk(BlockBackend *blk, uint8_t *buf,

                               int64_t total_sectors)

{

    VHDDynDiskHeader *dyndisk_header =

        (VHDDynDiskHeader *) buf;

    size_t block_size, num_bat_entries;

    int i;

    int ret;

    int64_t offset = 0;

    // Write the footer (twice: at the beginning and at the end)

    block_size = 0x200000;

    num_bat_entries = (total_sectors + block_size / 512) / (block_size / 512);

    ret = blk_pwrite(blk, offset, buf, HEADER_SIZE);

    if (ret) {

        goto fail;

    }

    offset = 1536 + ((num_bat_entries * 4 + 511) & ~511);

    ret = blk_pwrite(blk, offset, buf, HEADER_SIZE);

    if (ret < 0) {

        goto fail;

    }

    // Write the initial BAT

    offset = 3 * 512;

    memset(buf, 0xFF, 512);

    for (i = 0; i < (num_bat_entries * 4 + 511) / 512; i++) {

        ret = blk_pwrite(blk, offset, buf, 512);

        if (ret < 0) {

            goto fail;

        }

        offset += 512;

    }

    // Prepare the Dynamic Disk Header

    memset(buf, 0, 1024);

    memcpy(dyndisk_header->magic, "cxsparse", 8);

    /*

     * Note: The spec is actually wrong here for data_offset, it says

     * 0xFFFFFFFF, but MS tools expect all 64 bits to be set.

     */

    dyndisk_header->data_offset = cpu_to_be64(0xFFFFFFFFFFFFFFFFULL);

    dyndisk_header->table_offset = cpu_to_be64(3 * 512);

    dyndisk_header->version = cpu_to_be32(0x00010000);

    dyndisk_header->block_size = cpu_to_be32(block_size);

    dyndisk_header->max_table_entries = cpu_to_be32(num_bat_entries);

    dyndisk_header->checksum = cpu_to_be32(vpc_checksum(buf, 1024));

    // Write the header

    offset = 512;

    ret = blk_pwrite(blk, offset, buf, 1024);

    if (ret < 0) {

        goto fail;

    }

 fail:

    return ret;

}


static int vmdk_is_cid_valid(BlockDriverState *bs)

{

    BDRVVmdkState *s = bs->opaque;

    uint32_t cur_pcid;

    if (!s->cid_checked && bs->backing) {

        BlockDriverState *p_bs = bs->backing->bs;

        cur_pcid = vmdk_read_cid(p_bs, 0);

        if (s->parent_cid != cur_pcid) {

            /* CID not valid */

            return 0;

        }

    }

    s->cid_checked = true;

    /* CID valid */

    return 1;

}


static inline int mpeg2_decode_block_intra(MpegEncContext *s, int16_t *block, int n)

{

    int level, dc, diff, i, j, run;

    int component;

    RLTable *rl;

    uint8_t * const scantable = s->intra_scantable.permutated;

    const uint16_t *quant_matrix;

    const int qscale = s->qscale;

    int mismatch;

    /* DC coefficient */

    if (n < 4) {

        quant_matrix = s->intra_matrix;

        component = 0;

    } else {

        quant_matrix = s->chroma_intra_matrix;

        component = (n & 1) + 1;

    }

    diff = decode_dc(&s->gb, component);

    if (diff >= 0xffff)

        return -1;

    dc  = s->last_dc[component];

    dc += diff;

    s->last_dc[component] = dc;

    block[0] = dc << (3 - s->intra_dc_precision);

    av_dlog(s->avctx, "dc=%d\n", block[0]);

    mismatch = block[0] ^ 1;

    i = 0;

    if (s->intra_vlc_format)

        rl = &ff_rl_mpeg2;

    else

        rl = &ff_rl_mpeg1;

    {

        OPEN_READER(re, &s->gb);

        /* now quantify & encode AC coefficients */

        for (;;) {

            UPDATE_CACHE(re, &s->gb);

            GET_RL_VLC(level, run, re, &s->gb, rl->rl_vlc[0], TEX_VLC_BITS, 2, 0);

            if (level == 127) {

                break;

            } else if (level != 0) {

                i += run;

                j  = scantable[i];

                level = (level * qscale * quant_matrix[j]) >> 4;

                level = (level ^ SHOW_SBITS(re, &s->gb, 1)) - SHOW_SBITS(re, &s->gb, 1);

                LAST_SKIP_BITS(re, &s->gb, 1);

            } else {

                /* escape */

                run = SHOW_UBITS(re, &s->gb, 6) + 1; LAST_SKIP_BITS(re, &s->gb, 6);

                UPDATE_CACHE(re, &s->gb);

                level = SHOW_SBITS(re, &s->gb, 12); SKIP_BITS(re, &s->gb, 12);

                i += run;

                j  = scantable[i];

                if (level < 0) {

                    level = (-level * qscale * quant_matrix[j]) >> 4;

                    level = -level;

                } else {

                    level = (level * qscale * quant_matrix[j]) >> 4;

                }

            }

            if (i > 63) {

                av_log(s->avctx, AV_LOG_ERROR, "ac-tex damaged at %d %d\n", s->mb_x, s->mb_y);

                return -1;

            }

            mismatch ^= level;

            block[j]  = level;

        }

        CLOSE_READER(re, &s->gb);

    }

    block[63] ^= mismatch & 1;

    s->block_last_index[n] = i;

    return 0;

}


PPC_OP(test_ctr_true)

{

    T0 = (regs->ctr != 0 && (T0 & PARAM(1)) != 0);

    RETURN();

}


static inline int mov_stsc_index_valid(int index, int count)

{

    return index + 1 < count;

}


static void init_proc_POWER7 (CPUPPCState *env)

{

    gen_spr_ne_601(env);

    gen_spr_7xx(env);

    /* Time base */

    gen_tbl(env);

    /* Processor identification */

    spr_register(env, SPR_PIR, "PIR",

                 SPR_NOACCESS, SPR_NOACCESS,

                 &spr_read_generic, &spr_write_pir,

                 0x00000000);

#if !defined(CONFIG_USER_ONLY)

    /* PURR & SPURR: Hack - treat these as aliases for the TB for now */

    spr_register_kvm(env, SPR_PURR,   "PURR",

                     &spr_read_purr, SPR_NOACCESS,

                     &spr_read_purr, SPR_NOACCESS,

                     KVM_REG_PPC_PURR, 0x00000000);

    spr_register_kvm(env, SPR_SPURR,   "SPURR",

                     &spr_read_purr, SPR_NOACCESS,

                     &spr_read_purr, SPR_NOACCESS,

                     KVM_REG_PPC_SPURR, 0x00000000);

    spr_register(env, SPR_CFAR, "SPR_CFAR",

                 SPR_NOACCESS, SPR_NOACCESS,

                 &spr_read_cfar, &spr_write_cfar,

                 0x00000000);

    spr_register_kvm(env, SPR_DSCR, "SPR_DSCR",

                     SPR_NOACCESS, SPR_NOACCESS,

                     &spr_read_generic, &spr_write_generic,

                     KVM_REG_PPC_DSCR, 0x00000000);

#endif /* !CONFIG_USER_ONLY */

    /* Memory management */

    /* XXX : not implemented */

    spr_register(env, SPR_MMUCFG, "MMUCFG",

                 SPR_NOACCESS, SPR_NOACCESS,

                 &spr_read_generic, SPR_NOACCESS,

                 0x00000000); /* TOFIX */

    /* XXX : not implemented */

    spr_register(env, SPR_CTRL, "SPR_CTRLT",

                 SPR_NOACCESS, SPR_NOACCESS,

                 &spr_read_generic, &spr_write_generic,

                 0x80800000);

    spr_register(env, SPR_UCTRL, "SPR_CTRLF",

                 SPR_NOACCESS, SPR_NOACCESS,

                 &spr_read_generic, &spr_write_generic,

                 0x80800000);

    spr_register(env, SPR_VRSAVE, "SPR_VRSAVE",

                 &spr_read_generic, &spr_write_generic,

                 &spr_read_generic, &spr_write_generic,

                 0x00000000);

#if !defined(CONFIG_USER_ONLY)

    env->slb_nr = 32;

#endif

    init_excp_POWER7(env);

    env->dcache_line_size = 128;

    env->icache_line_size = 128;

    /* Allocate hardware IRQ controller */

    ppcPOWER7_irq_init(env);

    /* Can't find information on what this should be on reset.  This

     * value is the one used by 74xx processors. */

    vscr_init(env, 0x00010000);

}


void spapr_events_init(sPAPREnvironment *spapr)

{

    spapr->epow_irq = spapr_allocate_msi(0);

    spapr->epow_notifier.notify = spapr_powerdown_req;

    qemu_register_powerdown_notifier(&spapr->epow_notifier);

    spapr_rtas_register("check-exception", check_exception);

}


target_ulong helper_add_suov(CPUTriCoreState *env, target_ulong r1,

                             target_ulong r2)

{

    int64_t t1 = extract64(r1, 0, 32);

    int64_t t2 = extract64(r2, 0, 32);

    int64_t result = t1 + t2;

    return suov32(env, result);

}


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

{

    DeviceClass *dc = DEVICE_CLASS(klass);

    dc->realize = pcspk_realizefn;

    set_bit(DEVICE_CATEGORY_SOUND, dc->categories);

    dc->no_user = 1;

    dc->props = pcspk_properties;

}


static int decode_frame(AVCodecContext *avctx, void *data, int *got_frame, AVPacket *avpkt)

{

    AVFrame *frame = data;

    const uint8_t *buf = avpkt->data;

    int buf_size = avpkt->size;

    ZmbvContext * const c = avctx->priv_data;

    int zret = Z_OK; // Zlib return code

    int len = buf_size;

    int hi_ver, lo_ver, ret;

    uint8_t *tmp;

    if ((ret = ff_get_buffer(avctx, frame, 0)) < 0) {

        av_log(avctx, AV_LOG_ERROR, "get_buffer() failed\n");

        return ret;

    }

    /* parse header */

    c->flags = buf[0];

    buf++; len--;

    if (c->flags & ZMBV_KEYFRAME) {

        hi_ver = buf[0];

        lo_ver = buf[1];

        c->comp = buf[2];

        c->fmt = buf[3];

        c->bw = buf[4];

        c->bh = buf[5];

        c->decode_intra = NULL;

        c->decode_xor = NULL;

        buf += 6;

        len -= 6;

        av_log(avctx, AV_LOG_DEBUG,

               "Flags=%X ver=%i.%i comp=%i fmt=%i blk=%ix%i\n",

               c->flags,hi_ver,lo_ver,c->comp,c->fmt,c->bw,c->bh);

        if (hi_ver != 0 || lo_ver != 1) {

            avpriv_request_sample(avctx, "Version %i.%i", hi_ver, lo_ver);

            return AVERROR_PATCHWELCOME;

        }

        if (c->bw == 0 || c->bh == 0) {

            avpriv_request_sample(avctx, "Block size %ix%i", c->bw, c->bh);

            return AVERROR_PATCHWELCOME;

        }

        if (c->comp != 0 && c->comp != 1) {

            avpriv_request_sample(avctx, "Compression type %i", c->comp);

            return AVERROR_PATCHWELCOME;

        }

        switch (c->fmt) {

        case ZMBV_FMT_8BPP:

            c->bpp = 8;

            c->decode_intra = zmbv_decode_intra;

            c->decode_xor = zmbv_decode_xor_8;

            break;

        case ZMBV_FMT_15BPP:

        case ZMBV_FMT_16BPP:

            c->bpp = 16;

            c->decode_intra = zmbv_decode_intra;

            c->decode_xor = zmbv_decode_xor_16;

            break;

#ifdef ZMBV_ENABLE_24BPP

        case ZMBV_FMT_24BPP:

            c->bpp = 24;

            c->decode_intra = zmbv_decode_intra;

            c->decode_xor = zmbv_decode_xor_24;

            break;

#endif //ZMBV_ENABLE_24BPP

        case ZMBV_FMT_32BPP:

            c->bpp = 32;

            c->decode_intra = zmbv_decode_intra;

            c->decode_xor = zmbv_decode_xor_32;

            break;

        default:

            c->decode_intra = NULL;

            c->decode_xor = NULL;

            avpriv_request_sample(avctx, "Format %i", c->fmt);

            return AVERROR_PATCHWELCOME;

        }

        zret = inflateReset(&c->zstream);

        if (zret != Z_OK) {

            av_log(avctx, AV_LOG_ERROR, "Inflate reset error: %d\n", zret);

            return AVERROR_UNKNOWN;

        }

        tmp = av_realloc(c->cur,  avctx->width * avctx->height * (c->bpp / 8));

        if (!tmp)

            return AVERROR(ENOMEM);

        c->cur = tmp;

        tmp = av_realloc(c->prev, avctx->width * avctx->height * (c->bpp / 8));

        if (!tmp)

            return AVERROR(ENOMEM);

        c->prev = tmp;

        c->bx   = (c->width  + c->bw - 1) / c->bw;

        c->by   = (c->height + c->bh - 1) / c->bh;

    }

    if (c->decode_intra == NULL) {

        av_log(avctx, AV_LOG_ERROR, "Error! Got no format or no keyframe!\n");

        return AVERROR_INVALIDDATA;

    }

    if (c->comp == 0) { //Uncompressed data

        if (c->decomp_size < len) {

            av_log(avctx, AV_LOG_ERROR, "Buffer too small\n");

            return AVERROR_INVALIDDATA;

        }

        memcpy(c->decomp_buf, buf, len);

    } else { // ZLIB-compressed data

        c->zstream.total_in = c->zstream.total_out = 0;

        c->zstream.next_in = buf;

        c->zstream.avail_in = len;

        c->zstream.next_out = c->decomp_buf;

        c->zstream.avail_out = c->decomp_size;

        zret = inflate(&c->zstream, Z_SYNC_FLUSH);

        if (zret != Z_OK && zret != Z_STREAM_END) {

            av_log(avctx, AV_LOG_ERROR, "inflate error %d\n", zret);

            return AVERROR_INVALIDDATA;

        }

        c->decomp_len = c->zstream.total_out;

    }

    if (c->flags & ZMBV_KEYFRAME) {

        frame->key_frame = 1;

        frame->pict_type = AV_PICTURE_TYPE_I;

        c->decode_intra(c);

    } else {

        frame->key_frame = 0;

        frame->pict_type = AV_PICTURE_TYPE_P;

        if (c->decomp_len)

            c->decode_xor(c);

    }

    /* update frames */

    {

        uint8_t *out, *src;

        int i, j;

        out = frame->data[0];

        src = c->cur;

        switch (c->fmt) {

        case ZMBV_FMT_8BPP:

            for (j = 0; j < c->height; j++) {

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

                    out[i * 3 + 0] = c->pal[(*src) * 3 + 0];

                    out[i * 3 + 1] = c->pal[(*src) * 3 + 1];

                    out[i * 3 + 2] = c->pal[(*src) * 3 + 2];

                    src++;

                }

                out += frame->linesize[0];

            }

            break;

        case ZMBV_FMT_15BPP:

            for (j = 0; j < c->height; j++) {

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

                    uint16_t tmp = AV_RL16(src);

                    src += 2;

                    out[i * 3 + 0] = (tmp & 0x7C00) >> 7;

                    out[i * 3 + 1] = (tmp & 0x03E0) >> 2;

                    out[i * 3 + 2] = (tmp & 0x001F) << 3;

                }

                out += frame->linesize[0];

            }

            break;

        case ZMBV_FMT_16BPP:

            for (j = 0; j < c->height; j++) {

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

                    uint16_t tmp = AV_RL16(src);

                    src += 2;

                    out[i * 3 + 0] = (tmp & 0xF800) >> 8;

                    out[i * 3 + 1] = (tmp & 0x07E0) >> 3;

                    out[i * 3 + 2] = (tmp & 0x001F) << 3;

                }

                out += frame->linesize[0];

            }

            break;

#ifdef ZMBV_ENABLE_24BPP

        case ZMBV_FMT_24BPP:

            for (j = 0; j < c->height; j++) {

                memcpy(out, src, c->width * 3);

                src += c->width * 3;

                out += frame->linesize[0];

            }

            break;

#endif //ZMBV_ENABLE_24BPP

        case ZMBV_FMT_32BPP:

            for (j = 0; j < c->height; j++) {

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

                    uint32_t tmp = AV_RL32(src);

                    src += 4;

                    AV_WB24(out+(i*3), tmp);

                }

                out += frame->linesize[0];

            }

            break;

        default:

            av_log(avctx, AV_LOG_ERROR, "Cannot handle format %i\n", c->fmt);

        }

        FFSWAP(uint8_t *, c->cur, c->prev);

    }

    *got_frame = 1;

    /* always report that the buffer was completely consumed */

    return buf_size;

}


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

                        int filter_type, double kaiser_beta){

    int ph, i;

    double x, y, w, t;

    double *tab = av_malloc_array(tap_count+1,  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;

    av_assert0(phase_count == 1 || phase_count % 2 == 0);

    for(ph = 0; ph <= phase_count / 2; 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;

                t = cos(w);

                y *= 0.3635819 - 0.4891775 * t + 0.1365995 * (2*t*t-1) - 0.0106411 * (4*t*t*t - 3*t);

                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;

            if (i < tap_count)

                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);

            if (tap_count % 2 == 0) {

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

                    ((int16_t*)filter)[(phase_count-ph) * alloc + tap_count-1-i] = ((int16_t*)filter)[ph * alloc + i];

            }

            else {

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

                    ((int16_t*)filter)[(phase_count-ph) * alloc + tap_count-i] =

                        av_clip(lrintf(tab[i] * scale / (norm - tab[0] + tab[tap_count])), 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));

            if (tap_count % 2 == 0) {

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

                    ((int32_t*)filter)[(phase_count-ph) * alloc + tap_count-1-i] = ((int32_t*)filter)[ph * alloc + i];

            }

            else {

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

                    ((int32_t*)filter)[(phase_count-ph) * alloc + tap_count-i] =

                        av_clipl_int32(llrint(tab[i] * scale / (norm - tab[0] + tab[tap_count])));

            }

            break;

        case AV_SAMPLE_FMT_FLTP:

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

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

            if (tap_count % 2 == 0) {

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

                    ((float*)filter)[(phase_count-ph) * alloc + tap_count-1-i] = ((float*)filter)[ph * alloc + i];

            }

            else {

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

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

            }

            break;

        case AV_SAMPLE_FMT_DBLP:

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

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

            if (tap_count % 2 == 0) {

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

                    ((double*)filter)[(phase_count-ph) * alloc + tap_count-1-i] = ((double*)filter)[ph * alloc + i];

            }

            else {

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

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

            }

            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;

}


static void fft_test(AC3MDCTContext *mdct, AVLFG *lfg)

{

    IComplex in[FN], in1[FN];

    int k, n, i;

    float sum_re, sum_im, a;

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

        in[i].re = av_lfg_get(lfg) % 65535 - 32767;

        in[i].im = av_lfg_get(lfg) % 65535 - 32767;

        in1[i]   = in[i];

    }

    fft(mdct, in, 7);

    /* do it by hand */

    for (k = 0; k < FN; k++) {

        sum_re = 0;

        sum_im = 0;

        for (n = 0; n < FN; n++) {

            a = -2 * M_PI * (n * k) / FN;

            sum_re += in1[n].re * cos(a) - in1[n].im * sin(a);

            sum_im += in1[n].re * sin(a) + in1[n].im * cos(a);

        }

        av_log(NULL, AV_LOG_DEBUG, "%3d: %6d,%6d %6.0f,%6.0f\n",

               k, in[k].re, in[k].im, sum_re / FN, sum_im / FN);

    }

}


static void correlate_slice_buffered(SnowContext *s, slice_buffer * sb, SubBand *b, DWTELEM *src, int stride, int inverse, int use_median, int start_y, int end_y){

    const int w= b->width;

    int x,y;

//    START_TIMER

    DWTELEM * line;

    DWTELEM * prev;

    if (start_y != 0)

        line = slice_buffer_get_line(sb, ((start_y - 1) * b->stride_line) + b->buf_y_offset) + b->buf_x_offset;

    for(y=start_y; y<end_y; y++){

        prev = line;

//        line = slice_buffer_get_line_from_address(sb, src + (y * stride));

        line = slice_buffer_get_line(sb, (y * b->stride_line) + b->buf_y_offset) + b->buf_x_offset;

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

            if(x){

                if(use_median){

                    if(y && x+1<w) line[x] += mid_pred(line[x - 1], prev[x], prev[x + 1]);

                    else  line[x] += line[x - 1];

                }else{

                    if(y) line[x] += mid_pred(line[x - 1], prev[x], line[x - 1] + prev[x] - prev[x - 1]);

                    else  line[x] += line[x - 1];

                }

            }else{

                if(y) line[x] += prev[x];

            }

        }

    }

//    STOP_TIMER("correlate")

}


static void rv34_idct_add_c(uint8_t *dst, ptrdiff_t stride, DCTELEM *block){

    int      temp[16];

    uint8_t *cm = ff_cropTbl + MAX_NEG_CROP;

    int      i;

    rv34_row_transform(temp, block);

    memset(block, 0, 16*sizeof(DCTELEM));

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

        const int z0 = 13*(temp[4*0+i] +    temp[4*2+i]) + 0x200;

        const int z1 = 13*(temp[4*0+i] -    temp[4*2+i]) + 0x200;

        const int z2 =  7* temp[4*1+i] - 17*temp[4*3+i];

        const int z3 = 17* temp[4*1+i] +  7*temp[4*3+i];

        dst[0] = cm[ dst[0] + ( (z0 + z3) >> 10 ) ];

        dst[1] = cm[ dst[1] + ( (z1 + z2) >> 10 ) ];

        dst[2] = cm[ dst[2] + ( (z1 - z2) >> 10 ) ];

        dst[3] = cm[ dst[3] + ( (z0 - z3) >> 10 ) ];

        dst  += stride;

    }

}


int ff_vc1_parse_frame_header(VC1Context *v, GetBitContext* gb)

{

    int pqindex, lowquant, status;

    if (v->finterpflag)

        v->interpfrm = get_bits1(gb);

    if (!v->s.avctx->codec)

        return -1;

    if (v->s.avctx->codec_id == AV_CODEC_ID_MSS2)

        v->respic   =

        v->rangered =

        v->multires = get_bits(gb, 2) == 1;

    else

        skip_bits(gb, 2); //framecnt unused

    v->rangeredfrm = 0;

    if (v->rangered)

        v->rangeredfrm = get_bits1(gb);

    v->s.pict_type = get_bits1(gb);

    if (v->s.avctx->max_b_frames) {

        if (!v->s.pict_type) {

            if (get_bits1(gb))

                v->s.pict_type = AV_PICTURE_TYPE_I;

            else

                v->s.pict_type = AV_PICTURE_TYPE_B;

        } else

            v->s.pict_type = AV_PICTURE_TYPE_P;

    } else

        v->s.pict_type = v->s.pict_type ? AV_PICTURE_TYPE_P : AV_PICTURE_TYPE_I;

    v->bi_type = 0;

    if (v->s.pict_type == AV_PICTURE_TYPE_B) {

        if (read_bfraction(v, gb) < 0)

            return AVERROR_INVALIDDATA;

        if (v->bfraction == 0) {

            v->s.pict_type = AV_PICTURE_TYPE_BI;

        }

    }

    if (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_BI)

        skip_bits(gb, 7); // skip buffer fullness

    if (v->parse_only)

        return 0;

    /* calculate RND */

    if (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_BI)

        v->rnd = 1;

    if (v->s.pict_type == AV_PICTURE_TYPE_P)

        v->rnd ^= 1;

    /* Quantizer stuff */

    pqindex = get_bits(gb, 5);

    if (!pqindex)

        return -1;

    if (v->quantizer_mode == QUANT_FRAME_IMPLICIT)

        v->pq = ff_vc1_pquant_table[0][pqindex];

    else

        v->pq = ff_vc1_pquant_table[1][pqindex];

    v->pquantizer = 1;

    if (v->quantizer_mode == QUANT_FRAME_IMPLICIT)

        v->pquantizer = pqindex < 9;

    if (v->quantizer_mode == QUANT_NON_UNIFORM)

        v->pquantizer = 0;

    v->pqindex = pqindex;

    if (pqindex < 9)

        v->halfpq = get_bits1(gb);

    else

        v->halfpq = 0;

    if (v->quantizer_mode == QUANT_FRAME_EXPLICIT)

        v->pquantizer = get_bits1(gb);

    v->dquantfrm = 0;

    if (v->extended_mv == 1)

        v->mvrange = get_unary(gb, 0, 3);

    v->k_x = v->mvrange + 9 + (v->mvrange >> 1); //k_x can be 9 10 12 13

    v->k_y = v->mvrange + 8; //k_y can be 8 9 10 11

    v->range_x = 1 << (v->k_x - 1);

    v->range_y = 1 << (v->k_y - 1);

    if (v->multires && v->s.pict_type != AV_PICTURE_TYPE_B)

        v->respic = get_bits(gb, 2);

    if (v->res_x8 && (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_BI)) {

        v->x8_type = get_bits1(gb);

    } else

        v->x8_type = 0;

    av_dlog(v->s.avctx, "%c Frame: QP=[%i]%i (+%i/2) %i\n",

            (v->s.pict_type == AV_PICTURE_TYPE_P) ? 'P' : ((v->s.pict_type == AV_PICTURE_TYPE_I) ? 'I' : 'B'),

            pqindex, v->pq, v->halfpq, v->rangeredfrm);

    if (v->first_pic_header_flag)

        rotate_luts(v);

    switch (v->s.pict_type) {

    case AV_PICTURE_TYPE_P:

        if (v->pq < 5)       v->tt_index = 0;

        else if (v->pq < 13) v->tt_index = 1;

        else                 v->tt_index = 2;

        lowquant = (v->pq > 12) ? 0 : 1;

        v->mv_mode = ff_vc1_mv_pmode_table[lowquant][get_unary(gb, 1, 4)];

        if (v->mv_mode == MV_PMODE_INTENSITY_COMP) {

            v->mv_mode2 = ff_vc1_mv_pmode_table2[lowquant][get_unary(gb, 1, 3)];

            v->lumscale = get_bits(gb, 6);

            v->lumshift = get_bits(gb, 6);

            v->last_use_ic = 1;

            /* fill lookup tables for intensity compensation */

            INIT_LUT(v->lumscale, v->lumshift, v->last_luty[0], v->last_lutuv[0], 1);

            INIT_LUT(v->lumscale, v->lumshift, v->last_luty[1], v->last_lutuv[1], 1);

        }

        v->qs_last = v->s.quarter_sample;

        if (v->mv_mode == MV_PMODE_1MV_HPEL || v->mv_mode == MV_PMODE_1MV_HPEL_BILIN)

            v->s.quarter_sample = 0;

        else if (v->mv_mode == MV_PMODE_INTENSITY_COMP) {

            if (v->mv_mode2 == MV_PMODE_1MV_HPEL || v->mv_mode2 == MV_PMODE_1MV_HPEL_BILIN)

                v->s.quarter_sample = 0;

            else

                v->s.quarter_sample = 1;

        } else

            v->s.quarter_sample = 1;

        v->s.mspel = !(v->mv_mode == MV_PMODE_1MV_HPEL_BILIN || (v->mv_mode == MV_PMODE_INTENSITY_COMP && v->mv_mode2 == MV_PMODE_1MV_HPEL_BILIN));

        if ((v->mv_mode  == MV_PMODE_INTENSITY_COMP &&

             v->mv_mode2 == MV_PMODE_MIXED_MV)      ||

            v->mv_mode   == MV_PMODE_MIXED_MV) {

            status = bitplane_decoding(v->mv_type_mb_plane, &v->mv_type_is_raw, v);

            if (status < 0)

                return -1;

            av_log(v->s.avctx, AV_LOG_DEBUG, "MB MV Type plane encoding: "

                   "Imode: %i, Invert: %i\n", status>>1, status&1);

        } else {

            v->mv_type_is_raw = 0;

            memset(v->mv_type_mb_plane, 0, v->s.mb_stride * v->s.mb_height);

        }

        status = bitplane_decoding(v->s.mbskip_table, &v->skip_is_raw, v);

        if (status < 0)

            return -1;

        av_log(v->s.avctx, AV_LOG_DEBUG, "MB Skip plane encoding: "

               "Imode: %i, Invert: %i\n", status>>1, status&1);

        /* Hopefully this is correct for P frames */

        v->s.mv_table_index = get_bits(gb, 2); //but using ff_vc1_ tables

        v->cbpcy_vlc = &ff_vc1_cbpcy_p_vlc[get_bits(gb, 2)];

        if (v->dquant) {

            av_log(v->s.avctx, AV_LOG_DEBUG, "VOP DQuant info\n");

            vop_dquant_decoding(v);

        }

        v->ttfrm = 0; //FIXME Is that so ?

        if (v->vstransform) {

            v->ttmbf = get_bits1(gb);

            if (v->ttmbf) {

                v->ttfrm = ff_vc1_ttfrm_to_tt[get_bits(gb, 2)];

            }

        } else {

            v->ttmbf = 1;

            v->ttfrm = TT_8X8;

        }

        break;

    case AV_PICTURE_TYPE_B:

        if (v->pq < 5)       v->tt_index = 0;

        else if (v->pq < 13) v->tt_index = 1;

        else                 v->tt_index = 2;

        v->mv_mode          = get_bits1(gb) ? MV_PMODE_1MV : MV_PMODE_1MV_HPEL_BILIN;

        v->qs_last          = v->s.quarter_sample;

        v->s.quarter_sample = (v->mv_mode == MV_PMODE_1MV);

        v->s.mspel          = v->s.quarter_sample;

        status = bitplane_decoding(v->direct_mb_plane, &v->dmb_is_raw, v);

        if (status < 0)

            return -1;

        av_log(v->s.avctx, AV_LOG_DEBUG, "MB Direct Type plane encoding: "

               "Imode: %i, Invert: %i\n", status>>1, status&1);

        status = bitplane_decoding(v->s.mbskip_table, &v->skip_is_raw, v);

        if (status < 0)

            return -1;

        av_log(v->s.avctx, AV_LOG_DEBUG, "MB Skip plane encoding: "

               "Imode: %i, Invert: %i\n", status>>1, status&1);

        v->s.mv_table_index = get_bits(gb, 2);

        v->cbpcy_vlc        = &ff_vc1_cbpcy_p_vlc[get_bits(gb, 2)];

        if (v->dquant) {

            av_log(v->s.avctx, AV_LOG_DEBUG, "VOP DQuant info\n");

            vop_dquant_decoding(v);

        }

        v->ttfrm = 0;

        if (v->vstransform) {

            v->ttmbf = get_bits1(gb);

            if (v->ttmbf) {

                v->ttfrm = ff_vc1_ttfrm_to_tt[get_bits(gb, 2)];

            }

        } else {

            v->ttmbf = 1;

            v->ttfrm = TT_8X8;

        }

        break;

    }

    if (!v->x8_type) {

        /* AC Syntax */

        v->c_ac_table_index = decode012(gb);

        if (v->s.pict_type == AV_PICTURE_TYPE_I || v->s.pict_type == AV_PICTURE_TYPE_BI) {

            v->y_ac_table_index = decode012(gb);

        }

        /* DC Syntax */

        v->s.dc_table_index = get_bits1(gb);

    }

    if (v->s.pict_type == AV_PICTURE_TYPE_BI) {

        v->s.pict_type = AV_PICTURE_TYPE_B;

        v->bi_type     = 1;

    }

    return 0;

}


static int mov_preroll_write_stbl_atoms(AVIOContext *pb, MOVTrack *track)

{

    struct sgpd_entry {

        int count;

        int16_t roll_distance;

        int group_description_index;

    };

    struct sgpd_entry *sgpd_entries = NULL;

    int entries = -1;

    int group = 0;

    int i, j;

    const int OPUS_SEEK_PREROLL_MS = 80;

    int roll_samples = av_rescale_q(OPUS_SEEK_PREROLL_MS,

                                    (AVRational){1, 1000},

                                    (AVRational){1, 48000});

    if (track->entry) {

        sgpd_entries = av_malloc_array(track->entry, sizeof(*sgpd_entries));

        if (!sgpd_entries)

            return AVERROR(ENOMEM);

    }

    av_assert0(track->par->codec_id == AV_CODEC_ID_OPUS);

    for (i = 0; i < track->entry; i++) {

        int roll_samples_remaining = roll_samples;

        int distance = 0;

        for (j = i - 1; j >= 0; j--) {

            roll_samples_remaining -= get_cluster_duration(track, j);

            distance++;

            if (roll_samples_remaining <= 0)

                break;

        }

        /* We don't have enough preceeding samples to compute a valid

           roll_distance here, so this sample can't be independently

           decoded. */

        if (roll_samples_remaining > 0)

            distance = 0;

        /* Verify distance is a minimum of 2 (60ms) packets and a maximum of

           32 (2.5ms) packets. */

        av_assert0(distance == 0 || (distance >= 2 && distance <= 32));

        if (i && distance == sgpd_entries[entries].roll_distance) {

            sgpd_entries[entries].count++;

        } else {

            entries++;

            sgpd_entries[entries].count = 1;

            sgpd_entries[entries].roll_distance = distance;

            sgpd_entries[entries].group_description_index = distance ? ++group : 0;

        }

    }

    entries++;

    if (!group)

        return 0;

    /* Write sgpd tag */

    avio_wb32(pb, 24 + (group * 2)); /* size */

    ffio_wfourcc(pb, "sgpd");

    avio_wb32(pb, 1 << 24); /* fullbox */

    ffio_wfourcc(pb, "roll");

    avio_wb32(pb, 2); /* default_length */

    avio_wb32(pb, group); /* entry_count */

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

        if (sgpd_entries[i].group_description_index) {

            avio_wb16(pb, -sgpd_entries[i].roll_distance); /* roll_distance */

        }

    }

    /* Write sbgp tag */

    avio_wb32(pb, 20 + (entries * 8)); /* size */

    ffio_wfourcc(pb, "sbgp");

    avio_wb32(pb, 0); /* fullbox */

    ffio_wfourcc(pb, "roll");

    avio_wb32(pb, entries); /* entry_count */

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

        avio_wb32(pb, sgpd_entries[i].count); /* sample_count */

        avio_wb32(pb, sgpd_entries[i].group_description_index); /* group_description_index */

    }

    av_free(sgpd_entries);

    return 0;

}


static av_always_inline void emulated_edge_mc(uint8_t *buf, const uint8_t *src,

                                              ptrdiff_t linesize_arg,

                                              int block_w, int block_h,

                                              int src_x, int src_y,

                                              int w, int h,

                                              emu_edge_core_func *core_fn)

{

    int start_y, start_x, end_y, end_x, src_y_add = 0;

    int linesize = linesize_arg;

    if(!w || !h)

        return;

    if (src_y >= h) {

        src -= src_y*linesize;

        src_y_add = h - 1;

        src_y     = h - 1;

    } else if (src_y <= -block_h) {

        src -= src_y*linesize;

        src_y_add = 1 - block_h;

        src_y     = 1 - block_h;

    }

    if (src_x >= w) {

        src   += w - 1 - src_x;

        src_x  = w - 1;

    } else if (src_x <= -block_w) {

        src   += 1 - block_w - src_x;

        src_x  = 1 - block_w;

    }

    start_y = FFMAX(0, -src_y);

    start_x = FFMAX(0, -src_x);

    end_y   = FFMIN(block_h, h-src_y);

    end_x   = FFMIN(block_w, w-src_x);

    av_assert2(start_x < end_x && block_w > 0);

    av_assert2(start_y < end_y && block_h > 0);

    // fill in the to-be-copied part plus all above/below

    src += (src_y_add + start_y) * linesize + start_x;

    buf += start_x;

    core_fn(buf, src, linesize, start_y, end_y,

            block_h, start_x, end_x, block_w);

}


static int vmdk_init_tables(BlockDriverState *bs, VmdkExtent *extent,

                            Error **errp)

{

    int ret;

    int l1_size, i;

    /* read the L1 table */

    l1_size = extent->l1_size * sizeof(uint32_t);

    extent->l1_table = g_try_malloc(l1_size);

    if (l1_size && extent->l1_table == NULL) {

        return -ENOMEM;

    }

    ret = bdrv_pread(extent->file,

                     extent->l1_table_offset,

                     extent->l1_table,

                     l1_size);

    if (ret < 0) {

        error_setg_errno(errp, -ret,

                         "Could not read l1 table from extent '%s'",

                         extent->file->filename);

        goto fail_l1;

    }

    for (i = 0; i < extent->l1_size; i++) {

        le32_to_cpus(&extent->l1_table[i]);

    }

    if (extent->l1_backup_table_offset) {

        extent->l1_backup_table = g_try_malloc(l1_size);

        if (l1_size && extent->l1_backup_table == NULL) {

            ret = -ENOMEM;

            goto fail_l1;

        }

        ret = bdrv_pread(extent->file,

                         extent->l1_backup_table_offset,

                         extent->l1_backup_table,

                         l1_size);

        if (ret < 0) {

            error_setg_errno(errp, -ret,

                             "Could not read l1 backup table from extent '%s'",

                             extent->file->filename);

            goto fail_l1b;

        }

        for (i = 0; i < extent->l1_size; i++) {

            le32_to_cpus(&extent->l1_backup_table[i]);

        }

    }

    extent->l2_cache =

        g_new(uint32_t, extent->l2_size * L2_CACHE_SIZE);

    return 0;

 fail_l1b:

    g_free(extent->l1_backup_table);

 fail_l1:

    g_free(extent->l1_table);

    return ret;

}


static void bdrv_password_cb(void *opaque, const char *password,

                             void *readline_opaque)

{

    Monitor *mon = opaque;

    BlockDriverState *bs = readline_opaque;

    int ret = 0;

    Error *local_err = NULL;

    bdrv_add_key(bs, password, &local_err);

    if (local_err) {

        error_report_err(local_err);

        ret = -EPERM;

    }

    if (mon->password_completion_cb)

        mon->password_completion_cb(mon->password_opaque, ret);

    monitor_read_command(mon, 1);

}


static int vmdk_L2update(BlockDriverState *bs, VmdkMetaData *m_data)

{

    BDRVVmdkState *s = bs->opaque;

    /* update L2 table */

    if (bdrv_pwrite(bs->file, ((int64_t)m_data->l2_offset * 512) + (m_data->l2_index * sizeof(m_data->offset)),

                    &(m_data->offset), sizeof(m_data->offset)) != sizeof(m_data->offset))

        return -1;

    /* update backup L2 table */

    if (s->l1_backup_table_offset != 0) {

        m_data->l2_offset = s->l1_backup_table[m_data->l1_index];

        if (bdrv_pwrite(bs->file, ((int64_t)m_data->l2_offset * 512) + (m_data->l2_index * sizeof(m_data->offset)),

                        &(m_data->offset), sizeof(m_data->offset)) != sizeof(m_data->offset))

            return -1;

    }

    return 0;

}


static int bdrv_inactivate_recurse(BlockDriverState *bs,

                                   bool setting_flag)

{

    BdrvChild *child, *parent;

    int ret;

    if (!setting_flag && bs->drv->bdrv_inactivate) {

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

        if (ret < 0) {

            return ret;

        }

    }

    if (setting_flag) {

        uint64_t perm, shared_perm;

        bs->open_flags |= BDRV_O_INACTIVE;

        QLIST_FOREACH(parent, &bs->parents, next_parent) {

            if (parent->role->inactivate) {

                ret = parent->role->inactivate(parent);

                if (ret < 0) {

                    bs->open_flags &= ~BDRV_O_INACTIVE;

                    return ret;

                }

            }

        }

        /* Update permissions, they may differ for inactive nodes */

        bdrv_get_cumulative_perm(bs, &perm, &shared_perm);

        bdrv_check_perm(bs, perm, shared_perm, NULL, &error_abort);

        bdrv_set_perm(bs, perm, shared_perm);

    }

    QLIST_FOREACH(child, &bs->children, next) {

        ret = bdrv_inactivate_recurse(child->bs, setting_flag);

        if (ret < 0) {

            return ret;

        }

    }

    /* At this point persistent bitmaps should be already stored by the format

     * driver */

    bdrv_release_persistent_dirty_bitmaps(bs);

    return 0;

}


int qcow2_read_snapshots(BlockDriverState *bs)

{

    BDRVQcowState *s = bs->opaque;

    QCowSnapshotHeader h;

    QCowSnapshotExtraData extra;

    QCowSnapshot *sn;

    int i, id_str_size, name_size;

    int64_t offset;

    uint32_t extra_data_size;

    int ret;

    if (!s->nb_snapshots) {

        s->snapshots = NULL;

        s->snapshots_size = 0;

        return 0;

    }

    offset = s->snapshots_offset;

    s->snapshots = g_malloc0(s->nb_snapshots * sizeof(QCowSnapshot));

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

        /* Read statically sized part of the snapshot header */

        offset = align_offset(offset, 8);

        ret = bdrv_pread(bs->file, offset, &h, sizeof(h));

        if (ret < 0) {

            goto fail;

        }

        offset += sizeof(h);

        sn = s->snapshots + i;

        sn->l1_table_offset = be64_to_cpu(h.l1_table_offset);

        sn->l1_size = be32_to_cpu(h.l1_size);

        sn->vm_state_size = be32_to_cpu(h.vm_state_size);

        sn->date_sec = be32_to_cpu(h.date_sec);

        sn->date_nsec = be32_to_cpu(h.date_nsec);

        sn->vm_clock_nsec = be64_to_cpu(h.vm_clock_nsec);

        extra_data_size = be32_to_cpu(h.extra_data_size);

        id_str_size = be16_to_cpu(h.id_str_size);

        name_size = be16_to_cpu(h.name_size);

        /* Read extra data */

        ret = bdrv_pread(bs->file, offset, &extra,

                         MIN(sizeof(extra), extra_data_size));

        if (ret < 0) {

            goto fail;

        }

        offset += extra_data_size;

        if (extra_data_size >= 8) {

            sn->vm_state_size = be64_to_cpu(extra.vm_state_size_large);

        }

        if (extra_data_size >= 16) {

            sn->disk_size = be64_to_cpu(extra.disk_size);

        } else {

            sn->disk_size = bs->total_sectors * BDRV_SECTOR_SIZE;

        }

        /* Read snapshot ID */

        sn->id_str = g_malloc(id_str_size + 1);

        ret = bdrv_pread(bs->file, offset, sn->id_str, id_str_size);

        if (ret < 0) {

            goto fail;

        }

        offset += id_str_size;

        sn->id_str[id_str_size] = '\0';

        /* Read snapshot name */

        sn->name = g_malloc(name_size + 1);

        ret = bdrv_pread(bs->file, offset, sn->name, name_size);

        if (ret < 0) {

            goto fail;

        }

        offset += name_size;

        sn->name[name_size] = '\0';

        if (offset - s->snapshots_offset > QCOW_MAX_SNAPSHOTS_SIZE) {

            ret = -EFBIG;

            goto fail;

        }

    }

    assert(offset - s->snapshots_offset <= INT_MAX);

    s->snapshots_size = offset - s->snapshots_offset;

    return 0;

fail:

    qcow2_free_snapshots(bs);

    return ret;

}


static abi_long do_fcntl(int fd, int cmd, abi_ulong arg)

{

    struct flock fl;

    struct target_flock *target_fl;

    struct flock64 fl64;

    struct target_flock64 *target_fl64;

#ifdef F_GETOWN_EX

    struct f_owner_ex fox;

    struct target_f_owner_ex *target_fox;

#endif

    abi_long ret;

    int host_cmd = target_to_host_fcntl_cmd(cmd);

    if (host_cmd == -TARGET_EINVAL)

	    return host_cmd;

    switch(cmd) {

    case TARGET_F_GETLK:

        if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))

            return -TARGET_EFAULT;

        fl.l_type =

                  target_to_host_bitmask(tswap16(target_fl->l_type), flock_tbl);

        fl.l_whence = tswap16(target_fl->l_whence);

        fl.l_start = tswapal(target_fl->l_start);

        fl.l_len = tswapal(target_fl->l_len);

        fl.l_pid = tswap32(target_fl->l_pid);

        unlock_user_struct(target_fl, arg, 0);

        ret = get_errno(fcntl(fd, host_cmd, &fl));

        if (ret == 0) {

            if (!lock_user_struct(VERIFY_WRITE, target_fl, arg, 0))

                return -TARGET_EFAULT;

            target_fl->l_type =

                          host_to_target_bitmask(tswap16(fl.l_type), flock_tbl);

            target_fl->l_whence = tswap16(fl.l_whence);

            target_fl->l_start = tswapal(fl.l_start);

            target_fl->l_len = tswapal(fl.l_len);

            target_fl->l_pid = tswap32(fl.l_pid);

            unlock_user_struct(target_fl, arg, 1);

        }

        break;

    case TARGET_F_SETLK:

    case TARGET_F_SETLKW:

        if (!lock_user_struct(VERIFY_READ, target_fl, arg, 1))

            return -TARGET_EFAULT;

        fl.l_type =

                  target_to_host_bitmask(tswap16(target_fl->l_type), flock_tbl);

        fl.l_whence = tswap16(target_fl->l_whence);

        fl.l_start = tswapal(target_fl->l_start);

        fl.l_len = tswapal(target_fl->l_len);

        fl.l_pid = tswap32(target_fl->l_pid);

        unlock_user_struct(target_fl, arg, 0);

        ret = get_errno(fcntl(fd, host_cmd, &fl));

        break;

    case TARGET_F_GETLK64:

        if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))

            return -TARGET_EFAULT;

        fl64.l_type =

           target_to_host_bitmask(tswap16(target_fl64->l_type), flock_tbl) >> 1;

        fl64.l_whence = tswap16(target_fl64->l_whence);

        fl64.l_start = tswap64(target_fl64->l_start);

        fl64.l_len = tswap64(target_fl64->l_len);

        fl64.l_pid = tswap32(target_fl64->l_pid);

        unlock_user_struct(target_fl64, arg, 0);

        ret = get_errno(fcntl(fd, host_cmd, &fl64));

        if (ret == 0) {

            if (!lock_user_struct(VERIFY_WRITE, target_fl64, arg, 0))

                return -TARGET_EFAULT;

            target_fl64->l_type =

                   host_to_target_bitmask(tswap16(fl64.l_type), flock_tbl) >> 1;

            target_fl64->l_whence = tswap16(fl64.l_whence);

            target_fl64->l_start = tswap64(fl64.l_start);

            target_fl64->l_len = tswap64(fl64.l_len);

            target_fl64->l_pid = tswap32(fl64.l_pid);

            unlock_user_struct(target_fl64, arg, 1);

        }

        break;

    case TARGET_F_SETLK64:

    case TARGET_F_SETLKW64:

        if (!lock_user_struct(VERIFY_READ, target_fl64, arg, 1))

            return -TARGET_EFAULT;

        fl64.l_type =

           target_to_host_bitmask(tswap16(target_fl64->l_type), flock_tbl) >> 1;

        fl64.l_whence = tswap16(target_fl64->l_whence);

        fl64.l_start = tswap64(target_fl64->l_start);

        fl64.l_len = tswap64(target_fl64->l_len);

        fl64.l_pid = tswap32(target_fl64->l_pid);

        unlock_user_struct(target_fl64, arg, 0);

        ret = get_errno(fcntl(fd, host_cmd, &fl64));

        break;

    case TARGET_F_GETFL:

        ret = get_errno(fcntl(fd, host_cmd, arg));

        if (ret >= 0) {

            ret = host_to_target_bitmask(ret, fcntl_flags_tbl);

        }

        break;

    case TARGET_F_SETFL:

        ret = get_errno(fcntl(fd, host_cmd, target_to_host_bitmask(arg, fcntl_flags_tbl)));

        break;

#ifdef F_GETOWN_EX

    case TARGET_F_GETOWN_EX:

        ret = get_errno(fcntl(fd, host_cmd, &fox));

        if (ret >= 0) {

            if (!lock_user_struct(VERIFY_WRITE, target_fox, arg, 0))

                return -TARGET_EFAULT;

            target_fox->type = tswap32(fox.type);

            target_fox->pid = tswap32(fox.pid);

            unlock_user_struct(target_fox, arg, 1);

        }

        break;

#endif

#ifdef F_SETOWN_EX

    case TARGET_F_SETOWN_EX:

        if (!lock_user_struct(VERIFY_READ, target_fox, arg, 1))

            return -TARGET_EFAULT;

        fox.type = tswap32(target_fox->type);

        fox.pid = tswap32(target_fox->pid);

        unlock_user_struct(target_fox, arg, 0);

        ret = get_errno(fcntl(fd, host_cmd, &fox));

        break;

#endif

    case TARGET_F_SETOWN:

    case TARGET_F_GETOWN:

    case TARGET_F_SETSIG:

    case TARGET_F_GETSIG:

    case TARGET_F_SETLEASE:

    case TARGET_F_GETLEASE:

        ret = get_errno(fcntl(fd, host_cmd, arg));

        break;

    default:

        ret = get_errno(fcntl(fd, cmd, arg));

        break;

    }

    return ret;

}


const uint8_t *avpriv_find_start_code(const uint8_t *av_restrict p,

                                      const uint8_t *end,

                                      uint32_t *av_restrict state)

{

    int i;

    assert(p <= end);

    if (p >= end)

        return end;

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

        uint32_t tmp = *state << 8;

        *state = tmp + *(p++);

        if (tmp == 0x100 || p == end)

            return p;

    }

    while (p < end) {

        if      (p[-1] > 1      ) p += 3;

        else if (p[-2]          ) p += 2;

        else if (p[-3]|(p[-1]-1)) p++;

        else {

            p++;

            break;

        }

    }

    p = FFMIN(p, end) - 4;

    *state = AV_RB32(p);

    return p + 4;

}