Uploaded image for project: 'MariaDB Connector/J'
  1. MariaDB Connector/J
  2. CONJ-1011

NullpointerException when cancelling a query from an other thread

Details

    • Bug
    • Status: Closed (View Workflow)
    • Major
    • Resolution: Fixed
    • 2.7.5
    • 2.7.7
    • Other
    • None
    • Java 11 / Linux / JavaMelody (but should not be related)

    Description

      When cancelling an other query from an other thread, you might get an NPE in rare cases:

      java.lang.NullPointerException
      	at org.mariadb.jdbc.MariaDbStatement.skipMoreResults(MariaDbStatement.java:1187)
      	at org.mariadb.jdbc.MariaDbStatement.cancel(MariaDbStatement.java:981)
      	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
      	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
      	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
      	at java.base/java.lang.reflect.Method.invoke(Method.java:566)
      	at net.bull.javamelody.JdbcWrapper$StatementInvocationHandler.invoke(JdbcWrapper.java:163)
      	at net.bull.javamelody.JdbcWrapper$DelegatingInvocationHandler.invoke(JdbcWrapper.java:306)
      	at com.sun.proxy.$Proxy345.cancel(Unknown Source)
      	at io.ebean.util.JdbcClose.cancel(JdbcClose.java:76)
      

      As you see, 'protocol' is null in https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L1187

      I investigate a bit and have the following explanation for the bug:

      Thread #1 starts a query

      Thread #2 tries to cancel the query.
      It invokes L980 protocol.cancelCurrentQuery() successfully

      Thread #1 now closes the query and sets protocol = null

      When Thread #2 tries to execute L981, which calls L1187 protocol.skip() - you get an NPE.

      There is no kind of locking the access of protocol and this can be modified in a concurrent thread.

      Unfortunately, I cannot provide a test. The bug is very hard to reproduce and happens only in production...

      Side note: I think the bug may not happen with 3.x, because the code is totally different (but we did not update to 3.x, yet)

      Attachments

        Activity

          Roland Praml Roland Praml created issue -
          Roland Praml Roland Praml made changes -
          Field Original Value New Value
          Description When cancelling an other query from an other thread, you might get an NPE in rare cases:
          {code}
          java.lang.NullPointerException
          at org.mariadb.jdbc.MariaDbStatement.skipMoreResults(MariaDbStatement.java:1187)
          at org.mariadb.jdbc.MariaDbStatement.cancel(MariaDbStatement.java:981)
          at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
          at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
          at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
          at java.base/java.lang.reflect.Method.invoke(Method.java:566)
          at net.bull.javamelody.JdbcWrapper$StatementInvocationHandler.invoke(JdbcWrapper.java:163)
          at net.bull.javamelody.JdbcWrapper$DelegatingInvocationHandler.invoke(JdbcWrapper.java:306)
          at com.sun.proxy.$Proxy345.cancel(Unknown Source)
          at io.ebean.util.JdbcClose.cancel(JdbcClose.java:76)
          {code}

          As you see, 'protocol' is null in https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L1187


          I investigate a bit and have the following explanation for the bug:

          Thread #1 starts a query

          Thread #2 tries to cancel the query.
          It invokes [protocol.cancelCurrentQuery()|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L980] successfully

          Thread #1 now closes the query and sets [protocol = null|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L805]

          When Thread #2 tries to execute [protocol.skip()|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L1187] - you get an NPE.

          There is no kind of locking the access of protocol and this can be modified in a concurrent thread.

          Unfortunately, I cannot provide a test. The bug is very hard to reproduce and happens only in production...

          Side note: I think the bug may not happen with 3.x, because the code is totally different (but we did not update to 3.x, yet)
          When cancelling an other query from an other thread, you might get an NPE in rare cases:
          {code}
          java.lang.NullPointerException
          at org.mariadb.jdbc.MariaDbStatement.skipMoreResults(MariaDbStatement.java:1187)
          at org.mariadb.jdbc.MariaDbStatement.cancel(MariaDbStatement.java:981)
          at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
          at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
          at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
          at java.base/java.lang.reflect.Method.invoke(Method.java:566)
          at net.bull.javamelody.JdbcWrapper$StatementInvocationHandler.invoke(JdbcWrapper.java:163)
          at net.bull.javamelody.JdbcWrapper$DelegatingInvocationHandler.invoke(JdbcWrapper.java:306)
          at com.sun.proxy.$Proxy345.cancel(Unknown Source)
          at io.ebean.util.JdbcClose.cancel(JdbcClose.java:76)
          {code}

          As you see, 'protocol' is null in https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L1187


          I investigate a bit and have the following explanation for the bug:

          Thread #1 starts a query

          Thread #2 tries to cancel the query.
          It invokes L980 [protocol.cancelCurrentQuery()|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L980] successfully

          Thread #1 now closes the query and sets [protocol = null|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L805]

          When Thread #2 tries to execute L981, which calls L1187 [protocol.skip()|https://github.com/mariadb-corporation/mariadb-connector-j/blob/2.7.5/src/main/java/org/mariadb/jdbc/MariaDbStatement.java#L1187] - you get an NPE.

          There is no kind of locking the access of protocol and this can be modified in a concurrent thread.

          Unfortunately, I cannot provide a test. The bug is very hard to reproduce and happens only in production...

          Side note: I think the bug may not happen with 3.x, because the code is totally different (but we did not update to 3.x, yet)
          diego dupin Diego Dupin made changes -
          Fix Version/s 2.7.7 [ 28325 ]
          diego dupin Diego Dupin added a comment -

          Thanks for detailed explaination.
          This will be corrected in next version.

          diego dupin Diego Dupin added a comment - Thanks for detailed explaination. This will be corrected in next version.
          diego dupin Diego Dupin made changes -
          Status Open [ 1 ] In Progress [ 3 ]
          diego dupin Diego Dupin made changes -
          issue.field.resolutiondate 2022-09-30 12:33:15.0 2022-09-30 12:33:15.584
          diego dupin Diego Dupin made changes -
          Component/s Other [ 12201 ]
          Resolution Fixed [ 1 ]
          Status In Progress [ 3 ] Closed [ 6 ]

          People

            diego dupin Diego Dupin
            Roland Praml Roland Praml
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved:

              Git Integration

                Error rendering 'com.xiplink.jira.git.jira_git_plugin:git-issue-webpanel'. Please contact your Jira administrators.