@cryptotaxi247 / kubo / commits / 54f6e9087

fix: change CID breaking logic when parsing ipld.ErrNotFound

This commit was moved from ipfs/go-ipfs-http-client@a3b49352bfd1b885567018092a06f303de18b7aa

Jorropo committed Apr 2, 2022 at 03:25 UTC 54f6e90870c61a686f57b0bd0f1ad4923615897b
2 files changed +16 -26
client/httpapi/errors.go
+9 -15
@@ -47,18 +47,6 @@ func parseErrNotFoundWithFallbackToError(msg error) error {
47 return msg
48 }
49
50 -// Use a string to move it into RODATA
51 -// print("".join("\\x01" if chr(i) not in string.ascii_letters + string.digits else "\\x00" for i in range(ord('z')+1)))
52 -const notAsciiLetterOrDigitsLUT = "\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x01\x01\x01\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x01\x01\x01\x01\x01\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00"
53 -
54 -func notAsciiLetterOrDigits(r rune) bool {
55 - if r > 'z' {
56 - return true
57 - }
58 -
59 - return notAsciiLetterOrDigitsLUT[r] > 0
60 -}
61 -
50 //lint:ignore ST1008 this function is not using the error as a mean to return failure but it massages it to return the correct type
51 func parseErrNotFound(msg string) (error, bool) {
52 if msg == "" {
@@ -76,6 +64,12 @@ func parseErrNotFound(msg string) (error, bool) {
64 return nil, false
65 }
66
67 +// Assume CIDs break on:
68 +// - Whitespaces: " \t\n\r\v\f"
69 +// - Semicolon: ";" this is to parse ipld.ErrNotFound wrapped in multierr
70 +// - Double Quotes: "\"" this is for parsing %q and %#v formating
71 +const cidBreakSet = " \t\n\r\v\f;\""
72 +
73 //lint:ignore ST1008 using error as values
74 func parseIPLDErrNotFound(msg string) (error, bool) {
75 // The patern we search for is:
@@ -99,9 +93,9 @@ func parseIPLDErrNotFound(msg string) (error, bool) {
93 c = cid.Undef
94 postIndex = len("node")
95 } else {
102 - // Assume that CIDs only contain a-zA-Z0-9 characters.
103 - // This is true because go-ipld-format use go-cid#Cid.String which use base{3{2,6},58}.
104 - postIndex = strings.IndexFunc(msgPostKey, notAsciiLetterOrDigits)
96 + postIndex = strings.IndexFunc(msgPostKey, func(r rune) bool {
97 + return strings.ContainsAny(string(r), cidBreakSet)
98 + })
99 if postIndex < 0 {
100 postIndex = len(msgPostKey)
101 }
client/httpapi/errors_test.go
+7 -11
@@ -3,7 +3,6 @@ package httpapi
3 import (
4 "errors"
5 "fmt"
6 - "strings"
6 "testing"
7
8 "github.com/ipfs/go-cid"
@@ -36,12 +35,17 @@ func TestParseIPLDNotFound(t *testing.T) {
35 t.Errorf("expected empty string to give no error; got %T %q", err, err.Error())
36 }
37
39 - for _, wrap := range [...]string{
38 + cidBreaks := make([]string, len(cidBreakSet))
39 + for i, v := range cidBreakSet {
40 + cidBreaks[i] = "%w" + string(v)
41 + }
42 +
43 + for _, wrap := range append(cidBreaks,
44 "",
45 "merkledag: %w",
46 "testing: %w the test",
47 "%w is wrong",
44 - } {
48 + ) {
49 for _, err := range [...]error{
50 errors.New("ipld: could not find "),
51 errors.New("ipld: could not find Bad_CID"),
@@ -79,11 +83,3 @@ func TestBlockstoreNotFoundMatchingIPLDErrNotFound(t *testing.T) {
83 doParseIpldNotFoundTest(t, err)
84 }
85 }
82 -
83 -func TestNotAsciiLetterOrDigits(t *testing.T) {
84 - for i := rune(0); i <= 256; i++ {
85 - if notAsciiLetterOrDigits(i) != !strings.ContainsAny(string(i), "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789") {
86 - t.Errorf("%q is incorrectly identified", i)
87 - }
88 - }
89 -}