ffmpeg中av_image_alloc()函式的用法 以及 另一種同樣功能的函式用法
一、ffmpeg中av_image_alloc()是這樣定義的。此函式的功能是按照指定的寬、高、畫素格式來分析影象記憶體。
引數說明:
pointers[4]:儲存影象通道的地址。如果是RGB,則前三個指標分別指向R,G,B的記憶體地址。第四個指標保留不用 linesizes[4]:儲存影象每個通道的記憶體對齊的步長,即一行的對齊記憶體的寬度,此值大小等於影象寬度。 w: 要申請記憶體的影象寬度。 h: 要申請記憶體的影象高度。 pix_fmt: 要申請記憶體的影象的畫素格式。 align: 用於記憶體對齊的值。 返回值:所申請的記憶體空間的總大小。如果是負值,表示申請失敗。 /** * Allocate an image with size w and h and pixel format pix_fmt, and * fill pointers and linesizes accordingly. * The allocated image buffer has to be freed by using * av_freep(&pointers[0]). * * @param align the value to use for buffer size alignment * @return the size in bytes required for the image buffer, a negative * error code in case of failure */ int av_image_alloc(uint8_t *pointers[4], int linesizes[4], int w, int h, enum AVPixelFormat pix_fmt, int align);
(1)呼叫例項
參見本地工程 \vs2010cProjects\ffmpeg_yuv_file_show_sdl2\ffmpeg_yuv_file_show_sdl2。
具體程式碼:
ret= av_image_alloc(src_data, src_linesize,src_w, src_h, src_pixfmt, 1); //按照長、寬、畫素格式分配各個通道的記憶體大小以及步長(linesize),記憶體地址儲存到src_data的指標陣列中 if (ret< 0) { printf( "Could not allocate source image\n"); return -1; }
二、另一種同樣功能的函式呼叫方法
int image_buf_size = av_image_get_buffer_size(AV_PIX_FMT_YUV420P, pCodecCtx->width, pCodecCtx->height, 1); //計算指定畫素格式、影象寬、高所需要的對齊的記憶體大小
out_buffer = (unsigned char *)av_malloc(image_buf_size); //分配指定大小的記憶體空間
av_image_get_buffer_size()函式的作用是通過指定畫素格式、影象寬、影象高來計算所需的記憶體大小。
ffmpeg中關於av_image_get_buffer_size()的定義如下:
/**
* Return the size in bytes of the amount of data required to store an
* image with the given parameters.
*
* @param pix_fmt the pixel format of the image
* @param width the width of the image in pixels
* @param height the height of the image in pixels
* @param align the assumed linesize alignment
* @return the buffer size in bytes, a negative error code in case of failure
*/
int av_image_get_buffer_size(enum AVPixelFormat pix_fmt, int width, int height, int align);
重點說明一個引數align:此引數是設定記憶體對齊的對齊數,也就是按多大的位元組進行記憶體對齊。比如設定為1,表示按1位元組對齊,那麼得到的結果就是與實際的記憶體大小一樣。再比如設定為4,表示按4位元組對齊。也就是記憶體的起始地址必須是4的整倍數。
ffmpeg中關於av_image_fill_array()函式的定義:
/**
* Setup the data pointers and linesizes based on the specified image
* parameters and the provided array.
*
* The fields of the given image are filled in by using the src
* address which points to the image data buffer. Depending on the
* specified pixel format, one or multiple image data pointers and
* line sizes will be set. If a planar format is specified, several
* pointers will be set pointing to the different picture planes and
* the line sizes of the different planes will be stored in the
* lines_sizes array. Call with src == NULL to get the required
* size for the src buffer.
*
* To allocate the buffer and fill in the dst_data and dst_linesize in
* one call, use av_image_alloc().
*
* @param dst_data data pointers to be filled in
* @param dst_linesize linesizes for the image in dst_data to be filled in
* @param src buffer which will contain or contains the actual image data, can be NULL
* @param pix_fmt the pixel format of the image
* @param width the width of the image in pixels
* @param height the height of the image in pixels
* @param align the value used in src for linesize alignment
* @return the size in bytes required for src, a negative error code
* in case of failure
*/
int av_image_fill_arrays(uint8_t *dst_data[4], int dst_linesize[4],
const uint8_t *src,
enum AVPixelFormat pix_fmt, int width, int height, int align);
av_image_fill_arrays()函式自身不具備記憶體申請的功能,此函式類似於格式化已經申請的記憶體,即通過av_malloc()函式申請的記憶體空間。
再者,av_image_fill_arrays()中引數具體說明:
dst_data[4]: [out]對申請的記憶體格式化為三個通道後,分別儲存其地址
dst_linesize[4]: [out]格式化的記憶體的步長(即記憶體對齊後的寬度)
*src: [in]av_alloc()函式申請的記憶體地址。
pix_fmt: [in] 申請 src記憶體時的畫素格式
width: [in]申請src記憶體時指定的寬度
height: [in]申請scr記憶體時指定的高度
align: [in]申請src記憶體時指定的對齊位元組數。
(1)呼叫例項1
image_buf_size = av_image_get_buffer_size(AV_PIX_FMT_YUV420P, 11, 5, 1); //按1位元組進行記憶體對齊,得到的記憶體大小最接近實際大小
printf("image_buf_size:%d\n",image_buf_size);
image_buf_size = av_image_get_buffer_size(AV_PIX_FMT_YUV420P, 11, 5, 0); //按0位元組進行記憶體對齊,得到的記憶體大小是0
printf("image_buf_size:%d\n",image_buf_size);
image_buf_size = av_image_get_buffer_size(AV_PIX_FMT_YUV420P, 11, 5, 4); //按4位元組進行記憶體對齊,得到的記憶體大小稍微大一些
printf("image_buf_size:%d\n",image_buf_size);
(2)呼叫例項2
img_convert_out_buffer = (unsigned char *)av_malloc(av_image_get_buffer_size(dst_pixfmt, dst_w, dst_h, 1));
av_image_fill_arrays(pFrameYUV->data,pFrameYUV->linesize, img_convert_out_buffer,dst_pixfmt, dst_w, dst_h, 1);
img_convert_ctx = sws_getContext(src_w, src_h, src_pixfmt,
dst_w, dst_h, dst_pixfmt,
SWS_BICUBIC, NULL, NULL, NULL);
(3)呼叫方法總結
通過以上例項可以看到,(a)計算所需記憶體大小av_image_get_bufferz_size() --> (b) 按計算的記憶體大小申請所需記憶體 av_malloc() --> (c) 對申請的記憶體進行格式化 av_image_fill_arrays();