mirror of
https://dev.iopsys.eu/feed/iopsys.git
synced 2025-12-10 07:44:50 +01:00
517 lines
15 KiB
Bash
Executable file
517 lines
15 KiB
Bash
Executable file
#!/bin/bash
|
|
|
|
function genconfig {
|
|
export CLEAN=0
|
|
export DIRTY="--dirty"
|
|
export IMPORT=1
|
|
export SRCTREEOVERR=0
|
|
export FILEDIR="files/"
|
|
CURRENT_CONFIG_FILE=".current_config_file"
|
|
export CONFIGPATH="package/feeds/iopsys/iop"
|
|
CUSTPATH="customerconfigs"
|
|
export CUSTCONF="customerconfigs/customers"
|
|
export VERBOSE=0
|
|
export DEVELOPER=0
|
|
target="bogus"
|
|
target_config_path=""
|
|
brcmbca_feed="target/linux/feeds/brcmbca"
|
|
airoha_feed="target/linux/feeds/airoha"
|
|
x86_feed="target/linux/feeds/x86"
|
|
armsr_feed="target/linux/feeds/armsr"
|
|
mediatek_feed="target/linux/feeds/mediatek"
|
|
qualcomm_ipq95xx_feed="target/linux/feeds/ipq95xx"
|
|
qualcomm_ipq53xx_feed="target/linux/feeds/ipq53xx"
|
|
|
|
Red='\033[0;31m' # Red
|
|
Color_Off='\033[0m' # Text Reset
|
|
Yellow='\033[0;33m' # Yellow
|
|
|
|
function find_last {
|
|
egrep "^[ #]*${1}[ =]" $2 | tail -n1
|
|
}
|
|
|
|
function is_new {
|
|
for opt in $conf_warned
|
|
do
|
|
if [ "$opt" == "$1" ]
|
|
then
|
|
return 1
|
|
fi
|
|
done
|
|
# option not found return true
|
|
return 0
|
|
}
|
|
|
|
function verify_config {
|
|
local conf_opt
|
|
local conf_org
|
|
local conf_new
|
|
|
|
while read -r line
|
|
do
|
|
conf_opt=$(echo $line | grep "^[ #]*CONFIG_" | sed 's|.*\(CONFIG_[^ =]*\)[ =].*|\1|')
|
|
if [ -n "${conf_opt}" ]
|
|
then
|
|
conf_org=$(find_last ${conf_opt} .genconfig.config)
|
|
conf_new=$(find_last ${conf_opt} .config)
|
|
if [ "$conf_org" != "$conf_new" ]
|
|
then
|
|
if is_new $conf_opt
|
|
then
|
|
echo -e "config option [${Red}$conf_opt${Color_Off}] is not set correctly in .config"
|
|
echo -e "got value [${Yellow}$conf_new${Color_Off}] but wanted [${Yellow}$conf_org${Color_Off}]"
|
|
echo "This is a real problem somebody needs to investigate"
|
|
echo ""
|
|
conf_warned="$conf_warned $conf_opt"
|
|
fi
|
|
else
|
|
true
|
|
# for debug to see all options
|
|
#echo -e "wanted [$conf_org] got [$conf_new]"
|
|
fi
|
|
fi
|
|
done < .genconfig.config
|
|
}
|
|
|
|
# Takes a board name and returns the target name in global var $target
|
|
set_target() {
|
|
local profile=$1
|
|
|
|
[ -n "$profile" ] || return
|
|
|
|
if [ -n "$TARGET" -a -d "./target/linux/feeds/$TARGET" ]; then
|
|
local targetpath="./target/linux/feeds/$TARGET"
|
|
local profiles=
|
|
local pfound=0
|
|
|
|
if [ -e "$targetpath/genconfig" ]; then
|
|
profiles=$(cd $targetpath; ./genconfig)
|
|
|
|
for p in $profiles; do
|
|
if [ $p == $profile ]; then
|
|
pfound=1
|
|
break
|
|
fi
|
|
done
|
|
fi
|
|
|
|
if [ $pfound -eq 1 ]; then
|
|
target="$(echo $TARGET | tr '-' '_')"
|
|
target_config_path="$targetpath/config"
|
|
fi
|
|
|
|
return
|
|
fi
|
|
|
|
[ -e $brcmbca_feed/genconfig ] &&
|
|
brcmbca=$(cd $brcmbca_feed; ./genconfig)
|
|
[ -e $airoha_feed/genconfig ] &&
|
|
airoha=$(cd $airoha_feed; ./genconfig)
|
|
[ -e $x86_feed/genconfig ] &&
|
|
x86=$(cd $x86_feed; ./genconfig)
|
|
[ -e $armsr_feed/genconfig ] &&
|
|
armsr=$(cd $armsr_feed; ./genconfig)
|
|
[ -e $mediatek_feed/genconfig ] &&
|
|
mediatek=$(cd $mediatek_feed; ./genconfig)
|
|
[ -e $qualcomm_ipq95xx_feed/genconfig ] &&
|
|
ipq95xx=$(cd $qualcomm_ipq95xx_feed; ./genconfig)
|
|
[ -e $qualcomm_ipq53xx_feed/genconfig ] &&
|
|
ipq53xx=$(cd $qualcomm_ipq53xx_feed; ./genconfig)
|
|
|
|
if [ "$profile" == "LIST" ]; then
|
|
for list in brcmbca airoha x86 armsr mediatek ipq95xx ipq53xx; do
|
|
echo "$list based boards:"
|
|
a=$(echo "${!list}" | sort)
|
|
for b in $a; do
|
|
echo -e "\t$b"
|
|
done
|
|
done
|
|
return
|
|
fi
|
|
|
|
for p in $airoha; do
|
|
if [ $p == $profile ]; then
|
|
target="airoha"
|
|
target_config_path="$airoha_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $x86; do
|
|
if [ $p == $profile ]; then
|
|
target="x86"
|
|
target_config_path="$x86_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $armsr; do
|
|
if [ $p == $profile ]; then
|
|
target="armsr"
|
|
target_config_path="$armsr_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $mediatek; do
|
|
if [ $p == $profile ]; then
|
|
target="mediatek"
|
|
target_config_path="$mediatek_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $ipq95xx; do
|
|
if [ $p == $profile ]; then
|
|
target="ipq95xx"
|
|
target_config_path="$qualcomm_ipq95xx_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $ipq53xx; do
|
|
if [ $p == $profile ]; then
|
|
target="ipq53xx"
|
|
target_config_path="$qualcomm_ipq53xx_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
|
|
for p in $brcmbca; do
|
|
if [ $p == $profile ]; then
|
|
target="brcmbca"
|
|
target_config_path="$brcmbca_feed/config"
|
|
return
|
|
fi
|
|
done
|
|
}
|
|
|
|
git remote -v | grep -qE '(git@|ssh://)' && {
|
|
DEVELOPER=1
|
|
}
|
|
|
|
v() {
|
|
[ "$VERBOSE" -ge 1 ] && echo "$@"
|
|
}
|
|
|
|
usage() {
|
|
echo
|
|
echo 1>&2 "Usage: $0 [ OPTIONS ] < Board_Type > [ Customer [customer2 ]...]"
|
|
echo
|
|
echo -e " -c|--clean\t\tRemove all files under ./files and import from config "
|
|
echo -e " -D|--no-dirty\t\tIgnore dirty tree"
|
|
echo -e " -v|--verbose\t\tVerbose"
|
|
echo -e " -n|--no-update\tDo NOT! Update customer config before applying"
|
|
echo -e " -t|--target\t\tExplicitly specify the linux target to build the board profile from"
|
|
echo -e " -s|--override\t\tEnable 'Package source tree override'"
|
|
echo -e " -S|--brcmsingle\tForce build of bcmkernel to use only one thread"
|
|
echo -e " -h|--help\t\tShow this message"
|
|
echo -e " -l|--list [customer]\tList all Customers or all boards for one customer"
|
|
echo -e " -a|--list-all\t\tList all Customers and their board types"
|
|
echo -e " -b|--boards\t\tList all board types"
|
|
echo
|
|
echo "Example ./iop genconfig eg400 OPERATORX"
|
|
echo "(if no customerconfig is chosen, iopsys config will be used)"
|
|
echo
|
|
exit 0
|
|
}
|
|
|
|
list_customers()
|
|
{
|
|
local ALL="$1"
|
|
local CUSTOMER="$2"
|
|
if [ "$CUSTOMER" -a -d "$CUSTCONF/$CUSTOMER" ]; then
|
|
local boards="$(ls -1 "$CUSTCONF/$CUSTOMER" | grep -v common)"
|
|
if [ "$boards" ]; then
|
|
echo "$CUSTOMER has following boards:"
|
|
for board in $boards; do
|
|
echo -e "\t$board"
|
|
done
|
|
else
|
|
echo "No boards found for $CUSTOMER"
|
|
fi
|
|
elif [ "$CUSTOMER" ]; then
|
|
echo "No customer called $CUSTOMER"
|
|
exit 1
|
|
elif [ -d $CUSTCONF ]; then
|
|
local customers="$(ls -1 $CUSTCONF)"
|
|
if [ "$customers" -a "$ALL" == 1 ]; then
|
|
for customer in $customers; do
|
|
echo $customer
|
|
local boards="$(ls -1 $CUSTCONF/$customer | grep -v common)"
|
|
if [ "$boards" ]; then
|
|
for board in $boards; do
|
|
echo -e "\t$board"
|
|
done
|
|
else
|
|
echo "has no boards"
|
|
fi
|
|
done
|
|
elif [ "$customers" ]; then
|
|
echo -e "$customers"
|
|
else
|
|
echo "no customers found"
|
|
fi
|
|
else
|
|
echo "No $CUSTCONF folder found"
|
|
fi
|
|
exit 0
|
|
}
|
|
|
|
|
|
generate_config()
|
|
{
|
|
DIFFFILE="$1"
|
|
MASTERFILE="$2"
|
|
while read p; do
|
|
v "$p"
|
|
sed -r -i "$p" $MASTERFILE
|
|
done < $DIFFFILE
|
|
}
|
|
|
|
setup_dirs()
|
|
{
|
|
git remote -v | grep -q http || {
|
|
CUSTBRANCH="$(git rev-parse --abbrev-ref HEAD)"
|
|
if git ls-remote $CUSTREPO -q 2>/dev/null; then
|
|
if [ ! -d "$CUSTPATH" ]; then
|
|
echo "Cloning $CUSTBRANCH branch of $CUSTREPO"
|
|
git clone -b "$CUSTBRANCH" "$CUSTREPO" "$CUSTPATH" 2>/dev/null || {
|
|
DEFBRANCH="$(git remote show $CUSTREPO | grep 'HEAD branch' | cut -d' ' -f5)"
|
|
echo "$CUSTBRANCH branch is not found, cloning $DEFBRANCH branch of $CUSTREPO"
|
|
git clone "$CUSTREPO" "$CUSTPATH"
|
|
}
|
|
elif [ $IMPORT -eq 1 ]; then
|
|
cd $CUSTPATH
|
|
echo "Checking out $CUSTBRANCH branch in $CUSTPATH"
|
|
git checkout "$CUSTBRANCH" 2>/dev/null || {
|
|
DEFBRANCH="$(git symbolic-ref refs/remotes/origin/HEAD | cut -d '/' -f4)"
|
|
echo "Checking out $CUSTBRANCH branch has failed, using $DEFBRANCH branch in $CUSTPATH"
|
|
}
|
|
v "git pull"
|
|
git pull
|
|
cd - >/dev/null #go back
|
|
fi
|
|
else
|
|
echo "You do not have access to $CUSTREPO"
|
|
fi
|
|
}
|
|
|
|
if [ ! -d "$FILEDIR" ]; then
|
|
mkdir -p $FILEDIR
|
|
elif [ -d "$FILEDIR" -a $CLEAN -eq 1 ]; then
|
|
v "rm -rf $FILEDIR*"
|
|
rm -rf $FILEDIR*
|
|
fi
|
|
}
|
|
|
|
get_subtarget_for_device() {
|
|
readonly target="$1"
|
|
readonly device="$2"
|
|
readonly targetinfo_file="tmp/info/.targetinfo-feeds_$target"
|
|
readonly target_profile_line="Target-Profile: DEVICE_$device"
|
|
# We want to know after which Target: $target/$subtarget line
|
|
# our $target_profile_line appears
|
|
# This is a crude way to "parse" the file using shell 🤯
|
|
# 1. grep for both lines with line number output
|
|
# 2. grep again to determine the device profile line that we looked for
|
|
# but output one context line before as well to determine corresponding subtarget line
|
|
# 4. Use head and sed to extract the subtarget
|
|
grep "^Target: $target/\|^$target_profile_line" "$targetinfo_file" \
|
|
| grep -E -B1 "^$target_profile_line" \
|
|
| head -n1 \
|
|
| sed -E "s|^Target: $target/||"
|
|
}
|
|
|
|
create_and_copy_files()
|
|
{
|
|
local BOARDTYPE=$1
|
|
shift
|
|
local CUSTOMERS=$@
|
|
|
|
# Validate seleced board and customers
|
|
set_target $BOARDTYPE
|
|
if [ $target == "bogus" ]; then
|
|
echo "Hardware profile does not exist"
|
|
exit 1
|
|
elif [ -n "$CUSTOMERS" ]; then
|
|
for CUSTOMER in $CUSTOMERS; do
|
|
if [ ! -d "$CUSTCONF/$CUSTOMER/" ]; then
|
|
echo "Customer profile for '$CUSTOMER' does not exist"
|
|
exit 1
|
|
elif [ ! -d "$CUSTCONF/$CUSTOMER/$BOARDTYPE/" ]; then
|
|
echo "'$BOARDTYPE' board profile does not exist for customer '$CUSTOMER'"
|
|
if [ -f "$CUSTCONF/$CUSTOMER/common/common.diff" ]; then
|
|
echo "Common profile configuration will be used"
|
|
else
|
|
exit 1
|
|
fi
|
|
fi
|
|
done
|
|
fi
|
|
|
|
# Generate base config
|
|
rm -f .config
|
|
v "Config $BOARDTYPE selected"
|
|
v "cp $CONFIGPATH/config .config"
|
|
cp $CONFIGPATH/config .config
|
|
|
|
if [ -f $target_config_path/config ]; then
|
|
cat $target_config_path/config >> .config
|
|
echo "" >> .config
|
|
fi
|
|
if [ -f $target_config_path/$BOARDTYPE/config ]; then
|
|
cat $target_config_path/$BOARDTYPE/config >> .config
|
|
echo "" >> .config
|
|
fi
|
|
# hack to support custom-devices until we have deprecated this genconfig-script...
|
|
if [ -f "feeds/custom_devices/devices/$target/config/$BOARDTYPE/config" ]; then
|
|
cat "feeds/custom_devices/devices/$target/config/$BOARDTYPE/config" >> .config
|
|
echo "" >> .config
|
|
fi
|
|
|
|
# Special handling for targets which use TARGET_DEVICES
|
|
case "$target" in
|
|
airoha | mediatek | brcmbca | ipq95xx | ipq53xx)
|
|
# This assumes the device name to be unique within one target,
|
|
# which is a fair assumption to make.
|
|
local subtarget="$(get_subtarget_for_device "${target/_/-}" "$BOARDTYPE")"
|
|
if [ -z "$subtarget" ]; then
|
|
echo "Error determining subtarget for $target / ${BOARDTYPE}"
|
|
return 1
|
|
fi
|
|
echo "CONFIG_TARGET_${target}=y" >> .config
|
|
echo "CONFIG_TARGET_${target}_${subtarget}=y" >> .config
|
|
echo "CONFIG_TARGET_DEVICE_${target}_${subtarget}_DEVICE_${BOARDTYPE}=y" >> .config
|
|
;;
|
|
*)
|
|
echo "CONFIG_TARGET_${target}=y" >> .config
|
|
echo "CONFIG_TARGET_${target}_${BOARDTYPE}=y" >> .config
|
|
;;
|
|
esac
|
|
|
|
echo "$CUSTOMERS $BOARDTYPE" > $CURRENT_CONFIG_FILE
|
|
|
|
# Add customerconfig diff if a customer is selected
|
|
if [ -n "$CUSTOMERS" ]; then
|
|
for CUSTOMER in $CUSTOMERS; do
|
|
if [ -d "$CUSTCONF/$CUSTOMER/common/fs" ]; then
|
|
v "cp -ar $CUSTCONF/$CUSTOMER/common/fs/* $FILEDIR"
|
|
cp -ar $CUSTCONF/$CUSTOMER/common/fs/* $FILEDIR
|
|
fi
|
|
if [ -d "$CUSTCONF/$CUSTOMER/$BOARDTYPE/fs" ]; then
|
|
v "cp -ar $CUSTCONF/$CUSTOMER/$BOARDTYPE/fs/* $FILEDIR"
|
|
cp -ar $CUSTCONF/$CUSTOMER/$BOARDTYPE/fs/* $FILEDIR
|
|
fi
|
|
if [ -e "$CUSTCONF/$CUSTOMER/common/common.diff" ]; then
|
|
v "Apply $CUSTCONF/$CUSTOMER/common/common.diff"
|
|
cat $CUSTCONF/$CUSTOMER/common/common.diff >> .config
|
|
echo "" >> .config
|
|
fi
|
|
if [ -e "$CUSTCONF/$CUSTOMER/$BOARDTYPE/$BOARDTYPE.diff" ]; then
|
|
v "Apply $CUSTCONF/$CUSTOMER/$BOARDTYPE/$BOARDTYPE.diff"
|
|
cat $CUSTCONF/$CUSTOMER/$BOARDTYPE/$BOARDTYPE.diff >> .config
|
|
echo "" >> .config
|
|
fi
|
|
done
|
|
fi
|
|
|
|
# Set target version
|
|
local git_version
|
|
if ! git_version="$(git describe --always $DIRTY --tags --match '[0-9].*.*' --match '[0-9][0-9].*.*')"; then
|
|
echo "ERROR: Failed getting version via git describe, exiting." >&2
|
|
return 1
|
|
fi
|
|
local version="${git_version,,}${CUSTOMERS:+-${CUSTOMERS// /}}"
|
|
local version_lower="${version,,}"
|
|
echo "CONFIG_TARGET_VERSION=\"${version_lower}\"" >> .config
|
|
echo "CONFIG_VERSION_CODE=\"${version_lower}\"" >> .config
|
|
echo "CONFIG_VERSION_PRODUCT=\"$BOARDTYPE"\" >> .config
|
|
|
|
# Enable Package source tree override if selected
|
|
[ $SRCTREEOVERR -eq 1 ] && echo CONFIG_SRC_TREE_OVERRIDE=y >> .config
|
|
|
|
# developer mode selected ?
|
|
echo "CONFIG_DEVEL=y" >>.config
|
|
if [ $DEVELOPER -eq 1 ]; then
|
|
# rewrite url to clone with ssh instead of http
|
|
echo "CONFIG_GITMIRROR_REWRITE=y" >>.config
|
|
else
|
|
echo "# CONFIG_GITMIRROR_REWRITE is not set" >>.config
|
|
fi
|
|
|
|
if [ -n "$BRCM_MAX_JOBS" ]
|
|
then
|
|
echo "CONFIG_BRCM_MAX_JOBS=\"1\"" >>.config
|
|
fi
|
|
|
|
# Force regeneration of kernel Makefile
|
|
# Needed to disable kmods for iopsys-brcm targets
|
|
touch package/kernel/linux/Makefile
|
|
|
|
# we need to signal to bradcom SDK that we have changed the board id
|
|
# currently boardparms.c and boardparms_voice.c is the only place that is depending on boardid name
|
|
# so just touch that file.
|
|
[ -d ./build_dir ] && find build_dir/ -name "boardparms*c" -print0 2>/dev/null | xargs -0 touch 2>/dev/null
|
|
|
|
# Store generated config
|
|
cp .config .genconfig.config
|
|
|
|
# Set default values based on selected parameters
|
|
v "$(make defconfig 2>&1)"
|
|
|
|
echo Set version to $(grep -w CONFIG_TARGET_VERSION .config | cut -d'=' -f2 | tr -d '"')
|
|
|
|
# Clean base-file package to force rebuild when changing profile
|
|
v "$(make package/base-files/clean 2>&1)"
|
|
|
|
verify_config
|
|
}
|
|
|
|
####### main #####
|
|
if [ ! -e tmp/.iop_bootstrap ]; then
|
|
echo "You have not installed feeds. Running genconfig in this state would create a non functional configuration."
|
|
echo "Run: iop feeds_update"
|
|
exit 1
|
|
fi
|
|
|
|
if [ $# -eq 0 ]; then
|
|
echo Current profile:
|
|
cat $CURRENT_CONFIG_FILE
|
|
echo "Try ./iop genconfig -h' to get instructions if you want to change current config"
|
|
exit 0
|
|
else
|
|
while [ -n "$1" ]; do
|
|
case "$1" in
|
|
|
|
-c|--clean) export CLEAN=1;;
|
|
-D|--no-dirty) export DIRTY="";;
|
|
-n|--no-update) export IMPORT=0;;
|
|
-v|--verbose) export VERBOSE="$(($VERBOSE + 1))";;
|
|
-t|--target) export TARGET="$2"; shift;;
|
|
-p|--profile) export PROFILE="$2"; shift;;
|
|
-r|--repo) export CUSTREPO="$2"; shift;;
|
|
-s|--override) export SRCTREEOVERR=1;;
|
|
-S|--brcmsingel) export BRCM_MAX_JOBS=1;;
|
|
-h|--help) usage;;
|
|
-l|--list) list_customers 0 $2;;
|
|
-a|--list-all)list_customers 1;;
|
|
-b|--boards)set_target LIST;exit 0;;
|
|
-*)
|
|
echo "Invalid option: $1 "
|
|
echo "Try -h or --help for more information."
|
|
exit 1
|
|
;;
|
|
*) break;;
|
|
esac
|
|
shift;
|
|
done
|
|
|
|
CUSTREPO="${CUSTREPO:-git@dev.iopsys.eu:consumer/iopsys.git}"
|
|
|
|
setup_dirs
|
|
create_and_copy_files "$@" || exit 1
|
|
fi
|
|
}
|
|
|
|
register_command "genconfig" "Generate configuration for board and customer"
|