1#!/bin/sh -e
2
3export TRAVIS_API_URL="https://api.travis-ci.org"
4LOCAL_BUILD_DIR=${LOCAL_BUILD_DIR:-build}
5
6COMMON_SCRIPTS="jobs_running_cnt.py inside_docker.sh"
7
8echo_red()   { printf "\033[1;31m$*\033[m\n"; }
9echo_green() { printf "\033[1;32m$*\033[m\n"; }
10echo_blue()  { printf "\033[1;34m$*\033[m\n"; }
11
12get_script_path() {
13	local script="$1"
14
15	[ -n "$script" ] || return 1
16
17	if [ -f "CI/travis/$script" ] ; then
18		echo "CI/travis/$script"
19	elif [ -f "ci/travis/$script" ] ; then
20		echo "ci/travis/$script"
21	elif [ -f "${LOCAL_BUILD_DIR}/$script" ] ; then
22		echo "${LOCAL_BUILD_DIR}/$script"
23	else
24		return 1
25	fi
26}
27
28pipeline_branch() {
29	local branch=$1
30
31	[ -n "$branch" ] || return 1
32
33	# master is a always a pipeline branch
34	[ "$branch" = "master" ] && return 0
35
36	set +x
37	# Check if branch name is 20XX_RY where:
38	#   XX - 14 to 99 /* wooh, that's a lot of years */
39	#   Y  - 1 to 9   /* wooh, that's a lot of releases per year */
40	for year in $(seq 2014 2099) ; do
41		for rel_num in $(seq 1 9) ; do
42			[ "$branch" = "${year}_R${rel_num}" ] && \
43				return 0
44		done
45	done
46
47	return 1
48}
49
50should_trigger_next_builds() {
51	local branch="$1"
52
53	[ -z "${COVERITY_SCAN_PROJECT_NAME}" ] || return 1
54
55	# These Travis-CI vars have to be non-empty
56	[ -n "$TRAVIS_PULL_REQUEST" ] || return 1
57	[ -n "$branch" ] || return 1
58	set +x
59	[ -n "$TRAVIS_API_TOKEN" ] || return 1
60
61	# Has to be a non-pull-request
62	[ "$TRAVIS_PULL_REQUEST" = "false" ] || return 1
63
64	pipeline_branch "$branch" || return 1
65
66	local python_script="$(get_script_path jobs_running_cnt.py)"
67	if [ -z "$python_script" ] ; then
68		echo "Could not find 'jobs_running_cnt.py'"
69		return 1
70	fi
71
72	local jobs_cnt=$(python $python_script)
73
74	# Trigger next job if we are the last job running
75	[ "$jobs_cnt" = "1" ]
76}
77
78trigger_build() {
79	local repo_slug="$1"
80	local branch="$2"
81
82	[ -n "$repo_slug" ] || return 1
83	[ -n "$branch" ] || return 1
84
85	local body="{
86		\"request\": {
87			\"branch\":\"$branch\"
88		}
89	}"
90
91	# Turn off tracing here (shortly)
92	set +x
93	curl -s -X POST \
94		-H "Content-Type: application/json" \
95		-H "Accept: application/json" \
96		-H "Travis-API-Version: 3" \
97		-H "Authorization: token $TRAVIS_API_TOKEN" \
98		-d "$body" \
99		https://api.travis-ci.org/repo/$repo_slug/requests
100}
101
102trigger_adi_build() {
103	local adi_repo="$1"
104	local branch="$2"
105
106	[ -n "$adi_repo" ] || return 1
107	trigger_build "analogdevicesinc%2F$adi_repo" "$branch"
108}
109
110command_exists() {
111	local cmd=$1
112	[ -n "$cmd" ] || return 1
113	type "$cmd" >/dev/null 2>&1
114}
115
116get_ldist() {
117	case "$(uname)" in
118	Linux*)
119		if [ ! -f /etc/os-release ] ; then
120			if [ -f /etc/centos-release ] ; then
121				echo "centos-$(sed -e 's/CentOS release //' -e 's/(.*)$//' \
122					-e 's/ //g' /etc/centos-release)-$(uname -m)"
123				return 0
124			fi
125			ls /etc/*elease
126			[ -z "${OSTYPE}" ] || {
127				echo "${OSTYPE}-unknown"
128				return 0
129			}
130			echo "linux-unknown"
131			return 0
132		fi
133		. /etc/os-release
134		if ! command_exists dpkg ; then
135			echo $ID-$VERSION_ID-$(uname -m)
136		else
137			echo $ID-$VERSION_ID-$(dpkg --print-architecture)
138		fi
139		;;
140	Darwin*)
141		echo "darwin-$(sw_vers -productVersion)"
142		;;
143	*)
144		echo "$(uname)-unknown"
145		;;
146	esac
147	return 0
148}
149
150__brew_install_or_upgrade() {
151	brew install $1 || \
152		brew upgrade $1 || \
153		brew ls --version $1
154}
155
156brew_install_or_upgrade() {
157	while [ -n "$1" ] ; do
158		__brew_install_or_upgrade "$1" || return 1
159		shift
160	done
161}
162
163sftp_cmd_pipe() {
164	sftp ${EXTRA_SSH} ${SSHUSER}@${SSHHOST}
165}
166
167sftp_rm_artifact() {
168	local artifact="$1"
169	sftp_cmd_pipe <<-EOF
170		cd ${DEPLOY_TO}
171		rm ${artifact}
172	EOF
173}
174
175sftp_upload() {
176	local FROM="$1"
177	local TO="$2"
178	local LATE="$3"
179
180	sftp_cmd_pipe <<-EOF
181		cd ${DEPLOY_TO}
182
183		put ${FROM} ${TO}
184		ls -l ${TO}
185
186		symlink ${TO} ${LATE}
187		ls -l ${LATE}
188		bye
189	EOF
190}
191
192upload_file_to_swdownloads() {
193
194	if [ "$#" -ne 4 ] ; then
195		echo "skipping deployment of something"
196		echo "send called with $@"
197		return 0
198	fi
199
200	local LIBNAME=$1
201	local FROM=$2
202	local FNAME=$3
203	local EXT=$4
204
205	if [ -z "$FROM" ] ; then
206		echo no file to send
207		return 1
208	fi
209
210	if [ ! -r "$FROM" ] ; then
211		echo "file $FROM is not readable"
212		return 1
213	fi
214
215	if [ -n "$TRAVIS_PULL_REQUEST_BRANCH" ] ; then
216		local branch="$TRAVIS_PULL_REQUEST_BRANCH"
217	else
218		local branch="$TRAVIS_BRANCH"
219	fi
220
221	local TO=${branch}_${FNAME}
222	local LATE=${branch}_latest_${LIBNAME}${LDIST}${EXT}
223	local GLOB=${DEPLOY_TO}/${branch}_${LIBNAME}-*
224
225	echo attemting to deploy $FROM to $TO
226	echo and ${branch}_${LIBNAME}${LDIST}${EXT}
227	ssh -V
228
229	for rmf in ${TO} ${LATE} ; do
230		sftp_rm_artifact ${rmf} || \
231			echo_blue "Could not delete ${rmf}"
232	done
233
234	sftp_upload "${FROM}" "${TO}" "${LATE}" || {
235		echo_red "Failed to upload artifact from '${FROM}', to '${TO}', symlink '${LATE}'"
236		return 1
237	}
238
239	# limit things to a few files, so things don't grow forever
240	if [ "${EXT}" = ".deb" ] ; then
241		for files in $(ssh ${EXTRA_SSH} ${SSHUSER}@${SSHHOST} \
242			"ls -lt ${GLOB}" | tail -n +100 | awk '{print $NF}')
243		do
244			ssh ${EXTRA_SSH} ${SSHUSER}@${SSHHOST} \
245				"rm ${DEPLOY_TO}/${files}" || \
246				return 1
247		done
248	fi
249
250	return 0
251}
252
253prepare_docker_image() {
254	local DOCKER_IMAGE="$1"
255	sudo apt-get -qq update
256	echo 'DOCKER_OPTS="-H tcp://127.0.0.1:2375 -H unix:///var/run/docker.sock -s devicemapper"' | sudo tee /etc/default/docker > /dev/null
257	sudo service docker restart
258	sudo docker pull "$DOCKER_IMAGE"
259}
260
261run_docker_script() {
262	local DOCKER_SCRIPT="$(get_script_path $1)"
263	local DOCKER_IMAGE="$2"
264	local OS_TYPE="$3"
265	local MOUNTPOINT="${4:-docker_build_dir}"
266	sudo docker run --rm=true \
267		-v "$(pwd):/${MOUNTPOINT}:rw" \
268		$DOCKER_IMAGE \
269		/bin/bash -e "/${MOUNTPOINT}/${DOCKER_SCRIPT}" "${MOUNTPOINT}" "${OS_TYPE}"
270}
271
272ensure_command_exists() {
273	local cmd="$1"
274	local package="$2"
275	[ -n "$cmd" ] || return 1
276	[ -n "$package" ] || package="$cmd"
277	! command_exists "$cmd" || return 0
278	# go through known package managers
279	for pacman in apt-get brew yum ; do
280		command_exists $pacman || continue
281		$pacman install -y $package || {
282			# Try an update if install doesn't work the first time
283			$pacman -y update && \
284				$pacman install -y $package
285		}
286		return $?
287	done
288	return 1
289}
290
291ensure_command_exists sudo
292
293# Other scripts will download lib.sh [this script] and lib.sh will
294# in turn download the other scripts it needs.
295# This gives way more flexibility when changing things, as they propagate
296for script in $COMMON_SCRIPTS ; do
297	[ ! -f "CI/travis/$script" ] || continue
298	[ ! -f "ci/travis/$script" ] || continue
299	[ ! -f "${LOCAL_BUILD_DIR}/$script" ] || continue
300	mkdir -p ${LOCAL_BUILD_DIR}
301	ensure_command_exists wget
302	wget https://raw.githubusercontent.com/analogdevicesinc/libiio/master/CI/travis/$script \
303		-O $LOCAL_BUILD_DIR/$script
304done
305