Repository: minio/minio (language: go)

Issue:
compression with encryption turned-on fails minio-go functional tests
## Expected Behavior
No test failure

## Current Behavior
```
#!/bin/bash

export MINIO_CI_CD= "on"
export MINIO_COMPRESSION_ENABLE="on"
export MINIO_COMPRESSION_MIME_TYPES="*"
export MINIO_COMPRESSION_ALLOW_ENCRYPTION="on"
export MINIO_KMS_SECRET_KEY="my-minio-key:OSMM+vkKUTCvQs9YL/CVMIMt43HFhkUpqJxTmGl6rYw="

minio server /tmp/new
```

```
MINT_ROOT_DIR=/tmp ../mint/create-data-files.sh

MINT_DATA_DIR=/tmp/data SERVER_ENDPOINT=localhost:9000 ACCESS_KEY=minioadmin SECRET_KEY=minioadmin ENABLE_HTTPS=0 MINT_MODE=full go run functional_tests.go
```

```
{"args":{"destination":{"Bucket":"minio-go-test-aib5yh1szmafzbc9","Object":"dstObject","Encryption":{},"UserMetadata":null,"ReplaceMetadata":false,"UserTags":null,"ReplaceTags":false,"LegalHold":"","Mode":"","RetainUntilDate":"0001-01-01T00:00:00Z","Size":0,"Progress":null},"source":{"Bucket":"minio-go-test-aib5yh1szmafzbc9","Object":"srcObject","VersionID":"","MatchETag":"","NoMatchETag":"","MatchModifiedSince":"0001-01-01T00:00:00Z","MatchUnmodifiedSince":"0001-01-01T00:00:00Z","MatchRange":false,"Start":0,"End":0,"Encryption":null}},"duration":51,"function":"CopyObject(destination, source)","name":"minio-go: testUnencryptedToSSES3CopyObject","status":"PASS"}

API: SYSTEM()
Time: 21:17:02 UTC 05/25/2023
DeploymentID: 1e957ab8-9928-4620-9998-4152a62240bf
Error: Drive: /tmp/new  -> minio-go-testuwc2xzdbse3sho633/r4k5o93rf2jvp2q9kfaamxb9gqxcp5-dest/afb1c8b6-2003-4908-b97a-43817f7decef/part.3 - content hash does not match - expected a1611875cc5a9c88c588422b5b1e15c244e3af22282815cfb7f3580fc085d4a1, got 18ba761946f55e524994396b321d2d9eef3dc159d412b664a14a1621ce02fa84 (*errors.errorString)
       3: internal/logger/logger.go:258:logger.LogIf()
       2: cmd/bitrot-streaming.go:196:cmd.(*streamingBitrotReader).ReadAt()
       1: cmd/erasure-decode.go:167:cmd.(*parallelReader).Read.func1()

API: GetObject(bucket=minio-go-testuwc2xzdbse3sho633, object=r4k5o93rf2jvp2q9kfaamxb9gqxcp5-dest)
Time: 21:17:02 UTC 05/25/2023
DeploymentID: 1e957ab8-9928-4620-9998-4152a62240bf
RequestID: 17627F85838AC2A1
RemoteHost: 127.0.0.1
Host: localhost:9000
UserAgent: MinIO (linux; amd64) minio-go/v7.0.56 MinIO-go-FunctionalTest/0.1.0
Error: Unable to write all the data to client: Storage resources are insufficient for the read operation minio-go-testuwc2xzdbse3sho633/r4k5o93rf2jvp2q9kfaamxb9gqxcp5-dest (*fmt.wrapError)
       4: internal/logger/logger.go:258:logger.LogIf()
       3: cmd/object-handlers.go:548:cmd.objectAPIHandlers.getObjectHandler()
       2: cmd/object-handlers.go:605:cmd.objectAPIHandlers.GetObjectHandler()
       1: net/http/server.go:2122:http.HandlerFunc.ServeHTTP()
{"args":{},"duration":81,"error":"unexpected EOF","function":"CopyObjectPart(destination, source)","message":"Read buffer failed","name":"minio-go: testUnencryptedToSSES3CopyObjectPart","status":"FAIL"}
exit status 1
```

## Possible Solution
Not sure

## Steps to Reproduce (for bugs)
As mentioned above along with the script

## Regression
Not sure

## Your Environment
laster minio master, latest minio-go master



Discussion / hints:
Add to this - no error seen when 

