[PATCH modular] Publish.sh: batch release and autotagging of modules

Gaetan Nadon memsize at videotron.ca
Thu Oct 6 13:09:23 PDT 2011


Features:
- Navigate the build tree from a given list of modules to release
- Accepts a list in the format produced by build.sh -L
- Tag and version names picked-up from Makefile
- Section name picked-up from module list
- It only release tarballs it has created from the module
- Timely feedback, extensive error checking and final report
- Leave module untouched if already released
- Recover from a failed run with --autoresume
- Verify what will happen with --dry-run
- Generate the announce e-mail
- Update the jhbuild moduleset

Example:

util/modular/publish.sh app/xdm lib/libX11-1.1.3 mesa/drm xserver
In this example, libX11-1.1.3 would be at branch 1.1.3 and could be released
in the same batch run with libX11 master. The last subdir name does not matter.

Design
-------
The new script is called "publish" for the moment as it may complement or
replace the release script. It is yet to be seen.

The development process ends with a module whose last commit is a
version bump in the fdo repository. All testing is assumed to have been done.

The user is not asked to do anything with git tags. No harm done if user tags
the module with the correct tag name. Any non conforming tag will be ignored.

The srcipt runs 'make dist' to create the tarball. We don't have to prompt
the user for the tar name, the version number or the section name.

The "section" is technically the first subdir down from the script invocation
directory. For all but a few, it mathces the subdir on host /svr where the
tarballs are uploaded. There may be zero or one subdir below the "section".
Exceptions such as mesa/drm have custom code to handle.

Interface
---------
Usage: publish.sh [options] section[/module]...

Section:
app|data|doc|driver|font|lib|mesa|proto|util|xcb|
xkeyboard-config|xserver

Module:
One optional subdirectory (name does not matter) for a git module.

Options:
  --autoresume <file> Resume publishing modules from last attempt. Use <file>
  --dry-run           Does everything except tagging and uploading tarballs
  --force             Force overwritting an existing release
  --help              Display this help and exit successfully
  --modfile <file>    Publish the section/modules specified in <file>
  --moduleset <file>  The jhbuild moduleset full pathname to be updated
  --no-quit           Do not quit after error; just print error message
  --user <name>       Username of your fdo account if not configured in ssh

Environment variables defined by the "make" program and used by publish.sh:
  MAKE        The name of the make command [make]
  MAKEFLAGS:  Options to pass to all $(MAKE) invocations

Usage Scenarios
----------------
Due to a change to the m4 macro, all font packages need to released.

    util/modular/build.sh -L | grep font/ > myList.txt
    util/modular/publish.sh --autoresume resume.txt --modfile myList.txt

A developer is asking a buddy to relase a few protocols and libraries.
He sends the list in an e-mail. Once all is done on disk:

    edit myList.txt (or save from e-mail)
    util/modular/publish.sh --no-quit --modfile myList.txt

A single app needs to be released for an important bug fix

    util/modular/publish.sh app/xdm

Supports libdrm and xkeybboard-config:

    util/modular/publish.sh xkeyboard-config mesa/drm

Signed-off-by: Gaetan Nadon <memsize at videotron.ca>
---

Left to do: 
 - decide on the name of the script.
 - update the wiki accordingly. New maintainers can be referred to the wiki
   which refers them to the script (hopefully just one script)

 publish.sh |  681 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 681 insertions(+), 0 deletions(-)
 create mode 100755 publish.sh

