1
0
Fork 0
mirror of https://github.com/alfg/mp4-rust.git synced 2024-05-30 05:28:05 +00:00

Add mp4dump example and update all mp4boxes with get_type and get_size methods.

This commit is contained in:
Alf 2020-08-23 22:11:59 -07:00
parent c4ff8627b0
commit d51a193272
25 changed files with 403 additions and 0 deletions

90
examples/mp4dump.rs Normal file
View file

@ -0,0 +1,90 @@
use std::env;
use std::fs::File;
use std::io::prelude::*;
use std::io::{self, BufReader};
use std::path::Path;
use mp4::{Result};
fn main() {
let args: Vec<String> = env::args().collect();
if args.len() < 2 {
println!("Usage: mp4dump <filename>");
std::process::exit(1);
}
if let Err(err) = dump(&args[1]) {
let _ = writeln!(io::stderr(), "{}", err);
}
}
fn dump<P: AsRef<Path>>(filename: &P) -> Result<()> {
let f = File::open(filename)?;
let size = f.metadata()?.len();
let reader = BufReader::new(f);
let mp4 = mp4::Mp4Reader::read_header(reader, size)?;
// ftyp
println!("[{}] size={} ", mp4.ftyp.get_type(), mp4.ftyp.get_size());
// moov
println!("[{}] size={} ", mp4.moov.get_type(), mp4.moov.get_size());
println!(" [{}] size={} ", mp4.moov.mvhd.get_type(), mp4.moov.mvhd.get_size());
// Tracks.
for track in mp4.tracks().iter() {
// trak
println!(" [{}] size={} ", track.trak.get_type(), track.trak.get_size());
println!(" [{}] size={} ", track.trak.tkhd.get_type(), track.trak.tkhd.get_size());
if let Some(ref edts) = track.trak.edts {
println!(" [{}] size={} ", edts.get_type(), edts.get_size());
if let Some(ref elst) = edts.elst {
println!(" [{}] size={} ", elst.get_type(), elst.get_size());
}
}
// trak.mdia.
println!(" [{}] size={} ", track.trak.mdia.get_type(), track.trak.mdia.get_size());
println!(" [{}] size={} ", track.trak.mdia.mdhd.get_type(), track.trak.mdia.mdhd.get_size());
println!(" [{}] size={} ", track.trak.mdia.hdlr.get_type(), track.trak.mdia.hdlr.get_size());
println!(" [{}] size={} ", track.trak.mdia.minf.get_type(), track.trak.mdia.minf.get_size());
// trak.mdia.minf
if let Some(ref vmhd) = track.trak.mdia.minf.vmhd {
println!(" [{}] size={} ", vmhd.get_type(), vmhd.get_size());
}
if let Some(ref smhd) = track.trak.mdia.minf.smhd {
println!(" [{}] size={} ", smhd.get_type(), smhd.get_size());
}
// trak.mdia.minf.stbl
println!(" [{}] size={} ", track.trak.mdia.minf.stbl.get_type(), track.trak.mdia.minf.stbl.get_size());
println!(" [{}] size={} ", track.trak.mdia.minf.stbl.stsd.get_type(), track.trak.mdia.minf.stbl.stsd.get_size());
if let Some(ref avc1) = track.trak.mdia.minf.stbl.stsd.avc1 {
println!(" [{}] size={} ", avc1.get_type(), avc1.get_size());
}
if let Some(ref mp4a) = track.trak.mdia.minf.stbl.stsd.mp4a {
println!(" [{}] size={} ", mp4a.get_type(), mp4a.get_size());
}
println!(" [{}] size={} ", track.trak.mdia.minf.stbl.stts.get_type(), track.trak.mdia.minf.stbl.stts.get_size());
if let Some(ref ctts) = track.trak.mdia.minf.stbl.ctts {
println!(" [{}] size={} ", ctts.get_type(), ctts.get_size());
}
if let Some(ref stss) = track.trak.mdia.minf.stbl.stss {
println!(" [{}] size={} ", stss.get_type(), stss.get_size());
}
println!(" [{}] size={} ", track.trak.mdia.minf.stbl.stsc.get_type(), track.trak.mdia.minf.stbl.stsc.get_size());
println!(" [{}] size={} ", track.trak.mdia.minf.stbl.stsz.get_type(), track.trak.mdia.minf.stbl.stsz.get_size());
if let Some(ref stco) = track.trak.mdia.minf.stbl.stco {
println!(" [{}] size={} ", stco.get_type(), stco.get_size());
}
if let Some(ref co64) = track.trak.mdia.minf.stbl.co64 {
println!(" [{}] size={} ", co64.get_type(), co64.get_size());
}
}
Ok(())
}

View file

