diff --git a/build/tools/mk_sdk_repo_xml.sh b/build/tools/mk_sdk_repo_xml.sh new file mode 100755 index 000000000..f7bbec19f --- /dev/null +++ b/build/tools/mk_sdk_repo_xml.sh @@ -0,0 +1,254 @@ +#!/bin/bash +# +# Generates an SDK Repository XML based on the input files. + +set -e + +PROG_DIR=$(dirname $0) + +TYPES="tool platform-tool platform sample doc add-on" +OSES="linux macosx windows any linux-x86 darwin" + +TMP_DIR=$(mktemp -d -t sdkrepo.tmp.XXXXXXXX) +trap "rm -rf $TMP_DIR" EXIT + +function error() { + echo "*** ERROR: " $@ + usage +} + +function usage() { + cat < "$OUT" < + +EOFH + +# check_enum value value1 value2 value3... +# returns valueN if matched or nothing. +function check_enum() { + local VALUE="$1" + local i + shift + for i in "$@"; do + if [[ "$i" == "$VALUE" ]]; then + echo "$VALUE" + break; + fi + done +} + +# Parse all archives. + +ATTRS=( + # for repository packages + Pkg.Revision revision + Pkg.Desc description + Platform.Version version + AndroidVersion.ApiLevel api-level + AndroidVersion.CodeName codename + Platform.MinToolsRev min-tools-rev + Platform.MinPlatformToolsRev min-platform-tools-rev + Extra.Path path + Extra.Vendor vendor + Extra.MinApiLevel min-api-level + Sample.MinApiLevel min-api-level + # for addon packages + vendor vendor + name name + description description + api api-level + version revision + revision revision +) + +function parse_attributes() { + local PROPS="$1" + shift + local RESULT="" + local VALUE + + while [[ "$1" ]]; do + # Parse the property, if present. Any space is replaced by @ + VALUE=$( grep "^$1=" "$PROPS" | cut -d = -f 2 | tr ' ' '@' | tr -d '\r' ) + if [[ -n "$VALUE" ]]; then + RESULT="$RESULT $2 $VALUE" + fi + shift + shift + done + + echo "$RESULT" +} + +function output_attributes() { + local OUT="$1" + shift + local KEY VALUE + + while [[ "$1" ]]; do + KEY="$1" + VALUE="${2//@/ }" + echo " $VALUE" >> "$OUT" + shift + shift + done +} + +while [[ -n "$1" ]]; do + # Process archives. + # First we expect a type. For conveniency the type can be plural. + TYPE=$(check_enum "${1%%s}" $TYPES) + [[ -z $TYPE ]] && error "Unknown archive type '$1'." + shift + + MAP="" + FIRST="1" + LIBS_XML="" + + OS=$(check_enum "$1" $OSES) + while [[ $OS ]]; do + shift + [[ $OS == "linux-x86" ]] && OS=linux + [[ $OS == "darwin" ]] && OS=macosx + + SRC="$1" + DST="$1" + if [[ "${SRC/:/}" != "$SRC" ]]; then + DST="${SRC/*:/}" + SRC="${SRC/:*/}" + fi + [[ ! -f "$SRC" ]] && error "Missing file for archive $TYPE/$OS: $SRC" + shift + + # Depending on the archive type, we need a number of attributes + # from the source.properties or the manifest.ini. We'll take + # these attributes from the first zip found. + # + # What we need vs. which package uses it: + # - description all + # - revision all + # - version platform + # - api-level platform sample doc add-on + # - codename platform sample doc add-on + # - min-tools-rev platform sample + # - min-platform-tools-rev tool + # - min-api-level extra + # - vendor extra add-on + # - path extra + # + # We don't actually validate here. + # Just take whatever is defined and put it in the XML. + # XML validation against the schema will be done at the end. + + if [[ $FIRST ]]; then + FIRST="" + + if unzip -t "$SRC" | grep -qs "source.properties" ; then + # Extract Source Properties + # unzip: -j=flat (no dirs), -q=quiet, -o=overwrite, -d=dest dir + unzip -j -q -o -d "$TMP_DIR" "$SRC" "*/source.properties" + PROPS="$TMP_DIR/source.properties" + + elif unzip -t "$SRC" | grep -qs "manifest.ini" ; then + unzip -j -q -o -d "$TMP_DIR" "$SRC" "*/manifest.ini" + PROPS="$TMP_DIR/manifest.ini" + + # Parse the libs for an addon and generate the node + # libraries is a semi-colon separated list + LIBS=$(parse_attributes "$PROPS" "libraries") + LIBS_XML=" " + for LIB in ${LIBS//;/ }; do + LIBS_XML="$LIBS_XML + $LIB" + done + LIBS_XML="$LIBS_XML + " + + else + error "Failed to find source.properties or manifest.ini in $SRC" + fi + + [[ ! -f $PROPS ]] && error "Failed to extract $PROPS from $SRC" + MAP=$(parse_attributes "$PROPS" ${ATTRS[@]}) + + # Time to generate the XML for the package + echo " " >> "$OUT" + output_attributes "$OUT" $MAP + [[ -n "$LIBS_XML" ]] && echo "$LIBS_XML" >> "$OUT" + echo " " >> "$OUT" + fi + + # Generate archive info + echo "## Add $TYPE/$OS archive $SRC" + if [[ $( uname ) == "Darwin" ]]; then + SIZE=$( stat -f %z "$SRC" ) + else + SIZE=$( stat -c %s "$SRC" ) + fi + SHA1=$( sha1sum "$SRC" | cut -d " " -f 1 ) + + cat >> "$OUT" < + $SIZE + $SHA1 + $DST + +EOFA + + # Skip to next arch/zip entry. + # If not a valid OS, close the archives/package nodes. + OS=$(check_enum "$1" $OSES) + + if [[ ! "$OS" ]]; then + echo " " >> "$OUT" + echo " " >> "$OUT" + fi + done + +done + +# Generate XML footer +echo "" >> "$OUT" + +echo "## Validate XML against schema" +xmllint --schema $SCHEMA "$OUT"