Skip to content

Commit

Permalink
BBufferGroup: Check for duplicated buffer id
Browse files Browse the repository at this point in the history
* This exclude some possible cheating cases.
  It impose to have only a buffer_id per thread,
  so instances will not be duplicated if not needed.
  • Loading branch information
Numerio committed Jul 11, 2015
1 parent 0341eac commit 1cc20d8
Show file tree
Hide file tree
Showing 3 changed files with 68 additions and 30 deletions.
7 changes: 7 additions & 0 deletions headers/private/media/SharedBufferList.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,8 +27,15 @@ class SharedBufferList
status_t Lock();
status_t Unlock();

status_t AddBuffer(sem_id groupReclaimSem,
const buffer_clone_info& info,
BBuffer** buffer);

// Call AddBuffer and CheckID locked
status_t AddBuffer(sem_id groupReclaimSem,
BBuffer* buffer);
status_t CheckID(sem_id groupSem,
media_buffer_id id) const;

status_t RequestBuffer(sem_id groupReclaimSem,
int32 buffersInGroup, size_t size,
Expand Down
22 changes: 1 addition & 21 deletions src/kits/media/BufferGroup.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -150,32 +150,12 @@ BBufferGroup::AddBuffer(const buffer_clone_info& info, BBuffer** _buffer)
if (fInitError != B_OK)
return B_NO_INIT;

// TODO: we need to make sure that a media_buffer_id is only added
// once to each group

BBuffer* buffer = new(std::nothrow) BBuffer(info);
if (buffer == NULL)
return B_NO_MEMORY;

if (buffer->Data() == NULL) {
// BBuffer::Data() will return NULL if an error occured
ERROR("BBufferGroup: error while creating buffer\n");
delete buffer;
return B_ERROR;
}

status_t status = fBufferList->AddBuffer(fReclaimSem, buffer);
status_t status = fBufferList->AddBuffer(fReclaimSem, info, _buffer);
if (status != B_OK) {
ERROR("BBufferGroup: error when adding buffer\n");
delete buffer;
return status;
}

atomic_add(&fBufferCount, 1);

if (_buffer != NULL)
*_buffer = buffer;

return B_OK;
}

Expand Down
69 changes: 60 additions & 9 deletions src/kits/media/SharedBufferList.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -162,6 +162,46 @@ SharedBufferList::Unlock()
}


status_t
SharedBufferList::AddBuffer(sem_id groupReclaimSem,
const buffer_clone_info& info, BBuffer** _buffer)
{
status_t status = Lock();
if (status != B_OK)
return status;

// Check if the id exists
status = CheckID(groupReclaimSem, info.buffer);
if (status != B_OK) {
Unlock();
return status;
}
BBuffer* buffer = new(std::nothrow) BBuffer(info);
if (buffer == NULL) {
Unlock();
return B_NO_MEMORY;
}

if (buffer->Data() == NULL) {
// BBuffer::Data() will return NULL if an error occured
ERROR("BBufferGroup: error while creating buffer\n");
delete buffer;
Unlock();
return B_ERROR;
}

status = AddBuffer(groupReclaimSem, buffer);
if (status != B_OK) {
delete buffer;
Unlock();
return status;
} else if (_buffer != NULL)
*_buffer = buffer;

return Unlock();
}


status_t
SharedBufferList::AddBuffer(sem_id groupReclaimSem, BBuffer* buffer)
{
Expand All @@ -170,12 +210,7 @@ SharedBufferList::AddBuffer(sem_id groupReclaimSem, BBuffer* buffer)
if (buffer == NULL)
return B_BAD_VALUE;

status_t status = Lock();
if (status != B_OK)
return status;

if (fCount == kMaxBuffers) {
Unlock();
return B_MEDIA_TOO_MANY_BUFFERS;
}

Expand All @@ -185,11 +220,27 @@ SharedBufferList::AddBuffer(sem_id groupReclaimSem, BBuffer* buffer)
fInfos[fCount].reclaimed = true;
fCount++;

status = release_sem_etc(groupReclaimSem, 1, B_DO_NOT_RESCHEDULE);
if (status != B_OK)
return status;
return release_sem_etc(groupReclaimSem, 1, B_DO_NOT_RESCHEDULE);
}

return Unlock();

status_t
SharedBufferList::CheckID(sem_id groupSem, media_buffer_id id) const
{
CALLED();

if (id == 0)
return B_OK;
if (id < 0)
return B_BAD_VALUE;

for (int32 i = 0; i < fCount; i++) {
if (fInfos[i].id == id
&& fInfos[i].reclaim_sem == groupSem) {
return B_ERROR;
}
}
return B_OK;
}


Expand Down

0 comments on commit 1cc20d8

Please sign in to comment.