diff --git a/ansible/group_vars/all.yml b/ansible/group_vars/all.yml
index 5ec9f5da89..357191385a 100644
--- a/ansible/group_vars/all.yml
+++ b/ansible/group_vars/all.yml
@@ -1047,9 +1047,10 @@ openstack_auth:
 #######################
 # Glance options
 #######################
-glance_backend_file: "{{ not (glance_backend_ceph | bool or glance_backend_swift | bool or glance_backend_vmware | bool) }}"
+glance_backend_file: "{{ not (glance_backend_ceph | bool or glance_backend_s3 | bool or glance_backend_swift | bool or glance_backend_vmware | bool) }}"
 glance_backend_ceph: "no"
 glance_backend_vmware: "no"
+glance_backend_s3: "no"
 enable_glance_image_cache: "no"
 glance_backend_swift: "{{ enable_swift | bool }}"
 glance_file_datadir_volume: "glance"
@@ -1094,7 +1095,7 @@ cinder_target_helper: "{{ 'lioadm' if ansible_facts.os_family == 'RedHat' else '
 # Valid options are [ '', redis, etcd ]
 cinder_coordination_backend: "{{ 'redis' if enable_redis | bool else 'etcd' if enable_etcd | bool else '' }}"
 
-# Valid options are [ nfs, swift, ceph ]
+# Valid options are [ nfs, swift, ceph, s3 ]
 cinder_backup_driver: "ceph"
 cinder_backup_share: ""
 cinder_backup_mount_options_nfs: ""
@@ -1334,6 +1335,15 @@ distro_python_version: "{{ distro_python_version_map[kolla_base_distro] }}"
 
 kolla_base_distro_version: "{{ kolla_base_distro_version_default_map[kolla_base_distro] }}"
 
+#############
+# S3 options
+#############
+# Common options for S3 Cinder Backup and Glance S3 backend.
+s3_url:
+s3_bucket:
+s3_access_key:
+s3_secret_key:
+
 ##########
 # Telegraf
 ##########
diff --git a/ansible/roles/cinder/defaults/main.yml b/ansible/roles/cinder/defaults/main.yml
index 1a4440bc5f..361d3961f2 100644
--- a/ansible/roles/cinder/defaults/main.yml
+++ b/ansible/roles/cinder/defaults/main.yml
@@ -313,6 +313,14 @@ pure_fc_backend: "pure_fc_backend"
 pure_api_token:
 pure_san_ip:
 
+################################
+# Cinder Backup S3
+################################
+cinder_backup_s3_url: "{{ s3_url }}"
+cinder_backup_s3_bucket: "{{ s3_bucket }}"
+cinder_backup_s3_access_key: "{{ s3_access_key }}"
+cinder_backup_s3_secret_key: "{{ s3_secret_key }}"
+
 ####################
 # Kolla
 ####################
diff --git a/ansible/roles/cinder/tasks/precheck.yml b/ansible/roles/cinder/tasks/precheck.yml
index 049b9599fc..6bb50a7084 100644
--- a/ansible/roles/cinder/tasks/precheck.yml
+++ b/ansible/roles/cinder/tasks/precheck.yml
@@ -54,3 +54,15 @@
     - enable_cinder | bool
     - enable_cinder_backend_lvm | bool
     - inventory_hostname in groups['cinder-volume']
+
+- name: Check if S3 configurations are defined
+  assert:
+    that:
+      - vars[item] is defined
+    msg: "Cinder backup S3 backend is enabled, either the {{ item }} or {{ item | replace('cinder_backup_','') }} variable must be defined."
+  with_items:
+    - cinder_backup_s3_url
+    - cinder_backup_s3_bucket
+    - cinder_backup_s3_access_key
+    - cinder_backup_s3_secret_key
+  when: cinder_backup_driver == "s3"
diff --git a/ansible/roles/cinder/templates/cinder.conf.j2 b/ansible/roles/cinder/templates/cinder.conf.j2
index 1d8536b461..f4b72fa43b 100644
--- a/ansible/roles/cinder/templates/cinder.conf.j2
+++ b/ansible/roles/cinder/templates/cinder.conf.j2
@@ -47,6 +47,12 @@ backup_swift_auth = per_user
 backup_swift_auth_version = 1
 backup_swift_user =
 backup_swift_key =
+{% elif cinder_backup_driver == "s3" %}
+backup_driver = cinder.backup.drivers.s3.S3BackupDriver
+backup_s3_endpoint_url = {{ cinder_backup_s3_url }}
+backup_s3_store_bucket = {{ cinder_backup_s3_bucket }}
+backup_s3_store_access_key = {{ cinder_backup_s3_access_key }}
+backup_s3_store_secret_key = {{ cinder_backup_s3_secret_key }}
 {% endif %}
 {% endif %}
 
diff --git a/ansible/roles/glance/defaults/main.yml b/ansible/roles/glance/defaults/main.yml
index a15ecc895e..e14c67f0dc 100644
--- a/ansible/roles/glance/defaults/main.yml
+++ b/ansible/roles/glance/defaults/main.yml
@@ -139,6 +139,13 @@ glance_database_shard:
 haproxy_glance_api_client_timeout: "6h"
 haproxy_glance_api_server_timeout: "6h"
 
