static int vc1_decode_frame(AVCodecContext *avctx, void *data, int *data_size, AVPacket *avpkt) { const uint8_t *buf = avpkt->data; int buf_size = avpkt->size, n_slices = 0, i; VC1Context *v = avctx->priv_data; MpegEncContext *s = &v->s; AVFrame *pict = data; uint8_t *buf2 = NULL; const uint8_t *buf_start = buf; int mb_height, n_slices1; struct { uint8_t *buf; GetBitContext gb; int mby_start; } *slices = NULL, *tmp; /* no supplementary picture */ if (buf_size == 0 || (buf_size == 4 && AV_RB32(buf) == VC1_CODE_ENDOFSEQ)) { /* special case for last picture */ if (s->low_delay == 0 && s->next_picture_ptr) { *pict = s->next_picture_ptr->f; s->next_picture_ptr = NULL; *data_size = sizeof(AVFrame); } return 0; } if (s->avctx->codec->capabilities&CODEC_CAP_HWACCEL_VDPAU) { if (v->profile < PROFILE_ADVANCED) avctx->pix_fmt = AV_PIX_FMT_VDPAU_WMV3; else avctx->pix_fmt = AV_PIX_FMT_VDPAU_VC1; } //for advanced profile we may need to parse and unescape data if (avctx->codec_id == AV_CODEC_ID_VC1 || avctx->codec_id == AV_CODEC_ID_VC1IMAGE) { int buf_size2 = 0; buf2 = av_mallocz(buf_size + FF_INPUT_BUFFER_PADDING_SIZE); if (IS_MARKER(AV_RB32(buf))) { /* frame starts with marker and needs to be parsed */ const uint8_t *start, *end, *next; int size; next = buf; for (start = buf, end = buf + buf_size; next < end; start = next) { next = find_next_marker(start + 4, end); size = next - start - 4; if (size <= 0) continue; switch (AV_RB32(start)) { case VC1_CODE_FRAME: if (avctx->hwaccel || s->avctx->codec->capabilities&CODEC_CAP_HWACCEL_VDPAU) buf_start = start; buf_size2 = vc1_unescape_buffer(start + 4, size, buf2); break; case VC1_CODE_FIELD: { int buf_size3; tmp = av_realloc(slices, sizeof(*slices) * (n_slices+1)); if (!tmp) goto err; slices = tmp; slices[n_slices].buf = av_mallocz(buf_size + FF_INPUT_BUFFER_PADDING_SIZE); if (!slices[n_slices].buf) goto err; buf_size3 = vc1_unescape_buffer(start + 4, size, slices[n_slices].buf); init_get_bits(&slices[n_slices].gb, slices[n_slices].buf, buf_size3 << 3); /* assuming that the field marker is at the exact middle, hope it's correct */ slices[n_slices].mby_start = s->mb_height >> 1; n_slices1 = n_slices - 1; // index of the last slice of the first field n_slices++; break; } case VC1_CODE_ENTRYPOINT: /* it should be before frame data */ buf_size2 = vc1_unescape_buffer(start + 4, size, buf2); init_get_bits(&s->gb, buf2, buf_size2 * 8); ff_vc1_decode_entry_point(avctx, v, &s->gb); break; case VC1_CODE_SLICE: { int buf_size3; tmp = av_realloc(slices, sizeof(*slices) * (n_slices+1)); if (!tmp) goto err; slices = tmp; slices[n_slices].buf = av_mallocz(buf_size + FF_INPUT_BUFFER_PADDING_SIZE); if (!slices[n_slices].buf) goto err; buf_size3 = vc1_unescape_buffer(start + 4, size, slices[n_slices].buf); init_get_bits(&slices[n_slices].gb, slices[n_slices].buf, buf_size3 << 3); slices[n_slices].mby_start = get_bits(&slices[n_slices].gb, 9); n_slices++; break; } } } } else if (v->interlace && ((buf[0] & 0xC0) == 0xC0)) { /* WVC1 interlaced stores both fields divided by marker */ const uint8_t *divider; int buf_size3; divider = find_next_marker(buf, buf + buf_size); if ((divider == (buf + buf_size)) || AV_RB32(divider) != VC1_CODE_FIELD) { av_log(avctx, AV_LOG_ERROR, "Error in WVC1 interlaced frame\n"); goto err; } else { // found field marker, unescape second field tmp = av_realloc(slices, sizeof(*slices) * (n_slices+1)); if (!tmp) goto err; slices = tmp; slices[n_slices].buf = av_mallocz(buf_size + FF_INPUT_BUFFER_PADDING_SIZE); if (!slices[n_slices].buf) goto err; buf_size3 = vc1_unescape_buffer(divider + 4, buf + buf_size - divider - 4, slices[n_slices].buf); init_get_bits(&slices[n_slices].gb, slices[n_slices].buf, buf_size3 << 3); slices[n_slices].mby_start = s->mb_height >> 1; n_slices1 = n_slices - 1; n_slices++; } buf_size2 = vc1_unescape_buffer(buf, divider - buf, buf2); } else { buf_size2 = vc1_unescape_buffer(buf, buf_size, buf2); } init_get_bits(&s->gb, buf2, buf_size2*8); } else init_get_bits(&s->gb, buf, buf_size*8); if (v->res_sprite) { v->new_sprite = !get_bits1(&s->gb); v->two_sprites = get_bits1(&s->gb); /* res_sprite means a Windows Media Image stream, AV_CODEC_ID_*IMAGE means we're using the sprite compositor. These are intentionally kept separate so you can get the raw sprites by using the wmv3 decoder for WMVP or the vc1 one for WVP2 */ if (avctx->codec_id == AV_CODEC_ID_WMV3IMAGE || avctx->codec_id == AV_CODEC_ID_VC1IMAGE) { if (v->new_sprite) { // switch AVCodecContext parameters to those of the sprites avctx->width = avctx->coded_width = v->sprite_width; avctx->height = avctx->coded_height = v->sprite_height; } else { goto image; } } } if (s->context_initialized && (s->width != avctx->coded_width || s->height != avctx->coded_height)) { ff_vc1_decode_end(avctx); } if (!s->context_initialized) { if (ff_msmpeg4_decode_init(avctx) < 0 || ff_vc1_decode_init_alloc_tables(v) < 0) return -1; s->low_delay = !avctx->has_b_frames || v->res_sprite; if (v->profile == PROFILE_ADVANCED) { s->h_edge_pos = avctx->coded_width; s->v_edge_pos = avctx->coded_height; } } /* We need to set current_picture_ptr before reading the header, * otherwise we cannot store anything in there. */ if (s->current_picture_ptr == NULL || s->current_picture_ptr->f.data[0]) { int i = ff_find_unused_picture(s, 0); if (i < 0) goto err; s->current_picture_ptr = &s->picture[i]; } // do parse frame header v->pic_header_flag = 0; if (v->profile < PROFILE_ADVANCED) { if (ff_vc1_parse_frame_header(v, &s->gb) == -1) { goto err; } } else { if (ff_vc1_parse_frame_header_adv(v, &s->gb) == -1) { goto err; } } if ((avctx->codec_id == AV_CODEC_ID_WMV3IMAGE || avctx->codec_id == AV_CODEC_ID_VC1IMAGE) && s->pict_type != AV_PICTURE_TYPE_I) { av_log(v->s.avctx, AV_LOG_ERROR, "Sprite decoder: expected I-frame\n"); goto err; } // process pulldown flags s->current_picture_ptr->f.repeat_pict = 0; // Pulldown flags are only valid when 'broadcast' has been set. // So ticks_per_frame will be 2 if (v->rff) { // repeat field s->current_picture_ptr->f.repeat_pict = 1; } else if (v->rptfrm) { // repeat frames s->current_picture_ptr->f.repeat_pict = v->rptfrm * 2; } // for skipping the frame s->current_picture.f.pict_type = s->pict_type; s->current_picture.f.key_frame = s->pict_type == AV_PICTURE_TYPE_I; /* skip B-frames if we don't have reference frames */ if (s->last_picture_ptr == NULL && (s->pict_type == AV_PICTURE_TYPE_B || s->dropable)) { goto err; } if ((avctx->skip_frame >= AVDISCARD_NONREF && s->pict_type == AV_PICTURE_TYPE_B) || (avctx->skip_frame >= AVDISCARD_NONKEY && s->pict_type != AV_PICTURE_TYPE_I) || avctx->skip_frame >= AVDISCARD_ALL) { goto end; } if (s->next_p_frame_damaged) { if (s->pict_type == AV_PICTURE_TYPE_B) goto end; else s->next_p_frame_damaged = 0; } if (ff_MPV_frame_start(s, avctx) < 0) { goto err; } s->me.qpel_put = s->dsp.put_qpel_pixels_tab; s->me.qpel_avg = s->dsp.avg_qpel_pixels_tab; if ((CONFIG_VC1_VDPAU_DECODER) &&s->avctx->codec->capabilities&CODEC_CAP_HWACCEL_VDPAU) ff_vdpau_vc1_decode_picture(s, buf_start, (buf + buf_size) - buf_start); else if (avctx->hwaccel) { if (avctx->hwaccel->start_frame(avctx, buf, buf_size) < 0) goto err; if (avctx->hwaccel->decode_slice(avctx, buf_start, (buf + buf_size) - buf_start) < 0) goto err; if (avctx->hwaccel->end_frame(avctx) < 0) goto err; } else { ff_er_frame_start(s); v->bits = buf_size * 8; v->end_mb_x = s->mb_width; if (v->field_mode) { uint8_t *tmp[2]; s->current_picture.f.linesize[0] <<= 1; s->current_picture.f.linesize[1] <<= 1; s->current_picture.f.linesize[2] <<= 1; s->linesize <<= 1; s->uvlinesize <<= 1; tmp[0] = v->mv_f_last[0]; tmp[1] = v->mv_f_last[1]; v->mv_f_last[0] = v->mv_f_next[0]; v->mv_f_last[1] = v->mv_f_next[1]; v->mv_f_next[0] = v->mv_f[0]; v->mv_f_next[1] = v->mv_f[1]; v->mv_f[0] = tmp[0]; v->mv_f[1] = tmp[1]; } mb_height = s->mb_height >> v->field_mode; for (i = 0; i <= n_slices; i++) { if (i > 0 && slices[i - 1].mby_start >= mb_height) { if (v->field_mode <= 0) { av_log(v->s.avctx, AV_LOG_ERROR, "Slice %d starts beyond " "picture boundary (%d >= %d)\n", i, slices[i - 1].mby_start, mb_height); continue; } v->second_field = 1; v->blocks_off = s->mb_width * s->mb_height << 1; v->mb_off = s->mb_stride * s->mb_height >> 1; } else { v->second_field = 0; v->blocks_off = 0; v->mb_off = 0; } if (i) { v->pic_header_flag = 0; if (v->field_mode && i == n_slices1 + 2) { if (ff_vc1_parse_frame_header_adv(v, &s->gb) < 0) { av_log(v->s.avctx, AV_LOG_ERROR, "Field header damaged\n"); continue; } } else if (get_bits1(&s->gb)) { v->pic_header_flag = 1; if (ff_vc1_parse_frame_header_adv(v, &s->gb) < 0) { av_log(v->s.avctx, AV_LOG_ERROR, "Slice header damaged\n"); continue; } } } s->start_mb_y = (i == 0) ? 0 : FFMAX(0, slices[i-1].mby_start % mb_height); if (!v->field_mode || v->second_field) s->end_mb_y = (i == n_slices ) ? mb_height : FFMIN(mb_height, slices[i].mby_start % mb_height); else s->end_mb_y = (i <= n_slices1 + 1) ? mb_height : FFMIN(mb_height, slices[i].mby_start % mb_height); ff_vc1_decode_blocks(v); if (i != n_slices) s->gb = slices[i].gb; } if (v->field_mode) { v->second_field = 0; if (s->pict_type == AV_PICTURE_TYPE_B) { memcpy(v->mv_f_base, v->mv_f_next_base, 2 * (s->b8_stride * (s->mb_height * 2 + 1) + s->mb_stride * (s->mb_height + 1) * 2)); } s->current_picture.f.linesize[0] >>= 1; s->current_picture.f.linesize[1] >>= 1; s->current_picture.f.linesize[2] >>= 1; s->linesize >>= 1; s->uvlinesize >>= 1; } av_dlog(s->avctx, "Consumed %i/%i bits\n", get_bits_count(&s->gb), s->gb.size_in_bits); // if (get_bits_count(&s->gb) > buf_size * 8) // return -1; ff_er_frame_end(s); } ff_MPV_frame_end(s); if (avctx->codec_id == AV_CODEC_ID_WMV3IMAGE || avctx->codec_id == AV_CODEC_ID_VC1IMAGE) { image: avctx->width = avctx->coded_width = v->output_width; avctx->height = avctx->coded_height = v->output_height; if (avctx->skip_frame >= AVDISCARD_NONREF) goto end; #if CONFIG_WMV3IMAGE_DECODER || CONFIG_VC1IMAGE_DECODER if (vc1_decode_sprites(v, &s->gb)) goto err; #endif *pict = v->sprite_output_frame; *data_size = sizeof(AVFrame); } else { if (s->pict_type == AV_PICTURE_TYPE_B || s->low_delay) { *pict = s->current_picture_ptr->f; } else if (s->last_picture_ptr != NULL) { *pict = s->last_picture_ptr->f; } if (s->last_picture_ptr || s->low_delay) { *data_size = sizeof(AVFrame); ff_print_debug_info(s, pict); } } end: av_free(buf2); for (i = 0; i < n_slices; i++) av_free(slices[i].buf); av_free(slices); return buf_size; err: av_free(buf2); for (i = 0; i < n_slices; i++) av_free(slices[i].buf); av_free(slices); return -1; }


int ff_h263_decode_frame(AVCodecContext *avctx, void *data, int *got_frame, AVPacket *avpkt) { const uint8_t *buf = avpkt->data; int buf_size = avpkt->size; MpegEncContext *s = avctx->priv_data; int ret; AVFrame *pict = data; s->flags= avctx->flags; s->flags2= avctx->flags2; /* no supplementary picture */ if (buf_size == 0) { /* special case for last picture */ if (s->low_delay==0 && s->next_picture_ptr) { if ((ret = av_frame_ref(pict, &s->next_picture_ptr->f)) < 0) return ret; s->next_picture_ptr= NULL; *got_frame = 1; } return 0; } if(s->flags&CODEC_FLAG_TRUNCATED){ int next; if(CONFIG_MPEG4_DECODER && s->codec_id==AV_CODEC_ID_MPEG4){ next= ff_mpeg4_find_frame_end(&s->parse_context, buf, buf_size); }else if(CONFIG_H263_DECODER && s->codec_id==AV_CODEC_ID_H263){ next= ff_h263_find_frame_end(&s->parse_context, buf, buf_size); }else if(CONFIG_H263P_DECODER && s->codec_id==AV_CODEC_ID_H263P){ next= ff_h263_find_frame_end(&s->parse_context, buf, buf_size); }else{ av_log(s->avctx, AV_LOG_ERROR, "this codec does not support truncated bitstreams\n"); return AVERROR(EINVAL); } if( ff_combine_frame(&s->parse_context, next, (const uint8_t **)&buf, &buf_size) < 0 ) return buf_size; } retry: if(s->divx_packed && s->bitstream_buffer_size){ int i; for(i=0; i<buf_size-3; i++){ if(buf[i]==0 && buf[i+1]==0 && buf[i+2]==1){ if(buf[i+3]==0xB0){ av_log(s->avctx, AV_LOG_WARNING, "Discarding excessive bitstream in packed xvid\n"); s->bitstream_buffer_size=0; } break; } } } if(s->bitstream_buffer_size && (s->divx_packed || buf_size<20)){ //divx 5.01+/xvid frame reorder init_get_bits(&s->gb, s->bitstream_buffer, s->bitstream_buffer_size*8); }else init_get_bits(&s->gb, buf, buf_size*8); s->bitstream_buffer_size=0; if (!s->context_initialized) { if ((ret = ff_MPV_common_init(s)) < 0) //we need the idct permutaton for reading a custom matrix return ret; } /* We need to set current_picture_ptr before reading the header, * otherwise we cannot store anyting in there */ if (s->current_picture_ptr == NULL || s->current_picture_ptr->f.data[0]) { int i= ff_find_unused_picture(s, 0); if (i < 0) return i; s->current_picture_ptr= &s->picture[i]; } /* let's go :-) */ if (CONFIG_WMV2_DECODER && s->msmpeg4_version==5) { ret= ff_wmv2_decode_picture_header(s); } else if (CONFIG_MSMPEG4_DECODER && s->msmpeg4_version) { ret = ff_msmpeg4_decode_picture_header(s); } else if (CONFIG_MPEG4_DECODER && s->h263_pred) { if(s->avctx->extradata_size && s->picture_number==0){ GetBitContext gb; init_get_bits(&gb, s->avctx->extradata, s->avctx->extradata_size*8); ret = ff_mpeg4_decode_picture_header(s, &gb); } ret = ff_mpeg4_decode_picture_header(s, &s->gb); } else if (CONFIG_H263I_DECODER && s->codec_id == AV_CODEC_ID_H263I) { ret = ff_intel_h263_decode_picture_header(s); } else if (CONFIG_FLV_DECODER && s->h263_flv) { ret = ff_flv_decode_picture_header(s); } else { ret = ff_h263_decode_picture_header(s); } if (ret < 0 || ret==FRAME_SKIPPED) { if ( s->width != avctx->coded_width || s->height != avctx->coded_height) { av_log(s->avctx, AV_LOG_WARNING, "Reverting picture dimensions change due to header decoding failure\n"); s->width = avctx->coded_width; s->height= avctx->coded_height; } } if(ret==FRAME_SKIPPED) return get_consumed_bytes(s, buf_size); /* skip if the header was thrashed */ if (ret < 0){ av_log(s->avctx, AV_LOG_ERROR, "header damaged\n"); return ret; } avctx->has_b_frames= !s->low_delay; if(s->xvid_build==-1 && s->divx_version==-1 && s->lavc_build==-1){ if(s->stream_codec_tag == AV_RL32("XVID") || s->codec_tag == AV_RL32("XVID") || s->codec_tag == AV_RL32("XVIX") || s->codec_tag == AV_RL32("RMP4") || s->codec_tag == AV_RL32("ZMP4") || s->codec_tag == AV_RL32("SIPP") ) s->xvid_build= 0; #if 0 if(s->codec_tag == AV_RL32("DIVX") && s->vo_type==0 && s->vol_control_parameters==1 && s->padding_bug_score > 0 && s->low_delay) // XVID with modified fourcc s->xvid_build= 0; #endif } if(s->xvid_build==-1 && s->divx_version==-1 && s->lavc_build==-1){ if(s->codec_tag == AV_RL32("DIVX") && s->vo_type==0 && s->vol_control_parameters==0) s->divx_version= 400; //divx 4 } if(s->xvid_build>=0 && s->divx_version>=0){ s->divx_version= s->divx_build= -1; } if(s->workaround_bugs&FF_BUG_AUTODETECT){ if(s->codec_tag == AV_RL32("XVIX")) s->workaround_bugs|= FF_BUG_XVID_ILACE; if(s->codec_tag == AV_RL32("UMP4")){ s->workaround_bugs|= FF_BUG_UMP4; } if(s->divx_version>=500 && s->divx_build<1814){ s->workaround_bugs|= FF_BUG_QPEL_CHROMA; } if(s->divx_version>502 && s->divx_build<1814){ s->workaround_bugs|= FF_BUG_QPEL_CHROMA2; } if(s->xvid_build<=3U) s->padding_bug_score= 256*256*256*64; if(s->xvid_build<=1U) s->workaround_bugs|= FF_BUG_QPEL_CHROMA; if(s->xvid_build<=12U) s->workaround_bugs|= FF_BUG_EDGE; if(s->xvid_build<=32U) s->workaround_bugs|= FF_BUG_DC_CLIP; #define SET_QPEL_FUNC(postfix1, postfix2) \ s->dsp.put_ ## postfix1 = ff_put_ ## postfix2;\ s->dsp.put_no_rnd_ ## postfix1 = ff_put_no_rnd_ ## postfix2;\ s->dsp.avg_ ## postfix1 = ff_avg_ ## postfix2; if(s->lavc_build<4653U) s->workaround_bugs|= FF_BUG_STD_QPEL; if(s->lavc_build<4655U) s->workaround_bugs|= FF_BUG_DIRECT_BLOCKSIZE; if(s->lavc_build<4670U){ s->workaround_bugs|= FF_BUG_EDGE; } if(s->lavc_build<=4712U) s->workaround_bugs|= FF_BUG_DC_CLIP; if(s->divx_version>=0) s->workaround_bugs|= FF_BUG_DIRECT_BLOCKSIZE; if(s->divx_version==501 && s->divx_build==20020416) s->padding_bug_score= 256*256*256*64; if(s->divx_version<500U){ s->workaround_bugs|= FF_BUG_EDGE; } if(s->divx_version>=0) s->workaround_bugs|= FF_BUG_HPEL_CHROMA; #if 0 if(s->divx_version==500) s->padding_bug_score= 256*256*256*64; /* very ugly XVID padding bug detection FIXME/XXX solve this differently * Let us hope this at least works. */ if( s->resync_marker==0 && s->data_partitioning==0 && s->divx_version==-1 && s->codec_id==AV_CODEC_ID_MPEG4 && s->vo_type==0) s->workaround_bugs|= FF_BUG_NO_PADDING; if(s->lavc_build<4609U) //FIXME not sure about the version num but a 4609 file seems ok s->workaround_bugs|= FF_BUG_NO_PADDING; #endif } if(s->workaround_bugs& FF_BUG_STD_QPEL){ SET_QPEL_FUNC(qpel_pixels_tab[0][ 5], qpel16_mc11_old_c) SET_QPEL_FUNC(qpel_pixels_tab[0][ 7], qpel16_mc31_old_c) SET_QPEL_FUNC(qpel_pixels_tab[0][ 9], qpel16_mc12_old_c) SET_QPEL_FUNC(qpel_pixels_tab[0][11], qpel16_mc32_old_c) SET_QPEL_FUNC(qpel_pixels_tab[0][13], qpel16_mc13_old_c) SET_QPEL_FUNC(qpel_pixels_tab[0][15], qpel16_mc33_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][ 5], qpel8_mc11_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][ 7], qpel8_mc31_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][ 9], qpel8_mc12_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][11], qpel8_mc32_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][13], qpel8_mc13_old_c) SET_QPEL_FUNC(qpel_pixels_tab[1][15], qpel8_mc33_old_c) } if(avctx->debug & FF_DEBUG_BUGS) av_log(s->avctx, AV_LOG_DEBUG, "bugs: %X lavc_build:%d xvid_build:%d divx_version:%d divx_build:%d %s\n", s->workaround_bugs, s->lavc_build, s->xvid_build, s->divx_version, s->divx_build, s->divx_packed ? "p" : ""); #if HAVE_MMX if (s->codec_id == AV_CODEC_ID_MPEG4 && s->xvid_build>=0 && avctx->idct_algo == FF_IDCT_AUTO && (av_get_cpu_flags() & AV_CPU_FLAG_MMX)) { avctx->idct_algo= FF_IDCT_XVIDMMX; ff_dct_common_init(s); goto retry; } #endif /* After H263 & mpeg4 header decode we have the height, width,*/ /* and other parameters. So then we could init the picture */ /* FIXME: By the way H263 decoder is evolving it should have */ /* an H263EncContext */ if (s->width != avctx->coded_width || s->height != avctx->coded_height || s->context_reinit) { /* H.263 could change picture size any time */ s->context_reinit = 0; avcodec_set_dimensions(avctx, s->width, s->height); if ((ret = ff_MPV_common_frame_size_change(s))) return ret; } if((s->codec_id==AV_CODEC_ID_H263 || s->codec_id==AV_CODEC_ID_H263P || s->codec_id == AV_CODEC_ID_H263I)) s->gob_index = ff_h263_get_gob_height(s); // for skipping the frame s->current_picture.f.pict_type = s->pict_type; s->current_picture.f.key_frame = s->pict_type == AV_PICTURE_TYPE_I; /* skip B-frames if we don't have reference frames */ if (s->last_picture_ptr == NULL && (s->pict_type == AV_PICTURE_TYPE_B || s->droppable)) return get_consumed_bytes(s, buf_size); if( (avctx->skip_frame >= AVDISCARD_NONREF && s->pict_type==AV_PICTURE_TYPE_B) || (avctx->skip_frame >= AVDISCARD_NONKEY && s->pict_type!=AV_PICTURE_TYPE_I) || avctx->skip_frame >= AVDISCARD_ALL) return get_consumed_bytes(s, buf_size); if(s->next_p_frame_damaged){ if(s->pict_type==AV_PICTURE_TYPE_B) return get_consumed_bytes(s, buf_size); else s->next_p_frame_damaged=0; } if((!s->no_rounding) || s->pict_type==AV_PICTURE_TYPE_B){ s->me.qpel_put= s->dsp.put_qpel_pixels_tab; s->me.qpel_avg= s->dsp.avg_qpel_pixels_tab; }else{ s->me.qpel_put= s->dsp.put_no_rnd_qpel_pixels_tab; s->me.qpel_avg= s->dsp.avg_qpel_pixels_tab; } if ((ret = ff_MPV_frame_start(s, avctx)) < 0) return ret; if (!s->divx_packed && !avctx->hwaccel) ff_thread_finish_setup(avctx); if (CONFIG_MPEG4_VDPAU_DECODER && (s->avctx->codec->capabilities & CODEC_CAP_HWACCEL_VDPAU)) { ff_vdpau_mpeg4_decode_picture(s, s->gb.buffer, s->gb.buffer_end - s->gb.buffer); goto frame_end; } if (avctx->hwaccel) { if ((ret = avctx->hwaccel->start_frame(avctx, s->gb.buffer, s->gb.buffer_end - s->gb.buffer)) < 0) return ret; } ff_mpeg_er_frame_start(s); //the second part of the wmv2 header contains the MB skip bits which are stored in current_picture->mb_type //which is not available before ff_MPV_frame_start() if (CONFIG_WMV2_DECODER && s->msmpeg4_version==5){ ret = ff_wmv2_decode_secondary_picture_header(s); if(ret<0) return ret; if(ret==1) goto frame_end; } /* decode each macroblock */ s->mb_x=0; s->mb_y=0; ret = decode_slice(s); while(s->mb_y<s->mb_height){ if(s->msmpeg4_version){ if(s->slice_height==0 || s->mb_x!=0 || (s->mb_y%s->slice_height)!=0 || get_bits_left(&s->gb)<0) break; }else{ int prev_x=s->mb_x, prev_y=s->mb_y; if(ff_h263_resync(s)<0) break; if (prev_y * s->mb_width + prev_x < s->mb_y * s->mb_width + s->mb_x) s->er.error_occurred = 1; } if(s->msmpeg4_version<4 && s->h263_pred) ff_mpeg4_clean_buffers(s); if (decode_slice(s) < 0) ret = AVERROR_INVALIDDATA; } if (s->msmpeg4_version && s->msmpeg4_version<4 && s->pict_type==AV_PICTURE_TYPE_I) if(!CONFIG_MSMPEG4_DECODER || ff_msmpeg4_decode_ext_header(s, buf_size) < 0){ s->er.error_status_table[s->mb_num - 1] = ER_MB_ERROR; } av_assert1(s->bitstream_buffer_size==0); frame_end: ff_er_frame_end(&s->er); if (avctx->hwaccel) { if ((ret = avctx->hwaccel->end_frame(avctx)) < 0) return ret; } ff_MPV_frame_end(s); /* divx 5.01+ bitstream reorder stuff */ /* Since this clobbers the input buffer and hwaccel codecs still need the * data during hwaccel->end_frame we should not do this any earlier */ if(s->codec_id==AV_CODEC_ID_MPEG4 && s->divx_packed){ int current_pos= s->gb.buffer == s->bitstream_buffer ? 0 : (get_bits_count(&s->gb)>>3); int startcode_found=0; if(buf_size - current_pos > 7){ int i; for(i=current_pos; i<buf_size-4; i++){ if(buf[i]==0 && buf[i+1]==0 && buf[i+2]==1 && buf[i+3]==0xB6){ startcode_found=!(buf[i+4]&0x40); break; } } } if(startcode_found){ av_fast_malloc( &s->bitstream_buffer, &s->allocated_bitstream_buffer_size, buf_size - current_pos + FF_INPUT_BUFFER_PADDING_SIZE); if (!s->bitstream_buffer) return AVERROR(ENOMEM); memcpy(s->bitstream_buffer, buf + current_pos, buf_size - current_pos); s->bitstream_buffer_size= buf_size - current_pos; } } if (!s->divx_packed && avctx->hwaccel) ff_thread_finish_setup(avctx); av_assert1(s->current_picture.f.pict_type == s->current_picture_ptr->f.pict_type); av_assert1(s->current_picture.f.pict_type == s->pict_type); if (s->pict_type == AV_PICTURE_TYPE_B || s->low_delay) { if ((ret = av_frame_ref(pict, &s->current_picture_ptr->f)) < 0) return ret; ff_print_debug_info(s, s->current_picture_ptr, pict); ff_mpv_export_qp_table(s, pict, s->current_picture_ptr, FF_QSCALE_TYPE_MPEG1); } else if (s->last_picture_ptr != NULL) { if ((ret = av_frame_ref(pict, &s->last_picture_ptr->f)) < 0) return ret; ff_print_debug_info(s, s->last_picture_ptr, pict); ff_mpv_export_qp_table(s, pict, s->last_picture_ptr, FF_QSCALE_TYPE_MPEG1); } if(s->last_picture_ptr || s->low_delay){ if ( pict->format == AV_PIX_FMT_YUV420P && (s->codec_tag == AV_RL32("GEOV") || s->codec_tag == AV_RL32("GEOX"))) { int x, y, p; av_frame_make_writable(pict); for (p=0; p<3; p++) { int w = FF_CEIL_RSHIFT(pict-> width, !!p); int h = FF_CEIL_RSHIFT(pict->height, !!p); int linesize = pict->linesize[p]; for (y=0; y<(h>>1); y++) for (x=0; x<w; x++) FFSWAP(int, pict->data[p][x + y*linesize], pict->data[p][x + (h-1-y)*linesize]); } } *got_frame = 1; } return (ret && (avctx->err_recognition & AV_EF_EXPLODE))?ret:get_consumed_bytes(s, buf_size); }


void avcodec_free_context(AVCodecContext **pavctx) { AVCodecContext *avctx = *pavctx; if (!avctx) return; avcodec_close(avctx); av_freep(&avctx->extradata); av_freep(&avctx->subtitle_header); av_freep(pavctx); }


void ff_mpeg_flush(AVCodecContext *avctx){ int i; MpegEncContext *s = avctx->priv_data; if(s==NULL || s->picture==NULL) return; for(i=0; i<MAX_PICTURE_COUNT; i++){ if(s->picture[i].data[0] && ( s->picture[i].type == FF_BUFFER_TYPE_INTERNAL || s->picture[i].type == FF_BUFFER_TYPE_USER)) avctx->release_buffer(avctx, (AVFrame*)&s->picture[i]); } s->current_picture_ptr = s->last_picture_ptr = s->next_picture_ptr = NULL; s->mb_x= s->mb_y= 0; s->parse_context.state= -1; s->parse_context.frame_start_found= 0; s->parse_context.overread= 0; s->parse_context.overread_index= 0; s->parse_context.index= 0; s->parse_context.last_index= 0; s->bitstream_buffer_size=0; }


void *kvmppc_create_spapr_tce(uint32_t liobn, uint32_t window_size, int *pfd) { struct kvm_create_spapr_tce args = { .liobn = liobn, .window_size = window_size, }; long len; int fd; void *table; /* Must set fd to -1 so we don't try to munmap when called for * destroying the table, which the upper layers -will- do */ *pfd = -1; if (!cap_spapr_tce) { return NULL; } fd = kvm_vm_ioctl(kvm_state, KVM_CREATE_SPAPR_TCE, &args); if (fd < 0) { fprintf(stderr, "KVM: Failed to create TCE table for liobn 0x%x\n", liobn); return NULL; } len = (window_size / SPAPR_VIO_TCE_PAGE_SIZE) * sizeof(VIOsPAPR_RTCE); /* FIXME: round this up to page size */ table = mmap(NULL, len, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0); if (table == MAP_FAILED) { fprintf(stderr, "KVM: Failed to map TCE table for liobn 0x%x\n", liobn); close(fd); return NULL; } *pfd = fd; return table; }


long do_rt_sigreturn(CPUM68KState *env) { struct target_rt_sigframe *frame; abi_ulong frame_addr = env->aregs[7] - 4; target_sigset_t target_set; sigset_t set; trace_user_do_rt_sigreturn(env, frame_addr); if (!lock_user_struct(VERIFY_READ, frame, frame_addr, 1)) goto badframe; target_to_host_sigset_internal(&set, &target_set); set_sigmask(&set); /* restore registers */ if (target_rt_restore_ucontext(env, &frame->uc)) goto badframe; if (do_sigaltstack(frame_addr + offsetof(struct target_rt_sigframe, uc.tuc_stack), 0, get_sp_from_cpustate(env)) == -EFAULT) goto badframe; unlock_user_struct(frame, frame_addr, 0); return -TARGET_QEMU_ESIGRETURN; badframe: unlock_user_struct(frame, frame_addr, 0); force_sig(TARGET_SIGSEGV); return 0; }


static BlockAIOCB *bdrv_co_aio_prw_vector(BdrvChild *child, int64_t offset, QEMUIOVector *qiov, BdrvRequestFlags flags, BlockCompletionFunc *cb, void *opaque, bool is_write) { Coroutine *co; BlockAIOCBCoroutine *acb; /* Matched by bdrv_co_complete's bdrv_dec_in_flight. */ bdrv_inc_in_flight(child->bs); acb = qemu_aio_get(&bdrv_em_co_aiocb_info, child->bs, cb, opaque); acb->child = child; acb->need_bh = true; acb->req.error = -EINPROGRESS; acb->req.offset = offset; acb->req.qiov = qiov; acb->req.flags = flags; acb->is_write = is_write; co = qemu_coroutine_create(bdrv_co_do_rw, acb); qemu_coroutine_enter(co); bdrv_co_maybe_schedule_bh(acb); return &acb->common; }


static void ahci_port_write(AHCIState *s, int port, int offset, uint32_t val) { AHCIPortRegs *pr = &s->dev[port].port_regs; DPRINTF(port, "offset: 0x%x val: 0x%x\n", offset, val); switch (offset) { case PORT_LST_ADDR: pr->lst_addr = val; map_page(s->as, &s->dev[port].lst, ((uint64_t)pr->lst_addr_hi << 32) | pr->lst_addr, 1024); s->dev[port].cur_cmd = NULL; break; case PORT_LST_ADDR_HI: pr->lst_addr_hi = val; map_page(s->as, &s->dev[port].lst, ((uint64_t)pr->lst_addr_hi << 32) | pr->lst_addr, 1024); s->dev[port].cur_cmd = NULL; break; case PORT_FIS_ADDR: pr->fis_addr = val; map_page(s->as, &s->dev[port].res_fis, ((uint64_t)pr->fis_addr_hi << 32) | pr->fis_addr, 256); break; case PORT_FIS_ADDR_HI: pr->fis_addr_hi = val; map_page(s->as, &s->dev[port].res_fis, ((uint64_t)pr->fis_addr_hi << 32) | pr->fis_addr, 256); break; case PORT_IRQ_STAT: pr->irq_stat &= ~val; ahci_check_irq(s); break; case PORT_IRQ_MASK: pr->irq_mask = val & 0xfdc000ff; ahci_check_irq(s); break; case PORT_CMD: pr->cmd = val & ~(PORT_CMD_LIST_ON | PORT_CMD_FIS_ON); if (pr->cmd & PORT_CMD_START) { pr->cmd |= PORT_CMD_LIST_ON; } if (pr->cmd & PORT_CMD_FIS_RX) { pr->cmd |= PORT_CMD_FIS_ON; } /* XXX usually the FIS would be pending on the bus here and issuing deferred until the OS enables FIS receival. Instead, we only submit it once - which works in most cases, but is a hack. */ if ((pr->cmd & PORT_CMD_FIS_ON) && !s->dev[port].init_d2h_sent) { ahci_init_d2h(&s->dev[port]); s->dev[port].init_d2h_sent = true; } check_cmd(s, port); break; case PORT_TFDATA: s->dev[port].port.ifs[0].error = (val >> 8) & 0xff; s->dev[port].port.ifs[0].status = val & 0xff; break; case PORT_SIG: pr->sig = val; break; case PORT_SCR_STAT: pr->scr_stat = val; break; case PORT_SCR_CTL: if (((pr->scr_ctl & AHCI_SCR_SCTL_DET) == 1) && ((val & AHCI_SCR_SCTL_DET) == 0)) { ahci_reset_port(s, port); } pr->scr_ctl = val; break; case PORT_SCR_ERR: pr->scr_err &= ~val; break; case PORT_SCR_ACT: /* RW1 */ pr->scr_act |= val; break; case PORT_CMD_ISSUE: pr->cmd_issue |= val; check_cmd(s, port); break; default: break; } }


static int jacosub_read_header(AVFormatContext *s) { AVBPrint header; AVIOContext *pb = s->pb; char line[JSS_MAX_LINESIZE]; JACOsubContext *jacosub = s->priv_data; int shift_set = 0; // only the first shift matters int merge_line = 0; int i, ret; AVStream *st = avformat_new_stream(s, NULL); if (!st) return AVERROR(ENOMEM); avpriv_set_pts_info(st, 64, 1, 100); st->codec->codec_type = AVMEDIA_TYPE_SUBTITLE; st->codec->codec_id = AV_CODEC_ID_JACOSUB; jacosub->timeres = 30; av_bprint_init(&header, 1024+FF_INPUT_BUFFER_PADDING_SIZE, 4096); while (!avio_feof(pb)) { int cmd_len; const char *p = line; int64_t pos = avio_tell(pb); int len = ff_get_line(pb, line, sizeof(line)); p = jss_skip_whitespace(p); /* queue timed line */ if (merge_line || timed_line(p)) { AVPacket *sub; sub = ff_subtitles_queue_insert(&jacosub->q, line, len, merge_line); if (!sub) return AVERROR(ENOMEM); sub->pos = pos; merge_line = len > 1 && !strcmp(&line[len - 2], "\\\n"); continue; } /* skip all non-compiler commands and focus on the command */ if (*p != '#') continue; p++; i = get_jss_cmd(p[0]); if (i == -1) continue; /* trim command + spaces */ cmd_len = strlen(cmds[i]); if (av_strncasecmp(p, cmds[i], cmd_len) == 0) p += cmd_len; else p++; p = jss_skip_whitespace(p); /* handle commands which affect the whole script */ switch (cmds[i][0]) { case 'S': // SHIFT command affect the whole script... if (!shift_set) { jacosub->shift = get_shift(jacosub->timeres, p); shift_set = 1; } av_bprintf(&header, "#S %s", p); break; case 'T': // ...but must be placed after TIMERES jacosub->timeres = strtol(p, NULL, 10); if (!jacosub->timeres) jacosub->timeres = 30; else av_bprintf(&header, "#T %s", p); break; } } /* general/essential directives in the extradata */ ret = avpriv_bprint_to_extradata(st->codec, &header); if (ret < 0) return ret; /* SHIFT and TIMERES affect the whole script so packet timing can only be * done in a second pass */ for (i = 0; i < jacosub->q.nb_subs; i++) { AVPacket *sub = &jacosub->q.subs[i]; read_ts(jacosub, sub->data, &sub->pts, &sub->duration); } ff_subtitles_queue_finalize(&jacosub->q); return 0; }


static int get_packet_payload_size(AVFormatContext *ctx, int stream_index, int64_t pts, int64_t dts) { MpegMuxContext *s = ctx->priv_data; int buf_index; StreamInfo *stream; stream = ctx->streams[stream_index]->priv_data; buf_index = 0; if (((s->packet_number % s->pack_header_freq) == 0)) { /* pack header size */ if (s->is_mpeg2) buf_index += 14; else buf_index += 12; if (s->is_vcd) { /* there is exactly one system header for each stream in a VCD MPEG, One in the very first video packet and one in the very first audio packet (see VCD standard p. IV-7 and IV-8).*/ if (stream->packet_number==0) /* The system headers refer only to the stream they occur in, so they have a constant size.*/ buf_index += 15; } else { if ((s->packet_number % s->system_header_freq) == 0) buf_index += s->system_header_size; } } if (s->is_vcd && stream->packet_number==0) /* the first pack of each stream contains only the pack header, the system header and some padding (see VCD standard p. IV-6) Add the padding size, so that the actual payload becomes 0.*/ buf_index += s->packet_size - buf_index; else { /* packet header size */ buf_index += 6; if (s->is_mpeg2) buf_index += 3; if (pts != AV_NOPTS_VALUE) { if (dts != pts) buf_index += 5 + 5; else buf_index += 5; } else { if (!s->is_mpeg2) buf_index++; } if (stream->id < 0xc0) { /* AC3/LPCM private data header */ buf_index += 4; if (stream->id >= 0xa0) { int n; buf_index += 3; /* NOTE: we round the payload size to an integer number of LPCM samples */ n = (s->packet_size - buf_index) % stream->lpcm_align; if (n) buf_index += (stream->lpcm_align - n); } } if (s->is_vcd && stream->id == AUDIO_ID) /* The VCD standard demands that 20 zero bytes follow each audio packet (see standard p. IV-8).*/ buf_index+=20; } return s->packet_size - buf_index; }


ogm_header(AVFormatContext *s, int idx) { struct ogg *ogg = s->priv_data; struct ogg_stream *os = ogg->streams + idx; AVStream *st = s->streams[idx]; const uint8_t *p = os->buf + os->pstart; uint64_t time_unit; uint64_t spu; uint32_t size; if(!(*p & 1)) return 0; if(*p == 1) { p++; if(*p == 'v'){ int tag; st->codec->codec_type = AVMEDIA_TYPE_VIDEO; p += 8; tag = bytestream_get_le32(&p); st->codec->codec_id = ff_codec_get_id(ff_codec_bmp_tags, tag); st->codec->codec_tag = tag; } else if (*p == 't') { st->codec->codec_type = AVMEDIA_TYPE_SUBTITLE; st->codec->codec_id = CODEC_ID_TEXT; p += 12; } else { uint8_t acid[5]; int cid; st->codec->codec_type = AVMEDIA_TYPE_AUDIO; p += 8; bytestream_get_buffer(&p, acid, 4); acid[4] = 0; cid = strtol(acid, NULL, 16); st->codec->codec_id = ff_codec_get_id(ff_codec_wav_tags, cid); // our parser completely breaks AAC in Ogg if (st->codec->codec_id != CODEC_ID_AAC) st->need_parsing = AVSTREAM_PARSE_FULL; } size = bytestream_get_le32(&p); size = FFMIN(size, os->psize); time_unit = bytestream_get_le64(&p); spu = bytestream_get_le64(&p); p += 4; /* default_len */ p += 8; /* buffersize + bits_per_sample */ if(st->codec->codec_type == AVMEDIA_TYPE_VIDEO){ st->codec->width = bytestream_get_le32(&p); st->codec->height = bytestream_get_le32(&p); avpriv_set_pts_info(st, 64, time_unit, spu * 10000000); } else { st->codec->channels = bytestream_get_le16(&p); p += 2; /* block_align */ st->codec->bit_rate = bytestream_get_le32(&p) * 8; st->codec->sample_rate = spu * 10000000 / time_unit; avpriv_set_pts_info(st, 64, 1, st->codec->sample_rate); if (size >= 56 && st->codec->codec_id == CODEC_ID_AAC) { p += 4; size -= 4; } if (size > 52) { av_assert0(FF_INPUT_BUFFER_PADDING_SIZE <= 52); size -= 52; st->codec->extradata_size = size; st->codec->extradata = av_malloc(size + FF_INPUT_BUFFER_PADDING_SIZE); bytestream_get_buffer(&p, st->codec->extradata, size); } } } else if (*p == 3) { if (os->psize > 8) ff_vorbis_comment(s, &st->metadata, p+7, os->psize-8); } return 1; }


static int ape_decode_frame(AVCodecContext *avctx, void *data, int *got_frame_ptr, AVPacket *avpkt) { AVFrame *frame = data; const uint8_t *buf = avpkt->data; APEContext *s = avctx->priv_data; uint8_t *sample8; int16_t *sample16; int32_t *sample24; int i, ch, ret; int blockstodecode; /* this should never be negative, but bad things will happen if it is, so check it just to make sure. */ av_assert0(s->samples >= 0); if(!s->samples){ uint32_t nblocks, offset; int buf_size; if (!avpkt->size) { *got_frame_ptr = 0; return 0; } if (avpkt->size < 8) { av_log(avctx, AV_LOG_ERROR, "Packet is too small\n"); return AVERROR_INVALIDDATA; } buf_size = avpkt->size & ~3; if (buf_size != avpkt->size) { av_log(avctx, AV_LOG_WARNING, "packet size is not a multiple of 4. " "extra bytes at the end will be skipped.\n"); } if (s->fileversion < 3950) // previous versions overread two bytes buf_size += 2; av_fast_malloc(&s->data, &s->data_size, buf_size); if (!s->data) return AVERROR(ENOMEM); s->dsp.bswap_buf((uint32_t*)s->data, (const uint32_t*)buf, buf_size >> 2); memset(s->data + (buf_size & ~3), 0, buf_size & 3); s->ptr = s->data; s->data_end = s->data + buf_size; nblocks = bytestream_get_be32(&s->ptr); offset = bytestream_get_be32(&s->ptr); if (s->fileversion >= 3900) { if (offset > 3) { av_log(avctx, AV_LOG_ERROR, "Incorrect offset passed\n"); s->data = NULL; return AVERROR_INVALIDDATA; } if (s->data_end - s->ptr < offset) { av_log(avctx, AV_LOG_ERROR, "Packet is too small\n"); return AVERROR_INVALIDDATA; } s->ptr += offset; } else { if ((ret = init_get_bits8(&s->gb, s->ptr, s->data_end - s->ptr)) < 0) return ret; if (s->fileversion > 3800) skip_bits_long(&s->gb, offset * 8); else skip_bits_long(&s->gb, offset); } if (!nblocks || nblocks > INT_MAX) { av_log(avctx, AV_LOG_ERROR, "Invalid sample count: %u.\n", nblocks); return AVERROR_INVALIDDATA; } s->samples = nblocks; /* Initialize the frame decoder */ if (init_frame_decoder(s) < 0) { av_log(avctx, AV_LOG_ERROR, "Error reading frame header\n"); return AVERROR_INVALIDDATA; } } if (!s->data) { *got_frame_ptr = 0; return avpkt->size; } blockstodecode = FFMIN(s->blocks_per_loop, s->samples); // for old files coefficients were not interleaved, // so we need to decode all of them at once if (s->fileversion < 3930) blockstodecode = s->samples; /* reallocate decoded sample buffer if needed */ av_fast_malloc(&s->decoded_buffer, &s->decoded_size, 2 * FFALIGN(blockstodecode, 8) * sizeof(*s->decoded_buffer)); if (!s->decoded_buffer) return AVERROR(ENOMEM); memset(s->decoded_buffer, 0, s->decoded_size); s->decoded[0] = s->decoded_buffer; s->decoded[1] = s->decoded_buffer + FFALIGN(blockstodecode, 8); /* get output buffer */ frame->nb_samples = blockstodecode; if ((ret = ff_get_buffer(avctx, frame, 0)) < 0) return ret; s->error=0; if ((s->channels == 1) || (s->frameflags & APE_FRAMECODE_PSEUDO_STEREO)) ape_unpack_mono(s, blockstodecode); else ape_unpack_stereo(s, blockstodecode); emms_c(); if (s->error) { s->samples=0; av_log(avctx, AV_LOG_ERROR, "Error decoding frame\n"); return AVERROR_INVALIDDATA; } switch (s->bps) { case 8: for (ch = 0; ch < s->channels; ch++) { sample8 = (uint8_t *)frame->data[ch]; for (i = 0; i < blockstodecode; i++) *sample8++ = (s->decoded[ch][i] + 0x80) & 0xff; } break; case 16: for (ch = 0; ch < s->channels; ch++) { sample16 = (int16_t *)frame->data[ch]; for (i = 0; i < blockstodecode; i++) *sample16++ = s->decoded[ch][i]; } break; case 24: for (ch = 0; ch < s->channels; ch++) { sample24 = (int32_t *)frame->data[ch]; for (i = 0; i < blockstodecode; i++) *sample24++ = s->decoded[ch][i] << 8; } break; } s->samples -= blockstodecode; *got_frame_ptr = 1; return !s->samples ? avpkt->size : 0; }


e1000_receive_iov(NetClientState *nc, const struct iovec *iov, int iovcnt) { E1000State *s = qemu_get_nic_opaque(nc); PCIDevice *d = PCI_DEVICE(s); struct e1000_rx_desc desc; dma_addr_t base; unsigned int n, rdt; uint32_t rdh_start; uint16_t vlan_special = 0; uint8_t vlan_status = 0; uint8_t min_buf[MIN_BUF_SIZE]; struct iovec min_iov; uint8_t *filter_buf = iov->iov_base; size_t size = iov_size(iov, iovcnt); size_t iov_ofs = 0; size_t desc_offset; size_t desc_size; size_t total_size; static const int PRCregs[6] = { PRC64, PRC127, PRC255, PRC511, PRC1023, PRC1522 }; if (!(s->mac_reg[STATUS] & E1000_STATUS_LU)) { return -1; } if (!(s->mac_reg[RCTL] & E1000_RCTL_EN)) { return -1; } /* Pad to minimum Ethernet frame length */ if (size < sizeof(min_buf)) { iov_to_buf(iov, iovcnt, 0, min_buf, size); memset(&min_buf[size], 0, sizeof(min_buf) - size); inc_reg_if_not_full(s, RUC); min_iov.iov_base = filter_buf = min_buf; min_iov.iov_len = size = sizeof(min_buf); iovcnt = 1; iov = &min_iov; } else if (iov->iov_len < MAXIMUM_ETHERNET_HDR_LEN) { /* This is very unlikely, but may happen. */ iov_to_buf(iov, iovcnt, 0, min_buf, MAXIMUM_ETHERNET_HDR_LEN); filter_buf = min_buf; } /* Discard oversized packets if !LPE and !SBP. */ if ((size > MAXIMUM_ETHERNET_LPE_SIZE || (size > MAXIMUM_ETHERNET_VLAN_SIZE && !(s->mac_reg[RCTL] & E1000_RCTL_LPE))) && !(s->mac_reg[RCTL] & E1000_RCTL_SBP)) { inc_reg_if_not_full(s, ROC); return size; } if (!receive_filter(s, filter_buf, size)) { return size; } if (vlan_enabled(s) && is_vlan_packet(s, filter_buf)) { vlan_special = cpu_to_le16(be16_to_cpup((uint16_t *)(filter_buf + 14))); iov_ofs = 4; if (filter_buf == iov->iov_base) { memmove(filter_buf + 4, filter_buf, 12); } else { iov_from_buf(iov, iovcnt, 4, filter_buf, 12); while (iov->iov_len <= iov_ofs) { iov_ofs -= iov->iov_len; iov++; } } vlan_status = E1000_RXD_STAT_VP; size -= 4; } rdh_start = s->mac_reg[RDH]; desc_offset = 0; total_size = size + fcs_len(s); if (!e1000_has_rxbufs(s, total_size)) { set_ics(s, 0, E1000_ICS_RXO); return -1; } do { desc_size = total_size - desc_offset; if (desc_size > s->rxbuf_size) { desc_size = s->rxbuf_size; } base = rx_desc_base(s) + sizeof(desc) * s->mac_reg[RDH]; pci_dma_read(d, base, &desc, sizeof(desc)); desc.special = vlan_special; desc.status |= (vlan_status | E1000_RXD_STAT_DD); if (desc.buffer_addr) { if (desc_offset < size) { size_t iov_copy; hwaddr ba = le64_to_cpu(desc.buffer_addr); size_t copy_size = size - desc_offset; if (copy_size > s->rxbuf_size) { copy_size = s->rxbuf_size; } do { iov_copy = MIN(copy_size, iov->iov_len - iov_ofs); pci_dma_write(d, ba, iov->iov_base + iov_ofs, iov_copy); copy_size -= iov_copy; ba += iov_copy; iov_ofs += iov_copy; if (iov_ofs == iov->iov_len) { iov++; iov_ofs = 0; } } while (copy_size); } desc_offset += desc_size; desc.length = cpu_to_le16(desc_size); if (desc_offset >= total_size) { desc.status |= E1000_RXD_STAT_EOP | E1000_RXD_STAT_IXSM; } else { /* Guest zeroing out status is not a hardware requirement. Clear EOP in case guest didn't do it. */ desc.status &= ~E1000_RXD_STAT_EOP; } } else { // as per intel docs; skip descriptors with null buf addr DBGOUT(RX, "Null RX descriptor!!\n"); } pci_dma_write(d, base, &desc, sizeof(desc)); if (++s->mac_reg[RDH] * sizeof(desc) >= s->mac_reg[RDLEN]) s->mac_reg[RDH] = 0; /* see comment in start_xmit; same here */ if (s->mac_reg[RDH] == rdh_start) { DBGOUT(RXERR, "RDH wraparound @%x, RDT %x, RDLEN %x\n", rdh_start, s->mac_reg[RDT], s->mac_reg[RDLEN]); set_ics(s, 0, E1000_ICS_RXO); return -1; } } while (desc_offset < total_size); increase_size_stats(s, PRCregs, total_size); inc_reg_if_not_full(s, TPR); s->mac_reg[GPRC] = s->mac_reg[TPR]; /* TOR - Total Octets Received: * This register includes bytes received in a packet from the <Destination * Address> field through the <CRC> field, inclusively. * Always include FCS length (4) in size. */ grow_8reg_if_not_full(s, TORL, size+4); s->mac_reg[GORCL] = s->mac_reg[TORL]; s->mac_reg[GORCH] = s->mac_reg[TORH]; n = E1000_ICS_RXT0; if ((rdt = s->mac_reg[RDT]) < s->mac_reg[RDH]) rdt += s->mac_reg[RDLEN] / sizeof(desc); if (((rdt - s->mac_reg[RDH]) * sizeof(desc)) <= s->mac_reg[RDLEN] >> s->rxbuf_min_shift) n |= E1000_ICS_RXDMT0; set_ics(s, 0, n); return size; }


static void close_peer_eventfds(IVShmemState *s, int posn) { int i, n; if (!ivshmem_has_feature(s, IVSHMEM_IOEVENTFD)) { return; } if (posn < 0 || posn >= s->nb_peers) { error_report("invalid peer %d", posn); return; } n = s->peers[posn].nb_eventfds; memory_region_transaction_begin(); for (i = 0; i < n; i++) { ivshmem_del_eventfd(s, posn, i); } memory_region_transaction_commit(); for (i = 0; i < n; i++) { event_notifier_cleanup(&s->peers[posn].eventfds[i]); } g_free(s->peers[posn].eventfds); s->peers[posn].nb_eventfds = 0; }


static void pci_ivshmem_exit(PCIDevice *dev) { IVShmemState *s = IVSHMEM(dev); int i; fifo8_destroy(&s->incoming_fifo); if (s->migration_blocker) { migrate_del_blocker(s->migration_blocker); error_free(s->migration_blocker); } if (s->shm_fd >= 0) { void *addr = memory_region_get_ram_ptr(&s->ivshmem); vmstate_unregister_ram(&s->ivshmem, DEVICE(dev)); memory_region_del_subregion(&s->bar, &s->ivshmem); if (munmap(addr, s->ivshmem_size) == -1) { error_report("Failed to munmap shared memory %s", strerror(errno)); } } if (s->eventfd_chr) { for (i = 0; i < s->vectors; i++) { if (s->eventfd_chr[i]) { qemu_chr_free(s->eventfd_chr[i]); } } g_free(s->eventfd_chr); } if (s->peers) { for (i = 0; i < s->nb_peers; i++) { close_peer_eventfds(s, i); } g_free(s->peers); } if (ivshmem_has_feature(s, IVSHMEM_MSI)) { msix_uninit_exclusive_bar(dev); } g_free(s->eventfd_table); }


static inline void RENAME(rgb32tobgr16)(const uint8_t *src, uint8_t *dst, long src_size) { const uint8_t *s = src; const uint8_t *end; #if COMPILE_TEMPLATE_MMX const uint8_t *mm_end; #endif uint16_t *d = (uint16_t *)dst; end = s + src_size; #if COMPILE_TEMPLATE_MMX __asm__ volatile(PREFETCH" %0"::"m"(*src):"memory"); __asm__ volatile( "movq %0, %%mm7 \n\t" "movq %1, %%mm6 \n\t" ::"m"(red_16mask),"m"(green_16mask)); mm_end = end - 15; while (s < mm_end) { __asm__ volatile( PREFETCH" 32%1 \n\t" "movd %1, %%mm0 \n\t" "movd 4%1, %%mm3 \n\t" "punpckldq 8%1, %%mm0 \n\t" "punpckldq 12%1, %%mm3 \n\t" "movq %%mm0, %%mm1 \n\t" "movq %%mm0, %%mm2 \n\t" "movq %%mm3, %%mm4 \n\t" "movq %%mm3, %%mm5 \n\t" "psllq $8, %%mm0 \n\t" "psllq $8, %%mm3 \n\t" "pand %%mm7, %%mm0 \n\t" "pand %%mm7, %%mm3 \n\t" "psrlq $5, %%mm1 \n\t" "psrlq $5, %%mm4 \n\t" "pand %%mm6, %%mm1 \n\t" "pand %%mm6, %%mm4 \n\t" "psrlq $19, %%mm2 \n\t" "psrlq $19, %%mm5 \n\t" "pand %2, %%mm2 \n\t" "pand %2, %%mm5 \n\t" "por %%mm1, %%mm0 \n\t" "por %%mm4, %%mm3 \n\t" "por %%mm2, %%mm0 \n\t" "por %%mm5, %%mm3 \n\t" "psllq $16, %%mm3 \n\t" "por %%mm3, %%mm0 \n\t" MOVNTQ" %%mm0, %0 \n\t" :"=m"(*d):"m"(*s),"m"(blue_16mask):"memory"); d += 4; s += 16; } __asm__ volatile(SFENCE:::"memory"); __asm__ volatile(EMMS:::"memory"); #endif while (s < end) { register int rgb = *(const uint32_t*)s; s += 4; *d++ = ((rgb&0xF8)<<8) + ((rgb&0xFC00)>>5) + ((rgb&0xF80000)>>19); } }


static int truemotion1_decode_header(TrueMotion1Context *s) { int i; int width_shift = 0; int new_pix_fmt; struct frame_header header; uint8_t header_buffer[128]; /* logical maximum size of the header */ const uint8_t *sel_vector_table; header.header_size = ((s->buf[0] >> 5) | (s->buf[0] << 3)) & 0x7f; if (s->buf[0] < 0x10) { av_log(s->avctx, AV_LOG_ERROR, "invalid header size (%d)\n", s->buf[0]); return -1; } /* unscramble the header bytes with a XOR operation */ memset(header_buffer, 0, 128); for (i = 1; i < header.header_size; i++) header_buffer[i - 1] = s->buf[i] ^ s->buf[i + 1]; header.compression = header_buffer[0]; header.deltaset = header_buffer[1]; header.vectable = header_buffer[2]; header.ysize = AV_RL16(&header_buffer[3]); header.xsize = AV_RL16(&header_buffer[5]); header.checksum = AV_RL16(&header_buffer[7]); header.version = header_buffer[9]; header.header_type = header_buffer[10]; header.flags = header_buffer[11]; header.control = header_buffer[12]; /* Version 2 */ if (header.version >= 2) { if (header.header_type > 3) { av_log(s->avctx, AV_LOG_ERROR, "invalid header type (%d)\n", header.header_type); return -1; } else if ((header.header_type == 2) || (header.header_type == 3)) { s->flags = header.flags; if (!(s->flags & FLAG_INTERFRAME)) s->flags |= FLAG_KEYFRAME; } else s->flags = FLAG_KEYFRAME; } else /* Version 1 */ s->flags = FLAG_KEYFRAME; if (s->flags & FLAG_SPRITE) { av_log(s->avctx, AV_LOG_INFO, "SPRITE frame found, please report the sample to the developers\n"); /* FIXME header.width, height, xoffset and yoffset aren't initialized */ #if 0 s->w = header.width; s->h = header.height; s->x = header.xoffset; s->y = header.yoffset; #else return -1; #endif } else { s->w = header.xsize; s->h = header.ysize; if (header.header_type < 2) { if ((s->w < 213) && (s->h >= 176)) { s->flags |= FLAG_INTERPOLATED; av_log(s->avctx, AV_LOG_INFO, "INTERPOLATION selected, please report the sample to the developers\n"); } } } if (header.compression >= 17) { av_log(s->avctx, AV_LOG_ERROR, "invalid compression type (%d)\n", header.compression); return -1; } if ((header.deltaset != s->last_deltaset) || (header.vectable != s->last_vectable)) select_delta_tables(s, header.deltaset); if ((header.compression & 1) && header.header_type) sel_vector_table = pc_tbl2; else { if (header.vectable < 4) sel_vector_table = tables[header.vectable - 1]; else { av_log(s->avctx, AV_LOG_ERROR, "invalid vector table id (%d)\n", header.vectable); return -1; } } if (compression_types[header.compression].algorithm == ALGO_RGB24H) { new_pix_fmt = PIX_FMT_RGB32; width_shift = 1; } else new_pix_fmt = PIX_FMT_RGB555; // RGB565 is supported as well s->w >>= width_shift; if (av_image_check_size(s->w, s->h, 0, s->avctx) < 0) return -1; if (s->w != s->avctx->width || s->h != s->avctx->height || new_pix_fmt != s->avctx->pix_fmt) { if (s->frame.data[0]) s->avctx->release_buffer(s->avctx, &s->frame); s->avctx->sample_aspect_ratio = (AVRational){ 1 << width_shift, 1 }; s->avctx->pix_fmt = new_pix_fmt; avcodec_set_dimensions(s->avctx, s->w, s->h); av_fast_malloc(&s->vert_pred, &s->vert_pred_size, s->avctx->width * sizeof(unsigned int)); } /* There is 1 change bit per 4 pixels, so each change byte represents * 32 pixels; divide width by 4 to obtain the number of change bits and * then round up to the nearest byte. */ s->mb_change_bits_row_size = ((s->avctx->width >> (2 - width_shift)) + 7) >> 3; if ((header.deltaset != s->last_deltaset) || (header.vectable != s->last_vectable)) { if (compression_types[header.compression].algorithm == ALGO_RGB24H) gen_vector_table24(s, sel_vector_table); else if (s->avctx->pix_fmt == PIX_FMT_RGB555) gen_vector_table15(s, sel_vector_table); else gen_vector_table16(s, sel_vector_table); } /* set up pointers to the other key data chunks */ s->mb_change_bits = s->buf + header.header_size; if (s->flags & FLAG_KEYFRAME) { /* no change bits specified for a keyframe; only index bytes */ s->index_stream = s->mb_change_bits; } else { /* one change bit per 4x4 block */ s->index_stream = s->mb_change_bits + (s->mb_change_bits_row_size * (s->avctx->height >> 2)); } s->index_stream_size = s->size - (s->index_stream - s->buf); s->last_deltaset = header.deltaset; s->last_vectable = header.vectable; s->compression = header.compression; s->block_width = compression_types[header.compression].block_width; s->block_height = compression_types[header.compression].block_height; s->block_type = compression_types[header.compression].block_type; if (s->avctx->debug & FF_DEBUG_PICT_INFO) av_log(s->avctx, AV_LOG_INFO, "tables: %d / %d c:%d %dx%d t:%d %s%s%s%s\n", s->last_deltaset, s->last_vectable, s->compression, s->block_width, s->block_height, s->block_type, s->flags & FLAG_KEYFRAME ? " KEY" : "", s->flags & FLAG_INTERFRAME ? " INTER" : "", s->flags & FLAG_SPRITE ? " SPRITE" : "", s->flags & FLAG_INTERPOLATED ? " INTERPOL" : ""); return header.header_size; }


static int opt_input_ts_scale(const char *opt, const char *arg) { unsigned int stream; double scale; char *p; stream = strtol(arg, &p, 0); if (*p) p++; scale= strtod(p, &p); if(stream >= MAX_STREAMS) ffmpeg_exit(1); ts_scale = grow_array(ts_scale, sizeof(*ts_scale), &nb_ts_scale, stream + 1); ts_scale[stream] = scale; return 0; }


static av_always_inline int normal_limit(uint8_t *p, int stride, int E, int I) { LOAD_PIXELS return simple_limit(p, stride, 2*E+I) && FFABS(p3-p2) <= I && FFABS(p2-p1) <= I && FFABS(p1-p0) <= I && FFABS(q3-q2) <= I && FFABS(q2-q1) <= I && FFABS(q1-q0) <= I; }


static int mov_open_dref(AVIOContext **pb, const char *src, MOVDref *ref, AVIOInterruptCB *int_cb, int use_absolute_path, AVFormatContext *fc) { /* try relative path, we do not try the absolute because it can leak information about our system to an attacker */ if (ref->nlvl_to > 0 && ref->nlvl_from > 0) { char filename[1024]; const char *src_path; int i, l; /* find a source dir */ src_path = strrchr(src, '/'); if (src_path) src_path++; else src_path = src; /* find a next level down to target */ for (i = 0, l = strlen(ref->path) - 1; l >= 0; l--) if (ref->path[l] == '/') { if (i == ref->nlvl_to - 1) break; else i++; } /* compose filename if next level down to target was found */ if (i == ref->nlvl_to - 1 && src_path - src < sizeof(filename)) { memcpy(filename, src, src_path - src); filename[src_path - src] = 0; for (i = 1; i < ref->nlvl_from; i++) av_strlcat(filename, "../", sizeof(filename)); av_strlcat(filename, ref->path + l + 1, sizeof(filename)); if (!avio_open2(pb, filename, AVIO_FLAG_READ, int_cb, NULL)) return 0; } } else if (use_absolute_path) { av_log(fc, AV_LOG_WARNING, "Using absolute path on user request, " "this is a possible security issue\n"); if (!avio_open2(pb, ref->path, AVIO_FLAG_READ, int_cb, NULL)) return 0; } return AVERROR(ENOENT); }


static int swScale(SwsContext *c, const uint8_t* src[], int srcStride[], int srcSliceY, int srcSliceH, uint8_t* dst[], int dstStride[]) { /* load a few things into local vars to make the code more readable? and faster */ const int srcW= c->srcW; const int dstW= c->dstW; const int dstH= c->dstH; const int chrDstW= c->chrDstW; const int chrSrcW= c->chrSrcW; const int lumXInc= c->lumXInc; const int chrXInc= c->chrXInc; const enum PixelFormat dstFormat= c->dstFormat; const int flags= c->flags; int16_t *vLumFilterPos= c->vLumFilterPos; int16_t *vChrFilterPos= c->vChrFilterPos; int16_t *hLumFilterPos= c->hLumFilterPos; int16_t *hChrFilterPos= c->hChrFilterPos; int16_t *vLumFilter= c->vLumFilter; int16_t *vChrFilter= c->vChrFilter; int16_t *hLumFilter= c->hLumFilter; int16_t *hChrFilter= c->hChrFilter; int32_t *lumMmxFilter= c->lumMmxFilter; int32_t *chrMmxFilter= c->chrMmxFilter; int32_t av_unused *alpMmxFilter= c->alpMmxFilter; const int vLumFilterSize= c->vLumFilterSize; const int vChrFilterSize= c->vChrFilterSize; const int hLumFilterSize= c->hLumFilterSize; const int hChrFilterSize= c->hChrFilterSize; int16_t **lumPixBuf= c->lumPixBuf; int16_t **chrUPixBuf= c->chrUPixBuf; int16_t **chrVPixBuf= c->chrVPixBuf; int16_t **alpPixBuf= c->alpPixBuf; const int vLumBufSize= c->vLumBufSize; const int vChrBufSize= c->vChrBufSize; uint8_t *formatConvBuffer= c->formatConvBuffer; const int chrSrcSliceY= srcSliceY >> c->chrSrcVSubSample; const int chrSrcSliceH= -((-srcSliceH) >> c->chrSrcVSubSample); int lastDstY; uint32_t *pal=c->pal_yuv; yuv2planar1_fn yuv2yuv1 = c->yuv2yuv1; yuv2planarX_fn yuv2yuvX = c->yuv2yuvX; yuv2packed1_fn yuv2packed1 = c->yuv2packed1; yuv2packed2_fn yuv2packed2 = c->yuv2packed2; yuv2packedX_fn yuv2packedX = c->yuv2packedX; /* vars which will change and which we need to store back in the context */ int dstY= c->dstY; int lumBufIndex= c->lumBufIndex; int chrBufIndex= c->chrBufIndex; int lastInLumBuf= c->lastInLumBuf; int lastInChrBuf= c->lastInChrBuf; if (isPacked(c->srcFormat)) { src[0]= src[1]= src[2]= src[3]= src[0]; srcStride[0]= srcStride[1]= srcStride[2]= srcStride[3]= srcStride[0]; } srcStride[1]<<= c->vChrDrop; srcStride[2]<<= c->vChrDrop; DEBUG_BUFFERS("swScale() %p[%d] %p[%d] %p[%d] %p[%d] -> %p[%d] %p[%d] %p[%d] %p[%d]\n", src[0], srcStride[0], src[1], srcStride[1], src[2], srcStride[2], src[3], srcStride[3], dst[0], dstStride[0], dst[1], dstStride[1], dst[2], dstStride[2], dst[3], dstStride[3]); DEBUG_BUFFERS("srcSliceY: %d srcSliceH: %d dstY: %d dstH: %d\n", srcSliceY, srcSliceH, dstY, dstH); DEBUG_BUFFERS("vLumFilterSize: %d vLumBufSize: %d vChrFilterSize: %d vChrBufSize: %d\n", vLumFilterSize, vLumBufSize, vChrFilterSize, vChrBufSize); if (dstStride[0]%8 !=0 || dstStride[1]%8 !=0 || dstStride[2]%8 !=0 || dstStride[3]%8 != 0) { static int warnedAlready=0; //FIXME move this into the context perhaps if (flags & SWS_PRINT_INFO && !warnedAlready) { av_log(c, AV_LOG_WARNING, "Warning: dstStride is not aligned!\n" " ->cannot do aligned memory accesses anymore\n"); warnedAlready=1; } } /* Note the user might start scaling the picture in the middle so this will not get executed. This is not really intended but works currently, so people might do it. */ if (srcSliceY ==0) { lumBufIndex=-1; chrBufIndex=-1; dstY=0; lastInLumBuf= -1; lastInChrBuf= -1; } lastDstY= dstY; for (;dstY < dstH; dstY++) { unsigned char *dest =dst[0]+dstStride[0]*dstY; const int chrDstY= dstY>>c->chrDstVSubSample; unsigned char *uDest=dst[1]+dstStride[1]*chrDstY; unsigned char *vDest=dst[2]+dstStride[2]*chrDstY; unsigned char *aDest=(CONFIG_SWSCALE_ALPHA && alpPixBuf) ? dst[3]+dstStride[3]*dstY : NULL; const int firstLumSrcY= vLumFilterPos[dstY]; //First line needed as input const int firstLumSrcY2= vLumFilterPos[FFMIN(dstY | ((1<<c->chrDstVSubSample) - 1), dstH-1)]; const int firstChrSrcY= vChrFilterPos[chrDstY]; //First line needed as input int lastLumSrcY= firstLumSrcY + vLumFilterSize -1; // Last line needed as input int lastLumSrcY2=firstLumSrcY2+ vLumFilterSize -1; // Last line needed as input int lastChrSrcY= firstChrSrcY + vChrFilterSize -1; // Last line needed as input int enough_lines; //handle holes (FAST_BILINEAR & weird filters) if (firstLumSrcY > lastInLumBuf) lastInLumBuf= firstLumSrcY-1; if (firstChrSrcY > lastInChrBuf) lastInChrBuf= firstChrSrcY-1; assert(firstLumSrcY >= lastInLumBuf - vLumBufSize + 1); assert(firstChrSrcY >= lastInChrBuf - vChrBufSize + 1); DEBUG_BUFFERS("dstY: %d\n", dstY); DEBUG_BUFFERS("\tfirstLumSrcY: %d lastLumSrcY: %d lastInLumBuf: %d\n", firstLumSrcY, lastLumSrcY, lastInLumBuf); DEBUG_BUFFERS("\tfirstChrSrcY: %d lastChrSrcY: %d lastInChrBuf: %d\n", firstChrSrcY, lastChrSrcY, lastInChrBuf); // Do we have enough lines in this slice to output the dstY line enough_lines = lastLumSrcY2 < srcSliceY + srcSliceH && lastChrSrcY < -((-srcSliceY - srcSliceH)>>c->chrSrcVSubSample); if (!enough_lines) { lastLumSrcY = srcSliceY + srcSliceH - 1; lastChrSrcY = chrSrcSliceY + chrSrcSliceH - 1; DEBUG_BUFFERS("buffering slice: lastLumSrcY %d lastChrSrcY %d\n", lastLumSrcY, lastChrSrcY); } //Do horizontal scaling while(lastInLumBuf < lastLumSrcY) { const uint8_t *src1= src[0]+(lastInLumBuf + 1 - srcSliceY)*srcStride[0]; const uint8_t *src2= src[3]+(lastInLumBuf + 1 - srcSliceY)*srcStride[3]; lumBufIndex++; assert(lumBufIndex < 2*vLumBufSize); assert(lastInLumBuf + 1 - srcSliceY < srcSliceH); assert(lastInLumBuf + 1 - srcSliceY >= 0); hyscale(c, lumPixBuf[ lumBufIndex ], dstW, src1, srcW, lumXInc, hLumFilter, hLumFilterPos, hLumFilterSize, formatConvBuffer, pal, 0); if (CONFIG_SWSCALE_ALPHA && alpPixBuf) hyscale(c, alpPixBuf[ lumBufIndex ], dstW, src2, srcW, lumXInc, hLumFilter, hLumFilterPos, hLumFilterSize, formatConvBuffer, pal, 1); lastInLumBuf++; DEBUG_BUFFERS("\t\tlumBufIndex %d: lastInLumBuf: %d\n", lumBufIndex, lastInLumBuf); } while(lastInChrBuf < lastChrSrcY) { const uint8_t *src1= src[1]+(lastInChrBuf + 1 - chrSrcSliceY)*srcStride[1]; const uint8_t *src2= src[2]+(lastInChrBuf + 1 - chrSrcSliceY)*srcStride[2]; chrBufIndex++; assert(chrBufIndex < 2*vChrBufSize); assert(lastInChrBuf + 1 - chrSrcSliceY < (chrSrcSliceH)); assert(lastInChrBuf + 1 - chrSrcSliceY >= 0); //FIXME replace parameters through context struct (some at least) if (c->needs_hcscale) hcscale(c, chrUPixBuf[chrBufIndex], chrVPixBuf[chrBufIndex], chrDstW, src1, src2, chrSrcW, chrXInc, hChrFilter, hChrFilterPos, hChrFilterSize, formatConvBuffer, pal); lastInChrBuf++; DEBUG_BUFFERS("\t\tchrBufIndex %d: lastInChrBuf: %d\n", chrBufIndex, lastInChrBuf); } //wrap buf index around to stay inside the ring buffer if (lumBufIndex >= vLumBufSize) lumBufIndex-= vLumBufSize; if (chrBufIndex >= vChrBufSize) chrBufIndex-= vChrBufSize; if (!enough_lines) break; //we can't output a dstY line so let's try with the next slice #if HAVE_MMX updateMMXDitherTables(c, dstY, lumBufIndex, chrBufIndex, lastInLumBuf, lastInChrBuf); #endif if (dstY >= dstH-2) { // hmm looks like we can't use MMX here without overwriting this array's tail find_c_packed_planar_out_funcs(c, &yuv2yuv1, &yuv2yuvX, &yuv2packed1, &yuv2packed2, &yuv2packedX); } { const int16_t **lumSrcPtr= (const int16_t **) lumPixBuf + lumBufIndex + firstLumSrcY - lastInLumBuf + vLumBufSize; const int16_t **chrUSrcPtr= (const int16_t **) chrUPixBuf + chrBufIndex + firstChrSrcY - lastInChrBuf + vChrBufSize; const int16_t **chrVSrcPtr= (const int16_t **) chrVPixBuf + chrBufIndex + firstChrSrcY - lastInChrBuf + vChrBufSize; const int16_t **alpSrcPtr= (CONFIG_SWSCALE_ALPHA && alpPixBuf) ? (const int16_t **) alpPixBuf + lumBufIndex + firstLumSrcY - lastInLumBuf + vLumBufSize : NULL; if (isPlanarYUV(dstFormat) || dstFormat==PIX_FMT_GRAY8) { //YV12 like const int chrSkipMask= (1<<c->chrDstVSubSample)-1; if ((dstY&chrSkipMask) || isGray(dstFormat)) uDest=vDest= NULL; //FIXME split functions in lumi / chromi if (c->yuv2yuv1 && vLumFilterSize == 1 && vChrFilterSize == 1) { // unscaled YV12 const int16_t *lumBuf = lumSrcPtr[0]; const int16_t *chrUBuf= chrUSrcPtr[0]; const int16_t *chrVBuf= chrVSrcPtr[0]; const int16_t *alpBuf= (CONFIG_SWSCALE_ALPHA && alpPixBuf) ? alpSrcPtr[0] : NULL; yuv2yuv1(c, lumBuf, chrUBuf, chrVBuf, alpBuf, dest, uDest, vDest, aDest, dstW, chrDstW); } else { //General YV12 yuv2yuvX(c, vLumFilter+dstY*vLumFilterSize , lumSrcPtr, vLumFilterSize, vChrFilter+chrDstY*vChrFilterSize, chrUSrcPtr, chrVSrcPtr, vChrFilterSize, alpSrcPtr, dest, uDest, vDest, aDest, dstW, chrDstW); } } else { assert(lumSrcPtr + vLumFilterSize - 1 < lumPixBuf + vLumBufSize*2); assert(chrUSrcPtr + vChrFilterSize - 1 < chrUPixBuf + vChrBufSize*2); if (c->yuv2packed1 && vLumFilterSize == 1 && vChrFilterSize == 2) { //unscaled RGB int chrAlpha= vChrFilter[2*dstY+1]; yuv2packed1(c, *lumSrcPtr, *chrUSrcPtr, *(chrUSrcPtr+1), *chrVSrcPtr, *(chrVSrcPtr+1), alpPixBuf ? *alpSrcPtr : NULL, dest, dstW, chrAlpha, dstFormat, flags, dstY); } else if (c->yuv2packed2 && vLumFilterSize == 2 && vChrFilterSize == 2) { //bilinear upscale RGB int lumAlpha= vLumFilter[2*dstY+1]; int chrAlpha= vChrFilter[2*dstY+1]; lumMmxFilter[2]= lumMmxFilter[3]= vLumFilter[2*dstY ]*0x10001; chrMmxFilter[2]= chrMmxFilter[3]= vChrFilter[2*chrDstY]*0x10001; yuv2packed2(c, *lumSrcPtr, *(lumSrcPtr+1), *chrUSrcPtr, *(chrUSrcPtr+1), *chrVSrcPtr, *(chrVSrcPtr+1), alpPixBuf ? *alpSrcPtr : NULL, alpPixBuf ? *(alpSrcPtr+1) : NULL, dest, dstW, lumAlpha, chrAlpha, dstY); } else { //general RGB yuv2packedX(c, vLumFilter+dstY*vLumFilterSize, lumSrcPtr, vLumFilterSize, vChrFilter+dstY*vChrFilterSize, chrUSrcPtr, chrVSrcPtr, vChrFilterSize, alpSrcPtr, dest, dstW, dstY); } } } } if ((dstFormat == PIX_FMT_YUVA420P) && !alpPixBuf) fillPlane(dst[3], dstStride[3], dstW, dstY-lastDstY, lastDstY, 255); #if HAVE_MMX2 if (av_get_cpu_flags() & AV_CPU_FLAG_MMX2) __asm__ volatile("sfence":::"memory"); #endif emms_c(); /* store changed local vars back in the context */ c->dstY= dstY; c->lumBufIndex= lumBufIndex; c->chrBufIndex= chrBufIndex; c->lastInLumBuf= lastInLumBuf; c->lastInChrBuf= lastInChrBuf; return dstY - lastDstY; }


int sws_setColorspaceDetails(struct SwsContext *c, const int inv_table[4], int srcRange, const int table[4], int dstRange, int brightness, int contrast, int saturation) { const AVPixFmtDescriptor *desc_dst = av_pix_fmt_desc_get(c->dstFormat); const AVPixFmtDescriptor *desc_src = av_pix_fmt_desc_get(c->srcFormat); memcpy(c->srcColorspaceTable, inv_table, sizeof(int) * 4); memcpy(c->dstColorspaceTable, table, sizeof(int) * 4); c->brightness = brightness; c->contrast = contrast; c->saturation = saturation; c->srcRange = srcRange; c->dstRange = dstRange; if (isYUV(c->dstFormat) || isGray(c->dstFormat)) return -1; c->dstFormatBpp = av_get_bits_per_pixel(desc_dst); c->srcFormatBpp = av_get_bits_per_pixel(desc_src); ff_yuv2rgb_c_init_tables(c, inv_table, srcRange, brightness, contrast, saturation); // FIXME factorize if (HAVE_ALTIVEC && av_get_cpu_flags() & AV_CPU_FLAG_ALTIVEC) ff_yuv2rgb_init_tables_altivec(c, inv_table, brightness, contrast, saturation); return 0; }


static void alpha_cpu_class_init(ObjectClass *oc, void *data) { DeviceClass *dc = DEVICE_CLASS(oc); CPUClass *cc = CPU_CLASS(oc); AlphaCPUClass *acc = ALPHA_CPU_CLASS(oc); acc->parent_realize = dc->realize; dc->realize = alpha_cpu_realizefn; cc->class_by_name = alpha_cpu_class_by_name; cc->has_work = alpha_cpu_has_work; cc->do_interrupt = alpha_cpu_do_interrupt; cc->cpu_exec_interrupt = alpha_cpu_exec_interrupt; cc->dump_state = alpha_cpu_dump_state; cc->set_pc = alpha_cpu_set_pc; cc->gdb_read_register = alpha_cpu_gdb_read_register; cc->gdb_write_register = alpha_cpu_gdb_write_register; #ifdef CONFIG_USER_ONLY cc->handle_mmu_fault = alpha_cpu_handle_mmu_fault; #else cc->do_unassigned_access = alpha_cpu_unassigned_access; cc->do_unaligned_access = alpha_cpu_do_unaligned_access; cc->get_phys_page_debug = alpha_cpu_get_phys_page_debug; dc->vmsd = &vmstate_alpha_cpu; #endif cc->disas_set_info = alpha_cpu_disas_set_info; cc->gdb_num_core_regs = 67; /* * Reason: alpha_cpu_initfn() calls cpu_exec_init(), which saves * the object in cpus -> dangling pointer after final * object_unref(). */ dc->cannot_destroy_with_object_finalize_yet = true; }


static void rtas_ibm_write_pci_config(sPAPREnvironment *spapr, uint32_t token, uint32_t nargs, target_ulong args, uint32_t nret, target_ulong rets) { uint32_t val, size, addr; uint64_t buid = ((uint64_t)rtas_ld(args, 1) << 32) | rtas_ld(args, 2); PCIDevice *dev = find_dev(spapr, buid, rtas_ld(args, 0)); if (!dev) { rtas_st(rets, 0, -1); return; } val = rtas_ld(args, 4); size = rtas_ld(args, 3); addr = rtas_pci_cfgaddr(rtas_ld(args, 0)); pci_default_write_config(dev, addr, val, size); rtas_st(rets, 0, 0); }


static int submit_stats(AVCodecContext *avctx) { #ifdef TH_ENCCTL_2PASS_IN TheoraContext *h = avctx->priv_data; int bytes; if (!avctx->stats_in) { av_log(avctx, AV_LOG_ERROR, "No statsfile for second pass\n"); return AVERROR(EINVAL); h->stats_size = strlen(avctx->stats_in) * 3/4; h->stats = av_malloc(h->stats_size); h->stats_size = av_base64_decode(h->stats, avctx->stats_in, h->stats_size); while (h->stats_size - h->stats_offset > 0) { bytes = th_encode_ctl(h->t_state, TH_ENCCTL_2PASS_IN, h->stats + h->stats_offset, h->stats_size - h->stats_offset); if (bytes < 0) { av_log(avctx, AV_LOG_ERROR, "Error submitting stats\n"); return AVERROR_EXTERNAL; if (!bytes) return 0; h->stats_offset += bytes; return 0; #else av_log(avctx, AV_LOG_ERROR, "libtheora too old to support 2pass\n"); return AVERROR(ENOSUP); #endif


static int encode_plane(AVCodecContext *avctx, uint8_t *src, uint8_t *dst, int stride, int width, int height, PutByteContext *pb) { UtvideoContext *c = avctx->priv_data; uint8_t lengths[256]; uint64_t counts[256] = { 0 }; HuffEntry he[256]; uint32_t offset = 0, slice_len = 0; int i, sstart, send = 0; int symbol; /* Do prediction / make planes */ switch (c->frame_pred) { case PRED_NONE: for (i = 0; i < c->slices; i++) { sstart = send; send = height * (i + 1) / c->slices; write_plane(src + sstart * stride, dst + sstart * width, stride, width, send - sstart); } break; case PRED_LEFT: for (i = 0; i < c->slices; i++) { sstart = send; send = height * (i + 1) / c->slices; left_predict(src + sstart * stride, dst + sstart * width, stride, width, send - sstart); } break; case PRED_MEDIAN: for (i = 0; i < c->slices; i++) { sstart = send; send = height * (i + 1) / c->slices; median_predict(c, src + sstart * stride, dst + sstart * width, stride, width, send - sstart); } break; default: av_log(avctx, AV_LOG_ERROR, "Unknown prediction mode: %d\n", c->frame_pred); return AVERROR_OPTION_NOT_FOUND; } /* Count the usage of values */ count_usage(dst, width, height, counts); /* Check for a special case where only one symbol was used */ for (symbol = 0; symbol < 256; symbol++) { /* If non-zero count is found, see if it matches width * height */ if (counts[symbol]) { /* Special case if only one symbol was used */ if (counts[symbol] == width * height) { /* * Write a zero for the single symbol * used in the plane, else 0xFF. */ for (i = 0; i < 256; i++) { if (i == symbol) bytestream2_put_byte(pb, 0); else bytestream2_put_byte(pb, 0xFF); } /* Write zeroes for lengths */ for (i = 0; i < c->slices; i++) bytestream2_put_le32(pb, 0); /* And that's all for that plane folks */ return 0; } break; } } /* Calculate huffman lengths */ ff_huff_gen_len_table(lengths, counts); /* * Write the plane's header into the output packet: * - huffman code lengths (256 bytes) * - slice end offsets (gotten from the slice lengths) */ for (i = 0; i < 256; i++) { bytestream2_put_byte(pb, lengths[i]); he[i].len = lengths[i]; he[i].sym = i; } /* Calculate the huffman codes themselves */ calculate_codes(he); send = 0; for (i = 0; i < c->slices; i++) { sstart = send; send = height * (i + 1) / c->slices; /* * Write the huffman codes to a buffer, * get the offset in bits and convert to bytes. */ offset += write_huff_codes(dst + sstart * width, c->slice_bits, width * (send - sstart), width, send - sstart, he) >> 3; slice_len = offset - slice_len; /* Byteswap the written huffman codes */ c->dsp.bswap_buf((uint32_t *) c->slice_bits, (uint32_t *) c->slice_bits, slice_len >> 2); /* Write the offset to the stream */ bytestream2_put_le32(pb, offset); /* Seek to the data part of the packet */ bytestream2_seek_p(pb, 4 * (c->slices - i - 1) + offset - slice_len, SEEK_CUR); /* Write the slices' data into the output packet */ bytestream2_put_buffer(pb, c->slice_bits, slice_len); /* Seek back to the slice offsets */ bytestream2_seek_p(pb, -4 * (c->slices - i - 1) - offset, SEEK_CUR); slice_len = offset; } /* And at the end seek to the end of written slice(s) */ bytestream2_seek_p(pb, offset, SEEK_CUR); return 0; }


static int vhdx_create(const char *filename, QEMUOptionParameter *options, Error **errp) { int ret = 0; uint64_t image_size = (uint64_t) 2 * GiB; uint32_t log_size = 1 * MiB; uint32_t block_size = 0; uint64_t signature; uint64_t metadata_offset; bool use_zero_blocks = false; gunichar2 *creator = NULL; glong creator_items; BlockDriverState *bs; const char *type = NULL; VHDXImageType image_type; Error *local_err = NULL; while (options && options->name) { if (!strcmp(options->name, BLOCK_OPT_SIZE)) { image_size = options->value.n; } else if (!strcmp(options->name, VHDX_BLOCK_OPT_LOG_SIZE)) { log_size = options->value.n; } else if (!strcmp(options->name, VHDX_BLOCK_OPT_BLOCK_SIZE)) { block_size = options->value.n; } else if (!strcmp(options->name, BLOCK_OPT_SUBFMT)) { type = options->value.s; } else if (!strcmp(options->name, VHDX_BLOCK_OPT_ZERO)) { use_zero_blocks = options->value.n != 0; } options++; } if (image_size > VHDX_MAX_IMAGE_SIZE) { error_setg_errno(errp, EINVAL, "Image size too large; max of 64TB"); ret = -EINVAL; goto exit; } if (type == NULL) { type = "dynamic"; } if (!strcmp(type, "dynamic")) { image_type = VHDX_TYPE_DYNAMIC; } else if (!strcmp(type, "fixed")) { image_type = VHDX_TYPE_FIXED; } else if (!strcmp(type, "differencing")) { error_setg_errno(errp, ENOTSUP, "Differencing files not yet supported"); ret = -ENOTSUP; goto exit; } else { ret = -EINVAL; goto exit; } /* These are pretty arbitrary, and mainly designed to keep the BAT * size reasonable to load into RAM */ if (block_size == 0) { if (image_size > 32 * TiB) { block_size = 64 * MiB; } else if (image_size > (uint64_t) 100 * GiB) { block_size = 32 * MiB; } else if (image_size > 1 * GiB) { block_size = 16 * MiB; } else { block_size = 8 * MiB; } } /* make the log size close to what was specified, but must be * min 1MB, and multiple of 1MB */ log_size = ROUND_UP(log_size, MiB); block_size = ROUND_UP(block_size, MiB); block_size = block_size > VHDX_BLOCK_SIZE_MAX ? VHDX_BLOCK_SIZE_MAX : block_size; ret = bdrv_create_file(filename, options, &local_err); if (ret < 0) { error_propagate(errp, local_err); goto exit; } ret = bdrv_file_open(&bs, filename, NULL, NULL, BDRV_O_RDWR, &local_err); if (ret < 0) { error_propagate(errp, local_err); goto exit; } /* Create (A) */ /* The creator field is optional, but may be useful for * debugging / diagnostics */ creator = g_utf8_to_utf16("QEMU v" QEMU_VERSION, -1, NULL, &creator_items, NULL); signature = cpu_to_le64(VHDX_FILE_SIGNATURE); bdrv_pwrite(bs, VHDX_FILE_ID_OFFSET, &signature, sizeof(signature)); if (ret < 0) { goto delete_and_exit; } if (creator) { bdrv_pwrite(bs, VHDX_FILE_ID_OFFSET + sizeof(signature), creator, creator_items * sizeof(gunichar2)); if (ret < 0) { goto delete_and_exit; } } /* Creates (B),(C) */ ret = vhdx_create_new_headers(bs, image_size, log_size); if (ret < 0) { goto delete_and_exit; } /* Creates (D),(E),(G) explicitly. (F) created as by-product */ ret = vhdx_create_new_region_table(bs, image_size, block_size, 512, log_size, use_zero_blocks, image_type, &metadata_offset); if (ret < 0) { goto delete_and_exit; } /* Creates (H) */ ret = vhdx_create_new_metadata(bs, image_size, block_size, 512, metadata_offset, image_type); if (ret < 0) { goto delete_and_exit; } delete_and_exit: bdrv_unref(bs); exit: g_free(creator); return ret; }


static int zero_single_l2(BlockDriverState *bs, uint64_t offset, uint64_t nb_clusters, int flags) { BDRVQcow2State *s = bs->opaque; uint64_t *l2_table; int l2_index; int ret; int i; ret = get_cluster_table(bs, offset, &l2_table, &l2_index); if (ret < 0) { return ret; } /* Limit nb_clusters to one L2 table */ nb_clusters = MIN(nb_clusters, s->l2_size - l2_index); assert(nb_clusters <= INT_MAX); for (i = 0; i < nb_clusters; i++) { uint64_t old_offset; old_offset = be64_to_cpu(l2_table[l2_index + i]); /* Update L2 entries */ qcow2_cache_entry_mark_dirty(bs, s->l2_table_cache, l2_table); if (old_offset & QCOW_OFLAG_COMPRESSED || flags & BDRV_REQ_MAY_UNMAP) { l2_table[l2_index + i] = cpu_to_be64(QCOW_OFLAG_ZERO); qcow2_free_any_clusters(bs, old_offset, 1, QCOW2_DISCARD_REQUEST); } else { l2_table[l2_index + i] |= cpu_to_be64(QCOW_OFLAG_ZERO); } } qcow2_cache_put(bs, s->l2_table_cache, (void **) &l2_table); return nb_clusters; }


static int megasas_dcmd_set_properties(MegasasState *s, MegasasCmd *cmd) { struct mfi_ctrl_props info; size_t dcmd_size = sizeof(info); if (cmd->iov_size < dcmd_size) { trace_megasas_dcmd_invalid_xfer_len(cmd->index, cmd->iov_size, dcmd_size); return MFI_STAT_INVALID_PARAMETER; } dma_buf_write((uint8_t *)&info, cmd->iov_size, &cmd->qsg); trace_megasas_dcmd_unsupported(cmd->index, cmd->iov_size); return MFI_STAT_OK; }


static int fd_open(BlockDriverState *bs) { BDRVRawState *s = bs->opaque; int last_media_present; if (s->type != FTYPE_FD) return 0; last_media_present = (s->fd >= 0); if (s->fd >= 0 && (qemu_get_clock(rt_clock) - s->fd_open_time) >= FD_OPEN_TIMEOUT) { close(s->fd); s->fd = -1; raw_close_fd_pool(s); #ifdef DEBUG_FLOPPY printf("Floppy closed\n"); #endif } if (s->fd < 0) { if (s->fd_got_error && (qemu_get_clock(rt_clock) - s->fd_error_time) < FD_OPEN_TIMEOUT) { #ifdef DEBUG_FLOPPY printf("No floppy (open delayed)\n"); #endif return -EIO; } s->fd = open(bs->filename, s->fd_open_flags); if (s->fd < 0) { s->fd_error_time = qemu_get_clock(rt_clock); s->fd_got_error = 1; if (last_media_present) s->fd_media_changed = 1; #ifdef DEBUG_FLOPPY printf("No floppy\n"); #endif return -EIO; } #ifdef DEBUG_FLOPPY printf("Floppy opened\n"); #endif } if (!last_media_present) s->fd_media_changed = 1; s->fd_open_time = qemu_get_clock(rt_clock); s->fd_got_error = 0; return 0; }


static void qdev_print(Monitor *mon, DeviceState *dev, int indent) { BusState *child; qdev_printf("dev: %s, id \"%s\"\n", dev->info->name, dev->id ? dev->id : ""); indent += 2; if (dev->num_gpio_in) { qdev_printf("gpio-in %d\n", dev->num_gpio_in); } if (dev->num_gpio_out) { qdev_printf("gpio-out %d\n", dev->num_gpio_out); } qdev_print_props(mon, dev, dev->info->props, "dev", indent); qdev_print_props(mon, dev, dev->parent_bus->info->props, "bus", indent); if (dev->parent_bus->info->print_dev) dev->parent_bus->info->print_dev(mon, dev, indent); LIST_FOREACH(child, &dev->child_bus, sibling) { qbus_print(mon, child, indent); } }


static int qcow2_load_vmstate(BlockDriverState *bs, QEMUIOVector *qiov, int64_t pos) { BDRVQcow2State *s = bs->opaque; bool zero_beyond_eof = bs->zero_beyond_eof; int ret; BLKDBG_EVENT(bs->file, BLKDBG_VMSTATE_LOAD); bs->zero_beyond_eof = false; ret = bdrv_preadv(bs, qcow2_vm_state_offset(s) + pos, qiov); bs->zero_beyond_eof = zero_beyond_eof; return ret; }


static av_cold int g726_encode_init(AVCodecContext *avctx) { G726Context* c = avctx->priv_data; if (avctx->strict_std_compliance > FF_COMPLIANCE_UNOFFICIAL && avctx->sample_rate != 8000) { av_log(avctx, AV_LOG_ERROR, "Sample rates other than 8kHz are not " "allowed when the compliance level is higher than unofficial. " "Resample or reduce the compliance level.\n"); return AVERROR(EINVAL); } av_assert0(avctx->sample_rate > 0); if(avctx->channels != 1){ av_log(avctx, AV_LOG_ERROR, "Only mono is supported\n"); return -1; } if (avctx->bit_rate % avctx->sample_rate) { av_log(avctx, AV_LOG_ERROR, "Bitrate - Samplerate combination is invalid\n"); return AVERROR(EINVAL); } c->code_size = (avctx->bit_rate + avctx->sample_rate/2) / avctx->sample_rate; if (c->code_size < 2 || c->code_size > 5) { av_log(avctx, AV_LOG_ERROR, "Invalid number of bits %d\n", c->code_size); return AVERROR(EINVAL); } avctx->bits_per_coded_sample = c->code_size; g726_reset(c, c->code_size - 2); avctx->coded_frame = avcodec_alloc_frame(); if (!avctx->coded_frame) return AVERROR(ENOMEM); avctx->coded_frame->key_frame = 1; /* select a frame size that will end on a byte boundary and have a size of approximately 1024 bytes */ avctx->frame_size = ((int[]){ 4096, 2736, 2048, 1640 })[c->code_size - 2]; return 0; }


int qemu_acl_insert(qemu_acl *acl, int deny, const char *match, int index) { qemu_acl_entry *entry; qemu_acl_entry *tmp; int i = 0; if (index <= 0) return -1; if (index >= acl->nentries) return qemu_acl_append(acl, deny, match); entry = qemu_malloc(sizeof(*entry)); entry->match = qemu_strdup(match); entry->deny = deny; TAILQ_FOREACH(tmp, &acl->entries, next) { i++; if (i == index) { TAILQ_INSERT_BEFORE(tmp, entry, next); acl->nentries++; break; } } return i; }


int64_t bdrv_get_block_status(BlockDriverState *bs, int64_t sector_num, int nb_sectors, int *pnum, BlockDriverState **file) { return bdrv_get_block_status_above(bs, backing_bs(bs), sector_num, nb_sectors, pnum, file); }


static int vmdk_probe(const uint8_t *buf, int buf_size, const char *filename) { uint32_t magic; if (buf_size < 4) return 0; magic = be32_to_cpu(*(uint32_t *)buf); if (magic == VMDK3_MAGIC || magic == VMDK4_MAGIC) { return 100; } else { const char *p = (const char *)buf; const char *end = p + buf_size; while (p < end) { if (*p == '#') { /* skip comment line */ while (p < end && *p != '\n') { p++; } p++; continue; } if (*p == ' ') { while (p < end && *p == ' ') { p++; } /* skip '\r' if windows line endings used. */ if (p < end && *p == '\r') { p++; } /* only accept blank lines before 'version=' line */ if (p == end || *p != '\n') { return 0; } p++; continue; } if (end - p >= strlen("version=X\n")) { if (strncmp("version=1\n", p, strlen("version=1\n")) == 0 || strncmp("version=2\n", p, strlen("version=2\n")) == 0) { return 100; } } if (end - p >= strlen("version=X\r\n")) { if (strncmp("version=1\r\n", p, strlen("version=1\r\n")) == 0 || strncmp("version=2\r\n", p, strlen("version=2\r\n")) == 0) { return 100; } } return 0; } return 0; } }


static int write_elf64_note(DumpState *s) { Elf64_Phdr phdr; int endian = s->dump_info.d_endian; target_phys_addr_t begin = s->memory_offset - s->note_size; int ret; memset(&phdr, 0, sizeof(Elf64_Phdr)); phdr.p_type = cpu_convert_to_target32(PT_NOTE, endian); phdr.p_offset = cpu_convert_to_target64(begin, endian); phdr.p_paddr = 0; phdr.p_filesz = cpu_convert_to_target64(s->note_size, endian); phdr.p_memsz = cpu_convert_to_target64(s->note_size, endian); phdr.p_vaddr = 0; ret = fd_write_vmcore(&phdr, sizeof(Elf64_Phdr), s); if (ret < 0) { dump_error(s, "dump: failed to write program header table.\n"); return -1; } return 0; }


void bdrv_append(BlockDriverState *bs_new, BlockDriverState *bs_top) { assert(!bdrv_requests_pending(bs_top)); assert(!bdrv_requests_pending(bs_new)); bdrv_ref(bs_top); change_parent_backing_link(bs_top, bs_new); bdrv_set_backing_hd(bs_new, bs_top); bdrv_unref(bs_top); /* bs_new is now referenced by its new parents, we don't need the * additional reference any more. */ bdrv_unref(bs_new); }


static void restore_sigcontext(CPUSH4State *regs, struct target_sigcontext *sc, target_ulong *r0_p) { int i; #define COPY(x) __get_user(regs->x, &sc->sc_##x) COPY(gregs[1]); COPY(gregs[2]); COPY(gregs[3]); COPY(gregs[4]); COPY(gregs[5]); COPY(gregs[6]); COPY(gregs[7]); COPY(gregs[8]); COPY(gregs[9]); COPY(gregs[10]); COPY(gregs[11]); COPY(gregs[12]); COPY(gregs[13]); COPY(gregs[14]); COPY(gregs[15]); COPY(gbr); COPY(mach); COPY(macl); COPY(pr); COPY(sr); COPY(pc); #undef COPY for (i=0; i<16; i++) { __get_user(regs->fregs[i], &sc->sc_fpregs[i]); } __get_user(regs->fpscr, &sc->sc_fpscr); __get_user(regs->fpul, &sc->sc_fpul); regs->tra = -1; /* disable syscall checks */ __get_user(*r0_p, &sc->sc_gregs[0]); }


static void vtd_update_iotlb(IntelIOMMUState *s, uint16_t source_id, uint16_t domain_id, hwaddr addr, uint64_t slpte, bool read_flags, bool write_flags) { VTDIOTLBEntry *entry = g_malloc(sizeof(*entry)); uint64_t *key = g_malloc(sizeof(*key)); uint64_t gfn = addr >> VTD_PAGE_SHIFT_4K; VTD_DPRINTF(CACHE, "update iotlb sid 0x%"PRIx16 " gpa 0x%"PRIx64 " slpte 0x%"PRIx64 " did 0x%"PRIx16, source_id, addr, slpte, domain_id); if (g_hash_table_size(s->iotlb) >= VTD_IOTLB_MAX_SIZE) { VTD_DPRINTF(CACHE, "iotlb exceeds size limit, forced to reset"); vtd_reset_iotlb(s); } entry->gfn = gfn; entry->domain_id = domain_id; entry->slpte = slpte; entry->read_flags = read_flags; entry->write_flags = write_flags; *key = gfn | ((uint64_t)(source_id) << VTD_IOTLB_SID_SHIFT); g_hash_table_replace(s->iotlb, key, entry); }


static void armv7m_nvic_init(SysBusDevice *dev) { nvic_state *s= FROM_SYSBUSGIC(nvic_state, dev); CPUState *env; env = qdev_get_prop_ptr(&dev->qdev, "cpu"); gic_init(&s->gic); cpu_register_physical_memory(0xe000e000, 0x1000, s->gic.iomemtype); s->systick.timer = qemu_new_timer(vm_clock, systick_timer_tick, s); if (env->v7m.nvic) hw_error("CPU can only have one NVIC\n"); env->v7m.nvic = s; register_savevm("armv7m_nvic", -1, 1, nvic_save, nvic_load, s); }


lookup_scalar(const OptsVisitor *ov, const char *name, Error **errp) { if (ov->repeated_opts == NULL) { GQueue *list; /* the last occurrence of any QemuOpt takes effect when queried by name */ list = lookup_distinct(ov, name, errp); return list ? g_queue_peek_tail(list) : NULL; } return g_queue_peek_head(ov->repeated_opts); }


static void hextile_enc_cord(uint8_t *ptr, int x, int y, int w, int h) { ptr[0] = ((x & 0x0F) << 4) | (y & 0x0F); ptr[1] = (((w - 1) & 0x0F) << 4) | ((h - 1) & 0x0F); }


static void RENAME(hyscale_fast)(SwsContext *c, int16_t *dst, int dstWidth, const uint8_t *src, int srcW, int xInc) { int16_t *filterPos = c->hLumFilterPos; int16_t *filter = c->hLumFilter; void *mmx2FilterCode= c->lumMmx2FilterCode; int i; #if defined(PIC) uint64_t ebxsave; #endif #if ARCH_X86_64 uint64_t retsave; #endif __asm__ volatile( #if defined(PIC) "mov %%"REG_b", %5 \n\t" #if ARCH_X86_64 "mov -8(%%rsp), %%"REG_a" \n\t" "mov %%"REG_a", %6 \n\t" #endif #else #if ARCH_X86_64 "mov -8(%%rsp), %%"REG_a" \n\t" "mov %%"REG_a", %5 \n\t" #endif #endif "pxor %%mm7, %%mm7 \n\t" "mov %0, %%"REG_c" \n\t" "mov %1, %%"REG_D" \n\t" "mov %2, %%"REG_d" \n\t" "mov %3, %%"REG_b" \n\t" "xor %%"REG_a", %%"REG_a" \n\t" // i PREFETCH" (%%"REG_c") \n\t" PREFETCH" 32(%%"REG_c") \n\t" PREFETCH" 64(%%"REG_c") \n\t" #if ARCH_X86_64 #define CALL_MMX2_FILTER_CODE \ "movl (%%"REG_b"), %%esi \n\t"\ "call *%4 \n\t"\ "movl (%%"REG_b", %%"REG_a"), %%esi \n\t"\ "add %%"REG_S", %%"REG_c" \n\t"\ "add %%"REG_a", %%"REG_D" \n\t"\ "xor %%"REG_a", %%"REG_a" \n\t"\ #else #define CALL_MMX2_FILTER_CODE \ "movl (%%"REG_b"), %%esi \n\t"\ "call *%4 \n\t"\ "addl (%%"REG_b", %%"REG_a"), %%"REG_c" \n\t"\ "add %%"REG_a", %%"REG_D" \n\t"\ "xor %%"REG_a", %%"REG_a" \n\t"\ #endif /* ARCH_X86_64 */ CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE CALL_MMX2_FILTER_CODE #if defined(PIC) "mov %5, %%"REG_b" \n\t" #if ARCH_X86_64 "mov %6, %%"REG_a" \n\t" "mov %%"REG_a", -8(%%rsp) \n\t" #endif #else #if ARCH_X86_64 "mov %5, %%"REG_a" \n\t" "mov %%"REG_a", -8(%%rsp) \n\t" #endif #endif :: "m" (src), "m" (dst), "m" (filter), "m" (filterPos), "m" (mmx2FilterCode) #if defined(PIC) ,"m" (ebxsave) #endif #if ARCH_X86_64 ,"m"(retsave) #endif : "%"REG_a, "%"REG_c, "%"REG_d, "%"REG_S, "%"REG_D #if !defined(PIC) ,"%"REG_b #endif ); for (i=dstWidth-1; (i*xInc)>>16 >=srcW-1; i--) dst[i] = src[srcW-1]*128; }


static int decode_dc_progressive(MJpegDecodeContext *s, int16_t *block, int component, int dc_index, uint16_t *quant_matrix, int Al) { int val; s->bdsp.clear_block(block); val = mjpeg_decode_dc(s, dc_index); if (val == 0xfffff) { av_log(s->avctx, AV_LOG_ERROR, "error dc\n"); return AVERROR_INVALIDDATA; } val = (val * (quant_matrix[0] << Al)) + s->last_dc[component]; s->last_dc[component] = val; block[0] = val; return 0; }


static void vga_screen_dump_common(VGAState *s, const char *filename, int w, int h) { DisplayState *saved_ds, ds1, *ds = &ds1; DisplayChangeListener dcl; /* XXX: this is a little hackish */ vga_invalidate_display(s); saved_ds = s->ds; memset(ds, 0, sizeof(DisplayState)); memset(&dcl, 0, sizeof(DisplayChangeListener)); dcl.dpy_update = vga_save_dpy_update; dcl.dpy_resize = vga_save_dpy_resize; dcl.dpy_refresh = vga_save_dpy_refresh; register_displaychangelistener(ds, &dcl); ds->surface = qemu_create_displaysurface(ds, w, h); s->ds = ds; s->graphic_mode = -1; vga_update_display(s); ppm_save(filename, ds->surface); qemu_free_displaysurface(ds); s->ds = saved_ds; }


static int ehci_state_execute(EHCIQueue *q) { EHCIPacket *p = QTAILQ_FIRST(&q->packets); int again = 0; assert(p != NULL); assert(p->qtdaddr == q->qtdaddr); if (ehci_qh_do_overlay(q) != 0) { return -1; } // TODO verify enough time remains in the uframe as in 4.4.1.1 // TODO write back ptr to async list when done or out of time // TODO Windows does not seem to ever set the MULT field if (!q->async) { int transactCtr = get_field(q->qh.epcap, QH_EPCAP_MULT); if (!transactCtr) { ehci_set_state(q->ehci, q->async, EST_HORIZONTALQH); again = 1; goto out; } } if (q->async) { ehci_set_usbsts(q->ehci, USBSTS_REC); } p->usb_status = ehci_execute(p, "process"); if (p->usb_status == USB_RET_PROCERR) { again = -1; goto out; } if (p->usb_status == USB_RET_ASYNC) { ehci_flush_qh(q); trace_usb_ehci_packet_action(p->queue, p, "async"); p->async = EHCI_ASYNC_INFLIGHT; ehci_set_state(q->ehci, q->async, EST_HORIZONTALQH); again = (ehci_fill_queue(p) == USB_RET_PROCERR) ? -1 : 1; goto out; } ehci_set_state(q->ehci, q->async, EST_EXECUTING); again = 1; out: return again; }


static void update_msix_table_msg_data(S390PCIBusDevice *pbdev, uint64_t offset, uint64_t *data, uint8_t len) { uint32_t val; uint8_t *msg_data; if (offset % PCI_MSIX_ENTRY_SIZE != 8) { return; } if (len != 4) { DPRINTF("access msix table msg data but len is %d\n", len); return; } msg_data = (uint8_t *)data - offset % PCI_MSIX_ENTRY_SIZE + PCI_MSIX_ENTRY_VECTOR_CTRL; val = pci_get_long(msg_data) | (pbdev->fid << ZPCI_MSI_VEC_BITS); pci_set_long(msg_data, val); DPRINTF("update msix msg_data to 0x%" PRIx64 "\n", *data); }


void ff_er_add_slice(ERContext *s, int startx, int starty, int endx, int endy, int status) { const int start_i = av_clip(startx + starty * s->mb_width, 0, s->mb_num - 1); const int end_i = av_clip(endx + endy * s->mb_width, 0, s->mb_num); const int start_xy = s->mb_index2xy[start_i]; const int end_xy = s->mb_index2xy[end_i]; int mask = -1; if (s->avctx->hwaccel && s->avctx->hwaccel->decode_slice) return; if (start_i > end_i || start_xy > end_xy) { av_log(s->avctx, AV_LOG_ERROR, "internal error, slice end before start\n"); return; } if (!s->avctx->error_concealment) return; mask &= ~VP_START; if (status & (ER_AC_ERROR | ER_AC_END)) { mask &= ~(ER_AC_ERROR | ER_AC_END); s->error_count -= end_i - start_i + 1; } if (status & (ER_DC_ERROR | ER_DC_END)) { mask &= ~(ER_DC_ERROR | ER_DC_END); s->error_count -= end_i - start_i + 1; } if (status & (ER_MV_ERROR | ER_MV_END)) { mask &= ~(ER_MV_ERROR | ER_MV_END); s->error_count -= end_i - start_i + 1; } if (status & ER_MB_ERROR) { s->error_occurred = 1; s->error_count = INT_MAX; } if (mask == ~0x7F) { memset(&s->error_status_table[start_xy], 0, (end_xy - start_xy) * sizeof(uint8_t)); } else { int i; for (i = start_xy; i < end_xy; i++) s->error_status_table[i] &= mask; } if (end_i == s->mb_num) s->error_count = INT_MAX; else { s->error_status_table[end_xy] &= mask; s->error_status_table[end_xy] |= status; } s->error_status_table[start_xy] |= VP_START; if (start_xy > 0 && !(s->avctx->active_thread_type & FF_THREAD_SLICE) && er_supported(s) && s->avctx->skip_top * s->mb_width < start_i) { int prev_status = s->error_status_table[s->mb_index2xy[start_i - 1]]; prev_status &= ~ VP_START; if (prev_status != (ER_MV_END | ER_DC_END | ER_AC_END)) { s->error_occurred = 1; s->error_count = INT_MAX; } } }


static inline void RENAME(yuv2yuvX)(SwsContext *c, const int16_t *lumFilter, const int16_t **lumSrc, int lumFilterSize, const int16_t *chrFilter, const int16_t **chrUSrc, const int16_t **chrVSrc, int chrFilterSize, const int16_t **alpSrc, uint8_t *dest, uint8_t *uDest, uint8_t *vDest, uint8_t *aDest, long dstW, long chrDstW) { if (uDest) { YSCALEYUV2YV12X(CHR_MMX_FILTER_OFFSET, uDest, chrDstW, 0) YSCALEYUV2YV12X(CHR_MMX_FILTER_OFFSET, vDest, chrDstW + c->uv_off, c->uv_off) } if (CONFIG_SWSCALE_ALPHA && aDest) { YSCALEYUV2YV12X(ALP_MMX_FILTER_OFFSET, aDest, dstW, 0) } YSCALEYUV2YV12X(LUM_MMX_FILTER_OFFSET, dest, dstW, 0) }


void bitmap_clear(unsigned long *map, long start, long nr) { unsigned long *p = map + BIT_WORD(start); const long size = start + nr; int bits_to_clear = BITS_PER_LONG - (start % BITS_PER_LONG); unsigned long mask_to_clear = BITMAP_FIRST_WORD_MASK(start); while (nr - bits_to_clear >= 0) { *p &= ~mask_to_clear; nr -= bits_to_clear; bits_to_clear = BITS_PER_LONG; mask_to_clear = ~0UL; p++; } if (nr) { mask_to_clear &= BITMAP_LAST_WORD_MASK(size); *p &= ~mask_to_clear; } }


static inline void tcg_temp_free_internal(int idx) { TCGContext *s = &tcg_ctx; TCGTemp *ts; int k; assert(idx >= s->nb_globals && idx < s->nb_temps); ts = &s->temps[idx]; assert(ts->temp_allocated != 0); ts->temp_allocated = 0; k = ts->base_type; if (ts->temp_local) k += TCG_TYPE_COUNT; ts->next_free_temp = s->first_free_temp[k]; s->first_free_temp[k] = idx;


static void mcf_uart_do_tx(mcf_uart_state *s) { if (s->tx_enabled && (s->sr & MCF_UART_TxEMP) == 0) { if (s->chr) qemu_chr_fe_write(s->chr, (unsigned char *)&s->tb, 1); s->sr |= MCF_UART_TxEMP; } if (s->tx_enabled) { s->sr |= MCF_UART_TxRDY; } else { s->sr &= ~MCF_UART_TxRDY; } }


int av_cold ff_mlp_init_crc2D(AVCodecParserContext *s) { if (!crc_init_2D) { av_crc_init(crc_2D, 0, 16, 0x002D, sizeof(crc_2D)); crc_init_2D = 1; } return 0; }


static void mainstone_common_init(MemoryRegion *address_space_mem, MachineState *machine, enum mainstone_model_e model, int arm_id) { uint32_t sector_len = 256 * 1024; hwaddr mainstone_flash_base[] = { MST_FLASH_0, MST_FLASH_1 }; PXA2xxState *mpu; DeviceState *mst_irq; DriveInfo *dinfo; int i; int be; MemoryRegion *rom = g_new(MemoryRegion, 1); const char *cpu_model = machine->cpu_model; if (!cpu_model) cpu_model = "pxa270-c5"; /* Setup CPU & memory */ mpu = pxa270_init(address_space_mem, mainstone_binfo.ram_size, cpu_model); memory_region_init_ram(rom, NULL, "mainstone.rom", MAINSTONE_ROM, &error_abort); vmstate_register_ram_global(rom); memory_region_set_readonly(rom, true); memory_region_add_subregion(address_space_mem, 0, rom); #ifdef TARGET_WORDS_BIGENDIAN be = 1; #else be = 0; #endif /* There are two 32MiB flash devices on the board */ for (i = 0; i < 2; i ++) { dinfo = drive_get(IF_PFLASH, 0, i); if (!dinfo) { if (qtest_enabled()) { break; } fprintf(stderr, "Two flash images must be given with the " "'pflash' parameter\n"); exit(1); } if (!pflash_cfi01_register(mainstone_flash_base[i], NULL, i ? "mainstone.flash1" : "mainstone.flash0", MAINSTONE_FLASH, blk_by_legacy_dinfo(dinfo), sector_len, MAINSTONE_FLASH / sector_len, 4, 0, 0, 0, 0, be)) { fprintf(stderr, "qemu: Error registering flash memory.\n"); exit(1); } } mst_irq = sysbus_create_simple("mainstone-fpga", MST_FPGA_PHYS, qdev_get_gpio_in(mpu->gpio, 0)); /* setup keypad */ pxa27x_register_keypad(mpu->kp, map, 0xe0); /* MMC/SD host */ pxa2xx_mmci_handlers(mpu->mmc, NULL, qdev_get_gpio_in(mst_irq, MMC_IRQ)); pxa2xx_pcmcia_set_irq_cb(mpu->pcmcia[0], qdev_get_gpio_in(mst_irq, S0_IRQ), qdev_get_gpio_in(mst_irq, S0_CD_IRQ)); pxa2xx_pcmcia_set_irq_cb(mpu->pcmcia[1], qdev_get_gpio_in(mst_irq, S1_IRQ), qdev_get_gpio_in(mst_irq, S1_CD_IRQ)); smc91c111_init(&nd_table[0], MST_ETH_PHYS, qdev_get_gpio_in(mst_irq, ETHERNET_IRQ)); mainstone_binfo.kernel_filename = machine->kernel_filename; mainstone_binfo.kernel_cmdline = machine->kernel_cmdline; mainstone_binfo.initrd_filename = machine->initrd_filename; mainstone_binfo.board_id = arm_id; arm_load_kernel(mpu->cpu, &mainstone_binfo); }


Visitor *validate_test_init(TestInputVisitorData *data, const char *json_string, ...) { Visitor *v; va_list ap; va_start(ap, json_string); data->obj = qobject_from_jsonv(json_string, &ap); va_end(ap); g_assert(data->obj != NULL); data->qiv = qmp_input_visitor_new_strict(data->obj); g_assert(data->qiv != NULL); v = qmp_input_get_visitor(data->qiv); g_assert(v != NULL); return v; }


void vmstate_save_state(QEMUFile *f, const VMStateDescription *vmsd, void *opaque, QJSON *vmdesc) { VMStateField *field = vmsd->fields; trace_vmstate_save_state_top(vmsd->name); if (vmsd->pre_save) { vmsd->pre_save(opaque); } if (vmdesc) { json_prop_str(vmdesc, "vmsd_name", vmsd->name); json_prop_int(vmdesc, "version", vmsd->version_id); json_start_array(vmdesc, "fields"); } while (field->name) { if (!field->field_exists || field->field_exists(opaque, vmsd->version_id)) { void *first_elem = opaque + field->offset; int i, n_elems = vmstate_n_elems(opaque, field); int size = vmstate_size(opaque, field); int64_t old_offset, written_bytes; QJSON *vmdesc_loop = vmdesc; trace_vmstate_save_state_loop(vmsd->name, field->name, n_elems); if (field->flags & VMS_POINTER) { first_elem = *(void **)first_elem; assert(first_elem || !n_elems); } for (i = 0; i < n_elems; i++) { void *curr_elem = first_elem + size * i; vmsd_desc_field_start(vmsd, vmdesc_loop, field, i, n_elems); old_offset = qemu_ftell_fast(f); if (field->flags & VMS_ARRAY_OF_POINTER) { assert(curr_elem); curr_elem = *(void **)curr_elem; } if (field->flags & VMS_STRUCT) { vmstate_save_state(f, field->vmsd, curr_elem, vmdesc_loop); } else { field->info->put(f, curr_elem, size, field, vmdesc_loop); } written_bytes = qemu_ftell_fast(f) - old_offset; vmsd_desc_field_end(vmsd, vmdesc_loop, field, written_bytes, i); /* Compressed arrays only care about the first element */ if (vmdesc_loop && vmsd_can_compress(field)) { vmdesc_loop = NULL; } } } else { if (field->flags & VMS_MUST_EXIST) { error_report("Output state validation failed: %s/%s", vmsd->name, field->name); assert(!(field->flags & VMS_MUST_EXIST)); } } field++; } if (vmdesc) { json_end_array(vmdesc); } vmstate_subsection_save(f, vmsd, opaque, vmdesc); }


static AVStream *add_av_stream1(FFServerStream *stream, AVCodecContext *codec, int copy) { AVStream *fst; if(stream->nb_streams >= FF_ARRAY_ELEMS(stream->streams)) return NULL; fst = av_mallocz(sizeof(AVStream)); if (!fst) return NULL; if (copy) { fst->codec = avcodec_alloc_context3(codec->codec); if (!fst->codec) { av_free(fst); return NULL; } avcodec_copy_context(fst->codec, codec); } else /* live streams must use the actual feed's codec since it may be * updated later to carry extradata needed by them. */ fst->codec = codec; fst->priv_data = av_mallocz(sizeof(FeedData)); fst->index = stream->nb_streams; avpriv_set_pts_info(fst, 33, 1, 90000); fst->sample_aspect_ratio = codec->sample_aspect_ratio; stream->streams[stream->nb_streams++] = fst; return fst; }