Another attempt at deadlock elimination. BLD200501251900
authorjsichi@netbeans.org
Wed, 19 Jan 2005 22:40:47 +0000
changeset 1655876b227d4106
parent 1654 8e7a1f9943da
child 1656 f889ff7baa37
Another attempt at deadlock elimination.
mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcPrimaryIndex.java
mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcStorage.java
     1.1 --- a/mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcPrimaryIndex.java	Wed Jan 19 01:00:18 2005 +0000
     1.2 +++ b/mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcPrimaryIndex.java	Wed Jan 19 22:40:47 2005 +0000
     1.3 @@ -28,6 +28,8 @@
     1.4  class JdbcPrimaryIndex
     1.5      extends JdbcSinglevaluedIndex implements MDRCache.OverflowHandler
     1.6  {
     1.7 +    // NOTE:  around cache access sequences, we synchronize on
     1.8 +    // the parent storage, not on "this", to prevent deadlock
     1.9      private final MDRCache cache;
    1.10  
    1.11      // NOTE:  most of this class was ripped from BtreeDatabase
    1.12 @@ -160,7 +162,7 @@
    1.13      public boolean put(
    1.14          Object key,Object value) throws StorageException
    1.15      {
    1.16 -        synchronized(cache) {
    1.17 +        synchronized(storage) {
    1.18              MOFID mKey = makeMOFID(key);
    1.19              if (!exists(mKey)) {
    1.20                  addToCache(mKey,value);
    1.21 @@ -176,7 +178,7 @@
    1.22      public void replace(Object key, Object value)
    1.23          throws StorageException, StorageBadRequestException
    1.24      {
    1.25 -        synchronized(cache) {
    1.26 +        synchronized(storage) {
    1.27              MOFID mKey = makeMOFID(key);
    1.28          
    1.29              if (!exists(mKey)) {
    1.30 @@ -209,7 +211,7 @@
    1.31      // override JdbcSinglevaluedIndex
    1.32      public Object getIfExists(Object key) throws StorageException
    1.33      {
    1.34 -        synchronized(cache) {
    1.35 +        synchronized(storage) {
    1.36              MOFID mKey = makeMOFID(key);
    1.37              Object retval;
    1.38              retval = cache.get(mKey);
    1.39 @@ -254,7 +256,7 @@
    1.40      public void add(
    1.41          Object key, Object value) throws StorageException
    1.42      {
    1.43 -        synchronized(cache) {
    1.44 +        synchronized(storage) {
    1.45              MOFID mKey = makeMOFID(key);
    1.46              if (exists(mKey)) {
    1.47                  throw new StorageBadRequestException(
    1.48 @@ -268,7 +270,7 @@
    1.49      // override JdbcIndex
    1.50      public boolean remove(Object key) throws StorageException
    1.51      {
    1.52 -        synchronized(cache) {
    1.53 +        synchronized(storage) {
    1.54              MOFID mKey = makeMOFID(key);
    1.55              if (!exists(mKey)) {
    1.56                  return false;
     2.1 --- a/mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcStorage.java	Wed Jan 19 01:00:18 2005 +0000
     2.2 +++ b/mdr/extras/jdbcstorage/src/org/netbeans/mdr/persistence/jdbcimpl/JdbcStorage.java	Wed Jan 19 22:40:47 2005 +0000
     2.3 @@ -63,8 +63,6 @@
     2.4  
     2.5      private final Map entryTypeToDataTypeMap;
     2.6  
     2.7 -    private final Object connectionMutex;
     2.8 -
     2.9      private Statement jdbcStmt;
    2.10      
    2.11      private ResultSet jdbcResultSet;
    2.12 @@ -125,10 +123,6 @@
    2.13              JdbcStorageFactory.STORAGE_QUERY_DUPLICATES,
    2.14              false);
    2.15  
    2.16 -        // we use a private object for synchronization on the JDBC connection
    2.17 -        // because external code synchronizes on "this" storage object
    2.18 -        connectionMutex = new Object();
    2.19 -        
    2.20          boolean success = false;
    2.21          
    2.22          try {
    2.23 @@ -917,88 +911,82 @@
    2.24          }
    2.25      }
    2.26  
    2.27 -    ListIterator getResultSetIterator(
    2.28 +    synchronized ListIterator getResultSetIterator(
    2.29          LazyPreparedStatement lps,Object [] args,EntryType entryType)
    2.30          throws StorageException
    2.31      {
    2.32 -        synchronized(connectionMutex) {
    2.33 +        try {
    2.34 +            PreparedStatement ps = prepareStatement(lps);
    2.35 +            bindArgs(ps,args);
    2.36 +            jdbcResultSet = ps.executeQuery();
    2.37 +            // TODO:  assert exactly one column
    2.38 +            List list = new ArrayList();
    2.39              try {
    2.40 -                PreparedStatement ps = prepareStatement(lps);
    2.41 -                bindArgs(ps,args);
    2.42 -                jdbcResultSet = ps.executeQuery();
    2.43 -                // TODO:  assert exactly one column
    2.44 -                List list = new ArrayList();
    2.45 -                try {
    2.46 -                    while (jdbcResultSet.next()) {
    2.47 -                        Object obj = getResultObj(entryType);
    2.48 -                        list.add(obj);
    2.49 -                    }
    2.50 -                } finally {
    2.51 -                    closeResultSet();
    2.52 +                while (jdbcResultSet.next()) {
    2.53 +                    Object obj = getResultObj(entryType);
    2.54 +                    list.add(obj);
    2.55                  }
    2.56 -                if (entryType == EntryType.STREAMABLE) {
    2.57 -                    // Postprocess the returned byte arrays, converting them
    2.58 -                    // into real objects.  Note that we do this outside of the
    2.59 -                    // main fetch loop to avoid nasty reentrancy issues.
    2.60 -                    ListIterator listIter = list.listIterator();
    2.61 -                    while (listIter.hasNext()) {
    2.62 -                        byte [] bytes = (byte []) listIter.next();
    2.63 -                        listIter.set(readByteArray(bytes));
    2.64 -                    }
    2.65 +            } finally {
    2.66 +                closeResultSet();
    2.67 +            }
    2.68 +            if (entryType == EntryType.STREAMABLE) {
    2.69 +                // Postprocess the returned byte arrays, converting them
    2.70 +                // into real objects.  Note that we do this outside of the
    2.71 +                // main fetch loop to avoid nasty reentrancy issues.
    2.72 +                ListIterator listIter = list.listIterator();
    2.73 +                while (listIter.hasNext()) {
    2.74 +                    byte [] bytes = (byte []) listIter.next();
    2.75 +                    listIter.set(readByteArray(bytes));
    2.76                  }
    2.77 -                return list.listIterator();
    2.78 -            } catch (SQLException ex) {
    2.79 -                throw newJdbcException(ex);
    2.80              }
    2.81 +            return list.listIterator();
    2.82 +        } catch (SQLException ex) {
    2.83 +            throw newJdbcException(ex);
    2.84          }
    2.85      }
    2.86  
    2.87 -    int getResultSetCount(
    2.88 +    synchronized int getResultSetCount(
    2.89          LazyPreparedStatement lps,Object [] args)
    2.90          throws StorageException
    2.91      {
    2.92 -        synchronized(connectionMutex) {
    2.93 +        try {
    2.94 +            PreparedStatement ps = prepareStatement(lps);
    2.95 +            bindArgs(ps,args);
    2.96 +            jdbcResultSet = ps.executeQuery();
    2.97              try {
    2.98 -                PreparedStatement ps = prepareStatement(lps);
    2.99 -                bindArgs(ps,args);
   2.100 -                jdbcResultSet = ps.executeQuery();
   2.101 -                try {
   2.102 -                    int n = 0;
   2.103 -                    while (jdbcResultSet.next()) {
   2.104 -                        ++n;
   2.105 -                    }
   2.106 -                    return n;
   2.107 -                } finally {
   2.108 -                    closeResultSet();
   2.109 +                int n = 0;
   2.110 +                while (jdbcResultSet.next()) {
   2.111 +                    ++n;
   2.112                  }
   2.113 -            } catch (SQLException ex) {
   2.114 -                throw newJdbcException(ex);
   2.115 +                return n;
   2.116 +            } finally {
   2.117 +                closeResultSet();
   2.118              }
   2.119 +        } catch (SQLException ex) {
   2.120 +            throw newJdbcException(ex);
   2.121          }
   2.122      }
   2.123  
   2.124 -    int getSingletonInt(
   2.125 +    synchronized int getSingletonInt(
   2.126          LazyPreparedStatement lps,Object [] args)
   2.127          throws StorageException
   2.128      {
   2.129 -        synchronized(connectionMutex) {
   2.130 +        try {
   2.131 +            PreparedStatement ps = prepareStatement(lps);
   2.132 +            bindArgs(ps,args);
   2.133 +            jdbcResultSet = ps.executeQuery();
   2.134              try {
   2.135 -                PreparedStatement ps = prepareStatement(lps);
   2.136 -                bindArgs(ps,args);
   2.137 -                jdbcResultSet = ps.executeQuery();
   2.138 -                try {
   2.139 -                    // TODO:  assert exactly one column
   2.140 -                    if (!jdbcResultSet.next()) {
   2.141 -                        return -1;
   2.142 -                    }
   2.143 -                    int n = jdbcResultSet.getInt(1);
   2.144 -                    return n;
   2.145 -                } finally {
   2.146 -                    closeResultSet();
   2.147 +                // TODO:  assert exactly one column
   2.148 +                if (!jdbcResultSet.next()) {
   2.149 +                    return -1;
   2.150                  }
   2.151 -            } catch (SQLException ex) {
   2.152 -                throw newJdbcException(ex);
   2.153 +                int n = jdbcResultSet.getInt(1);
   2.154 +                return n;
   2.155 +            } finally {
   2.156 +                closeResultSet();
   2.157              }
   2.158 +        } catch (SQLException ex) {
   2.159 +            throw newJdbcException(ex);
   2.160          }
   2.161      }
   2.162  
   2.163 @@ -1045,17 +1033,15 @@
   2.164          return data;
   2.165      }
   2.166  
   2.167 -    int executeUpdate(LazyPreparedStatement lps,Object [] args)
   2.168 +    synchronized int executeUpdate(LazyPreparedStatement lps,Object [] args)
   2.169          throws StorageException
   2.170      {
   2.171 -        synchronized(connectionMutex) {
   2.172 -            try {
   2.173 -                PreparedStatement ps = prepareStatement(lps);
   2.174 -                bindArgs(ps,args);
   2.175 -                return ps.executeUpdate();
   2.176 -            } catch (SQLException ex) {
   2.177 -                throw newJdbcException(ex);
   2.178 -            }
   2.179 +        try {
   2.180 +            PreparedStatement ps = prepareStatement(lps);
   2.181 +            bindArgs(ps,args);
   2.182 +            return ps.executeUpdate();
   2.183 +        } catch (SQLException ex) {
   2.184 +            throw newJdbcException(ex);
   2.185          }
   2.186      }
   2.187  }