+####################
+# Glance S3 Backend
+####################
+glance_backend_s3_url: "{{ s3_url }}"
+glance_backend_s3_bucket: "{{ s3_bucket }}"
+glance_backend_s3_access_key: "{{ s3_access_key }}"
+glance_backend_s3_secret_key: "{{ s3_secret_key }}"
 
 ####################
 # Docker
@@ -209,6 +216,9 @@ glance_api_container_proxy: "{{ container_proxy }}"
 # Glance
 ####################
 glance_backends:
+  - name: s3
+    type: s3
+    enabled: "{{ glance_backend_s3 | bool }}"
   - name: file
     type: file
     enabled: "{{ glance_backend_file | bool }}"
@@ -232,6 +242,7 @@ glance_ceph_backends:
     enabled: "{{ glance_backend_ceph | bool }}"
 
 glance_store_backends: "{{ glance_backends | selectattr('enabled', 'equalto', true) | list + glance_ceph_backends | selectattr('enabled', 'equalto', true) | list }}"
+glance_default_backend: "{% if glance_backend_vmware | bool %}vmware{% elif glance_backend_ceph | bool %}{{ glance_ceph_backends[0].name }}{% elif glance_backend_swift | bool %}swift{% elif glance_backend_s3 | bool %}s3{% else %}file{% endif %}"
 
 ####################
 # OpenStack
diff --git a/ansible/roles/glance/tasks/precheck.yml b/ansible/roles/glance/tasks/precheck.yml
index d7d54c7f19..f1fd7d78af 100644
--- a/ansible/roles/glance/tasks/precheck.yml
+++ b/ansible/roles/glance/tasks/precheck.yml
@@ -24,3 +24,15 @@
     - glance_services['glance-api'].host_in_groups | bool
     - glance_services['glance-api'].enabled | bool
     - container_facts['glance_api'] is not defined
