http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageMvccUpdateTxStateHintRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageMvccUpdateTxStateHintRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageMvccUpdateTxStateHintRecord.java index 7e53609..fd77728 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageMvccUpdateTxStateHintRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageMvccUpdateTxStateHintRecord.java @@ -50,7 +50,7 @@ public class DataPageMvccUpdateTxStateHintRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { DataPageIO io = PageIO.getPageIO(pageAddr); - io.updateTxState(pageAddr, itemId, pageMem.pageSize(), txState); + io.updateTxState(pageAddr, itemId, pageMem.realPageSize(groupId()), txState); } /** {@inheritDoc} */
http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageRemoveRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageRemoveRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageRemoveRecord.java index f7776be..abc84ea 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageRemoveRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageRemoveRecord.java @@ -53,7 +53,7 @@ public class DataPageRemoveRecord extends PageDeltaRecord { throws IgniteCheckedException { AbstractDataPageIO io = PageIO.getPageIO(pageAddr); - io.removeRow(pageAddr, itemId, pageMem.pageSize()); + io.removeRow(pageAddr, itemId, pageMem.realPageSize(groupId())); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageUpdateRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageUpdateRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageUpdateRecord.java index ed469a4..6f5d8fd 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageUpdateRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/DataPageUpdateRecord.java @@ -71,7 +71,7 @@ public class DataPageUpdateRecord extends PageDeltaRecord { AbstractDataPageIO io = PageIO.getPageIO(pageAddr); - io.updateRow(pageAddr, itemId, pageMem.pageSize(), payload, null, 0); + io.updateRow(pageAddr, itemId, pageMem.realPageSize(groupId()), payload, null, 0); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/InitNewPageRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/InitNewPageRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/InitNewPageRecord.java index c177a04..d0ba2aa 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/InitNewPageRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/InitNewPageRecord.java @@ -57,7 +57,7 @@ public class InitNewPageRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { PageIO io = PageIO.getPageIO(ioType, ioVer); - io.initNewPage(pageAddr, newPageId, pageMem.pageSize()); + io.initNewPage(pageAddr, newPageId, pageMem.realPageSize(groupId())); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageAddRootRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageAddRootRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageAddRootRecord.java index 4972155..9bf3aef 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageAddRootRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageAddRootRecord.java @@ -44,7 +44,7 @@ public class MetaPageAddRootRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { BPlusMetaIO io = BPlusMetaIO.VERSIONS.forPage(pageAddr); - io.addRoot(pageAddr, rootId, pageMem.pageSize()); + io.addRoot(pageAddr, rootId, pageMem.realPageSize(groupId())); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageCutRootRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageCutRootRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageCutRootRecord.java index 5b896f6..1383a38 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageCutRootRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageCutRootRecord.java @@ -38,7 +38,7 @@ public class MetaPageCutRootRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { BPlusMetaIO io = BPlusMetaIO.VERSIONS.forPage(pageAddr); - io.cutRoot(pageAddr, pageMem.pageSize()); + io.cutRoot(pageAddr, pageMem.realPageSize(groupId())); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRecord.java index ca995bf..7b3f3a9 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRecord.java @@ -76,7 +76,7 @@ public class MetaPageInitRecord extends InitNewPageRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { PageMetaIO io = PageMetaIO.getPageIO(ioType, ioVer); - io.initNewPage(pageAddr, newPageId, pageMem.pageSize()); + io.initNewPage(pageAddr, newPageId, pageMem.realPageSize(groupId())); io.setTreeRoot(pageAddr, treeRoot); io.setReuseListRoot(pageAddr, reuseListRoot); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootInlineRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootInlineRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootInlineRecord.java index 0d3c155..71ae85d 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootInlineRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootInlineRecord.java @@ -51,7 +51,7 @@ public class MetaPageInitRootInlineRecord extends MetaPageInitRootRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { BPlusMetaIO io = BPlusMetaIO.VERSIONS.forPage(pageAddr); - io.initRoot(pageAddr, rootId, pageMem.pageSize()); + io.initRoot(pageAddr, rootId, pageMem.realPageSize(groupId())); io.setInlineSize(pageAddr, inlineSize); } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootRecord.java index 78a7e4f..7eca278 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/MetaPageInitRootRecord.java @@ -44,7 +44,7 @@ public class MetaPageInitRootRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { BPlusMetaIO io = BPlusMetaIO.VERSIONS.forPage(pageAddr); - io.initRoot(pageAddr, rootId, pageMem.pageSize()); + io.initRoot(pageAddr, rootId, pageMem.realPageSize(groupId())); io.setInlineSize(pageAddr, 0); } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/NewRootInitRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/NewRootInitRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/NewRootInitRecord.java index 4b8f747..1d78033 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/NewRootInitRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/NewRootInitRecord.java @@ -71,7 +71,8 @@ public class NewRootInitRecord<L> extends PageDeltaRecord { /** {@inheritDoc} */ @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { - io.initNewRoot(pageAddr, newRootId, leftChildId, null, rowBytes, rightChildId, pageMem.pageSize(), false); + io.initNewRoot(pageAddr, newRootId, leftChildId, null, rowBytes, rightChildId, pageMem.realPageSize(groupId()), + false); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListAddPageRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListAddPageRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListAddPageRecord.java index 6c7fc71..6f877b9 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListAddPageRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListAddPageRecord.java @@ -54,7 +54,7 @@ public class PagesListAddPageRecord extends PageDeltaRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { PagesListNodeIO io = PagesListNodeIO.VERSIONS.forPage(pageAddr); - int cnt = io.addPage(pageAddr, dataPageId, pageMem.pageSize()); + int cnt = io.addPage(pageAddr, dataPageId, pageMem.realPageSize(groupId())); assert cnt >= 0 : cnt; } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListInitNewPageRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListInitNewPageRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListInitNewPageRecord.java index b2512aa..53c23b1 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListInitNewPageRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/PagesListInitNewPageRecord.java @@ -76,11 +76,11 @@ public class PagesListInitNewPageRecord extends InitNewPageRecord { @Override public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException { PagesListNodeIO io = PageIO.getPageIO(PageIO.T_PAGE_LIST_NODE, ioVer); - io.initNewPage(pageAddr, pageId(), pageMem.pageSize()); + io.initNewPage(pageAddr, pageId(), pageMem.realPageSize(groupId())); io.setPreviousId(pageAddr, prevPageId); if (addDataPageId != 0L) { - int cnt = io.addPage(pageAddr, addDataPageId, pageMem.pageSize()); + int cnt = io.addPage(pageAddr, addDataPageId, pageMem.realPageSize(groupId())); assert cnt == 0 : cnt; } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/TrackingPageDeltaRecord.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/TrackingPageDeltaRecord.java b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/TrackingPageDeltaRecord.java index 089eb9a..3f11c58 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/TrackingPageDeltaRecord.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/pagemem/wal/record/delta/TrackingPageDeltaRecord.java @@ -76,7 +76,7 @@ public class TrackingPageDeltaRecord extends PageDeltaRecord { pageIdToMark, nextSnapshotId, lastSuccessfulSnapshotId, - pageMem.pageSize()); + pageMem.realPageSize(groupId())); } /** {@inheritDoc} */ http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/authentication/IgniteAuthenticationProcessor.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/authentication/IgniteAuthenticationProcessor.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/authentication/IgniteAuthenticationProcessor.java index ded37e7..d1598cd 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/authentication/IgniteAuthenticationProcessor.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/authentication/IgniteAuthenticationProcessor.java @@ -97,9 +97,6 @@ public class IgniteAuthenticationProcessor extends GridProcessorAdapter implemen /** Whan the future is done the node is ready for authentication. */ private final GridFutureAdapter<Void> readyForAuthFut = new GridFutureAdapter<>(); - /** Random is used to get random server node to authentication from client node. */ - private static final Random RND = new Random(System.currentTimeMillis()); - /** Operation mutex. */ private final Object mux = new Object(); @@ -313,18 +310,7 @@ public class IgniteAuthenticationProcessor extends GridProcessorAdapter implemen AuthenticateFuture fut; synchronized (mux) { - Collection<ClusterNode> aliveNodes = ctx.discovery().aliveServerNodes(); - - int rndIdx = RND.nextInt(aliveNodes.size()) + 1; - - int i = 0; - ClusterNode rndNode = null; - - for (Iterator<ClusterNode> it = aliveNodes.iterator(); i < rndIdx && it.hasNext(); i++) - rndNode = it.next(); - - if (rndNode == null) - assert rndNode != null; + ClusterNode rndNode = U.randomServerNode(ctx); fut = new AuthenticateFuture(rndNode.id()); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/ClusterCachesInfo.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/ClusterCachesInfo.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/ClusterCachesInfo.java index 8bed063..6ab4e67 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/ClusterCachesInfo.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/ClusterCachesInfo.java @@ -158,17 +158,6 @@ class ClusterCachesInfo { } /** - * @param cacheName Cache name. - * @param grpName Group name. - * @return Group ID. - */ - private int cacheGroupId(String cacheName, @Nullable String grpName) { - assert cacheName != null; - - return grpName != null ? CU.cacheId(grpName) : CU.cacheId(cacheName); - } - - /** * @param checkConsistency {@code True} if need check cache configurations consistency. * @throws IgniteCheckedException If failed. */ @@ -363,6 +352,9 @@ class ClusterCachesInfo { "Query parallelism", locAttr.qryParallelism(), rmtAttr.qryParallelism(), true); } } + + CU.checkAttributeMismatch(log, rmtAttr.cacheName(), rmt, "isEncryptionEnabled", + "Cache encrypted", locAttr.isEncryptionEnabled(), rmtAttr.isEncryptionEnabled(), true); } /** @@ -574,7 +566,8 @@ class ClusterCachesInfo { ccfg, cacheId, req.initiatingNodeId(), - req.deploymentId()); + req.deploymentId(), + req.encryptionKey()); DynamicCacheDescriptor startDesc = new DynamicCacheDescriptor(ctx, ccfg, @@ -1536,7 +1529,7 @@ class ClusterCachesInfo { ", conflictingCacheName=" + desc.cacheName() + ']'; } - int grpId = cacheGroupId(cfg.getName(), cfg.getGroupName()); + int grpId = CU.cacheGroupId(cfg.getName(), cfg.getGroupName()); if (cfg.getGroupName() != null) { if (cacheGroupByName(cfg.getGroupName()) == null) { @@ -1647,7 +1640,8 @@ class ClusterCachesInfo { cfg, cacheId, nodeId, - joinData.cacheDeploymentId()); + joinData.cacheDeploymentId(), + null); ctx.discovery().setCacheFilter( cacheId, @@ -1761,6 +1755,7 @@ class ClusterCachesInfo { * @param cacheId Cache ID. * @param rcvdFrom Node ID cache was recived from. * @param deploymentId Deployment ID. + * @param encKey Encryption key. * @return Group descriptor. */ private CacheGroupDescriptor registerCacheGroup( @@ -1769,7 +1764,8 @@ class ClusterCachesInfo { CacheConfiguration<?, ?> startedCacheCfg, Integer cacheId, UUID rcvdFrom, - IgniteUuid deploymentId) { + IgniteUuid deploymentId, + @Nullable byte[] encKey) { if (startedCacheCfg.getGroupName() != null) { CacheGroupDescriptor desc = cacheGroupByName(startedCacheCfg.getGroupName()); @@ -1780,7 +1776,7 @@ class ClusterCachesInfo { } } - int grpId = cacheGroupId(startedCacheCfg.getName(), startedCacheCfg.getGroupName()); + int grpId = CU.cacheGroupId(startedCacheCfg.getName(), startedCacheCfg.getGroupName()); Map<String, Integer> caches = Collections.singletonMap(startedCacheCfg.getName(), cacheId); @@ -1798,6 +1794,9 @@ class ClusterCachesInfo { persistent, null); + if (startedCacheCfg.isEncryptionEnabled()) + ctx.encryption().beforeCacheGroupStart(grpId, encKey); + if (ctx.cache().context().pageStore() != null) ctx.cache().context().pageStore().beforeCacheGroupStart(grpDesc); @@ -1930,6 +1929,9 @@ class ClusterCachesInfo { CU.validateCacheGroupsAttributesMismatch(log, cfg, startCfg, "backups", "Backups", cfg.getBackups(), startCfg.getBackups(), true); } + + CU.validateCacheGroupsAttributesMismatch(log, cfg, startCfg, "encryptionEnabled", "Encrypted", + cfg.isEncryptionEnabled(), startCfg.isEncryptionEnabled(), true); } /** http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/DynamicCacheChangeRequest.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/DynamicCacheChangeRequest.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/DynamicCacheChangeRequest.java index 2b942b0..5b8a89c 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/DynamicCacheChangeRequest.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/DynamicCacheChangeRequest.java @@ -95,6 +95,9 @@ public class DynamicCacheChangeRequest implements Serializable { /** */ private transient boolean locallyConfigured; + /** Encryption key. */ + @Nullable private byte[] encKey; + /** * @param reqId Unique request ID. * @param cacheName Cache stop name. @@ -424,6 +427,20 @@ public class DynamicCacheChangeRequest implements Serializable { this.disabledAfterStart = disabledAfterStart; } + /** + * @param encKey Encryption key. + */ + public void encryptionKey(@Nullable byte[] encKey) { + this.encKey = encKey; + } + + /** + * @return Encryption key. + */ + @Nullable public byte[] encryptionKey() { + return encKey; + } + /** {@inheritDoc} */ @Override public String toString() { return "DynamicCacheChangeRequest [cacheName=" + cacheName() + http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheAttributes.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheAttributes.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheAttributes.java index 01daee2..230320a 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheAttributes.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheAttributes.java @@ -353,6 +353,13 @@ public class GridCacheAttributes implements Serializable { } /** + * @return Is cache encryption enabled. + */ + public boolean isEncryptionEnabled() { + return ccfg.isEncryptionEnabled(); + } + + /** * @param obj Object to get class of. * @return Class name or {@code null}. */ @@ -364,4 +371,4 @@ public class GridCacheAttributes implements Serializable { @Override public String toString() { return S.toString(GridCacheAttributes.class, this); } -} \ No newline at end of file +} http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheProcessor.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheProcessor.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheProcessor.java index 16e1799..f595ecf 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheProcessor.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheProcessor.java @@ -25,6 +25,7 @@ import java.util.Deque; import java.util.HashMap; import java.util.HashSet; import java.util.IdentityHashMap; +import java.util.Iterator; import java.util.LinkedList; import java.util.List; import java.util.ListIterator; @@ -61,6 +62,7 @@ import org.apache.ignite.configuration.MemoryConfiguration; import org.apache.ignite.configuration.NearCacheConfiguration; import org.apache.ignite.configuration.TransactionConfiguration; import org.apache.ignite.configuration.WALMode; +import org.apache.ignite.spi.encryption.EncryptionSpi; import org.apache.ignite.events.EventType; import org.apache.ignite.internal.GridKernalContext; import org.apache.ignite.internal.IgniteClientDisconnectedCheckedException; @@ -136,6 +138,7 @@ import org.apache.ignite.internal.util.F0; import org.apache.ignite.internal.util.future.GridCompoundFuture; import org.apache.ignite.internal.util.future.GridFinishedFuture; import org.apache.ignite.internal.util.future.GridFutureAdapter; +import org.apache.ignite.internal.util.lang.GridPlainClosure; import org.apache.ignite.internal.util.lang.IgniteOutClosureX; import org.apache.ignite.internal.util.tostring.GridToStringInclude; import org.apache.ignite.internal.util.typedef.CIX1; @@ -149,6 +152,7 @@ import org.apache.ignite.internal.util.typedef.internal.U; import org.apache.ignite.lang.IgniteBiTuple; import org.apache.ignite.lang.IgniteClosure; import org.apache.ignite.lang.IgniteFuture; +import org.apache.ignite.lang.IgniteInClosure; import org.apache.ignite.lang.IgnitePredicate; import org.apache.ignite.lang.IgniteUuid; import org.apache.ignite.lifecycle.LifecycleAware; @@ -598,6 +602,22 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor } } } + + if (cc.isEncryptionEnabled() && !ctx.clientNode()) { + if (!CU.isPersistentCache(cc, c.getDataStorageConfiguration())) { + throw new IgniteCheckedException("Using encryption is not allowed" + + " for not persistent cache [cacheName=" + cc.getName() + ", groupName=" + cc.getGroupName() + + ", cacheType=" + cacheType + "]"); + } + + EncryptionSpi encSpi = c.getEncryptionSpi(); + + if (encSpi == null) { + throw new IgniteCheckedException("EncryptionSpi should be configured to use encrypted cache " + + "[cacheName=" + cc.getName() + ", groupName=" + cc.getGroupName() + + ", cacheType=" + cacheType + "]"); + } + } } /** @@ -903,6 +923,15 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor ", configuredAtomicityMode=" + cfg.getAtomicityMode() + ", storedAtomicityMode=" + cfgFromStore.getAtomicityMode() + "]"); } + + boolean staticCfgVal = cfg.isEncryptionEnabled(); + + boolean storedVal = cfgFromStore.isEncryptionEnabled(); + + if (storedVal != staticCfgVal) { + throw new IgniteCheckedException("Encrypted flag value differs. Static config value is '" + staticCfgVal + + "' and value stored on the disk is '" + storedVal + "'"); + } } /** @@ -1311,7 +1340,8 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor ", mode=" + cfg.getCacheMode() + ", atomicity=" + cfg.getAtomicityMode() + ", backups=" + cfg.getBackups() + - ", mvcc=" + cacheCtx.mvccEnabled() +']'); + ", mvcc=" + cacheCtx.mvccEnabled() +']' + + ", encryptionEnabled=" + cfg.isEncryptionEnabled() +']'); } } @@ -3107,7 +3137,9 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor if (checkThreadTx) checkEmptyTransactions(); - try { + GridPlainClosure<Collection<byte[]>, IgniteInternalFuture<Boolean>> startCacheClsr = (grpKeys) -> { + assert ccfg == null || !ccfg.isEncryptionEnabled() || !grpKeys.isEmpty(); + DynamicCacheChangeRequest req = prepareCacheChangeRequest( ccfg, cacheName, @@ -3117,7 +3149,8 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor failIfExists, failIfNotStarted, false, - null); + null, + ccfg != null && ccfg.isEncryptionEnabled() ? grpKeys.iterator().next() : null); if (req != null) { if (req.clientStartOnly()) @@ -3127,6 +3160,16 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor } else return new GridFinishedFuture<>(); + }; + + try { + if (ccfg != null && ccfg.isEncryptionEnabled()) { + ctx.encryption().checkEncryptedCacheSupported(); + + return generateEncryptionKeysAndStartCacheAfter(1, startCacheClsr); + } + + return startCacheClsr.apply(Collections.EMPTY_SET); } catch (Exception e) { return new GridFinishedFuture<>(e); @@ -3134,6 +3177,48 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor } /** + * Send {@code GenerateEncryptionKeyRequest} and execute {@code after} closure if succeed. + * + * @param keyCnt Count of keys to generate. + * @param after Closure to execute after encryption keys would be generated. + */ + private IgniteInternalFuture<Boolean> generateEncryptionKeysAndStartCacheAfter(int keyCnt, + GridPlainClosure<Collection<byte[]>, IgniteInternalFuture<Boolean>> after) { + IgniteInternalFuture<Collection<byte[]>> genEncKeyFut = ctx.encryption().generateKeys(keyCnt); + + GridFutureAdapter<Boolean> res = new GridFutureAdapter<>(); + + genEncKeyFut.listen(new IgniteInClosure<IgniteInternalFuture<Collection<byte[]>>>() { + @Override public void apply(IgniteInternalFuture<Collection<byte[]>> fut) { + try { + Collection<byte[]> grpKeys = fut.result(); + + if (F.size(grpKeys, F.alwaysTrue()) != keyCnt) + res.onDone(false, fut.error()); + + IgniteInternalFuture<Boolean> dynStartCacheFut = after.apply(grpKeys); + + dynStartCacheFut.listen(new IgniteInClosure<IgniteInternalFuture<Boolean>>() { + @Override public void apply(IgniteInternalFuture<Boolean> fut) { + try { + res.onDone(fut.get(), fut.error()); + } + catch (IgniteCheckedException e) { + res.onDone(false, e); + } + } + }); + } + catch (Exception e) { + res.onDone(false, e); + } + } + }); + + return res; + } + + /** * @param startReqs Start requests. * @param cachesToClose Cache tp close. * @return Future for cache change operation. @@ -3167,7 +3252,7 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor * @param disabledAfterStart If true, cache proxies will be only activated after {@link #restartProxies()}. * @return Future that will be completed when all caches are deployed. */ - public IgniteInternalFuture<?> dynamicStartCaches(Collection<CacheConfiguration> ccfgList, boolean failIfExists, + public IgniteInternalFuture<Boolean> dynamicStartCaches(Collection<CacheConfiguration> ccfgList, boolean failIfExists, boolean checkThreadTx, boolean disabledAfterStart) { return dynamicStartCachesByStoredConf( ccfgList.stream().map(StoredCacheData::new).collect(Collectors.toList()), @@ -3186,7 +3271,7 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor * @param disabledAfterStart If true, cache proxies will be only activated after {@link #restartProxies()}. * @return Future that will be completed when all caches are deployed. */ - public IgniteInternalFuture<?> dynamicStartCachesByStoredConf( + public IgniteInternalFuture<Boolean> dynamicStartCachesByStoredConf( Collection<StoredCacheData> storedCacheDataList, boolean failIfExists, boolean checkThreadTx, @@ -3194,11 +3279,15 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor if (checkThreadTx) checkEmptyTransactions(); - List<DynamicCacheChangeRequest> srvReqs = null; - Map<String, DynamicCacheChangeRequest> clientReqs = null; + GridPlainClosure<Collection<byte[]>, IgniteInternalFuture<Boolean>> startCacheClsr = (grpKeys) -> { + List<DynamicCacheChangeRequest> srvReqs = null; + Map<String, DynamicCacheChangeRequest> clientReqs = null; + + Iterator<byte[]> grpKeysIter = grpKeys.iterator(); - try { for (StoredCacheData ccfg : storedCacheDataList) { + assert !ccfg.config().isEncryptionEnabled() || grpKeysIter.hasNext(); + DynamicCacheChangeRequest req = prepareCacheChangeRequest( ccfg.config(), ccfg.config().getName(), @@ -3208,7 +3297,8 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor failIfExists, true, disabledAfterStart, - ccfg.queryEntities()); + ccfg.queryEntities(), + ccfg.config().isEncryptionEnabled() ? grpKeysIter.next() : null); if (req != null) { if (req.clientStartOnly()) { @@ -3225,16 +3315,14 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor } } } - } - catch (Exception e) { - return new GridFinishedFuture<>(e); - } - if (srvReqs != null || clientReqs != null) { + if (srvReqs == null && clientReqs == null) + return new GridFinishedFuture<>(); + if (clientReqs != null && srvReqs == null) return startClientCacheChange(clientReqs, null); - GridCompoundFuture<?, ?> compoundFut = new GridCompoundFuture<>(); + GridCompoundFuture<?, Boolean> compoundFut = new GridCompoundFuture<>(); for (DynamicCacheStartFuture fut : initiateCacheChanges(srvReqs)) compoundFut.add((IgniteInternalFuture)fut); @@ -3248,9 +3336,16 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor compoundFut.markInitialized(); return compoundFut; + }; + + int encGrpCnt = 0; + + for (StoredCacheData ccfg : storedCacheDataList) { + if (ccfg.config().isEncryptionEnabled()) + encGrpCnt++; } - else - return new GridFinishedFuture<>(); + + return generateEncryptionKeysAndStartCacheAfter(encGrpCnt, startCacheClsr); } /** Resolve cache type for input cacheType */ @@ -4539,6 +4634,7 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor * @param failIfNotStarted If {@code true} fails if cache is not started. * @param disabledAfterStart If true, cache proxies will be only activated after {@link #restartProxies()}. * @param qryEntities Query entities. + * @param encKey Encryption key. * @return Request or {@code null} if cache already exists. * @throws IgniteCheckedException if some of pre-checks failed * @throws CacheExistsException if cache exists and failIfExists flag is {@code true} @@ -4552,7 +4648,8 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor boolean failIfExists, boolean failIfNotStarted, boolean disabledAfterStart, - @Nullable Collection<QueryEntity> qryEntities + @Nullable Collection<QueryEntity> qryEntities, + @Nullable byte[] encKey ) throws IgniteCheckedException { DynamicCacheDescriptor desc = cacheDescriptor(cacheName); @@ -4564,6 +4661,8 @@ public class GridCacheProcessor extends GridProcessorAdapter implements Metastor req.disabledAfterStart(disabledAfterStart); + req.encryptionKey(encKey); + if (ccfg != null) { cloneCheckSerializable(ccfg); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheUtils.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheUtils.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheUtils.java index 91a449f..c316621 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheUtils.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/GridCacheUtils.java @@ -58,6 +58,7 @@ import org.apache.ignite.configuration.DataRegionConfiguration; import org.apache.ignite.configuration.DataStorageConfiguration; import org.apache.ignite.configuration.IgniteConfiguration; import org.apache.ignite.configuration.TransactionConfiguration; +import org.apache.ignite.spi.encryption.EncryptionSpi; import org.apache.ignite.internal.GridKernalContext; import org.apache.ignite.internal.IgniteClientDisconnectedCheckedException; import org.apache.ignite.internal.IgniteInternalFuture; @@ -1149,6 +1150,17 @@ public class GridCacheUtils { } /** + * @param cacheName Cache name. + * @param grpName Group name. + * @return Group ID. + */ + public static int cacheGroupId(String cacheName, @Nullable String grpName) { + assert cacheName != null; + + return grpName != null ? CU.cacheId(grpName) : CU.cacheId(cacheName); + } + + /** * @param cfg Grid configuration. * @param cacheName Cache name. * @return {@code True} in this is IGFS data or meta cache. @@ -1900,6 +1912,17 @@ public class GridCacheUtils { } /** + * @param pageSize Page size. + * @param encSpi Encryption spi. + * @return Page size without encryption overhead. + */ + public static int encryptedPageSize(int pageSize, EncryptionSpi encSpi) { + return pageSize + - (encSpi.encryptedSizeNoPadding(pageSize) - pageSize) + - encSpi.blockSize(); /* For CRC. */ + } + + /** * @param sctx Shared context. * @param cacheIds Cache ids. * @return First partitioned cache or {@code null} in case no partitioned cache ids are in list. http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/IgniteCacheOffheapManagerImpl.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/IgniteCacheOffheapManagerImpl.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/IgniteCacheOffheapManagerImpl.java index a968737..0182c8a 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/IgniteCacheOffheapManagerImpl.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/IgniteCacheOffheapManagerImpl.java @@ -3139,7 +3139,8 @@ public class IgniteCacheOffheapManagerImpl implements IgniteCacheOffheapManager DataPageIO iox = (DataPageIO)io; - int offset = iox.getPayloadOffset(pageAddr, itemId, grp.dataRegion().pageMemory().pageSize(), MVCC_INFO_SIZE); + int offset = iox.getPayloadOffset(pageAddr, itemId, + grp.dataRegion().pageMemory().realPageSize(grp.groupId()), MVCC_INFO_SIZE); long newCrd = iox.newMvccCoordinator(pageAddr, offset); long newCntr = iox.newMvccCounter(pageAddr, offset); @@ -3168,8 +3169,8 @@ public class IgniteCacheOffheapManagerImpl implements IgniteCacheOffheapManager DataPageIO iox = (DataPageIO)io; - int pageSize = grp.dataRegion().pageMemory().pageSize(); - int offset = iox.getPayloadOffset(pageAddr, itemId, pageSize, MVCC_INFO_SIZE); + int offset = iox.getPayloadOffset(pageAddr, itemId, + grp.dataRegion().pageMemory().realPageSize(grp.groupId()), MVCC_INFO_SIZE); long crd = iox.mvccCoordinator(pageAddr, offset); long cntr = iox.mvccCounter(pageAddr, offset); @@ -3222,7 +3223,8 @@ public class IgniteCacheOffheapManagerImpl implements IgniteCacheOffheapManager DataPageIO iox = (DataPageIO)io; - int offset = iox.getPayloadOffset(pageAddr, itemId, grp.dataRegion().pageMemory().pageSize(), MVCC_INFO_SIZE); + int offset = iox.getPayloadOffset(pageAddr, itemId, + grp.dataRegion().pageMemory().realPageSize(grp.groupId()), MVCC_INFO_SIZE); long crd = iox.mvccCoordinator(pageAddr, offset); long cntr = iox.mvccCounter(pageAddr, offset); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/distributed/dht/preloader/GridDhtPartitionsExchangeFuture.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/distributed/dht/preloader/GridDhtPartitionsExchangeFuture.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/distributed/dht/preloader/GridDhtPartitionsExchangeFuture.java index f43afa0..2052c36 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/distributed/dht/preloader/GridDhtPartitionsExchangeFuture.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/distributed/dht/preloader/GridDhtPartitionsExchangeFuture.java @@ -1052,6 +1052,8 @@ public class GridDhtPartitionsExchangeFuture extends GridDhtTopologyFutureAdapte registerCachesFuture = cctx.affinity().onCacheChangeRequest(this, crd, exchActions); + cctx.kernalContext().encryption().onDeActivate(cctx.kernalContext()); + if (log.isInfoEnabled()) { log.info("Successfully deactivated data structures, services and caches [" + "nodeId=" + cctx.localNodeId() + http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/mvcc/MvccUtils.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/mvcc/MvccUtils.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/mvcc/MvccUtils.java index 896c9aa..a659245 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/mvcc/MvccUtils.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/mvcc/MvccUtils.java @@ -577,7 +577,8 @@ public class MvccUtils { try{ DataPageIO dataIo = DataPageIO.VERSIONS.forPage(pageAddr); - int offset = dataIo.getPayloadOffset(pageAddr, itemId(link), pageMem.pageSize(), MVCC_INFO_SIZE); + int offset = dataIo.getPayloadOffset(pageAddr, itemId(link), pageMem.realPageSize(grpId), + MVCC_INFO_SIZE); long mvccCrd = dataIo.mvccCoordinator(pageAddr, offset); long mvccCntr = dataIo.mvccCounter(pageAddr, offset); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/CacheDataRowAdapter.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/CacheDataRowAdapter.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/CacheDataRowAdapter.java index 574e6d5..8b44ff6 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/CacheDataRowAdapter.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/CacheDataRowAdapter.java @@ -155,7 +155,7 @@ public class CacheDataRowAdapter implements CacheDataRow { DataPagePayload data = io.readPayload(pageAddr, itemId(nextLink), - pageMem.pageSize()); + pageMem.realPageSize(grpId)); nextLink = data.nextLink(); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/DataStructure.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/DataStructure.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/DataStructure.java index 0177407..c23a970 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/DataStructure.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/DataStructure.java @@ -387,10 +387,10 @@ public abstract class DataStructure implements PageLockListener { } /** - * @return Page size. + * @return Page size without encryption overhead. */ - protected final int pageSize() { - return pageMem.pageSize(); + protected int pageSize() { + return pageMem.realPageSize(grpId); } @Override public void onBeforeWriteLock(int cacheId, long pageId, long page) { http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheDatabaseSharedManager.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheDatabaseSharedManager.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheDatabaseSharedManager.java index d54a64f..b2f2f33 100755 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheDatabaseSharedManager.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheDatabaseSharedManager.java @@ -1430,6 +1430,9 @@ public class GridCacheDatabaseSharedManager extends IgniteCacheDatabaseSharedMan grpIds.add(tup.get1().groupId()); pageMem.onCacheGroupDestroyed(tup.get1().groupId()); + + if (tup.get2()) + cctx.kernalContext().encryption().onCacheGroupDestroyed(gctx.groupId()); } Collection<IgniteInternalFuture<Void>> clearFuts = new ArrayList<>(destroyed.size()); http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheOffheapManager.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheOffheapManager.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheOffheapManager.java index 801703b..c6f8415 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheOffheapManager.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/GridCacheOffheapManager.java @@ -482,8 +482,6 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple try { final long curAddr = pageMem.writeLock(grpId, curId, curPage); - int pageSize = pageMem.pageSize(); - assert curAddr != 0; try { @@ -492,12 +490,12 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple if (init) { partCntrIo = PagePartitionCountersIO.VERSIONS.latest(); - partCntrIo.initNewPage(curAddr, curId, pageSize); + partCntrIo.initNewPage(curAddr, curId, pageMem.realPageSize(grpId)); } else partCntrIo = PageIO.getPageIO(curAddr); - written += partCntrIo.writeCacheSizes(pageSize, curAddr, data, written); + written += partCntrIo.writeCacheSizes(pageMem.realPageSize(grpId), curAddr, data, written); nextId = partCntrIo.getNextCountersPageId(curAddr); @@ -727,7 +725,7 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple if (PageIO.getType(pageAddr) != PageIO.T_META) { PageMetaIO pageIO = PageMetaIO.VERSIONS.latest(); - pageIO.initNewPage(pageAddr, metaId, pageMem.pageSize()); + pageIO.initNewPage(pageAddr, metaId, pageMem.realPageSize(grpId)); metastoreRoot = pageMem.allocatePage(grpId, PageIdAllocator.INDEX_PARTITION, PageMemory.FLAG_IDX); reuseListRoot = pageMem.allocatePage(grpId, PageIdAllocator.INDEX_PARTITION, PageMemory.FLAG_IDX); @@ -1464,7 +1462,7 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple if (PageIO.getType(pageAddr) != PageIO.T_PART_META) { PagePartitionMetaIO io = PagePartitionMetaIO.VERSIONS.latest(); - io.initNewPage(pageAddr, partMetaId, pageMem.pageSize()); + io.initNewPage(pageAddr, partMetaId, pageMem.realPageSize(grpId)); treeRoot = pageMem.allocatePage(grpId, partId, PageMemory.FLAG_DATA); reuseListRoot = pageMem.allocatePage(grpId, partId, PageMemory.FLAG_DATA); @@ -1478,8 +1476,10 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple io.setReuseListRoot(pageAddr, reuseListRoot); io.setPendingTreeRoot(pageAddr, pendingTreeRoot); - if (PageHandler.isWalDeltaRecordNeeded(pageMem, grpId, partMetaId, partMetaPage, wal, null)) - wal.log(new PageSnapshot(new FullPageId(partMetaId, grpId), pageAddr, pageMem.pageSize())); + if (PageHandler.isWalDeltaRecordNeeded(pageMem, grpId, partMetaId, partMetaPage, wal, null)) { + wal.log(new PageSnapshot(new FullPageId(partMetaId, grpId), pageAddr, + pageMem.pageSize(), pageMem.realPageSize(grpId))); + } allocated = true; } @@ -1508,8 +1508,11 @@ public class GridCacheOffheapManager extends IgniteCacheOffheapManagerImpl imple io.setPendingTreeRoot(pageAddr, pendingTreeRoot); - if (PageHandler.isWalDeltaRecordNeeded(pageMem, grpId, partMetaId, partMetaPage, wal, null)) - wal.log(new PageSnapshot(new FullPageId(partMetaId, grpId), pageAddr, pageMem.pageSize())); + if (PageHandler.isWalDeltaRecordNeeded(pageMem, grpId, partMetaId, partMetaPage, wal, + null)) { + wal.log(new PageSnapshot(new FullPageId(partMetaId, grpId), pageAddr, + pageMem.pageSize(), pageMem.realPageSize(grpId))); + } pendingTreeAllocated = true; } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIO.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIO.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIO.java new file mode 100644 index 0000000..008a728 --- /dev/null +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIO.java @@ -0,0 +1,371 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.ignite.internal.processors.cache.persistence.file; + +import java.io.IOException; +import java.io.Serializable; +import java.nio.ByteBuffer; +import java.nio.MappedByteBuffer; +import org.apache.ignite.spi.encryption.EncryptionSpi; +import org.apache.ignite.internal.managers.encryption.GridEncryptionManager; +import org.apache.ignite.internal.processors.cache.persistence.tree.io.PageIO; +import org.apache.ignite.internal.processors.cache.persistence.wal.crc.PureJavaCrc32; +import org.apache.ignite.internal.util.typedef.internal.CU; + +/** + * Implementation of {@code FileIO} that supports encryption(decryption) of pages written(readed) to(from) file. + * + * @see EncryptedFileIOFactory + */ +public class EncryptedFileIO implements FileIO { + /** + * Underlying file. + */ + private final FileIO plainFileIO; + + /** + * Group id. + */ + private final int groupId; + + /** + * Size of plain data page in bytes. + */ + private final int pageSize; + + /** + * Size of file header in bytes. + */ + private final int headerSize; + + /** + * Shared database manager. + */ + private final GridEncryptionManager encMgr; + + /** + * Shared database manager. + */ + private final EncryptionSpi encSpi; + + /** + * Encryption key. + */ + private Serializable encKey; + + /** + * Extra bytes added by encryption. + */ + private final int encryptionOverhead; + + /** + * Array of zeroes to fulfill tail of decrypted page. + */ + private final byte[] zeroes; + + /** + * @param plainFileIO Underlying file. + * @param groupId Group id. + * @param pageSize Size of plain data page in bytes. + * @param headerSize Size of file header in bytes. + * @param encMgr Encryption manager. + */ + EncryptedFileIO(FileIO plainFileIO, int groupId, int pageSize, int headerSize, + GridEncryptionManager encMgr, EncryptionSpi encSpi) { + this.plainFileIO = plainFileIO; + this.groupId = groupId; + this.pageSize = pageSize; + this.headerSize = headerSize; + this.encMgr = encMgr; + this.encSpi = encSpi; + + this.encryptionOverhead = pageSize - CU.encryptedPageSize(pageSize, encSpi); + this.zeroes = new byte[encryptionOverhead]; + } + + /** {@inheritDoc} */ + @Override public long position() throws IOException { + return plainFileIO.position(); + } + + /** {@inheritDoc} */ + @Override public void position(long newPosition) throws IOException { + plainFileIO.position(newPosition); + } + + /** {@inheritDoc} */ + @Override public int read(ByteBuffer destBuf) throws IOException { + assert position() == 0; + + return plainFileIO.read(destBuf); + } + + /** {@inheritDoc} */ + @Override public int readFully(ByteBuffer destBuf) throws IOException { + return read(destBuf); + } + + /** {@inheritDoc} */ + @Override public int read(ByteBuffer destBuf, long position) throws IOException { + assert destBuf.remaining() >= pageSize; + assert position() != 0; + + ByteBuffer encrypted = ByteBuffer.allocate(pageSize); + + int res = plainFileIO.read(encrypted, position); + + if (res < 0) + return res; + + if (res != pageSize) { + throw new IllegalStateException("Expecting to read whole page[" + pageSize + " bytes], " + + "but read only " + res + " bytes"); + } + + encrypted.rewind(); + + decrypt(encrypted, destBuf); + + return res; + } + + /** {@inheritDoc} */ + @Override public int readFully(ByteBuffer destBuf, long position) throws IOException { + assert destBuf.capacity() == pageSize; + assert position() != 0; + + ByteBuffer encrypted = ByteBuffer.allocate(pageSize); + + int res = plainFileIO.readFully(encrypted, position); + + if (res < 0) + return res; + + if (res != pageSize) { + throw new IllegalStateException("Expecting to read whole page[" + pageSize + " bytes], " + + "but read only " + res + " bytes"); + } + + encrypted.rewind(); + + decrypt(encrypted, destBuf); + + return res; + } + + /** {@inheritDoc} */ + @Override public int read(byte[] buf, int off, int len) throws IOException { + throw new UnsupportedOperationException("Encrypted File doesn't support this operation"); + } + + /** {@inheritDoc} */ + @Override public int readFully(byte[] buf, int off, int len) throws IOException { + return read(buf, off, len); + } + + /** {@inheritDoc} */ + @Override public int write(ByteBuffer srcBuf) throws IOException { + assert position() == 0; + assert headerSize == srcBuf.capacity(); + + return plainFileIO.write(srcBuf); + } + + /** {@inheritDoc} */ + @Override public int writeFully(ByteBuffer srcBuf) throws IOException { + return write(srcBuf); + } + + /** {@inheritDoc} */ + @Override public int write(ByteBuffer srcBuf, long position) throws IOException { + ByteBuffer encrypted = ByteBuffer.allocate(pageSize); + + encrypt(srcBuf, encrypted); + + encrypted.rewind(); + + return plainFileIO.write(encrypted, position); + } + + /** {@inheritDoc} */ + @Override public int writeFully(ByteBuffer srcBuf, long position) throws IOException { + ByteBuffer encrypted = ByteBuffer.allocate(pageSize); + + encrypt(srcBuf, encrypted); + + encrypted.rewind(); + + return plainFileIO.writeFully(encrypted, position); + } + + /** + * @param srcBuf Source buffer. + * @param res Destination buffer. + * @throws IOException If failed. + */ + private void encrypt(ByteBuffer srcBuf, ByteBuffer res) throws IOException { + assert position() != 0; + assert srcBuf.remaining() >= pageSize; + assert tailIsEmpty(srcBuf, PageIO.getType(srcBuf)); + + int srcLimit = srcBuf.limit(); + + srcBuf.limit(srcBuf.position() + plainDataSize()); + + encSpi.encryptNoPadding(srcBuf, key(), res); + + res.rewind(); + + storeCRC(res); + + srcBuf.limit(srcLimit); + srcBuf.position(srcBuf.position() + encryptionOverhead); + } + + /** + * @param encrypted Encrypted buffer. + * @param destBuf Destination buffer. + */ + private void decrypt(ByteBuffer encrypted, ByteBuffer destBuf) throws IOException { + assert encrypted.remaining() >= pageSize; + assert encrypted.limit() >= pageSize; + + checkCRC(encrypted); + + encrypted.limit(encryptedDataSize()); + + encSpi.decryptNoPadding(encrypted, key(), destBuf); + + destBuf.put(zeroes); //Forcibly purge page buffer tail. + } + + /** + * Stores CRC in res. + * + * @param res Destination buffer. + */ + private void storeCRC(ByteBuffer res) { + int crc = PureJavaCrc32.calcCrc32(res, encryptedDataSize()); + + res.put((byte) (crc >> 24)); + res.put((byte) (crc >> 16)); + res.put((byte) (crc >> 8)); + res.put((byte) crc); + } + + /** + * Checks encrypted data integrity. + * + * @param encrypted Encrypted data buffer. + */ + private void checkCRC(ByteBuffer encrypted) throws IOException { + int crc = PureJavaCrc32.calcCrc32(encrypted, encryptedDataSize()); + + int storedCrc = 0; + + storedCrc |= (int)encrypted.get() << 24; + storedCrc |= ((int)encrypted.get() & 0xff) << 16; + storedCrc |= ((int)encrypted.get() & 0xff) << 8; + storedCrc |= encrypted.get() & 0xff; + + if(crc != storedCrc) { + throw new IOException("Content of encrypted page is broken. [StoredCrc=" + storedCrc + + ", calculatedCrd=" + crc + "]"); + } + + encrypted.position(encrypted.position() - (encryptedDataSize() + 4 /* CRC size. */)); + } + + /** + * @return Encrypted data size. + */ + private int encryptedDataSize() { + return pageSize - encSpi.blockSize(); + } + + /** + * @return Plain data size. + */ + private int plainDataSize() { + return pageSize - encryptionOverhead; + } + + /** */ + private boolean tailIsEmpty(ByteBuffer src, int pageType) { + int srcPos = src.position(); + + src.position(srcPos + plainDataSize()); + + for (int i = 0; i < encryptionOverhead; i++) + assert src.get() == 0 : "Tail of src should be empty [i=" + i + ", pageType=" + pageType + "]"; + + src.position(srcPos); + + return true; + } + + /** + * @return Encryption key. + */ + private Serializable key() { + if (encKey == null) + return encKey = encMgr.groupKey(groupId); + + return encKey; + } + + /** {@inheritDoc} */ + @Override public int write(byte[] buf, int off, int len) throws IOException { + throw new UnsupportedOperationException("Encrypted File doesn't support this operation"); + } + + /** {@inheritDoc} */ + @Override public int writeFully(byte[] buf, int off, int len) throws IOException { + return write(buf, off, len); + } + + /** {@inheritDoc} */ + @Override public MappedByteBuffer map(int sizeBytes) throws IOException { + throw new UnsupportedOperationException("Encrypted File doesn't support this operation"); + } + + /** {@inheritDoc} */ + @Override public void force() throws IOException { + plainFileIO.force(); + } + + /** {@inheritDoc} */ + @Override public void force(boolean withMetadata) throws IOException { + plainFileIO.force(withMetadata); + } + + /** {@inheritDoc} */ + @Override public long size() throws IOException { + return plainFileIO.size(); + } + + /** {@inheritDoc} */ + @Override public void clear() throws IOException { + plainFileIO.clear(); + } + + /** {@inheritDoc} */ + @Override public void close() throws IOException { + plainFileIO.close(); + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIOFactory.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIOFactory.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIOFactory.java new file mode 100644 index 0000000..336aab6 --- /dev/null +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/EncryptedFileIOFactory.java @@ -0,0 +1,100 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.apache.ignite.internal.processors.cache.persistence.file; + +import java.io.File; +import java.io.IOException; +import java.nio.file.OpenOption; +import org.apache.ignite.spi.encryption.EncryptionSpi; +import org.apache.ignite.internal.managers.encryption.GridEncryptionManager; + +/** + * Factory to produce {@code EncryptedFileIO}. + */ +public class EncryptedFileIOFactory implements FileIOFactory { + /** */ + private static final long serialVersionUID = 0L; + + /** + * Factory to produce underlying {@code FileIO} instances. + */ + private FileIOFactory plainIOFactory; + + /** + * Size of plain data page in bytes. + */ + private int pageSize; + + /** + * Size of file header in bytes. + */ + private int headerSize; + + /** + * Group id. + */ + private int groupId; + + /** + * Encryption manager. + */ + private GridEncryptionManager encMgr; + + /** + * Encryption spi. + */ + private EncryptionSpi encSpi; + + /** + * @param plainIOFactory Underlying file factory. + * @param groupId Group id. + * @param pageSize Size of plain data page in bytes. + * @param encMgr Encryption manager. + */ + EncryptedFileIOFactory(FileIOFactory plainIOFactory, int groupId, int pageSize, GridEncryptionManager encMgr, + EncryptionSpi encSpi) { + this.plainIOFactory = plainIOFactory; + this.groupId = groupId; + this.pageSize = pageSize; + this.encMgr = encMgr; + this.encSpi = encSpi; + } + + /** {@inheritDoc} */ + @Override public FileIO create(File file) throws IOException { + FileIO io = plainIOFactory.create(file); + + return new EncryptedFileIO(io, groupId, pageSize, headerSize, encMgr, encSpi); + } + + /** {@inheritDoc} */ + @Override public FileIO create(File file, OpenOption... modes) throws IOException { + FileIO io = plainIOFactory.create(file, modes); + + return new EncryptedFileIO(io, groupId, pageSize, headerSize, encMgr, encSpi); + } + + /** + * Sets size of file header in bytes. + * + * @param headerSize Size of file header in bytes. + */ + void headerSize(int headerSize) { + this.headerSize = headerSize; + } +} http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStore.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStore.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStore.java index 110807c..2e07867 100755 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStore.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStore.java @@ -235,11 +235,8 @@ public class FilePageStore implements PageStore { return fileSize; } - /** - * @param delete {@code True} to delete file. - * @throws StorageException If failed in case of underlying I/O exception. - */ - public void stop(boolean delete) throws StorageException { + /** {@inheritDoc} */ + @Override public void stop(boolean delete) throws StorageException { lock.writeLock().lock(); try { @@ -264,13 +261,8 @@ public class FilePageStore implements PageStore { } } - /** - * Truncates and deletes partition file. - * - * @param tag New partition tag. - * @throws StorageException If failed in case of underlying I/O exception. - */ - public void truncate(int tag) throws StorageException { + /** {@inheritDoc} */ + @Override public void truncate(int tag) throws StorageException { init(); lock.writeLock().lock(); @@ -298,10 +290,8 @@ public class FilePageStore implements PageStore { } } - /** - * - */ - public void beginRecover() { + /** {@inheritDoc} */ + @Override public void beginRecover() { lock.writeLock().lock(); try { @@ -312,10 +302,8 @@ public class FilePageStore implements PageStore { } } - /** - * @throws StorageException If failed in case of underlying I/O exception. - */ - public void finishRecover() throws StorageException { + /** {@inheritDoc} */ + @Override public void finishRecover() throws StorageException { lock.writeLock().lock(); try { http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreFactory.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreFactory.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreFactory.java index fe93d07..2fb1d50 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreFactory.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreFactory.java @@ -20,6 +20,7 @@ package org.apache.ignite.internal.processors.cache.persistence.file; import java.io.File; import org.apache.ignite.IgniteCheckedException; import org.apache.ignite.internal.pagemem.PageIdAllocator; +import org.apache.ignite.internal.pagemem.store.PageStore; import org.apache.ignite.internal.processors.cache.persistence.AllocatedPageTracker; /** @@ -32,5 +33,5 @@ public interface FilePageStoreFactory { * @param type Data type, can be {@link PageIdAllocator#FLAG_IDX} or {@link PageIdAllocator#FLAG_DATA}. * @param file File Page store file. */ - public FilePageStore createPageStore(byte type, File file, AllocatedPageTracker allocatedTracker) throws IgniteCheckedException; + PageStore createPageStore(byte type, File file, AllocatedPageTracker allocatedTracker) throws IgniteCheckedException; } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreManager.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreManager.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreManager.java index 101a33d..c6cd9e5 100755 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreManager.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FilePageStoreManager.java @@ -262,7 +262,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen for (CacheStoreHolder holder : idxCacheStores.values()) { holder.idxStore.beginRecover(); - for (FilePageStore partStore : holder.partStores) + for (PageStore partStore : holder.partStores) partStore.beginRecover(); } } @@ -273,7 +273,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen for (CacheStoreHolder holder : idxCacheStores.values()) { holder.idxStore.finishRecover(); - for (FilePageStore partStore : holder.partStores) + for (PageStore partStore : holder.partStores) partStore.finishRecover(); } } @@ -292,7 +292,8 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen new File(storeWorkDir, workingDir), cacheId, partitions, - tracker + tracker, + cctx.cacheContext(cacheId) != null && cctx.cacheContext(cacheId).config().isEncryptionEnabled() ); CacheStoreHolder old = idxCacheStores.put(cacheId, holder); @@ -321,9 +322,10 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen if (!idxCacheStores.containsKey(grpId)) { CacheStoreHolder holder = initDir( new File(storeWorkDir, META_STORAGE_NAME), - grpId, - 1, - AllocatedPageTracker.NO_OP ); + grpId, + 1, + AllocatedPageTracker.NO_OP, + false); CacheStoreHolder old = idxCacheStores.put(grpId, holder); @@ -400,9 +402,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen PageStore store = getStore(grpId, partId); - assert store instanceof FilePageStore : store; - - ((FilePageStore)store).truncate(tag); + store.truncate(tag); } /** {@inheritDoc} */ @@ -521,7 +521,8 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen cacheWorkDir, grpDesc.groupId(), grpDesc.config().getAffinity().partitions(), - allocatedTracker + allocatedTracker, + ccfg.isEncryptionEnabled() ); } @@ -530,13 +531,15 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen * @param grpId Group ID. * @param partitions Number of partitions. * @param allocatedTracker Metrics updater. + * @param encrypted {@code True} if this cache encrypted. * @return Cache store holder. * @throws IgniteCheckedException If failed. */ private CacheStoreHolder initDir(File cacheWorkDir, int grpId, int partitions, - AllocatedPageTracker allocatedTracker) throws IgniteCheckedException { + AllocatedPageTracker allocatedTracker, + boolean encrypted) throws IgniteCheckedException { try { boolean dirExisted = checkAndInitCacheWorkDir(cacheWorkDir); @@ -545,19 +548,48 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen if (dirExisted && !idxFile.exists()) grpsWithoutIdx.add(grpId); - FilePageStoreFactory pageStoreFactory = new FileVersionCheckingFactory( - pageStoreFileIoFactory, pageStoreV1FileIoFactory, igniteCfg.getDataStorageConfiguration()); - FilePageStore idxStore = + FileIOFactory pageStoreFileIoFactory = this.pageStoreFileIoFactory; + FileIOFactory pageStoreV1FileIoFactory = this.pageStoreV1FileIoFactory; + + if (encrypted) { + pageStoreFileIoFactory = new EncryptedFileIOFactory( + this.pageStoreFileIoFactory, + grpId, + pageSize(), + cctx.kernalContext().encryption(), + cctx.gridConfig().getEncryptionSpi()); + + pageStoreV1FileIoFactory = new EncryptedFileIOFactory( + this.pageStoreV1FileIoFactory, + grpId, + pageSize(), + cctx.kernalContext().encryption(), + cctx.gridConfig().getEncryptionSpi()); + } + + FileVersionCheckingFactory pageStoreFactory = new FileVersionCheckingFactory( + pageStoreFileIoFactory, + pageStoreV1FileIoFactory, + igniteCfg.getDataStorageConfiguration()); + + if (encrypted) { + int headerSize = pageStoreFactory.headerSize(pageStoreFactory.latestVersion()); + + ((EncryptedFileIOFactory)pageStoreFileIoFactory).headerSize(headerSize); + ((EncryptedFileIOFactory)pageStoreV1FileIoFactory).headerSize(headerSize); + } + + PageStore idxStore = pageStoreFactory.createPageStore( PageMemory.FLAG_IDX, idxFile, allocatedTracker); - FilePageStore[] partStores = new FilePageStore[partitions]; + PageStore[] partStores = new PageStore[partitions]; for (int partId = 0; partId < partStores.length; partId++) { - FilePageStore partStore = + PageStore partStore = pageStoreFactory.createPageStore( PageMemory.FLAG_DATA, getPartitionFile(cacheWorkDir, partId), @@ -885,7 +917,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen @Nullable IgniteCheckedException aggr) { aggr = shutdown(holder.idxStore, cleanFile, aggr); - for (FilePageStore store : holder.partStores) { + for (PageStore store : holder.partStores) { if (store != null) aggr = shutdown(store, cleanFile, aggr); } @@ -942,7 +974,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen * @param aggr Aggregating exception. * @return Aggregating exception, if error occurred. */ - private IgniteCheckedException shutdown(FilePageStore store, boolean cleanFile, IgniteCheckedException aggr) { + private IgniteCheckedException shutdown(PageStore store, boolean cleanFile, IgniteCheckedException aggr) { try { if (store != null) store.stop(cleanFile); @@ -978,7 +1010,7 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen if (partId > PageIdAllocator.MAX_PARTITION_ID) throw new IgniteCheckedException("Partition ID is reserved: " + partId); - FilePageStore store = holder.partStores[partId]; + PageStore store = holder.partStores[partId]; if (store == null) throw new IgniteCheckedException("Failed to get page store for the given partition ID " + @@ -1038,15 +1070,15 @@ public class FilePageStoreManager extends GridCacheSharedManagerAdapter implemen */ private static class CacheStoreHolder { /** Index store. */ - private final FilePageStore idxStore; + private final PageStore idxStore; /** Partition stores. */ - private final FilePageStore[] partStores; + private final PageStore[] partStores; /** * */ - CacheStoreHolder(FilePageStore idxStore, FilePageStore[] partStores) { + public CacheStoreHolder(PageStore idxStore, PageStore[] partStores) { this.idxStore = idxStore; this.partStores = partStores; } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FileVersionCheckingFactory.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FileVersionCheckingFactory.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FileVersionCheckingFactory.java index bc938a5..af478de 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FileVersionCheckingFactory.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/file/FileVersionCheckingFactory.java @@ -62,14 +62,6 @@ public class FileVersionCheckingFactory implements FilePageStoreFactory { this.memCfg = memCfg; } - /** - * @param fileIOFactory File IO factory for V1 & V2 page store and for version checking. - * @param memCfg Memory configuration. - */ - public FileVersionCheckingFactory(FileIOFactory fileIOFactory, DataStorageConfiguration memCfg) { - this(fileIOFactory, fileIOFactory, memCfg); - } - /** {@inheritDoc} */ @Override public FilePageStore createPageStore( byte type, @@ -140,4 +132,21 @@ public class FileVersionCheckingFactory implements FilePageStoreFactory { throw new IllegalArgumentException("Unknown version of file page store: " + ver + " for file [" + file.getAbsolutePath() + "]"); } } + + /** + * @param ver Version. + * @return Header size. + */ + public int headerSize(int ver) { + switch (ver) { + case FilePageStore.VERSION: + return FilePageStore.HEADER_SIZE; + + case FilePageStoreV2.VERSION: + return memCfg.getPageSize(); + + default: + throw new IllegalArgumentException("Unknown version of file page store."); + } + } } http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/freelist/PagesList.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/freelist/PagesList.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/freelist/PagesList.java index 831465d..f1cc32a 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/freelist/PagesList.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/freelist/PagesList.java @@ -276,7 +276,9 @@ public abstract class PagesList extends DataStructure { int tailIdx = 0; while (tailIdx < tails.length) { - int written = curPage != 0L ? curIo.addTails(pageMem.pageSize(), curAddr, bucket, tails, tailIdx) : 0; + int written = curPage != 0L ? + curIo.addTails(pageMem.realPageSize(grpId), curAddr, bucket, tails, tailIdx) : + 0; if (written == 0) { if (nextPageId == 0L) { http://git-wip-us.apache.org/repos/asf/ignite/blob/8ae9c180/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/metastorage/MetaStorage.java ---------------------------------------------------------------------- diff --git a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/metastorage/MetaStorage.java b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/metastorage/MetaStorage.java index 556d997..3981d4d 100644 --- a/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/metastorage/MetaStorage.java +++ b/modules/core/src/main/java/org/apache/ignite/internal/processors/cache/persistence/metastorage/MetaStorage.java @@ -361,6 +361,7 @@ public class MetaStorage implements DbCheckpointListener, ReadOnlyMetastorage, R // Initialize new page. PagePartitionMetaIO io = PagePartitionMetaIO.VERSIONS.latest(); + //MetaStorage never encrypted so realPageSize == pageSize. io.initNewPage(pageAddr, partMetaId, pageMem.pageSize()); treeRoot = pageMem.allocatePage(METASTORAGE_CACHE_ID, partId, PageMemory.FLAG_DATA); @@ -537,6 +538,7 @@ public class MetaStorage implements DbCheckpointListener, ReadOnlyMetastorage, R try { SimpleDataPageIO io = (SimpleDataPageIO)ioVersions().forPage(pageAddr); + //MetaStorage never encrypted so realPageSize == pageSize. DataPagePayload data = io.readPayload(pageAddr, itemId(nextLink), pageMem.pageSize()); nextLink = data.nextLink();
