-
Notifications
You must be signed in to change notification settings - Fork 1.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Detect and prevent mixed raw and non-raw sends #8308
Conversation
|
@DeHackEd We're still working on on-disk reverse compatibility, but |
@@ -2485,6 +2529,8 @@ dsl_crypto_populate_key_nvlist(dsl_dataset_t *ds, nvlist_t **nvl_out) | |||
fnvlist_add_uint64(nvl, "mdn_indblkshift", mdn->dn_indblkshift); | |||
fnvlist_add_uint64(nvl, "mdn_nblkptr", mdn->dn_nblkptr); | |||
fnvlist_add_uint64(nvl, "mdn_maxblkid", mdn->dn_maxblkid); | |||
fnvlist_add_uint64(nvl, "to_ivset_guid", to_ivset_guid); | |||
fnvlist_add_uint64(nvl, "from_ivset_guid", from_ivset_guid); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
maybe we should only add these if they are nonzero?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My thought process at the time was that this would allow us to identify source systems that have the new version of zfs that supports ivset guids, but are sending an old snapshot without one set.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does the code care about that, or is that just in case developers want to inspect the send stream with zstreamdump and make inferences based on it?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thats just mostly for developers / debugging.
d16a8b2
to
f79bb53
Compare
f79bb53
to
00183bc
Compare
00183bc
to
7c00f93
Compare
All the code and tests should now be ready for review. I'm still working on the wording for the errata page, but I expect that PR should be made tomorrow. |
Codecov Report
@@ Coverage Diff @@
## master #8308 +/- ##
==========================================
+ Coverage 78.53% 78.72% +0.18%
==========================================
Files 380 380
Lines 116007 116091 +84
==========================================
+ Hits 91108 91391 +283
+ Misses 24899 24700 -199
Continue to review full report at Codecov.
|
This is what we are all waiting on yes? :) Will fix that last issue? |
Hopefully, yes. |
b58560d
to
6f87f6d
Compare
Related errata documentation PR for the website: zfsonlinux/zfsonlinux.github.com#45 |
For reference, these are the commands used to generate the test pool for the errata handling test:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks good. I'll see about doing some additional manual testing latter this week. In the meanwhile, it looks like this change introduced a small memory leak and it needs to be rebased.
tests/zfs-tests/tests/functional/cli_root/zpool_import/zpool_import_errata4.ksh
Outdated
Show resolved
Hide resolved
This patch adds the bookmark v2 feature to the on-disk format. This feature will be needed for the upcoming redacted sends and for an upcoming fix that for raw receives. The feature is not currently used by any code and thus thich change is a no-op, aside from the fact that the user can now enable the feature. Signed-off-by: Tom Caputi <[email protected]>
6f87f6d
to
f4d2f6f
Compare
@behlendorf your comments have been addressed. The memory leak was actually an existing leak that the new tests exposed (now fixed in the PR). I would appreciate it if someone could look at the changes related to that to make sure I didn't miss any cases. The fixes for that are all in |
Currently, there is an issue in the raw receive code where raw receives are allowed to happen on top of previously non-raw received datasets. This is a problem because the source-side dataset doesn't know about how the blocks on the destination were encrypted. As a result, any MAC in the objset's checksum-of-MACs tree that is a parent of both blocks encrypted on the source and blocks encrypted by the destination will be incorrect. This will result in authentication errors when we decrypt the dataset. This patch fixes this issue by adding a new check to the raw receive code. The code now maintains an "IVset guid", which acts as an identifier for the set of IVs used to encrypt a given snapshot. When a snapshot is raw received, the destination snapshot will take this value from the DRR_BEGIN payload. Non-raw receives and normal "zfs snap" operations will cause ZFS to generate a new IVset guid. When a raw incremental stream is received, ZFS will check that the "from" IVset guid in the stream matches that of the "from" destination snapshot. If they do not match, the code will error out the receive, preventing the problem. This patch requires an on-disk format change to add the IVset guids to snapshots and bookmarks. As a result, this patch has errata handling and a tunable to help affected users resolve the issue with as little interruption as possible. Signed-off-by: Tom Caputi <[email protected]>
f4d2f6f
to
6337e5f
Compare
@@ -2485,6 +2529,8 @@ dsl_crypto_populate_key_nvlist(dsl_dataset_t *ds, nvlist_t **nvl_out) | |||
fnvlist_add_uint64(nvl, "mdn_indblkshift", mdn->dn_indblkshift); | |||
fnvlist_add_uint64(nvl, "mdn_nblkptr", mdn->dn_nblkptr); | |||
fnvlist_add_uint64(nvl, "mdn_maxblkid", mdn->dn_maxblkid); | |||
fnvlist_add_uint64(nvl, "to_ivset_guid", to_ivset_guid); | |||
fnvlist_add_uint64(nvl, "from_ivset_guid", from_ivset_guid); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Does the code care about that, or is that just in case developers want to inspect the send stream with zstreamdump and make inferences based on it?
module/zfs/zcp_get.c
Outdated
case ZFS_PROP_IVSET_GUID: | ||
error = zap_lookup(ds->ds_dir->dd_pool->dp_meta_objset, | ||
ds->ds_object, DS_FIELD_IVSET_GUID, sizeof (numval), | ||
1, &numval); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Doing this without checking if the dataset is zapified won't work right, for a few reasons:
- on debug bits, this will panic (see zap_lockdir())
- on nondebug bits on other platforms (e.g. illumos), this will probably panic, since the check in zap_lockdir_impl() is unique to ZoL.
- on nondebug bits on ZoL, this will return EINVAL (incorrect channel program) when we want ENOENT (property not present). See zcp_handle_error().
(it would make my life easier if new changes were new commits instead of force-pushed over the one, and only squashed right before merging at the end :) ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Other than matt's comments, everything looks good to me. I was mostly looking at the send/recv logic, since that's what I know best.
526e4d8
to
f035853
Compare
Squash this commit before merging. Signed-off-by: Tom Caputi <[email protected]>
Squash this before merging Signed-off-by: Tom Caputi <[email protected]>
This patch adds the bookmark v2 feature to the on-disk format. This feature will be needed for the upcoming redacted sends and for an upcoming fix that for raw receives. The feature is not currently used by any code and thus this change is a no-op, aside from the fact that the user can now enable the feature. Reviewed-by: Paul Dagnelie <[email protected]> Reviewed-by: Brian Behlendorf <[email protected]> Reviewed-by: Matt Ahrens <[email protected]> Signed-off-by: Tom Caputi <[email protected]> Issue #8308
This patch attempts to address some user concerns that have arisen since errata 4 was introduced. * The errata warning has been made less scary for users without any encrypted datasets. * The errata warning now clears itself without a pool reimport if the bookmark_v2 feature is enabled and no encrypted datasets exist. * It is no longer possible to create new encrypted datasets without enabling the bookmark_v2 feature, thus helping to ensure that the errata is resolved. Reviewed-by: Brian Behlendorf <[email protected]> Signed-off-by: Tom Caputi <[email protected]> Issue ##8308 Closes #8504
is there any way an existing pool with the top-level-dataset being an encrypted one to transfer the data on the pool? Or will I have to backup the pool, destroy it and start fresh? |
Hmmm. That is a good point. @behlendorf do you know of a way to do this? |
Good question. Sorry no, I can't think of a great way to do this. |
ugh, ok, thx. Note to self: Never create root datasets with experimental features 😆 |
@kpande It is possible to create a different encryption root, but that doesn't help me in getting rid of the top dataset. I think this should maybe be made clear for Admins in Errata #4? Like "if you have a top-level |
Currently, there is an issue in the raw receive code where
raw receives are allowed to happen on top of previously
non-raw received datasets. This is a problem because the
source-side dataset doesn't know about how the blocks on
the destination were encrypted. As a result, any MAC in
the objset's checksum-of-MACs tree that is a parent of both
blocks encrypted on the source and blocks encrypted by the
destination will be incorrect. This will result in
authentication errors when we decrypt the dataset.
This patch fixes this issue by adding a new check to the
raw receive code. The code now maintains an "IVset guid",
which acts as an identifier for the set of IVs used to
encrypt a given snapshot. When a snapshot is raw received,
the destination snapshot will take this value from the
DRR_BEGIN payload. Non-raw receives and normal "zfs snap"
operations will cause ZFS to generate a new IVset guid.
When a raw incremental stream is received, ZFS will check
that the "from" IVset guid in the stream matches that of
the "from" destination snapshot. If they do not match, the
code will error out the receive, preventing the problem.
WIP: Still working on reverse compatibility for existing encrypted datasets.
Signed-off-by: Tom Caputi [email protected]
Motivation and Context
This issue was originally found and reported by Jason King.
How Has This Been Tested?
send_mixed_raw.ksh has been added to ensure the new code detects and prevents mixed raw. The patch has also been tested against. Some sample datasets that Jason provided and it seems to work correctly now.
Types of changes
Checklist:
Signed-off-by
.