Hello,
I am having problems when calling Lock on a Direct Sound Secondary Buffer.
I have created a class that represents and manages DirectSound
secondary buffers. The member mWritePosition is used to track the write position.
Originally I did not have as many checks before calling Lock but, since
I could not figure out the problem, I added the extra checks to ensure
my values are within (what I believe to be, based on the documentation) the valid range.
I am trying to stream into the buffer up to 'dataSize'. The function is
intended to be called and if the available space to be written is less
than the desired dataSize then dataSize is adjusted to the maximum.
Filling the buffer seems to work as expected up until
mWritePosition>=mBufferSize (which it is then changed to
mWritePosition-=mBufferSize), at this point Lock constantly returns
DSERR_INVALIDPARAM.
My guess is that DSERR_INVALIDPARAM returned when the "dangerous" (
between Play Cursor and Write Cursor) is asked to be locked. However my
extensive checks seem to ensure these values are correct. It is almost
as though Lock has the condition if(requestedWritePosition <
writeCursor) return DSERR_INVALIDPARAM;
The Commented out section is a text visual representation of the buffer
and the pointers within (numbers ticked by too quickly to properly
analyse them).
My Problem appears to be the same as
http://forums.microsoft.com/MSDN/ShowPost.aspx?PostID=498765&SiteID=1
Where it was not answered.
Any help is greatly appreciated :)
Cheers
Sean
Code (Really not happy about not having C++ code option in Format Code Block window)
| 1 |
u32 Buffer::Append(void* data, u32 dataSize) |
| 2 |
{ |
| 3 |
void* block1=0; |
| 4 |
DWORD block1Bytes=0; |
| 5 |
void* block2=0; |
| 6 |
DWORD block2Bytes=0; |
| 7 |
DWORD bytesWritten=0; |
| 8 |
DWORD playPos,writePos,writeLen; |
| 9 |
|
| 10 |
HRESULT hRes = mBuffer->GetCurrentPosition(&playPos,&writePos); |
| 11 |
if(playPos > writePos) |
| 12 |
if(mWritePosition < writePos || mWritePosition > playPos) |
| 13 |
{ |
| 14 |
std::cout << "mWritePosition < writePos || mWritePosition > playPos" << std::endl; |
| 15 |
return 0; |
| 16 |
} |
| 17 |
|
| 18 |
if(mWritePosition < writePos && mWritePosition > playPos) |
| 19 |
{ |
| 20 |
std::cout << "mWritePosition < writePos && mWritePosition > playPos" << std::endl; |
| 21 |
return 0; |
| 22 |
} |
| 23 |
|
| 24 |
if (mWritePosition < playPos) |
| 25 |
writeLen = playPos - mWritePosition; |
| 26 |
else |
| 27 |
writeLen = mBufferSize - mWritePosition + playPos; |
| 28 |
|
| 29 |
if(dataSize>writeLen) |
| 30 |
dataSize=writeLen; |
| 31 |
|
| 32 |
if(dataSize==0) |
| 33 |
return 0; |
| 34 |
|
| 35 |
//#define PERCENT_BAR_RANGE 65 |
| 36 |
// u32 playPosP=((playPos* PERCENT_BAR_RANGE)/mBufferSize); |
| 37 |
// u32 writePosP=((writePos* PERCENT_BAR_RANGE)/mBufferSize); |
| 38 |
// u32 mwritePosP=((mWritePosition* PERCENT_BAR_RANGE)/mBufferSize); |
| 39 |
// std::cout << /*mwritePosP << "|" << mWritePosition <<*/ "["; |
| 40 |
// |
| 41 |
// for(int p=0;p<PERCENT_BAR_RANGE; ++p) |
| 42 |
// { |
| 43 |
// u32 d=(((mWritePosition+writeLen)* PERCENT_BAR_RANGE)/mBufferSize); |
| 44 |
// u32 d2=0; |
| 45 |
// if(mWritePosition+writeLen > mBufferSize) |
| 46 |
// d2=playPosP; |
| 47 |
// if(p==writePosP && p==playPosP) |
| 48 |
// std::cout << "X"; |
| 49 |
// else |
| 50 |
// if(p==writePosP) |
| 51 |
// std::cout << "<"; |
| 52 |
// else |
| 53 |
// if(p==playPosP) |
| 54 |
// std::cout << ">"; |
| 55 |
// else |
| 56 |
// if(p==mwritePosP) |
| 57 |
// std::cout << "W"; |
| 58 |
// else |
| 59 |
// if((p<d && p>mwritePosP) || p<d2) |
| 60 |
// std::cout << "D"; |
| 61 |
// else |
| 62 |
// std::cout << " "; |
| 63 |
// } |
| 64 |
// std::cout << "]\r"; |
| 65 |
|
| 66 |
|
| 67 |
int r=mBuffer->Lock(mWritePosition,dataSize, &block1,&block1Bytes, &block2, &block2Bytes, 0);//DSBLOCK_FROMWRITECURSOR);//DSBLOCK_ENTIREBUFFER); |
| 68 |
if(r==DS_OK) |
| 69 |
{ |
| 70 |
if(dataSize>block1Bytes) |
| 71 |
{ |
| 72 |
memcpy(block1, data, block1Bytes); |
| 73 |
dataSize-=block1Bytes; |
| 74 |
bytesWritten+=block1Bytes; |
| 75 |
if(dataSize>block2Bytes) |
| 76 |
dataSize=block2Bytes; |
| 77 |
memcpy(block2, &(((u8*)data)[bytesWritten]), dataSize); |
| 78 |
bytesWritten+=dataSize; |
| 79 |
mBuffer->Unlock(&block1, block1Bytes, &block2, dataSize); |
| 80 |
}else |
| 81 |
{ |
| 82 |
memcpy(block1, data, dataSize); |
| 83 |
bytesWritten+=dataSize; |
| 84 |
mBuffer->Unlock(&block1, dataSize, &block2, 0); |
| 85 |
} |
| 86 |
}else |
| 87 |
{ |
| 88 |
switch(r) |
| 89 |
{ |
| 90 |
case DSERR_BUFFERLOST: std::cout << "Buffer::Append() - DSERR_BUFFERLOST" << std::endl; break; |
| 91 |
case DSERR_INVALIDCALL: std::cout << "Buffer::Append() - DSERR_INVALIDCALL" << std::endl; break; |
| 92 |
case DSERR_INVALIDPARAM: std::cout << "Buffer::Append() - DSERR_INVALIDPARAM" << std::endl; |
| 93 |
break; |
| 94 |
case DSERR_PRIOLEVELNEEDED: std::cout << "Buffer::Append() - DSERR_BUFFERLOST" << std::endl; break; |
| 95 |
}; |
| 96 |
} |
| 97 |
mWritePosition+=bytesWritten; |
| 98 |
if(mWritePosition>=mBufferSize) |
| 99 |
{ |
| 100 |
mWritePosition-=mBufferSize; |
| 101 |
} |
| 102 |
return bytesWritten; |
| 103 |
} |
| 104 |
|
| 105 |
|
| 106 |
|
| 107 |
|
| 108 |
|