users@grizzly.java.net

Re: org.glassfish.grizzly.Buffer.get(i) != org.glassfish.grizzly.Buffer.toByteBuffer().get(i)

From: Евгений Бушуев <yevgen.bushuyev_at_gmail.com>
Date: Fri, 28 Nov 2014 23:46:16 +0200

Yes, the limit and position of the buffers are really different. Like this:

dbResponseBuffer.limit() = 396

dbResponseBuffer.position() = 0

dbResponseBuffer.toByteBuffer().limit() = 676

dbResponseBuffer.toByteBuffer().position() = 280


so I've been reading bytes out of position-limit range. But, the docs
for toByteBuffer statethat:

Converts this <code>Buffer</code> to a {_at_link ByteBuffer}.

* If this <code>Buffer</code> is not composite - then returned
* {_at_link ByteBuffer}'s content is a shared subsequence of this buffer's
* content,...

the dbResponseBuffer.isComposite() returns 'false' so I was sure I
should be given same content as in grizzly.Buffer. Another thing - the
docs for java.nio.Buffer say that

<p> <i>Absolute</i> operations take an explicit element index and do not
* affect the position. Absolute <i>get</i> and <i>put</i> operations throw
* an {_at_link IndexOutOfBoundsException} if the index argument exceeds the
* limit.

and docs for grizzly buffer say that

JDK {_at_link ByteBuffer} was taken as base for Grizzly <tt>Buffer</tt>

so get(i) should return correct value regardless of limit/position or
throw exception.

With this in mind, could you please suggest a way to obtain
nio.ByteBuffer from grizzly.Buffer so that nio.ByteByffer.get(i) will
always be equal to grizzly.Buffer.get(i) ?


Best regards, Eugene.


2014-11-28 22:03 GMT+02:00 Oleksiy Stashok <oleksiy.stashok_at_oracle.com>:

> Let's doublecheck one thing, we're talking about ByteBuffer's content
> within its [*position*; *limit*) boundaries, right? You don't have to
> check ByteBuffer's content outside of these boundaries.
> So when you do:
>
> ByteBuffer byteBuf = grizzlyBuffer.toByteBuffer();
>
> The content of Grizzly Buffer is located within ByteBuffer's [*position*;
> *limit*). The returned ByteBuffer's *position* might be > 0 and its
> *limit* != *capacity*.
> To make sure the byteBuf content is correct or incorrect do this:
>
> ByteBuffer byteBuf = grizzlyBuffer.toByteBuffer().slice();
>
> Thanks.
>
> WBR,
> Alexey.
>
>
> On 28.11.14 11:46, Евгений Бушуев wrote:
>
> Grizzly Buffer's content seems to be correct. It's binary data (mongo's
> bson, http://bsonspec.org/) so it's difficult to make sure if it's
> correct looking at it in debugger. But at least documents' boundaries in
> the beginning of the doc are correct. The returned ByteBuffer content
> resembles mix of responses from sibling handler.
>
> Best regards, Eugene.
>
> 2014-11-28 21:29 GMT+02:00 Oleksiy Stashok <oleksiy.stashok_at_oracle.com>:
>
>> Hmm,
>>
>> when it happens can you pls. check if Grizzly Buffer's content is correct
>> and the problem is only seen in the ByteBuffer content?
>> Is the ByteBuffer content completely wrong or it's only ByteBuffer's
>> position/limit problem?
>>
>> Thanks.
>>
>> WBR,
>> Alexey.
>>
>>
>> On 28.11.14 11:18, Евгений Бушуев wrote:
>>
>> Hi,
>>
>> The example is the code you've suggested in "Read doesn't work" thread.
>> In the DbProtocolFilter.handleRead dbResponseBuffer passed to
>> processResponse(associatedHttpRequest, response, dbResponseBuffer)
>> sometimes returns 'wrong' ByteBuffer. I'm not 100% sure, but I think it
>> happens under heavy loads with two http handlers registered.
>>
>> Best regards, Eugene.
>>
>> 2014-11-28 20:31 GMT+02:00 Oleksiy Stashok <oleksiy.stashok_at_oracle.com>:
>>
>>> Hi,
>>>
>>> may be I misunderstood your problem.
>>> Can you pls. give an example where you think it fails. Expected vs.
>>> reality :)
>>>
>>> Thank you.
>>>
>>> WBR,
>>> Alexey.
>>>
>>>
>>> On 28.11.14 02:33, Евгений Бушуев wrote:
>>>
>>> Ok, but how then can I check if it was created with an offset and get
>>> 'proper' byte buffer? All usages I can find in samples just check if it's
>>> not composite and call toByteBuffer.
>>>
>>> I'm getting the 'wrong' byteBuffer from Grizzly Buffer obtained from
>>> ctx.getMessage() in a filter and have no control upon its creation, I just
>>> call myConnection.write(new ByteBufferWrapper(requetBytes)) (as you
>>> suggested here before). But I still want to keep my code using 'pure' nio
>>> types and thus want to get bytebuffer from grizzly buffer.
>>>
>>> Best regards, Eugene.
>>>
>>> 2014-11-27 19:01 GMT+02:00 Oleksiy Stashok <oleksiy.stashok_at_oracle.com>:
>>>
>>>> Hi,
>>>>
>>>> yes, it's normal.
>>>> Grizzly Buffer may wrap a ByteBuffer with a specific offset or just a
>>>> part of ByteBuffer (view), which you have to consider.
>>>> Normally when you do toByteBuffer() - the returned ByteBuffer's
>>>> position and limit will represent current Grizzly Buffer's view.
>>>>
>>>> WBR,
>>>> Alexey.
>>>>
>>>>
>>>> On 27.11.14 08:12, Евгений Бушуев wrote:
>>>>
>>>>> Hi!
>>>>>
>>>>> Is it legal for a org.glassfish.grizzly.Buffer
>>>>> (org.glassfish.grizzly.memory.HeapMemoryManager.TrimmableHeapBuffer#TrimmableHeapBuffer)
>>>>> to return ByteBuffer from its toByteBuffer method so that ByteBuffer's
>>>>> content won't be same as in original grizzly.Buffer?
>>>>>
>>>>> Can't figure out why this happens, seems to be random. The
>>>>> grizzly.Buffer instance is not composite.
>>>>>
>>>>> Best regards, Eugene.
>>>>>
>>>>
>>>>
>>>
>>>
>>
>>
>
>