-
-
Notifications
You must be signed in to change notification settings - Fork 3k
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
Disallow usage of unsafe hashes for reading and adding content #4751
Conversation
27eb665
to
e643269
Compare
Short observations:
|
Random failure in bitswap:
Passes locally |
Sharness has passed. Restarting tests to make them green. |
Lets not call the package removeme. Lets just put it in thirdparty (Which is already synonymous for removeme at this point). |
blockservice/blockservice.go
Outdated
@@ -149,6 +155,13 @@ func (s *blockService) AddBlock(o blocks.Block) error { | |||
} | |||
|
|||
func (s *blockService) AddBlocks(bs []blocks.Block) error { | |||
//hash security |
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.
for consistency, add a space before the word hash
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.
Code LGTM, could use some tests.
Travis fail looks random
@whyrusleeping I think there might be one issue with this whole code, GC might be failing when there are insecure blocks in the bockstore. |
Regarding GC, if a block can not be read it is unsafe to continue as that block could potentially point to other blocks that should not be removed. There are two solutions (1) somehow allow reading of blocks with insecure hashes, (2) force a repo migration, have the the tool check for insecure blocks and then refuse to upgrade until those blocks are dealt with by the user, the tool should also check if the insure blocks point to secure blocks and inform the user of the situation. We could also also provide a separate tool that will automatically convert insecure hashes to a secure hash of there choosing. |
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.
As far as a stop-gap, this looks good to me (modulo a few more comments for grepability).
blockservice/blockservice.go
Outdated
} | ||
|
||
func getBlock(ctx context.Context, c *cid.Cid, bs blockstore.Blockstore, f exchange.Fetcher) (blocks.Block, error) { | ||
err := verifcid.ValidateCid(c) |
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.
Add // hash security
comment for future grep.
@@ -258,7 +258,7 @@ You can now check what blocks have been created by: | |||
exch = offline.Exchange(addblockstore) | |||
} | |||
|
|||
bserv := blockservice.New(addblockstore, exch) | |||
bserv := blockservice.New(addblockstore, exch) // hash security 001 |
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 this need the hash security comment?
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 is the only place n.Exchnage
is used standalone. ~Kubuxu
edd60bf
to
6e613d3
Compare
As this code still allows the use of CID's with insecure hashes, a potentially easy solution to the GC problem allow the reading of insecure hashes, but disallow the publishing or writing of insecure hashes. This will also provide a gentler upgrade path for the rare case when a user has a repo with insecure hashes. Another solution to just the GC problem is to allow the reading of insecure hashes in the local blockstore, but not the blockservice. This may also allow the user to read them locally, but I am not sure as I think the blockservice is always used even in offline mode. I am also unsure if this will prevent the publishing of insecure hashes. A third solution is to put a special case in the GC code that will dig out the underlying blockstore and use that directly. I like this solution the least. |
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.
Things will break badly in the unlikely event that there are blocks with an insecure hash in the repo. See my other comments.
@Kubuxu @whyrusleeping as I said in IRC I can take over this P.R. if it will help. |
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
@@ -462,25 +463,23 @@ var verifyPinCmd = &cmds.Command{ | |||
cmds.Text: func(res cmds.Response) (io.Reader, error) { | |||
quiet, _, _ := res.Request().Option("quiet").Bool() | |||
|
|||
outChan, ok := res.Output().(<-chan interface{}) | |||
out, err := unwrapOutput(res.Output()) |
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 like its being changed to only emit a single output. Whats going on here?
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.
I would like to know what is going on also.
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.
The marshaller is called for every message pushed down the channel. I am not sure why the legacy layer is doing this but it prints out all the results.
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 is one of the many reasons I've given up on fixing issues with the compat layer and have started just converting commands to use the new system).
test/sharness/t0275-cid-security.sh
Outdated
# should work online | ||
test_launch_ipfs_daemon | ||
test_cat_get | ||
test_kill_ipfs_daemon |
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.
Could you add a test in here that manually puts a bad hash into the datastore, and then runs a gc?
This tenatively looks good to me. I'd like to see a few more tests before moving forward though. |
@Stebalien want to give the gc changes another lookover here? |
@whyrusleeping I've added test for general GC but I am unable to test pin set cases. This is because there is no way to add insecure block to pinset. |
@Kubuxu if there are insecure hashes will those end up being published? |
@kevina you mean by reprovider? Yes but it will continue to work. |
@kevina reprovider won't be providing insecure hashes anymore |
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.
[Please Ignore]
I am not thrilled with the idea of forcing a user to downgrade to read insure hashes, but as a stop-gap measure this will work, especially since it is unlikely that the insure hashes are used much, if at all.
@Kubuxu okay, We should be sure and mark any places where Cid's are verified so that they can cleanly be removed once the strict Cid code lands. |
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.
Please don't grow thirdparty
, I have to extract these modules and it puts more work on me.
@@ -10,6 +10,7 @@ import ( | |||
"io" | |||
|
|||
exchange "github.com/ipfs/go-ipfs/exchange" | |||
"github.com/ipfs/go-ipfs/thirdparty/verifcid" |
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.
We should not be putting more stuff in thirdparty
. If it needs to be re-used across submodules or has interest for other places put it in a different repo, if not, place it in the submodule directly. It complicates extractions afterwards...
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 is temporary measure, it will be removed as we are able to propagate go-cid (code comes from PR to go-cid).
The temporary measure was applied because we want to release ASAP and have this behaviour fixed in this release.
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.
Then place that code as submodules of blockservice
? That way the temporary measure can go together with the temporary code and be fixed with it when it's extracted. Otherwise I will have to do exactly that.
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.
@hsanjuan the reason I want it in thirdparty is explicitly because it needs to be moved to the cid package as soon as possible. But (as you know) we have a bunch of stuff in-flight that prevents us from bubbling up the cid package without other complications, so its going here for now as a "please remove me"
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.
@whyrusleeping sure, I understand the reasons, but it still introduces a blocker for me.
I'm trying to communicate that if it's placed under blockservice
with a "please-remove-me" note it doesn't become a blocker while solving your problem at the same time.
If you say this will be removed from thirdparty
right away after the release, OK. I'm just scared that things will take longer though.
@@ -17,6 +17,7 @@ import ( | |||
pin "github.com/ipfs/go-ipfs/pin" | |||
repo "github.com/ipfs/go-ipfs/repo" | |||
cfg "github.com/ipfs/go-ipfs/repo/config" | |||
"github.com/ipfs/go-ipfs/thirdparty/verifbs" |
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 too
@@ -462,25 +463,23 @@ var verifyPinCmd = &cmds.Command{ | |||
cmds.Text: func(res cmds.Response) (io.Reader, error) { | |||
quiet, _, _ := res.Request().Option("quiet").Bool() | |||
|
|||
outChan, ok := res.Output().(<-chan interface{}) | |||
out, err := unwrapOutput(res.Output()) |
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 is one of the many reasons I've given up on fixing issues with the compat layer and have started just converting commands to use the new system).
Failure:
|
missed file from commit, fixing (I didn't notice the CI failures for some reason). |
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
License: MIT Signed-off-by: Jakub Sztandera <kubuxu@protonmail.ch>
Fixed |
Alright, here goes. |
Should be done