Browse code

Configure endpoints to use SSL natively or via proxy

Configure nova, cinder, glance, swift and neutron to use SSL
on the endpoints using either SSL natively or via a TLS proxy
using stud.

To enable SSL via proxy, in local.conf add

ENABLED_SERVICES+=,tls-proxy

This will create a new test root CA, a subordinate CA and an SSL
server cert. It uses the value of hostname -f for the certificate
subject. The CA certicates are also added to the system CA bundle.

To enable SSL natively, in local.conf add:

USE_SSL=True

Native SSL by default will also use the devstack-generate root and
subordinate CA.

You can override this on a per-service basis by setting

<SERVICE>_SSL_CERT=/path/to/cert
<SERVICE>_SSL_KEY=/path/to/key
<SERVICE>_SSL_PATH=/path/to/ca

You should also set SERVICE_HOST to the FQDN of the host. This
value defaults to the host IP address.

Change-Id: I36fe56c063ca921131ad98439bd452cb135916ac
Closes-Bug: 1328226

Rob Crittenden authored on 2014/03/20 06:47:42
Showing 13 changed files
... ...
@@ -11,6 +11,9 @@ Listen %ADMINPORT%
11 11
     </IfVersion>
12 12
     ErrorLog /var/log/%APACHE_NAME%/keystone.log
13 13
     CustomLog /var/log/%APACHE_NAME%/keystone_access.log combined
14
+    %SSLENGINE%
15
+    %SSLCERTFILE%
16
+    %SSLKEYFILE%
14 17
 </VirtualHost>
15 18
 
16 19
 <VirtualHost *:%ADMINPORT%>
... ...
@@ -23,6 +26,9 @@ Listen %ADMINPORT%
23 23
     </IfVersion>
24 24
     ErrorLog /var/log/%APACHE_NAME%/keystone.log
25 25
     CustomLog /var/log/%APACHE_NAME%/keystone_access.log combined
26
+    %SSLENGINE%
27
+    %SSLCERTFILE%
28
+    %SSLKEYFILE%
26 29
 </VirtualHost>
27 30
 
28 31
 # Workaround for missing path on RHEL6, see
... ...
@@ -9,5 +9,6 @@ python-routes
9 9
 python-sqlalchemy
10 10
 python-webob
11 11
 sqlite
12
+mod_ssl
12 13
 
13 14
 # Deps installed via pip for RHEL
