From eb6ab2e84ab184321bd649b4def182f93e62b6df Mon Sep 17 00:00:00 2001
From: xiadanni <xiadanni1@huawei.com>
Date: Mon, 24 Jan 2022 19:03:30 +0800
Subject: [PATCH] [Backport]treat manifest provided URLs differently

fix CVE-2020-15157

Conflict:NA
Reference:https://github.com/containerd/containerd/commit/1ead8d9deb3b175bf40413b8c47b3d19c2262726
https://github.com/containerd/containerd/commit/abbb17959f55bbb9b7eb37f965d7dad2f4ea8744

Signed-off-by: xiadanni <xiadanni1@huawei.com>
---
 remotes/docker/fetcher.go | 28 ++++++++++++++++++++--------
 1 file changed, 20 insertions(+), 8 deletions(-)

diff --git a/remotes/docker/fetcher.go b/remotes/docker/fetcher.go
index 4a2ce3c39..00e7a47c6 100644
--- a/remotes/docker/fetcher.go
+++ b/remotes/docker/fetcher.go
@@ -56,6 +56,26 @@ func (r dockerFetcher) Fetch(ctx context.Context, desc ocispec.Descriptor) (io.R
 	}
 
 	return newHTTPReadSeeker(desc.Size, func(offset int64) (io.ReadCloser, error) {
+		if len(desc.URLs) > 0 {
+			db := *r.dockerBase
+			// Remove authorizer to avoid authentication when
+			// connecting to manifest provided URLs.
+			// Prevents https://github.com/containerd/containerd/security/advisories/GHSA-742w-89gc-8m9c
+			db.auth = nil
+			nr := dockerFetcher{
+				dockerBase: &db,
+			}
+			for _, u := range desc.URLs {
+				log.G(ctx).WithField("url", u).Debug("trying alternative url")
+				rc, err := nr.open(ctx, u, desc.MediaType, offset)
+				if err != nil {
+					log.G(ctx).WithField("error", err).Debug("error trying url")
+					continue // try one of the other urls.
+				}
+
+				return rc, nil
+			}
+		}
 		for _, u := range urls {
 			rc, err := r.open(ctx, u, desc.MediaType, offset)
 			if err != nil {
@@ -142,14 +162,6 @@ func (r dockerFetcher) open(ctx context.Context, u, mediatype string, offset int
 func (r *dockerFetcher) getV2URLPaths(ctx context.Context, desc ocispec.Descriptor) ([]string, error) {
 	var urls []string
 
-	if len(desc.URLs) > 0 {
-		// handle fetch via external urls.
-		for _, u := range desc.URLs {
-			log.G(ctx).WithField("url", u).Debug("adding alternative url")
-			urls = append(urls, u)
-		}
-	}
-
 	switch desc.MediaType {
 	case images.MediaTypeDockerSchema2Manifest, images.MediaTypeDockerSchema2ManifestList,
 		images.MediaTypeDockerSchema1Manifest,
-- 
2.27.0

