Blame multilib-fix

189cce
#! /bin/sh
189cce
d22c0c
# Fix multilib issue for header files.
d22c0c
# Copyright (C) 2015 Red Hat, Inc.
d22c0c
# Written by Pavel Raiskup <praiskup@redhat.com>
189cce
#
d22c0c
# This program is free software; you can redistribute it and/or modify
d22c0c
# it under the terms of the GNU General Public License as published by
d22c0c
# the Free Software Foundation; either version 2 of the License, or
d22c0c
# (at your option) any later version.
189cce
#
d22c0c
# This program is distributed in the hope that it will be useful,
d22c0c
# but WITHOUT ANY WARRANTY; without even the implied warranty of
d22c0c
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
d22c0c
# GNU General Public License for more details.
189cce
#
d22c0c
# You should have received a copy of the GNU General Public License along
d22c0c
# with this program; if not, write to the Free Software Foundation, Inc.,
d22c0c
# 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
1a9b5b
1a9b5b
1a9b5b
# Replace the multilib-unclean file with multilib-clean stub, while the
d22c0c
# original file is moved to unique architecture-specific location.
189cce
189cce
progname=$(basename "$0")
189cce
189cce
opt_arch=$(uname -i)
189cce
# See rhbz#1242873 for more info.
189cce
test "$opt_arch" = ppc64p7 && opt_arch=ppc64
189cce
189cce
opt_buildroot=$(pwd)
189cce
opt_verbose=:
9f438c
opt_field_separator=-
189cce
189cce
# TODO: we could pretty easily implement other then 'cpp-header' stubs, if the
189cce
# target file type allows some kind of "transparent" file inclusion.  For
ccd34d
# example shell scripts might use '. "${destdir}/${filename}_x86_64.sh'.
d22c0c
# The solution is taken from Fedora PostgreSQL RPM package.
189cce
print_stub ()
189cce
{
f2fed8
    # The '#else' branch here is not needed!  We never install this header on
f2fed8
    # systems where this set of '#ifdef's is not enough (adding suggested e.g.
f2fed8
    # in rhbz#1242873).
f2fed8
9f438c
    replacement=$filename$opt_field_separator
189cce
cat <
189cce
/*
189cce
 * Kluge to support multilib installation of both 32- and 64-bit RPMS:
189cce
 * we need to arrange that header files that appear in both RPMs are
189cce
 * identical.  Hence, this file is architecture-independent and calls
189cce
 * in an arch-dependent file that will appear in just one RPM.
189cce
 *
189cce
 * To avoid breaking arches not explicitly supported by Red Hat, we
189cce
 * use this indirection file *only* on known multilib arches.
189cce
 *
189cce
 * Note: this may well fail if user tries to use gcc's -I- option.
189cce
 * But that option is deprecated anyway.
189cce
 */
189cce
#if defined(__x86_64__)
9f438c
#include "${replacement}x86_64.h"
189cce
#elif defined(__i386__)
9f438c
#include "${replacement}i386.h"
189cce
#elif defined(__ppc64__) || defined(__powerpc64__)
9f438c
#include "${replacement}ppc64.h"
189cce
#elif defined(__ppc__) || defined(__powerpc__)
9f438c
#include "${replacement}ppc.h"
189cce
#elif defined(__s390x__)
9f438c
#include "${replacement}s390x.h"
189cce
#elif defined(__s390__)
9f438c
#include "${replacement}s390.h"
189cce
#elif defined(__sparc__) && defined(__arch64__)
9f438c
#include "${replacement}sparc64.h"
189cce
#elif defined(__sparc__)
9f438c
#include "${replacement}sparc.h"
189cce
#endif
189cce
EOF
189cce
}
189cce
189cce
print_help ()
189cce
{
189cce
    _h_exit=false
189cce
    test -n "$1" && _h_exit=:
189cce
189cce
    cat <
189cce
Usage: $progname [OPTIONS]
189cce
189cce
Replace the multilib-unclean header file with multilib-clean stub, while the
189cce
original file is moved to unique architecture-specific location.  This should be
189cce
absolutely safe operation (effects of '#include <header.h>' are unchanged.
189cce
189cce
To allow us to do incompatible changes in this script, packagers should use this
ccd34d
script only through available RPM macros.
189cce
189cce
--buildroot     prefix (directory where we play with installed files, usually
189cce
                after 'make install DESTDIR=buildroot')
ccd34d
--file          for example /some/path/test.h
9f438c
--field-separator   by default we move filename.h to filename<sep><arch>.h; this
aeb305
                option allows you to override the <sep> part
189cce
--verbose       print some useful information
189cce
--help          show this help
189cce
EOF
189cce
189cce
    $_h_exit && exit "$1"
189cce
}
189cce
189cce
verbose ()
189cce
{
189cce
    $opt_verbose && echo "INFO: $progname: $*"
189cce
}
189cce
189cce
die ()
189cce
{
189cce
    echo >&2 " # $*"
189cce
    print_help 1
189cce
}
189cce
189cce
error ()
189cce
{
189cce
    error_occurred=:
189cce
    echo >&2 " ! $*"
189cce
}
189cce
189cce
error_occurred=false
189cce
189cce
while test $# -gt 0
189cce
do
189cce
    _opt=$1 ; shift
189cce
    case $_opt in
9f438c
        --buildroot|--arch|--file|--field-separator)
