summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnton Khirnov <anton@khirnov.net>2012-02-25 18:05:55 +0100
committerAnton Khirnov <anton@khirnov.net>2012-02-29 14:16:25 +0100
commitdd2a4bcfd72eee85710142943a1c68ac02520771 (patch)
treec7bb50d89cf364659b550ed2ca910e9e87803fa5
parenta93b09cb45b86427d6e81fa51c660877d8d5fd17 (diff)
lavf: generic code for exporting attached pictures.
-rw-r--r--libavformat/avformat.h16
-rw-r--r--libavformat/utils.c46
2 files changed, 44 insertions, 18 deletions
diff --git a/libavformat/avformat.h b/libavformat/avformat.h
index 1aa18d8213..65ed376c89 100644
--- a/libavformat/avformat.h
+++ b/libavformat/avformat.h
@@ -530,6 +530,13 @@ typedef struct AVIndexEntry {
#define AV_DISPOSITION_HEARING_IMPAIRED 0x0080 /**< stream for hearing impaired audiences */
#define AV_DISPOSITION_VISUAL_IMPAIRED 0x0100 /**< stream for visual impaired audiences */
#define AV_DISPOSITION_CLEAN_EFFECTS 0x0200 /**< stream without voice */
+/**
+ * The stream is stored in the file as an attached picture/"cover art" (e.g.
+ * APIC frame in ID3v2). The single packet associated with it will be returned
+ * among the first few packets read from the file unless seeking takes place.
+ * It can also be accessed at any time in AVStream.attached_pic.
+ */
+#define AV_DISPOSITION_ATTACHED_PIC 0x0400
/**
* Stream structure.
@@ -602,6 +609,15 @@ typedef struct AVStream {
*/
AVRational avg_frame_rate;
+ /**
+ * For streams with AV_DISPOSITION_ATTACHED_PIC disposition, this packet
+ * will contain the attached picture.
+ *
+ * decoding: set by libavformat, must not be modified by the caller.
+ * encoding: unused
+ */
+ AVPacket attached_pic;
+
/*****************************************************************
* All fields below this line are not part of the public API. They
* may not be used outside of libavformat and can be changed and
diff --git a/libavformat/utils.c b/libavformat/utils.c
index 0f9c8b6293..c8dd7f5868 100644
--- a/libavformat/utils.c
+++ b/libavformat/utils.c
@@ -498,10 +498,27 @@ static int init_input(AVFormatContext *s, const char *filename, AVDictionary **o
return av_probe_input_buffer(s->pb, &s->iformat, filename, s, 0, 0);
}
+static AVPacket *add_to_pktbuf(AVPacketList **packet_buffer, AVPacket *pkt,
+ AVPacketList **plast_pktl){
+ AVPacketList *pktl = av_mallocz(sizeof(AVPacketList));
+ if (!pktl)
+ return NULL;
+
+ if (*packet_buffer)
+ (*plast_pktl)->next = pktl;
+ else
+ *packet_buffer = pktl;
+
+ /* add the packet in the buffered packet list */
+ *plast_pktl = pktl;
+ pktl->pkt= *pkt;
+ return &pktl->pkt;
+}
+
int avformat_open_input(AVFormatContext **ps, const char *filename, AVInputFormat *fmt, AVDictionary **options)
{
AVFormatContext *s = *ps;
- int ret = 0;
+ int i, ret = 0;
AVDictionary *tmp = NULL;
if (!s && !(s = avformat_alloc_context()))
@@ -551,6 +568,14 @@ int avformat_open_input(AVFormatContext **ps, const char *filename, AVInputForma
if ((ret = s->iformat->read_header(s)) < 0)
goto fail;
+ /* queue attached pictures */
+ for (i = 0; i < s->nb_streams; i++)
+ if (s->streams[i]->disposition & AV_DISPOSITION_ATTACHED_PIC) {
+ AVPacket copy = s->streams[i]->attached_pic;
+ copy.destruct = NULL;
+ add_to_pktbuf(&s->raw_packet_buffer, &copy, &s->raw_packet_buffer_end);
+ }
+
if (s->pb && !s->data_offset)
s->data_offset = avio_tell(s->pb);
@@ -574,23 +599,6 @@ fail:
/*******************************************************/
-static AVPacket *add_to_pktbuf(AVPacketList **packet_buffer, AVPacket *pkt,
- AVPacketList **plast_pktl){
- AVPacketList *pktl = av_mallocz(sizeof(AVPacketList));
- if (!pktl)
- return NULL;
-
- if (*packet_buffer)
- (*plast_pktl)->next = pktl;
- else
- *packet_buffer = pktl;
-
- /* add the packet in the buffered packet list */
- *plast_pktl = pktl;
- pktl->pkt= *pkt;
- return &pktl->pkt;
-}
-
int av_read_packet(AVFormatContext *s, AVPacket *pkt)
{
int ret, i;
@@ -2547,6 +2555,8 @@ void avformat_free_context(AVFormatContext *s)
av_parser_close(st->parser);
av_free_packet(&st->cur_pkt);
}
+ if (st->attached_pic.data)
+ av_free_packet(&st->attached_pic);
av_dict_free(&st->metadata);
av_free(st->index_entries);
av_free(st->codec->extradata);