@@ -2,6 +2,7 @@ package gateway
22
33import (
44 "context"
5+ "encoding/binary"
56 "fmt"
67 "io"
78 "net/http"
@@ -224,31 +225,43 @@ func getCarRootCidAndLastSegment(imPath path.ImmutablePath) (cid.Cid, string, er
224225}
225226
226227func getCarEtag (imPath path.ImmutablePath , params CarParams , rootCid cid.Cid ) string {
227- data := imPath .String ()
228+ h := xxhash .New ()
229+ h .WriteString (imPath .String ())
230+ // be careful with hashes here, we need boundries and per entry salt, we don't want a request that has:
231+ // - scope = dfs
232+ // and:
233+ // - order = dfs
234+ // to result in the same hash because if we just do hash(scope + order) they would both yield hash("dfs").
228235 if params .Scope != DagScopeAll {
229- data += string (params .Scope )
236+ h .WriteString ("\x00 scope=" )
237+ h .WriteString (string (params .Scope ))
230238 }
231239
232240 // 'order' from IPIP-412 impact Etag only if set to something else
233241 // than DFS (which is the implicit default)
234242 if params .Order != DagOrderDFS {
235- data += string (params .Order )
243+ h .WriteString ("\x00 order=" )
244+ h .WriteString (string (params .Order ))
236245 }
237246
238247 // 'dups' from IPIP-412 impact Etag only if 'y'
239- if dups := params .Duplicates . String () ; dups == "y" {
240- data += dups
248+ if dups := params .Duplicates ; dups == DuplicateBlocksIncluded {
249+ h . WriteString ( " \x00 dups=y" )
241250 }
242251
243252 if params .Range != nil {
244253 if params .Range .From != 0 || params .Range .To != nil {
245- data += strconv .FormatInt (params .Range .From , 10 )
254+ h .WriteString ("\x00 range=" )
255+ var b [8 ]byte
256+ binary .LittleEndian .PutUint64 (b [:], uint64 (params .Range .From ))
257+ h .Write (b [:])
246258 if params .Range .To != nil {
247- data += strconv .FormatInt (* params .Range .To , 10 )
259+ binary .LittleEndian .PutUint64 (b [:], uint64 (* params .Range .To ))
260+ h .Write (b [:])
248261 }
249262 }
250263 }
251264
252- suffix := strconv .FormatUint (xxhash .Sum64 ([] byte ( data ) ), 32 )
265+ suffix := strconv .FormatUint (h .Sum64 (), 32 )
253266 return `W/"` + rootCid .String () + ".car." + suffix + `"`
254267}
0 commit comments