diff --git a/Documentation/CRDs/specification.md b/Documentation/CRDs/specification.md index 73b047744..06754acbb 100644 --- a/Documentation/CRDs/specification.md +++ b/Documentation/CRDs/specification.md @@ -12064,6 +12064,52 @@ KeyManagementServiceSpec
The settings for supporting AWS-SSE:S3 with RGW
+sslOptions,omitzeroSslOptions sets the SSL context options for the Ceph RGW beast frontend. +See https://docs.ceph.com/en/latest/radosgw/frontends/#options
+ciphersCiphers specifies the cipher suites used during the TLS handshake. +Multiple suites are supported with ‘:’ colon-separated. +Each value must be a valid OpenSSL cipher suite name. +See https://docs.openssl.org/master/man1/openssl-ciphers/#cipher-suite-names
+tlsGroupsTlsGroups specifies one or more TLS Group strings separated by colons. +Multiple suites are supported with ‘:’ colon-separated. +The pseudo group name DEFAULT can be used to select the OpenSSL built-in default list of groups. +Other valid group names will depend on OpenSSL version +See https://docs.openssl.org/master/man3/SSL_CTX_set1_curves/#description
++(Appears on:ObjectStoreSecuritySpec) +
+SslOptionsSpec specifies the SSL context options for the Ceph RGW beast frontend. +See https://docs.ceph.com/en/latest/radosgw/frontends/#options
+| Field | +Description | +
|---|---|
+defaultWorkarounds+ +bool + + |
+
+(Optional)
+ defaultWorkarounds implements various bug workaround when true, or disables it when false. Default disabled. + |
+
+noCompression+ +bool + + |
+
+(Optional)
+ noCompression disables compression when true, or disables it when false. Default disabled. + |
+
+sslv2+ +bool + + |
+
+(Optional)
+ sslv2 enables SSL v2 when true, or disables it when false. Default disabled. + |
+
+sslv3+ +bool + + |
+
+(Optional)
+ sslv3 enables SSL v3 when true, or disables it when false. Default disabled. + |
+
+tlsv1_0+ +bool + + |
+
+(Optional)
+ tlsv1_0 enables TLS v1.0 when true, or disables it when false. Default disabled. + |
+
+tlsv1_1+ +bool + + |
+
+(Optional)
+ tlsv1_1 enables TLS v1.1 when true, or disables it when false. Default disabled. + |
+
+tlsv1_2+ +bool + + |
+
+(Optional)
+ tlsv1_2 enables TLS v1.2 when true, or disables it when false. Default enabled. + |
+
+singleDiffieHellmanUse+ +bool + + |
+
+(Optional)
+ SingleDiffieHellmanUse always creates a new key when using tmp_dh parameters when true, or disables it when false. Default disabled. + |
+
diff --git a/deploy/charts/rook-ceph/templates/resources.yaml b/deploy/charts/rook-ceph/templates/resources.yaml index 591d6c601..2bdf52b20 100644 --- a/deploy/charts/rook-ceph/templates/resources.yaml +++ b/deploy/charts/rook-ceph/templates/resources.yaml @@ -14721,6 +14721,17 @@ spec: description: Security represents security settings nullable: true properties: + ciphers: + description: |- + Ciphers specifies the cipher suites used during the TLS handshake. + Multiple suites are supported with ':' colon-separated. + Each value must be a valid OpenSSL cipher suite name. + See https://docs.openssl.org/master/man1/openssl-ciphers/#cipher-suite-names + items: + type: string + maxItems: 1000 + minItems: 0 + type: array keyRotation: description: KeyRotation defines options for Key Rotation. nullable: true @@ -14763,6 +14774,46 @@ spec: description: TokenSecretName is the kubernetes secret containing the KMS token type: string type: object + sslOptions: + description: |- + SslOptions sets the SSL context options for the Ceph RGW beast frontend. + See https://docs.ceph.com/en/latest/radosgw/frontends/#options + properties: + defaultWorkarounds: + description: defaultWorkarounds implements various bug workaround when true, or disables it when false. Default disabled. + type: boolean + noCompression: + description: noCompression disables compression when true, or disables it when false. Default disabled. + type: boolean + singleDiffieHellmanUse: + description: SingleDiffieHellmanUse always creates a new key when using tmp_dh parameters when true, or disables it when false. Default disabled. + type: boolean + sslv2: + description: sslv2 enables SSL v2 when true, or disables it when false. Default disabled. + type: boolean + sslv3: + description: sslv3 enables SSL v3 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_0: + description: tlsv1_0 enables TLS v1.0 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_1: + description: tlsv1_1 enables TLS v1.1 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_2: + description: tlsv1_2 enables TLS v1.2 when true, or disables it when false. Default enabled. + type: boolean + type: object + tlsGroups: + description: |- + TlsGroups specifies one or more TLS Group strings separated by colons. + Multiple suites are supported with ':' colon-separated. + The pseudo group name DEFAULT can be used to select the OpenSSL built-in default list of groups. + Other valid group names will depend on OpenSSL version + See https://docs.openssl.org/master/man3/SSL_CTX_set1_curves/#description + items: + type: string + type: array type: object sharedPools: description: The pool information when configuring RADOS namespaces in existing pools. diff --git a/deploy/examples/crds.yaml b/deploy/examples/crds.yaml index c99ea3cac..dd845277a 100644 --- a/deploy/examples/crds.yaml +++ b/deploy/examples/crds.yaml @@ -14710,6 +14710,17 @@ spec: description: Security represents security settings nullable: true properties: + ciphers: + description: |- + Ciphers specifies the cipher suites used during the TLS handshake. + Multiple suites are supported with ':' colon-separated. + Each value must be a valid OpenSSL cipher suite name. + See https://docs.openssl.org/master/man1/openssl-ciphers/#cipher-suite-names + items: + type: string + maxItems: 1000 + minItems: 0 + type: array keyRotation: description: KeyRotation defines options for Key Rotation. nullable: true @@ -14752,6 +14763,46 @@ spec: description: TokenSecretName is the kubernetes secret containing the KMS token type: string type: object + sslOptions: + description: |- + SslOptions sets the SSL context options for the Ceph RGW beast frontend. + See https://docs.ceph.com/en/latest/radosgw/frontends/#options + properties: + defaultWorkarounds: + description: defaultWorkarounds implements various bug workaround when true, or disables it when false. Default disabled. + type: boolean + noCompression: + description: noCompression disables compression when true, or disables it when false. Default disabled. + type: boolean + singleDiffieHellmanUse: + description: SingleDiffieHellmanUse always creates a new key when using tmp_dh parameters when true, or disables it when false. Default disabled. + type: boolean + sslv2: + description: sslv2 enables SSL v2 when true, or disables it when false. Default disabled. + type: boolean + sslv3: + description: sslv3 enables SSL v3 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_0: + description: tlsv1_0 enables TLS v1.0 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_1: + description: tlsv1_1 enables TLS v1.1 when true, or disables it when false. Default disabled. + type: boolean + tlsv1_2: + description: tlsv1_2 enables TLS v1.2 when true, or disables it when false. Default enabled. + type: boolean + type: object + tlsGroups: + description: |- + TlsGroups specifies one or more TLS Group strings separated by colons. + Multiple suites are supported with ':' colon-separated. + The pseudo group name DEFAULT can be used to select the OpenSSL built-in default list of groups. + Other valid group names will depend on OpenSSL version + See https://docs.openssl.org/master/man3/SSL_CTX_set1_curves/#description + items: + type: string + type: array type: object sharedPools: description: The pool information when configuring RADOS namespaces in existing pools. diff --git a/pkg/apis/ceph.rook.io/v1/types.go b/pkg/apis/ceph.rook.io/v1/types.go index f5da4f988..b1f07401d 100755 --- a/pkg/apis/ceph.rook.io/v1/types.go +++ b/pkg/apis/ceph.rook.io/v1/types.go @@ -394,6 +394,64 @@ type ObjectStoreSecuritySpec struct { // +optional // +nullable ServerSideEncryptionS3 KeyManagementServiceSpec `json:"s3,omitempty"` + + // SslOptions sets the SSL context options for the Ceph RGW beast frontend. + // See https://docs.ceph.com/en/latest/radosgw/frontends/#options + // +optional + SslOptions *SslOptionsSpec `json:"sslOptions,omitzero"` //nolint:kubeapilinter // MinProperties cannot be applied to a struct pointer field + + // Ciphers specifies the cipher suites used during the TLS handshake. + // Multiple suites are supported with ':' colon-separated. + // Each value must be a valid OpenSSL cipher suite name. + // See https://docs.openssl.org/master/man1/openssl-ciphers/#cipher-suite-names + // +kubebuilder:validation:MinItems=0 + // +kubebuilder:validation:MaxItems=1000 + // +optional + Ciphers []string `json:"ciphers,omitempty"` //nolint:kubeapilinter // List doesn't have min/max length + + // TlsGroups specifies one or more TLS Group strings separated by colons. + // Multiple suites are supported with ':' colon-separated. + // The pseudo group name DEFAULT can be used to select the OpenSSL built-in default list of groups. + // Other valid group names will depend on OpenSSL version + // See https://docs.openssl.org/master/man3/SSL_CTX_set1_curves/#description + // +optional + TlsGroups []string `json:"tlsGroups,omitempty"` //nolint:kubeapilinter // List doesn't have min/max length +} + +// SslOptionsSpec specifies the SSL context options for the Ceph RGW beast frontend. +// See https://docs.ceph.com/en/latest/radosgw/frontends/#options +type SslOptionsSpec struct { + // defaultWorkarounds implements various bug workaround when true, or disables it when false. Default disabled. + // +optional + DefaultWorkarounds *bool `json:"defaultWorkarounds,omitempty"` + + // noCompression disables compression when true, or disables it when false. Default disabled. + // +optional + NoCompression *bool `json:"noCompression,omitempty"` + + // sslv2 enables SSL v2 when true, or disables it when false. Default disabled. + // +optional + SSLv2 *bool `json:"sslv2,omitempty"` + + // sslv3 enables SSL v3 when true, or disables it when false. Default disabled. + // +optional + SSLv3 *bool `json:"sslv3,omitempty"` + + // tlsv1_0 enables TLS v1.0 when true, or disables it when false. Default disabled. + // +optional + TLSv1_0 *bool `json:"tlsv1_0,omitempty"` + + // tlsv1_1 enables TLS v1.1 when true, or disables it when false. Default disabled. + // +optional + TLSv1_1 *bool `json:"tlsv1_1,omitempty"` + + // tlsv1_2 enables TLS v1.2 when true, or disables it when false. Default enabled. + // +optional + TLSv1_2 *bool `json:"tlsv1_2,omitempty"` + + // SingleDiffieHellmanUse always creates a new key when using tmp_dh parameters when true, or disables it when false. Default disabled. + // +optional + SingleDiffieHellmanUse *bool `json:"singleDiffieHellmanUse,omitempty"` } // KeyManagementServiceSpec represent various details of the KMS server diff --git a/pkg/apis/ceph.rook.io/v1/zz_generated.deepcopy.go b/pkg/apis/ceph.rook.io/v1/zz_generated.deepcopy.go index 0ea8068ef..0cba6d6ad 100644 --- a/pkg/apis/ceph.rook.io/v1/zz_generated.deepcopy.go +++ b/pkg/apis/ceph.rook.io/v1/zz_generated.deepcopy.go @@ -4428,6 +4428,21 @@ func (in *ObjectStoreSecuritySpec) DeepCopyInto(out *ObjectStoreSecuritySpec) { *out = *in in.SecuritySpec.DeepCopyInto(&out.SecuritySpec) in.ServerSideEncryptionS3.DeepCopyInto(&out.ServerSideEncryptionS3) + if in.SslOptions != nil { + in, out := &in.SslOptions, &out.SslOptions + *out = new(SslOptionsSpec) + (*in).DeepCopyInto(*out) + } + if in.Ciphers != nil { + in, out := &in.Ciphers, &out.Ciphers + *out = make([]string, len(*in)) + copy(*out, *in) + } + if in.TlsGroups != nil { + in, out := &in.TlsGroups, &out.TlsGroups + *out = make([]string, len(*in)) + copy(*out, *in) + } return } @@ -5510,6 +5525,62 @@ func (in *SnapshotSchedulesSpec) DeepCopy() *SnapshotSchedulesSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *SslOptionsSpec) DeepCopyInto(out *SslOptionsSpec) { + *out = *in + if in.DefaultWorkarounds != nil { + in, out := &in.DefaultWorkarounds, &out.DefaultWorkarounds + *out = new(bool) + **out = **in + } + if in.NoCompression != nil { + in, out := &in.NoCompression, &out.NoCompression + *out = new(bool) + **out = **in + } + if in.SSLv2 != nil { + in, out := &in.SSLv2, &out.SSLv2 + *out = new(bool) + **out = **in + } + if in.SSLv3 != nil { + in, out := &in.SSLv3, &out.SSLv3 + *out = new(bool) + **out = **in + } + if in.TLSv1_0 != nil { + in, out := &in.TLSv1_0, &out.TLSv1_0 + *out = new(bool) + **out = **in + } + if in.TLSv1_1 != nil { + in, out := &in.TLSv1_1, &out.TLSv1_1 + *out = new(bool) + **out = **in + } + if in.TLSv1_2 != nil { + in, out := &in.TLSv1_2, &out.TLSv1_2 + *out = new(bool) + **out = **in + } + if in.SingleDiffieHellmanUse != nil { + in, out := &in.SingleDiffieHellmanUse, &out.SingleDiffieHellmanUse + *out = new(bool) + **out = **in + } + return +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new SslOptionsSpec. +func (in *SslOptionsSpec) DeepCopy() *SslOptionsSpec { + if in == nil { + return nil + } + out := new(SslOptionsSpec) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *StatesSpec) DeepCopyInto(out *StatesSpec) { *out = *in diff --git a/pkg/operator/ceph/object/config.go b/pkg/operator/ceph/object/config.go index c7e5af0d2..e07110aee 100644 --- a/pkg/operator/ceph/object/config.go +++ b/pkg/operator/ceph/object/config.go @@ -24,12 +24,14 @@ import ( "time" "github.com/pkg/errors" + cephv1 "github.com/rook/rook/pkg/apis/ceph.rook.io/v1" cephconfig "github.com/rook/rook/pkg/operator/ceph/config" "github.com/rook/rook/pkg/operator/ceph/config/keyring" "github.com/rook/rook/pkg/operator/ceph/controller" "github.com/rook/rook/pkg/util/log" v1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/utils/ptr" ) const ( @@ -92,6 +94,67 @@ func (c *clusterConfig) portString() string { return portString } +// rgwFrontendStr builds the "rgw frontends" value including the beast frontend name, +// port/TLS config, SSL options, and cipher settings. +func (c *clusterConfig) rgwFrontendStr() string { + frontendStr := fmt.Sprintf("%s %s", rgwFrontendName, c.portString()) + + if c.store.Spec.Security == nil { + return frontendStr + } + + // Only emit ssl_options when SSLOptions is set. + if c.store.Spec.Security.SslOptions != nil { + if sslOptions := buildSSLOptions(c.store.Spec.Security.SslOptions); sslOptions != "" { + frontendStr = fmt.Sprintf("%s ssl_options=%s", frontendStr, sslOptions) + } + } + + if len(c.store.Spec.Security.Ciphers) > 0 { + frontendStr = fmt.Sprintf("%s ssl_ciphers=%s", frontendStr, strings.Join(c.store.Spec.Security.Ciphers, ":")) + } + + if len(c.store.Spec.Security.TlsGroups) > 0 { + frontendStr = fmt.Sprintf("%s tls_groups=%s", frontendStr, strings.Join(c.store.Spec.Security.TlsGroups, ":")) + } + + return frontendStr +} + +// buildSSLOptions constructs the colon-separated ssl_options string for the beast frontend. +// See https://docs.ceph.com/en/latest/radosgw/frontends/ +func buildSSLOptions(opts *cephv1.SslOptionsSpec) string { + var options []string + if ptr.Deref(opts.DefaultWorkarounds, false) { + options = append(options, "default_workarounds") + } + if ptr.Deref(opts.NoCompression, false) { + options = append(options, "no_compression") + } + if ptr.Deref(opts.SingleDiffieHellmanUse, false) { + options = append(options, "single_dh_use") + } + + // Omitted sslv2, sslv3, tlsv1_0, and tlsv1_1 default to disabled + if !ptr.Deref(opts.SSLv2, false) { + options = append(options, "no_sslv2") + } + if !ptr.Deref(opts.SSLv3, false) { + options = append(options, "no_sslv3") + } + if !ptr.Deref(opts.TLSv1_0, false) { + options = append(options, "no_tlsv1") + } + if !ptr.Deref(opts.TLSv1_1, false) { + options = append(options, "no_tlsv1_1") + } + if !ptr.Deref(opts.TLSv1_2, true) { + options = append(options, "no_tlsv1_2") + } + + return strings.Join(options, ":") +} + func generateCephXUser(name string) string { user := strings.TrimPrefix(name, AppName) return "client.rgw" + strings.ReplaceAll(user, "-", ".") diff --git a/pkg/operator/ceph/object/config_test.go b/pkg/operator/ceph/object/config_test.go index de1bc3a38..3409a177d 100644 --- a/pkg/operator/ceph/object/config_test.go +++ b/pkg/operator/ceph/object/config_test.go @@ -30,6 +30,7 @@ import ( v1 "k8s.io/api/core/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + "k8s.io/utils/ptr" ) func newConfig(t *testing.T) *clusterConfig { @@ -97,6 +98,163 @@ func TestPortString(t *testing.T) { assert.Equal(t, "port=8080", result) } +func TestRgwFrontendStr(t *testing.T) { + // No Security set + cfg := newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + result := cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80", result, "case 1") + + // Empty SslOptions struct + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + SslOptions: &cephv1.SslOptionsSpec{}, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 ssl_options=no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1", result, "case 2") + + // Restrict all old protocols + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + SslOptions: &cephv1.SslOptionsSpec{ + SSLv2: ptr.To(true), + SSLv3: ptr.To(true), + TLSv1_0: ptr.To(true), + TLSv1_1: ptr.To(true), + TLSv1_2: ptr.To(true), + }, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80", result, "case 3") + + // Restrict to TLS 1.3 only + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + SslOptions: &cephv1.SslOptionsSpec{ + SSLv2: ptr.To(false), + SSLv3: ptr.To(false), + TLSv1_0: ptr.To(false), + TLSv1_1: ptr.To(false), + TLSv1_2: ptr.To(false), + }, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 ssl_options=no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1:no_tlsv1_2", result, "case 4") + + // With ciphers only + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + Ciphers: []string{"AES256-SHA", "AES128-SHA"}, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 ssl_ciphers=AES256-SHA:AES128-SHA", result, "case 5") + + // With both SSL options and ciphers + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + SslOptions: &cephv1.SslOptionsSpec{}, + Ciphers: []string{"AES256-SHA"}, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 ssl_options=no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1 ssl_ciphers=AES256-SHA", result, "case 6") + + // With tls_groups only + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + TlsGroups: []string{"X25519", "P-256"}, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 tls_groups=X25519:P-256", result, "case 7") + + // Combined ssl_options, ssl_ciphers, tls_groups + cfg = newConfig(t) + cfg.clusterSpec.Network.HostNetwork = true + cfg.store.Spec.Gateway.Port = 80 + cfg.store.Spec.Security = &cephv1.ObjectStoreSecuritySpec{ + SslOptions: &cephv1.SslOptionsSpec{ + DefaultWorkarounds: ptr.To(true), + NoCompression: ptr.To(true), + }, + Ciphers: []string{ + "TLS_DHE_RSA_WITH_AES_256_GCM_SHA384", + "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256", + }, + TlsGroups: []string{"X25519", "P-256"}, + } + result = cfg.rgwFrontendStr() + assert.Equal(t, "beast port=80 ssl_options=default_workarounds:no_compression:no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1 ssl_ciphers=TLS_DHE_RSA_WITH_AES_256_GCM_SHA384:TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 tls_groups=X25519:P-256", result, "case 8") +} + +func TestBuildSslOptions(t *testing.T) { + // All nil + result := buildSSLOptions(&cephv1.SslOptionsSpec{}) + assert.Equal(t, "no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1", result, "case 1") + + // All protocols explicitly disabled + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + SSLv2: ptr.To(false), + SSLv3: ptr.To(false), + TLSv1_0: ptr.To(false), + TLSv1_1: ptr.To(false), + TLSv1_2: ptr.To(false), + }) + assert.Equal(t, "no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1:no_tlsv1_2", result, "case 2") + + // Enable TLSv1.1, TLSv1.2, rest disabled + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + SSLv2: ptr.To(false), + SSLv3: ptr.To(false), + TLSv1_0: ptr.To(false), + TLSv1_1: ptr.To(true), + TLSv1_2: ptr.To(true), + }) + assert.Equal(t, "no_sslv2:no_sslv3:no_tlsv1", result, "case 3") + + // Enable all protocols + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + SSLv2: ptr.To(true), + SSLv3: ptr.To(true), + TLSv1_0: ptr.To(true), + TLSv1_1: ptr.To(true), + TLSv1_2: ptr.To(true), + }) + assert.Equal(t, "", result, "case 4") + + // Non-protocol beast options enabled; legacy TLS protocol pointers omitted (default off) + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + DefaultWorkarounds: ptr.To(true), + NoCompression: ptr.To(true), + SingleDiffieHellmanUse: ptr.To(true), + }) + assert.Equal(t, "default_workarounds:no_compression:single_dh_use:no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1", result, "case 5") + + // Non-protocol option plus TLS 1.2 enabled + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + DefaultWorkarounds: ptr.To(true), + TLSv1_2: ptr.To(true), + }) + assert.Equal(t, "default_workarounds:no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1", result, "case 6") + + // Only TLSv1.2 disabled; + result = buildSSLOptions(&cephv1.SslOptionsSpec{ + TLSv1_2: ptr.To(false), + }) + assert.Equal(t, "no_sslv2:no_sslv3:no_tlsv1:no_tlsv1_1:no_tlsv1_2", result, "case 7") +} + func TestGenerateCephXUser(t *testing.T) { fakeUser := generateCephXUser("rook-ceph-rgw-fake-store-fake-user") assert.Equal(t, "client.rgw.fake.store.fake.user", fakeUser) diff --git a/pkg/operator/ceph/object/spec.go b/pkg/operator/ceph/object/spec.go index 27df46066..716ac76a7 100644 --- a/pkg/operator/ceph/object/spec.go +++ b/pkg/operator/ceph/object/spec.go @@ -430,7 +430,7 @@ func (c *clusterConfig) makeDaemonContainer(rgwConfig *rgwConfig) (v1.Container, controller.DaemonFlags(c.clusterInfo, c.clusterSpec, strings.TrimPrefix(generateCephXUser(rgwConfig.ResourceName), "client.")), "--foreground", - cephconfig.NewFlag("rgw frontends", fmt.Sprintf("%s %s", rgwFrontendName, c.portString())), + cephconfig.NewFlag("rgw frontends", c.rgwFrontendStr()), cephconfig.NewFlag("rgw-mime-types-file", mimeTypesMountPath()), cephconfig.NewFlag("rgw realm", rgwConfig.Realm), cephconfig.NewFlag("rgw zonegroup", rgwConfig.ZoneGroup),