diff --git a/publish.sh b/publish.sh
new file mode 100755
index 0000000..d5210e6
--- /dev/null
+++ b/publish.sh
@@ -0,0 +1,681 @@
+#!/bin/sh
+#
+#		Creates and upload a git module tarball
+#
+# Note on portability:
+# This script is intended to run on any platform supported by X.Org.
+# Basically, it should be able to run in a Bourne shell.
+#
+#
+
+export LC_ALL=C
+
+#------------------------------------------------------------------------------
+#			Function: check_local_changes
+#------------------------------------------------------------------------------
+#
+check_local_changes() {
+    git diff --quiet HEAD > /dev/null 2>&1
+    if [ $? -ne 0 ]; then
+        echo ""
+        echo "Uncommitted changes found. Did you forget to commit? Aborting."
+	echo ""
+	echo "You can perform a 'git stash' to save your local changes and"
+	echo "a 'git stash apply' to recover them after the tarball release."
+	echo "Make sure to rebuild and run 'make distcheck' again."
+	echo ""
+	echo "Alternatively, you can clone the module in another directory"
+	echo "and run ./configure. No need to build if testing was finished."
+        echo ""
+	return 1
+    fi
+    return 0
+}
+
+#------------------------------------------------------------------------------
+#			Function: check_option_args
+#------------------------------------------------------------------------------
+#
+# perform sanity checks on cmdline args which require arguments
+# arguments:
+#   $1 - the option being examined
+#   $2 - the argument to the option
+# returns:
+#   if it returns, everything is good
+#   otherwise it exit's
+check_option_args() {
+    option=$1
+    arg=$2
+
+    # check for an argument
+    if [ x"$arg" = x ]; then
+	echo ""
+	echo "Error: the '$option' option is missing its required argument."
+	echo ""
+	usage
+	exit 1
+    fi
+
+    # does the argument look like an option?
+    echo $arg | grep "^-" > /dev/null
+    if [ $? -eq 0 ]; then
+	echo ""
+	echo "Error: the argument '$arg' of option '$option' looks like an option itself."
+	echo ""
+	usage
+	exit 1
+    fi
+}
+
+#------------------------------------------------------------------------------
+#			Function: check_modules_specification
+#------------------------------------------------------------------------------
+#
+check_modules_specification() {
+
+if [ x"$MODFILE" = x ]; then
+    if [ x"${INPUT_MODULES}" = x ]; then
+	echo ""
+	echo "Error: no modules specified (blank command line)."
+	usage
+	exit 1
+    fi
+fi
+
+}
+
+#------------------------------------------------------------------------------
+#			Function: check_script_invocation
+#------------------------------------------------------------------------------
+#
+check_script_invocation() {
+if [ ! -d "util/modular" ]; then
+    echo ""
+    echo "Error: the srcipt must be invoked from the top source tree where modules"
+    echo "are found by section and module name such as \"app/xfs\" or \"xserver\""
+    echo "pwd="`pwd`
+    echo ""
+    usage
+    exit 1
+fi
+}
+
+#------------------------------------------------------------------------------
+#			Function: generate_announce
+#------------------------------------------------------------------------------
+#
+generate_announce()
+{
+    cat <<RELEASE
+Subject: [ANNOUNCE] $pkg_name $pkg_version
+To: $list_to
+CC: $list_cc
+
+`git log --no-merges "$tag_range" | git shortlog`
+
+git tag: $tar_name
+
+http://$host_current/$section_path/$tarbz2
+MD5:  `$MD5SUM $tarbz2`
+SHA1: `$SHA1SUM $tarbz2`
+SHA256: `$SHA256SUM $tarbz2`
+
+http://$host_current/$section_path/$targz
+MD5:  `$MD5SUM $targz`
+SHA1: `$SHA1SUM $targz`
+SHA256: `$SHA256SUM $targz`
+
+RELEASE
+}
+
+#------------------------------------------------------------------------------
+#			Function: read_modfile
+#------------------------------------------------------------------------------
+#
+# Read the module names from the file and set a variable to hold them
+# This will be the same interface as cmd line supplied modules
+#
+read_modfile() {
+
+    if [ x"$MODFILE" != x ]; then
+	# Make sure the file is sane
+	if [ ! -r "$MODFILE" ]; then
+	    echo "Error: module file '$MODFILE' is not readable or does not exist."
+	    exit 1
+	fi
+	# read from input file, skipping blank and comment lines
+	while read line; do
+	    # skip blank lines
+	    if [ x"$line" = x ]; then
+		continue
+	    fi
+	    # skip comment lines
+	    echo "$line" | grep "^#" > /dev/null
+	    if [ $? -eq 0 ]; then
+		continue
+	    fi
+	    INPUT_MODULES="$INPUT_MODULES $line"
+	done <"$MODFILE"
+    fi
+    return 0
+}
+
+#------------------------------------------------------------------------------
+#			Function: print_epilog
+#------------------------------------------------------------------------------
+#
+print_epilog() {
+
+epilog="========  Successful Completion"
+if [ x"$NO_QUIT" != x ]; then
+    if [ x"$failed_modules" != x ]; then
+	epilog="========  Partial Completion"
+    fi
+elif [ x"$failed_modules" != x ]; then
+	epilog="========  Stopped on Error"
+fi
+
+echo ""
+echo "$epilog `date`"
+
+# Report about modules that failed for one reason or another
+if [ x"$failed_modules" != x ]; then
+    echo "	List of failed modules:"
+    for mod in $failed_modules; do
+	echo "	$mod"
+    done
+    echo "========"
+    echo ""
+fi
+
+}
+
+#------------------------------------------------------------------------------
+#			Function: process_modules
+#------------------------------------------------------------------------------
+#
+# Loop through each module to publish
+# Exit on error if --no-quit no specified
+#
+process_modules() {
+    for MODULE_RPATH in ${INPUT_MODULES}; do
+	process_module
+	if [ $? -ne 0 ]; then
+	    echo "Error: processing module \"$MODULE_RPATH\" failed."
+	    if [ x"$NO_QUIT" = x ]; then
+		print_epilog
+		exit 1
+	    fi
+	fi
+    done
+}
+
+#------------------------------------------------------------------------------
+#			Function: process_module
+#------------------------------------------------------------------------------
+# Code 'return 0' on success to process the next module
+# Code 'return 1' on error to process next module if invoked with --no-quit 
+#
+process_module() {
+
+    # Skip already processed modules when resuming from a previous failure
+    if [ x"$RESUME" != x ]; then
+	if [ x"$RESUME" = x"$MODULE_RPATH" ]; then
+	    # The current module is the one that failed last time
+	    echo "Info: resuming from $RESUME module"
+	    unset RESUME
+	else
+	    # The current module has already been processed successfully last time
+	    echo "Info: skipping $MODULE_RPATH in autoresume mode."
+	    return 0
+	fi
+    fi
+
+    echo ""
+    echo "========  Processing \"$MODULE_RPATH\""
+
+    top_src=`pwd`
+    if [ ! -d $MODULE_RPATH ] ; then
+        echo "Error: $MODULE_RPATH cannot be found under $top_src."
+	failed_modules="$failed_modules $MODULE_RPATH"
+        return 1
+    fi
+
+    # Write down the module about to be processed so we can resume in case of failure
+    if [ x"$RESUME_FILE" != x ]; then
+        echo "$MODULE_RPATH" >> $RESUME_FILE
+    fi
+
+    # Change directory to be in the git module
+    cd $MODULE_RPATH
+    if [ $? -ne 0 ]; then
+	echo "Error: failed to cd to $MODULE_RPATH."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	return 1
+    fi
+
+    # ----- Now in the git module *root* directory ----- #
+
+    # Check that this is indeed a git module
+    if [ ! -d .git ]; then
+	echo "Error: there is no git module here: `pwd`"
+	failed_modules="$failed_modules $MODULE_RPATH"
+	return 1
+    fi
+
+    # Change directory to be in the git build directory (could be out-of-source)
+    status_file=`find . -name config.status`
+    if [ $? -ne 0 ]; then
+	echo "Error: failed to locate config.status."
+	echo "Has the module been configured?"
+	failed_modules="$failed_modules $MODULE_RPATH"
+	return 1
+    fi
+    if [ x"$status_file" = x ]; then
+	echo "Error: failed to locate config.status."
+	echo "Has the module been configured?"
+	failed_modules="$failed_modules $MODULE_RPATH"
+	return 1	
+    fi
+    build_dir=`dirname $status_file`
+    cd $build_dir
+    if [ $? -ne 0 ]; then
+	echo "Error: failed to cd to $MODULE_RPATH/$build_dir."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+
+    # ----- Now in the git module *build* directory ----- #
+
+    # Check for uncommitted/queued changes.
+    check_local_changes
+    if [ $? -ne 0 ]; then
+	cd $top_src
+	return 1
+    fi
+
+    # Determine what is the current branch and the remote name
+    current_branch=`git branch | grep "\*" | sed -e "s/\* //"`
+    remote_name=`git config --get branch.$current_branch.remote`
+    echo "Info: working off the \"$current_branch\" branch tracking the remote \"$remote_name\"."
+
+    # Run 'make dist' to ensure the tarball matches the git module content
+    # Important to run make dist before looking in Makefile, may need to reconfigure
+    echo "Info: running \"make dist\" to create tarballs:"
+    ${MAKE} $MAKEFLAGS dist > /dev/null
+    if [ $? -ne 0 ]; then
+	echo "Error: \"$MAKE $MAKEFLAGS dist\" failed."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+
+    # Find out the tarname from the makefile
+    pkg_name=`grep '^PACKAGE = ' Makefile | sed 's|PACKAGE = ||'`
+    pkg_version=`grep '^VERSION = ' Makefile | sed 's|VERSION = ||'`
+    tar_name="$pkg_name-$pkg_version"
+    targz=$tar_name.tar.gz
+    tarbz2=$tar_name.tar.bz2
+    ls -l $targz
+    ls -l $tarbz2
+
+    # Obtain the top commit SHA which should be the version bump
+    # It should not have been tagged yet (the script will do it later)
+    local_top_commit_sha=`git  rev-list --max-count=1 HEAD`
+    if [ $? -ne 0 ]; then
+	echo "Error: unable to obtain the local top commit id."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+
+    # Check that the top commit looks like a version bump
+    git diff --unified=0 HEAD^ | grep $pkg_version >/dev/null 2>&1
+    if [ $? -ne 0 ]; then
+	echo "Error: the local top commit does not look like a version bump."
+	echo "       the diff does not contain the string \"$pkg_version\"."
+	local_top_commit_descr=`git log --oneline --max-count=1 $local_top_commit_sha`
+	echo "       the local top commit is: \"$local_top_commit_descr\""
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+
+    # Check that the top commit has been pushed to remote
+    remote_top_commit_sha=`git  rev-list --max-count=1 $remote_name/$current_branch`
+    if [ $? -ne 0 ]; then
+	echo "Error: unable to obtain top commit from the remote repository."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+    if [ x"$remote_top_commit_sha" != x"$local_top_commit_sha" ]; then
+	echo "Error: the local top commit has not been pushed to the remote."
+	local_top_commit_descr=`git log --oneline --max-count=1 $local_top_commit_sha`
+	echo "       the local top commit is: \"$local_top_commit_descr\""
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    fi
+
+    # If a tag exists with the the tar name, ensure it is tagging the top commit
+    # It may happen if the version set in configure.ac has been previously released
+    tagged_commit_sha=`git  rev-list --max-count=1 $tar_name 2>/dev/null`
+    if [ $? -eq 0 ]; then
+	# Check if the tag is pointing to the top commit
+	if [ x"$tagged_commit_sha" != x"$remote_top_commit_sha" ]; then
+	    echo "Error: the \"$tar_name\" already exists."
+	    echo "       this tag is not tagging the top commit."
+	    remote_top_commit_descr=`git log --oneline --max-count=1 $remote_top_commit_sha`
+	    echo "       the top commit is: \"$remote_top_commit_descr\""
+	    local_tag_commit_descr=`git log --oneline --max-count=1 $tagged_commit_sha`
+	    echo "       tag \"$tar_name\" is tagging some other commit: \"$local_tag_commit_descr\""
+	    failed_modules="$failed_modules $MODULE_RPATH"
+	    cd $top_src
+	    return 1
+	else
+	    echo "Info: module already tagged with \"$tar_name\"."
+	fi
+    else
+	# Tag the top commit with the tar name
+	if [ x"$DRY_RUN" = x ]; then
+	    git tag -m $tar_name $tar_name
+	    if [ $? -ne 0 ]; then
+		echo "Error:  unable to tag module with \"$tar_name\"."
+		failed_modules="$failed_modules $MODULE_RPATH"
+		cd $top_src
+		return 1
+	    else
+		echo "Info: module tagged with \"$tar_name\"."
+	    fi
+	else
+	    echo "Info: skipping the commit tagging in dry-run mode."
+	fi
+    fi
+
+    # --------- Now the tarballs are ready to upload ----------
+
+    # The hostname which is used to connect to the development resources
+    hostname="annarchy.freedesktop.org"
+
+    # Some hostnames are also used as /srv subdirs
+    host_xorg="xorg.freedesktop.org"
+    host_dri="dri.freedesktop.org"
+
+    # Mailing lists where to post the all [Announce] e-mails
+    list_to="xorg-announce at lists.freedesktop.org"
+
+    # Mailing lists to be CC according to the project (xorg|dri|xkb)
+    list_xorg_user="xorg at lists.freedesktop.org"
+    list_dri_devel="dri-devel at lists.sourceforge.net"
+    list_xkb="xkb at listserv.bat.ru"
+
+    # Find the section (subdirs) where the tarballs are to be uploaded
+    # The module relative path can be app/xfs, xserver, or mesa/drm for example
+    section=`echo $MODULE_RPATH | cut -d'/' -f1`
+    if [ $? -ne 0 ]; then
+	echo "Error: unable to extract section from $MODULE_RPATH first field."
+	failed_modules="$failed_modules $MODULE_RPATH"
+	cd $top_src
+	return 1
+    else
+	host_current=$host_xorg
+	section_path=archive/individual/$section
+	srv_path="/srv/$host_current/$section_path"
+	list_cc=$list_xorg_user
+    fi
+
+    # Setup upload directories, hostnames and mailing lists
+    # Module mesa/drm goes in the dri "libdrm" section
+    if [ x"$section" = xmesa ]; then
+	section=`echo $MODULE_RPATH | cut -d'/' -f2`
+	if [ $? -ne 0 ]; then
+	    echo "Error: unable to extract section from $MODULE_RPATH second field."
+	    failed_modules="$failed_modules $MODULE_RPATH"
+	    cd $top_src
+	    return 1
+	elif [ x"$section" = xdrm ]; then
+	    host_current=$host_dri
+	    section_path=www/libdrm
+	    srv_path="/srv/$host_current/$section_path"
+	    list_cc=$list_dri_devel
+	else
+	    echo "Error: section $section is not supported, only libdrm is."
+	    failed_modules="$failed_modules $MODULE_RPATH"
+	    cd $top_src
+	    return 1
+	fi	
+    fi
+    # Module xkeyboard-config goes in a subdir of the xorg "data" section
+    if [ x"$section" = xxkeyboard-config ]; then
+	host_current=$host_xorg
+	section_path=archive/individual/data/$section
+	srv_path="/srv/$host_current/$section_path"
+	list_cc=$list_xkb
+    fi
+        
+    # Check for already existing tarballs
+    ssh $USER_NAME$hostname ls $srv_path/$targz >/dev/null 2>&1 ||
+    ssh $USER_NAME$hostname ls $srv_path/$tarbz2  >/dev/null 2>&1
+    if [ $? -eq 0 ]; then
+	if [ "x$FORCE" = "xyes" ]; then
+	    echo "Warning: overwriting released tarballs due to --force option."
+	else
+	    echo "Error: tarball $tar_name already exists. Use --force to overwrite."
+	    failed_modules="$failed_modules $MODULE_RPATH"
+	    cd $top_src
+	    return 1
+	fi	
+    fi
+    
+    # Upload to host using the 'scp' remote file copy program
+    if [ x"$DRY_RUN" = x ]; then
+	echo "Info: uploading tarballs to web server:"
+	scp $targz $tarbz2 $USER_NAME@$hostname:$srv_path
+	if [ $? -ne 0 ]; then
+	    echo "Error: the tarballs uploading failed."
+	    cd $top_src
+	    return 1
+	fi
+    else
+	echo "Info: skipping tarballs uploading in dry-run mode."
+    fi
+
+    # Pushing the top commit tag to the remote repository
+    if [ x$DRY_RUN = x ]; then
+	echo "Info: pushing tag \"$tar_name\" to remote \"$remote_name\":"
+	git push $remote_name $tar_name
+	if [ $? -ne 0 ]; then
+	    echo "Error: unable to push tag \"$tar_name\" to the remote repository."
+	    echo "       it is recommended you fix this manually and not run the script again"
+	    cd $top_src
+	    return 1
+	fi
+    else
+	echo "Info: skipped pushing tag \"$tar_name\" to the remote repository in dry-run mode."
+    fi
+    
+    MD5SUM=`which md5sum || which gmd5sum`
+    SHA1SUM=`which sha1sum || which gsha1sum`
+    SHA256SUM=`which sha256sum || which gsha256sum`
+
+    # --------- Generate the announce e-mail ------------------
+    # Failing to generate the announce is not considered a fatal error
+
+    # Git-describe returns only "the most recent tag", it may not be the expected one
+    # However, we only use it for the commit history which will be the same anyway.
+    tag_previous=`git describe --abbrev=0 HEAD^ 2>/dev/null`
+    # Git fails with rc=128 if no tags can be found prior to HEAD^
+    if [ $? -ne 0 ]; then
+	if [ $? -ne 0 ]; then
+	    echo "Warning: unable to find a previous tag."
+	    echo "         perhaps a first release on this branch."
+	    echo "         Please check the commit history in the announce."
+	fi
+    fi
+    if [ x"$tag_previous" != x ]; then
+	# The top commit may not have been tagged in dry-run mode. Use commit.
+	tag_range=$tag_previous..$local_top_commit_sha
+    else
+	tag_range=$tar_name
+    fi
+    generate_announce > "$tar_name.announce"
+    echo "Info: [ANNOUNCE] template generated in \"$tar_name.announce\" file."
+    echo "      Please pgp sign and send it."
+
+    # --------- Update the JH Build moduleset -----------------
+    # Failing to update the jh moduleset is not considered a fatal error
+    if [ x"$JH_MODULESET" != x ]; then
+	if [ x$DRY_RUN = x ]; then
+	    sha1sum=`$SHA1SUM $targz | cut -d' ' -f1`
+	    $top_src/util/modular/update-moduleset.sh $JH_MODULESET $sha1sum $targz
+	    echo "Info: updated jh moduleset: \"$JH_MODULESET\""
+	else
+	    echo "Info: skipping jh moduleset \"$JH_MODULESET\" update in dry-run mode."
+	fi
+    fi
+
+    # --------- Successful completion --------------------------
+    cd $top_src
+    return 0
+
+}
+
+#------------------------------------------------------------------------------
+#			Function: usage
+#------------------------------------------------------------------------------
+# Displays the script usage and exits successfully
+#
+usage() {
+    basename="`expr "//$0" : '.*/\([^/]*\)'`"
+    cat <<HELP
+
+Usage: $basename [options] section[/module]...
+
+Section:
+app|data|doc|driver|font|lib|mesa|proto|util|xcb|
+xkeyboard-config|xserver
+
+Module:
+One optional subdirectory (name does not matter) for a git module.
+
+Options:
+  --autoresume <file> Resume publishing modules from last attempt. Use <file>
+  --dry-run           Does everything except tagging and uploading tarballs
+  --force             Force overwritting an existing release
+  --help              Display this help and exit successfully
+  --modfile <file>    Publish the section/modules specified in <file>
+  --moduleset <file>  The jhbuild moduleset full pathname to be updated
+  --no-quit           Do not quit after error; just print error message
+  --user <name>       Username of your fdo account if not configured in ssh
+
+Environment variables defined by the "make" program and used by publish.sh:
+  MAKE        The name of the make command [make]
+  MAKEFLAGS:  Options to pass to all \$(MAKE) invocations
+
+HELP
+}
+
+#------------------------------------------------------------------------------
+#			Script main line
+#------------------------------------------------------------------------------
+#	
+
+# Choose which make program to use (could be gmake)
+MAKE=${MAKE:="make"}
+
+# Process command line args
+while [ $# != 0 ]
+do
+    case $1 in
+    # Resume publishing modules from last attempt. Use <file>
+    --autoresume)
+	check_option_args $1 $2
+	shift
+	RESUME_FILE=$1
+	[ -f $1 ] && RESUME=`tail -n 1 $1`
+	;;
+    # Does everything except uploading tarball
+    --dry-run)
+	DRY_RUN=yes
+	;;
+    # Force overwritting an existing release
+    # Use only if nothing changed in the git repo
+    --force)
+	FORCE=yes
+	;;
+    # Display this help and exit successfully
+    --help)
+	usage
+	exit 0
+	;;
+    # Publish the section/modules specified in <file>
+    --modfile)
+	check_option_args $1 $2
+	shift
+	MODFILE=$1
+	;;
+    # The jhbuild moduleset to update with relase info
+    --moduleset)
+	check_option_args $1 $2
+        shift
+        JH_MODULESET=$1
+        ;;
+    # Do not quit after error; just print error message
+    --no-quit)
+	NO_QUIT=yes
+	;;
+    # Username of your fdo account if not configured in ssh
+    --user)
+	check_option_args $1 $2
+	shift
+	USER_NAME=$1
+	;;
+    --*)
+	echo ""
+        echo "Error: unknown option: $1"
+	echo ""
+	usage
+        exit 1
+        ;;
+    -*)
+	echo ""
+        echo "Error: unknown option: $1"
+	echo ""
+        usage
+        exit 1
+        ;;
+    *)
+        if [ x"${MODFILE}" != x ]; then
+	    echo ""
+	    echo "Error: specifying both modules and --modfile is not permitted"
+	    echo ""
+	    usage
+            exit 1
+	fi
+	INPUT_MODULES="${INPUT_MODULES} $1"
+	;;
+    esac
+
+    shift
+done
+
+# Script must be invoked from top source directory
+check_script_invocation
+
+# If no modules specified (blank cmd line) display help
+check_modules_specification
+
+# Read the module file and normalize input in INPUT_MODULES
+read_modfile
+
+# Loop through each module to publish
+# Exit on error if --no-quit no specified
+process_modules
+
+# Succesfull completion of the script, delete the autoresume file
+rm -f $RESUME_FILE
+
+# Print the epilog with final status
+print_epilog
-- 
1.7.4.1



More information about the xorg-devel mailing list