Skip to content

Commit

Permalink
Merge pull request #834 from DolbyLaboratories/dolby/ac4_fix
Browse files Browse the repository at this point in the history
fix AC4 memory leaks.
  • Loading branch information
barbibulle committed May 20, 2023
2 parents d2c1ab6 + 4371ab5 commit 4a45f65
Show file tree
Hide file tree
Showing 3 changed files with 43 additions and 19 deletions.
59 changes: 40 additions & 19 deletions Source/C++/Codecs/Ap4Ac4Parser.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -119,7 +119,7 @@ AP4_Ac4Header::AP4_Ac4Header(const AP4_UI08* bytes, unsigned int size)
unsigned int firstPresentationNSubstreamGroups = 0;

if (m_NPresentations > 0){
m_PresentationV1= new AP4_Dac4Atom::Ac4Dsi::PresentationV1[m_NPresentations];
m_PresentationV1 = new AP4_Dac4Atom::Ac4Dsi::PresentationV1[m_NPresentations];
AP4_SetMemory(m_PresentationV1, 0, m_NPresentations * sizeof(m_PresentationV1[0]));
} else {
m_PresentationV1 = NULL;
Expand Down Expand Up @@ -168,7 +168,7 @@ AP4_Ac4Header::AP4_Ac4Header(const AP4_UI08* bytes, unsigned int size)
m_PresentationV1[pres_idx].d.v1.dolby_atmos_indicator |= m_PresentationV1[pres_idx].d.v1.substream_groups[sg].d.v1.dolby_atmos_indicator;
}
}
delete[] substream_groups;
delete [] substream_groups;

if (bObjorAjoc == 0){
m_ChannelCount = AP4_Ac4ChannelCountFromSpeakerGroupIndexMask(speakerGroupIndexMask);
Expand All @@ -178,6 +178,22 @@ AP4_Ac4Header::AP4_Ac4Header(const AP4_UI08* bytes, unsigned int size)
}
}

AP4_Ac4Header::~AP4_Ac4Header()
{
if (m_PresentationV1) {
assert(m_PresentationV1 != NULL);
for (unsigned int pres_idx = 0; pres_idx < m_NPresentations; pres_idx++) {
assert(m_PresentationV1[pres_idx].d.v1.substream_groups != NULL);
for (int j = 0; j < m_PresentationV1[pres_idx].d.v1.n_substream_groups; j++)
delete[] m_PresentationV1[pres_idx].d.v1.substream_groups[j].d.v1.substreams;
delete[] m_PresentationV1[pres_idx].d.v1.substream_groups;
delete[] m_PresentationV1[pres_idx].d.v1.substream_group_indexs;
}
delete[] m_PresentationV1;
}
}


/*----------------------------------------------------------------------+
| AP4_Ac4Header::MatchFixed
|
Expand Down Expand Up @@ -352,7 +368,7 @@ AP4_Result
AP4_Ac4Parser::FindFrame(AP4_Ac4Frame& frame)
{
unsigned int available;
unsigned char *raw_header = new unsigned char[AP4_AC4_HEADER_SIZE];
unsigned char raw_header[AP4_AC4_HEADER_SIZE];
AP4_Result result;

/* align to the start of the next byte */
Expand All @@ -369,8 +385,6 @@ AP4_Ac4Parser::FindFrame(AP4_Ac4Frame& frame)
return AP4_ERROR_NOT_ENOUGH_DATA;
}

delete[] raw_header;
raw_header = new unsigned char[sync_frame_size];
/*
* Error handling to skip the 'fake' sync word.
* - the maximum sync frame size is about (AP4_BITSTREAM_BUFFER_SIZE - 1) bytes.
Expand All @@ -382,10 +396,15 @@ AP4_Ac4Parser::FindFrame(AP4_Ac4Frame& frame)
}
return AP4_ERROR_NOT_ENOUGH_DATA;
}

unsigned char *rawframe = new unsigned char[sync_frame_size];

// copy the whole frame becasue toc size is unknown
m_Bits.PeekBytes(raw_header, sync_frame_size);
m_Bits.PeekBytes(rawframe, sync_frame_size);
/* parse the header */
AP4_Ac4Header ac4_header(raw_header, sync_frame_size);
AP4_Ac4Header ac4_header(rawframe, sync_frame_size);

delete[] rawframe;