@ -43,6 +43,14 @@ impl Avc1Box {
avcc: AvcCBox::new(&config.seq_param_set, &config.pic_param_set),
}
}
pub fn get_type(&self) -> BoxType {
BoxType::Avc1Box
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + 8 + 70 + self.avcc.box_size()
}
}
impl Mp4Box for Avc1Box {

View file

@ -10,6 +10,16 @@ pub struct Co64Box {
pub entries: Vec<u64>,
}
impl Co64Box {
pub fn get_type(&self) -> BoxType {
BoxType::Co64Box
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (8 * self.entries.len() as u64)
}
}
impl Mp4Box for Co64Box {
fn box_type() -> BoxType {
BoxType::Co64Box

View file

@ -10,6 +10,16 @@ pub struct CttsBox {
pub entries: Vec<CttsEntry>,
}
impl CttsBox {
pub fn get_type(&self) -> BoxType {
BoxType::CttsBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (8 * self.entries.len() as u64)
}
}
#[derive(Debug, Clone, PartialEq, Default)]
pub struct CttsEntry {
pub sample_count: u32,

View file

@ -12,6 +12,18 @@ impl EdtsBox {
pub(crate) fn new() -> EdtsBox {
Default::default()
}
pub fn get_type(&self) -> BoxType {
BoxType::EdtsBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE;
if let Some(ref elst) = self.elst {
size += elst.box_size();
}
size
}
}
impl Mp4Box for EdtsBox {

View file

@ -18,6 +18,23 @@ pub struct ElstEntry {
pub media_rate_fraction: u16,
}
impl ElstBox {
pub fn get_type(&self) -> BoxType {
BoxType::ElstBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + HEADER_EXT_SIZE + 4;
if self.version == 1 {
size += self.entries.len() as u64 * 20;
} else {
assert_eq!(self.version, 0);
size += self.entries.len() as u64 * 12;
}
size
}
}
impl Mp4Box for ElstBox {
fn box_type() -> BoxType {
BoxType::ElstBox

View file

@ -10,6 +10,16 @@ pub struct FtypBox {
pub compatible_brands: Vec<FourCC>,
}
impl FtypBox {
pub fn get_type(&self) -> BoxType {
BoxType::FtypBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + 8 + (4 * self.compatible_brands.len() as u64)
}
}
impl Mp4Box for FtypBox {
fn box_type() -> BoxType {
BoxType::FtypBox

View file

@ -11,6 +11,16 @@ pub struct HdlrBox {
pub name: String,
}
impl HdlrBox {
pub fn get_type(&self) -> BoxType {
BoxType::HdlrBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 20 + self.name.len() as u64 + 1
}
}
impl Mp4Box for HdlrBox {
fn box_type() -> BoxType {
BoxType::HdlrBox

View file

@ -15,6 +15,25 @@ pub struct MdhdBox {
pub language: String,
}
impl MdhdBox {
pub fn get_type(&self) -> BoxType {
BoxType::MdhdBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + HEADER_EXT_SIZE;
if self.version == 1 {
size += 28;
} else {
assert_eq!(self.version, 0);
size += 16;
}
size += 4;
size
}
}
impl Default for MdhdBox {
fn default() -> Self {
MdhdBox {

View file

@ -10,6 +10,16 @@ pub struct MdiaBox {
pub minf: MinfBox,
}
impl MdiaBox {
pub fn get_type(&self) -> BoxType {
BoxType::MdiaBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + self.mdhd.box_size() + self.hdlr.box_size() + self.minf.box_size()
}
}
impl Mp4Box for MdiaBox {
fn box_type() -> BoxType {
BoxType::MdiaBox

View file

@ -10,6 +10,24 @@ pub struct MinfBox {
pub stbl: StblBox,
}
impl MinfBox {
pub fn get_type(&self) -> BoxType {
BoxType::MinfBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE;
if let Some(ref vmhd) = self.vmhd {
size += vmhd.box_size();
}
if let Some(ref smhd) = self.smhd {
size += smhd.box_size();
}
size += self.stbl.box_size();
size
}
}
impl Mp4Box for MinfBox {
fn box_type() -> BoxType {
BoxType::MinfBox

View file

@ -9,6 +9,20 @@ pub struct MoovBox {
pub traks: Vec<TrakBox>,
}
impl MoovBox {
pub fn get_type(&self) -> BoxType {
BoxType::MoovBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + self.mvhd.box_size();
for trak in self.traks.iter() {
size += trak.box_size();
}
size
}
}
impl Mp4Box for MoovBox {
fn box_type() -> BoxType {
BoxType::MoovBox

View file

@ -34,6 +34,18 @@ impl Mp4aBox {
esds: Some(EsdsBox::new(config)),
}
}
pub fn get_type(&self) -> BoxType {
BoxType::Mp4aBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + 8 + 20;
if let Some(ref esds) = self.esds {
size += esds.box_size();
}
size
}
}
impl Mp4Box for Mp4aBox {

View file

@ -14,6 +14,24 @@ pub struct MvhdBox {
pub rate: FixedPointU16,
}
impl MvhdBox {
pub fn get_type(&self) -> BoxType {
BoxType::MvhdBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + HEADER_EXT_SIZE;
if self.version == 1 {
size += 28;
} else {
assert_eq!(self.version, 0);
size += 16;
}
size += 80;
size
}
}
impl Default for MvhdBox {
fn default() -> Self {
MvhdBox {

View file

@ -10,6 +10,16 @@ pub struct SmhdBox {
pub balance: FixedPointI8,
}
impl SmhdBox {
pub fn get_type(&self) -> BoxType {
BoxType::SmhdBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4
}
}
impl Default for SmhdBox {
fn default() -> Self {
SmhdBox {

View file

@ -18,6 +18,33 @@ pub struct StblBox {
pub co64: Option<Co64Box>,
}
impl StblBox {
pub fn get_type(&self) -> BoxType {
BoxType::StblBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE;
size += self.stsd.box_size();
size += self.stts.box_size();
if let Some(ref ctts) = self.ctts {
size += ctts.box_size();
}
if let Some(ref stss) = self.stss {
size += stss.box_size();
}
size += self.stsc.box_size();
size += self.stsz.box_size();
if let Some(ref stco) = self.stco {
size += stco.box_size();
}
if let Some(ref co64) = self.co64 {
size += co64.box_size();
}
size
}
}
impl Mp4Box for StblBox {
fn box_type() -> BoxType {
BoxType::StblBox

View file

@ -10,6 +10,16 @@ pub struct StcoBox {
pub entries: Vec<u32>,
}
impl StcoBox {
pub fn get_type(&self) -> BoxType {
BoxType::StcoBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (4 * self.entries.len() as u64)
}
}
impl Mp4Box for StcoBox {
fn box_type() -> BoxType {
BoxType::StcoBox

View file

@ -10,6 +10,16 @@ pub struct StscBox {
pub entries: Vec<StscEntry>,
}
impl StscBox {
pub fn get_type(&self) -> BoxType {
BoxType::StscBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (12 * self.entries.len() as u64)
}
}
#[derive(Debug, Clone, PartialEq, Default)]
pub struct StscEntry {
pub first_chunk: u32,

View file

@ -12,6 +12,22 @@ pub struct StsdBox {
pub mp4a: Option<Mp4aBox>,
}
impl StsdBox {
pub fn get_type(&self) -> BoxType {
BoxType::StsdBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + HEADER_EXT_SIZE + 4;
if let Some(ref avc1) = self.avc1 {
size += avc1.box_size();
} else if let Some(ref mp4a) = self.mp4a {
size += mp4a.box_size();
}
size
}
}
impl Mp4Box for StsdBox {
fn box_type() -> BoxType {
BoxType::StsdBox

View file

@ -10,6 +10,16 @@ pub struct StssBox {
pub entries: Vec<u32>,
}
impl StssBox {
pub fn get_type(&self) -> BoxType {
BoxType::StssBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (4 * self.entries.len() as u64)
}
}
impl Mp4Box for StssBox {
fn box_type() -> BoxType {
BoxType::StssBox

View file

@ -12,6 +12,16 @@ pub struct StszBox {
pub sample_sizes: Vec<u32>,
}
impl StszBox {
pub fn get_type(&self) -> BoxType {
BoxType::StszBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 8 + (4 * self.sample_sizes.len() as u64)
}
}
impl Mp4Box for StszBox {
fn box_type() -> BoxType {
BoxType::StszBox

View file

@ -10,6 +10,16 @@ pub struct SttsBox {
pub entries: Vec<SttsEntry>,
}
impl SttsBox {
pub fn get_type(&self) -> BoxType {
BoxType::SttsBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 4 + (8 * self.entries.len() as u64)
}
}
#[derive(Debug, Clone, PartialEq, Default)]
pub struct SttsEntry {
pub sample_count: u32,

View file

@ -52,6 +52,22 @@ pub struct Matrix {
}
impl TkhdBox {
pub fn get_type(&self) -> BoxType {
BoxType::TkhdBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE + HEADER_EXT_SIZE;
if self.version == 1 {
size += 32;
} else {
assert_eq!(self.version, 0);
size += 20;
}
size += 60;
size
}
pub fn set_width(&mut self, width: u16) {
self.width = FixedPointU16::new(width);
}

View file

@ -10,6 +10,22 @@ pub struct TrakBox {
pub mdia: MdiaBox,
}
impl TrakBox {
pub fn get_type(&self) -> BoxType {
BoxType::TrakBox
}
pub fn get_size(&self) -> u64 {
let mut size = HEADER_SIZE;
size += self.tkhd.box_size();
if let Some(ref edts) = self.edts {
size += edts.box_size();
}
size += self.mdia.box_size();
size
}
}
impl Mp4Box for TrakBox {
fn box_type() -> BoxType {
BoxType::TrakBox

View file

@ -18,6 +18,16 @@ pub struct RgbColor {
pub blue: u16,
}
impl VmhdBox {
pub fn get_type(&self) -> BoxType {
BoxType::VmhdBox
}
pub fn get_size(&self) -> u64 {
HEADER_SIZE + HEADER_EXT_SIZE + 8
}
}
impl Mp4Box for VmhdBox {
fn box_type() -> BoxType {
BoxType::VmhdBox