github.com/minio/minio@v0.0.0-20240328213742-3f72439b8a27/internal/crypto/header.go (about) 1 // Copyright (c) 2015-2021 MinIO, Inc. 2 // 3 // This file is part of MinIO Object Storage stack 4 // 5 // This program is free software: you can redistribute it and/or modify 6 // it under the terms of the GNU Affero General Public License as published by 7 // the Free Software Foundation, either version 3 of the License, or 8 // (at your option) any later version. 9 // 10 // This program is distributed in the hope that it will be useful 11 // but WITHOUT ANY WARRANTY; without even the implied warranty of 12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 // GNU Affero General Public License for more details. 14 // 15 // You should have received a copy of the GNU Affero General Public License 16 // along with this program. If not, see <http://www.gnu.org/licenses/>. 17 18 package crypto 19 20 import ( 21 "bytes" 22 "crypto/md5" 23 "encoding/base64" 24 "net/http" 25 26 xhttp "github.com/minio/minio/internal/http" 27 ) 28 29 // RemoveSensitiveHeaders removes confidential encryption 30 // information - e.g. the SSE-C key - from the HTTP headers. 31 // It has the same semantics as RemoveSensitiveEntries. 32 func RemoveSensitiveHeaders(h http.Header) { 33 h.Del(xhttp.AmzServerSideEncryptionCustomerKey) 34 h.Del(xhttp.AmzServerSideEncryptionCopyCustomerKey) 35 h.Del(xhttp.AmzMetaUnencryptedContentLength) 36 h.Del(xhttp.AmzMetaUnencryptedContentMD5) 37 } 38 39 // SSECopy represents AWS SSE-C for copy requests. It provides 40 // functionality to handle SSE-C copy requests. 41 var SSECopy = ssecCopy{} 42 43 type ssecCopy struct{} 44 45 // IsRequested returns true if the HTTP headers contains 46 // at least one SSE-C copy header. Regular SSE-C headers 47 // are ignored. 48 func (ssecCopy) IsRequested(h http.Header) bool { 49 if _, ok := h[xhttp.AmzServerSideEncryptionCopyCustomerAlgorithm]; ok { 50 return true 51 } 52 if _, ok := h[xhttp.AmzServerSideEncryptionCopyCustomerKey]; ok { 53 return true 54 } 55 if _, ok := h[xhttp.AmzServerSideEncryptionCopyCustomerKeyMD5]; ok { 56 return true 57 } 58 return false 59 } 60 61 // ParseHTTP parses the SSE-C copy headers and returns the SSE-C client key 62 // on success. Regular SSE-C headers are ignored. 63 func (ssecCopy) ParseHTTP(h http.Header) (key [32]byte, err error) { 64 if h.Get(xhttp.AmzServerSideEncryptionCopyCustomerAlgorithm) != xhttp.AmzEncryptionAES { 65 return key, ErrInvalidCustomerAlgorithm 66 } 67 if h.Get(xhttp.AmzServerSideEncryptionCopyCustomerKey) == "" { 68 return key, ErrMissingCustomerKey 69 } 70 if h.Get(xhttp.AmzServerSideEncryptionCopyCustomerKeyMD5) == "" { 71 return key, ErrMissingCustomerKeyMD5 72 } 73 74 clientKey, err := base64.StdEncoding.DecodeString(h.Get(xhttp.AmzServerSideEncryptionCopyCustomerKey)) 75 if err != nil || len(clientKey) != 32 { // The client key must be 256 bits long 76 return key, ErrInvalidCustomerKey 77 } 78 keyMD5, err := base64.StdEncoding.DecodeString(h.Get(xhttp.AmzServerSideEncryptionCopyCustomerKeyMD5)) 79 if md5Sum := md5.Sum(clientKey); err != nil || !bytes.Equal(md5Sum[:], keyMD5) { 80 return key, ErrCustomerKeyMD5Mismatch 81 } 82 copy(key[:], clientKey) 83 return key, nil 84 }