diff --git a/src/main/java/net/onrc/onos/datastore/hazelcast/HZTable.java b/src/main/java/net/onrc/onos/datastore/hazelcast/HZTable.java
index ec98349..894854c 100644
--- a/src/main/java/net/onrc/onos/datastore/hazelcast/HZTable.java
+++ b/src/main/java/net/onrc/onos/datastore/hazelcast/HZTable.java
@@ -33,12 +33,12 @@
      * @return initial value
      */
     protected static long getInitialVersion() {
-	long version = initialVersion.incrementAndGet();
-	if (version == HZClient.VERSION_NONEXISTENT) {
-	    // used up whole 64bit space?
-	    version = initialVersion.incrementAndGet();
-	}
-	return version;
+        long version = initialVersion.incrementAndGet();
+        if (version == HZClient.VERSION_NONEXISTENT) {
+            // used up whole 64bit space?
+            version = initialVersion.incrementAndGet();
+        }
+        return version;
     }
 
     /**
@@ -47,141 +47,141 @@
      * @return
      */
     protected static long getNextVersion(final long version) {
-	long nextVersion = version + 1;
-	if (nextVersion == HZClient.VERSION_NONEXISTENT) {
-	    ++nextVersion;
-	}
-	return nextVersion;
+        long nextVersion = version + 1;
+        if (nextVersion == HZClient.VERSION_NONEXISTENT) {
+            ++nextVersion;
+        }
+        return nextVersion;
     }
 
     static class VersionedValue implements IdentifiedDataSerializable {
-	private static final long serialVersionUID = -3149375966890712708L;
+        private static final long serialVersionUID = -3149375966890712708L;
 
-	private byte[] value;
-	private long version;
+        private byte[] value;
+        private long version;
 
-	protected VersionedValue() {
-	    value = new byte[0];
-	    version = HZClient.VERSION_NONEXISTENT;
-	}
+        protected VersionedValue() {
+            value = new byte[0];
+            version = HZClient.VERSION_NONEXISTENT;
+        }
 
-	public VersionedValue(final byte[] value, final long version) {
-	    this.value = value;
-	    this.version = version;
-	}
+        public VersionedValue(final byte[] value, final long version) {
+            this.value = value;
+            this.version = version;
+        }
 
-	public byte[] getValue() {
-	    return value;
-	}
+        public byte[] getValue() {
+            return value;
+        }
 
-	public long getVersion() {
-	    return version;
-	}
+        public long getVersion() {
+            return version;
+        }
 
-	public void setValue(final byte[] value) {
-	    this.value = value;
-	}
+        public void setValue(final byte[] value) {
+            this.value = value;
+        }
 
-	public void setNextVersion() {
-	    this.version = getNextVersion(this.version);
-	}
+        public void setNextVersion() {
+            this.version = getNextVersion(this.version);
+        }
 
-	@Override
-	public void writeData(final ObjectDataOutput out) throws IOException {
-	    out.writeLong(version);
-	    out.writeInt(value.length);
-	    if (value.length > 0) {
-		out.write(value);
-	    }
-	}
+        @Override
+        public void writeData(final ObjectDataOutput out) throws IOException {
+            out.writeLong(version);
+            out.writeInt(value.length);
+            if (value.length > 0) {
+                out.write(value);
+            }
+        }
 
-	@Override
-	public void readData(final ObjectDataInput in) throws IOException {
-	    version = in.readLong();
-	    final int valueLen = in.readInt();
-	    value = new byte[valueLen];
-	    in.readFully(value);
-	}
+        @Override
+        public void readData(final ObjectDataInput in) throws IOException {
+            version = in.readLong();
+            final int valueLen = in.readInt();
+            value = new byte[valueLen];
+            in.readFully(value);
+        }
 
-	@Override
-	public int getFactoryId() {
-	    return VersionedValueSerializableFactory.FACTORY_ID;
-	}
+        @Override
+        public int getFactoryId() {
+            return VersionedValueSerializableFactory.FACTORY_ID;
+        }
 
-	@Override
-	public int getId() {
-	    return VersionedValueSerializableFactory.VERSIONED_VALUE_ID;
-	}
+        @Override
+        public int getId() {
+            return VersionedValueSerializableFactory.VERSIONED_VALUE_ID;
+        }
 
-	@Override
-	public int hashCode() {
-	    final int prime = 31;
-	    int result = 1;
-	    result = prime * result + (int) (version ^ (version >>> 32));
-	    result = prime * result + Arrays.hashCode(value);
-	    return result;
-	}
+        @Override
+        public int hashCode() {
+            final int prime = 31;
+            int result = 1;
+            result = prime * result + (int) (version ^ (version >>> 32));
+            result = prime * result + Arrays.hashCode(value);
+            return result;
+        }
 
-	@Override
-	public boolean equals(final Object obj) {
-	    if (this == obj) {
-		return true;
-	    }
-	    if (obj == null) {
-		return false;
-	    }
-	    if (getClass() != obj.getClass()) {
-		return false;
-	    }
-	    VersionedValue other = (VersionedValue) obj;
-	    if (version != other.version) {
-		return false;
-	    }
-	    if (!Arrays.equals(value, other.value)) {
-		return false;
-	    }
-	    return true;
-	}
+        @Override
+        public boolean equals(final Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (obj == null) {
+                return false;
+            }
+            if (getClass() != obj.getClass()) {
+                return false;
+            }
+            VersionedValue other = (VersionedValue) obj;
+            if (version != other.version) {
+                return false;
+            }
+            if (!Arrays.equals(value, other.value)) {
+                return false;
+            }
+            return true;
+        }
     }
 
     // TODO Refactor and extract common parts
     public static class Entry implements IKVEntry {
-	final byte[] key;
-	byte[] value;
-	long version;
+        final byte[] key;
+        byte[] value;
+        long version;
 
-	public Entry(final byte[] key, final byte[] value, final long version) {
-	    this.key = key;
-	    this.setValue(value);
-	    this.setVersion(version);
-	}
+        public Entry(final byte[] key, final byte[] value, final long version) {
+            this.key = key;
+            this.setValue(value);
+            this.setVersion(version);
+        }
 
-	public Entry(final byte[] key) {
-	    this(key, null, HZClient.VERSION_NONEXISTENT);
-	}
+        public Entry(final byte[] key) {
+            this(key, null, HZClient.VERSION_NONEXISTENT);
+        }
 
-	@Override
-	public byte[] getKey() {
-	    return key;
-	}
+        @Override
+        public byte[] getKey() {
+            return key;
+        }
 
-	@Override
-	public byte[] getValue() {
-	    return value;
-	}
+        @Override
+        public byte[] getValue() {
+            return value;
+        }
 
-	@Override
-	public long getVersion() {
-	    return version;
-	}
+        @Override
+        public long getVersion() {
+            return version;
+        }
 
-	void setValue(final byte[] value) {
-	    this.value = value;
-	}
+        void setValue(final byte[] value) {
+            this.value = value;
+        }
 
-	void setVersion(final long version) {
-	    this.version = version;
-	}
+        void setVersion(final long version) {
+            this.version = version;
+        }
     }
 
 
