diff --git a/integrations/api_repo_git_tags_test.go b/integrations/api_repo_git_tags_test.go
index ef2e1ccd08..ad710a4520 100644
--- a/integrations/api_repo_git_tags_test.go
+++ b/integrations/api_repo_git_tags_test.go
@@ -50,7 +50,7 @@ func TestAPIGitTags(t *testing.T) {
 	assert.Equal(t, aTagName, tag.Tag)
 	assert.Equal(t, aTag.ID.String(), tag.SHA)
 	assert.Equal(t, commit.ID.String(), tag.Object.SHA)
-	assert.Equal(t, aTagMessage, tag.Message)
+	assert.Equal(t, aTagMessage+"\n", tag.Message)
 	assert.Equal(t, user.Name, tag.Tagger.Name)
 	assert.Equal(t, user.Email, tag.Tagger.Email)
 	assert.Equal(t, util.URLJoin(repo.APIURL(), "git/tags", aTag.ID.String()), tag.URL)
diff --git a/modules/git/repo_tree_nogogit.go b/modules/git/repo_tree_nogogit.go
index 416205d8a0..867c3fa5aa 100644
--- a/modules/git/repo_tree_nogogit.go
+++ b/modules/git/repo_tree_nogogit.go
@@ -33,7 +33,7 @@ func (repo *Repository) getTree(id SHA1) (*Tree, error) {
 
 	bufReader := bufio.NewReader(stdoutReader)
 	// ignore the SHA
-	_, typ, _, err := ReadBatchLine(bufReader)
+	_, typ, size, err := ReadBatchLine(bufReader)
 	if err != nil {
 		return nil, err
 	}
@@ -41,7 +41,7 @@ func (repo *Repository) getTree(id SHA1) (*Tree, error) {
 	switch typ {
 	case "tag":
 		resolvedID := id
-		data, err := ioutil.ReadAll(bufReader)
+		data, err := ioutil.ReadAll(io.LimitReader(bufReader, size))
 		if err != nil {
 			return nil, err
 		}
@@ -57,7 +57,7 @@ func (repo *Repository) getTree(id SHA1) (*Tree, error) {
 		log("tag.commit.Tree: %s %v", commit.Tree.ID.String(), commit.Tree.repo)
 		return &commit.Tree, nil
 	case "commit":
-		commit, err := CommitFromReader(repo, id, bufReader)
+		commit, err := CommitFromReader(repo, id, io.LimitReader(bufReader, size))
 		if err != nil {
 			_ = stdoutReader.CloseWithError(err)
 			return nil, err
diff --git a/modules/git/tag.go b/modules/git/tag.go
index d58a9a202d..0323cc42ed 100644
--- a/modules/git/tag.go
+++ b/modules/git/tag.go
@@ -64,7 +64,7 @@ l:
 			}
 			nextline += eol + 1
 		case eol == 0:
-			tag.Message = string(data[nextline+1 : len(data)-1])
+			tag.Message = string(data[nextline+1:])
 			break l
 		default:
 			break l
diff --git a/modules/git/tag_test.go b/modules/git/tag_test.go
new file mode 100644
index 0000000000..3aa49df4b2
--- /dev/null
+++ b/modules/git/tag_test.go
@@ -0,0 +1,76 @@
+// Copyright 2020 The Gitea Authors. All rights reserved.
+// Use of this source code is governed by a MIT-style
+// license that can be found in the LICENSE file.
+
+package git
+
+import (
+	"testing"
+	"time"
+
+	"github.com/stretchr/testify/assert"
+)
+
+func Test_parseTagData(t *testing.T) {
+	testData := []struct {
+		data []byte
+		tag  Tag
+	}{
+		{data: []byte(`object 3b114ab800c6432ad42387ccf6bc8d4388a2885a
+type commit
+tag 1.22.0
+tagger Lucas Michot <lucas@semalead.com> 1484491741 +0100
+
+`), tag: Tag{
+			Name:      "",
+			ID:        SHA1{},
+			repo:      nil,
+			Object:    SHA1{0x3b, 0x11, 0x4a, 0xb8, 0x0, 0xc6, 0x43, 0x2a, 0xd4, 0x23, 0x87, 0xcc, 0xf6, 0xbc, 0x8d, 0x43, 0x88, 0xa2, 0x88, 0x5a},
+			Type:      "commit",
+			Tagger:    &Signature{Name: "Lucas Michot", Email: "lucas@semalead.com", When: time.Unix(1484491741, 0)},
+			Message:   "",
+			Signature: nil,
+		}},
+		{data: []byte(`object 7cdf42c0b1cc763ab7e4c33c47a24e27c66bfccc
+type commit
+tag 1.22.1
+tagger Lucas Michot <lucas@semalead.com> 1484553735 +0100
+
+test message
+o
+
+ono`), tag: Tag{
+			Name:      "",
+			ID:        SHA1{},
+			repo:      nil,
+			Object:    SHA1{0x7c, 0xdf, 0x42, 0xc0, 0xb1, 0xcc, 0x76, 0x3a, 0xb7, 0xe4, 0xc3, 0x3c, 0x47, 0xa2, 0x4e, 0x27, 0xc6, 0x6b, 0xfc, 0xcc},
+			Type:      "commit",
+			Tagger:    &Signature{Name: "Lucas Michot", Email: "lucas@semalead.com", When: time.Unix(1484553735, 0)},
+			Message:   "test message\no\n\nono",
+			Signature: nil,
+		}},
+	}
+
+	for _, test := range testData {
+		tag, err := parseTagData(test.data)
+		assert.NoError(t, err)
+		assert.EqualValues(t, test.tag.ID, tag.ID)
+		assert.EqualValues(t, test.tag.Object, tag.Object)
+		assert.EqualValues(t, test.tag.Name, tag.Name)
+		assert.EqualValues(t, test.tag.Message, tag.Message)
+		assert.EqualValues(t, test.tag.Type, tag.Type)
+		if test.tag.Signature != nil && assert.NotNil(t, tag.Signature) {
+			assert.EqualValues(t, test.tag.Signature.Signature, tag.Signature.Signature)
+			assert.EqualValues(t, test.tag.Signature.Payload, tag.Signature.Payload)
+		} else {
+			assert.Nil(t, tag.Signature)
+		}
+		if test.tag.Tagger != nil && assert.NotNil(t, tag.Tagger) {
+			assert.EqualValues(t, test.tag.Tagger.Name, tag.Tagger.Name)
+			assert.EqualValues(t, test.tag.Tagger.Email, tag.Tagger.Email)
+			assert.EqualValues(t, test.tag.Tagger.When.Unix(), tag.Tagger.When.Unix())
+		} else {
+			assert.Nil(t, tag.Tagger)
+		}
+	}
+}