add SSE-KMS not-implemented error handling (#6234)

This commit adds error handling for SSE-KMS requests to
HEAD, GET, PUT and COPY operations. The server responds
with `not implemented` if a client sends a SSE-KMS
request.
master
Andreas Auernhammer 6 years ago committed by Harshavardhana
parent a6b8a5487a
commit d531080b7e
  1. 6
      cmd/api-errors.go
  2. 86
      cmd/object-handlers.go

@ -129,6 +129,7 @@ const (
ErrMaximumExpires ErrMaximumExpires
ErrSlowDown ErrSlowDown
ErrInvalidPrefixMarker ErrInvalidPrefixMarker
ErrBadRequest
// Add new error codes here. // Add new error codes here.
// SSE-S3 related API errors // SSE-S3 related API errors
@ -636,6 +637,11 @@ var errorCodeResponse = map[APIErrorCode]APIError{
Description: "Invalid marker prefix combination", Description: "Invalid marker prefix combination",
HTTPStatusCode: http.StatusBadRequest, HTTPStatusCode: http.StatusBadRequest,
}, },
ErrBadRequest: {
Code: "BadRequest",
Description: "400 BadRequest",
HTTPStatusCode: http.StatusBadRequest,
},
// FIXME: Actual XML error response also contains the header which missed in list of signed header parameters. // FIXME: Actual XML error response also contains the header which missed in list of signed header parameters.
ErrUnsignedHeaders: { ErrUnsignedHeaders: {

@ -258,17 +258,19 @@ func (api objectAPIHandlers) SelectObjectContentHandler(w http.ResponseWriter, r
func (api objectAPIHandlers) GetObjectHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) GetObjectHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "GetObject") ctx := newContext(r, w, "GetObject")
var object, bucket string
vars := mux.Vars(r)
bucket = vars["bucket"]
object = vars["object"]
// Fetch object stat info.
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if crypto.S3.IsRequested(r.Header) || crypto.S3KMS.IsRequested(r.Header) { // If SSE-S3 or SSE-KMS present -> AWS fails with undefined error
writeErrorResponse(w, ErrBadRequest, r.URL)
return
}
vars := mux.Vars(r)
bucket := vars["bucket"]
object := vars["object"]
getObjectInfo := objectAPI.GetObjectInfo getObjectInfo := objectAPI.GetObjectInfo
if api.CacheAPI() != nil { if api.CacheAPI() != nil {
@ -419,16 +421,19 @@ func (api objectAPIHandlers) GetObjectHandler(w http.ResponseWriter, r *http.Req
func (api objectAPIHandlers) HeadObjectHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) HeadObjectHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "HeadObject") ctx := newContext(r, w, "HeadObject")
var object, bucket string
vars := mux.Vars(r)
bucket = vars["bucket"]
object = vars["object"]
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponseHeadersOnly(w, ErrServerNotInitialized) writeErrorResponseHeadersOnly(w, ErrServerNotInitialized)
return return
} }
if crypto.S3.IsRequested(r.Header) || crypto.S3KMS.IsRequested(r.Header) { // If SSE-S3 or SSE-KMS present -> AWS fails with undefined error
writeErrorResponse(w, ErrBadRequest, r.URL)
return
}
vars := mux.Vars(r)
bucket := vars["bucket"]
object := vars["object"]
getObjectInfo := objectAPI.GetObjectInfo getObjectInfo := objectAPI.GetObjectInfo
if api.CacheAPI() != nil { if api.CacheAPI() != nil {
@ -547,14 +552,19 @@ func getCpObjMetadataFromHeader(ctx context.Context, r *http.Request, userMeta m
func (api objectAPIHandlers) CopyObjectHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) CopyObjectHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "CopyObject") ctx := newContext(r, w, "CopyObject")
vars := mux.Vars(r)
dstBucket := vars["bucket"]
dstObject := vars["object"]
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if !objectAPI.IsEncryptionSupported() && crypto.S3KMS.IsRequested(r.Header) {
writeErrorResponse(w, ErrNotImplemented, r.URL) // SSE-KMS is not supported
return
}
vars := mux.Vars(r)
dstBucket := vars["bucket"]
dstObject := vars["object"]
if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, dstBucket, dstObject); s3Error != ErrNone { if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, dstBucket, dstObject); s3Error != ErrNone {
writeErrorResponse(w, s3Error, r.URL) writeErrorResponse(w, s3Error, r.URL)
@ -853,10 +863,8 @@ func (api objectAPIHandlers) PutObjectHandler(w http.ResponseWriter, r *http.Req
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if !objectAPI.IsEncryptionSupported() && crypto.S3KMS.IsRequested(r.Header) {
// X-Amz-Copy-Source shouldn't be set for this call. writeErrorResponse(w, ErrNotImplemented, r.URL) // SSE-KMS is not supported
if _, ok := r.Header["X-Amz-Copy-Source"]; ok {
writeErrorResponse(w, ErrInvalidCopySource, r.URL)
return return
} }
@ -864,6 +872,12 @@ func (api objectAPIHandlers) PutObjectHandler(w http.ResponseWriter, r *http.Req
bucket := vars["bucket"] bucket := vars["bucket"]
object := vars["object"] object := vars["object"]
// X-Amz-Copy-Source shouldn't be set for this call.
if _, ok := r.Header["X-Amz-Copy-Source"]; ok {
writeErrorResponse(w, ErrInvalidCopySource, r.URL)
return
}
// Validate storage class metadata if present // Validate storage class metadata if present
if _, ok := r.Header[amzStorageClassCanonical]; ok { if _, ok := r.Header[amzStorageClassCanonical]; ok {
if !isValidStorageClassMeta(r.Header.Get(amzStorageClassCanonical)) { if !isValidStorageClassMeta(r.Header.Get(amzStorageClassCanonical)) {
@ -1058,16 +1072,19 @@ func (api objectAPIHandlers) PutObjectHandler(w http.ResponseWriter, r *http.Req
func (api objectAPIHandlers) NewMultipartUploadHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) NewMultipartUploadHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "NewMultipartUpload") ctx := newContext(r, w, "NewMultipartUpload")
var object, bucket string
vars := mux.Vars(r)
bucket = vars["bucket"]
object = vars["object"]
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if !objectAPI.IsEncryptionSupported() && crypto.S3KMS.IsRequested(r.Header) {
writeErrorResponse(w, ErrNotImplemented, r.URL) // SSE-KMS is not supported
return
}
vars := mux.Vars(r)
bucket := vars["bucket"]
object := vars["object"]
if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, bucket, object); s3Error != ErrNone { if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, bucket, object); s3Error != ErrNone {
writeErrorResponse(w, s3Error, r.URL) writeErrorResponse(w, s3Error, r.URL)
@ -1138,15 +1155,19 @@ func (api objectAPIHandlers) NewMultipartUploadHandler(w http.ResponseWriter, r
func (api objectAPIHandlers) CopyObjectPartHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) CopyObjectPartHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "CopyObjectPart") ctx := newContext(r, w, "CopyObjectPart")
vars := mux.Vars(r)
dstBucket := vars["bucket"]
dstObject := vars["object"]
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if !objectAPI.IsEncryptionSupported() && crypto.S3KMS.IsRequested(r.Header) {
writeErrorResponse(w, ErrNotImplemented, r.URL) // SSE-KMS is not supported
return
}
vars := mux.Vars(r)
dstBucket := vars["bucket"]
dstObject := vars["object"]
if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, dstBucket, dstObject); s3Error != ErrNone { if s3Error := checkRequestAuthType(ctx, r, policy.PutObjectAction, dstBucket, dstObject); s3Error != ErrNone {
writeErrorResponse(w, s3Error, r.URL) writeErrorResponse(w, s3Error, r.URL)
@ -1339,14 +1360,19 @@ func (api objectAPIHandlers) CopyObjectPartHandler(w http.ResponseWriter, r *htt
func (api objectAPIHandlers) PutObjectPartHandler(w http.ResponseWriter, r *http.Request) { func (api objectAPIHandlers) PutObjectPartHandler(w http.ResponseWriter, r *http.Request) {
ctx := newContext(r, w, "PutObjectPart") ctx := newContext(r, w, "PutObjectPart")
vars := mux.Vars(r)
bucket := vars["bucket"]
object := vars["object"]
objectAPI := api.ObjectAPI() objectAPI := api.ObjectAPI()
if objectAPI == nil { if objectAPI == nil {
writeErrorResponse(w, ErrServerNotInitialized, r.URL) writeErrorResponse(w, ErrServerNotInitialized, r.URL)
return return
} }
if !objectAPI.IsEncryptionSupported() && crypto.S3KMS.IsRequested(r.Header) {
writeErrorResponse(w, ErrNotImplemented, r.URL) // SSE-KMS is not supported
return
}
vars := mux.Vars(r)
bucket := vars["bucket"]
object := vars["object"]
// X-Amz-Copy-Source shouldn't be set for this call. // X-Amz-Copy-Source shouldn't be set for this call.
if _, ok := r.Header["X-Amz-Copy-Source"]; ok { if _, ok := r.Header["X-Amz-Copy-Source"]; ok {

Loading…
Cancel
Save