FFmpeg
Main Page
Related Pages
Modules
Namespaces
Data Structures
Files
Examples
File List
Globals
•
All
Data Structures
Namespaces
Files
Functions
Variables
Typedefs
Enumerations
Enumerator
Macros
Groups
Pages
libavformat
replaygain.c
Go to the documentation of this file.
1
/*
2
* This file is part of FFmpeg.
3
*
4
* FFmpeg is free software; you can redistribute it and/or
5
* modify it under the terms of the GNU Lesser General Public
6
* License as published by the Free Software Foundation; either
7
* version 2.1 of the License, or (at your option) any later version.
8
*
9
* FFmpeg is distributed in the hope that it will be useful,
10
* but WITHOUT ANY WARRANTY; without even the implied warranty of
11
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12
* Lesser General Public License for more details.
13
*
14
* You should have received a copy of the GNU Lesser General Public
15
* License along with FFmpeg; if not, write to the Free Software
16
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
17
*/
18
19
/**
20
* @file
21
* replaygain tags parsing
22
*/
23
24
#include <stdint.h>
25
#include <stdlib.h>
26
#include <string.h>
27
28
#include "
libavutil/avstring.h
"
29
#include "
libavutil/dict.h
"
30
#include "
libavutil/intreadwrite.h
"
31
#include "
libavutil/mathematics.h
"
32
#include "
libavutil/mem.h
"
33
#include "
libavutil/replaygain.h
"
34
35
#include "
avformat.h
"
36
#include "
replaygain.h
"
37
38
static
int32_t
parse_value
(
const
char
*
value
,
int32_t
min
)
39
{
40
char
*fraction;
41
int
scale = 10000;
42
int32_t
mb
= 0;
43
int
sign = 1;
44
int
db;
45
46
if
(!value)
47
return
min
;
48
49
value += strspn(value,
" \t"
);
50
51
if
(*value ==
'-'
)
52
sign = -1;
53
54
db = strtol(value, &fraction, 0);
55
if
(*fraction++ ==
'.'
) {
56
while
(
av_isdigit
(*fraction) && scale) {
57
mb += scale * (*fraction -
'0'
);
58
scale /= 10;
59
fraction++;
60
}
61
}
62
63
if
(abs(db) > (INT32_MAX -
mb
) / 100000)
64
return
min
;
65
66
return
db * 100000 + sign *
mb
;
67
}
68
69
int
ff_replaygain_export_raw
(
AVStream
*st,
int32_t
tg
, uint32_t tp,
70
int32_t
ag, uint32_t ap)
71
{
72
AVPacketSideData
*sd, *tmp;
73
AVReplayGain
*replaygain;
74
int
i;
75
76
if
(tg == INT32_MIN && ag == INT32_MIN)
77
return
0;
78
79
for
(i = 0; i < st->
nb_side_data
; i++) {
80
AVPacketSideData
*src_sd = &st->
side_data
[i];
81
82
if
(src_sd->
type
==
AV_PKT_DATA_REPLAYGAIN
)
83
return
0;
84
}
85
86
replaygain =
av_mallocz
(
sizeof
(*replaygain));
87
if
(!replaygain)
88
return
AVERROR
(ENOMEM);
89
90
tmp =
av_realloc_array
(st->
side_data
, st->
nb_side_data
+ 1,
sizeof
(*tmp));
91
if
(!tmp) {
92
av_freep
(&replaygain);
93
return
AVERROR
(ENOMEM);
94
}
95
st->
side_data
= tmp;
96
st->
nb_side_data
++;
97
98
sd = &st->
side_data
[st->
nb_side_data
- 1];
99
sd->
type
=
AV_PKT_DATA_REPLAYGAIN
;
100
sd->
data
= (
uint8_t
*)replaygain;
101
sd->
size
=
sizeof
(*replaygain);
102
103
replaygain->
track_gain
=
tg
;
104
replaygain->
track_peak
= tp;
105
replaygain->
album_gain
= ag;
106
replaygain->
album_peak
= ap;
107
108
return
0;
109
}
110
111
int
ff_replaygain_export
(
AVStream
*st,
AVDictionary
*metadata)
112
{
113
const
AVDictionaryEntry
*
tg
, *tp, *ag, *ap;
114
115
tg =
av_dict_get
(metadata,
"REPLAYGAIN_TRACK_GAIN"
, NULL, 0);
116
tp =
av_dict_get
(metadata,
"REPLAYGAIN_TRACK_PEAK"
, NULL, 0);
117
ag =
av_dict_get
(metadata,
"REPLAYGAIN_ALBUM_GAIN"
, NULL, 0);
118
ap =
av_dict_get
(metadata,
"REPLAYGAIN_ALBUM_PEAK"
, NULL, 0);
119
120
return
ff_replaygain_export_raw
(st,
121
parse_value
(tg ? tg->
value
: NULL, INT32_MIN),
122
parse_value
(tp ? tp->
value
: NULL, 0),
123
parse_value
(ag ? ag->
value
: NULL, INT32_MIN),
124
parse_value
(ap ? ap->
value
: NULL, 0));
125
}
Generated on Sun Jul 20 2014 23:06:05 for FFmpeg by
1.8.2