```
export MINIO_COMPRESSION_ALLOW_ENCRYPTION="on"
```

This is not set.
Checking it out.

Fix patch:
diff --git a/cmd/erasure-multipart.go b/cmd/erasure-multipart.go
index 0c4d872037917..1aec3dfc08413 100644
--- a/cmd/erasure-multipart.go
+++ b/cmd/erasure-multipart.go
@@ -499,21 +499,6 @@ func (er erasureObjects) NewMultipartUpload(ctx context.Context, bucket, object
 	return er.newMultipartUpload(ctx, bucket, object, opts)
 }
 
-// CopyObjectPart - reads incoming stream and internally erasure codes
-// them. This call is similar to put object part operation but the source
-// data is read from an existing object.
-//
-// Implements S3 compatible Upload Part Copy API.
-func (er erasureObjects) CopyObjectPart(ctx context.Context, srcBucket, srcObject, dstBucket, dstObject, uploadID string, partID int, startOffset int64, length int64, srcInfo ObjectInfo, srcOpts, dstOpts ObjectOptions) (pi PartInfo, e error) {
-	partInfo, err := er.PutObjectPart(ctx, dstBucket, dstObject, uploadID, partID, NewPutObjReader(srcInfo.Reader), dstOpts)
-	if err != nil {
-		return pi, toObjectErr(err, dstBucket, dstObject)
-	}
-
-	// Success.
-	return partInfo, nil
-}
-
 // renamePart - renames multipart part to its relevant location under uploadID.
 func renamePart(ctx context.Context, disks []StorageAPI, srcBucket, srcEntry, dstBucket, dstEntry string, writeQuorum int) ([]StorageAPI, error) {
 	g := errgroup.WithNErrs(len(disks))
@@ -667,7 +652,8 @@ func (er erasureObjects) PutObjectPart(ctx context.Context, bucket, object, uplo
 		buffer = make([]byte, 1) // Allocate atleast a byte to reach EOF
 	case size == -1:
 		if size := data.ActualSize(); size > 0 && size < fi.Erasure.BlockSize {
-			buffer = make([]byte, data.ActualSize()+256, data.ActualSize()*2+512)
+			// Account for padding and forced compression overhead and encryption.
+			buffer = make([]byte, data.ActualSize()+256+32+32, data.ActualSize()*2+512)
 		} else {
 			buffer = er.bp.Get()
 			defer er.bp.Put(buffer)
diff --git a/cmd/erasure-server-pool.go b/cmd/erasure-server-pool.go
index 279cafeb8a5a3..604406a623a1e 100644
--- a/cmd/erasure-server-pool.go
+++ b/cmd/erasure-server-pool.go
@@ -1459,7 +1459,7 @@ func (z *erasureServerPools) CopyObjectPart(ctx context.Context, srcBucket, srcO
 	}
 
 	return z.PutObjectPart(ctx, destBucket, destObject, uploadID, partID,
-		NewPutObjReader(srcInfo.Reader), dstOpts)
+		srcInfo.PutObjReader, dstOpts)
 }
 
 // PutObjectPart - writes part of an object to hashedSet based on the object name.
diff --git a/cmd/erasure-sets.go b/cmd/erasure-sets.go
index 9c4172f3107ff..58974d5dea84f 100644
--- a/cmd/erasure-sets.go
+++ b/cmd/erasure-sets.go
@@ -899,14 +899,6 @@ func (s *erasureSets) NewMultipartUpload(ctx context.Context, bucket, object str
 	return set.NewMultipartUpload(ctx, bucket, object, opts)
 }
 
-// Copies a part of an object from source hashedSet to destination hashedSet.
-func (s *erasureSets) CopyObjectPart(ctx context.Context, srcBucket, srcObject, destBucket, destObject string, uploadID string, partID int,
-	startOffset int64, length int64, srcInfo ObjectInfo, srcOpts, dstOpts ObjectOptions,
-) (partInfo PartInfo, err error) {
-	destSet := s.getHashedSet(destObject)
-	return destSet.PutObjectPart(ctx, destBucket, destObject, uploadID, partID, NewPutObjReader(srcInfo.Reader), dstOpts)
-}
-
 // PutObjectPart - writes part of an object to hashedSet based on the object name.
 func (s *erasureSets) PutObjectPart(ctx context.Context, bucket, object, uploadID string, partID int, data *PutObjReader, opts ObjectOptions) (info PartInfo, err error) {
 	set := s.getHashedSet(object)


Test patch: