3 * Copyright (c) 2003-2015 HandBrake Team
4 * This file is part of the HandBrake source code.
5 * Homepage: <http://handbrake.fr/>.
6 * It may be used under the terms of the GNU General Public License v2.
7 * For full terms see the file COPYING file or visit http://www.gnu.org/licenses/gpl-2.0.html
14 #include "nal_units.h"
16 static const uint8_t hb_annexb_startcode
[] = { 0x00, 0x00, 0x00, 0x01, };
18 size_t hb_nal_unit_write_annexb(uint8_t *buf
,
19 const uint8_t *nal_unit
,
20 const size_t nal_unit_size
)
24 memcpy(buf
, hb_annexb_startcode
, sizeof(hb_annexb_startcode
));
25 memcpy(buf
+ sizeof(hb_annexb_startcode
), nal_unit
, nal_unit_size
);
28 return sizeof(hb_annexb_startcode
) + nal_unit_size
;
31 size_t hb_nal_unit_write_isomp4(uint8_t *buf
,
32 const uint8_t *nal_unit
,
33 const size_t nal_unit_size
)
36 uint8_t length
[4]; // 4-byte length replaces Annex B start code prefix
40 for (i
= 0; i
< sizeof(length
); i
++)
42 length
[i
] = (nal_unit_size
>> (8 * (sizeof(length
) - 1 - i
))) & 0xff;
45 memcpy(buf
, &length
[0], sizeof(length
));
46 memcpy(buf
+ sizeof(length
), nal_unit
, nal_unit_size
);
49 return sizeof(length
) + nal_unit_size
;
52 uint8_t* hb_annexb_find_next_nalu(const uint8_t *start
, size_t *size
)
55 uint8_t *buf
= (uint8_t*)start
;
56 uint8_t *end
= (uint8_t*)start
+ *size
;
58 /* Look for an Annex B start code prefix (3-byte sequence == 1) */
61 if (!buf
[0] && !buf
[1] && buf
[2] == 1)
63 nal
= (buf
+= 3); // NAL unit begins after start code
76 * Start code prefix found, look for the next one to determine the size
78 * A 4-byte sequence == 1 is also a start code, so check for a 3-byte
79 * sequence == 0 too (start code emulation prevention will prevent such a
80 * sequence from occurring outside of a start code prefix)
84 if (!buf
[0] && !buf
[1] && (!buf
[2] || buf
[2] == 1))
96 hb_buffer_t
* hb_nal_bitstream_annexb_to_mp4(const uint8_t *data
,
101 size_t out_size
, buf_size
;
105 buf
= (uint8_t*)data
;
106 end
= (uint8_t*)data
+ size
;
108 while ((buf
= hb_annexb_find_next_nalu(buf
, &buf_size
)) != NULL
)
110 out_size
+= hb_nal_unit_write_isomp4(NULL
, buf
, buf_size
);
111 buf_size
= end
- buf
;
114 out
= hb_buffer_init(out_size
);
117 hb_error("hb_nal_bitstream_annexb_to_mp4: hb_buffer_init failed");
123 buf
= (uint8_t*)data
;
124 end
= (uint8_t*)data
+ size
;
126 while ((buf
= hb_annexb_find_next_nalu(buf
, &buf_size
)) != NULL
)
128 out_size
+= hb_nal_unit_write_isomp4(out
->data
+ out_size
, buf
, buf_size
);
129 buf_size
= end
- buf
;
135 static size_t mp4_nal_unit_length(const uint8_t *data
,
136 const size_t nal_length_size
,
137 size_t *nal_unit_length
)
141 /* In MP4, NAL units are preceded by a 2-4 byte length field */
142 for (i
= 0, *nal_unit_length
= 0; i
< nal_length_size
; i
++)
144 *nal_unit_length
|= data
[i
] << (8 * (nal_length_size
- 1 - i
));
147 return nal_length_size
;
150 hb_buffer_t
* hb_nal_bitstream_mp4_to_annexb(const uint8_t *data
,
152 const uint8_t nal_length_size
)
156 size_t out_size
, nal_size
;
159 buf
= (uint8_t*)data
;
160 end
= (uint8_t*)data
+ size
;
162 while (end
- buf
> nal_length_size
)
164 buf
+= mp4_nal_unit_length(buf
, nal_length_size
, &nal_size
);
165 if (end
- buf
< nal_size
)
167 hb_log("hb_nal_bitstream_mp4_to_annexb: truncated bitstream"
168 " (remaining: %lu, expected: %lu)", end
- buf
, nal_size
);
172 out_size
+= hb_nal_unit_write_annexb(NULL
, buf
, nal_size
);
176 out
= hb_buffer_init(out_size
);
179 hb_error("hb_nal_bitstream_mp4_to_annexb: hb_buffer_init failed");
184 buf
= (uint8_t*)data
;
185 end
= (uint8_t*)data
+ size
;
187 while (end
- buf
> nal_length_size
)
189 buf
+= mp4_nal_unit_length(buf
, nal_length_size
, &nal_size
);
190 out_size
+= hb_nal_unit_write_annexb(out
->data
+ out_size
, buf
, nal_size
);