// Place before goto statement to resolve Xcode compiler issue
unsigned int bit_rate_mode = 0;
Expand All @@ -402,39 +421,41 @@ AP4_Ac4Parser::FindFrame(AP4_Ac4Frame& frame)
// TODO: find the proper AP4_AC4_MAX_TOC_SIZE or just parse what this step need ?
if (available >= ac4_header.m_FrameSize + ac4_header.m_HeaderSize + ac4_header.m_CrcSize + AP4_AC4_HEADER_SIZE + AP4_AC4_MAX_TOC_SIZE) {
// enough to peek at the header of the next frame
unsigned char *peek_raw_header = new unsigned char[AP4_AC4_HEADER_SIZE];

m_Bits.SkipBytes(ac4_header.m_FrameSize + ac4_header.m_HeaderSize + ac4_header.m_CrcSize);
m_Bits.PeekBytes(peek_raw_header, AP4_AC4_HEADER_SIZE);
m_Bits.PeekBytes(raw_header, AP4_AC4_HEADER_SIZE);

// duplicated work, just to get the frame size
AP4_BitReader peak_tmp_bits(peek_raw_header, AP4_AC4_HEADER_SIZE);
unsigned int peak_sync_frame_size = GetSyncFrameSize(peak_tmp_bits);
AP4_BitReader peak_tmp_bits(raw_header, AP4_AC4_HEADER_SIZE);
unsigned int next_sync_frame_size = GetSyncFrameSize(peak_tmp_bits);

unsigned char *next_rawframe = new unsigned char[next_sync_frame_size];

delete[] peek_raw_header;
peek_raw_header = new unsigned char[peak_sync_frame_size];
// copy the whole frame becasue toc size is unknown
if (m_Bits.GetBytesAvailable() < (peak_sync_frame_size)) {
peak_sync_frame_size = m_Bits.GetBytesAvailable();
if (m_Bits.GetBytesAvailable() < (next_sync_frame_size)) {
next_sync_frame_size = m_Bits.GetBytesAvailable();
}
m_Bits.PeekBytes(peek_raw_header, peak_sync_frame_size);
m_Bits.PeekBytes(next_rawframe, next_sync_frame_size);

m_Bits.SkipBytes(-((int)(ac4_header.m_FrameSize + ac4_header.m_HeaderSize + ac4_header.m_CrcSize)));

/* check the header */
AP4_Ac4Header peek_ac4_header(peek_raw_header, peak_sync_frame_size);
AP4_Ac4Header peek_ac4_header(next_rawframe, next_sync_frame_size);

delete[] next_rawframe;

result = peek_ac4_header.Check();
if (AP4_FAILED(result)) {
// TODO: need to reserve current sync frame ?
m_Bits.SkipBytes(sync_frame_size + peak_sync_frame_size);
m_Bits.SkipBytes(sync_frame_size + next_sync_frame_size);
goto fail;
}

/* check that the fixed part of this header is the same as the */
/* fixed part of the previous header */
if (!AP4_Ac4Header::MatchFixed(ac4_header, peek_ac4_header)) {
// TODO: need to reserve current sync frame ?
m_Bits.SkipBytes(sync_frame_size + peak_sync_frame_size);
m_Bits.SkipBytes(sync_frame_size + next_sync_frame_size);
goto fail;
}
} else if (available < (ac4_header.m_FrameSize + ac4_header.m_HeaderSize + ac4_header.m_CrcSize) || (m_Bits.m_Flags & AP4_BITSTREAM_FLAG_EOS) == 0) {
Expand Down
2 changes: 2 additions & 0 deletions Source/C++/Codecs/Ap4Ac4Parser.h
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,8 @@ class AP4_Ac4Header {
public:
// constructor
AP4_Ac4Header(const AP4_UI08* bytes, unsigned int size);
// destructor
~AP4_Ac4Header();

// methods
AP4_Result Check();
Expand Down
1 change: 1 addition & 0 deletions Source/C++/Core/Ap4Dac4Atom.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -418,6 +418,7 @@ AP4_Dac4Atom::~AP4_Dac4Atom()
delete[] m_Dsi.d.v1.presentations[i].d.v1.substream_groups[j].d.v1.substreams;
}
delete[] m_Dsi.d.v1.presentations[i].d.v1.substream_groups;
delete[] m_Dsi.d.v1.presentations[i].d.v1.substream_group_indexs;
}
delete[] m_Dsi.d.v1.presentations;
}
Expand Down

0 comments on commit 4a45f65

Please sign in to comment.