Merge "Fix some Markdown formatting issues"
diff --git a/.gitignore b/.gitignore
index 798b081..0c22c6b 100644
--- a/.gitignore
+++ b/.gitignore
@@ -13,3 +13,5 @@
 accrc
 .stackenv
 .prereqs
+docs/
+docs-files
diff --git a/eucarc b/eucarc
index 2b0f7dd..3502351 100644
--- a/eucarc
+++ b/eucarc
@@ -13,7 +13,7 @@
 fi
 
 # Find the other rc files
-RC_DIR=$(cd $(dirname "$BASH_SOURCE") && pwd)
+RC_DIR=$(cd $(dirname "${BASH_SOURCE:-$0}") && pwd)
 
 # Get user configuration
 source $RC_DIR/openrc
diff --git a/functions b/functions
index f4fb806..0a73b9f 100644
--- a/functions
+++ b/functions
@@ -1258,9 +1258,18 @@
     # ensure that further actions can do things like setup.py sdist
     safe_chown -R $STACK_USER $1/*.egg-info
 
-    # Undo requirements changes, if we made them
-    if [ $update_requirements -eq 0 ]; then
-        (cd $project_dir && git checkout -- requirements.txt test-requirements.txt setup.py)
+    # We've just gone and possibly modified the user's source tree in an
+    # automated way, which is considered bad form if it's a development
+    # tree because we've screwed up their next git checkin. So undo it.
+    #
+    # However... there are some circumstances, like running in the gate
+    # where we really really want the overridden version to stick. So provide
+    # a variable that tells us whether or not we should UNDO the requirements
+    # changes (this will be set to False in the OpenStack ci gate)
+    if [ $UNDO_REQUIREMENTS = "True"]; then
+        if [ $update_requirements -eq 0 ]; then
+            (cd $project_dir && git reset --hard)
+        fi
     fi
 }
 
diff --git a/lib/ceilometer b/lib/ceilometer
index 9257611..f95ed30 100644
--- a/lib/ceilometer
+++ b/lib/ceilometer
@@ -94,7 +94,7 @@
     iniset $CEILOMETER_CONF keystone_authtoken admin_tenant_name $SERVICE_TENANT_NAME
     iniset $CEILOMETER_CONF keystone_authtoken signing_dir $CEILOMETER_AUTH_CACHE_DIR
 
-    if [[ "$CEILOMETER_BACKEND" = 'mysql' ]]; then
+    if [ "$CEILOMETER_BACKEND" = 'mysql' ] || [ "$CEILOMETER_BACKEND" = 'postgresql' ] ; then
         iniset $CEILOMETER_CONF database connection `database_connection_url ceilometer`
     else
         iniset $CEILOMETER_CONF database connection mongodb://localhost:27017/ceilometer
@@ -119,7 +119,7 @@
     sudo chown $STACK_USER $CEILOMETER_AUTH_CACHE_DIR
     rm -f $CEILOMETER_AUTH_CACHE_DIR/*
 
-    if [[ "$CEILOMETER_BACKEND" = 'mysql' ]]; then
+    if [ "$CEILOMETER_BACKEND" = 'mysql' ] || [ "$CEILOMETER_BACKEND" = 'postgresql' ] ; then
         recreate_database ceilometer utf8
         $CEILOMETER_BIN_DIR/ceilometer-dbsync
     fi
@@ -141,6 +141,12 @@
     screen_it ceilometer-acentral "cd ; ceilometer-agent-central --config-file $CEILOMETER_CONF"
     screen_it ceilometer-collector "cd ; ceilometer-collector --config-file $CEILOMETER_CONF"
     screen_it ceilometer-api "cd ; ceilometer-api -d -v --log-dir=$CEILOMETER_API_LOG_DIR --config-file $CEILOMETER_CONF"
+
+    echo "Waiting for ceilometer-api to start..."
+    if ! timeout $SERVICE_TIMEOUT sh -c "while ! curl --noproxy '*' -s http://localhost:8777/v2/ >/dev/null; do sleep 1; done"; then
+        die $LINENO "ceilometer-api did not start"
+    fi
+
     screen_it ceilometer-alarm-notifier "cd ; ceilometer-alarm-notifier --config-file $CEILOMETER_CONF"
     screen_it ceilometer-alarm-evaluator "cd ; ceilometer-alarm-evaluator --config-file $CEILOMETER_CONF"
 }
diff --git a/lib/cinder b/lib/cinder
index ae0e28c..20d6e61 100644
--- a/lib/cinder
+++ b/lib/cinder
@@ -284,6 +284,11 @@
             iniset $CINDER_CONF DEFAULT xenapi_nfs_server "$CINDER_XENAPI_NFS_SERVER"
             iniset $CINDER_CONF DEFAULT xenapi_nfs_serverpath "$CINDER_XENAPI_NFS_SERVERPATH"
         )
+    elif [ "$CINDER_DRIVER" == "nfs" ]; then
+        iniset $CINDER_CONF DEFAULT volume_driver "cinder.volume.drivers.nfs.NfsDriver"
+        iniset $CINDER_CONF DEFAULT nfs_shares_config "$CINDER_CONF_DIR/nfs_shares.conf"
+        echo "$CINDER_NFS_SERVERPATH" | sudo tee "$CINDER_CONF_DIR/nfs_shares.conf"
+        sudo chmod 666 $CINDER_CONF_DIR/nfs_shares.conf
     elif [ "$CINDER_DRIVER" == "sheepdog" ]; then
         iniset $CINDER_CONF DEFAULT volume_driver "cinder.volume.drivers.sheepdog.SheepdogDriver"
     elif [ "$CINDER_DRIVER" == "glusterfs" ]; then
diff --git a/lib/ironic b/lib/ironic
index ff99e58..9f86e84 100644
--- a/lib/ironic
+++ b/lib/ironic
@@ -93,6 +93,8 @@
 # configure_ironic_api() - Is used by configure_ironic(). Performs
 # API specific configuration.
 function configure_ironic_api() {
+    iniset $IRONIC_CONF_FILE DEFAULT auth_strategy keystone
+    iniset $IRONIC_CONF_FILE DEFAULT policy_file $IRONIC_POLICY_JSON
     iniset $IRONIC_CONF_FILE keystone_authtoken auth_host $KEYSTONE_AUTH_HOST
     iniset $IRONIC_CONF_FILE keystone_authtoken auth_port $KEYSTONE_AUTH_PORT
     iniset $IRONIC_CONF_FILE keystone_authtoken auth_protocol $KEYSTONE_AUTH_PROTOCOL
diff --git a/lib/neutron b/lib/neutron
index 50bdb74..9834b59 100644
--- a/lib/neutron
+++ b/lib/neutron
@@ -110,6 +110,10 @@
 Q_USE_DEBUG_COMMAND=${Q_USE_DEBUG_COMMAND:-False}
 # The name of the default q-l3 router
 Q_ROUTER_NAME=${Q_ROUTER_NAME:-router1}
+# nova vif driver that all plugins should use
+NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtGenericVIFDriver"}
+
+
 # List of config file names in addition to the main plugin config file
 # See _configure_neutron_common() for details about setting it up
 declare -a Q_PLUGIN_EXTRA_CONF_FILES
diff --git a/lib/neutron_plugins/bigswitch_floodlight b/lib/neutron_plugins/bigswitch_floodlight
index 2450731..93ec497 100644
--- a/lib/neutron_plugins/bigswitch_floodlight
+++ b/lib/neutron_plugins/bigswitch_floodlight
@@ -9,7 +9,7 @@
 source $TOP_DIR/lib/neutron_thirdparty/bigswitch_floodlight     # for third party service specific configuration values
 
 function neutron_plugin_create_nova_conf() {
-    NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtGenericVIFDriver"}
+    :
 }
 
 function neutron_plugin_install_agent_packages() {
diff --git a/lib/neutron_plugins/linuxbridge_agent b/lib/neutron_plugins/linuxbridge_agent
index 88c49c5..85e8c08 100644
--- a/lib/neutron_plugins/linuxbridge_agent
+++ b/lib/neutron_plugins/linuxbridge_agent
@@ -11,7 +11,7 @@
 }
 
 function neutron_plugin_create_nova_conf() {
-    NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtGenericVIFDriver"}
+    :
 }
 
 function neutron_plugin_install_agent_packages() {
diff --git a/lib/neutron_plugins/nicira b/lib/neutron_plugins/nicira
index 7c99b69..87d3c3d 100644
--- a/lib/neutron_plugins/nicira
+++ b/lib/neutron_plugins/nicira
@@ -26,7 +26,6 @@
 }
 
 function neutron_plugin_create_nova_conf() {
-    NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtOpenVswitchDriver"}
     # if n-cpu is enabled, then setup integration bridge
     if is_service_enabled n-cpu; then
         setup_integration_bridge
diff --git a/lib/neutron_plugins/ovs_base b/lib/neutron_plugins/ovs_base
index 1214f3b..89db29d 100644
--- a/lib/neutron_plugins/ovs_base
+++ b/lib/neutron_plugins/ovs_base
@@ -73,7 +73,7 @@
 }
 
 function _neutron_ovs_base_configure_nova_vif_driver() {
-    NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtGenericVIFDriver"}
+    :
 }
 
 # Restore xtrace
diff --git a/lib/neutron_plugins/plumgrid b/lib/neutron_plugins/plumgrid
index 9d3c92f..d4050bb 100644
--- a/lib/neutron_plugins/plumgrid
+++ b/lib/neutron_plugins/plumgrid
@@ -9,8 +9,7 @@
 #source $TOP_DIR/lib/neutron_plugins/ovs_base
 
 function neutron_plugin_create_nova_conf() {
-
-    NOVA_VIF_DRIVER=${NOVA_VIF_DRIVER:-"nova.virt.libvirt.vif.LibvirtGenericVIFDriver"}
+    :
 }
 
 function neutron_plugin_setup_interface_driver() {
diff --git a/lib/nova b/lib/nova
index 98b32ea..e9fbd56 100644
--- a/lib/nova
+++ b/lib/nova
@@ -614,21 +614,25 @@
 
 # start_nova_compute() - Start the compute process
 function start_nova_compute() {
-    NOVA_CONF_BOTTOM=$NOVA_CONF
+    if is_service_enabled n-cell; then
+        local compute_cell_conf=$NOVA_CELLS_CONF
+    else
+        local compute_cell_conf=$NOVA_CONF
+    fi
 
     if [[ "$VIRT_DRIVER" = 'libvirt' ]]; then
         # The group **$LIBVIRT_GROUP** is added to the current user in this script.
         # Use 'sg' to execute nova-compute as a member of the **$LIBVIRT_GROUP** group.
-        screen_it n-cpu "cd $NOVA_DIR && sg $LIBVIRT_GROUP '$NOVA_BIN_DIR/nova-compute --config-file $NOVA_CONF_BOTTOM'"
+        screen_it n-cpu "cd $NOVA_DIR && sg $LIBVIRT_GROUP '$NOVA_BIN_DIR/nova-compute --config-file $compute_cell_conf'"
     elif [[ "$VIRT_DRIVER" = 'fake' ]]; then
         for i in `seq 1 $NUMBER_FAKE_NOVA_COMPUTE`; do
-            screen_it n-cpu "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-compute --config-file $NOVA_CONF_BOTTOM"
+            screen_it n-cpu "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-compute --config-file $compute_cell_conf"
         done
     else
         if is_service_enabled n-cpu && [[ -r $NOVA_PLUGINS/hypervisor-$VIRT_DRIVER ]]; then
             start_nova_hypervisor
         fi
-        screen_it n-cpu "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-compute --config-file $NOVA_CONF_BOTTOM"
+        screen_it n-cpu "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-compute --config-file $compute_cell_conf"
     fi
 }
 
diff --git a/lib/nova_plugins/hypervisor-docker b/lib/nova_plugins/hypervisor-docker
index 300522f..655c2df 100644
--- a/lib/nova_plugins/hypervisor-docker
+++ b/lib/nova_plugins/hypervisor-docker
@@ -26,7 +26,6 @@
 
 # Set up default directories
 DOCKER_DIR=$DEST/docker
-DOCKER_REPO=${DOCKER_REPO:-https://github.com/dotcloud/openstack-docker.git}
 DOCKER_BRANCH=${DOCKER_BRANCH:-master}
 
 DOCKER_UNIX_SOCKET=/var/run/docker.sock
@@ -56,10 +55,6 @@
 
 # configure_nova_hypervisor - Set config files, create data dirs, etc
 function configure_nova_hypervisor() {
-    git_clone $DOCKER_REPO $DOCKER_DIR $DOCKER_BRANCH
-
-    ln -snf ${DOCKER_DIR}/nova-driver $NOVA_DIR/nova/virt/docker
-
     iniset $NOVA_CONF DEFAULT compute_driver docker.DockerDriver
     iniset $GLANCE_API_CONF DEFAULT container_formats ami,ari,aki,bare,ovf,docker
 
diff --git a/lib/stackforge b/lib/stackforge
new file mode 100644
index 0000000..4b79de0
--- /dev/null
+++ b/lib/stackforge
@@ -0,0 +1,67 @@
+# lib/stackforge
+#
+# Functions to install stackforge libraries that we depend on so
+# that we can try their git versions during devstack gate.
+#
+# This is appropriate for python libraries that release to pypi and are
+# expected to be used beyond OpenStack like, but are requirements
+# for core services in global-requirements.
+#    * wsme
+#    * pecan
+#
+# This is not appropriate for stackforge projects which are early stage
+# OpenStack tools
+
+# Dependencies:
+# ``functions`` file
+
+# ``stack.sh`` calls the entry points in this order:
+#
+# install_stackforge
+
+# Save trace setting
+XTRACE=$(set +o | grep xtrace)
+set +o xtrace
+
+
+# Defaults
+# --------
+WSME_DIR=$DEST/wsme
+PECAN_DIR=$DEST/pecan
+
+# Entry Points
+# ------------
+
+# install_stackforge() - Collect source and prepare
+function install_stackforge() {
+    # TODO(sdague): remove this once we get to Icehouse, this just makes
+    # for a smoother transition of existing users.
+    cleanup_stackforge
+
+    git_clone $WSME_REPO $WSME_DIR $WSME_BRANCH
+    setup_develop $WSME_DIR
+
+    git_clone $PECAN_REPO $PECAN_DIR $PECAN_BRANCH
+    setup_develop $PECAN_DIR
+}
+
+# cleanup_stackforge() - purge possibly old versions of stackforge libraries
+function cleanup_stackforge() {
+    # this means we've got an old version installed, lets get rid of it
+    # otherwise python hates itself
+    for lib in wsme pecan; do
+        if ! python -c "import $lib" 2>/dev/null; then
+            echo "Found old $lib... removing to ensure consistency"
+            local PIP_CMD=$(get_pip_command)
+            pip_install $lib
+            sudo $PIP_CMD uninstall -y $lib
+        fi
+    done
+}
+
+# Restore xtrace
+$XTRACE
+
+# Local variables:
+# mode: shell-script
+# End:
diff --git a/lib/swift b/lib/swift
index db6ae18..b46537f 100644
--- a/lib/swift
+++ b/lib/swift
@@ -74,6 +74,10 @@
 # the end of the pipeline.
 SWIFT_EXTRAS_MIDDLEWARE_LAST=${SWIFT_EXTRAS_MIDDLEWARE_LAST}
 
+# Set ``SWIFT_EXTRAS_MIDDLEWARE_NO_AUTH`` to extras middlewares that need to be at
+# the beginning of the pipeline, before authentication middlewares.
+SWIFT_EXTRAS_MIDDLEWARE_NO_AUTH=${SWIFT_EXTRAS_MIDDLEWARE_NO_AUTH:-crossdomain}
+
 # The ring uses a configurable number of bits from a path’s MD5 hash as
 # a partition index that designates a device. The number of bits kept
 # from the hash is known as the partition power, and 2 to the partition
@@ -212,7 +216,7 @@
 
 # configure_swift() - Set config files, create data dirs and loop image
 function configure_swift() {
-    local swift_pipeline=" "
+    local swift_pipeline="${SWIFT_EXTRAS_MIDDLEWARE_NO_AUTH}"
     local node_number
     local swift_node_config
     local swift_log_dir
@@ -273,7 +277,7 @@
     # tempauth would be prefixed with the reseller_prefix setting `TEMPAUTH_` the
     # token for keystoneauth would have the standard reseller_prefix `AUTH_`
     if is_service_enabled swift3;then
-        swift_pipeline=" swift3 s3token "
+        swift_pipeline+=" swift3 s3token "
     fi
     swift_pipeline+=" authtoken keystoneauth tempauth "
     sed -i "/^pipeline/ { s/tempauth/${swift_pipeline} ${SWIFT_EXTRAS_MIDDLEWARE}/ ;}" ${SWIFT_CONFIG_PROXY_SERVER}
@@ -285,6 +289,9 @@
     iniuncomment ${SWIFT_CONFIG_PROXY_SERVER} filter:tempauth reseller_prefix
     iniset ${SWIFT_CONFIG_PROXY_SERVER} filter:tempauth reseller_prefix "TEMPAUTH"
 
+    # Configure Crossdomain
+    iniset ${SWIFT_CONFIG_PROXY_SERVER} filter:crossdomain use "egg:swift#crossdomain"
+
     # Configure Keystone
     sed -i '/^# \[filter:authtoken\]/,/^# \[filter:keystoneauth\]$/ s/^#[ \t]*//' ${SWIFT_CONFIG_PROXY_SERVER}
     iniset ${SWIFT_CONFIG_PROXY_SERVER} filter:authtoken auth_host $KEYSTONE_AUTH_HOST
diff --git a/lib/tempest b/lib/tempest
index 25814b6..a50b25e 100644
--- a/lib/tempest
+++ b/lib/tempest
@@ -300,7 +300,7 @@
     iniset $TEMPEST_CONF cli cli_dir $NOVA_BIN_DIR
 
     # service_available
-    for service in nova cinder glance neutron swift heat horizon ; do
+    for service in nova cinder glance neutron swift heat horizon ceilometer; do
         if is_service_enabled $service ; then
             iniset $TEMPEST_CONF service_available $service "True"
         else
diff --git a/openrc b/openrc
index 3de7e39..5344d24 100644
--- a/openrc
+++ b/openrc
@@ -18,7 +18,7 @@
 fi
 
 # Find the other rc files
-RC_DIR=$(cd $(dirname "$BASH_SOURCE") && pwd)
+RC_DIR=$(cd $(dirname "${BASH_SOURCE:-$0}") && pwd)
 
 # Import common functions
 source $RC_DIR/functions
diff --git a/stack.sh b/stack.sh
index 5813a8a..36312ea 100755
--- a/stack.sh
+++ b/stack.sh
@@ -131,7 +131,7 @@
 
 # Warn users who aren't on an explicitly supported distro, but allow them to
 # override check and attempt installation with ``FORCE=yes ./stack``
-if [[ ! ${DISTRO} =~ (oneiric|precise|quantal|raring|saucy|7.0|wheezy|sid|testing|jessie|f16|f17|f18|f19|opensuse-12.2|rhel6) ]]; then
+if [[ ! ${DISTRO} =~ (oneiric|precise|quantal|raring|saucy|trusty|7.0|wheezy|sid|testing|jessie|f16|f17|f18|f19|opensuse-12.2|rhel6) ]]; then
     echo "WARNING: this script has not been tested on $DISTRO"
     if [[ "$FORCE" != "yes" ]]; then
         die $LINENO "If you wish to run this script anyway run with FORCE=yes"
@@ -299,6 +299,7 @@
 source $TOP_DIR/lib/tls
 source $TOP_DIR/lib/infra
 source $TOP_DIR/lib/oslo
+source $TOP_DIR/lib/stackforge
 source $TOP_DIR/lib/horizon
 source $TOP_DIR/lib/keystone
 source $TOP_DIR/lib/glance
@@ -629,6 +630,11 @@
 # Install oslo libraries that have graduated
 install_oslo
 
+# Install stackforge libraries for testing
+if is_service_enabled stackforge_libs; then
+    install_stackforge
+fi
+
 # Install clients libraries
 install_keystoneclient
 install_glanceclient
