moov box是个container box,读取box头部之后就开始读取子box了
/*** moov box的定义,包含:** mvhd、trak(cmov无意义)*/static mp4_atom_handler mp4_moov_atoms[] = { { "mvhd", &Mp4Meta::mp4_read_mvhd_atom }, { "trak", &Mp4Meta::mp4_read_trak_atom }, { "cmov", &Mp4Meta::mp4_read_cmov_atom }, { NULL, NULL }};读取moov box
// 读取moov boxintMp4Meta::mp4_read_moov_atom(int64_t atom_header_size, int64_t atom_data_size){ int64_t atom_size; int ret; if (mdat_atom.buffer != NULL) // not reasonable for streaming media return -1; atom_size = atom_header_size + atom_data_size; if (atom_data_size >= MP4_MAX_BUFFER_SIZE) return -1; if (meta_avail < atom_size) { // data unsufficient, wait return 0; } moov_atom.buffer = TSIOBufferCreate(); moov_atom.reader = TSIOBufferReaderAlloc(moov_atom.buffer); TSIOBufferCopy(moov_atom.buffer, meta_reader, atom_header_size, 0); mp4_meta_consume(atom_header_size); // 读取box,注意第一个参数是函数指针数组 ret = mp4_read_atom(mp4_moov_atoms, atom_data_size); return ret;}读取moov box的子box
读取子box,根据子box的名字分别调用:
1、mp4_read_mvhd_atom处理mvhd box
2、mp4_read_trak_atom处理trak box
3、mp4_read_cmov_atom处理cmov box
intMp4Meta::mp4_read_atom(mp4_atom_handler *atom, int64_t size){ int i, ret, rc; int64_t atom_size, atom_header_size; char buf[32]; char *atom_header, *atom_name; if (meta_avail < size) // data insufficient, not reasonable for internal atom box. return -1; while (size > 0) { if (meta_avail < (int64_t)sizeof(uint32_t)) // data insufficient, not reasonable for internal atom box. return -1; IOBufferReaderCopy(meta_reader, buf, sizeof(mp4_atom_header64)); atom_size = mp4_get_32value(buf); if (atom_size == 0) { return 1; } atom_header = buf; if (atom_size < (int64_t)sizeof(mp4_atom_header)) { if (atom_size == 1) { if (meta_avail < (int64_t)sizeof(mp4_atom_header64)) { return -1; } } else { return -1; } atom_size = mp4_get_64value(atom_header + 8); atom_header_size = sizeof(mp4_atom_header64); } else { // regular atom if (meta_avail < (int64_t)sizeof(mp4_atom_header)) return -1; atom_header_size = sizeof(mp4_atom_header); } atom_name = atom_header + 4; if (atom_size + this->passed > this->cl) { return -1; } // 根据mp4_moov_atoms的定义,下面会调用: // mp4_read_mvhd_atom处理mvhd、mp4_read_trak_atom处理trak、mp4_read_cmov_atom处理cmov for (i = 0; atom[i].name; i++) { if (memcmp(atom_name, atom[i].name, 4) == 0) { if (meta_avail < atom_size) return -1; ret = (this->*atom[i].handler)(atom_header_size, atom_size - atom_header_size); // -1: error, 0: success. if (ret < 0) { return ret; } goto next; } } // insignificant atom box rc = mp4_atom_next(atom_size, false); if (rc < 0) { return rc; }next: size -= atom_size; continue; } return 1;}
新闻热点
疑难解答