Skip to content

Commit

Permalink
Add Content-Length header to HEAD requests (#14542)
Browse files Browse the repository at this point in the history
* Add Content-Length header to HEAD requests

This change adds the header Content-Length to HEAD HTTP requests.

The previous behaviour was blocking some Windows executables (i.e
bitsadmin.exe) from downloading files hosted in Gitea.

This along with PR #14541, makes the web server compliant with HTTP RFC 2616 which states
"The methods GET and HEAD MUST be supported by all general-purpose servers"
and
"The HEAD method is identical to GET except that the server MUST NOT return a message-body in the response."

This should also respond to issues #8030 and #14532.

* This change adds the header Content-Length to HEAD HTTP requests

Pass the Size of the content as a parameter to ServeData() instead of
calculating it using ioutil.ReadAll(reader) --> this call is dangerous
and can result in a denial of service.

* Add Content-Length header to HEAD requests

Quick fix for imported dependency not used.

* Check if size is positiv int ...

Co-authored-by: zeripath <art27@cantab.net>
  • Loading branch information
faridtsl and zeripath authored Feb 5, 2021
1 parent 4457d0e commit f72ce26
Show file tree
Hide file tree
Showing 2 changed files with 9 additions and 4 deletions.
2 changes: 1 addition & 1 deletion routers/repo/attachment.go
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,7 @@ func GetAttachment(ctx *context.Context) {
return
}

if err = ServeData(ctx, attach.Name, fr); err != nil {
if err = ServeData(ctx, attach.Name, attach.Size, fr); err != nil {
ctx.ServerError("ServeData", err)
return
}
Expand Down
11 changes: 8 additions & 3 deletions routers/repo/download.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ import (
)

// ServeData download file from io.Reader
func ServeData(ctx *context.Context, name string, reader io.Reader) error {
func ServeData(ctx *context.Context, name string, size int64, reader io.Reader) error {
buf := make([]byte, 1024)
n, err := reader.Read(buf)
if err != nil && err != io.EOF {
Expand All @@ -31,6 +31,11 @@ func ServeData(ctx *context.Context, name string, reader io.Reader) error {
}

ctx.Resp.Header().Set("Cache-Control", "public,max-age=86400")
if size >= 0 {
ctx.Resp.Header().Set("Content-Length", fmt.Sprintf("%d", size))
} else {
log.Error("ServeData called to serve data: %s with size < 0: %d", name, size)
}
name = path.Base(name)

// Google Chrome dislike commas in filenames, so let's change it to a space
Expand Down Expand Up @@ -76,7 +81,7 @@ func ServeBlob(ctx *context.Context, blob *git.Blob) error {
}
}()

return ServeData(ctx, ctx.Repo.TreePath, dataRc)
return ServeData(ctx, ctx.Repo.TreePath, blob.Size(), dataRc)
}

// ServeBlobOrLFS download a git.Blob redirecting to LFS if necessary
Expand Down Expand Up @@ -105,7 +110,7 @@ func ServeBlobOrLFS(ctx *context.Context, blob *git.Blob) error {
log.Error("ServeBlobOrLFS: Close: %v", err)
}
}()
return ServeData(ctx, ctx.Repo.TreePath, lfsDataRc)
return ServeData(ctx, ctx.Repo.TreePath, meta.Size, lfsDataRc)
}

return ServeBlob(ctx, blob)
Expand Down

0 comments on commit f72ce26

Please sign in to comment.