You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@mina.apache.org by "Jonathan Valliere (Jira)" <ji...@apache.org> on 2020/04/15 15:45:00 UTC

[jira] [Resolved] (DIRMINA-966) NIO Datagram messages can get duplicated when unable to be sent by the underlying DatagramChannel

     [ https://issues.apache.org/jira/browse/DIRMINA-966?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]

Jonathan Valliere resolved DIRMINA-966.
---------------------------------------
    Fix Version/s:     (was: 2.0.8)
                   2.1.4
       Resolution: Fixed

Fixed https://gitbox.apache.org/repos/asf?p=mina.git;a=commit;h=55f4b4d66bd05b4f26d61e1ad51f025e20452889

> NIO Datagram messages can get duplicated when unable to be sent by the underlying DatagramChannel
> -------------------------------------------------------------------------------------------------
>
>                 Key: DIRMINA-966
>                 URL: https://issues.apache.org/jira/browse/DIRMINA-966
>             Project: MINA
>          Issue Type: Bug
>          Components: Core
>    Affects Versions: 2.0.7
>            Reporter: Michael McKnight
>            Assignee: Jonathan Valliere
>            Priority: Major
>             Fix For: 2.1.4
>
>
> AbstractPollingConnectionlessIoAcceptor.write method...
> within the "for ( ;; )" loop if the channel write fails to send, indicated by 0 being returned, the message is re-enqueued.  However the loop is not exited and the same message is tried again.  For each failure to send the same message over and over a new WriteRequest is added to the queue and the message will be sent again for each WriteRequest.
> Even though the WriteRequest references the same IoBuffer, after each successful write the IoBuffer is reset which enables each subsequent WriteRequest in the queue to send it again.
> I have had instances where the kernel buffer is full and delays for up to 500ms or so which resulted in ~ 300 duplicate messages being sent.
> Here is the block of code in question within the for ( ;; ) loop:
> {code}
> int localWrittenBytes = send( session, buf, destination );
> if ( ( localWrittenBytes == 0 ) || ( writtenBytes >= maxWrittenBytes ) )
> {
>    // Kernel buffer is full or wrote too much
>    setInterestedInWrite( session, true );
>    session.getWriteRequestQueue().offer( session, writeRequest );
>    scheduleFlush( session );
> }
> else
> {
>    setInterestedInWrite( session, false );
>    // Clear and fire event
>    session.setCurrentWriteRequest( null );
>    writtenBytes += localWrittenBytes;
>    buf.reset();
>    session.getFilterChain().fireMessageSent( writeRequest );
>    break;
> }
> {code}
> Possible fixes:
>  * adding a "break;" after the message has been re-queued would certainly resolve this but then messages could be delivered out of order.
>  * don't re-queue the message and just loop back through trying to send it again.
> Workaround:
>  * ensure that the SO_SNDBUF size is sufficiently large which could, depending on the application, alleviate the issue altogether or make it less likely to occur.



--
This message was sent by Atlassian Jira
(v8.3.4#803005)

---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@mina.apache.org
For additional commands, e-mail: dev-help@mina.apache.org