diff options
author | Libreboot Contributor <contributor@libreboot.org> | 2020-03-18 17:20:14 +0100 |
---|---|---|
committer | Libreboot Contributor <contributor@libreboot.org> | 2020-03-18 17:20:27 +0100 |
commit | 0f6ea1c9e0a25a9b7546f96f27cef8841f0d09b5 (patch) | |
tree | a28b9403123dd6204eb2dd8cb44eada12c169f4b /i18n/fr_FR/libs | |
parent | 6e5bdd1271059a9c61c80b21001fd3d14ff25045 (diff) | |
download | librebootfr-0f6ea1c9e0a25a9b7546f96f27cef8841f0d09b5.tar.gz librebootfr-0f6ea1c9e0a25a9b7546f96f27cef8841f0d09b5.zip |
Creation of i18n folder containing translations of the libreboot project. Added french one, not finished.
Diffstat (limited to 'i18n/fr_FR/libs')
-rwxr-xr-x | i18n/fr_FR/libs/common | 441 | ||||
-rwxr-xr-x | i18n/fr_FR/libs/git | 614 | ||||
-rwxr-xr-x | i18n/fr_FR/libs/project | 1712 | ||||
-rwxr-xr-x | i18n/fr_FR/libs/tool | 387 |
4 files changed, 3154 insertions, 0 deletions
diff --git a/i18n/fr_FR/libs/common b/i18n/fr_FR/libs/common new file mode 100755 index 00000000..b1091e4f --- /dev/null +++ b/i18n/fr_FR/libs/common @@ -0,0 +1,441 @@ +#!/usr/bin/env bash + +# Copyright (C) 2016 Paul Kocialkowski <contact@paulk.fr> +# +# 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 3 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, see <http://www.gnu.org/licenses/>. + +BUILD_SYSTEM="libreboot" + +PROJECTS="projects" +SOURCES="sources" +BUILD="build" +INSTALL="install" +RELEASE="release" +SYSTEMS="systems" +IMAGES="images" +TOOLS="tools" + +CONFIGS="configs" +PATCHES="patches" +TARGETS="targets" +REVISION="revision" +VARIANTS="variants" +BLOBS="blobs" +BLOBS_IGNORE="blobs-ignore" +BLOBS_DISCOVER="blobs-discover" +DEPENDENCIES="dependencies" + +DOTEPOCH=".epoch" +DOTRNDSEED=".rndseed" +DOTVERSION=".version" +DOTREVISION=".revision" +DOTTARFILES=".tarfiles" +ARCHIVE="tar.xz" +CHECKSUM="sha256sum" +DSIG="asc" + +CONFIG_SHELL="${CONFIG_SHELL:-$(which bash)}" +EDITOR="${EDITOR:-$(which vi || true)}" +TASKS="${TASKS:-1}" + +function_check() { + local function=$1 + + declare -f -F "$function" > /dev/null +} + +variable_check() { + local variable=$1 + + test ! -z "${!variable}" +} + +arguments_list() { + local argument + + for argument in "$@" + do + printf '%s\n' "$argument" + done +} + +download_wrapper() { + local download_dir="$1" + shift + local uris=($@) + + local wget_options=( + '--config=/dev/null' + '--secure-protocol=PFS' + "--directory-prefix=$download_dir" + '--continue' + '--' + ) + + local curl_options=( + '-q' + '--continue-at -' + '--remote-name' + '--retry 20' + '--ssl' + '--tlsv1.2' + '--' + ) + + if hash wget > /dev/null 2>&1; then + + wget "${wget_options[@]}" "${uris[@]}" + + elif hash curl > /dev/null 2>&1; then + ( + cd "$download_dir" + + curl "${curl_options[@]}" "${uris[@]}" + ) + else + printf '\n%s\n\n' 'Error: Neither wget nor curl were found' 1>&2 + + return 1 + fi +} + +diff_patch() { + local sources_path=$1 + local patch_path=$2 + + patch -fd "$sources_path" -r - < "$patch_path" +} + +diff_patch_check() { + local sources_path=$1 + local patch_path=$2 + + patch -sfd "$sources_path" --dry-run < "$patch_path" > /dev/null 2>&1 +} + +path_wildcard_expand() { + local path=$@ + + # Evaluation fails with unescaped whitespaces. + path=$(printf '%s\n' "$path" | sed "s/ /\\\ /g") + + eval "arguments_list "$path"" +} + +file_checksum_create() { + local path=$1 + + local checksum_path="$path.$CHECKSUM" + local name=$(basename "$path") + local directory_path=$(dirname "$path") + + ( + cd "$directory_path" + sha256sum "$name" > "$checksum_path" + ) +} + +file_checksum_check() { + local path=$1 + + local checksum_path="$path.$CHECKSUM" + local name=$(basename "$path") + local directory_path=$(dirname "$path") + + if ! [[ -f "$checksum_path" ]] + then + printf 1>&2 '%s\n' 'Could not verify file checksum!' + return 1 + fi + + ( + cd "$directory_path" + sha256sum -c "$checksum_path" + ) +} + +file_signature_create() { + local path=$1 + + local signature_path="$path.$DSIG" + + if [[ -z "$RELEASE_KEY" ]] + then + return 0 + fi + + gpg --default-key "$RELEASE_KEY" --armor --output "$signature_path" --detach-sign --yes "$path" +} + +file_signature_check() { + local path=$1 + + local signature_path="$path.$DSIG" + + if ! [[ -f "$signature_path" ]] + then + printf 1>&2 '%s\n' 'Could not verify file signature!' + return 1 + fi + + gpg --armor --verify "$signature_path" "$path" +} + +file_verification_create() { + local path=$1 + + file_checksum_create "$path" + file_signature_create "$path" +} + +file_verification_check() { + local path=$1 + + file_checksum_check "$path" + file_signature_check "$path" +} + +file_exists_check() { + local path=$1 + + test -f "$path" +} + +directory_filled_check() { + local path=$1 + + if [[ -z "$(ls -A "$path" 2> /dev/null)" ]] + then + return 1 + else + return 0 + fi +} + +archive_files_create() { + local source_path="$1" + + local directory="$(basename "$source_path")" + local tarfiles_path="$source_path/$DOTTARFILES" + local revision_path="$source_path/$DOTREVISION" + local version_path="$source_path/$DOTVERSION" + local epoch_path="$source_path/$DOTEPOCH" + local rnd_seed_path="$source_path/$DOTRNDSEED" + + # Files in "$tarfiles_path" are NUL terminated. + # `tr '\0' '\n'` for human-readable output. + if git_check "$source_path"; then + git_files "$source_path" > "$tarfiles_path" + printf '%s\0' "$DOTTARFILES" >> "$tarfiles_path" + else + find "$source_path" -print0 | env LC_ALL='C.UTF-8' sort -z | sed -z "1d;s,^$source_path/\\?,,;/^$DOTTARFILES\$/d" > "$tarfiles_path" + fi + + for dotfile in "$revision_path" \ + "$version_path" \ + "$epoch_path" \ + "$rnd_seed_path" + do + if [[ -f "$dotfile" ]]; then + printf '%s\0' ".${dotfile##*.}" >> "$tarfiles_path" + fi + done +} + +archive_files_date() { + local source_path="$1" + + local epoch_path="$source_path/$DOTEPOCH" + + if [[ -n "$SOURCE_DATE_EPOCH" ]]; then + find "$source_path" -execdir touch --no-dereference --date="@$SOURCE_DATE_EPOCH" {} + + fi +} + +archive_create() { + local archive_path="$1" + local source_path="$2" + local directory="$3" + + local tarfiles_path="$source_path/$DOTTARFILES" + local directory_path="$(dirname "$archive_path")" + + mkdir -p "$directory_path" + + if [[ -z "$directory" ]]; then + directory="$(basename "$source_path")" + fi + + archive_files_create "$source_path" + archive_files_date "$source_path" + + local tar_options=( + --create + --xz + --file="$archive_path" + --files-from="$tarfiles_path" + --transform="s,^,$directory/,S" + --no-recursion + --warning=no-filename-with-nuls + --null + --owner=0 + --group=0 + --numeric-owner + ) + + ( + cd "$source_path" + tar "${tar_options[@]}" + ) +} + +archive_extract() { + local archive_path="$1" + local destination_path="$2" + + if [[ -z "$destination_path" ]]; then + destination_path="$(dirname "$archive_path")" + fi + + tar -xf "$archive_path" -ps -C "$destination_path" +} + +rootfs_files_create() { + local source_path="$1" + + local directory="$(basename "$source_path")" + local tarfiles_path="$source_path/$DOTTARFILES" + + # Files in "$tarfiles_path" are NUL terminated. + # `tr '\0' '\n'` for human-readable output. + execute_root find "$source_path" -print0 | env LC_ALL='C.UTF-8' sort -z | sed -z "1d;s,^$source_path/\\?,,;/^$DOTTARFILES\$/d" > "$tarfiles_path" +} + +rootfs_files_date() { + local source_path="$1" + + local epoch_path="$source_path/$DOTEPOCH" + + if [[ -n "$SOURCE_DATE_EPOCH" ]]; then + execute_root find "$source_path" -execdir touch --no-dereference --date="@$SOURCE_DATE_EPOCH" {} + + fi +} + +rootfs_create() { + local rootfs_path="$1" + local source_path="$2" + local directory="$3" + + local tarfiles_path="$source_path/$DOTTARFILES" + local directory_path="$(dirname "$rootfs_path")" + + mkdir -p "$directory_path" + + if [[ -z "$directory" ]]; then + directory="$(basename "$source_path")" + fi + + rootfs_files_create "$source_path" + rootfs_files_date "$source_path" + + local tar_options=( + --create + --xz + --file="$rootfs_path" + --files-from="$tarfiles_path" + --no-recursion + --warning=no-filename-with-nuls + --null + --owner=0 + --group=0 + --numeric-owner + ) + + ( + cd "$source_path" + execute_root tar "${tar_options[@]}" + ) + + execute_root chmod 644 "$rootfs_path" + execute_root chown "$USER:$USER" "$rootfs_path" +} + +requirements() { + local requirement + local requirement_path + + for requirement in "$@" + do + requirement_path=$(which "$requirement" || true) + + if [[ -z "$requirement_path" ]] + then + printf 1>&2 '%s\n' "Missing requirement: $requirement" + exit 1 + fi + done +} + +requirements_root() { + local requirement + local requirement_path + + for requirement in "$@" + do + # We need to keep stdout output to show the command. + requirement_path=$(execute_root which "$requirement" || true) + + if [[ -z "$requirement_path" ]] + then + printf 1>&2 '%s\n' "Missing requirement: $requirement" + exit 1 + fi + done +} + +arguments_concat() { + local delimiter=$1 + shift + + local concat + + for argument in "$@" + do + if [[ -n "$concat" ]] + then + concat="$concat""$delimiter""$argument" + else + concat="$argument" + fi + done + + printf '%s\n' "$concat" +} + +execute_root() { + local sudo=$(which sudo 2> /dev/null || true) + local arguments + + printf 1>&2 '%s' 'Running command as root: ' + printf 1>&2 '%b\n' "$*" + + if [[ -n "$sudo" ]] + then + sudo "$@" + else + # Quote arguments for eval through su. + arguments=$(printf '%q ' "$@") + su -c "$arguments" + fi +} diff --git a/i18n/fr_FR/libs/git b/i18n/fr_FR/libs/git new file mode 100755 index 00000000..2cde3dd3 --- /dev/null +++ b/i18n/fr_FR/libs/git @@ -0,0 +1,614 @@ +#!/usr/bin/env bash + +# Copyright (C) 2016 Paul Kocialkowski <contact@paulk.fr> +# Copyright (C) 2019 Andrew Robbins <contact@andrewrobbins.info> +# +# 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 3 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, see <http://www.gnu.org/licenses/>. + +BRANCH_PREFIX="libreboot-" +DOTGIT=".git" +HEAD="HEAD" +ORIGIN_HEAD="origin/HEAD" +WILDDOTPATCH="*.patch" +GIT_NAME="Libreboot" +GIT_EMAIL="libreboot@libreboot.org" + +git_check() { + local repository_path=$1 + + directory_filled_check "$repository_path/$DOTGIT" +} + +git_clone() { + local repository_path=$1 + local url=$2 + + git clone "$url" "$repository_path" +} + +git_submodule_update() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git submodule update --init + ) +} + +git_merge() { + local repository_path=$1 + local revision=$2 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git merge "$revision" + ) +} + +git_branch_create() { + local repository_path=$1 + local branch=$2 + local revision=$3 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git checkout -B "$branch" + + if [[ -n "$revision" ]] + then + git reset --hard "$revision" + fi + ) +} + +git_branch_delete() { + local repository_path=$1 + local branch=$2 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git branch -D "$branch" + ) +} + +git_branch_checkout() { + local repository_path=$1 + local branch=$2 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git checkout "$branch" > /dev/null + ) +} + +git_branch_check() { + local repository_path=$1 + local branch=$2 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git rev-parse --verify "$branch" >/dev/null 2>&1 + ) +} + +git_fetch() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git fetch origin + ) +} + +git_fetch_check() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git fetch --dry-run origin >/dev/null 2>&1 + ) +} + +git_clean() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git clean -df + ) +} + +git_remove() { + local repository_path=$1 + local path=$2 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git rm -rf "$path" + ) +} + +git_diff_staged_check() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git diff --staged --quiet + ) +} + +git_diff_check() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git diff --quiet + ) +} + +git_commit() { + local repository_path=$1 + local message=$2 + + ( + export GIT_COMMITTER_NAME=$GIT_NAME + export GIT_COMMITTER_EMAIL=$GIT_EMAIL + + cd "$repository_path" 2>/dev/null || exit 1 + + git commit --author="$GIT_NAME <$GIT_EMAIL>" -m "$message" + ) +} + +git_am() { + local repository_path=$1 + local branch=$2 + local patch=$3 + + ( + export GIT_COMMITTER_NAME=$GIT_NAME + export GIT_COMMITTER_EMAIL=$GIT_EMAIL + + cd "$repository_path" 2>/dev/null || exit 1 + + git checkout "$branch" >/dev/null 2>&1 + + if ! git am "$patch"; then + git am --abort + + exit 1 + fi + ) +} + +git_apply() { + local repository_path=$1 + local branch=$2 + local patch=$3 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git checkout "$branch" >/dev/null 2>&1 + git apply --index "$patch" + ) +} + +git_apply_check() { + local repository_path=$1 + local branch=$2 + local patch=$3 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git checkout "$branch" >/dev/null 2>&1 + git apply --check "$patch" + ) +} + +git_patch() { + local repository_path=$1 + local branch=$2 + local patch=$3 + + git_apply_check "$repository_path" "$branch" "$patch" || return 1 + + case $patch in + *.patch) + git_am "$repository_path" "$branch" "$patch" + ;; + *.diff) + git_apply "$repository_path" "$branch" "$patch" + git_commit "$repository_path" "Applied ${patch##*/}" + ;; + *) + ;; + esac +} + +git_revision() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git rev-parse "$HEAD" + ) +} + +git_describe() { + local repository_path=$1 + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git describe --tags + ) +} + +git_files() { + local repository_path="$1" + + ( + cd "$repository_path" 2>/dev/null || exit 1 + + git ls-files -z | sort -z + ) +} + +git_project_repository_path() { + local repository=$1 + + printf '%s\n' "$root/$SOURCES/$repository" +} + +git_project_check() { + local repository=$1 + + local repository_path=$(git_project_repository_path "$repository") + + git_check "$repository_path" +} + +git_project_patch_recursive() { + local project=$1 + local repository=$2 + local branch=$3 + local path=$4 + + local repository_path=$(git_project_repository_path "$repository") + local project_path=$(project_path "$project") + local patches_path=$project_path/$PATCHES/$path + + if ! [[ -d $project_path/$PATCHES ]]; then + return 0 + fi + + for patch in "$patches_path"/[!.]*.@(patch|diff); do + git_patch "$repository_path" "$branch" "$patch" || return 1 + done + + if [[ -n $path && $path != . ]]; then + git_project_patch_recursive "$project" "$repository" "$branch" "$(dirname "$path")" + fi +} + +git_project_clone() { + local repository=$1 + shift + local urls=$@ + + local repository_path=$(git_project_repository_path "$repository") + local directory_path=$(dirname "$repository_path") + local url + + mkdir -p "$directory_path" + + ( + set +e + + for url in $urls + do + if git_clone "$repository_path" "$url" + then + return 0 + fi + done + + return 1 + ) +} + +git_project_prepare() { + local project=$1 + shift + local repository=$1 + shift + + git_project_prepare_revision "$project" "$repository" "$@" + git_project_prepare_blobs "$project" "$repository" "$@" + git_project_prepare_patch "$project" "$repository" "$@" +} + +git_project_prepare_blobs() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local blob + + while read -r blob + do + git_remove "$repository_path" "$blob" + done < <(project_blobs "$project" "$@") + + if ! git_diff_staged_check "$repository_path" + then + git_commit "$repository_path" "Removed blobs" + fi +} + +git_project_prepare_patch() { + local project=$1 + shift + local repository=$1 + shift + + local branch=$project + local argument + local path + + for argument in "$@" + do + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local prepare_branch=$BRANCH_PREFIX$branch + local prepare_path=$path + + git_project_patch_recursive "$project" "$repository" "$prepare_branch" "$prepare_path" + fi +} + +git_project_prepare_revision() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local project_path=$(project_path "$project") + local configs_path="$project_path/$CONFIGS" + local branch=$project + local prepare_revision + local argument + local path + + for argument in "" "$@" + do + if [[ -n $argument ]] + then + if [[ -z $path ]] + then + path="$argument" + else + path="$path/$argument" + fi + + branch="$branch-$argument" + fi + + local revision_path="$configs_path/$path/$REVISION" + + if [[ -f $revision_path ]]; then + prepare_revision=$(< "$revision_path") + fi + done + + if [[ -n $branch ]] + then + local prepare_branch=$BRANCH_PREFIX$branch + + git_branch_create "$repository_path" "$prepare_branch" "$prepare_revision" + fi +} + +git_project_prepare_check() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local branch=$project + local argument + + for argument in "$@" + do + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local prepare_branch=$BRANCH_PREFIX$branch + + git_branch_check "$repository_path" "$prepare_branch" + fi +} + +git_project_prepare_clean() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local branch=$project + local argument + + for argument in "$@" + do + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local prepare_branch=$BRANCH_PREFIX$branch + + if git_branch_check "$repository_path" "$prepare_branch" + then + git_branch_delete "$repository_path" "$prepare_branch" + fi + fi +} + +git_project_checkout() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local branch=$project + local argument + + for argument in "$@" + do + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local checkout_branch=$BRANCH_PREFIX$branch + + if git_branch_check "$repository_path" "$checkout_branch" + then + git_branch_checkout "$repository_path" "$checkout_branch" + git_submodule_update "$repository_path" + fi + fi +} + +git_project_update() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + + git_fetch "$repository_path" + git_branch_checkout "$repository_path" "$ORIGIN_HEAD" + + git_project_prepare_clean "$project" "$repository" "$@" + git_project_prepare "$project" "$repository" "$@" +} + +git_project_update_check() { + local project=$1 + shift + local repository=$1 + shift + + git_project_prepare_check "$project" "$repository" "$@" + + git_fetch_check "$repository_path" +} + +git_project_release() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local branch=$project + local argument + + for argument in "$@" + do + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local release_branch=$BRANCH_PREFIX$branch + + if git_branch_check "$repository_path" "$release_branch" + then + local archive_path="$root/$RELEASE/$SOURCES/$project/$release_branch.$ARCHIVE" + local sources_path="$root/$SOURCES/$repository" + + printf '%s\n' "Releasing sources archive for $project (with ${arguments:-no argument}) from "$repository" git" + + git_branch_checkout "$repository_path" "$release_branch" + git_submodule_update "$repository_path" + git_clean "$repository_path" + archive_create "$archive_path" "$sources_path" "$release_branch" + file_verification_create "$archive_path" + fi + fi +} + +git_project_release_check() { + local project=$1 + shift + local repository=$1 + shift + + local repository_path=$(git_project_repository_path "$repository") + local branch=$project + local argument + + for argument in "$@" + do + branch="$branch-$argument" + done + + if [[ -n $branch ]] + then + local release_branch=$BRANCH_PREFIX$branch + + if git_branch_check "$repository_path" "$release_branch" + then + local archive_path="$root/$RELEASE/$SOURCES/$project/$release_branch.$ARCHIVE" + + file_exists_check "$archive_path" + fi + fi +} diff --git a/i18n/fr_FR/libs/project b/i18n/fr_FR/libs/project new file mode 100755 index 00000000..d884556d --- /dev/null +++ b/i18n/fr_FR/libs/project @@ -0,0 +1,1712 @@ +#!/usr/bin/env bash + +# Copyright (C) 2016 Paul Kocialkowski <contact@paulk.fr> +# Copyright (C) 2018,2019 Andrew Robbins <contact@andrewrobbins.info> +# +# 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 3 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, see <http://www.gnu.org/licenses/>. + +PROJECT_ACTIONS_GENERIC=(usage dependencies download extract update build install release clean) +PROJECT_ACTIONS_GENERIC_IGNORE_CHECK=(usage clean) +PROJECT_ACTIONS_HELPERS=(arguments dependencies) + +INSTALL_REGEX='\([^:]*\):\(.*\)' + +project_include() { + local project=$1 + + local project_path=$(project_path "$project") + + unset -f "${PROJECT_ACTIONS[@]}" + + source "$project_path/$project" + + project_helper_include "$project" +} + +project_helper_include() { + local project=$1 + + local project_path=$(project_path "$project") + local include="$project_path/$project-helper" + + if [[ -f "$include" ]] + then + source "$include" + fi +} + +project_check() { + local project="${1##*/}" + + local project_path="$(project_path "$project")" + + if ! [[ -f "$project_path/$project" ]]; then + return 1 + fi +} + +project_dependencies() { + local project=$1 + shift + + if [[ -n "${PROJECTS_FORCE[*]}" ]]; then + local expanded + local project_force + + for project_force in "${PROJECTS_FORCE[@]}"; do + project_arguments_expand_recursive $project_force | while IFS='' read -r expanded; do + project_dependencies_sort $expanded + done + done + fi + + project_dependencies_sort "$project" "$@" | head -n -1 +} + +project_dependencies_collect() { + local project=$1 + shift + + local argument + local path + + for argument in "" "$@"; do + if [[ -z $argument ]]; then + path=$CONFIGS + else + path=$path/$argument + fi + + project_file_contents "$project" "$path" "$DEPENDENCIES" + done + + project_dependencies_collect_recursive "$project" "$@" +} + +project_dependencies_collect_recursive() { + local project=$1 + shift + + local argument + local path + + for argument in "" "$@"; do + if [[ -z $argument ]]; then + path=$CONFIGS + else + path=$path/$argument + fi + done + + project_action_helper arguments "$project" "$@" | while IFS='' read -r argument; do + project_file_contents "$project" "$path/$argument" "$DEPENDENCIES" + project_dependencies_collect_recursive "$project" "$@" "$argument" + done +} + +project_dependencies_encode_recursive() { + local project=$1 + shift + + local project_arguments=$(arguments_concat ' ' "$project" "$@") + local project_arguments_encoded=$(base64 -w0 <<< "$project_arguments") + + local dependency + + project_dependencies_collect "$project" "$@" | while IFS='' read -r dependency; do + local dependency_arguments=$(arguments_concat ' ' $dependency) + local dependency_arguments_encoded=$(base64 -w0 <<< "$dependency_arguments") + + printf '%s\n' "$project_arguments_encoded $dependency_arguments_encoded" + + project_dependencies_encode_recursive $dependency + done +} + +project_dependencies_sort() { + local project=$1 + shift + + ( + set -o pipefail + + project_dependencies_encode_recursive "$project" "$@" | tsort | base64 -d -w0 | tac + ) +} + +project_dependencies_check() { + local project=$1 + shift + + local dependency + local -i missing=0 + + project_dependencies "$project" "$@" | while read -r dependency; do + project_check $dependency || let ++missing + done + + return $missing +} + +project_dependencies_sources_check() { + local project=$1 + shift + + local dependency + local -i missing=0 + + project_dependencies "$project" "$@" | while read -r dependency; do + project_sources_directory_filled_check $dependency || let ++missing + done + + return $missing +} + +project_dependencies_action_arguments() { + local action=$1 + local project=$2 + shift 2 + + local -a dependency + + project_dependencies "$project" "$@" | while read -ra dependency; do + if project_function_check "${dependency[0]}" "$action"; then + project_action_arguments "$action" "${dependency[@]}" + fi + done +} + +project_function_check() { + local project=$1 + local function=$2 + + ( + project_include "$project" + + if ! function_check "$function"; then + exit 1 + fi + ) +} + +project_action() { + local action="$1" + shift + local project="$1" + shift + local arguments="$*" + + if project_action_check "$action" "$project" "$@"; then + return 0 + fi + + ( + set +e + + printf '%s\n' "Project $project $action (with ${arguments:-no argument})" + + ( + set -e + + "$action" "$@" + ) + + local -i exit_status=$? + + if ((exit_status)); then + printf 1>&2 '%s\n' "Project $project $action (with ${arguments:-no argument}) failed" + else + printf '%s\n' "Project $project $action (with ${arguments:-no argument}) completed" + fi + + exit $exit_status + ) + +} + +project_action_check() { + local action="$1" + shift + local project="$1" + shift + + ( + set +e + + if ! function_check "${action}_check"; then + return 1 + fi + + for project_force in $PROJECTS_FORCE; do + if [[ "$project_force" == "$project" ]]; then + return 1 + fi + done + + ( + set -e + "${action}_check" "$@" + ) + ) +} + +project_action_helper() { + local helper="$1" + shift + local project="$1" + shift + + ( + project_include "$project" + + if ! function_check "$helper"; then + exit 0 + fi + + "$helper" "$@" + ) +} + +project_action_arguments() { + local action="$1" + shift + local project="$1" + shift + + ( + project_include "$project" + + project_action_arguments_verify_recursive "$action" "$project" "$@" + project_action_arguments_recursive "$action" "$project" "$@" + ) +} + +project_action_arguments_verify_recursive() { + local action="$1" + shift + local project="$1" + shift + + local action_helper_arguments + + # Store final argument. + local argument="${*:$#}" + + local test + + if [[ "$#" -gt 1 ]]; then + # Set previous arguments. + set "${@:1:$#-1}" + elif [[ "$#" -eq 1 ]]; then + shift + else + return 0 + fi + + action_helper_arguments="$(project_action_helper 'arguments' "$project" "$@")" + + if [[ -n "$action_helper_arguments" ]]; then + test="$(printf '%s\n' "$action_helper_arguments" | grep -e "^$argument\$" || true)" + + if [[ -z "$test" ]]; then + printf 1>&2 '%s\n' "Invalid argument $argument for project $project action $action" + return 1 + fi + fi + + project_action_arguments_verify_recursive "$action" "$project" "$@" +} + +project_action_arguments_recursive() { + local action="$1" + shift + local project="$1" + shift + + local action_helper_arguments + local argument + + action_helper_arguments="$(project_action_helper 'arguments' "$project" "$@" || true)" + + if [[ -z "$action_helper_arguments" ]]; then + project_action "$action" "$project" "$@" + else + # This is to allow space characters in arguments. + local ifs_save="$IFS" + local IFS=$'\n' + + for argument in $(printf '%s\n' "$action_helper_arguments") + do + IFS="$ifs_save" + + # Only a single argument at a time is returned by the helper. + project_action_arguments_recursive "$action" "$project" "$@" "$argument" + done + fi +} + +project_action_projects() { + local action="$1" + shift + local project="$1" + shift + + local project_path="$(project_path "$project")" + local project_projects_path="$project_path/$CONFIGS/$PROJECTS" + local project_projects_action_path="$project_path/$CONFIGS/$PROJECTS-$action" + local arguments + local path + + if [[ -f "$project_projects_action_path" ]]; then + path="$project_projects_action_path" + else + path="$project_projects_path" + fi + + # Multiple arguments can be read from the file. + while read -r arguments; do + eval "project_action_arguments $action $arguments" + done < "$path" +} + +project_action_usage() { + local project=$1 + shift + + ( + project_include "$project" + + project_action usage "$project" "$@" + ) +} + +project_path() { + local project=$1 + + local project_path="$root/$PROJECTS/$project" + + printf '%s\n' "$project_path" +} + +project_sources_path() { + local project=$1 + shift + local repository=$1 + shift + + local sources_path + local argument + local path + + # Check downloaded and extracted sources first, using "$project." + path="$root/$SOURCES/$project" + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path-$argument" + fi + + if ! directory_filled_check "$path" + then + continue + fi + + sources_path=$path + done + + if [[ -n "$sources_path" ]] + then + printf '%s\n' "$sources_path" + return + fi + + # Check downloaded sources then, using "$repository." + path="$root/$SOURCES/$repository" + + if directory_filled_check "$path" + then + printf '%s\n' "$path" + return + fi + + # Check project sources finally, using "$project." + path="$root/$PROJECTS/$project/$SOURCES" + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + if ! directory_filled_check "$path" + then + continue + fi + + sources_path=$path + done + + if [[ -n "$sources_path" ]] + then + printf '%s\n' "$sources_path" + return + fi +} + +project_sources_directory_filled_check() { + local project=$1 + shift + + local sources_path=$(project_sources_path "$project" "$@") + + test ! -z "$sources_path" +} + +project_sources_directory_filled_error() { + local project=$1 + shift + local arguments="$*" + + local sources_path=$(project_sources_path "$project" "$@") + + if [[ -n "$sources_path" ]] + then + printf 1>&2 '%s\n' "Sources directory for project $project (with ${arguments:-no argument}) already exists" + return 1 + else + return 0 + fi +} + +project_sources_directory_missing_empty_error() { + local project=$1 + shift + local arguments="$*" + + local sources_path=$(project_sources_path "$project" "$@") + + if [[ -z "$sources_path" ]] + then + printf 1>&2 '%s\n' "Sources directory for project $project (with ${arguments:-no argument}) missing or empty" + return 1 + else + return 0 + fi +} + +project_sources_archive() { + local project=$1 + shift + + local sources_archive + local argument + local path="$root/$SOURCES/$project" + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path-$argument" + fi + + local archive="$path.$ARCHIVE" + + if ! [[ -f "$archive" ]] + then + continue + fi + + sources_archive=$archive + done + + if [[ -n "$sources_archive" ]] + then + printf '%s\n' "$sources_archive" + fi +} + +project_sources_archive_extract() { + local project=$1 + shift + local arguments="$*" + + local archive=$(project_sources_archive "$project" "$@") + local destination=$(dirname "$archive") + + printf '%s\n' "Extracting source archive for $project (with ${arguments:-no argument})" + + file_verification_check "$archive" + archive_extract "$archive" "$destination" +} + +project_sources_archive_update() { + local project=$1 + shift + local arguments="$*" + + local repository=$project + local sources_path=$(project_sources_path "$project" "$repository" "$@") + local archive=$(project_sources_archive "$project" "$@") + local destination=$(dirname "$archive") + + if [[ -d "$sources_path" ]] + then + rm -rf "$sources_path" + fi + + printf '%s\n' "Extracting source archive for $project (with ${arguments:-no argument})" + + file_verification_check "$archive" + archive_extract "$archive" "$destination" +} + +project_sources_archive_missing_error() { + local project=$1 + shift + local arguments="$*" + + local archive=$(project_sources_archive "$project" "$@") + if [[ -z "$archive" ]] || ! [[ -f "$archive" ]] + then + printf 1>&2 '%s\n' "Missing sources archive for $project (with ${arguments:-no argument})" + return 1 + else + return 0 + fi +} + +project_sources_archive_missing_check() { + local project=$1 + shift + + local archive=$(project_sources_archive "$project" "$@") + if [[ -z "$archive" ]] || ! [[ -f "$archive" ]] + then + return 0 + else + return 1 + fi +} + +project_sources_prepare() { + local project="$1" + shift + + project_sources_prepare_blobs "$project" "$@" + project_sources_prepare_patch "$project" "$@" +} + +project_sources_prepare_blobs() { + local project=$1 + shift + + local sources_path=$(project_sources_path "$project" "$project" "$@") + + ( + cd "$sources_path" || exit 1 + + project_blobs "$project" "$@" | while IFS='' read -r blob; do + rm -f -- "$blob" + done + ) +} + +project_sources_prepare_patch() { + local project="$1" + shift + + local argument + local path + + for argument in "$@"; do + if [[ -z $path ]]; then + path=$argument + else + path=$path/$argument + fi + done + + if [[ -n $project ]]; then + project_sources_patch_recursive "$project" "$path" + fi +} + +project_sources_prepare_check() { + local project=$1 + shift + + local sources_path=$(project_sources_path "$project" "$project" "$@") + + directory_filled_check "$sources_path" +} + +project_sources_patch_recursive() { + local project=$1 + local path=$2 + + local project_path=$(project_path "$project") + local sources_path=$(project_sources_path "$project" "$project" "$@") + local patches_path=$project_path/$PATCHES/$path + + if ! [[ -d $project_path/$PATCHES ]]; then + return 0 + fi + + for patch in "$patches_path"/[!.]*.@(patch|diff); do + project_sources_patch "$sources_path" "$patch" || return 1 + done + + if [[ -n $path && $path != . ]]; then + project_sources_patch_recursive "$project" "$(dirname "$path")" + fi +} + +project_blobs() { + local project=$1 + shift + + local blobs_path=$(project_blobs_path "$project" "$@") + local blobs_ignore_path=$(project_blobs_ignore_path "$project" "$@") + + if [[ -n $blobs_path ]]; then + if [[ -n $blobs_ignore_path ]]; then + comm -23 <(sort "$blobs_path") <(sort "$blobs_ignore_path") + else + cat "$blobs_path" + fi + fi +} + +project_sources_patch() { + local sources_path=$1 + local patch_path=$2 + + if diff_patch_check "$sources_path" "$patch_path"; then + diff_patch "$sources_path" "$patch_path" + else + return 1 + fi +} + +project_blobs_path() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local configs_path="$project_path/$CONFIGS" + local argument + local path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + local blobs_path="$configs_path/$path/$BLOBS" + + if [[ -f "$blobs_path" ]] + then + printf '%s\n' "$blobs_path" + return + fi + done +} + +project_blobs_ignore_path() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local configs_path="$project_path/$CONFIGS" + local argument + local path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + blobs_ignore_path="$configs_path/$path/$BLOBS_IGNORE" + + if [[ -f "$blobs_ignore_path" ]] + then + printf '%s\n' "$blobs_ignore_path" + return + fi + done +} + +project_arguments_targets() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local targets_path="$project_path/$CONFIGS" + local argument + + for argument in "$@" + do + targets_path="$targets_path/$argument" + done + + targets_path="$targets_path/$TARGETS" + + if [[ -f "$targets_path" ]] + then + cat "$targets_path" + fi +} + +project_arguments_expand_recursive() { + local project=$1 + shift + + local -a arguments + readarray -t arguments < <(project_action_helper arguments "$project" "$@") + + if [[ -z "${arguments[*]}" ]]; then + echo "$project" "$@" + + return 0 + fi + + local argument + + for argument in "${arguments[@]}"; do + project_arguments_expand_recursive "$project" "$@" "$argument" + done +} + +project_usage_actions() { + local project="$1" + shift + + printf '\n%s\n' 'Generic actions:' + + ( + for action in "${PROJECT_ACTIONS_GENERIC[@]}"; do + if function_check "$action"; then + printf '%s\n' " $action" + fi + done + ) + + if [[ "$#" -gt 0 ]]; then + printf '\n%s\n' 'Specific actions:' + + ( + for action in "$@"; do + printf '%s\n' " $action" + done + ) + fi +} + +project_usage_arguments() { + local project="$1" + shift + + printf '\n%s\n' 'Arguments:' + + project_usage_arguments_recursive "$project" ' ' "$@" +} + +project_usage_arguments_recursive() { + local project="$1" + shift + local spacing="$1" + shift + + local action_helper_arguments + local argument + + action_helper_arguments="$(project_action_helper 'arguments' "$project" "$@")" + + if [[ -n "$action_helper_arguments" ]]; then + for argument in $action_helper_arguments; do + printf '%s\n' "$spacing$argument" + project_usage_arguments_recursive "$project" " $spacing" "$@" "$argument" + done + fi +} + +project_download_git() { + local project=$1 + shift + local repository=$1 + shift + local urls=$1 + shift + + requirements "git" + + if ! git_project_check "$repository" + then + project_sources_directory_filled_error "$project" "$repository" "$@" + + git_project_clone "$repository" "$urls" + fi + + git_project_prepare "$project" "$repository" "$@" +} + +project_download_check_git() { + local project=$1 + shift + local repository=$1 + shift + + requirements "git" + + git_project_check "$repository" + git_project_prepare_check "$project" "$repository" "$@" +} + +project_download_archive() { + local project="$1" + shift + local archive_uri="$1" + shift + local archive_dsig_uri="$1" + + local archive="${archive_uri##*/}" + local compress_fmt="${archive##*.tar}" + + local directory_prefix="$root/$SOURCES" + local archive_path="$root/$SOURCES/$archive" + local sources_path="$root/$SOURCES/$project" + + if [[ "${compress_fmt#*.}" != "${ARCHIVE#*.}" ]]; then + ARCHIVE="tar$compress_fmt" + fi + + # TODO: Split this code block into separate functions + # Archive verification will be included at that point in time + if ! project_sources_directory_filled_check "$project"; then + download_wrapper "$directory_prefix" "$archive_uri" "$archive_dsig_uri" + archive_extract "$archive_path" "$directory_prefix" + + mv "${archive_path%.tar*}" "$sources_path" + fi + + project_sources_prepare "$project" +} + +project_download_check_archive() { + local project="$1" + local sources_path="$2" + + # TODO: Write the following function + #project_sources_archive_extract_check "$project" "$sources_path" +} + +project_extract() { + local project=$1 + shift + + local repository=$project + + if ! project_sources_directory_filled_check "$project" "$repository" "$@" + then + project_sources_archive_missing_error "$project" "$@" || return 1 + project_sources_archive_extract "$project" "$@" + fi +} + +project_extract_check() { + local project=$1 + shift + + local repository=$project + + project_sources_directory_filled_check "$project" "$repository" "$@" +} + +project_update_git() { + local project=$1 + shift + local repository=$1 + shift + + requirements "git" + + project_sources_directory_missing_empty_error "$project" "$repository" "$@" + + if git_project_check "$repository" + then + git_project_update "$project" "$repository" "$@" + else + if ! project_sources_archive_missing_check "$project" "$@" + then + project_sources_archive_update "$project" "$@" + fi + fi +} + +project_update_check_git() { + local project=$1 + shift + local repository=$1 + shift + + requirements "git" + + if git_project_check "$repository" + then + # Git repository should always be updated (even if upstream didn't progress). + # For instance, this is useful for testing new versions of patches without changing revision. + return 1 + else + project_sources_archive_missing_check "$project" "$@" + fi +} + +project_build_check() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local build_path=$(project_build_path "$project" "$@") + local source_file_path + local argument + local rule + local path + + if ! [[ -d $build_path ]] + then + return 1 + fi + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + configs_install_path="$project_path/$CONFIGS/$path/$INSTALL" + + if ! [[ -f "$configs_install_path" ]] + then + continue + fi + + while read -r rule + do + source=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\1/g") + source_path="$build_path/$source" + + # Source may contain a wildcard. + path_wildcard_expand "$source_path" | while read -r source_file_path + do + if ! [[ -f "$source_file_path" ]] && ! [[ -d "$source_file_path" ]] + then + return 1 + fi + done + done < "$configs_install_path" + done +} + +project_build_path() { + local project=$1 + shift + + local build_path="$root/$BUILD/$project" + local argument + + for argument in "$@" + do + build_path="$build_path-$argument" + done + + printf '%s\n' "$build_path" +} + +project_build_directory_missing_empty_error() { + local project=$1 + shift + local arguments="$*" + + local build_path=$(project_build_path "$project" "$@") + + if ! directory_filled_check "$build_path" + then + printf 1>&2 '%s\n' "Build directory for project $project (with ${arguments:-no argument}) missing or empty" + return 1 + else + return 0 + fi +} + +project_install() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local build_path=$(project_build_path "$project" "$@") + local install_path=$(project_install_path "$project" "$@") + local source_file_path + local argument + local rule + local path + + # Install built files first. + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + configs_install_path="$project_path/$CONFIGS/$path/$INSTALL" + + if ! [[ -f "$configs_install_path" ]] + then + continue + fi + + project_build_directory_missing_empty_error "$project" "$@" + + while read -r rule + do + source=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\1/g") + source_path="$build_path/$source" + + destination=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\2/g") + destination_path="$install_path/$destination" + destination_directory_path=$(dirname "$destination_path") + + mkdir -p "$destination_directory_path" + + # Source may contain a wildcard. + path_wildcard_expand "$source_path" | while read -r source_file_path + do + cp -rT "$source_file_path" "$destination_path" + done + done < "$configs_install_path" + done + + path="" + + # Install install files then. + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + install_install_path="$project_path/$INSTALL/$path/$INSTALL" + + if ! [[ -f "$install_install_path" ]] + then + continue + fi + + while read -r rule + do + source=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\1/g") + source_path="$project_path/$INSTALL/$path/$source" + + destination=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\2/g") + destination_path="$install_path/$destination" + destination_directory_path=$(dirname "$destination_path") + + mkdir -p "$destination_directory_path" + + # Source may contain a wildcard. + path_wildcard_expand "$source_path" | while read -r source_file_path + do + cp -rT "$source_file_path" "$destination_path" + done + done < "$install_install_path" + done +} + +project_install_check() { + local project=$1 + shift + + local project_path=$(project_path "$project") + local build_path=$(project_build_path "$project" "$@") + local install_path=$(project_install_path "$project" "$@") + local argument + local rule + local path + + if ! [[ -d $install_path ]] + then + return 1 + fi + + # Install built files first. + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + configs_install_path="$project_path/$CONFIGS/$path/$INSTALL" + + if ! [[ -f "$configs_install_path" ]] + then + continue + fi + + project_build_directory_missing_empty_error "$project" "$@" + + while read -r rule + do + destination=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\2/g") + destination_path="$install_path/$destination" + + if ! [[ -f "$destination_path" ]] && ! [[ -d "$destination_path" ]] + then + return 1 + fi + done < "$configs_install_path" + done + + path="" + + # Install install files then. + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + if [[ -z "$path" ]] + then + path="$argument" + else + path="$path/$argument" + fi + fi + + install_install_path="$project_path/$INSTALL/$path/$INSTALL" + + if ! [[ -f "$install_install_path" ]] + then + continue + fi + + while read -r rule + do + destination=$(printf '%s\n' "$rule" | sed "s/$INSTALL_REGEX/\\2/g") + destination_path="$install_path/$destination" + + if ! [[ -f "$destination_path" ]] && ! [[ -d "$destination_path" ]] + then + return 1 + fi + done < "$install_install_path" + done +} + +project_install_path() { + local project=$1 + shift + + local install_path="$root/$INSTALL/$project" + local argument + + for argument in "$@" + do + install_path="$install_path-$argument" + done + + printf '%s\n' "$install_path" +} + +project_install_directory_missing_empty_error() { + local project=$1 + shift + local arguments="$*" + + local install_path=$(project_install_path "$project" "$@") + + if ! directory_filled_check "$install_path" + then + printf 1>&2 '%s\n' "Install directory for project $project (with ${arguments:-no argument}) missing or empty" + return 1 + else + return 0 + fi +} + +project_release_path() { + local project=$1 + shift + local prefix=$1 + + local release_path="$root/$RELEASE/$prefix" + + # Special care for tools and systems, that depend on the host arch. + if [[ "$prefix" = "$SYSTEMS" ]] || [[ "$prefix" = "$TOOLS" ]] + then + local machine=$(uname -m) + + release_path="$release_path/$machine/$project" + else + release_path="$release_path/$project" + fi + + printf '%s\n' "$release_path" +} + +project_release_archive_path() { + local project=$1 + shift + local prefix=$1 + shift + + local release_path=$(project_release_path "$project" "$prefix") + local argument + local path="$project" + + for argument in "$@" + do + path="$path-$argument" + done + + local archive_path="$release_path/$path.$ARCHIVE" + + printf '%s\n' "$archive_path" +} + +project_release_rootfs_path() { + local project=$1 + shift + local prefix=$1 + shift + + local release_path=$(project_release_path "$project" "$prefix") + local argument + local path="$project" + + for argument in "$@" + do + path="$path-$argument" + done + + local rootfs_path="$release_path/$path.$ARCHIVE" + + printf '%s\n' "$rootfs_path" +} + +project_release_sources_archive_path() { + local project=$1 + shift + + local repository="$project" + local sources_path="$(project_sources_path "$project" "$repository" "$@")" + local archive_path="$root/$RELEASE/$SOURCES/$project/${sources_path##*/}.$ARCHIVE" + + printf '%s\n' "$archive_path" +} + +project_release_sources_archive_create() { + local project=$1 + shift + local arguments="$*" + + local repository=$project + local archive_path=$(project_release_sources_archive_path "$project" "$@") + local sources_path=$(project_sources_path "$project" "$repository" "$@") + + printf '%s\n' "Releasing sources archive for $project (with ${arguments:-no argument})" + + archive_create "$archive_path" "$sources_path" + file_verification_create "$archive_path" +} + +project_release_sources_archive_exists_check() { + local project=$1 + shift + + local archive_path=$(project_release_sources_archive_path "$project" "$@") + if [[ -z "$archive_path" ]] || ! [[ -f "$archive_path" ]] + then + return 1 + else + return 0 + fi +} + +project_release_sources_git() { + local project=$1 + shift + local repository=$1 + shift + + requirements "git" + + project_sources_directory_missing_empty_error "$project" "$repository" "$@" + + if git_project_check "$repository" + then + if ! git_project_release_check "$project" "$repository" "$@" + then + git_project_release "$project" "$repository" "$@" + fi + else + if ! project_release_sources_archive_exists_check "$project" "$@" + then + project_release_sources_archive_create "$project" "$@" + fi + fi +} + +project_release_check_sources_git() { + local project=$1 + shift + local repository=$1 + shift + + requirements "git" + + if git_project_check "$repository" + then + git_project_release_check "$project" "$repository" "$@" + else + project_release_sources_archive_exists_check "$project" "$@" + fi +} + +project_release_install() { + local project=$1 + shift + local prefix=$1 + shift + + local install_path=$(project_install_path "$project" "$@") + local release_path=$(project_release_path "$project" "$prefix") + local directory_path + local path + + project_install_directory_missing_empty_error "$project" "$@" + + local files=$(find "$install_path" -type f || true) + local file + + printf '%s\n' "$files" | while read -r file + do + path="$release_path/$file" + directory_path=$(dirname "$path") + + mkdir -p "$directory_path" + + cp "$install_path/$file" "$path" + file_verification_create "$path" + done +} + +project_release_install_check() { + local project=$1 + shift + local prefix=$1 + shift + + local install_path=$(project_install_path "$project" "$@") + local release_path=$(project_release_path "$project" "$prefix") + local path + + project_install_directory_missing_empty_error "$project" "$@" + + local files=$(find "$install_path" -type f || true) + local file + + printf '%s\n' "$files" | while read -r file + do + path="$release_path/$file" + + file_exists_check "$path" + done +} + +project_release_install_archive() { + local project=$1 + shift + local prefix=$1 + shift + + project_install_directory_missing_empty_error "$project" "$@" + + project_release_install_archive_create "$project" "$prefix" "$@" +} + +project_release_install_archive_check() { + local project=$1 + shift + + project_release_install_archive_exists_check "$project" "$@" +} + +project_release_install_archive_create() { + local project=$1 + shift + local prefix=$1 + shift + local arguments="$*" + + local install_path=$(project_install_path "$project" "$@") + local archive_path=$(project_release_archive_path "$project" "$prefix" "$@") + + printf '%s\n' "Releasing $prefix archive for $project (with ${arguments:-no argument})" + + archive_create "$archive_path" "$install_path" + file_verification_create "$archive_path" +} + +project_release_install_archive_exists_check() { + local project=$1 + shift + local prefix=$1 + shift + + local archive_path=$(project_release_archive_path "$project" "$prefix" "$@") + + file_exists_check "$archive_path" +} + +project_release_install_rootfs() { + local project=$1 + shift + local prefix=$1 + shift + + project_install_directory_missing_empty_error "$project" "$@" + + if ! project_release_install_rootfs_exists_check "$project" "$prefix" "$@" + then + project_release_install_rootfs_create "$project" "$prefix" "$@" + fi +} + +project_release_install_rootfs_check() { + local project=$1 + shift + + project_release_install_rootfs_exists_check "$project" "$@" +} + +project_release_install_rootfs_create() { + local project=$1 + shift + local prefix=$1 + shift + local arguments="$*" + + local install_path=$(project_install_path "$project" "$@") + local rootfs_path=$(project_release_rootfs_path "$project" "$prefix" "$@") + + printf '%s\n' "Releasing $prefix rootfs for $project (with ${arguments:-no argument})" + + rootfs_create "$rootfs_path" "$install_path" + file_verification_create "$rootfs_path" +} + +project_release_install_rootfs_exists_check() { + local project=$1 + shift + local prefix=$1 + shift + + local rootfs_path=$(project_release_rootfs_path "$project" "$prefix" "$@") + + file_exists_check "$rootfs_path" +} + +project_clean() { + local project=$1 + shift + + project_clean_build "$project" "$@" + project_clean_install "$project" "$@" + project_clean_release "$project" "$@" +} + +project_clean_build() { + local project=$1 + shift + + local build_path=$(project_build_path "$project" "$@") + + rm -rf "$build_path" +} + +project_clean_install() { + local project=$1 + shift + + local install_path=$(project_install_path "$project" "$@") + + rm -rf "$install_path" +} + +project_clean_release() { + local project=$1 + shift + + local prefix + + for prefix in "$SOURCES" "$SYSTEMS" "$IMAGES" "$TOOLS" "$DOCS" + do + local release_path=$(project_release_path "$project" "$prefix") + + rm -rf "$release_path" + done +} + +project_clean_rootfs() { + local project=$1 + shift + + project_clean_build "$project" "$@" + project_clean_rootfs_install "$project" "$@" + project_clean_release "$project" "$@" + +} + +project_clean_rootfs_install() { + local project=$1 + shift + + local install_path=$(project_install_path "$project" "$@") + + execute_root rm -rf "$install_path" + +} + +project_file_path() { + local project=$1 + shift + local directory=$1 + shift + local file=$1 + shift + + local project_path=$(project_path "$project") + local path="$project_path/$directory" + local argument + local file_path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + if ! [[ -f "$path/$file" ]] + then + continue + fi + + file_path="$path/$file" + + break + done + + if [[ -z "$file_path" ]] + then + return 1 + fi + + printf '%s\n' "$file_path" +} + +project_file_test() { + local file_path=$(project_file_path "$@") + + test -f "$file_path" +} + +project_file_contents() { + local file_path=$(project_file_path "$@") + + if [[ -f "$file_path" ]] + then + cat "$file_path" + fi +} + +project_file_contents_herit() { + local project=$1 + shift + local directory=$1 + shift + local file=$1 + shift + + local project_path=$(project_path "$project") + local path="$project_path/$directory" + local argument + local file_path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + file_path="$path/$file" + + if ! [[ -f "$file_path" ]] + then + continue + fi + + cat "$file_path" + done +} diff --git a/i18n/fr_FR/libs/tool b/i18n/fr_FR/libs/tool new file mode 100755 index 00000000..f4e8a783 --- /dev/null +++ b/i18n/fr_FR/libs/tool @@ -0,0 +1,387 @@ +#!/usr/bin/env bash + +# Copyright (C) 2016 Paul Kocialkowski <contact@paulk.fr> +# +# 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 3 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, see <http://www.gnu.org/licenses/>. + +TOOL_ACTIONS_GENERIC=(usage update execute) +TOOL_ACTIONS_GENERIC_IGNORE_CHECK=(usage update) +TOOL_ACTIONS_HELPERS=(arguments) + +tool_include() { + local tool=$1 + + local tool_path=$(tool_path "$tool") + + unset -f "${TOOL_ACTIONS[@]}" + + source "$tool_path/$tool" + + tool_helper_include "$tool" +} + +tool_helper_include() { + local tool=$1 + + local tool_path=$(tool_path "$tool") + local include="$tool_path/$tool-helper" + + if [[ -f "$include" ]] + then + source "$include" + fi +} + +tool_check() { + local tool="${1##*/}" + + local tool_path="$(tool_path "$tool")" + + if ! [[ -f "$tool_path/$tool" ]]; then + return 1 + fi +} + +tool_function_check() { + local tool=$1 + local function=$2 + + tool_include "$tool" + + if ! function_check "$function" + then + return 1 + fi + + return 0 +} + +tool_action() { + local action=$1 + shift + local tool=$1 + shift + local arguments=$@ + + ( + set +e + + if ! tool_check "$tool" + then + printf 1>&2 '%s\n' "Tool $tool check failed" + return 1 + fi + + tool_action_check "$action" "$tool" "$@" + + if [[ $? -eq 0 ]] + then + return 0 + fi + + tool_include "$tool" + + if ! function_check "$action" + then + return 0 + fi + + printf '%s\n\n' "Tool $tool $action (with ${arguments:-no argument})" + + ( + set -e + + "$action" "$@" + ) + + if [[ $? -ne 0 ]] + then + printf 1>&2 '\n%s\n' "Tool $tool $action (with ${arguments:-no argument}) failed" + + return 1 + else + printf '\n%s\n' "Tool $tool $action (with ${arguments:-no argument}) completed" + fi + ) +} + +tool_action_check() { + local action=$1 + shift + local tool=$1 + shift + + ( + set +e + + if ! tool_check "$tool" + then + printf 1>&2 '%s\n' "Tool $tool check failed" + return 1 + fi + + tool_include "$tool" + + if ! function_check "$action""_check" + then + return 1 + fi + + for tool_force in $TOOLS_FORCE + do + if [[ "$tool_force" = "$tool" ]] + then + return 1 + fi + done + + ( + set -e + "$action""_check" "$@" + ) + ) +} + +tool_action_helper() { + local helper=$1 + shift + local tool=$1 + shift + + ( + set +e + + if ! tool_check "$tool" + then + printf 1>&2 '%s\n' "Tool $tool check failed" + return 1 + fi + + tool_include "$tool" + + if ! function_check "$helper" + then + return 0 + fi + + ( + set -e + "$helper" "$@" + ) + ) +} + +tool_action_arguments_recursive() { + local action=$1 + shift + local tool=$1 + shift + + local action_helper_arguments=$(tool_action_helper "arguments" "$tool" "$@") + local argument + + if [[ $? -ne 0 ]] || [[ -z "$action_helper_arguments" ]] + then + tool_action "$action" "$tool" "$@" + else + printf '%s\n' "$action_helper_arguments" | while read argument + do + tool_action_arguments_recursive "$action" "$tool" "$@" "$argument" + done + fi +} + +tool_arguments_targets() { + local tool="$1" + shift + + local tool_path="$(tool_path "$tool")" + local targets_path="$tool_path/$CONFIGS" + local argument + + for argument in "$@"; do + targets_path="$targets_path/$argument" + done + + targets_path="$targets_path/$TARGETS" + + if [[ -f "$targets_path" ]]; then + cat "$targets_path" + fi +} + +tool_path() { + local tool=$1 + + local tool_path="$root/$TOOLS/$tool" + + printf '%s\n' "$tool_path" +} + +tool_sources_path() { + local tool=$1 + shift + + local path="$root/$TOOLS/$tool/$SOURCES" + local argument + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + if directory_filled_check "$path" + then + printf '%s\n' "$path" + return + fi + done +} + +tool_usage_actions() { + local tool=$1 + shift + + printf '\n%s\n' 'Generic actions:' + + for action in "${TOOL_ACTIONS_GENERIC[@]}" + do + if function_check "$action" + then + printf '%s\n' " $action" + fi + done + + if [[ $# -gt 0 ]] + then + printf '\n%s\n' 'Specific actions:' + + for action in "$@" + do + printf '%s\n' " $action" + done + fi +} + +tool_usage_arguments() { + local tool=$1 + shift + + printf '\n%s\n' 'Arguments:' + + tool_usage_arguments_recursive "$tool" " " "$@" +} + +tool_usage_arguments_recursive() { + local tool=$1 + shift + local spacing=$1 + shift + + local action_helper_arguments=$(tool_action_helper "arguments" "$tool" "$@") + local argument + + if [[ -n "$action_helper_arguments" ]] + then + printf '%s\n' "$action_helper_arguments" | while read argument + do + printf '%s\n' "$spacing$argument" + tool_usage_arguments_recursive "$tool" " $spacing" "$@" "$argument" + done + fi +} + +tool_file_path() { + local tool=$1 + shift + local directory=$1 + shift + local file=$1 + shift + + local tool_path=$(tool_path "$tool") + local path="$tool_path/$directory" + local argument + local file_path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + if ! [[ -f "$path/$file" ]] + then + continue + fi + + file_path="$path/$file" + done + + if [[ -z "$file_path" ]] + then + return 1 + fi + + printf '%s\n' "$file_path" +} + +tool_file_test() { + local file_path=$(tool_file_path "$@") + + test -f "$file_path" +} + +tool_file_contents() { + local file_path=$(tool_file_path "$@") + + if [[ -f "$file_path" ]] + then + cat "$file_path" + fi +} + +tool_file_contents_herit() { + local tool=$1 + shift + local directory=$1 + shift + local file=$1 + shift + + local tool_path=$(tool_path "$tool") + local path="$tool_path/$directory" + local argument + local file_path + + for argument in "" "$@" + do + if [[ -n "$argument" ]] + then + path="$path/$argument" + fi + + file_path="$path/$file" + + if ! [[ -f "$file_path" ]] + then + continue + fi + + cat "$file_path" + done +} |