Commit d0fc47f0 authored by Nikos Skalkotos's avatar Nikos Skalkotos

Merge branch 'develop'

parents cf5b888d f01d7e23
Copyright (C) 2011-2016 GRNET S.A. and individual contributors.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301, USA.
......@@ -20,23 +20,9 @@ Please see the [official Synnefo site](http://www.synnefo.org) and the
[latest snf-image docs](http://www.synnefo.org/docs/snf-image/latest/index.html)
for more information.
Contact Information
-------------------
Copyright and license
=====================
* User discussions: synnefo@googlegroups.com
* Development: synnefo-devel@googlegroups.com
Copyright (C) 2011-2016 GRNET S.A. and individual contributors.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
02110-1301, USA.
......@@ -39,7 +39,7 @@ master_doc = 'index'
# General information about the project.
project = u'snf-image'
copyright = u'2011, 2012, 2013, 2014 GRNET S.A. All rights reserved'
copyright = u'2011-2016 GRNET S.A. All rights reserved'
# The version info for the project you're documenting, acts as replacement for
# |version| and |release|, also used in various other places throughout the
......
......@@ -123,6 +123,20 @@ some external programs in ``/etc/default/snf-image``:
# card's NETWORK_TAGS variable.
# STATELESS_DHCPV6_TAGS="nfdhcpd stateless_dhcpv6"
# DEFAULT_NIC_CONFIG: This option defines the network configuration to be
# performed if there is a default NIC attached to the instance with no further
# information associated with it. This will happen if the user creates an
# instance and does not define any of the --net and --no-nics input arguments.
# In this case Ganeti will create a NIC with a random MAC and set up according
# to the cluster level NIC parameters. The user may want to leave this NIC
# unconfigured (by leaving this option empty), perform "dhcp" or use one of the
# various IPv6 auto configuration methods. The supported IPv6 methods are:
# "dhcpv6" (Stateful DHCPv6), "slaac_dhcp" (Stateless DHCPv6) and "slaac"
# (Stateless Autoconfiguration). IPv4 and IPv6 configuration methods can be
# defined in conjunction using the plus (`+') sign. IPv4 must precede (e.g.:
# "dhcp+slaac_dhcp").
# DEFAULT_NIC_CONFIG="dhcp"
# UNATTEND: This variable overwrites the unattend.xml file used when deploying
# a Windows image. snf-image-helper will use its own unattend.xml file if this
# variable is empty.
......@@ -167,6 +181,9 @@ The most common configuration parameters the user may need to overwrite are:
* **PROGRESS_MONITOR**: To specify an executable that will handle the
monitoring messages exported by *snf-image*
* **DHCP_TAGS**: To specify which Ganeti networks support DHCP
* **DEFAULT_NIC_CONFIG**: To specify a configuration method for the default
NIC Ganeti will attach on instances that were created without using the
*--net* or *--no-nics* input arguments.
* **STATELESS_DHCPV6_TAGS**: To specify which Ganeti networks support SLAAC
and stateless DHCPv6
* **STATEFUL_DHCPV6_TAGS**: To specify which Ganeti networks support DHCPv6
......
......@@ -15,6 +15,8 @@ following OS Parameters:
(:ref:`details <image-passwd>`)
* **img_passwd_hash** (optional): the hash of the password to be injected into
the image (:ref:`details <image-passwd-hash>`)
* **auth_keys** (optional): keys to be injected into the instance for remote
log in (:ref:`details <authorized-keys>`)
* **img_properties** (optional): additional image properties used to customize
the image (:ref:`details <image-properties>`)
* **img_personality** (optional): files to be injected into the image's file
......@@ -95,8 +97,8 @@ Image Password (img_passwd)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
The value of this parameter is the password to be injected into the image. If
this parameter is not set at all and **img_passwd_hash** is missing too, then
the *ChangePassword* task (see
this parameter is not set at all and **img_passwd_hash** and **auth_keys** are
missing too, then the *ChangePassword* task (see
:ref:`Image Configuration Tasks <image-configuration-tasks>`) will not run.
This parameter cannot be defined in conjunction with **img_passwd_hash**.
......@@ -106,12 +108,27 @@ Image Password Hash (img_passwd_hash)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The value of this parameter is the hash of the password to be injected into the
image. If this parameter is not set at all and **img_passwd** is missing too,
then the *ChangePassword* task (see
image. If this parameter is not set at all and **img_passwd** and **auth_keys**
are missing too, then the *ChangePassword* task (see
:ref:`Image Configuration Tasks <image-configuration-tasks>`) will not run.
This parameter is not applicable on Windows images and cannot be defined in
conjunction with **img_passwd**.
.. _authorized-keys:
Authorized Keys (auth_keys)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
The value of this parameter is a list of keys to be injected into the instance,
to allow password-less SSH log in. The supported format is the
*authorized_keys* file format of OpenSSH. The affected users are the ones
defined in the *USERS* image property (see
:ref:`Image Properties <image-properties>`). If this parameter is not set or is
empty and **img_passwd** and **img_passwd_hash** are missing too, then the
*ChangePassword* task (see
:ref:`Image Configuration Tasks <image-configuration-tasks>`) will not run.
This parameter is not applicable on Windows images.
.. _image-properties:
Image Properties (img_properties)
......
......@@ -29,6 +29,6 @@ files
/etc/default/snf-image
Configuration file for snf-image
/etc/defaults/snf-image-update-helper
/etc/default/snf-image-update-helper
Contains the default download URL
__version__ = "0.20.2"
__version__ = "0.21.dev0"
......@@ -1266,10 +1266,9 @@ networking_opts() {
initialize=no
finalize=no
while getopts "h?ifn:4:6:" opt; do
while getopts "hifn:4:6:" opt; do
case "$opt" in
h|\?)
echo $usage >&2
h) echo $usage >&2
exit 0
;;
i) initialize=yes
......@@ -1282,9 +1281,17 @@ networking_opts() {
;;
6) ipv6=$OPTARG
;;
\?) exit 1
;;
esac
done
shift $((OPTIND - 1))
if [ $# -ne 0 ]; then
log_error "Unknown arguments: $@" >&2
exit 1
fi
if [ -z "$index" -a "$initialize" = no -a "$finalize" = no ]; then
log_error "Either -i, -f or -n must be specified"
fi
......
......@@ -147,42 +147,75 @@ windows_password() {
done
}
unix_password() {
local flavor target password encrypted users tmp_shadow method default_method
flavor="$1"
target="$2"
password="$3"
shadow="${flavor}_shadow"
if [ ! -e "$target${!shadow}" ]; then
log_error "No ${!shadow} found!"
unix_auth() {
local flavor target password encrypted users usr tmp_shadow method home opt
local default_method keys entry keys_file keys_file_tmpl new_entry uid guid
while getopts 'f:k:m:p:t:' opt; do
case $opt in
f) flavor="$OPTARG"
;;
k) keys="$OPTARG"
;;
m) method="$OPTARG"
;;
p) password="$OPTARG"
;;
t) target="$OPTARG"
;;
*) log_error "Invalid option -$OPTARGS in unix_auth"
;;
esac
done
if [ -z "${flavor+dummy}" ]; then
log_error "unix_auth: flavor (-f) parameter needed but missing"
fi
if [ -z "${target+dummy}" ]; then
log_error "unix_auth: target (-t) parameter needed but missing"
fi
if [ -n "${password+dummy}" ]; then
shadow="${flavor}_shadow"
if [ ! -e "$target${!shadow}" ]; then
log_error "No ${!shadow} found!"
fi
case "$flavor" in
linux|freebsd)
default_method=sha512
;;
openbsd)
default_method=blowfish
;;
netbsd)
default_method=sha1
;;
*)
log_error "Unknown unix flavor: \`$flavor'"
;;
esac
method="${SNF_IMAGE_PROPERTY_PASSWD_HASHING_METHOD:-$default_method}"
if [ "$method" != "none" ]; then
echo -n "Encrypting password with \`$method' method ... "
encrypted=$("@scriptsdir@/hashpwd.py" -m "$method" "$password")
echo "done"
else
encrypted="$password"
case "$flavor" in
linux|freebsd)
default_method=sha512
;;
openbsd)
default_method=blowfish
;;
netbsd)
default_method=sha1
;;
*)
log_error "Unknown unix flavor: \`$flavor'"
;;
esac
method="${method:-$default_method}"
if [ "$method" != "none" ]; then
echo -n "Encrypting password with \`$method' method ... "
encrypted=$("@scriptsdir@/hashpwd.py" -m "$method" "$password")
echo "done"
else
encrypted="$password"
fi
fi
if [ -n "${keys}" ]; then
# Find the value of the AuthorizedKeysFile keyword if present in
# sshd_config. For more info check:
# https://www.freebsd.org/cgi/man.cgi?sshd_config(5)
keys_file_tmpl=$(cut -d'#' -f1 |
{ egrep '\<AuthorizedKeysFile' "${target}/etc/ssh/sshd_config" || true; } |
awk '{print $NF}')
keys_file_tmpl="$(printf "%q" "${keys_file_tmpl:-%h/.ssh/authorized_keys}")"
fi
users=()
declare -a users
if [ -n "$SNF_IMAGE_PROPERTY_USERS" ]; then
for usr in $SNF_IMAGE_PROPERTY_USERS; do
......@@ -190,33 +223,65 @@ unix_password() {
done
else
warn "Image property \`USERS' is missing or empty. " \
"Changing the password for default user: \`root'."
"Using default user: \`root'."
users+=("root")
fi
for i in $(seq 0 1 $((${#users[@]}-1))); do
tmp_shadow="$(mktemp)"
add_cleanup rm "$tmp_shadow"
for usr in "${users[@]}"; do
if [ -n "${password+dummy}" ]; then
echo -n "Setting ${usr} password ... "
tmp_shadow="$(mktemp)"
add_cleanup rm "$tmp_shadow"
echo -n "Setting ${users[$i]} password ... "
entry=$(grep "^${users[$i]}:" "$target${!shadow}") || true
if [ -z "$entry" ]; then
log_error "User: \`${users[$i]}' does not exist."
entry=$(grep "^${usr}:" "$target${!shadow}") || true
if [ -z "$entry" ]; then
log_error "User: \`${usr}' does not exist" \
"(not present in ${!shadow})."
fi
new_entry="$(${flavor}_change_shadow_entry "$entry" "$encrypted")"
grep -v "^${usr}:" "$target${!shadow}" > "$tmp_shadow"
echo "$new_entry" >> "$tmp_shadow"
cat "$tmp_shadow" > "$target${!shadow}"
echo "done"
fi
new_entry="$(${flavor}_change_shadow_entry "$entry" "$encrypted")"
grep -v "^${users[$i]}:" "$target${!shadow}" > "$tmp_shadow"
echo "$new_entry" >> "$tmp_shadow"
cat "$tmp_shadow" > "$target${!shadow}"
echo "done"
if [ -n "${keys+dummy}" ]; then
echo -n "Adding authorization keys for user: \`${usr}' ... "
IFS=':' read -ra entry <<<"$(grep "^${usr}:" "${target}/etc/passwd" || true)"
if [ "${entry[0]}" != "${usr}" ]; then
log_error "User: \`${usr}' does not exist" \
"(not present in /etc/passwd)"
fi
uid=${entry[2]}
guid=${entry[3]}
home=${entry[5]}
keys_file="${keys_file_tmpl//%%/\$\\'%\'}"
keys_file="${keys_file//%h/\$\{home\}}"
keys_file="${keys_file//%u/\$\{usr\}}"
eval keys_file=\"$keys_file\"
if [ -z "$keys_file" ]; then
log_error "Error while evaluating AuthorizedKeysFile: \`$keys_file'"
fi
mkdir -p "$(dirname "${target}${keys_file}")"
chown "${uid}:${guid}" "$(dirname "${target}${keys_file}")"
chmod 700 "$(dirname "${target}${keys_file}")"
echo "$keys" >> "${target}${keys_file}"
chown "${uid}:${guid}" "${target}${keys_file}"
chmod 600 "${target}${keys_file}"
echo "done"
fi
done
}
if [ -z "${SNF_IMAGE_PASSWD+dummy}" -a -z "${SNF_IMAGE_PASSWD_HASH+dummy}" ]; then
warn "Task ${PROGNAME:2} will not run. Password is not set"
exit 0
fi
#trim users var
SNF_IMAGE_PROPERTY_USERS=$(echo $SNF_IMAGE_PROPERTY_USERS)
......@@ -225,13 +290,46 @@ if [[ "$SNF_IMAGE_PROPERTY_OSFAMILY" =~ ^windows ]]; then
log_error "On Windows images password hash is not applicable."
fi
if [ -n "${SNF_IMAGE_AUTH_KEYS+dummy}" ]; then
warn "Injecting authorization keys is not supported for Windows"
fi
if [ -z "${SNF_IMAGE_PASSWD+dummy}" ]; then
warn "Task ${PROGNAME:2} will not run. Password is not set"
exit 0
fi
windows_password "$SNF_IMAGE_TARGET" "$SNF_IMAGE_PASSWD"
else
ARGS=("-f" "$SNF_IMAGE_PROPERTY_OSFAMILY" "-t" "$SNF_IMAGE_TARGET")
if [ -n "${SNF_IMAGE_PASSWD_HASH+dummy}" ]; then
SNF_IMAGE_PROPERTY_PASSWD_HASHING_METHOD=none
SNF_IMAGE_PASSWD="$SNF_IMAGE_PASSWD_HASH"
fi
unix_password "$SNF_IMAGE_PROPERTY_OSFAMILY" "$SNF_IMAGE_TARGET" "$SNF_IMAGE_PASSWD"
if [ -n "${SNF_IMAGE_PASSWD+dummy}" ]; then
ARGS+=("-p" "$SNF_IMAGE_PASSWD")
fi
if [ -n "${SNF_IMAGE_PROPERTY_PASSWD_HASHING_METHOD}" ]; then
ARGS+=("-m" "${SNF_IMAGE_PROPERTY_PASSWD_HASHING_METHOD}")
fi
if [ -n "${SNF_IMAGE_AUTH_KEYS+dummy}" ]; then
if [ -n "${SNF_IMAGE_AUTH_KEYS}" ]; then
ARGS+=("-k" "$SNF_IMAGE_AUTH_KEYS")
else
warn "Ignoring empty AUTH_KEYS parameter"
fi
fi
if [ -z "${SNF_IMAGE_PASSWD+dummy}" -a -z "${SNF_IMAGE_AUTH_KEYS}" ]; then
warn "Task: \`${PROGNAME:2} will not run. No password or key is set"
exit 0
fi
unix_auth "${ARGS[@]}"
fi
# For FreeBSD, OpenBSD and NetBSD we need to recreate the password databases
......
......@@ -112,28 +112,47 @@ for index in $(seq 0 $((SNF_IMAGE_NIC_COUNT-1))); do
ipv6=yes
fi
ARGS="-n $index"
ARGS=("-n" "$index")
if [ "$ipv4" = yes ]; then
if [ "$dhcp" = yes ]; then
ARGS+=" -4 dhcp"
ARGS+=("-4" "dhcp")
else
ARGS+=" -4 static"
ARGS+=("-4" "static")
fi
fi
if [ "$ipv6" = yes ]; then
if [ "$dhcp6" = stateful ]; then
ARGS+=" -6 dhcp"
ARGS+=("-6" "dhcp")
elif [ "$dhcp6" = stateless ]; then
ARGS+=" -6 slaac_dhcp"
ARGS+=("-6" "slaac_dhcp")
else
ARGS+=" -6 slaac"
ARGS+=("-6" "slaac")
fi
fi
echo "Running: $networking_tool $ARGS"
"$networking_tool" $ARGS
if [ $SNF_IMAGE_NIC_COUNT -eq 1 -a "$ipv4" = "no" -a "$ipv6" = "no" ]; then
# This looks like being the default NIC.
keys=(dhcp {dhcp+,}{dhcpv6,slaac,slaac_dhcp})
values=("-4 dhcp" {"-4 dhcp ",}{"-6 dhcp","-6 slaac","-6 slaac_dhcp"})
declare -A default_nic_action
for((i=0; i<${#keys[@]}; i++)); do
default_nic_action["${keys[$i]}"]="${values[$i]}"
done
warn "Detected a default NIC with no further info associated with it."
if [ -z "$SNF_IMAGE_DEFAULT_NIC_CONFIG" ]; then
warn "No configuration for default NIC is defined"
else
warn "Performing configuration for default NIC: $SNF_IMAGE_DEFAULT_NIC_CONFIG"
ARGS+=(${default_nic_action["$SNF_IMAGE_DEFAULT_NIC_CONFIG"]})
fi
fi
echo "Running: $networking_tool ${ARGS[@]}"
"$networking_tool" "${ARGS[@]}"
done
......
......@@ -137,7 +137,8 @@ get_api20_arguments() {
local osparams osp
osparams=(IMG_ID IMG_FORMAT IMG_PASSWD IMG_PASSWD_HASH IMG_PROPERTIES
IMG_PERSONALITY CONFIG_URL OS_PRODUCT_KEY OS_ANSWER_FILE)
IMG_PERSONALITY CONFIG_URL OS_PRODUCT_KEY OS_ANSWER_FILE
AUTH_KEYS)
# Store OSP_VAR in VAR
for param in "${osparams[@]}"; do
......@@ -561,6 +562,21 @@ fi
: ${DHCP_TAGS:="auto dhcp nfdhcpd"}
: ${STATEFUL_DHCPV6_TAGS:="dhcpv6 stateful_dhcpv6"}
: ${STATELESS_DHCPV6_TAGS:="nfdhcpd stateless_dhcpv6"}
: ${DEFAULT_NIC_CONFIG:="dhcp"}
found=no
for val in "" dhcp {dhcp+,}{dhcpv6,slaac,slaac_dhcp}; do
if [ "$DEFAULT_NIC_CONFIG" = "$val" ]; then
found=yes
break
fi
done
if [ "$found" = "no" ]; then
log_error "DEFAULT_NIC_CONFIG (=\`$DEFAULT_NIC_CONFIG') has invalid value."
log_error "Valid values are: \`'" dhcp {dhcp+,}{dhcpv6,slaac,slaac_dhcp}
exit 1
fi
SCRIPT_NAME=$(basename $0)
......
......@@ -185,6 +185,7 @@ snf_export_HOSTNAME="$instance"
snf_export_DHCP_TAGS="$DHCP_TAGS"
snf_export_STATEFUL_DHCPV6_TAGS="$STATEFUL_DHCPV6_TAGS"
snf_export_STATELESS_DHCPV6_TAGS="$STATELESS_DHCPV6_TAGS"
snf_export_DEFAULT_NIC_CONFIG="$DEFAULT_NIC_CONFIG"
if [ -n "${IMG_PASSWD+dummy}" ]; then
snf_export_PASSWD="$IMG_PASSWD"
......@@ -205,6 +206,10 @@ if [ -n "${OS_PRODUCT_KEY+dummy}" ]; then
snf_export_OS_PRODUCT_KEY="$OS_PRODUCT_KEY"
fi
if [ -n "${AUTH_KEYS+dummy}" ]; then
snf_export_AUTH_KEYS="$AUTH_KEYS"
fi
assign_disk_devices_to snf_export_DEV
create_floppy "$floppy"
......
......@@ -114,6 +114,20 @@
# card's NETWORK_TAGS variable.
# STATELESS_DHCPV6_TAGS="nfdhcpd stateless_dhcpv6"
# DEFAULT_NIC_CONFIG: This option defines the network configuration to be
# performed if there is a default NIC attached to the instance with no further
# information associated with it. This will happen if the user creates an
# instance and does not define any of the --net and --no-nics input arguments.
# In this case Ganeti will create a NIC with a random MAC and set up according
# to the cluster level NIC parameters. The user may want to leave this NIC
# unconfigured (by leaving this option empty), perform "dhcp" or use one of the
# various IPv6 auto configuration methods. The supported IPv6 methods are:
# "dhcpv6" (Stateful DHCPv6), "slaac_dhcp" (Stateless DHCPv6) and "slaac"
# (Stateless Autoconfiguration). IPv4 and IPv6 configuration methods can be
# defined in conjunction using the plus (`+') sign. IPv4 must precede (e.g.:
# "dhcp+slaac_dhcp").
# DEFAULT_NIC_CONFIG="dhcp"
# UNATTEND: This variable overwrites the unattend.xml file used when deploying
# a Windows image. snf-image-helper will use its own unattend.xml file if this
# variable is empty.
......
......@@ -4,6 +4,7 @@ img_passwd The password to be assigned to the user accounts
img_passwd_hash Hashed version of the password to be assigned to the user accounts (conflicts with img_passwd)
img_properties The image properties that are used to customize the image (json.dumps format)
img_personality The files to be injected into the image (base64 encoded in a json.dumps format)
auth_keys Keys to append to the users' authorized keys files for remote log in
os_product_key A product key to be used to license a Windows deployment (windows-only)
os_answer_file An answer file used by Windows to automate the setup process (windows-only)
config_url The URL to download configuration data from
......@@ -24,7 +24,7 @@ set -e
check_required() {
local required_params="IMG_ID IMG_FORMAT"
local osparams="$required_params IMG_PASSWD IMG_PROPERTIES IMG_PERSONALITY CONFIG_URL OS_PRODUCT_KEY OS_ANSWER_FILE"
local osparams="$required_params IMG_PASSWD IMG_PROPERTIES IMG_PERSONALITY CONFIG_URL OS_PRODUCT_KEY OS_ANSWER_FILE AUTH_KEYS"
local osp
source_variant
......@@ -46,6 +46,13 @@ check_required() {
fi
done
if [[ ! "${IMG_FORMAT}" =~ ^(disk|ext|ntfs)dump$ ]]; then
log_error "Invalid OS API Parameter img_format (=${IMG_FORMAT})."
log_error "Valid values are \`diskdump', \`extdump' and \`ntfsdump'"
exit 1
fi
if [ -n "${OS_PRODUCT_KEY+dummy}" ]; then
if [[ ! "${OS_PRODUCT_KEY}" =~ ^([a-zA-Z0-9]{5}-){4}[a-zA-Z0-9]{5}$ ]]; then
log_error "Invalid OS API Parameter: os_product_key."
......
m4_define([devflow_version], [0.20.2])
m4_define([devflow_version], [0.21.dev0])
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment