Repository: cassandra
Updated Branches:
  refs/heads/trunk b19ece1bd -> e39454873


Fix pre-3.0 counter mutation serialization

patch by pauloricardomg; reviewed by slebresne for CASSANDRA-10470


Project: http://git-wip-us.apache.org/repos/asf/cassandra/repo
Commit: http://git-wip-us.apache.org/repos/asf/cassandra/commit/df7c6581
Tree: http://git-wip-us.apache.org/repos/asf/cassandra/tree/df7c6581
Diff: http://git-wip-us.apache.org/repos/asf/cassandra/diff/df7c6581

Branch: refs/heads/trunk
Commit: df7c6581be66bd5f3bb1f7bf0e8a1a7f0a96069e
Parents: 10ef01d
Author: Paulo Motta <[email protected]>
Authored: Thu Oct 15 13:46:13 2015 -0700
Committer: Sylvain Lebresne <[email protected]>
Committed: Fri Oct 30 14:41:34 2015 +0100

----------------------------------------------------------------------
 CHANGES.txt                                     |  1 +
 .../org/apache/cassandra/db/LegacyLayout.java   | 28 +++++++++++++-------
 .../cassandra/db/context/CounterContext.java    | 16 +++++++++++
 3 files changed, 35 insertions(+), 10 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cassandra/blob/df7c6581/CHANGES.txt
----------------------------------------------------------------------
diff --git a/CHANGES.txt b/CHANGES.txt
index ca017d4..72f48f5 100644
--- a/CHANGES.txt
+++ b/CHANGES.txt
@@ -1,4 +1,5 @@
 3.0
+ * Fix backward compatibility for counters (CASSANDRA-10470)
  * Remove memory_allocator paramter from cassandra.yaml (CASSANDRA-10581)
  * Execute the metadata reload task of all registered indexes on CFS::reload 
(CASSANDRA-10604)
  * Fix thrift cas operations with defined columns (CASSANDRA-10576)

http://git-wip-us.apache.org/repos/asf/cassandra/blob/df7c6581/src/java/org/apache/cassandra/db/LegacyLayout.java
----------------------------------------------------------------------
diff --git a/src/java/org/apache/cassandra/db/LegacyLayout.java 
b/src/java/org/apache/cassandra/db/LegacyLayout.java
index 6cfd5d9..6e04559 100644
--- a/src/java/org/apache/cassandra/db/LegacyLayout.java
+++ b/src/java/org/apache/cassandra/db/LegacyLayout.java
@@ -367,29 +367,29 @@ public abstract class LegacyLayout
         for (LegacyLayout.LegacyCell cell : legacyPartition.cells)
         {
             
ByteBufferUtil.writeWithShortLength(cell.name.encode(partition.metadata()), 
out);
-            if (cell.kind == LegacyLayout.LegacyCell.Kind.EXPIRING)
+            out.writeByte(cell.serializationFlags());
+            if (cell.isExpiring())
             {
-                out.writeByte(LegacyLayout.EXPIRATION_MASK);  // serialization 
flags
                 out.writeInt(cell.ttl);
                 out.writeInt(cell.localDeletionTime);
             }
-            else if (cell.kind == LegacyLayout.LegacyCell.Kind.DELETED)
+            else if (cell.isTombstone())
             {
-                out.writeByte(LegacyLayout.DELETION_MASK);  // serialization 
flags
                 out.writeLong(cell.timestamp);
                 out.writeInt(TypeSizes.sizeof(cell.localDeletionTime));
                 out.writeInt(cell.localDeletionTime);
                 continue;
             }
-            else if (cell.kind == LegacyLayout.LegacyCell.Kind.COUNTER)
+            else if (cell.isCounterUpdate())
             {
-                out.writeByte(LegacyLayout.COUNTER_MASK);  // serialization 
flags
-                out.writeLong(Long.MIN_VALUE);  // timestampOfLastDelete (not 
used, and MIN_VALUE is the default)
+                out.writeLong(cell.timestamp);
+                long count = 
CounterContext.instance().getLocalCount(cell.value);
+                ByteBufferUtil.writeWithLength(ByteBufferUtil.bytes(count), 
out);
+                continue;
             }
-            else
+            else if (cell.isCounter())
             {
-                // normal cell
-                out.writeByte(0);  // serialization flags
+                out.writeLong(Long.MIN_VALUE);  // timestampOfLastDelete (not 
used, and MIN_VALUE is the default)
             }
 
             out.writeLong(cell.timestamp);
@@ -1401,11 +1401,19 @@ public abstract class LegacyLayout
                 return EXPIRATION_MASK;
             if (isTombstone())
                 return DELETION_MASK;
+            if (isCounterUpdate())
+                return COUNTER_UPDATE_MASK;
             if (isCounter())
                 return COUNTER_MASK;
             return 0;
         }
 
+        private boolean isCounterUpdate()
+        {
+            // See UpdateParameters.addCounter() for more details on this
+            return isCounter() && CounterContext.instance().isLocal(value);
+        }
+
         public ClusteringPrefix clustering()
         {
             return name.clustering;

http://git-wip-us.apache.org/repos/asf/cassandra/blob/df7c6581/src/java/org/apache/cassandra/db/context/CounterContext.java
----------------------------------------------------------------------
diff --git a/src/java/org/apache/cassandra/db/context/CounterContext.java 
b/src/java/org/apache/cassandra/db/context/CounterContext.java
index 9076817..e3f4dfd 100644
--- a/src/java/org/apache/cassandra/db/context/CounterContext.java
+++ b/src/java/org/apache/cassandra/db/context/CounterContext.java
@@ -674,6 +674,22 @@ public class CounterContext
     }
 
     /**
+     * Returns the count associated with the local counter id, or 0 if no such 
shard is present.
+     */
+    public long getLocalCount(ByteBuffer context)
+    {
+        return getLocalClockAndCount(context).count;
+    }
+
+    /**
+     * Checks if a context is local
+     */
+    public boolean isLocal(ByteBuffer context)
+    {
+        return ContextState.wrap(context).isLocal();
+    }
+
+    /**
      * Returns the clock and the count associated with the given counter id, 
or (0, 0) if no such shard is present.
      */
     @VisibleForTesting

Reply via email to