ccd34d
            _raw_opt=$(echo "$_opt" | sed -e 's/^--//' -e 's/-/_/g')
ccd34d
            eval "opt_$_raw_opt=\$1"
ccd34d
            shift || die "$_opt requires argument"
189cce
            ;;
189cce
        --help)
189cce
            print_help 0
189cce
            ;;
189cce
        *)
189cce
            error "unexpected '$_opt' program argument"
189cce
            ;;
189cce
    esac
189cce
done
189cce
$error_occurred && print_help 1
189cce
ccd34d
for i in arch buildroot file
189cce
do
189cce
    eval "test -z \"\$opt_$i\"" && error "--$i needs to be set"
189cce
done
189cce
$error_occurred && print_help 1
189cce
ccd34d
# --> /buildroot/usr/include/test.h
ccd34d
original_file="$opt_buildroot$opt_file"
ccd34d
ccd34d
# --> /buildroot/usr/include
ccd34d
destdir=$(dirname "$original_file")
ccd34d
ccd34d
# --> test.h
ccd34d
orig_basename=$(basename "$original_file")
ccd34d
ccd34d
# --> test
ccd34d
filename=${orig_basename%%.[a-zA-Z0-9_]}
ccd34d
ccd34d
# --> .h
ccd34d
suffix=${orig_basename##${filename}}
ccd34d
ccd34d
# --> ../test_x86_64.h (on x86_64)
9f438c
multilib_file="$destdir/$filename$opt_field_separator$opt_arch$suffix"
189cce
189cce
test -f "$original_file" || die "can't find '$original_file'"
189cce
189cce
case $opt_arch in
189cce
  # we only apply this to known Red Hat multilib arches, per bug #177564
189cce
  i386|x86_64|ppc|ppc64|s390|s390x|sparc|sparc64)
189cce
      ;;
189cce
  *)
189cce
      verbose "we don't need multilib haeder hack for '$opt_arch' architecture (no-op)"
189cce
      exit 0
189cce
      ;;
189cce
esac
189cce
189cce
verbose "moving: '$original_file' to '$multilib_file'"
189cce
189cce
mv "$original_file" "$multilib_file" || exit 1
189cce
if print_stub > "$original_file" && chmod 644 "$original_file"; then
189cce
    :
189cce
else
189cce
    die "can't write into '$original_file'"
189cce
fi
189cce
189cce
: