Merge "Add XAPI config to quantum rootwrap for XS/XCP."
diff --git a/README.md b/README.md
index 6570a14..1987db8 100644
--- a/README.md
+++ b/README.md
@@ -153,3 +153,23 @@
     MYSQL_HOST=$SERVICE_HOST
     RABBIT_HOST=$SERVICE_HOST
     Q_HOST=$SERVICE_HOST
+
+# Cells
+
+Cells is a new scaling option with a full spec at http://wiki.openstack.org/blueprint-nova-compute-cells.
+
+To setup a cells environment add the following to your `localrc`:
+
+    enable_service n-cell
+    enable_service n-api-meta
+    MULTI_HOST=True
+
+    # The following have not been tested with cells, they may or may not work.
+    disable_service n-obj
+    disable_service cinder
+    disable_service c-sch
+    disable_service c-api
+    disable_service c-vol
+    disable_service n-xvnc
+
+Be aware that there are some features currently missing in cells, one notable one being security groups.
diff --git a/exercises/quantum-adv-test.sh b/exercises/quantum-adv-test.sh
index fbb1b77..34f4f62 100755
--- a/exercises/quantum-adv-test.sh
+++ b/exercises/quantum-adv-test.sh
@@ -43,13 +43,12 @@
 # Import configuration
 source $TOP_DIR/openrc
 
-# If quantum is not enabled we exit with exitcode 55 which mean
-# exercise is skipped.
-is_service_enabled quantum && is_service_enabled q-agt && is_service_enabled q-dhcp || exit 55
-
-# Import quantum fucntions
+# Import quantum functions
 source $TOP_DIR/lib/quantum
 
+# If quantum is not enabled we exit with exitcode 55, which means exercise is skipped.
+quantum_plugin_check_adv_test_requirements || exit 55
+
 # Import exercise configuration
 source $TOP_DIR/exerciserc
 
diff --git a/files/apts/n-cpu b/files/apts/n-cpu
index ef281ca..88e0144 100644
--- a/files/apts/n-cpu
+++ b/files/apts/n-cpu
@@ -2,7 +2,7 @@
 nbd-client
 lvm2
 open-iscsi
-open-iscsi-utils
+open-iscsi-utils # Deprecated since quantal dist:lucid,oneiric,precise
 genisoimage
 sysfsutils
 sg3-utils
diff --git a/files/apts/nova b/files/apts/nova
index f4615c4..298e25f 100644
--- a/files/apts/nova
+++ b/files/apts/nova
@@ -2,8 +2,7 @@
 dnsmasq-utils # for dhcp_release only available in dist:oneiric,precise,quantal
 kpartx
 parted
-arping # only available in dist:natty
-iputils-arping # only available in dist:oneiric
+iputils-arping
 mysql-server # NOPRIME
 python-mysqldb
 python-xattr # needed for glance which is needed for nova --- this shouldn't be here
diff --git a/files/rpms/nova b/files/rpms/nova
index 328e7d6..c74f396 100644
--- a/files/rpms/nova
+++ b/files/rpms/nova
@@ -40,7 +40,7 @@
 python-suds
 python-tempita
 rabbitmq-server # NOPRIME
-qpid-cpp-server-daemon # NOPRIME
+qpid-cpp-server # NOPRIME
 sqlite
 sudo
 vconfig
diff --git a/files/rpms/quantum b/files/rpms/quantum
index 450e39c..32c6f62 100644
--- a/files/rpms/quantum
+++ b/files/rpms/quantum
@@ -18,8 +18,7 @@
 python-sqlalchemy
 python-suds
 rabbitmq-server # NOPRIME
-qpid-cpp-server-daemon # NOPRIME dist:f16,f17,f18
-qpid-cpp-server        # NOPRIME dist:rhel6
+qpid-cpp-server        # NOPRIME
 sqlite
 sudo
 vconfig
diff --git a/functions b/functions
index 02c2b3a..669fa69 100644
--- a/functions
+++ b/functions
@@ -380,6 +380,12 @@
             os_VENDOR=""
         done
         os_PACKAGE="rpm"
+    # If lsb_release is not installed, we should be able to detect Debian OS
+    elif [[ -f /etc/debian_version ]] && [[ $(cat /proc/version) =~ "Debian" ]]; then
+        os_VENDOR="Debian"
+        os_PACKAGE="deb"
+        os_CODENAME=$(awk '/VERSION=/' /etc/os-release | sed 's/VERSION=//' | sed -r 's/\"|\(|\)//g' | awk '{print $2}')
+        os_RELEASE=$(awk '/VERSION_ID=/' /etc/os-release | sed 's/VERSION_ID=//' | sed 's/\"//g')
     fi
     export os_VENDOR os_RELEASE os_UPDATE os_PACKAGE os_CODENAME
 }
@@ -425,8 +431,8 @@
 # Sets ``DISTRO`` from the ``os_*`` values
 function GetDistro() {
     GetOSVersion
-    if [[ "$os_VENDOR" =~ (Ubuntu) ]]; then
-        # 'Everyone' refers to Ubuntu releases by the code name adjective
+    if [[ "$os_VENDOR" =~ (Ubuntu) || "$os_VENDOR" =~ (Debian) ]]; then
+        # 'Everyone' refers to Ubuntu / Debian releases by the code name adjective
         DISTRO=$os_CODENAME
     elif [[ "$os_VENDOR" =~ (Fedora) ]]; then
         # For Fedora, just use 'f' and the release
@@ -459,11 +465,9 @@
     if [[ -z "$os_PACKAGE" ]]; then
         GetOSVersion
     fi
-
     [ "$os_PACKAGE" = "deb" ]
 }
 
-
 # Determine if current distribution is a Fedora-based distribution
 # (Fedora, RHEL, CentOS).
 # is_fedora
@@ -1411,6 +1415,35 @@
     fi
 }
 
+# Path permissions sanity check
+# check_path_perm_sanity path
+function check_path_perm_sanity() {
+    # Ensure no element of the path has 0700 permissions, which is very
+    # likely to cause issues for daemons.  Inspired by default 0700
+    # homedir permissions on RHEL and common practice of making DEST in
+    # the stack user's homedir.
+
+    local real_path=$(readlink -f $1)
+    local rebuilt_path=""
+    for i in $(echo ${real_path} | tr "/" " "); do
+        rebuilt_path=$rebuilt_path"/"$i
+
+        if [[ $(stat -c '%a' ${rebuilt_path}) = 700 ]]; then
+            echo "*** DEST path element"
+            echo "***    ${rebuilt_path}"
+            echo "*** appears to have 0700 permissions."
+            echo "*** This is very likely to cause fatal issues for devstack daemons."
+
+            if [[ -n "$SKIP_PATH_SANITY" ]]; then
+                return
+            else
+                echo "*** Set SKIP_PATH_SANITY to skip this check"
+                die $LINENO "Invalid path permissions"
+            fi
+        fi
+    done
+}
+
 # Restore xtrace
 $XTRACE
 
diff --git a/lib/baremetal b/lib/baremetal
index 8658c3a..bed3c09 100644
--- a/lib/baremetal
+++ b/lib/baremetal
@@ -204,7 +204,7 @@
     sudo mkdir -p /tftpboot
     sudo mkdir -p /tftpboot/pxelinux.cfg
     sudo cp /usr/lib/syslinux/pxelinux.0 /tftpboot/
-    sudo chown -R $STACK_USER:libvirtd /tftpboot
+    sudo chown -R $STACK_USER:$LIBVIRT_GROUP /tftpboot
 
     # ensure $NOVA_STATE_PATH/baremetal is prepared
     sudo mkdir -p $NOVA_STATE_PATH/baremetal
diff --git a/lib/ceilometer b/lib/ceilometer
index 6b110cb..90a1884 100644
--- a/lib/ceilometer
+++ b/lib/ceilometer
@@ -1,8 +1,8 @@
 # lib/ceilometer
 # Install and start **Ceilometer** service
 
-# To enable, add the following to localrc
-# ENABLED_SERVICES+=ceilometer-acompute,ceilometer-acentral,ceilometer-collector,ceilometer-api
+# To enable Ceilometer services, add the following to localrc
+# enable_service ceilometer-acompute ceilometer-acentral ceilometer-collector ceilometer-api
 
 # Dependencies:
 # - functions
@@ -70,7 +70,7 @@
 
     iniset_rpc_backend ceilometer $CEILOMETER_CONF DEFAULT
 
-    iniset $CEILOMETER_CONF DEFAULT notification_topics 'notifications,glance_notifications'
+    iniset $CEILOMETER_CONF DEFAULT notification_topics 'notifications'
     iniset $CEILOMETER_CONF DEFAULT verbose True
 
     # Install the policy file for the API server
@@ -125,7 +125,7 @@
 
 # start_ceilometer() - Start running processes, including screen
 function start_ceilometer() {
-    screen_it ceilometer-acompute "cd $CEILOMETER_DIR && sg libvirtd \"$CEILOMETER_BIN_DIR/ceilometer-agent-compute --config-file $CEILOMETER_CONF\""
+    screen_it ceilometer-acompute "cd $CEILOMETER_DIR && sg $LIBVIRT_GROUP \"$CEILOMETER_BIN_DIR/ceilometer-agent-compute --config-file $CEILOMETER_CONF\""
     screen_it ceilometer-acentral "cd $CEILOMETER_DIR && $CEILOMETER_BIN_DIR/ceilometer-agent-central --config-file $CEILOMETER_CONF"
     screen_it ceilometer-collector "cd $CEILOMETER_DIR && $CEILOMETER_BIN_DIR/ceilometer-collector --config-file $CEILOMETER_CONF"
     screen_it ceilometer-api "cd $CEILOMETER_DIR && $CEILOMETER_BIN_DIR/ceilometer-api -d -v --log-dir=$CEILOMETER_API_LOG_DIR --config-file $CEILOMETER_CONF"
diff --git a/lib/databases/mysql b/lib/databases/mysql
index 056aec4..211d797 100644
--- a/lib/databases/mysql
+++ b/lib/databases/mysql
@@ -36,8 +36,8 @@
 function recreate_database_mysql {
     local db=$1
     local charset=$2
-    mysql -u$DATABASE_USER -p$DATABASE_PASSWORD -e "DROP DATABASE IF EXISTS $db;"
-    mysql -u$DATABASE_USER -p$DATABASE_PASSWORD -e "CREATE DATABASE $db CHARACTER SET $charset;"
+    mysql -u$DATABASE_USER -p$DATABASE_PASSWORD -h$MYSQL_HOST -e "DROP DATABASE IF EXISTS $db;"
+    mysql -u$DATABASE_USER -p$DATABASE_PASSWORD -h$MYSQL_HOST -e "CREATE DATABASE $db CHARACTER SET $charset;"
 }
 
 function configure_database_mysql {
diff --git a/lib/heat b/lib/heat
index cd0a204..0c95ebb 100644
--- a/lib/heat
+++ b/lib/heat
@@ -159,7 +159,6 @@
     recreate_database heat utf8
 
     $HEAT_DIR/bin/heat-db-setup $os_PACKAGE -r $DATABASE_PASSWORD
-    $HEAT_DIR/tools/nova_create_flavors.sh
     create_heat_cache_dir
 }
 
diff --git a/lib/horizon b/lib/horizon
index 3d8b3e6..1ee530e 100644
--- a/lib/horizon
+++ b/lib/horizon
@@ -38,6 +38,18 @@
 APACHE_USER=${APACHE_USER:-$USER}
 APACHE_GROUP=${APACHE_GROUP:-$(id -gn $APACHE_USER)}
 
+# Set up service name and configuration path
+if is_ubuntu; then
+    APACHE_NAME=apache2
+    APACHE_CONF=sites-available/horizon
+elif is_fedora; then
+    APACHE_NAME=httpd
+    APACHE_CONF=conf.d/horizon.conf
+elif is_suse; then
+    APACHE_NAME=apache2
+    APACHE_CONF=vhosts.d/horizon.conf
+fi
+
 
 # Functions
 # ---------
@@ -135,8 +147,6 @@
 
     HORIZON_REQUIRE=''
     if is_ubuntu; then
-        APACHE_NAME=apache2
-        APACHE_CONF=sites-available/horizon
         # Clean up the old config name
         sudo rm -f /etc/apache2/sites-enabled/000-default
         # Be a good citizen and use the distro tools here
@@ -145,9 +155,6 @@
         # WSGI isn't enabled by default, enable it
         sudo a2enmod wsgi
     elif is_fedora; then
-        APACHE_NAME=httpd
-        APACHE_CONF=conf.d/horizon.conf
-
         if [[ "$os_RELEASE" -ge "18" ]]; then
             # fedora 18 has Require all denied  in its httpd.conf
             # and requires explicit Require all granted
@@ -155,14 +162,16 @@
         fi
         sudo sed '/^Listen/s/^.*$/Listen 0.0.0.0:80/' -i /etc/httpd/conf/httpd.conf
     elif is_suse; then
-        APACHE_NAME=apache2
-        APACHE_CONF=vhosts.d/horizon.conf
         # WSGI isn't enabled by default, enable it
         sudo a2enmod wsgi
     else
         exit_distro_not_supported "apache configuration"
     fi
 
+    # Remove old log files that could mess with how devstack detects whether Horizon
+    # has been successfully started (see start_horizon() and functions::screen_it())
+    sudo rm -f /var/log/$APACHE_NAME/horizon_*
+
     # Configure apache to run horizon
     sudo sh -c "sed -e \"
         s,%USER%,$APACHE_USER,g;
@@ -219,12 +228,8 @@
 
 # stop_horizon() - Stop running processes (non-screen)
 function stop_horizon() {
-    if is_ubuntu; then
-        stop_service apache2
-    elif is_fedora; then
-        stop_service httpd
-    elif is_suse; then
-        stop_service apache2
+    if [ -n "$APACHE_NAME" ]; then
+        stop_service $APACHE_NAME
     else
         exit_distro_not_supported "apache configuration"
     fi
diff --git a/lib/nova b/lib/nova
index f28094e..6fc0c79 100644
--- a/lib/nova
+++ b/lib/nova
@@ -37,6 +37,9 @@
 
 NOVA_CONF_DIR=/etc/nova
 NOVA_CONF=$NOVA_CONF_DIR/nova.conf
+NOVA_CELLS_CONF=$NOVA_CONF_DIR/nova-cells.conf
+NOVA_CELLS_DB=${NOVA_CELLS_DB:-nova_cell}
+
 NOVA_API_PASTE_INI=${NOVA_API_PASTE_INI:-$NOVA_CONF_DIR/api-paste.ini}
 
 # Public facing bits
@@ -125,10 +128,6 @@
 # Functions
 # ---------
 
-function add_nova_opt {
-    echo "$1" >>$NOVA_CONF
-}
-
 # Helper to clean iptables rules
 function clean_iptables() {
     # Delete rules
@@ -297,15 +296,15 @@
 
 
         if is_fedora || is_suse; then
-            if is_fedora && [[ "$os_RELEASE" -le "17" ]]; then
-                sudo bash -c 'cat <<EOF >/etc/polkit-1/localauthority/50-local.d/50-libvirt-remote-access.pkla
+            if is_fedora && [[  $DISTRO =~ (rhel6) || "$os_RELEASE" -le "17" ]]; then
+                sudo bash -c "cat <<EOF >/etc/polkit-1/localauthority/50-local.d/50-libvirt-remote-access.pkla
 [libvirt Management Access]
-Identity=unix-group:libvirtd
+Identity=unix-group:$LIBVIRT_GROUP
 Action=org.libvirt.unix.manage
 ResultAny=yes
 ResultInactive=yes
 ResultActive=yes
-EOF'
+EOF"
             elif is_suse && [[ $os_RELEASE = 12.2 || "$os_VENDOR" = "SUSE LINUX" ]]; then
                 # openSUSE < 12.3 or SLE
                 # Work around the fact that polkit-default-privs overrules pklas
@@ -338,10 +337,10 @@
 
         # The user that nova runs as needs to be member of **libvirtd** group otherwise
         # nova-compute will be unable to use libvirt.
-        if ! getent group libvirtd >/dev/null; then
-            sudo groupadd libvirtd
+        if ! getent group $LIBVIRT_GROUP >/dev/null; then
+            sudo groupadd $LIBVIRT_GROUP
         fi
-        add_user_to_group $STACK_USER libvirtd
+        add_user_to_group $STACK_USER $LIBVIRT_GROUP
 
         # libvirt detects various settings on startup, as we potentially changed
         # the system configuration (modules, filesystems), we need to restart
@@ -415,7 +414,6 @@
 
     # (Re)create ``nova.conf``
     rm -f $NOVA_CONF
-    add_nova_opt "[DEFAULT]"
     iniset $NOVA_CONF DEFAULT verbose "True"
     iniset $NOVA_CONF DEFAULT debug "True"
     iniset $NOVA_CONF DEFAULT auth_strategy "keystone"
@@ -539,6 +537,32 @@
     iniset $NOVA_CONF DEFAULT glance_api_servers "$GLANCE_HOSTPORT"
 }
 
+function init_nova_cells() {
+    if is_service_enabled n-cell; then
+        cp $NOVA_CONF $NOVA_CELLS_CONF
+        iniset $NOVA_CELLS_CONF DEFAULT sql_connection `database_connection_url $NOVA_CELLS_DB`
+        iniset $NOVA_CELLS_CONF DEFAULT rabbit_virtual_host child_cell
+        iniset $NOVA_CELLS_CONF DEFAULT dhcpbridge_flagfile $NOVA_CELLS_CONF
+        iniset $NOVA_CELLS_CONF cells enable True
+        iniset $NOVA_CELLS_CONF cells name child
+
+        iniset $NOVA_CONF DEFAULT scheduler_topic cells
+        iniset $NOVA_CONF DEFAULT compute_api_class nova.compute.cells_api.ComputeCellsAPI
+        iniset $NOVA_CONF cells enable True
+        iniset $NOVA_CONF cells name region
+
+        if is_service_enabled n-api-meta; then
+            NOVA_ENABLED_APIS=$(echo $NOVA_ENABLED_APIS | sed "s/,metadata//")
+            iniset $NOVA_CONF DEFAULT enabled_apis $NOVA_ENABLED_APIS
+            iniset $NOVA_CELLS_CONF DEFAULT enabled_apis metadata
+        fi
+
+        $NOVA_BIN_DIR/nova-manage --config-file $NOVA_CELLS_CONF db sync
+        $NOVA_BIN_DIR/nova-manage --config-file $NOVA_CELLS_CONF cell create --name=region --cell_type=parent --username=guest --hostname=$RABBIT_HOST --port=5672 --password=$RABBIT_PASSWORD --virtual_host=/ --woffset=0 --wscale=1
+        $NOVA_BIN_DIR/nova-manage cell create --name=child --cell_type=child --username=guest --hostname=$RABBIT_HOST --port=5672 --password=$RABBIT_PASSWORD --virtual_host=child_cell --woffset=0 --wscale=1
+    fi
+}
+
 # create_nova_cache_dir() - Part of the init_nova() process
 function create_nova_cache_dir() {
     # Create cache dir
@@ -578,6 +602,10 @@
         # Migrate nova database
         $NOVA_BIN_DIR/nova-manage db sync
 
+        if is_service_enabled n-cell; then
+            recreate_database $NOVA_CELLS_DB latin1
+        fi
+
         # (Re)create nova baremetal database
         if is_baremetal; then
             recreate_database nova_bm latin1
@@ -648,14 +676,26 @@
 
 # start_nova() - Start running processes, including screen
 function start_nova() {
-    # The group **libvirtd** is added to the current user in this script.
-    # Use 'sg' to execute nova-compute as a member of the **libvirtd** group.
+    NOVA_CONF_BOTTOM=$NOVA_CONF
+
     # ``screen_it`` checks ``is_service_enabled``, it is not needed here
     screen_it n-cond "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-conductor"
-    screen_it n-cpu "cd $NOVA_DIR && sg libvirtd $NOVA_BIN_DIR/nova-compute"
+
+    if is_service_enabled n-cell; then
+        NOVA_CONF_BOTTOM=$NOVA_CELLS_CONF
+        screen_it n-cond "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-conductor --config-file $NOVA_CELLS_CONF"
+        screen_it n-cell "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-cells --config-file $NOVA_CONF"
+        screen_it n-cell "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-cells --config-file $NOVA_CELLS_CONF"
+    fi
+
+    # 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-crt "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-cert"
-    screen_it n-net "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-network"
-    screen_it n-sch "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-scheduler"
+    screen_it n-net "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-network --config-file $NOVA_CONF_BOTTOM"
+    screen_it n-sch "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-scheduler --config-file $NOVA_CONF_BOTTOM"
+    screen_it n-api-meta "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-api-metadata --config-file $NOVA_CONF_BOTTOM"
+
     screen_it n-novnc "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-novncproxy --config-file $NOVA_CONF --web $NOVNC_DIR"
     screen_it n-xvnc "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-xvpvncproxy --config-file $NOVA_CONF"
     screen_it n-spice "cd $NOVA_DIR && $NOVA_BIN_DIR/nova-spicehtml5proxy --config-file $NOVA_CONF --web $SPICE_DIR"
@@ -670,7 +710,9 @@
 # stop_nova() - Stop running processes (non-screen)
 function stop_nova() {
     # Kill the nova screen windows
-    for serv in n-api n-cpu n-crt n-net n-sch n-novnc n-xvnc n-cauth n-cond n-spice; do
+    # Some services are listed here twice since more than one instance
+    # of a service may be running in certain configs.
+    for serv in n-api n-cpu n-crt n-net n-sch n-novnc n-xvnc n-cauth n-spice n-cond n-cond n-cell n-cell n-api-meta; do
         screen -S $SCREEN_NAME -p $serv -X kill
     done
 }
diff --git a/lib/quantum b/lib/quantum
index 96ccf20..dfd73e9 100644
--- a/lib/quantum
+++ b/lib/quantum
@@ -82,6 +82,8 @@
 Q_AUTH_STRATEGY=${Q_AUTH_STRATEGY:-keystone}
 # Use namespace or not
 Q_USE_NAMESPACE=${Q_USE_NAMESPACE:-True}
+# RHEL's support for namespaces requires using veths with ovs
+Q_OVS_USE_VETH=${Q_OVS_USE_VETH:-False}
 Q_USE_ROOTWRAP=${Q_USE_ROOTWRAP:-True}
 # Meta data IP
 Q_META_DATA_IP=${Q_META_DATA_IP:-$HOST_IP}
@@ -395,6 +397,10 @@
         pid=$(ps aux | awk '/[d]nsmasq.+interface=(tap|ns-)/ { print $2 }')
         [ ! -z "$pid" ] && sudo kill -9 $pid
     fi
+    if is_service_enabled q-meta; then
+        pid=$(ps aux | awk '/quantum-ns-metadata-proxy/ { print $2 }')
+        [ ! -z "$pid" ] && sudo kill -9 $pid
+    fi
 }
 
 # cleanup_quantum() - Remove residual data files, anything left over from previous
@@ -665,6 +671,11 @@
 }
 
 function _quantum_setup_interface_driver() {
+
+    # ovs_use_veth needs to be set before the plugin configuration
+    # occurs to allow plugins to override the setting.
+    iniset $1 DEFAULT ovs_use_veth $Q_OVS_USE_VETH
+
     quantum_plugin_setup_interface_driver $1
 }
 
diff --git a/lib/quantum_plugins/README.md b/lib/quantum_plugins/README.md
index 05bfb85..e829940 100644
--- a/lib/quantum_plugins/README.md
+++ b/lib/quantum_plugins/README.md
@@ -34,3 +34,5 @@
 * ``quantum_plugin_setup_interface_driver``
 * ``has_quantum_plugin_security_group``:
   return 0 if the plugin support quantum security group otherwise return 1
+* ``quantum_plugin_check_adv_test_requirements``:
+  return 0 if requirements are satisfied otherwise return 1
diff --git a/lib/quantum_plugins/bigswitch_floodlight b/lib/quantum_plugins/bigswitch_floodlight
index 4857f49..edee0eb 100644
--- a/lib/quantum_plugins/bigswitch_floodlight
+++ b/lib/quantum_plugins/bigswitch_floodlight
@@ -56,5 +56,9 @@
     return 1
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/brocade b/lib/quantum_plugins/brocade
index 6e26ad7..fc86deb 100644
--- a/lib/quantum_plugins/brocade
+++ b/lib/quantum_plugins/brocade
@@ -50,5 +50,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $BRCD_XTRACE
diff --git a/lib/quantum_plugins/linuxbridge b/lib/quantum_plugins/linuxbridge
index 324e255..b4b52e9 100644
--- a/lib/quantum_plugins/linuxbridge
+++ b/lib/quantum_plugins/linuxbridge
@@ -86,5 +86,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/nec b/lib/quantum_plugins/nec
index f61f50b..4a2a497 100644
--- a/lib/quantum_plugins/nec
+++ b/lib/quantum_plugins/nec
@@ -118,5 +118,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/nicira b/lib/quantum_plugins/nicira
index 6eefb02..305c3bf 100644
--- a/lib/quantum_plugins/nicira
+++ b/lib/quantum_plugins/nicira
@@ -146,5 +146,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/openvswitch b/lib/quantum_plugins/openvswitch
index f8512cf..dda9e61 100644
--- a/lib/quantum_plugins/openvswitch
+++ b/lib/quantum_plugins/openvswitch
@@ -147,5 +147,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/plumgrid b/lib/quantum_plugins/plumgrid
index 912aa7e..1456710 100644
--- a/lib/quantum_plugins/plumgrid
+++ b/lib/quantum_plugins/plumgrid
@@ -35,5 +35,8 @@
     :
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/ryu b/lib/quantum_plugins/ryu
index 1139232..1b039dc 100644
--- a/lib/quantum_plugins/ryu
+++ b/lib/quantum_plugins/ryu
@@ -71,5 +71,9 @@
     return 0
 }
 
+function quantum_plugin_check_adv_test_requirements() {
+    is_service_enabled q-agt && is_service_enabled q-dhcp && return 0
+}
+
 # Restore xtrace
 $MY_XTRACE
diff --git a/lib/quantum_plugins/services/agent_loadbalancer b/lib/quantum_plugins/services/agent_loadbalancer
index b6528b0..ee3faa5 100644
--- a/lib/quantum_plugins/services/agent_loadbalancer
+++ b/lib/quantum_plugins/services/agent_loadbalancer
@@ -34,6 +34,11 @@
 
     cp $QUANTUM_DIR/etc/lbaas_agent.ini $LBAAS_AGENT_CONF_FILENAME
 
+    iniset $LBAAS_AGENT_CONF_FILENAME DEFAULT use_namespaces $Q_USE_NAMESPACE
+    # ovs_use_veth needs to be set before the plugin configuration
+    # occurs to allow plugins to override the setting.
+    iniset $LBAAS_AGENT_CONF_FILENAME DEFAULT ovs_use_veth $Q_OVS_USE_VETH
+
     quantum_plugin_setup_interface_driver $LBAAS_AGENT_CONF_FILENAME
 
     if is_fedora; then
diff --git a/lib/rpc_backend b/lib/rpc_backend
index 3c485e4..fc439ec 100644
--- a/lib/rpc_backend
+++ b/lib/rpc_backend
@@ -30,7 +30,7 @@
     # that can be passed as arguments to is_service_enabled.
     # We check for a call to iniset_rpc_backend in these files, meaning
     # the service needs a backend.
-    rpc_candidates=$(grep -rl iniset_rpc_backend . | awk -F/ '{print $NF}')
+    rpc_candidates=$(grep -rl iniset_rpc_backend $TOP_DIR/lib/ | awk -F/ '{print $NF}')
     for c in ${rpc_candidates}; do
         if is_service_enabled $c; then
             rpc_needed=0
@@ -70,11 +70,7 @@
         fi
     elif is_service_enabled qpid; then
         if is_fedora; then
-            if [[ $DISTRO =~ (rhel6) ]]; then
-                uninstall_package qpid-cpp-server
-            else
-                uninstall_package qpid-cpp-server-daemon
-            fi
+            uninstall_package qpid-cpp-server
         elif is_ubuntu; then
             uninstall_package qpidd
         else
@@ -104,15 +100,12 @@
         rm -f "$tfile"
     elif is_service_enabled qpid; then
         if is_fedora; then
+            install_package qpid-cpp-server
             if [[ $DISTRO =~ (rhel6) ]]; then
-                install_package qpid-cpp-server
-
                # RHEL6 leaves "auth=yes" in /etc/qpidd.conf, it needs to
                # be no or you get GSS authentication errors as it
                # attempts to default to this.
                 sudo sed -i.bak 's/^auth=yes$/auth=no/' /etc/qpidd.conf
-            else
-                install_package qpid-cpp-server-daemon
             fi
         elif is_ubuntu; then
             install_package qpidd
@@ -145,6 +138,13 @@
         fi
         # change the rabbit password since the default is "guest"
         sudo rabbitmqctl change_password guest $RABBIT_PASSWORD
+        if is_service_enabled n-cell; then
+            # Add partitioned access for the child cell
+            if [ -z `sudo rabbitmqctl list_vhosts | grep child_cell` ]; then
+                sudo rabbitmqctl add_vhost child_cell
+                sudo rabbitmqctl set_permissions -p child_cell guest ".*" ".*" ".*"
+            fi
+        fi
     elif is_service_enabled qpid; then
         echo_summary "Starting qpid"
         restart_service qpidd
diff --git a/stack.sh b/stack.sh
index d43c948..7ec25cf 100755
--- a/stack.sh
+++ b/stack.sh
@@ -32,6 +32,15 @@
 # and ``DISTRO``
 GetDistro
 
+# Some dependencies are not available in Debian Wheezy official
+# repositories. However, it's possible to run OpenStack from gplhost
+# repository.
+if [[ "$os_VENDOR" =~ (Debian) ]]; then
+    echo 'deb http://archive.gplhost.com/debian grizzly main' | sudo tee /etc/apt/sources.list.d/gplhost_wheezy-backports.list
+    echo 'deb http://archive.gplhost.com/debian grizzly-backports main' | sudo tee -a /etc/apt/sources.list.d/gplhost_wheezy-backports.list
+    apt_get update
+    apt_get install --force-yes gplhost-archive-keyring
+fi
 
 # Global Settings
 # ===============
@@ -105,7 +114,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|f16|f17|f18|opensuse-12.2|rhel6) ]]; then
+if [[ ! ${DISTRO} =~ (oneiric|precise|quantal|raring|saucy|7.0|wheezy|sid|testing|jessie|f16|f17|f18|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"
@@ -199,6 +208,9 @@
 sudo mkdir -p $DEST
 sudo chown -R $STACK_USER $DEST
 
+# a basic test for $DEST path permissions (fatal on error unless skipped)
+check_path_perm_sanity ${DEST}
+
 # Set ``OFFLINE`` to ``True`` to configure ``stack.sh`` to run cleanly without
 # Internet access. ``stack.sh`` must have been previously run with Internet
 # access to install prerequisites and fetch repositories.
@@ -273,6 +285,7 @@
 
 # Set the destination directories for OpenStack projects
 OPENSTACKCLIENT_DIR=$DEST/python-openstackclient
+PBR_DIR=$DEST/pbr
 
 
 # Interactive Configuration
@@ -550,6 +563,10 @@
 # ============================
 
 if [[ is_fedora && $DISTRO =~ (rhel6) ]]; then
+    # Avoid having to configure selinux to allow things like httpd to
+    # access horizion files or run binaries like nodejs (LP#1175444)
+    sudo setenforce 0
+
     # An old version (2.0.1) of python-crypto is probably installed on
     # a fresh system, via the dependency chain
     # cas->python-paramiko->python-crypto (related to anaconda).
@@ -579,6 +596,17 @@
     # Nova stopping later on complaining that
     # '/var/lib/dbus/machine-id' doesn't exist.
     sudo service messagebus restart
+
+    # In setup.py, a "setup_requires" package is supposed to
+    # transient.  However there is a bug with rhel6 distribute where
+    # setup_requires packages can register entry points that aren't
+    # cleared out properly after the setup-phase; the end result is
+    # installation failures (bz#924038).  Thus we pre-install the
+    # problem package here; this way the setup_requires dependency is
+    # already satisfied and it will not need to be installed
+    # transiently, meaning we avoid the issue of it not being cleaned
+    # out properly.  Note we do this before the track-depends below.
+    pip_install hgtools
 fi
 
 TRACK_DEPENDS=${TRACK_DEPENDS:-False}
@@ -599,6 +627,10 @@
 
 echo_summary "Installing OpenStack project source"
 
+# Install pbr
+git_clone $PBR_REPO $PBR_DIR $PBR_BRANCH
+setup_develop $PBR_DIR
+
 # Install clients libraries
 install_keystoneclient
 install_glanceclient
@@ -1004,6 +1036,8 @@
         LIBVIRT_FIREWALL_DRIVER=${LIBVIRT_FIREWALL_DRIVER:-"nova.virt.libvirt.firewall.IptablesFirewallDriver"}
         iniset $NOVA_CONF DEFAULT firewall_driver "$LIBVIRT_FIREWALL_DRIVER"
     fi
+
+    init_nova_cells
 fi
 
 # Extra things to prepare nova for baremetal, before nova starts
@@ -1064,14 +1098,19 @@
     create_quantum_initial_network
     setup_quantum_debug
 elif is_service_enabled $DATABASE_BACKENDS && is_service_enabled n-net; then
+    NM_CONF=${NOVA_CONF}
+    if is_service_enabled n-cell; then
+        NM_CONF=${NOVA_CELLS_CONF}
+    fi
+
     # Create a small network
-    $NOVA_BIN_DIR/nova-manage network create "$PRIVATE_NETWORK_NAME" $FIXED_RANGE 1 $FIXED_NETWORK_SIZE $NETWORK_CREATE_ARGS
+    $NOVA_BIN_DIR/nova-manage --config-file $NM_CONF network create "$PRIVATE_NETWORK_NAME" $FIXED_RANGE 1 $FIXED_NETWORK_SIZE $NETWORK_CREATE_ARGS
 
     # Create some floating ips
-    $NOVA_BIN_DIR/nova-manage floating create $FLOATING_RANGE --pool=$PUBLIC_NETWORK_NAME
+    $NOVA_BIN_DIR/nova-manage --config-file $NM_CONF floating create $FLOATING_RANGE --pool=$PUBLIC_NETWORK_NAME
 
     # Create a second pool
-    $NOVA_BIN_DIR/nova-manage floating create --ip_range=$TEST_FLOATING_RANGE --pool=$TEST_FLOATING_POOL
+    $NOVA_BIN_DIR/nova-manage --config-file $NM_CONF floating create --ip_range=$TEST_FLOATING_RANGE --pool=$TEST_FLOATING_POOL
 fi
 
 if is_service_enabled quantum; then
diff --git a/stackrc b/stackrc
index 6dcb462..871c8a1 100644
--- a/stackrc
+++ b/stackrc
@@ -157,11 +157,21 @@
 BM_POSEUR_REPO=${BM_POSEUR_REPO:-${GIT_BASE}/tripleo/bm_poseur.git}
 BM_POSEUR_BRANCH=${BM_POSEUR_BRANCH:-master}
 
+# pbr
+# Used to drive the setuptools configs
+PBR_REPO=${PBR_REPO:-${GIT_BASE}/openstack-dev/pbr.git}
+PBR_BRANCH=${PBR_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** or **OpenVZ** based system.
 VIRT_DRIVER=${VIRT_DRIVER:-libvirt}
 LIBVIRT_TYPE=${LIBVIRT_TYPE:-kvm}
+if [[ "$os_VENDOR" =~ (Debian) ]]; then
+  LIBVIRT_GROUP=libvirt
+else
+  LIBVIRT_GROUP=libvirtd
+fi
 
 # Specify a comma-separated list of UEC images to download and install into glance.
 # supported urls here are:
diff --git a/tools/xen/README.md b/tools/xen/README.md
index 3fadc78..258d7a3 100644
--- a/tools/xen/README.md
+++ b/tools/xen/README.md
@@ -1,5 +1,4 @@
-Getting Started With XenServer 5.6 and Devstack
-===============================================
+# Getting Started With XenServer 5.6 and Devstack
 The purpose of the code in this directory it to help developers bootstrap
 a XenServer 5.6 (or greater) + Openstack development environment.  This file gives
 some pointers on how to get started.
@@ -9,8 +8,7 @@
 machine on the Xenserver host (called OS domU). The VM uses the XAPI toolstack
 to communicate with the host.
 
-Step 1: Install Xenserver
-------------------------
+## Step 1: Install Xenserver
 Install XenServer 5.6+ on a clean box. You can get XenServer by signing
 up for an account on citrix.com, and then visiting:
 https://www.citrix.com/English/ss/downloads/details.asp?downloadId=2311504&productId=683148
@@ -25,16 +23,14 @@
 * XenServer Gateway: 192.168.1.1
 * XenServer DNS: 192.168.1.1
 
-Step 2: Download devstack
---------------------------
+## Step 2: Download devstack
 On your XenServer host, run the following commands as root:
 
     wget --no-check-certificate https://github.com/openstack-dev/devstack/zipball/master
     unzip -o master -d ./devstack
     cd devstack/*/
 
-Step 3: Configure your localrc inside the devstack directory
-------------------------------------------------------------
+## Step 3: Configure your localrc inside the devstack directory
 Devstack uses a localrc for user-specific configuration.  Note that
 the XENAPI_PASSWORD must be your dom0 root password.
 Of course, use real passwords if this machine is exposed.
@@ -43,12 +39,18 @@
     MYSQL_PASSWORD=my_super_secret
     SERVICE_TOKEN=my_super_secret
     ADMIN_PASSWORD=my_super_secret
-    SERVICE_PASSWORD=$ADMIN_PASSWORD
+    SERVICE_PASSWORD=my_super_secret
     RABBIT_PASSWORD=my_super_secret
-    # This is the password for your guest (for both stack and root users)
+    SWIFT_HASH="66a3d6b56c1f479c8b4e70ab5c2000f5"
+    # This is the password for the OpenStack VM (for both stack and root users)
     GUEST_PASSWORD=my_super_secret
+
+    # XenAPI parameters
     # IMPORTANT: The following must be set to your dom0 root password!
-    XENAPI_PASSWORD=my_super_secret
+    XENAPI_PASSWORD=my_xenserver_root_password
+    XENAPI_CONNECTION_URL="http://address_of_your_xenserver"
+    VNCSERVER_PROXYCLIENT_ADDRESS=address_of_your_xenserver
+
     # Do not download the usual images yet!
     IMAGE_URLS=""
     # Explicitly set virt driver here
@@ -60,34 +62,32 @@
     # Host Interface, i.e. the interface on the nova vm you want to expose the
     # services on. Usually eth2 (management network) or eth3 (public network) and
     # not eth0 (private network with XenServer host) or eth1 (VM traffic network)
-    # This is also used as the interface for the Ubuntu install
     # The default is eth3.
     # HOST_IP_IFACE=eth3
+
+    # Settings for netinstalling Ubuntu
+    # UBUNTU_INST_RELEASE=precise
+
     # First time Ubuntu network install params
-    NETINSTALLIP="dhcp"
-    NAMESERVERS=""
-    NETMASK=""
-    GATEWAY=""
+    # UBUNTU_INST_IFACE="eth3"
+    # UBUNTU_INST_IP="dhcp"
     EOF
 
-Step 4: Run ./install_os_domU.sh from the tools/xen directory
--------------------------------------------------------------
-cd tools/xen
-./install_os_domU.sh
+## Step 4: Run `./install_os_domU.sh` from the `tools/xen` directory
 
-Once this script finishes executing, log into the VM (openstack domU)
-that it installed and tail the run.sh.log file. You will need to wait
-until it run.sh has finished executing.
+    cd tools/xen
+    ./install_os_domU.sh
 
+Once this script finishes executing, log into the VM (openstack domU) that it
+installed and tail the run.sh.log file. You will need to wait until it run.sh
+has finished executing.
 
-Step 5: Do cloudy stuff!
---------------------------
+## Step 5: Do cloudy stuff!
 * Play with horizon
 * Play with the CLI
 * Log bugs to devstack and core projects, and submit fixes!
 
-Step 6: Run from snapshot
--------------------------
+## Step 6: Run from snapshot
 If you want to quicky re-run devstack from a clean state,
 using the same settings you used in your previous run,
-you can revert the DomU to the snapshot called "before_first_boot"
+you can revert the DomU to the snapshot called `before_first_boot`
diff --git a/tools/xen/install_os_domU.sh b/tools/xen/install_os_domU.sh
index 7c3b839..0e194fe 100755
--- a/tools/xen/install_os_domU.sh
+++ b/tools/xen/install_os_domU.sh
@@ -1,15 +1,13 @@
 #!/bin/bash
 
-# This script is a level script
-# It must be run on a XenServer or XCP machine
+# This script must be run on a XenServer or XCP machine
 #
 # It creates a DomU VM that runs OpenStack services
 #
 # For more details see: README.md
 
-# Exit on errors
 set -o errexit
-# Echo commands
+set -o nounset
 set -o xtrace
 
 # Abort if localrc is not set
@@ -31,13 +29,12 @@
 # xapi functions
 . $THIS_DIR/functions
 
-
 #
 # Get Settings
 #
 
 # Source params - override xenrc params in your localrc to suit your taste
-source xenrc
+source $THIS_DIR/xenrc
 
 xe_min()
 {
@@ -253,11 +250,12 @@
             mkdir -p $HTTP_SERVER_LOCATION
         fi
         cp -f $THIS_DIR/devstackubuntupreseed.cfg $HTTP_SERVER_LOCATION
-        MIRROR=${MIRROR:-""}
-        if [ -n "$MIRROR" ]; then
-            sed -e "s,d-i mirror/http/hostname string .*,d-i mirror/http/hostname string $MIRROR," \
-                -i "${HTTP_SERVER_LOCATION}/devstackubuntupreseed.cfg"
-        fi
+
+        sed \
+            -e "s,\(d-i mirror/http/hostname string\).*,\1 $UBUNTU_INST_HTTP_HOSTNAME,g" \
+            -e "s,\(d-i mirror/http/directory string\).*,\1 $UBUNTU_INST_HTTP_DIRECTORY,g" \
+            -e "s,\(d-i mirror/http/proxy string\).*,\1 $UBUNTU_INST_HTTP_PROXY,g" \
+            -i "${HTTP_SERVER_LOCATION}/devstackubuntupreseed.cfg"
     fi
 
     # Update the template
diff --git a/tools/xen/prepare_guest.sh b/tools/xen/prepare_guest.sh
index fe52445..0e11226 100755
--- a/tools/xen/prepare_guest.sh
+++ b/tools/xen/prepare_guest.sh
@@ -10,54 +10,51 @@
 # creating the user called "stack",
 # and shuts down the VM to signal the script has completed
 
-set -x
-# Echo commands
+set -o errexit
+set -o nounset
 set -o xtrace
 
 # Configurable nuggets
-GUEST_PASSWORD=${GUEST_PASSWORD:-secrete}
-STAGING_DIR=${STAGING_DIR:-stage}
-DO_TGZ=${DO_TGZ:-1}
-XS_TOOLS_PATH=${XS_TOOLS_PATH:-"/root/xs-tools.deb"}
-STACK_USER=${STACK_USER:-stack}
+GUEST_PASSWORD="$1"
+XS_TOOLS_PATH="$2"
+STACK_USER="$3"
 
 # Install basics
-chroot $STAGING_DIR apt-get update
-chroot $STAGING_DIR apt-get install -y cracklib-runtime curl wget ssh openssh-server tcpdump ethtool
-chroot $STAGING_DIR apt-get install -y curl wget ssh openssh-server python-pip git vim-nox sudo
-chroot $STAGING_DIR pip install xenapi
+apt-get update
+apt-get install -y cracklib-runtime curl wget ssh openssh-server tcpdump ethtool
+apt-get install -y curl wget ssh openssh-server python-pip git vim-nox sudo
+pip install xenapi
 
 # Install XenServer guest utilities
-cp $XS_TOOLS_PATH ${STAGING_DIR}${XS_TOOLS_PATH}
-chroot $STAGING_DIR dpkg -i $XS_TOOLS_PATH
-chroot $STAGING_DIR update-rc.d -f xe-linux-distribution remove
-chroot $STAGING_DIR update-rc.d xe-linux-distribution defaults
+dpkg -i $XS_TOOLS_PATH
+update-rc.d -f xe-linux-distribution remove
+update-rc.d xe-linux-distribution defaults
 
 # Make a small cracklib dictionary, so that passwd still works, but we don't
 # have the big dictionary.
-mkdir -p $STAGING_DIR/usr/share/cracklib
-echo a | chroot $STAGING_DIR cracklib-packer
+mkdir -p /usr/share/cracklib
+echo a | cracklib-packer
 
 # Make /etc/shadow, and set the root password
-chroot $STAGING_DIR "pwconv"
-echo "root:$GUEST_PASSWORD" | chroot $STAGING_DIR chpasswd
+pwconv
+echo "root:$GUEST_PASSWORD" | chpasswd
 
 # Put the VPX into UTC.
-rm -f $STAGING_DIR/etc/localtime
+rm -f /etc/localtime
 
 # Add stack user
-chroot $STAGING_DIR groupadd libvirtd
-chroot $STAGING_DIR useradd $STACK_USER -s /bin/bash -d /opt/stack -G libvirtd
-echo $STACK_USER:$GUEST_PASSWORD | chroot $STAGING_DIR chpasswd
-echo "$STACK_USER ALL=(ALL) NOPASSWD: ALL" >> $STAGING_DIR/etc/sudoers
+groupadd libvirtd
+useradd $STACK_USER -s /bin/bash -d /opt/stack -G libvirtd
+echo $STACK_USER:$GUEST_PASSWORD | chpasswd
+echo "$STACK_USER ALL=(ALL) NOPASSWD: ALL" >> /etc/sudoers
 
 # Give ownership of /opt/stack to stack user
-chroot $STAGING_DIR chown -R $STACK_USER /opt/stack
+chown -R $STACK_USER /opt/stack
 
 # Make our ip address hostnames look nice at the command prompt
-echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> $STAGING_DIR/opt/stack/.bashrc
-echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> $STAGING_DIR/root/.bashrc
-echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> $STAGING_DIR/etc/profile
+echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> /opt/stack/.bashrc
+echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> /root/.bashrc
+echo "export PS1='${debian_chroot:+($debian_chroot)}\\u@\\H:\\w\\$ '" >> /etc/profile
 
 function setup_vimrc {
     if [ ! -e $1 ]; then
@@ -72,20 +69,15 @@
 }
 
 # Setup simple .vimrcs
-setup_vimrc $STAGING_DIR/root/.vimrc
-setup_vimrc $STAGING_DIR/opt/stack/.vimrc
-
-if [ "$DO_TGZ" = "1" ]; then
-    # Compress
-    rm -f stage.tgz
-    tar cfz stage.tgz stage
-fi
+setup_vimrc /root/.vimrc
+setup_vimrc /opt/stack/.vimrc
 
 # remove self from local.rc
 # so this script is not run again
 rm -rf /etc/rc.local
-mv /etc/rc.local.preparebackup /etc/rc.local
-cp $STAGING_DIR/etc/rc.local $STAGING_DIR/etc/rc.local.backup
+
+# Restore rc.local file
+cp /etc/rc.local.preparebackup /etc/rc.local
 
 # shutdown to notify we are done
 shutdown -h now
diff --git a/tools/xen/prepare_guest_template.sh b/tools/xen/prepare_guest_template.sh
index 19bd2f8..6ea6f63 100755
--- a/tools/xen/prepare_guest_template.sh
+++ b/tools/xen/prepare_guest_template.sh
@@ -15,9 +15,8 @@
 # The resultant image is started by install_os_domU.sh,
 # and once the VM has shutdown, build_xva.sh is run
 
-# Exit on errors
 set -o errexit
-# Echo commands
+set -o nounset
 set -o xtrace
 
 # This directory
@@ -75,7 +74,8 @@
 
 # run prepare_guest.sh on boot
 cat <<EOF >$STAGING_DIR/etc/rc.local
-GUEST_PASSWORD=$GUEST_PASSWORD STAGING_DIR=/ \
-    DO_TGZ=0 XS_TOOLS_PATH=$XS_TOOLS_PATH \
-    bash /opt/stack/prepare_guest.sh > /opt/stack/prepare_guest.log 2>&1
+#!/bin/sh -e
+bash /opt/stack/prepare_guest.sh \\
+    "$GUEST_PASSWORD" "$XS_TOOLS_PATH" "$STACK_USER" \\
+    > /opt/stack/prepare_guest.log 2>&1
 EOF
diff --git a/tools/xen/scripts/install_ubuntu_template.sh b/tools/xen/scripts/install_ubuntu_template.sh
index 43b6dec..b7a8eff 100755
--- a/tools/xen/scripts/install_ubuntu_template.sh
+++ b/tools/xen/scripts/install_ubuntu_template.sh
@@ -7,9 +7,8 @@
 # Based on a script by: David Markey <david.markey@citrix.com>
 #
 
-# Exit on errors
 set -o errexit
-# Echo commands
+set -o nounset
 set -o xtrace
 
 # This directory
@@ -54,11 +53,11 @@
 pvargs="-- quiet console=hvc0 partman/default_filesystem=ext3 \
 console-setup/ask_detect=false locale=${UBUNTU_INST_LOCALE} \
 keyboard-configuration/layoutcode=${UBUNTU_INST_KEYBOARD} \
-netcfg/choose_interface=${HOST_IP_IFACE} \
+netcfg/choose_interface=${UBUNTU_INST_IFACE} \
 netcfg/get_hostname=os netcfg/get_domain=os auto \
 url=${preseed_url}"
 
-if [ "$NETINSTALLIP" != "dhcp" ]; then
+if [ "$UBUNTU_INST_IP" != "dhcp" ]; then
     netcfgargs="netcfg/disable_autoconfig=true \
 netcfg/get_nameservers=${UBUNTU_INST_NAMESERVERS} \
 netcfg/get_ipaddress=${UBUNTU_INST_IP} \
@@ -70,11 +69,16 @@
 
 xe template-param-set uuid=$new_uuid \
     other-config:install-methods=http \
-    other-config:install-repository="$UBUNTU_INST_REPOSITORY" \
+    other-config:install-repository="http://${UBUNTU_INST_HTTP_HOSTNAME}${UBUNTU_INST_HTTP_DIRECTORY}" \
     PV-args="$pvargs" \
     other-config:debian-release="$UBUNTU_INST_RELEASE" \
     other-config:default_template=true \
     other-config:disks='<provision><disk device="0" size="'$disk_size'" sr="" bootable="true" type="system"/></provision>' \
     other-config:install-arch="$UBUNTU_INST_ARCH"
 
+if ! [ -z "$UBUNTU_INST_HTTP_PROXY" ]; then
+    xe template-param-set uuid=$new_uuid \
+        other-config:install-proxy="$UBUNTU_INST_HTTP_PROXY"
+fi
+
 echo "Ubuntu template installed uuid:$new_uuid"
diff --git a/tools/xen/xenrc b/tools/xen/xenrc
index e4d8ac9..e50f954 100644
--- a/tools/xen/xenrc
+++ b/tools/xen/xenrc
@@ -8,6 +8,9 @@
 # Name of this guest
 GUEST_NAME=${GUEST_NAME:-DevStackOSDomU}
 
+# Template cleanup
+CLEAN_TEMPLATES=${CLEAN_TEMPLATES:-false}
+
 # Size of image
 VDI_MB=${VDI_MB:-5000}
 OSDOMU_MEM_MB=1024
@@ -19,7 +22,6 @@
 # Host Interface, i.e. the interface on the nova vm you want to expose the
 # services on. Usually eth2 (management network) or eth3 (public network) and
 # not eth0 (private network with XenServer host) or eth1 (VM traffic network)
-# This is also used as the interface for the Ubuntu install
 HOST_IP_IFACE=${HOST_IP_IFACE:-eth3}
 
 #
@@ -62,15 +64,16 @@
 # XenServer 6.1 and later or XCP 1.6 or later
 # 11.10 is only really supported with XenServer 6.0.2 and later
 UBUNTU_INST_ARCH="amd64"
-UBUNTU_INST_REPOSITORY="http://archive.ubuntu.net/ubuntu"
+UBUNTU_INST_HTTP_HOSTNAME="archive.ubuntu.net"
+UBUNTU_INST_HTTP_DIRECTORY="/ubuntu"
+UBUNTU_INST_HTTP_PROXY=""
 UBUNTU_INST_LOCALE="en_US"
 UBUNTU_INST_KEYBOARD="us"
-# network configuration for HOST_IP_IFACE during install
+# network configuration for ubuntu netinstall
+UBUNTU_INST_IFACE="eth3"
 UBUNTU_INST_IP="dhcp"
 UBUNTU_INST_NAMESERVERS=""
 UBUNTU_INST_NETMASK=""
 UBUNTU_INST_GATEWAY=""
 
-# Load stackrc defaults
-# then override with settings from localrc
-cd ../.. && source ./stackrc && cd $TOP_DIR
+source ../../stackrc