@@ -190,136 +190,136 @@
     private final IMap<byte[], VersionedValue> map;
 
     public HZTable(final String mapName, final IMap<byte[], VersionedValue> map) {
-	this.mapName = mapName;
-	this.map = map;
+        this.mapName = mapName;
+        this.map = map;
     }
 
     @Override
     public String getTableName() {
-	return mapName;
+        return mapName;
     }
 
     @Override
     public IKVTableID getTableId() {
-	return this;
+        return this;
     }
 
     @Override
     public long create(final byte[] key, final byte[] value) throws ObjectExistsException {
-	final long version = getInitialVersion();
-	VersionedValue existing = map.putIfAbsent(key, new VersionedValue(value, version));
-	if (existing != null) {
-	    throw new ObjectExistsException(this, key);
-	}
-	return version;
+        final long version = getInitialVersion();
+        VersionedValue existing = map.putIfAbsent(key, new VersionedValue(value, version));
+        if (existing != null) {
+            throw new ObjectExistsException(this, key);
+        }
+        return version;
     }
 
     @Override
     public long forceCreate(final byte[] key, final byte[] value) {
-	final long version = getInitialVersion();
-	map.set(key, new VersionedValue(value, version));
-	return version;
+        final long version = getInitialVersion();
+        map.set(key, new VersionedValue(value, version));
+        return version;
     }
 
     @Override
     public IKVEntry read(final byte[] key) throws ObjectDoesntExistException {
-	final VersionedValue value = map.get(key);
-	if (value == null) {
-	    throw new ObjectDoesntExistException(this, key);
-	}
-	return new Entry(key, value.getValue(), value.getVersion());
+        final VersionedValue value = map.get(key);
+        if (value == null) {
+            throw new ObjectDoesntExistException(this, key);
+        }
+        return new Entry(key, value.getValue(), value.getVersion());
     }
 
     @Override
     public long update(final byte[] key, final byte[] value, final long version)
             throws ObjectDoesntExistException, WrongVersionException {
 
-	try {
-	    map.lock(key);
-	    final VersionedValue oldValue = map.get(key);
-	    if (oldValue == null) {
-		throw new ObjectDoesntExistException(this, key);
-	    }
-	    if (oldValue.getVersion() != version) {
-		throw new WrongVersionException(this, key, version, oldValue.getVersion());
-	    }
-	    final long nextVersion = getNextVersion(version);
-	    map.set(key, new VersionedValue(value, nextVersion));
-	    return nextVersion;
-	} finally {
-	    map.unlock(key);
-	}
+        try {
+            map.lock(key);
+            final VersionedValue oldValue = map.get(key);
+            if (oldValue == null) {
+                throw new ObjectDoesntExistException(this, key);
+            }
+            if (oldValue.getVersion() != version) {
+                throw new WrongVersionException(this, key, version, oldValue.getVersion());
+            }
+            final long nextVersion = getNextVersion(version);
+            map.set(key, new VersionedValue(value, nextVersion));
+            return nextVersion;
+        } finally {
+            map.unlock(key);
+        }
     }
 
     @Override
     public long update(final byte[] key, final byte[] value)
             throws ObjectDoesntExistException {
 
-	try {
-	    map.lock(key);
-	    final VersionedValue valueInMap = map.get(key);
-	    if (valueInMap == null) {
-		throw new ObjectDoesntExistException(this, key);
-	    }
-	    valueInMap.setValue(value);
-	    valueInMap.setNextVersion();
-	    map.set(key, valueInMap);
-	    return valueInMap.getVersion();
-	} finally {
-	    map.unlock(key);
-	}
+        try {
+            map.lock(key);
+            final VersionedValue valueInMap = map.get(key);
+            if (valueInMap == null) {
+                throw new ObjectDoesntExistException(this, key);
+            }
+            valueInMap.setValue(value);
+            valueInMap.setNextVersion();
+            map.set(key, valueInMap);
+            return valueInMap.getVersion();
+        } finally {
+            map.unlock(key);
+        }
     }
 
     @Override
     public long delete(final byte[] key, final long version)
             throws ObjectDoesntExistException, WrongVersionException {
 
-	try {
-	    map.lock(key);
-	    final VersionedValue oldValue = map.get(key);
-	    if (oldValue == null) {
-		throw new ObjectDoesntExistException(this, key);
-	    }
-	    if (oldValue.getVersion() != version) {
-		throw new WrongVersionException(this, key, version, oldValue.getVersion());
-	    }
-	    map.delete(key);
-	    return oldValue.getVersion();
-	} finally {
-	    map.unlock(key);
-	}
+        try {
+            map.lock(key);
+            final VersionedValue oldValue = map.get(key);
+            if (oldValue == null) {
+                throw new ObjectDoesntExistException(this, key);
+            }
+            if (oldValue.getVersion() != version) {
+                throw new WrongVersionException(this, key, version, oldValue.getVersion());
+            }
+            map.delete(key);
+            return oldValue.getVersion();
+        } finally {
+            map.unlock(key);
+        }
     }
 
     @Override
     public long forceDelete(final byte[] key) {
-	final VersionedValue valueInMap = map.remove(key);
-	if (valueInMap == null) {
-	    return HZClient.VERSION_NONEXISTENT;
-	}
-	return valueInMap.getVersion();
+        final VersionedValue valueInMap = map.remove(key);
+        if (valueInMap == null) {
+            return HZClient.VERSION_NONEXISTENT;
+        }
+        return valueInMap.getVersion();
     }
 
     @Override
     public Iterable<IKVEntry> getAllEntries() {
-	final Set<IMap.Entry<byte[], VersionedValue>> entries = map.entrySet();
-	List<IKVEntry> entryList = new ArrayList<IKVTable.IKVEntry>(entries.size());
-	for (IMap.Entry<byte[], VersionedValue> entry : entries) {
-	    entryList.add(new Entry(entry.getKey(), entry.getValue().getValue(), entry.getValue().getVersion()));
-	}
-	return entryList;
+        final Set<IMap.Entry<byte[], VersionedValue>> entries = map.entrySet();
+        List<IKVEntry> entryList = new ArrayList<IKVTable.IKVEntry>(entries.size());
+        for (IMap.Entry<byte[], VersionedValue> entry : entries) {
+            entryList.add(new Entry(entry.getKey(), entry.getValue().getValue(), entry.getValue().getVersion()));
+        }
+        return entryList;
     }
 
     @Override
     public String toString() {
-	return "[HZTable " + mapName + "]";
+        return "[HZTable " + mapName + "]";
     }
 
     IMap<byte[], VersionedValue> getBackendMap() {
-	return this.map;
+        return this.map;
     }
 
     @Override
     public long VERSION_NONEXISTENT() {
-	return HZClient.VERSION_NONEXISTENT;
+        return HZClient.VERSION_NONEXISTENT;
     }
 }
