summaryrefslogtreecommitdiff
path: root/start-container-docker.sh
blob: dd6099519022075a724c5203b18f021423f435e1 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
#!/bin/bash
set -e

# Start a local docker instance with the requested arch and distro

# This script is meant to be executed from Jenkins jobs inside TCWG
# lab. It prints shell commands meant to be executed in the parent
# shell, consisting in:
# - a cleanup statement, to remove the container on exit for instance
# - definition of ${CONTAINER}, used to prefix commands that you want
#   to run inside the container.
# - definition of ${session_host} and ${session_port}, can be used for
#   a remote connexion to the container

usage() {
    echo "Usage: $0 --arch container-arch --distro flavour [--session-host host] [--session-name name] [--task {build|test}]"
    echo
    echo "  container-arch: architecture (eg: amd64, i386, arm64, armhf)"
    echo "  distro: distribution (eg: trusty)"
    echo "  session-host: hostname where the container will run, defaults to localhost"
    echo "    useful if the name resolution does not work correctly"
    echo "  session-name: session, in case the default '$BUILD_NUMBER-$JOB_NAME' is not suitable"
    echo "  task: type of container (build or test, default=build)"
    exit 1
}

# Save stdout/stderr file descriptors
exec 3>&1 4>&2

# Make sure all output goes to stderr
exec 1>&2

container_arch=
distro=
session_host=
session_name=
task="build"

while [ $# -ge 1 ]
do
    case $1 in
	--arch)
	    container_arch=$2
	    [ x${container_arch} = x ] && usage
	    shift 2
	    ;;
	--distro)
	    distro=$2
	    [ x${distro} = x ] && usage
	    shift 2
	    ;;
	--session-host)
	    session_host=$2
	    [ x${session_host} = x ] && usage
	    shift 2
	    ;;
	--session-name)
	    session_name=$2
	    [ x${session_name} = x ] && usage
	    shift 2
	    ;;
	--task)
	    task=$2
	    [ x${task} = x ] && usage
	    shift 2
	    ;;
	*)
	    echo "Unsupported option: $1"
	    usage
	    ;;
    esac
done

[ x${container_arch} = x ] && usage
[ x${distro} = x ] && usage

[ x"$session_host" = x ] && session_host=localhost
session_host=${session_host}.tcwglab

if [ x"$session_name" = x ]; then
    # Set the default session_name, using BUILD_NUMBER and JOB_NAME,
    # as set by Jenkins.
    if [ "x$BUILD_NUMBER" = "x" ]; then
	echo "BUILD_NUMBER is not defined. Are you executing this from Jenkins ?"
	exit 1
    fi
    if [ "x$JOB_NAME" = "x" ]; then
	echo "JOB_NAME is not defined. Are you executing this from Jenkins ?"
	exit 1
    fi
    session_name=$(echo $BUILD_NUMBER-$JOB_NAME | sed -e "s#[/=,+]#-#g")
fi

# We want to bind-mount WORKSPACE, so make sure it is defined
if [ "x$WORKSPACE" = "x" ]; then
    echo "WORKSPACE is not defined. Are you executing this from Jenkins ?"
    exit 1
fi

case "${distro}:${task}" in
    "trusty":"build")
	image=linaro/ci-${container_arch}-tcwg-ubuntu:${distro}
	;;
    *)
	image=linaro/ci-${container_arch}-tcwg-${task}-ubuntu:${distro}
	;;
esac

DOCKER="docker -H $session_host:2375"
$DOCKER pull $image

session_id=$($DOCKER run --name $session_name -dtP \
		 -v $HOME/snapshots-ref:$HOME/snapshots-ref:ro \
		 -v $WORKSPACE:$WORKSPACE \
		 --memory=7500M --pids-limit=5000 \
		 $image)

if [ x"$session_id" = x ]; then
    exit 1
fi

# Remove the docker instance we have just created in case something
# goes wrong.
trap "$DOCKER rm -fv $session_id ; exec 1>&3 2>&4" EXIT

session_port=$($DOCKER port $session_id 22 | cut -d: -f 2)

# Wait until the ssh server is ready to serve connexions

# Make sure connexion messages go to stderr, so that in case of
# success stdout contains only the connexion info expected by the
# caller.
count=20
while [ $count -gt 0 ]
do
    ssh -p $session_port $session_host true && break
    echo SSH server not ready, waiting.....
    sleep 5
    count=$((count - 1))
done

if [ $count -eq 0 ]; then
    echo SSH server did not respond, exiting
    exit 1
fi

# Do not remove the container upon exit: it is now ready
trap EXIT

# Restore stdout/stderr
exec 1>&3 2>&4

cat <<EOF
CONTAINER="ssh -p $session_port -A $session_host"
CONTAINER_CLEANUP="$DOCKER rm -fv $session_id"
session_host=${session_host}
session_port=${session_port}
EOF