FFmpeg
Main Page
Related Pages
Modules
Data Structures
Files
Examples
File List
Globals
All
Data Structures
Files
Functions
Variables
Typedefs
Enumerations
Enumerator
Macros
Groups
Pages
libavformat
aiffenc.c
Go to the documentation of this file.
1
/*
2
* AIFF/AIFF-C muxer
3
* Copyright (c) 2006 Patrick Guimond
4
*
5
* This file is part of FFmpeg.
6
*
7
* FFmpeg is free software; you can redistribute it and/or
8
* modify it under the terms of the GNU Lesser General Public
9
* License as published by the Free Software Foundation; either
10
* version 2.1 of the License, or (at your option) any later version.
11
*
12
* FFmpeg is distributed in the hope that it will be useful,
13
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15
* Lesser General Public License for more details.
16
*
17
* You should have received a copy of the GNU Lesser General Public
18
* License along with FFmpeg; if not, write to the Free Software
19
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
20
*/
21
22
#include "
libavutil/intfloat.h
"
23
#include "
avformat.h
"
24
#include "
internal.h
"
25
#include "
aiff.h
"
26
#include "
avio_internal.h
"
27
#include "
isom.h
"
28
#include "
rawenc.h
"
29
30
typedef
struct
{
31
int64_t
form
;
32
int64_t
frames
;
33
int64_t
ssnd
;
34
}
AIFFOutputContext
;
35
36
static
void
put_meta
(
AVFormatContext
*s,
const
char
*key, uint32_t
id
)
37
{
38
AVDictionaryEntry
*
tag
;
39
AVIOContext
*pb = s->
pb
;
40
41
if
(tag =
av_dict_get
(s->
metadata
, key,
NULL
, 0)) {
42
int
size
= strlen(tag->
value
);
43
44
avio_wl32
(pb,
id
);
45
avio_wb32
(pb,
FFALIGN
(size, 2));
46
avio_write
(pb, tag->
value
, size);
47
if
(size & 1)
48
avio_w8
(pb, 0);
49
}
50
}
51
52
static
int
aiff_write_header
(
AVFormatContext
*s)
53
{
54
AIFFOutputContext
*aiff = s->
priv_data
;
55
AVIOContext
*pb = s->
pb
;
56
AVCodecContext
*enc = s->
streams
[0]->
codec
;
57
uint64_t
sample_rate
;
58
int
aifc = 0;
59
60
/* First verify if format is ok */
61
if
(!enc->
codec_tag
)
62
return
-1;
63
if
(enc->
codec_tag
!=
MKTAG
(
'N'
,
'O'
,
'N'
,
'E'
))
64
aifc = 1;
65
66
/* FORM AIFF header */
67
ffio_wfourcc
(pb,
"FORM"
);
68
aiff->
form
=
avio_tell
(pb);
69
avio_wb32
(pb, 0);
/* file length */
70
ffio_wfourcc
(pb, aifc ?
"AIFC"
:
"AIFF"
);
71
72
if
(aifc) {
// compressed audio
73
if
(!enc->
block_align
) {
74
av_log
(s,
AV_LOG_ERROR
,
"block align not set\n"
);
75
return
-1;
76
}
77
/* Version chunk */
78
ffio_wfourcc
(pb,
"FVER"
);
79
avio_wb32
(pb, 4);
80
avio_wb32
(pb, 0xA2805140);
81
}
82
83
if
(enc->
channels
> 2 && enc->
channel_layout
) {
84
ffio_wfourcc
(pb,
"CHAN"
);
85
avio_wb32
(pb, 12);
86
ff_mov_write_chan
(pb, enc->
channel_layout
);
87
}
88
89
put_meta
(s,
"title"
,
MKTAG
(
'N'
,
'A'
,
'M'
,
'E'
));
90
put_meta
(s,
"author"
,
MKTAG
(
'A'
,
'U'
,
'T'
,
'H'
));
91
put_meta
(s,
"copyright"
,
MKTAG
(
'('
,
'c'
,
')'
,
' '
));
92
put_meta
(s,
"comment"
,
MKTAG
(
'A'
,
'N'
,
'N'
,
'O'
));
93
94
/* Common chunk */
95
ffio_wfourcc
(pb,
"COMM"
);
96
avio_wb32
(pb, aifc ? 24 : 18);
/* size */
97
avio_wb16
(pb, enc->
channels
);
/* Number of channels */
98
99
aiff->
frames
=
avio_tell
(pb);
100
avio_wb32
(pb, 0);
/* Number of frames */
101
102
if
(!enc->
bits_per_coded_sample
)
103
enc->
bits_per_coded_sample
=
av_get_bits_per_sample
(enc->
codec_id
);
104
if
(!enc->
bits_per_coded_sample
) {
105
av_log
(s,
AV_LOG_ERROR
,
"could not compute bits per sample\n"
);
106
return
-1;
107
}
108
if
(!enc->
block_align
)
109
enc->
block_align
= (enc->
bits_per_coded_sample
* enc->
channels
) >> 3;
110
111
avio_wb16
(pb, enc->
bits_per_coded_sample
);
/* Sample size */
112
113
sample_rate =
av_double2int
(enc->
sample_rate
);
114
avio_wb16
(pb, (sample_rate >> 52) + (16383 - 1023));
115
avio_wb64
(pb, UINT64_C(1) << 63 | sample_rate << 11);
116
117
if
(aifc) {
118
avio_wl32
(pb, enc->
codec_tag
);
119
avio_wb16
(pb, 0);
120
}
121
122
if
(enc->
codec_tag
==
MKTAG
(
'Q'
,
'D'
,
'M'
,
'2'
) && enc->
extradata_size
) {
123
ffio_wfourcc
(pb,
"wave"
);
124
avio_wb32
(pb, enc->
extradata_size
);
125
avio_write
(pb, enc->
extradata
, enc->
extradata_size
);
126
}
127
128
/* Sound data chunk */
129
ffio_wfourcc
(pb,
"SSND"
);
130
aiff->
ssnd
=
avio_tell
(pb);
/* Sound chunk size */
131
avio_wb32
(pb, 0);
/* Sound samples data size */
132
avio_wb32
(pb, 0);
/* Data offset */
133
avio_wb32
(pb, 0);
/* Block-size (block align) */
134
135
avpriv_set_pts_info
(s->
streams
[0], 64, 1, s->
streams
[0]->
codec
->
sample_rate
);
136
137
/* Data is starting here */
138
avio_flush
(pb);
139
140
return
0;
141
}
142
143
static
int
aiff_write_trailer
(
AVFormatContext
*s)
144
{
145
AVIOContext
*pb = s->
pb
;
146
AIFFOutputContext
*aiff = s->
priv_data
;
147
AVCodecContext
*enc = s->
streams
[0]->
codec
;
148
149
/* Chunks sizes must be even */
150
int64_t file_size, end_size;
151
end_size = file_size =
avio_tell
(pb);
152
if
(file_size & 1) {
153
avio_w8
(pb, 0);
154
end_size++;
155
}
156
157
if
(s->
pb
->
seekable
) {
158
/* File length */
159
avio_seek
(pb, aiff->
form
, SEEK_SET);
160
avio_wb32
(pb, file_size - aiff->
form
- 4);
161
162
/* Number of sample frames */
163
avio_seek
(pb, aiff->
frames
, SEEK_SET);
164
avio_wb32
(pb, (file_size-aiff->
ssnd
-12)/enc->
block_align
);
165
166
/* Sound Data chunk size */
167
avio_seek
(pb, aiff->
ssnd
, SEEK_SET);
168
avio_wb32
(pb, file_size - aiff->
ssnd
- 4);
169
170
/* return to the end */
171
avio_seek
(pb, end_size, SEEK_SET);
172
173
avio_flush
(pb);
174
}
175
176
return
0;
177
}
178
179
AVOutputFormat
ff_aiff_muxer
= {
180
.
name
=
"aiff"
,
181
.long_name =
NULL_IF_CONFIG_SMALL
(
"Audio IFF"
),
182
.mime_type =
"audio/aiff"
,
183
.extensions =
"aif,aiff,afc,aifc"
,
184
.priv_data_size =
sizeof
(
AIFFOutputContext
),
185
.audio_codec =
AV_CODEC_ID_PCM_S16BE
,
186
.video_codec =
AV_CODEC_ID_NONE
,
187
.
write_header
=
aiff_write_header
,
188
.
write_packet
=
ff_raw_write_packet
,
189
.
write_trailer
=
aiff_write_trailer
,
190
.codec_tag = (
const
AVCodecTag
*
const
[]){
ff_codec_aiff_tags
, 0 },
191
};
Generated on Sat May 25 2013 03:58:46 for FFmpeg by
1.8.2