+
+- name: Check if S3 configurations are defined
+  assert:
+    that:
+      - vars[item] is defined
+    msg: "Glance S3 backend is enabled, either the {{ item }} or {{ item | replace('glance_backend_','') }} variable must be defined."
+  with_items:
+    - glance_backend_s3_url
+    - glance_backend_s3_bucket
+    - glance_backend_s3_access_key
+    - glance_backend_s3_secret_key
+  when: glance_backend_s3 | bool
diff --git a/ansible/roles/glance/templates/glance-api.conf.j2 b/ansible/roles/glance/templates/glance-api.conf.j2
index 9f603a7150..4590b8c04c 100644
--- a/ansible/roles/glance/templates/glance-api.conf.j2
+++ b/ansible/roles/glance/templates/glance-api.conf.j2
@@ -56,15 +56,7 @@ memcached_servers = {% for host in groups['memcached'] %}{{ 'api' | kolla_addres
 flavor = {% if enable_glance_image_cache | bool %}keystone+cachemanagement{% else %}keystone{% endif %}
 
 [glance_store]
-{% if glance_backend_vmware | bool %}
-default_backend = vmware
-{% elif glance_backend_ceph | bool %}
-default_backend = "{{ glance_ceph_backends[0].name }}"
-{% elif glance_backend_swift | bool %}
-default_backend = swift
-{% else %}
-default_backend = file
-{% endif %}
+default_backend = "{{ glance_default_backend }}"
 
 {% if glance_backend_file | bool %}
 [file]
@@ -92,6 +84,14 @@ swift_store_config_file = /etc/glance/glance-swift.conf
 swift_store_auth_insecure = True
 {% endif %}
 
+{% if glance_backend_s3 | bool %}
+[s3]
+s3_store_host = {{ glance_backend_s3_url }}
+s3_store_access_key = {{ glance_backend_s3_access_key }}
+s3_store_secret_key = {{ glance_backend_s3_secret_key }}
+s3_store_bucket = {{ glance_backend_s3_bucket }}
+{% endif %}
+
 {% if glance_backend_vmware | bool %}
 [vmware]
 vmware_server_host = {{ vmware_vcenter_host_ip }}
diff --git a/doc/source/reference/shared-services/glance-guide.rst b/doc/source/reference/shared-services/glance-guide.rst
index 89b82bb6f0..48e8774aaa 100644
--- a/doc/source/reference/shared-services/glance-guide.rst
+++ b/doc/source/reference/shared-services/glance-guide.rst
@@ -63,6 +63,34 @@ To enable the vmware backend manually:
 
    glance_backend_vmware: "yes"
 
+Glance with S3 Backend
+~~~~~~~~~~~~~~~~~~~~~~
+
+Configuring Glance for S3 includes the following steps:
+
+#. Enable Glance S3 backend in ``globals.yml``:
+
+.. code-block:: yaml
+
+   glance_backend_s3: "yes"
+
+#. Configure S3 connection details in ``/etc/kolla/globals.yml``:
+
+   * ``glance_backend_s3_url`` (example: ``http://127.0.0.1:9000``)
+   * ``glance_backend_s3_access_key`` (example: ``minio``)
+   * ``glance_backend_s3_bucket`` (example: ``glance``)
+   * ``glance_backend_s3_secret_key`` (example: ``admin``)
+
+#. If you wish to use a single S3 backend for all supported services,
+use the following variables:
+
+   * ``s3_url``
+   * ``s3_access_key``
+   * ``s3_glance_bucket``
+   * ``s3_secret_key``
+
+   All Glance S3 configurations use these options as default values.
+
 Swift backend
 ~~~~~~~~~~~~~
 
diff --git a/doc/source/reference/storage/cinder-guide.rst b/doc/source/reference/storage/cinder-guide.rst
index 18f36d5f77..49f16405c1 100644
--- a/doc/source/reference/storage/cinder-guide.rst
+++ b/doc/source/reference/storage/cinder-guide.rst
@@ -201,6 +201,34 @@ in Kolla, the following parameter must be specified in ``globals.yml``:
 All configuration for custom NFS backend should be performed
 via ``cinder.conf`` in config overrides directory.
 
+Cinder-Backup with S3 Backend
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Configuring Cinder-Backup for S3 includes the following steps:
+
+#. Enable Cinder-Backup S3 backend in ``globals.yml``:
+
+.. code-block:: yaml
+
+   cinder_backup_driver: "s3"
+
+#. Configure S3 connection details in ``/etc/kolla/globals.yml``:
+
+   * ``cinder_backup_s3_url`` (example: ``http://127.0.0.1:9000``)
+   * ``cinder_backup_s3_access_key`` (example: ``minio``)
+   * ``cinder_backup_s3_bucket`` (example: ``cinder``)
+   * ``cinder_backup_s3_secret_key`` (example: ``admin``)
+
+#. If you wish to use a single S3 backend for all supported services,
+use the following variables:
+
+   * ``s3_url``
+   * ``s3_access_key``
+   * ``s3_glance_bucket``
+   * ``s3_secret_key``
+
+   All Cinder-Backup S3 configurations use these options as default values.
+
 Customizing backend names in cinder.conf
 ----------------------------------------
 
diff --git a/etc/kolla/globals.yml b/etc/kolla/globals.yml
index 223ec3bfa6..3eec3ba452 100644
--- a/etc/kolla/globals.yml
+++ b/etc/kolla/globals.yml
@@ -435,6 +435,15 @@ workaround_ansible_issue_8743: yes
 #enable_watcher: "no"
 #enable_zun: "no"
 
+#############
+# S3 options
+#############
+# Common options for S3 Cinder Backup and Glance S3 backend.
+#s3_url:
+#s3_bucket:
+#s3_access_key:
+#s3_secret_key:
+
 ##################
 # RabbitMQ options
 ##################
@@ -513,6 +522,7 @@ workaround_ansible_issue_8743: yes
 #glance_backend_file: "yes"
 #glance_backend_swift: "no"
 #glance_backend_vmware: "no"
+#glance_backend_s3: "no"
 #enable_glance_image_cache: "no"
 #glance_enable_property_protection: "no"
 #glance_enable_interoperable_image_import: "no"
@@ -521,6 +531,14 @@ workaround_ansible_issue_8743: yes
 # the default value is "no".
 #glance_enable_rolling_upgrade: "no"
 
+####################
+# Glance S3 Backend
+####################
+#glance_backend_s3_url: "{{ s3_url }}"
+#glance_backend_s3_bucket: "{{ s3_bucket }}"
+#glance_backend_s3_access_key: "{{ s3_access_key }}"
+#glance_backend_s3_secret_key: "{{ s3_secret_key }}"
+
 ####################
 # Osprofiler options
 ####################
@@ -554,11 +572,17 @@ workaround_ansible_issue_8743: yes
 # Valid options are [ '', redis, etcd ]
 #cinder_coordination_backend: "{{ 'redis' if enable_redis|bool else 'etcd' if enable_etcd|bool else '' }}"
 
-# Valid options are [ nfs, swift, ceph ]
+# Valid options are [ nfs, swift, ceph, s3 ]
 #cinder_backup_driver: "ceph"
 #cinder_backup_share: ""
 #cinder_backup_mount_options_nfs: ""
 
+# Cinder backup S3 options
+#cinder_backup_s3_url: "{{ s3_url }}"
+#cinder_backup_s3_bucket: "{{ s3_bucket }}"
+#cinder_backup_s3_access_key: "{{ s3_access_key }}"
+#cinder_backup_s3_secret_key: "{{ s3_secret_key }}"
+
 #######################
 # Cloudkitty options
 #######################
diff --git a/releasenotes/notes/s3-backend-support-180f57b6d0e417f2.yaml b/releasenotes/notes/s3-backend-support-180f57b6d0e417f2.yaml
new file mode 100644
index 0000000000..b8f5e06b3c
--- /dev/null
+++ b/releasenotes/notes/s3-backend-support-180f57b6d0e417f2.yaml
@@ -0,0 +1,4 @@
+---
+features:
+  - Added support for Cinder-Backup with S3 backend.
+  - Added support for Glance with S3 backend