diff --git a/stackrc b/stackrc
index 0151672..6adb676 100644
--- a/stackrc
+++ b/stackrc
@@ -1,7 +1,7 @@
 # stackrc
 #
 # Find the other rc files
-RC_DIR=$(cd $(dirname "$BASH_SOURCE") && pwd)
+RC_DIR=$(cd $(dirname "${BASH_SOURCE:-$0}") && pwd)
 
 # Destination path for installation
 DEST=/opt/stack
@@ -197,6 +197,16 @@
 TROVECLIENT_REPO=${TROVECLIENT_REPO:-${GIT_BASE}/openstack/python-troveclient.git}
 TROVECLIENT_BRANCH=${TROVECLIENT_BRANCH:-master}
 
+# stackforge libraries that are used by OpenStack core services
+# wsme
+WSME_REPO=${WSME_REPO:-${GIT_BASE}/stackforge/wsme.git}
+WSME_BRANCH=${WSME_BRANCH:-master}
+
+# pecan
+PECAN_REPO=${PECAN_REPO:-${GIT_BASE}/stackforge/pecan.git}
+PECAN_BRANCH=${PECAN_BRANCH:-master}
+
+
 # Nova hypervisor configuration.  We default to libvirt with **kvm** but will
 # drop back to **qemu** if we are unable to load the kvm module.  ``stack.sh`` can
 # also install an **LXC**, **OpenVZ** or **XenAPI** based system.  If xenserver-core
@@ -297,6 +307,9 @@
 # Do not install packages tagged with 'testonly' by default
 INSTALL_TESTONLY_PACKAGES=${INSTALL_TESTONLY_PACKAGES:-False}
 
+# Undo requirements changes by global requirements
+UNDO_REQUIREMENTS=${UNDO_REQUIREMENTS:-True}
+
 # Local variables:
 # mode: shell-script
 # End:
diff --git a/tools/xen/install_os_domU.sh b/tools/xen/install_os_domU.sh
index 9a2f5a8..33dc26f 100755
--- a/tools/xen/install_os_domU.sh
+++ b/tools/xen/install_os_domU.sh
@@ -271,6 +271,12 @@
 # Max out VCPU count for better performance
 max_vcpus "$GUEST_NAME"
 
+# Wipe out all network cards
+destroy_all_vifs_of "$GUEST_NAME"
+
+# Add only one interface to prepare the guest template
+add_interface "$GUEST_NAME" "$MGT_BRIDGE_OR_NET_NAME" "0"
+
 # start the VM to run the prepare steps
 xe vm-start vm="$GUEST_NAME"