... ...
@@ -73,7 +73,7 @@ function upload_image {
73 73
     # OpenVZ-format images are provided as .tar.gz, but not decompressed prior to loading
74 74
     if [[ "$image_url" =~ 'openvz' ]]; then
75 75
         image_name="${image_fname%.tar.gz}"
76
-        openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name" --public --container-format ami --disk-format ami < "${image}"
76
+        openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name" --public --container-format ami --disk-format ami < "${image}"
77 77
         return
78 78
     fi
79 79
 
... ...
@@ -184,7 +184,7 @@ function upload_image {
184 184
         vmdk_adapter_type="${props[1]:-$vmdk_adapter_type}"
185 185
         vmdk_net_adapter="${props[2]:-$vmdk_net_adapter}"
186 186
 
187
-        openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name" --public --container-format bare --disk-format vmdk --property vmware_disktype="$vmdk_disktype" --property vmware_adaptertype="$vmdk_adapter_type" --property hw_vif_model="$vmdk_net_adapter" < "${image}"
187
+        openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name" --public --container-format bare --disk-format vmdk --property vmware_disktype="$vmdk_disktype" --property vmware_adaptertype="$vmdk_adapter_type" --property hw_vif_model="$vmdk_net_adapter" < "${image}"
188 188
         return
189 189
     fi
190 190
 
... ...
@@ -202,7 +202,7 @@ function upload_image {
202 202
         fi
203 203
         openstack \
204 204
             --os-token $token \
205
-            --os-url http://$GLANCE_HOSTPORT \
205
+            --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT \
206 206
             image create \
207 207
             "$image_name" --public \
208 208
             --container-format=ovf --disk-format=vhd \
... ...
@@ -217,7 +217,7 @@ function upload_image {
217 217
         image_name="${image_fname%.xen-raw.tgz}"
218 218
         openstack \
219 219
             --os-token $token \
220
-            --os-url http://$GLANCE_HOSTPORT \
220
+            --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT \
221 221
             image create \
222 222
             "$image_name" --public \
223 223
             --container-format=tgz --disk-format=raw \
... ...
@@ -295,9 +295,9 @@ function upload_image {
295 295
 
296 296
     if [ "$container_format" = "bare" ]; then
297 297
         if [ "$unpack" = "zcat" ]; then
298
-            openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name" $img_property --public --container-format=$container_format --disk-format $disk_format < <(zcat --force "${image}")
298
+            openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name" $img_property --public --container-format=$container_format --disk-format $disk_format < <(zcat --force "${image}")
299 299
         else
300
-            openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name" $img_property --public --container-format=$container_format --disk-format $disk_format < "${image}"
300
+            openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name" $img_property --public --container-format=$container_format --disk-format $disk_format < "${image}"
301 301
         fi
302 302
     else
303 303
         # Use glance client to add the kernel the root filesystem.
... ...
@@ -305,12 +305,12 @@ function upload_image {
305 305
         # kernel for use when uploading the root filesystem.
306 306
         local kernel_id="" ramdisk_id="";
307 307
         if [ -n "$kernel" ]; then
308
-            kernel_id=$(openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name-kernel" $img_property --public --container-format aki --disk-format aki < "$kernel" | grep ' id ' | get_field 2)
308
+            kernel_id=$(openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name-kernel" $img_property --public --container-format aki --disk-format aki < "$kernel" | grep ' id ' | get_field 2)
309 309
         fi
310 310
         if [ -n "$ramdisk" ]; then
311
-            ramdisk_id=$(openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "$image_name-ramdisk" $img_property --public --container-format ari --disk-format ari < "$ramdisk" | grep ' id ' | get_field 2)
311
+            ramdisk_id=$(openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "$image_name-ramdisk" $img_property --public --container-format ari --disk-format ari < "$ramdisk" | grep ' id ' | get_field 2)
312 312
         fi
313
-        openstack --os-token $token --os-url http://$GLANCE_HOSTPORT image create "${image_name%.img}" $img_property --public --container-format ami --disk-format ami ${kernel_id:+--property kernel_id=$kernel_id} ${ramdisk_id:+--property ramdisk_id=$ramdisk_id} < "${image}"
313
+        openstack --os-token $token --os-url $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT image create "${image_name%.img}" $img_property --public --container-format ami --disk-format ami ${kernel_id:+--property kernel_id=$kernel_id} ${ramdisk_id:+--property ramdisk_id=$ramdisk_id} < "${image}"
314 314
     fi
315 315
 }
316 316
 
... ...
@@ -339,7 +339,7 @@ function use_database {
339 339
 function wait_for_service {
340 340
     local timeout=$1
341 341
     local url=$2
342
-    timeout $timeout sh -c "while ! curl --noproxy '*' -s $url >/dev/null; do sleep 1; done"
342
+    timeout $timeout sh -c "while ! curl -k --noproxy '*' -s $url >/dev/null; do sleep 1; done"
343 343
 }
344 344
 
345 345
 
... ...
@@ -46,6 +46,9 @@ CINDER_CONF=$CINDER_CONF_DIR/cinder.conf
46 46
 CINDER_API_PASTE_INI=$CINDER_CONF_DIR/api-paste.ini
47 47
 
48 48
 # Public facing bits
49
+if is_ssl_enabled_service "cinder" || is_service_enabled tls-proxy; then
50
+    CINDER_SERVICE_PROTOCOL="https"
51
+fi
49 52
 CINDER_SERVICE_HOST=${CINDER_SERVICE_HOST:-$SERVICE_HOST}
50 53
 CINDER_SERVICE_PORT=${CINDER_SERVICE_PORT:-8776}
51 54
 CINDER_SERVICE_PORT_INT=${CINDER_SERVICE_PORT_INT:-18776}
... ...
@@ -299,6 +302,20 @@ function configure_cinder {
299 299
     fi
300 300
 
301 301
     iniset $CINDER_CONF DEFAULT osapi_volume_workers "$API_WORKERS"
302
+
303
+    iniset $CINDER_CONF DEFAULT glance_api_servers "${GLANCE_SERVICE_PROTOCOL}://${GLANCE_HOSTPORT}"
304
+    if is_ssl_enabled_service glance || is_service_enabled tls-proxy; then
305
+        iniset $CINDER_CONF DEFAULT glance_protocol https
306
+    fi
307
+
308
+    # Register SSL certificates if provided
309
+    if is_ssl_enabled_service cinder; then
310
+        ensure_certificates CINDER
311
+
312
+        iniset $CINDER_CONF DEFAULT ssl_cert_file "$CINDER_SSL_CERT"
313
+        iniset $CINDER_CONF DEFAULT ssl_key_file "$CINDER_SSL_KEY"
314
+    fi
315
+
302 316
 }
303 317
 
304 318
 # create_cinder_accounts() - Set up common required cinder accounts
... ...
@@ -399,6 +416,12 @@ function _configure_tgt_for_config_d {
399 399
 
400 400
 # start_cinder() - Start running processes, including screen
401 401
 function start_cinder {
402
+    local service_port=$CINDER_SERVICE_PORT
403
+    local service_protocol=$CINDER_SERVICE_PROTOCOL
404
+    if is_service_enabled tls-proxy; then
405
+        service_port=$CINDER_SERVICE_PORT_INT
406
+        service_protocol="http"
407
+    fi
402 408
     if is_service_enabled c-vol; then
403 409
         # Delete any old stack.conf
404 410
         sudo rm -f /etc/tgt/conf.d/stack.conf
... ...
@@ -425,7 +448,7 @@ function start_cinder {
425 425
 
426 426
     run_process c-api "$CINDER_BIN_DIR/cinder-api --config-file $CINDER_CONF"
427 427
     echo "Waiting for Cinder API to start..."
428
-    if ! wait_for_service $SERVICE_TIMEOUT $CINDER_SERVICE_PROTOCOL://$CINDER_SERVICE_HOST:$CINDER_SERVICE_PORT; then
428
+    if ! wait_for_service $SERVICE_TIMEOUT $service_protocol://$CINDER_SERVICE_HOST:$service_port; then
429 429
         die $LINENO "c-api did not start"
430 430
     fi
431 431
 
... ...
@@ -51,8 +51,18 @@ else
51 51
     GLANCE_BIN_DIR=$(get_python_exec_prefix)
52 52
 fi
53 53
 
54
+if is_ssl_enabled_service "glance" || is_service_enabled tls-proxy; then
55
+    GLANCE_SERVICE_PROTOCOL="https"
56
+fi
57
+
54 58
 # Glance connection info.  Note the port must be specified.
55
-GLANCE_HOSTPORT=${GLANCE_HOSTPORT:-$SERVICE_HOST:9292}
59
+GLANCE_SERVICE_HOST=${GLANCE_SERVICE_HOST:-$SERVICE_HOST}
60
+GLANCE_SERVICE_PORT=${GLANCE_SERVICE_PORT:-9292}
61
+GLANCE_SERVICE_PORT_INT=${GLANCE_SERVICE_PORT_INT:-19292}
62
+GLANCE_HOSTPORT=${GLANCE_HOSTPORT:-$GLANCE_SERVICE_HOST:$GLANCE_SERVICE_PORT}
63
+GLANCE_SERVICE_PROTOCOL=${GLANCE_SERVICE_PROTOCOL:-$SERVICE_PROTOCOL}
64
+GLANCE_REGISTRY_PORT=${GLANCE_REGISTRY_PORT:-9191}
65
+GLANCE_REGISTRY_PORT_INT=${GLANCE_REGISTRY_PORT_INT:-19191}
56 66
 
57 67
 # Tell Tempest this project is present
58 68
 TEMPEST_SERVICES+=,glance
... ...
@@ -148,6 +158,26 @@ function configure_glance {
148 148
         iniset $GLANCE_API_CONF glance_store stores "file, http, swift"
149 149
     fi
150 150
 
151
+    if is_service_enabled tls-proxy; then
152
+        iniset $GLANCE_API_CONF DEFAULT bind_port $GLANCE_SERVICE_PORT_INT
153
+        iniset $GLANCE_REGISTRY_CONF DEFAULT bind_port $GLANCE_REGISTRY_PORT_INT
154
+    fi
155
+
156
+    # Register SSL certificates if provided
157
+    if is_ssl_enabled_service glance; then
158
+        ensure_certificates GLANCE
159
+
160
+        iniset $GLANCE_API_CONF DEFAULT cert_file "$GLANCE_SSL_CERT"
161
+        iniset $GLANCE_API_CONF DEFAULT key_file "$GLANCE_SSL_KEY"
162
+
163
+        iniset $GLANCE_REGISTRY_CONF DEFAULT cert_file "$GLANCE_SSL_CERT"
164
+        iniset $GLANCE_REGISTRY_CONF DEFAULT key_file "$GLANCE_SSL_KEY"
165
+    fi
166
+
167
+    if is_ssl_enabled_service glance || is_service_enabled tls-proxy; then
168
+        iniset $GLANCE_API_CONF DEFAULT registry_client_protocol https
169
+    fi
170
+
151 171
     cp -p $GLANCE_DIR/etc/glance-registry-paste.ini $GLANCE_REGISTRY_PASTE_INI
152 172
 
153 173
     cp -p $GLANCE_DIR/etc/glance-api-paste.ini $GLANCE_API_PASTE_INI
... ...
@@ -176,6 +206,14 @@ function configure_glance {
176 176
     cp -p $GLANCE_DIR/etc/schema-image.json $GLANCE_SCHEMA_JSON
177 177
 
178 178
     cp -p $GLANCE_DIR/etc/metadefs/*.json $GLANCE_METADEF_DIR
179
+
180
+    if is_ssl_enabled_service "cinder" || is_service_enabled tls-proxy; then
181
+        CINDER_SERVICE_HOST=${CINDER_SERVICE_HOST:-$SERVICE_HOST}
182
+        CINDER_SERVICE_PORT=${CINDER_SERVICE_PORT:-8776}
183
+
184
+        iniset $GLANCE_API_CONF DEFAULT cinder_endpoint_template "https://$CINDER_SERVICE_HOST:$CINDER_SERVICE_PORT/v1/%(project_id)s"
185
+        iniset $GLANCE_CACHE_CONF DEFAULT cinder_endpoint_template "https://$CINDER_SERVICE_HOST:$CINDER_SERVICE_PORT/v1/%(project_id)s"
186
+    fi
179 187
 }
180 188
 
181 189
 # create_glance_accounts() - Set up common required glance accounts
... ...
@@ -206,9 +244,9 @@ function create_glance_accounts {
206 206
                 "image" "Glance Image Service")
207 207
             get_or_create_endpoint $glance_service \
208 208
                 "$REGION_NAME" \
209
-                "http://$GLANCE_HOSTPORT" \
210
-                "http://$GLANCE_HOSTPORT" \
211
-                "http://$GLANCE_HOSTPORT"
209
+                "$GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT" \
210
+                "$GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT" \
211
+                "$GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT"
212 212
         fi
213 213
     fi
214 214
 }
... ...
@@ -265,10 +303,17 @@ function install_glance {
265 265
 
266 266
 # start_glance() - Start running processes, including screen
267 267
 function start_glance {
268
+    local service_protocol=$GLANCE_SERVICE_PROTOCOL
269
+    if is_service_enabled tls-proxy; then
270
+        start_tls_proxy '*' $GLANCE_SERVICE_PORT $GLANCE_SERVICE_HOST $GLANCE_SERVICE_PORT_INT &
271
+        start_tls_proxy '*' $GLANCE_REGISTRY_PORT $GLANCE_SERVICE_HOST $GLANCE_REGISTRY_PORT_INT &
272
+    fi
273
+
268 274
     run_process g-reg "$GLANCE_BIN_DIR/glance-registry --config-file=$GLANCE_CONF_DIR/glance-registry.conf"
269 275
     run_process g-api "$GLANCE_BIN_DIR/glance-api --config-file=$GLANCE_CONF_DIR/glance-api.conf"
276
+
270 277
     echo "Waiting for g-api ($GLANCE_HOSTPORT) to start..."
271
-    if ! timeout $SERVICE_TIMEOUT sh -c "while ! wget --no-proxy -q -O- http://$GLANCE_HOSTPORT; do sleep 1; done"; then
278
+    if ! wait_for_service $SERVICE_TIMEOUT $GLANCE_SERVICE_PROTOCOL://$GLANCE_HOSTPORT; then
272 279
         die $LINENO "g-api did not start"
273 280
     fi
274 281
 }
... ...
@@ -113,7 +113,7 @@ function configure_heat {
113 113
     configure_auth_token_middleware $HEAT_CONF heat $HEAT_AUTH_CACHE_DIR
114 114
 
115 115
     if is_ssl_enabled_service "key"; then
116
-        iniset $HEAT_CONF clients_keystone ca_file $KEYSTONE_SSL_CA
116
+        iniset $HEAT_CONF clients_keystone ca_file $SSL_BUNDLE_FILE
117 117
     fi
118 118
 
119 119
     # ec2authtoken
... ...
@@ -131,6 +131,18 @@ function configure_heat {
131 131
     # Cloudwatch API
132 132
     iniset $HEAT_CONF heat_api_cloudwatch bind_port $HEAT_API_CW_PORT
133 133
 
134
+    if is_ssl_enabled_service "key" || is_service_enabled tls-proxy; then
135
+        iniset $HEAT_CONF clients_keystone ca_file $SSL_BUNDLE_FILE
136
+    fi
137
+
138
+    if is_ssl_enabled_service "nova" || is_service_enabled tls-proxy; then
139
+        iniset $HEAT_CONF clients_nova ca_file $SSL_BUNDLE_FILE
140
+    fi
141
+
142
+    if is_ssl_enabled_service "cinder" || is_service_enabled tls-proxy; then
143
+        iniset $HEAT_CONF clients_cinder ca_file $SSL_BUNDLE_FILE
144
+    fi
145
+
134 146
     # heat environment
135 147
     sudo mkdir -p $HEAT_ENV_DIR
136 148
     sudo chown $STACK_USER $HEAT_ENV_DIR
... ...
@@ -95,7 +95,7 @@ KEYSTONE_VALID_IDENTITY_BACKENDS=kvs,ldap,pam,sql
95 95
 KEYSTONE_VALID_ASSIGNMENT_BACKENDS=kvs,ldap,sql
96 96
 
97 97
 # if we are running with SSL use https protocols
98
-if is_ssl_enabled_service "key"; then
98
+if is_ssl_enabled_service "key" || is_service_enabled tls-proxy; then
99 99
     KEYSTONE_AUTH_PROTOCOL="https"
100 100
     KEYSTONE_SERVICE_PROTOCOL="https"
101 101
 fi
... ...
@@ -123,7 +123,21 @@ function _config_keystone_apache_wsgi {
123 123
     sudo mkdir -p $KEYSTONE_WSGI_DIR
124 124
 
125 125
     local keystone_apache_conf=$(apache_site_config_for keystone)
126
-    local apache_version=$(get_apache_version)
126
+    local keystone_ssl=""
127
+    local keystone_certfile=""
128
+    local keystone_keyfile=""
129
+    local keystone_service_port=$KEYSTONE_SERVICE_PORT
130
+    local keystone_auth_port=$KEYSTONE_AUTH_PORT
131
+
132
+    if is_ssl_enabled_service key; then
133
+        keystone_ssl="SSLEngine On"
134
+        keystone_certfile="SSLCertificateFile $KEYSTONE_SSL_CERT"
135
+        keystone_keyfile="SSLCertificateKeyFile $KEYSTONE_SSL_KEY"
136
+    fi
137
+    if is_service_enabled tls-proxy; then
138
+        keystone_service_port=$KEYSTONE_SERVICE_PORT_INT
139
+        keystone_auth_port=$KEYSTONE_AUTH_PORT_INT
140
+    fi
127 141
 
128 142
     # copy proxy vhost and wsgi file
129 143
     sudo cp $KEYSTONE_DIR/httpd/keystone.py $KEYSTONE_WSGI_DIR/main
... ...
@@ -131,11 +145,14 @@ function _config_keystone_apache_wsgi {
131 131
 
132 132
     sudo cp $FILES/apache-keystone.template $keystone_apache_conf
133 133
     sudo sed -e "
134
-        s|%PUBLICPORT%|$KEYSTONE_SERVICE_PORT|g;
135
-        s|%ADMINPORT%|$KEYSTONE_AUTH_PORT|g;
134
+        s|%PUBLICPORT%|$keystone_service_port|g;
135
+        s|%ADMINPORT%|$keystone_auth_port|g;
136 136
         s|%APACHE_NAME%|$APACHE_NAME|g;
137 137
         s|%PUBLICWSGI%|$KEYSTONE_WSGI_DIR/main|g;
138 138
         s|%ADMINWSGI%|$KEYSTONE_WSGI_DIR/admin|g;
139
+        s|%SSLENGINE%|$keystone_ssl|g;
140
+        s|%SSLCERTFILE%|$keystone_certfile|g;
141
+        s|%SSLKEYFILE%|$keystone_keyfile|g;
139 142
         s|%USER%|$STACK_USER|g
140 143
     " -i $keystone_apache_conf
141 144
 }
... ...
@@ -200,8 +217,13 @@ function configure_keystone {
200 200
     fi
201 201
 
202 202
     # Set the URL advertised in the ``versions`` structure returned by the '/' route
203
-    iniset $KEYSTONE_CONF DEFAULT public_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:%(public_port)s/"
204
-    iniset $KEYSTONE_CONF DEFAULT admin_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:%(admin_port)s/"
203
+    if is_service_enabled tls-proxy; then
204
+        iniset $KEYSTONE_CONF DEFAULT public_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:$KEYSTONE_SERVICE_PORT/"
205
+        iniset $KEYSTONE_CONF DEFAULT admin_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:$KEYSTONE_AUTH_PORT/"
206
+    else
207
+        iniset $KEYSTONE_CONF DEFAULT public_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:%(public_port)s/"
208
+        iniset $KEYSTONE_CONF DEFAULT admin_endpoint "$KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:%(admin_port)s/"
209
+    fi
205 210
     iniset $KEYSTONE_CONF DEFAULT admin_bind_host "$KEYSTONE_ADMIN_BIND_HOST"
206 211
 
207 212
     # Register SSL certificates if provided
... ...
@@ -412,7 +434,7 @@ function configure_auth_token_middleware {
412 412
     iniset $conf_file $section auth_port $KEYSTONE_AUTH_PORT
413 413
     iniset $conf_file $section auth_protocol $KEYSTONE_AUTH_PROTOCOL
414 414
     iniset $conf_file $section identity_uri $KEYSTONE_AUTH_URI
415
-    iniset $conf_file $section cafile $KEYSTONE_SSL_CA
415
+    iniset $conf_file $section cafile $SSL_BUNDLE_FILE
416 416
     configure_API_version $conf_file $IDENTITY_API_VERSION $section
417 417
     iniset $conf_file $section admin_tenant_name $SERVICE_TENANT_NAME
418 418
     iniset $conf_file $section admin_user $admin_user
... ...
@@ -489,6 +511,9 @@ function install_keystone {
489 489
     setup_develop $KEYSTONE_DIR
490 490
     if [ "$KEYSTONE_USE_MOD_WSGI" == "True" ]; then
491 491
         install_apache_wsgi
492
+        if is_ssl_enabled_service "key"; then
493
+            enable_mod_ssl
494
+        fi
492 495
     fi
493 496
 }
494 497
 
... ...
@@ -496,8 +521,10 @@ function install_keystone {
496 496
 function start_keystone {
497 497
     # Get right service port for testing
498 498
     local service_port=$KEYSTONE_SERVICE_PORT
499
+    local auth_protocol=$KEYSTONE_AUTH_PROTOCOL
499 500
     if is_service_enabled tls-proxy; then
500 501
         service_port=$KEYSTONE_SERVICE_PORT_INT
502
+        auth_protocol="http"
501 503
     fi
502 504
 
503 505
     if [ "$KEYSTONE_USE_MOD_WSGI" == "True" ]; then
... ...
@@ -514,7 +541,7 @@ function start_keystone {
514 514
     # Check that the keystone service is running. Even if the tls tunnel
515 515
     # should be enabled, make sure the internal port is checked using
516 516
     # unencryted traffic at this point.
517
-    if ! timeout $SERVICE_TIMEOUT sh -c "while ! curl --noproxy '*' -k -s http://$KEYSTONE_SERVICE_HOST:$service_port/v$IDENTITY_API_VERSION/ >/dev/null; do sleep 1; done"; then
517
+    if ! timeout $SERVICE_TIMEOUT sh -c "while ! curl --noproxy '*' -k -s $auth_protocol://$KEYSTONE_SERVICE_HOST:$service_port/v$IDENTITY_API_VERSION/ >/dev/null; do sleep 1; done"; then
518 518
         die $LINENO "keystone did not start"
519 519
     fi
520 520
 
... ...
@@ -69,6 +69,11 @@ PUBLIC_NETWORK_GATEWAY=${PUBLIC_NETWORK_GATEWAY:-172.24.4.1}
69 69
 PRIVATE_SUBNET_NAME=${PRIVATE_SUBNET_NAME:-"private-subnet"}
70 70
 PUBLIC_SUBNET_NAME=${PUBLIC_SUBNET_NAME:-"public-subnet"}
71 71
 
72
+if is_ssl_enabled_service "neutron" || is_service_enabled tls-proxy; then
73
+    Q_PROTOCOL="https"
74
+fi
75
+
76
+
72 77
 # Set up default directories
73 78
 NEUTRON_DIR=$DEST/neutron
74 79
 NEUTRONCLIENT_DIR=$DEST/python-neutronclient
... ...
@@ -105,8 +110,12 @@ Q_DB_NAME=${Q_DB_NAME:-neutron}
105 105
 Q_PLUGIN=${Q_PLUGIN:-ml2}
106 106
 # Default Neutron Port
107 107
 Q_PORT=${Q_PORT:-9696}
108
+# Default Neutron Internal Port when using TLS proxy
109
+Q_PORT_INT=${Q_PORT_INT:-19696}
108 110
 # Default Neutron Host
109 111
 Q_HOST=${Q_HOST:-$SERVICE_HOST}
112
+# Default protocol
113
+Q_PROTOCOL=${Q_PROTOCOL:-$SERVICE_PROTOCOL}
110 114
 # Default admin username
111 115
 Q_ADMIN_USERNAME=${Q_ADMIN_USERNAME:-neutron}
112 116
 # Default auth strategy
... ...
@@ -409,7 +418,7 @@ function create_nova_conf_neutron {
409 409
     iniset $NOVA_CONF neutron auth_strategy "$Q_AUTH_STRATEGY"
410 410
     iniset $NOVA_CONF neutron admin_tenant_name "$SERVICE_TENANT_NAME"
411 411
     iniset $NOVA_CONF neutron region_name "$REGION_NAME"
412
-    iniset $NOVA_CONF neutron url "http://$Q_HOST:$Q_PORT"
412
+    iniset $NOVA_CONF neutron url "${Q_PROTOCOL}://$Q_HOST:$Q_PORT"
413 413
 
414 414
     if [[ "$Q_USE_SECGROUP" == "True" ]]; then
415 415
         LIBVIRT_FIREWALL_DRIVER=nova.virt.firewall.NoopFirewallDriver
... ...
@@ -462,9 +471,9 @@ function create_neutron_accounts {
462 462
                 "network" "Neutron Service")
463 463
             get_or_create_endpoint $neutron_service \
464 464
                 "$REGION_NAME" \
465
-                "http://$SERVICE_HOST:$Q_PORT/" \
466
-                "http://$SERVICE_HOST:$Q_PORT/" \
467
-                "http://$SERVICE_HOST:$Q_PORT/"
465
+                "$Q_PROTOCOL://$SERVICE_HOST:$Q_PORT/" \
466
+                "$Q_PROTOCOL://$SERVICE_HOST:$Q_PORT/" \
467
+                "$Q_PROTOCOL://$SERVICE_HOST:$Q_PORT/"
468 468
         fi
469 469
     fi
470 470
 }
... ...
@@ -590,12 +599,25 @@ function install_neutron_agent_packages {
590 590
 # Start running processes, including screen
591 591
 function start_neutron_service_and_check {
592 592
     local cfg_file_options="$(determine_config_files neutron-server)"
593
+    local service_port=$Q_PORT
594
+    local service_protocol=$Q_PROTOCOL
595
+    if is_service_enabled tls-proxy; then
596
+        service_port=$Q_PORT_INT
597
+        service_protocol="http"
598
+    fi
593 599
     # Start the Neutron service
594 600
     run_process q-svc "python $NEUTRON_BIN_DIR/neutron-server $cfg_file_options"
595 601
     echo "Waiting for Neutron to start..."
596
-    if ! timeout $SERVICE_TIMEOUT sh -c "while ! wget --no-proxy -q -O- http://$Q_HOST:$Q_PORT; do sleep 1; done"; then
602
+    if is_ssl_enabled_service "neutron"; then
603
+        ssl_ca="--ca-certificate=${SSL_BUNDLE_FILE}"
604
+    fi
605
+    if ! timeout $SERVICE_TIMEOUT sh -c "while ! wget ${ssl_ca} --no-proxy -q -O- $service_protocol://$Q_HOST:$service_port; do sleep 1; done"; then
597 606
         die $LINENO "Neutron did not start"
598 607
     fi
608
+    # Start proxy if enabled
609
+    if is_service_enabled tls-proxy; then
610
+        start_tls_proxy '*' $Q_PORT $Q_HOST $Q_PORT_INT &
611
+    fi
599 612
 }
600 613
 
601 614
 # Start running processes, including screen
... ...
@@ -730,6 +752,23 @@ function _configure_neutron_common {
730 730
         setup_colorized_logging $NEUTRON_CONF DEFAULT project_id
731 731
     fi
732 732
 
733
+    if is_service_enabled tls-proxy; then
734
+        # Set the service port for a proxy to take the original
735
+        iniset $NEUTRON_CONF DEFAULT bind_port "$Q_PORT_INT"
736
+    fi
737
+
738
+    if is_ssl_enabled_service "nova"; then
739
+        iniset $NEUTRON_CONF DEFAULT nova_ca_certificates_file "$SSL_BUNDLE_FILE"
740
+    fi
741
+
742
+    if is_ssl_enabled_service "neutron"; then
743
+        ensure_certificates NEUTRON
744
+
745
+        iniset $NEUTRON_CONF DEFAULT use_ssl True
746
+        iniset $NEUTRON_CONF DEFAULT ssl_cert_file "$NEUTRON_SSL_CERT"
747
+        iniset $NEUTRON_CONF DEFAULT ssl_key_file "$NEUTRON_SSL_KEY"
748
+    fi
749
+
733 750
     _neutron_setup_rootwrap
734 751
 }
735 752
 
... ...
@@ -44,11 +44,20 @@ NOVA_CELLS_DB=${NOVA_CELLS_DB:-nova_cell}
44 44
 
45 45
 NOVA_API_PASTE_INI=${NOVA_API_PASTE_INI:-$NOVA_CONF_DIR/api-paste.ini}
46 46
 
47
+if is_ssl_enabled_service "nova" || is_service_enabled tls-proxy; then
48
+    NOVA_SERVICE_PROTOCOL="https"
49
+    EC2_SERVICE_PROTOCOL="https"
50
+else
51
+    EC2_SERVICE_PROTOCOL="http"
52
+fi
53
+
47 54
 # Public facing bits
48 55
 NOVA_SERVICE_HOST=${NOVA_SERVICE_HOST:-$SERVICE_HOST}
49 56
 NOVA_SERVICE_PORT=${NOVA_SERVICE_PORT:-8774}
50 57
 NOVA_SERVICE_PORT_INT=${NOVA_SERVICE_PORT_INT:-18774}
51 58
 NOVA_SERVICE_PROTOCOL=${NOVA_SERVICE_PROTOCOL:-$SERVICE_PROTOCOL}
59
+EC2_SERVICE_PORT=${EC2_SERVICE_PORT:-8773}
60
+EC2_SERVICE_PORT_INT=${EC2_SERVICE_PORT_INT:-18773}
52 61
 
53 62
 # Support entry points installation of console scripts
54 63
 if [[ -d $NOVA_DIR/bin ]]; then
... ...
@@ -375,9 +384,9 @@ create_nova_accounts() {
375 375
                 "ec2" "EC2 Compatibility Layer")
376 376
             get_or_create_endpoint $ec2_service \
377 377
                 "$REGION_NAME" \
378
-                "http://$SERVICE_HOST:8773/services/Cloud" \
379
-                "http://$SERVICE_HOST:8773/services/Admin" \
380
-                "http://$SERVICE_HOST:8773/services/Cloud"
378
+                "$EC2_SERVICE_PROTOCOL://$SERVICE_HOST:8773/services/Cloud" \
379
+                "$EC2_SERVICE_PROTOCOL://$SERVICE_HOST:8773/services/Admin" \
380
+                "$EC2_SERVICE_PROTOCOL://$SERVICE_HOST:8773/services/Cloud"
381 381
         fi
382 382
     fi
383 383
 
... ...
@@ -441,6 +450,16 @@ function create_nova_conf {
441 441
         configure_auth_token_middleware $NOVA_CONF nova $NOVA_AUTH_CACHE_DIR
442 442
     fi
443 443
 
444
+    if is_service_enabled cinder; then
445
+        iniset $NOVA_CONF DEFAULT volume_api_class "nova.volume.cinder.API"
446
+        if is_ssl_enabled_service "cinder" || is_service_enabled tls-proxy; then
447
+            CINDER_SERVICE_HOST=${CINDER_SERVICE_HOST:-$SERVICE_HOST}
448
+            CINDER_SERVICE_PORT=${CINDER_SERVICE_PORT:-8776}
449
+            iniset $NOVA_CONF DEFAULT cinder_endpoint_template "https://$CINDER_SERVICE_HOST:$CINDER_SERVICE_PORT/v1/%(project_id)s"
450
+            iniset $NOVA_CONF DEFAULT cinder_ca_certificates_file $SSL_BUNDLE_FILE
451
+        fi
452
+    fi
453
+
444 454
     if [ -n "$NOVA_STATE_PATH" ]; then
445 455
         iniset $NOVA_CONF DEFAULT state_path "$NOVA_STATE_PATH"
446 456
         iniset $NOVA_CONF DEFAULT lock_path "$NOVA_STATE_PATH"
... ...
@@ -508,12 +527,31 @@ function create_nova_conf {
508 508
     fi
509 509
 
510 510
     iniset $NOVA_CONF DEFAULT ec2_dmz_host "$EC2_DMZ_HOST"
511
+    iniset $NOVA_CONF DEFAULT keystone_ec2_url $KEYSTONE_SERVICE_PROTOCOL://$KEYSTONE_SERVICE_HOST:$KEYSTONE_SERVICE_PORT/v2.0/ec2tokens
511 512
     iniset_rpc_backend nova $NOVA_CONF DEFAULT
512
-    iniset $NOVA_CONF glance api_servers "$GLANCE_HOSTPORT"
513
+    iniset $NOVA_CONF glance api_servers "${GLANCE_SERVICE_PROTOCOL}://${GLANCE_HOSTPORT}"
513 514
 
514 515
     iniset $NOVA_CONF DEFAULT osci_compute_workers "$API_WORKERS"
515 516
     iniset $NOVA_CONF DEFAULT ec2_workers "$API_WORKERS"
516 517
     iniset $NOVA_CONF DEFAULT metadata_workers "$API_WORKERS"
518
+
519
+    if is_ssl_enabled_service glance || is_service_enabled tls-proxy; then
520
+        iniset $NOVA_CONF DEFAULT glance_protocol https
521
+    fi
522
+
523
+    # Register SSL certificates if provided
524
+    if is_ssl_enabled_service nova; then
525
+        ensure_certificates NOVA
526
+
527
+        iniset $NOVA_CONF DEFAULT ssl_cert_file "$NOVA_SSL_CERT"
528
+        iniset $NOVA_CONF DEFAULT ssl_key_file "$NOVA_SSL_KEY"
529
+
530
+        iniset $NOVA_CONF DEFAULT enabled_ssl_apis "$NOVA_ENABLED_APIS"
531
+    fi
532
+
533
+    if is_service_enabled tls-proxy; then
534
+        iniset $NOVA_CONF DEFAULT ec2_listen_port $EC2_SERVICE_PORT_INT
535
+    fi
517 536
 }
518 537
 
519 538
 function init_nova_cells {
... ...
@@ -642,19 +680,22 @@ function install_nova {
642 642
 function start_nova_api {
643 643
     # Get right service port for testing
644 644
     local service_port=$NOVA_SERVICE_PORT
645
+    local service_protocol=$NOVA_SERVICE_PROTOCOL
645 646
     if is_service_enabled tls-proxy; then
646 647
         service_port=$NOVA_SERVICE_PORT_INT
648
+        service_protocol="http"
647 649
     fi
648 650
 
649 651
     run_process n-api "$NOVA_BIN_DIR/nova-api"
650 652
     echo "Waiting for nova-api to start..."
651
-    if ! wait_for_service $SERVICE_TIMEOUT http://$SERVICE_HOST:$service_port; then
653
+    if ! wait_for_service $SERVICE_TIMEOUT $service_protocol://$SERVICE_HOST:$service_port; then
652 654
         die $LINENO "nova-api did not start"
653 655
     fi
654 656
 
655 657
     # Start proxies if enabled
656 658
     if is_service_enabled tls-proxy; then
657 659
         start_tls_proxy '*' $NOVA_SERVICE_PORT $NOVA_SERVICE_HOST $NOVA_SERVICE_PORT_INT &
660
+        start_tls_proxy '*' $EC2_SERVICE_PORT $NOVA_SERVICE_HOST $EC2_SERVICE_PORT_INT &
658 661
     fi
659 662
 }
660 663
 
... ...
@@ -29,6 +29,10 @@ set +o xtrace
29 29
 # Defaults
30 30
 # --------
31 31
 
32
+if is_ssl_enabled_service "s-proxy" || is_service_enabled tls-proxy; then
33
+    SWIFT_SERVICE_PROTOCOL="https"
34
+fi
35
+
32 36
 # Set up default directories
33 37
 SWIFT_DIR=$DEST/swift
34 38
 SWIFTCLIENT_DIR=$DEST/python-swiftclient
... ...
@@ -36,6 +40,9 @@ SWIFT_AUTH_CACHE_DIR=${SWIFT_AUTH_CACHE_DIR:-/var/cache/swift}
36 36
 SWIFT_APACHE_WSGI_DIR=${SWIFT_APACHE_WSGI_DIR:-/var/www/swift}
37 37
 SWIFT3_DIR=$DEST/swift3
38 38
 
39
+SWIFT_SERVICE_PROTOCOL=${SWIFT_SERVICE_PROTOCOL:-$SERVICE_PROTOCOL}
40
+SWIFT_DEFAULT_BIND_PORT_INT=${SWIFT_DEFAULT_BIND_PORT_INT:-8081}
41
+
39 42
 # TODO: add logging to different location.
40 43
 
41 44
 # Set ``SWIFT_DATA_DIR`` to the location of swift drives and objects.
... ...
@@ -334,7 +341,18 @@ function configure_swift {
334 334
     iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT log_level DEBUG
335 335
 
336 336
     iniuncomment ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT bind_port
337
-    iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT bind_port ${SWIFT_DEFAULT_BIND_PORT:-8080}
337
+    if is_service_enabled tls-proxy; then
338
+        iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT bind_port ${SWIFT_DEFAULT_BIND_PORT_INT}
339
+    else
340
+        iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT bind_port ${SWIFT_DEFAULT_BIND_PORT:-8080}
341
+    fi
342
+
343
+    if is_ssl_enabled_service s-proxy; then
344
+        ensure_certificates SWIFT
345
+
346
+        iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT cert_file "$SWIFT_SSL_CERT"
347
+        iniset ${SWIFT_CONFIG_PROXY_SERVER} DEFAULT key_file "$SWIFT_SSL_KEY"
348
+    fi
338 349
 
339 350
     # Devstack is commonly run in a small slow environment, so bump the
340 351
     # timeouts up.
... ...
@@ -401,7 +419,7 @@ paste.filter_factory = keystoneclient.middleware.s3_token:filter_factory
401 401
 auth_port = ${KEYSTONE_AUTH_PORT}
402 402
 auth_host = ${KEYSTONE_AUTH_HOST}
403 403
 auth_protocol = ${KEYSTONE_AUTH_PROTOCOL}
404
-cafile = ${KEYSTONE_SSL_CA}
404
+cafile = ${SSL_BUNDLE_FILE}
405 405
 auth_token = ${SERVICE_TOKEN}
406 406
 admin_token = ${SERVICE_TOKEN}
407 407
 
... ...
@@ -560,9 +578,9 @@ function create_swift_accounts {
560 560
             "object-store" "Swift Service")
561 561
         get_or_create_endpoint $swift_service \
562 562
             "$REGION_NAME" \
563
-            "http://$SERVICE_HOST:8080/v1/AUTH_\$(tenant_id)s" \
564
-            "http://$SERVICE_HOST:8080" \
565
-            "http://$SERVICE_HOST:8080/v1/AUTH_\$(tenant_id)s"
563
+            "$SWIFT_SERVICE_PROTOCOL://$SERVICE_HOST:8080/v1/AUTH_\$(tenant_id)s" \
564
+            "$SWIFT_SERVICE_PROTOCOL://$SERVICE_HOST:8080" \
565
+            "$SWIFT_SERVICE_PROTOCOL://$SERVICE_HOST:8080/v1/AUTH_\$(tenant_id)s"
566 566
     fi
567 567
 
568 568
     local swift_tenant_test1=$(get_or_create_project swifttenanttest1)
... ...
@@ -675,6 +693,10 @@ function start_swift {
675 675
     for type in proxy ${todo}; do
676 676
         swift-init --run-dir=${SWIFT_DATA_DIR}/run ${type} stop || true
677 677
     done
678
+    if is_service_enabled tls-proxy; then
679
+        local proxy_port=${SWIFT_DEFAULT_BIND_PORT:-8080}
680
+        start_tls_proxy '*' $proxy_port $SERVICE_HOST $SWIFT_DEFAULT_BIND_PORT_INT &
681
+    fi
678 682
     run_process s-proxy "$SWIFT_DIR/bin/swift-proxy-server ${SWIFT_CONF_DIR}/proxy-server.conf -v"
679 683
     if [[ ${SWIFT_REPLICAS} == 1 ]]; then
680 684
         for type in object container account; do
... ...
@@ -317,7 +317,7 @@ function configure_tempest {
317 317
     iniset $TEMPEST_CONFIG network-feature-disabled api_extensions ${DISABLE_NETWORK_API_EXTENSIONS}
318 318
 
319 319
     # boto
320
-    iniset $TEMPEST_CONFIG boto ec2_url "http://$SERVICE_HOST:8773/services/Cloud"
320
+    iniset $TEMPEST_CONFIG boto ec2_url "$EC2_SERVICE_PROTOCOL://$SERVICE_HOST:8773/services/Cloud"
321 321
     iniset $TEMPEST_CONFIG boto s3_url "http://$SERVICE_HOST:${S3_SERVICE_PORT:-3333}"
322 322
     iniset $TEMPEST_CONFIG boto s3_materials_path "$BOTO_MATERIALS_PATH"
323 323
     iniset $TEMPEST_CONFIG boto ari_manifest cirros-${CIRROS_VERSION}-${CIRROS_ARCH}-initrd.manifest.xml
... ...
@@ -14,6 +14,7 @@
14 14
 #
15 15
 # - configure_CA
16 16
 # - init_CA
17
+# - cleanup_CA
17 18
 
18 19
 # - configure_proxy
19 20
 # - start_tls_proxy
... ...
@@ -27,6 +28,7 @@
27 27
 # - start_tls_proxy HOST_IP 5000 localhost 5000
28 28
 # - ensure_certificates
29 29
 # - is_ssl_enabled_service
30
+# - enable_mod_ssl
30 31
 
31 32
 # Defaults
32 33
 # --------
... ...
@@ -34,14 +36,9 @@
34 34
 if is_service_enabled tls-proxy; then
35 35
     # TODO(dtroyer): revisit this below after the search for HOST_IP has been done
36 36
     TLS_IP=${TLS_IP:-$SERVICE_IP}
37
-
38
-    # Set the default ``SERVICE_PROTOCOL`` for TLS
39
-    SERVICE_PROTOCOL=https
40 37
 fi
41 38
 
42
-# Make up a hostname for cert purposes
43
-# will be added to /etc/hosts?
44
-DEVSTACK_HOSTNAME=secure.devstack.org
39
+DEVSTACK_HOSTNAME=$(hostname -f)
45 40
 DEVSTACK_CERT_NAME=devstack-cert
46 41
 DEVSTACK_CERT=$DATA_DIR/$DEVSTACK_CERT_NAME.pem
47 42
 
... ...
@@ -209,6 +206,29 @@ function init_CA {
209 209
 
210 210
     # Create the CA bundle
211 211
     cat $ROOT_CA_DIR/cacert.pem $INT_CA_DIR/cacert.pem >>$INT_CA_DIR/ca-chain.pem
212
+    cat $INT_CA_DIR/ca-chain.pem >> $SSL_BUNDLE_FILE
213
+
214
+    if is_fedora; then
215
+        sudo cp $INT_CA_DIR/ca-chain.pem /usr/share/pki/ca-trust-source/anchors/devstack-chain.pem
216
+        sudo update-ca-trust
217
+    elif is_ubuntu; then
218
+        sudo cp $INT_CA_DIR/ca-chain.pem /usr/local/share/ca-certificates/devstack-int.crt
219
+        sudo cp $ROOT_CA_DIR/cacert.pem /usr/local/share/ca-certificates/devstack-root.crt
220
+        sudo update-ca-certificates
221
+    fi
222
+}
223
+
224
+# Clean up the CA files
225
+# cleanup_CA
226
+function cleanup_CA {
227
+    if is_fedora; then
228
+        sudo rm -f /usr/share/pki/ca-trust-source/anchors/devstack-chain.pem
229
+        sudo update-ca-trust
230
+    elif is_ubuntu; then
231
+        sudo rm -f /usr/local/share/ca-certificates/devstack-int.crt
232
+        sudo rm -f /usr/local/share/ca-certificates/devstack-root.crt
233
+        sudo update-ca-certificates
234
+    fi
212 235
 }
213 236
 
214 237
 # Create an initial server cert
... ...
@@ -331,6 +351,9 @@ function make_root_CA {
331 331
 function is_ssl_enabled_service {
332 332
     local services=$@
333 333
     local service=""
334
+    if [ "$USE_SSL" == "False" ]; then
335
+        return 1
336
+    fi
334 337
     for service in ${services}; do
335 338
         [[ ,${SSL_ENABLED_SERVICES}, =~ ,${service}, ]] && return 0
336 339
     done
... ...
@@ -345,8 +368,12 @@ function is_ssl_enabled_service {
345 345
 # The function expects to find a certificate, key and CA certificate in the
346 346
 # variables {service}_SSL_CERT, {service}_SSL_KEY and {service}_SSL_CA. For
347 347
 # example for keystone this would be KEYSTONE_SSL_CERT, KEYSTONE_SSL_KEY and
348
-# KEYSTONE_SSL_CA. If it does not find these certificates the program will
349
-# quit.
348
+# KEYSTONE_SSL_CA.
349
+#
350
+# If it does not find these certificates then the devstack-issued server
351
+# certificate, key and CA certificate will be associated with the service.
352
+#
353
+# If only some of the variables are provided then the function will quit.
350 354
 function ensure_certificates {
351 355
     local service=$1
352 356
 
... ...
@@ -358,7 +385,15 @@ function ensure_certificates {
358 358
     local key=${!key_var}
359 359
     local ca=${!ca_var}
360 360
 
361
-    if [[ -z "$cert" || -z "$key" || -z "$ca" ]]; then
361
+    if [[ -z "$cert" && -z "$key" && -z "$ca" ]]; then
362
+        local cert="$INT_CA_DIR/$DEVSTACK_CERT_NAME.crt"
363
+        local key="$INT_CA_DIR/private/$DEVSTACK_CERT_NAME.key"
364
+        local ca="$INT_CA_DIR/ca-chain.pem"
365
+        eval ${service}_SSL_CERT=\$cert
366
+        eval ${service}_SSL_KEY=\$key
367
+        eval ${service}_SSL_CA=\$ca
368
+        return # the CA certificate is already in the bundle
369
+    elif [[ -z "$cert" || -z "$key" || -z "$ca" ]]; then
362 370
         die $LINENO "Missing either the ${cert_var} ${key_var} or ${ca_var}" \
363 371
                     "variable to enable SSL for ${service}"
364 372
     fi
... ...
@@ -366,6 +401,21 @@ function ensure_certificates {
366 366
     cat $ca >> $SSL_BUNDLE_FILE
367 367
 }
368 368
 
369
+# Enable the mod_ssl plugin in Apache
370
+function enable_mod_ssl {
371
+    echo "Enabling mod_ssl"
372
+
373
+    if is_ubuntu; then
374
+        sudo a2enmod ssl
375
+    elif is_fedora; then
376
+        # Fedora enables mod_ssl by default
377
+        :
378
+    fi
379
+    if ! sudo `which httpd || which apache2ctl` -M | grep -w -q ssl_module; then
380
+        die $LINENO "mod_ssl is not enabled in apache2/httpd, please check for it manually and run stack.sh again"
381
+    fi
382
+}
383
+
369 384
 
370 385
 # Proxy Functions
371 386
 # ===============
... ...
@@ -340,6 +340,15 @@ source $TOP_DIR/lib/rpc_backend
340 340
 # and the specified rpc backend is available on your platform.
341 341
 check_rpc_backend
342 342
 
343
+# Use native SSL for servers in SSL_ENABLED_SERVICES
344
+USE_SSL=$(trueorfalse False $USE_SSL)
345
+
346
+# Service to enable with SSL if USE_SSL is True
347
+SSL_ENABLED_SERVICES="key,nova,cinder,glance,s-proxy,neutron"
348
+
349
+if is_service_enabled tls-proxy && [ "$USE_SSL" == "True" ]; then
350
+    die $LINENO "tls-proxy and SSL are mutually exclusive"
351
+fi
343 352
 
344 353
 # Configure Projects
345 354
 # ==================
... ...
@@ -822,7 +831,7 @@ if is_service_enabled heat; then
822 822
     configure_heat
823 823
 fi
824 824
 
825
-if is_service_enabled tls-proxy; then
825
+if is_service_enabled tls-proxy || [ "$USE_SSL" == "True" ]; then
826 826
     configure_CA
827 827
     init_CA
828 828
     init_cert