Put back more gcj stuff.
authorPeter Michael Green <plugwash@raspbian.org>
Thu, 29 Aug 2019 15:00:56 +0000 (15:00 +0000)
committerPeter Michael Green <plugwash@raspbian.org>
Thu, 29 Aug 2019 15:01:28 +0000 (15:01 +0000)
20 files changed:
classpath.security [new file with mode: 0644]
debian/README.Debian
debian/README.Debian.m4
debian/aot-compile [new file with mode: 0644]
debian/aotcompile.py [new file with mode: 0644]
debian/classfile.py [new file with mode: 0644]
debian/copyright.libgcj-common [new file with mode: 0644]
debian/dh_javadoc [new file with mode: 0644]
debian/dh_nativejava [new file with mode: 0644]
debian/generate-cacerts.pl.in [new file with mode: 0644]
debian/gij.prerm [new file with mode: 0644]
debian/libgcj-bc.overrides [new file with mode: 0644]
debian/libgcj-common.postinst [new file with mode: 0644]
debian/libgcj-common.preinst [new file with mode: 0644]
debian/libgcj-common.prerm [new file with mode: 0644]
debian/postinst-rebuild-gcj-db [new file with mode: 0644]
debian/postrm-rebuild-gcj-db [new file with mode: 0644]
debian/rebuild-gcj-db [new file with mode: 0644]
debian/rebuild-security-providers [new file with mode: 0755]
debian/rules

diff --git a/classpath.security b/classpath.security
new file mode 100644 (file)
index 0000000..d606f4b
--- /dev/null
@@ -0,0 +1,51 @@
+# classpath.security
+#    Copyright (C) 2002, 2006 Free Software Foundation, Inc.
+# 
+# This file is part of GNU Classpath.
+# 
+# GNU Classpath 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 2, or (at your option)
+# any later version.
+# 
+# GNU Classpath 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 GNU Classpath; see the file COPYING.  If not, write to the
+# Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+# 02110-1301 USA.
+# 
+# Linking this library statically or dynamically with other modules is
+# making a combined work based on this library.  Thus, the terms and
+# conditions of the GNU General Public License cover the whole
+# combination.
+# 
+# As a special exception, the copyright holders of this library give you
+# permission to link this library with independent modules to produce an
+# executable, regardless of the license terms of these independent
+# modules, and to copy and distribute the resulting executable under
+# terms of your choice, provided that you also meet, for each linked
+# independent module, the terms and conditions of the license of that
+# module.  An independent module is a module which is not derived from
+# or based on this library.  If you modify this library, you may extend
+# this exception to your version of the library, but you are not
+# obligated to do so.  If you do not wish to do so, delete this
+# exception statement from your version.
+
+# The VM-wide default callback handler class name.  MUST be a subclass of
+# javax.security.auth.callback.CallbackHandler
+auth.login.defaultCallbackHandler=gnu.javax.security.auth.callback.DefaultCallbackHandler
+
+# If this file isn't found we fall back to generating entropy through
+# "battling threads".
+securerandom.source=file:///dev/urandom
+
+# Note that the settings and ordering here are mirrored in Security.
+security.provider.1=gnu.java.security.provider.Gnu
+security.provider.2=gnu.javax.crypto.jce.GnuCrypto
+security.provider.3=gnu.javax.crypto.jce.GnuSasl
+security.provider.4=gnu.javax.net.ssl.provider.Jessie
+security.provider.5=gnu.javax.security.auth.callback.GnuCallbacks
index 5f609e7842f324fa54e49bf299647fb0289ea18b..04dcc82e0ce55bb49449b693cec1d03887e52bb6 100644 (file)
@@ -34,7 +34,7 @@ How are the default compilers selected?
 ---------------------------------------
 
 Starting in Debian 3.0, there is now a gcc-defaults package set. This
-creates the actual packages for gcc, gnat, g++, gobjc,
+creates the actual packages for gcc, gnat, g++, gobjc, chill, gcj, gij,
 gdc and gpc.  These packages will depend on the corresponding default
 compiler for that architecture. For Debian 5.0 for example, "gcc"
 depends on "gcc-5", which means that the "gcc-5" package will
@@ -50,14 +50,14 @@ similar.
 The default compiler versions for Debian GNU/Linux on armhf are
 (minor version numbers omitted):
 
-       cpp             : cpp-9
-       gcc             : gcc-9
-       g++             : g++-9
-       gfortran        : gfortran-9
-       gccgo           : gccgo-9
-       gobjc           : gobjc-9
-       gobjc++         : gobjc++-9
-       gdc             : gdc-9
+       cpp             : cpp-8
+       gcc             : gcc-8
+       g++             : g++-8
+       gfortran        : gfortran-8
+       gccgo           : gccgo-8
+       gobjc           : gobjc-8
+       gobjc++         : gobjc++-8
+       gdc             : gdc-8
 
 Most of the documentation for GCC including the manual pages is
 licensed under the GFDL and therefore not included in the main section.
index 4984cd6e56ad71a1d627c6e31a6e7674a2bb0bc4..e3b178604237ed4eba0b3ed621641ab781f81d46 100644 (file)
@@ -39,7 +39,7 @@ How are the default compilers selected?
 ---------------------------------------
 
 Starting in Debian 3.0, there is now a gcc-defaults package set. This
-creates the actual packages for gcc, gnat, g++, gobjc,
+creates the actual packages for gcc, gnat, g++, gobjc, chill, gcj, gij,
 gdc and gpc.  These packages will depend on the corresponding default
 compiler for that architecture. For Debian 5.0 for example, "gcc"
 depends on "gcc-5", which means that the "gcc-5" package will
@@ -59,6 +59,8 @@ The default compiler versions for Debian GNU/OS_NAME on DEB_ARCH are
        gcc             : gcc-PV_GCC
 ifenabled(`g++',`      g++             : g++-PV_GPP')
 ifenabled(`gfortran',` gfortran        : gfortran-PV_GFORT')
+ifenabled(`gcj',`      gcj             : gcj-PV_GCJ')
+ifenabled(`gcj',`      gij             : gij-PV_GIJ')
 ifenabled(`gccgo',`    gccgo           : gccgo-PV_GGO')
 ifenabled(`gobjc',`    gobjc           : gobjc-PV_GOBJC')
 ifenabled(`gobjc++',`  gobjc++         : gobjc++-PV_GOBJCXX')
diff --git a/debian/aot-compile b/debian/aot-compile
new file mode 100644 (file)
index 0000000..93e1c60
--- /dev/null
@@ -0,0 +1,98 @@
+#!/usr/bin/python
+
+## Copyright (C) 2006, 2008 Red Hat, Inc.
+## Written by Gary Benson <gbenson@redhat.com>
+##
+## 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 2 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.
+
+import sys
+sys.path.append("/usr/lib/gcc")
+import aotcompile
+import getopt
+import os
+
+usage = """\
+Usage: %s [OPTION...] SRCDIR DSTDIR
+AOT-compile all Java bytecode in SRCDIR into DSTDIR.
+
+Options:
+  -M, --make=PATH        make executable to use (%s)
+  -C, --gcj=PATH         gcj executable to use (%s)
+  -D, --dbtool=PATH      gcj-dbtool executable to use (%s)
+  -m, --makeflags=FLAGS  flags to pass to make during build
+  -c, --gcjflags=FLAGS   flags to pass to gcj during compilation
+                           in addition to %s
+  -l, --ldflags=FLAGS    flags to pass to gcj during linking
+                           in addition to %s
+  -e, --exclude=PATH     do not compile PATH
+  -L, --libdir=DIR       overwrite destination directory
+
+Extra flags may also be passed using the AOT_MAKEFLAGS, AOT_GCJFLAGS
+and AOT_LDFLAGS environment variables.
+
+The parallel=<n> option in DEB_BUILD_OPTIONS is passed to make unless
+-j<n> is passed with -m, --makeflags""" % (
+    os.path.basename(sys.argv[0]),
+    aotcompile.PATHS["make"],
+    aotcompile.PATHS["gcj"],
+    aotcompile.PATHS["dbtool"],
+    repr(" ".join(aotcompile.GCJFLAGS)),
+    repr(" ".join(aotcompile.LDFLAGS)))
+
+try:
+    try:
+        opts, args = getopt.getopt(
+            sys.argv[1:],
+            "M:C:D:m:c:l:e:L:",
+            ["make=", "gcj=", "dbtool=",
+             "makeflags=" "gcjflags=", "ldflags=",
+             "exclude=", "libdir="])
+        srcdir, dstdir = args
+    except:
+        print >>sys.stderr, usage
+        sys.exit(1)
+
+    compiler = aotcompile.Compiler(srcdir, dstdir)
+    for o, a in opts:
+        if o in ("-M", "--make"):
+            aotcompile.PATHS["make"] = a
+        if o in ("-C", "--gcj"):
+            aotcompile.PATHS["gcj"] = a
+        if o in ("-D", "--dbtool"):
+            aotcompile.PATHS["dbtool"] = a
+        if o in ("-m", "--makeflags"):
+            compiler.makeflags[0:0] = a.split()
+        if o in ("-c", "--gcjflags"):
+            compiler.gcjflags[0:0] = a.split()
+        if o in ("-l", "--ldflags"):
+            compiler.ldflags[0:0] = a.split()
+        if o in ("-e", "--exclude"):
+            compiler.exclusions.append(a)
+        if o in ("-L", "--libdir"):
+            compiler.libdir = a
+    
+    compiler.makeflags[0:0] = os.environ.get("AOT_MAKEFLAGS", "").split() 
+    compiler.gcjflags[0:0] = os.environ.get("AOT_GCJFLAGS", "").split() 
+    compiler.ldflags[0:0] = os.environ.get("AOT_LDFLAGS", "").split() 
+
+    try:
+        n = [int(o.replace('parallel=', '')) for o in os.environ.get("DEB_BUILD_OPTIONS", "").replace(',',' ').split() if o.startswith('parallel=')][-1]
+    except (ValueError, IndexError):
+        n=1
+    if not [o for o in compiler.makeflags if o.startswith('-j')] and n > 1:
+        compiler.makeflags.append('-j%d' % n)
+
+    compiler.compile()
+
+except aotcompile.Error, e:
+    print >>sys.stderr, "%s: error: %s" % (
+        os.path.basename(sys.argv[0]), e)
+    sys.exit(1)
diff --git a/debian/aotcompile.py b/debian/aotcompile.py
new file mode 100644 (file)
index 0000000..3ef7f1f
--- /dev/null
@@ -0,0 +1,435 @@
+
+# -*- python -*-
+
+## Copyright (C) 2005, 2006, 2008 Red Hat, Inc.
+## Written by Gary Benson <gbenson@redhat.com>
+##
+## 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 2 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.
+
+import classfile
+import copy
+import md5
+import operator
+import os
+import sys
+import cStringIO as StringIO
+import zipfile
+
+PATHS = {"make":   "/usr/bin/make",
+         "gcj":    "/usr/bin/gcj",
+         "dbtool": "/usr/bin/gcj-dbtool"}
+
+MAKEFLAGS = []
+GCJFLAGS = ["-g", "-O2", "-fPIC", "-findirect-dispatch", "-fjni"]
+LDFLAGS = ["-Wl,-Bsymbolic"]
+
+MAX_CLASSES_PER_JAR = 1024
+MAX_BYTES_PER_JAR = 1048576
+
+# Calculate the maximum jar size/maximum classes per jar.
+try:
+    for line in file('/proc/meminfo'):
+        if line.startswith('MemTotal:'):
+            memtotal = int(line.split()[1])
+            break
+    if memtotal < 2200000:
+        MAX_CLASSES_PER_JAR = 512
+        MAX_BYTES_PER_JAR = 524288
+    if memtotal < 1100000:
+        MAX_CLASSES_PER_JAR = 256
+        MAX_BYTES_PER_JAR = 262144
+except:
+    pass
+
+MAKEFILE = "Makefile"
+
+MAKEFILE_HEADER = '''\
+GCJ = %(gcj)s
+DBTOOL = %(dbtool)s
+GCJFLAGS = %(gcjflags)s
+LDFLAGS = %(ldflags)s
+
+%%.o: %%.jar
+       $(GCJ) -c $(GCJFLAGS) $< -o $@
+
+TARGETS = \\
+%(targets)s
+
+all: $(TARGETS)'''
+
+MAKEFILE_JOB = '''
+%(base)s_SOURCES = \\
+%(jars)s
+
+%(base)s_OBJECTS = \\
+$(%(base)s_SOURCES:.jar=.o)
+
+%(dso)s: $(%(base)s_OBJECTS)
+       $(GCJ) -shared $(GCJFLAGS) $(LDFLAGS) $^ -o $@
+
+%(db)s: $(%(base)s_SOURCES)
+       $(DBTOOL) -n $@ 64
+       for jar in $^; do \\
+            $(DBTOOL) -f $@ $$jar \\
+                %(libdir)s/%(dso)s; \\
+        done'''
+
+ZIPMAGIC, CLASSMAGIC = "PK\x03\x04", "\xca\xfe\xba\xbe"
+
+class Error(Exception):
+    pass
+
+class Compiler:
+    def __init__(self, srcdir, libdir, prefix = None):
+        self.srcdir = os.path.abspath(srcdir)
+        self.libdir = os.path.abspath(libdir)
+        if prefix is None:
+            self.dstdir = self.libdir
+        else:
+            self.dstdir = os.path.join(prefix, self.libdir.lstrip(os.sep))
+
+        # Calling code may modify these parameters
+        self.gcjflags = copy.copy(GCJFLAGS)
+        self.ldflags = copy.copy(LDFLAGS)
+        self.makeflags = copy.copy(MAKEFLAGS)
+        self.exclusions = []
+
+    def compile(self):
+        """Search srcdir for classes and jarfiles, then generate
+        solibs and mappings databases for them all in libdir."""
+        if not os.path.isdir(self.dstdir):
+            os.makedirs(self.dstdir)
+        oldcwd = os.getcwd()
+        os.chdir(self.dstdir)
+        try:            
+            jobs = self.getJobList()
+            if not jobs:
+                raise Error, "nothing to do"
+            self.writeMakefile(MAKEFILE, jobs)
+            for job in jobs:
+                job.writeJars()
+            system([PATHS["make"]] + self.makeflags)
+            for job in jobs:
+                job.clean()
+            os.unlink(MAKEFILE)
+        finally:
+            os.chdir(oldcwd)
+
+    def getJobList(self):
+        """Return all jarfiles and class collections in srcdir."""
+        jobs = weed_jobs(find_jobs(self.srcdir, self.exclusions))
+        set_basenames(jobs)
+        return jobs
+
+    def writeMakefile(self, path, jobs):
+        """Generate a makefile to build the solibs and mappings
+        databases for the specified list of jobs."""
+        fp = open(path, "w")
+        print >>fp, MAKEFILE_HEADER % {
+            "gcj": PATHS["gcj"],
+            "dbtool": PATHS["dbtool"],
+            "gcjflags": " ".join(self.gcjflags),
+            "ldflags": " ".join(self.ldflags),
+            "targets": " \\\n".join(reduce(operator.add, [
+                (job.dsoName(), job.dbName()) for job in jobs]))}
+        for job in jobs:
+            values = job.ruleArguments()
+            values["libdir"] = self.libdir
+            print >>fp, MAKEFILE_JOB % values
+        fp.close()
+
+def find_jobs(dir, exclusions = ()):
+    """Scan a directory and find things to compile: jarfiles (zips,
+    wars, ears, rars, etc: we go by magic rather than file extension)
+    and directories of classes."""
+    def visit((classes, zips), dir, items):
+        for item in items:
+            path = os.path.join(dir, item)
+            if os.path.islink(path) or not os.path.isfile(path):
+                continue
+            magic = open(path, "r").read(4)
+            if magic == ZIPMAGIC:
+                zips.append(path)
+            elif magic == CLASSMAGIC:
+                classes.append(path)
+    classes, paths = [], []
+    os.path.walk(dir, visit, (classes, paths))
+    # Convert the list of classes into a list of directories
+    while classes:
+        # XXX this requires the class to be correctly located in its heirachy.
+        path = classes[0][:-len(os.sep + classname(classes[0]) + ".class")]
+        paths.append(path)
+        classes = [cls for cls in classes if not cls.startswith(path)]
+    # Handle exclusions.  We're really strict about them because the
+    # option is temporary in aot-compile-rpm and dead options left in
+    # specfiles will hinder its removal.
+    for path in exclusions:
+        if path in paths:
+            paths.remove(path)
+        else:
+            raise Error, "%s: path does not exist or is not a job" % path
+    # Build the list of jobs
+    jobs = []
+    paths.sort()
+    for path in paths:
+        if os.path.isfile(path):
+            job = JarJob(path)
+        else:
+            job = DirJob(path)
+        if len(job.classes):
+            jobs.append(job)
+    return jobs
+
+class Job:
+    """A collection of classes that will be compiled as a unit."""
+    
+    def __init__(self, path):
+        self.path, self.classes, self.blocks = path, {}, None
+        self.classnames = {}
+
+    def addClass(self, bytes, name):
+        """Subclasses call this from their __init__ method for
+        every class they find."""
+        digest = md5.new(bytes).digest()
+        self.classes[digest] = bytes
+        self.classnames[digest] = name
+
+    def __makeBlocks(self):
+        """Split self.classes into chunks that can be compiled to
+        native code by gcj.  In the majority of cases this is not
+        necessary -- the job will have come from a jarfile which will
+        be equivalent to the one we generate -- but this only happens
+        _if_ the job was a jarfile and _if_ the jarfile isn't too big
+        and _if_ the jarfile has the correct extension and _if_ all
+        classes are correctly named and _if_ the jarfile has no
+        embedded jarfiles.  Fitting a special case around all these
+        conditions is tricky to say the least.
+
+        Note that this could be called at the end of each subclass's
+        __init__ method.  The reason this is not done is because we
+        need to parse every class file.  This is slow, and unnecessary
+        if the job is subsetted."""
+        names = {}
+        for hash, bytes in self.classes.items():
+            try:
+                name = classname(bytes)
+            except:
+                warn("job %s: class %s malformed or not a valid class file" % (self.path, self.classnames[hash]))
+                raise
+            if not names.has_key(name):
+                names[name] = []
+            names[name].append(hash)
+        names = names.items()
+        # We have to sort somehow, or the jars we generate 
+        # We sort by name in a simplistic attempt to keep related
+        # classes together so inter-class optimisation can happen.
+        names.sort()
+        self.blocks, bytes = [[]], 0
+        for name, hashes in names:
+            for hash in hashes:
+                if len(self.blocks[-1]) >= MAX_CLASSES_PER_JAR \
+                   or bytes >= MAX_BYTES_PER_JAR:
+                    self.blocks.append([])
+                    bytes = 0
+                self.blocks[-1].append((name, hash))
+                bytes += len(self.classes[hash])
+
+    # From Archit Shah:
+    #   The implementation and the documentation don't seem to match.
+    #  
+    #    [a, b].isSubsetOf([a]) => True
+    #  
+    #   Identical copies of all classes this collection do not exist
+    #   in the other. I think the method should be named isSupersetOf
+    #   and the documentation should swap uses of "this" and "other"
+    #
+    # XXX think about this when I've had more sleep...
+    def isSubsetOf(self, other):
+        """Returns True if identical copies of all classes in this
+        collection exist in the other."""
+        for item in other.classes.keys():
+            if not self.classes.has_key(item):
+                return False
+        return True
+
+    def __targetName(self, ext):
+        return self.basename + ext
+
+    def tempJarName(self, num):
+        return self.__targetName(".%d.jar" % (num + 1))
+
+    def tempObjName(self, num):
+        return self.__targetName(".%d.o" % (num + 1))
+
+    def dsoName(self):
+        """Return the filename of the shared library that will be
+        built from this job."""
+        return self.__targetName(".so")
+
+    def dbName(self):
+        """Return the filename of the mapping database that will be
+        built from this job."""
+        return self.__targetName(".db")
+
+    def ruleArguments(self):
+        """Return a dictionary of values that when substituted
+        into MAKEFILE_JOB will create the rules required to build
+        the shared library and mapping database for this job."""
+        if self.blocks is None:
+            self.__makeBlocks()
+        return {
+            "base": "".join(
+                [c.isalnum() and c or "_" for c in self.dsoName()]),
+            "jars": " \\\n".join(
+                [self.tempJarName(i) for i in xrange(len(self.blocks))]),
+            "dso": self.dsoName(),
+            "db": self.dbName()}
+
+    def writeJars(self):
+        """Generate jarfiles that can be native compiled by gcj."""
+        if self.blocks is None:
+            self.__makeBlocks()
+        for block, i in zip(self.blocks, xrange(len(self.blocks))):
+            jar = zipfile.ZipFile(self.tempJarName(i), "w", zipfile.ZIP_STORED)
+            for name, hash in block:
+                jar.writestr(
+                    zipfile.ZipInfo("%s.class" % name), self.classes[hash])
+            jar.close()
+
+    def clean(self):
+        """Delete all temporary files created during this job's build."""
+        if self.blocks is None:
+            self.__makeBlocks()
+        for i in xrange(len(self.blocks)):
+            os.unlink(self.tempJarName(i))
+            os.unlink(self.tempObjName(i))
+
+class JarJob(Job):
+    """A Job whose origin was a jarfile."""
+
+    def __init__(self, path):
+        Job.__init__(self, path)
+        self._walk(zipfile.ZipFile(path, "r"))
+
+    def _walk(self, zf):
+        for name in zf.namelist():
+            bytes = zf.read(name)
+            if bytes.startswith(ZIPMAGIC):
+                self._walk(zipfile.ZipFile(StringIO.StringIO(bytes)))
+            elif bytes.startswith(CLASSMAGIC):
+                self.addClass(bytes, name)
+
+class DirJob(Job):
+    """A Job whose origin was a directory of classfiles."""
+
+    def __init__(self, path):
+        Job.__init__(self, path)
+        os.path.walk(path, DirJob._visit, self)
+
+    def _visit(self, dir, items):
+        for item in items:
+            path = os.path.join(dir, item)
+            if os.path.islink(path) or not os.path.isfile(path):
+                continue
+            fp = open(path, "r")
+            magic = fp.read(4)
+            if magic == CLASSMAGIC:
+                self.addClass(magic + fp.read(), name)
+    
+def weed_jobs(jobs):
+    """Remove any jarfiles that are completely contained within
+    another.  This is more common than you'd think, and we only
+    need one nativified copy of each class after all."""
+    jobs = copy.copy(jobs)
+    while True:
+        for job1 in jobs:
+            for job2 in jobs:
+                if job1 is job2:
+                    continue
+                if job1.isSubsetOf(job2):
+                    msg = "subsetted %s" % job2.path
+                    if job2.isSubsetOf(job1):
+                        if (isinstance(job1, DirJob) and
+                            isinstance(job2, JarJob)):
+                            # In the braindead case where a package
+                            # contains an expanded copy of a jarfile
+                            # the jarfile takes precedence.
+                            continue
+                        msg += " (identical)"
+                    warn(msg)
+                    jobs.remove(job2)
+                    break
+            else:
+                continue
+            break
+        else:
+            break
+        continue
+    return jobs
+
+def set_basenames(jobs):
+    """Ensure that each jarfile has a different basename."""
+    names = {}
+    for job in jobs:
+        name = os.path.basename(job.path)
+        if not names.has_key(name):
+            names[name] = []
+        names[name].append(job)
+    for name, set in names.items():
+        if len(set) == 1:
+            set[0].basename = name
+            continue
+        # prefix the jar filenames to make them unique
+        # XXX will not work in most cases -- needs generalising
+        set = [(job.path.split(os.sep), job) for job in set]
+        minlen = min([len(bits) for bits, job in set])
+        set = [(bits[-minlen:], job) for bits, job in set]
+        bits = apply(zip, [bits for bits, job in set])
+        while True:
+            row = bits[-2]
+            for bit in row[1:]:
+                if bit != row[0]:
+                    break
+            else:
+                del bits[-2]
+                continue
+            break
+        set = zip(
+            ["_".join(name) for name in apply(zip, bits[-2:])],
+            [job for bits, job in set])
+        for name, job in set:
+            warn("building %s as %s" % (job.path, name))
+            job.basename = name
+    # XXX keep this check until we're properly general
+    names = {}
+    for job in jobs:
+        name = job.basename
+        if names.has_key(name):
+            raise Error, "%s: duplicate jobname" % name
+        names[name] = 1
+
+def system(command):
+    """Execute a command."""
+    status = os.spawnv(os.P_WAIT, command[0], command)
+    if status > 0:
+        raise Error, "%s exited with code %d" % (command[0], status)
+    elif status < 0:
+        raise Error, "%s killed by signal %d" % (command[0], -status)
+
+def warn(msg):
+    """Print a warning message."""
+    print >>sys.stderr, "%s: warning: %s" % (
+        os.path.basename(sys.argv[0]), msg)
+
+def classname(bytes):
+    """Extract the class name from the bytes of a class file."""
+    klass = classfile.Class(bytes)
+    return klass.constants[klass.constants[klass.name][1]][1]
diff --git a/debian/classfile.py b/debian/classfile.py
new file mode 100644 (file)
index 0000000..d7e7d7e
--- /dev/null
@@ -0,0 +1,222 @@
+
+## Copyright (C) 2004, 2005 Red Hat, Inc.
+## Written by Gary Benson <gbenson@redhat.com>
+##
+## 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 2 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.
+
+"""Read Java(TM) class files."""
+
+import cStringIO as StringIO
+import struct
+
+class Class:
+    def __init__(self, arg):
+        if hasattr(arg, "read"):
+            self.fp = arg
+        elif type(arg) == type(""):
+            if arg.startswith("\xca\xfe\xba\xbe"):
+                self.fp = StringIO.StringIO(arg)
+            else:
+                self.fp = open(arg, "r")
+        else:
+            raise TypeError, type(arg)
+
+        magic = self._read_int()
+        assert magic == 0xcafebabeL
+        minor, major = self._read(">HH")        
+        self.version = (major, minor)
+
+        self.pool_integrity_checks = None
+        try:
+            assert False
+        except AssertionError:
+            self.pool_integrity_checks = []
+
+        self._read_constants_pool()
+
+        self.access_flags = self._read_short()
+        self.name = self._read_reference_Class()
+        self.super = self._read_reference_Class()
+
+        self.interfaces = self._read_interfaces()
+        self.fields = self._read_fieldsormethods()
+        self.methods = self._read_fieldsormethods()
+        self.attributes = self._read_attributes()
+
+        if self.pool_integrity_checks is not None:
+            for index, tag in self.pool_integrity_checks:
+                assert self.constants[index][0] == tag
+
+        del self.fp, self.pool_integrity_checks
+
+    def __repr__(self):
+        result = []
+        attrs = [attr for attr in dir(self)
+                 if not attr.startswith("_") and attr != "Member"]
+        attrs.sort()
+        for attr in attrs:
+            result.append("%-13s %s" % (
+                attr + ":", attr == "constants" and
+                "<ELIDED>" or repr(getattr(self, attr))))
+        return "\n".join(result)
+
+    def _read_constants_pool(self):
+        self.constants = {}
+        skip = False
+        for i in xrange(1, self._read_short()):
+            if skip:
+                skip = False
+                continue
+            tag = {
+                1: "Utf8", 3: "Integer", 4: "Float", 5: "Long",
+                6: "Double", 7: "Class", 8: "String", 9: "Fieldref",
+                10: "Methodref", 11: "InterfaceMethodref",
+                12: "NameAndType"}[self._read_byte()]
+            skip = tag in ("Long", "Double") # crack crack crack!
+            self.constants[i] = (tag, getattr(self, "_read_constant_" + tag)())
+
+    def _read_interfaces(self):
+        result = []
+        for i in xrange(self._read_short()):
+            result.append(self._read_reference_Class())
+        return result
+
+    def _read_fieldsormethods(self):
+        result = []
+        for i in xrange(self._read_short()):
+            result.append(self.Member(self))
+        return result
+
+    class Member:
+        def __init__(self, source):
+            self.access_flags = source._read_short()
+            self.name = source._read_reference_Utf8()
+            self.descriptor = source._read_reference_Utf8()
+            self.attributes = source._read_attributes()
+
+        def __repr__(self):
+            result = []
+            attrs = [attr for attr in dir(self) if not attr.startswith("_")]
+            attrs.sort()
+            for attr in attrs:
+                value = getattr(self, attr)
+                if attr == "attributes" and value.has_key("Code"):
+                    value = value.copy()
+                    value.update({"Code": "<ELIDED>"})
+                result.append("%-13s %s" % (
+                    attr + ":", repr(value).replace(
+                        "'Code': '<ELIDED>'", "'Code': <ELIDED>")))
+            return ("\n%s" % (15 * " ")).join(result)
+
+    def _read_attributes(self):
+        result = {}
+        for i in xrange(self._read_short()):
+            name = self._read_reference_Utf8()
+            data = self.fp.read(self._read_int())
+            assert not result.has_key(name)
+            result[name] = data
+        return result
+
+    # Constants pool reference reader convenience functions
+
+    def _read_reference_Utf8(self):
+        return self._read_references("Utf8")[0]
+
+    def _read_reference_Class(self):
+        return self._read_references("Class")[0]
+
+    def _read_reference_Class_NameAndType(self):
+        return self._read_references("Class", "NameAndType")
+
+    def _read_references(self, *args):
+        result = []
+        for arg in args:
+            index = self._read_short()
+            if self.pool_integrity_checks is not None:
+                self.pool_integrity_checks.append((index, arg))
+            result.append(index)
+        return result
+
+    # Constants pool constant reader functions
+
+    def _read_constant_Utf8(self):
+        constant = self.fp.read(self._read_short())
+        try:
+            constant = constant.decode("utf-8")
+        except UnicodeError:
+            constant = _bork_utf8_decode(constant)
+        try:
+            constant = constant.encode("us-ascii")
+        except UnicodeError:
+            pass
+        return constant
+
+    def _read_constant_Integer(self):
+        return self._read_int()
+
+    def _read_constant_Float(self):
+        return self._read(">f")[0]
+
+    def _read_constant_Long(self):
+        return self._read(">q")[0]
+
+    def _read_constant_Double(self):
+        return self._read(">d")[0]
+
+    _read_constant_Class = _read_reference_Utf8
+    _read_constant_String = _read_reference_Utf8
+    _read_constant_Fieldref = _read_reference_Class_NameAndType
+    _read_constant_Methodref = _read_reference_Class_NameAndType
+    _read_constant_InterfaceMethodref = _read_reference_Class_NameAndType
+
+    def _read_constant_NameAndType(self):
+        return self._read_reference_Utf8(), self._read_reference_Utf8()
+
+    # Generic reader functions
+
+    def _read_int(self):
+        # XXX how else to read 32 bits on a 64-bit box?
+        h, l = map(long, self._read(">HH"))
+        return (h << 16) + l
+
+    def _read_short(self):
+        return self._read(">H")[0]
+
+    def _read_byte(self):
+        return self._read("B")[0]
+
+    def _read(self, fmt):
+        return struct.unpack(fmt, self.fp.read(struct.calcsize(fmt)))
+
+def _bork_utf8_decode(data):
+    # more crack!
+    bytes, unicode = map(ord, data), ""
+    while bytes:
+        b1 = bytes.pop(0)
+        if b1 & 0x80:
+            assert b1 & 0x40
+            b2 = bytes.pop(0)
+            assert b2 & 0xC0 == 0x80
+            if b1 & 0x20:
+                assert not b1 & 0x10
+                b3 = bytes.pop(0)
+                assert b3 & 0xC0 == 0x80
+                unicode += unichr(
+                    ((b1 & 0x0f) << 12) + ((b2 & 0x3f) << 6) + (b3 & 0x3f))
+            else:
+                unicode += unichr(((b1 & 0x1f) << 6) + (b2 & 0x3f))
+        else:
+            unicode += unichr(b1)
+    return unicode
+
+if __name__ == "__main__":
+    print Class("/usr/share/katana/build/ListDependentClasses.class")
+
diff --git a/debian/copyright.libgcj-common b/debian/copyright.libgcj-common
new file mode 100644 (file)
index 0000000..9b3c6e2
--- /dev/null
@@ -0,0 +1,31 @@
+gcc-defaults is Copyright (C) 2000, 2001, 2006 Debian.
+
+These scripts are 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 2, or (at your option) any
+later version.
+
+The file classpath.security in the libgcj-common package is part of
+GNU Classpath.  GNU Classpath 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 2, or (at
+your option) any later version.
+
+The files aot-compile aotcompile.py, classfile.py, generate-cacerts.pl
+are
+
+  Copyright (C) 2004, 2005 Red Hat, Inc.
+  Written by Gary Benson <gbenson@redhat.com>
+
+  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 2 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.
+
+On Debian GNU/Linux systems, the complete text of the GNU General
+Public License can be found in `/usr/share/common-licenses/GPL'.
diff --git a/debian/dh_javadoc b/debian/dh_javadoc
new file mode 100644 (file)
index 0000000..aa50462
--- /dev/null
@@ -0,0 +1,141 @@
+#!/usr/bin/perl -w
+
+=head1 NAME
+
+dh_javadoc - generate javadoc documentation and install in package directory
+
+=cut
+
+use strict;
+use Debian::Debhelper::Dh_Lib;
+
+=head1 SYNOPSIS
+
+B<dh_javadoc> [S<I<debhelper options>>] [B<-p<package>>] [B<--sourcedir I<source path>>] [S<I<Java packages>>]
+
+=head1 DESCRIPTION
+
+dh_javadoc is a debhelper program that is responsible for generating HTML Java
+documentation and installing it in package directories. This should be done in
+the documentaion package of all Java libraries. Normal Java programs should not
+be supplied with javadoc documentation (neither in their main package or in a
+separate documentation package)
+
+Any package specified as parameters will be installed into the first package
+dh_javadoc is told to act on. Use of the standard debhelper B<-p> option is
+highly recommended.
+
+A file named debian/package.javadoc may list additional packages to have
+documentation generated. These should be separated by new lines.
+
+When the Java policy is modified, this script will also install links to the
+documentation in a common place so that javadoc pages may be interlinked; and
+also provide a substitution variable for documentation package dependencies.
+
+Javadoc generation is done using gjdoc, currently the only free javadoc
+implementation. When new features are added to this (such as overview files),
+this script will be modified accordingly.
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<--sourcedir I<source path>>
+
+Specify the source path in which to look for Java source files.
+
+=item I<Java packages>
+
+Names of Java packages to be documented.
+
+=back
+
+=head1 TODO
+
+=over 4
+
+=item + 
+
+Check parameters more carefully.
+
+=item + 
+
+Add substvar for documentation dependencies
+
+=item + 
+
+Don't put the 'common' directory in all packages - refer to one in
+/usr/share/gjdoc & insist on creating that dependency 
+
+=item +
+
+Other items depend on gjdoc improvements:
+
+=over 8
+
+=item -
+
+Add package listings to common directory
+
+=item -
+
+Generate dependency substvar based on additional doc packages used.
+
+=back
+
+=back
+
+=cut
+
+use Cwd;
+
+init(options => {
+        "sourcedir=s" => \$dh{SOURCEDIR},
+});
+
+foreach my $package (@{$dh{DOPACKAGES}}) {
+       my $tmp=tmpdir($package);
+
+       my @packages = @ARGV;
+
+       if (-e "debian/$package.javadoc"){
+               open PACKAGES, "debian/$package.javadoc"
+                       or error("Unable to open file: debian/$package.javadoc: $!");
+               my @pkgs;
+               my $i = 0;
+               while(<PACKAGES>){chomp($pkgs[$i++]=$_);}
+               close PACKAGES or warning("Error closing debian/$package.javadoc: $!");
+               @packages = (@packages, @pkgs);
+       }
+       
+       my $src_dir;
+       if ($dh{SOURCEDIR}){
+               $src_dir = getcwd .'/'. $dh{SOURCEDIR};
+       }else{
+               $src_dir = getcwd();
+       }
+
+       if (! -e "/usr/bin/javadoc"){
+               error("/usr/bin/javadoc not found");
+       }
+       
+       # make directory
+       doit('install', '-g', '0', '-o', '0', '-d', "$tmp/usr/share/doc/$package/api/");
+       # generate javadoc
+       doit('javadoc', "-sourcepath",  $src_dir, "-d",  "$tmp/usr/share/doc/$package/api/", @packages);
+  # and remove gjdoc_rawcomment.cache
+  doit('rm', "-f", "gjdoc_rawcomment.cache");
+
+}
+
+=head1 SEE ALSO
+
+L<debhelper(7)>
+
+This program is designed similar to debhelper
+
+=head1 AUTHOR
+
+Mark Howard <mh@debian.org>
+
+=cut
diff --git a/debian/dh_nativejava b/debian/dh_nativejava
new file mode 100644 (file)
index 0000000..206b27a
--- /dev/null
@@ -0,0 +1,101 @@
+#!/usr/bin/perl -w
+
+=head1 NAME
+
+dh_nativejava - compile jar files to native code and register them
+
+=cut
+
+use strict;
+use Debian::Debhelper::Dh_Lib;
+use IO::File;
+use File::Temp qw(tempfile tempdir);
+use Cwd;
+
+=head1 SYNOPSIS
+
+B<dh_nativejava> [S<I<debhelper options>>] [B<-n>] [B<-o>] [B<--sourcedir=>I<dir>]
+
+=head1 DESCRIPTION
+
+dh_nativejava is a debhelper program that is responsible for compiling
+jars to native code and to make them known to the system.
+
+It also automatically generates the postinst and postrm commands needed
+to updated the global classmap database and adds a dependency on
+libgcj-common in the misc:Depends substitution variable.
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-n>, B<--noscripts>
+
+Do not modify postinst/postrm scripts.
+
+=item B<-o>, B<--onlyscripts>
+
+Only modify postinst/postrm scripts, do not actually compile any files
+or register them. May be useful if the files are already built and
+registered.
+
+=item B<--destdir=>I<directory>
+
+Use this if you want the compiled files to be put in a directory
+other than the default of "/usr/lib/gcj"
+
+=back
+
+=head1 NOTES
+
+Note that this command is not idempotent. "dh_clean -k" should be called
+between invocations of this command. Otherwise, it may cause multiple
+instances of the same text to be added to maintainer scripts.
+
+=cut
+
+init();
+
+my $destdir = $dh{DESTDIR};
+if (! $dh{DESTDIR}) {
+       $destdir = "/usr/lib/gcj";
+}
+
+my $pwd = getcwd;
+my ($tdir, $fh, $sourcelist);
+$tdir = tempdir(CLEANUP => 1);
+($fh, $sourcelist) = tempfile("sourcesXXXXX", DIR => $tdir);
+
+foreach my $package (@{$dh{DOPACKAGES}}) {
+       my $tmp=tmpdir($package);
+
+       # Figure out if this is a GCJ package.
+       if ($tmp =~ '-gcj$') {
+               my $jardir =$tmp;
+               $jardir =~ s/-gcj$//;
+               if (! $dh{ONLYSCRIPTS}) {
+                       complex_doit("find $pwd -type f ! -type l > $sourcelist");
+                       doit("aot-compile", "-L", $destdir, "-c", "-fsource-filename=$sourcelist", "$jardir", "$tmp/usr/lib/gcj");
+                       doit("mkdir", "-p", "$tmp/usr/share/gcj/classmap.d");
+                       complex_doit("mv $tmp/usr/lib/gcj/*.db $tmp/usr/share/gcj/classmap.d");
+               }
+               # Install scripts to rebuild global classmap.db.
+               if (! $dh{NOSCRIPTS}) {
+                       autoscript($package,"postinst", "postinst-rebuild-gcj-db", "");
+                       autoscript($package,"postrm", "postrm-rebuild-gcj-db", "");
+               }
+               addsubstvar($package, "misc:Depends", "libgcj-common (>> 1:4.1.1-13)");
+       }
+}
+
+END { unlink($sourcelist) or die "Couldn't unlink $sourcelist : $!" }
+
+=head1 SEE ALSO
+
+L<debhelper(7)>
+
+=head1 AUTHOR
+
+Michael Koch <mkoch@debian.org>, Matthias Klose <doko@ubuntu.com>
+
+=cut
diff --git a/debian/generate-cacerts.pl.in b/debian/generate-cacerts.pl.in
new file mode 100644 (file)
index 0000000..b90f6ef
--- /dev/null
@@ -0,0 +1,106 @@
+#!/usr/bin/perl
+
+# Copyright (C) 2007, 2009 Free Software Foundation
+#
+# 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 2 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.
+
+# generate-cacerts.pl generates a gkeytool keystore named 'cacerts'
+# from OpenSSL's certificate bundle.
+
+# First extract each of OpenSSL's bundled certificates into its own
+# aliased filename.
+chomp($file=@ARGV[0]);
+$file = "/etc/pki/tls/cert.pem" unless $file ne "";
+open(CERTS, $file);
+@certs = <CERTS>;
+close(CERTS);
+
+$pem_file_number = 0;
+$writing_cert = 0;
+foreach $cert (@certs)
+{
+        if ($cert eq "-----BEGIN CERTIFICATE-----\n")
+        {
+                 if ($writing_cert != 0)
+                 {
+                               die "$file is malformed.";
+                 }
+                 $pem_file_number++;
+                 # Numbering each file guarantees that cert aliases will be
+                 # unique.
+                 $pem_file_name = "$pem_file_number$cert_alias.pem";
+                 $writing_cert = 1;
+                 open(PEM, ">$pem_file_name");
+                 print PEM $cert;
+        }
+        elsif ($cert eq "-----END CERTIFICATE-----\n")
+        {
+                 $writing_cert = 0;
+                 print PEM $cert;
+                 close(PEM);
+        }
+        elsif ($cert =~ /Issuer: /)
+        {
+                 # Generate an alias using the OU and CN attributes of the
+                 # Issuer field if both are present, otherwise use only the CN
+                 # attribute.  The Issuer field must have either the OU or the
+                 # CN attribute.
+                 $_ = $cert;
+                 if ($cert =~ /OU=/)
+                 {
+                               s/Issuer:.*?OU=//;
+                               # Remove other occurrences of OU=.
+                               s/OU=.*CN=//;
+                               # Remove CN= if there were not other occurrences of OU=.
+                               s/CN=//;
+                 }
+                 elsif ($cert =~ /CN=/)
+                 {
+                               s/Issuer:.*CN=//;
+                 }
+                 s/\W//g;
+                 tr/A-Z/a-z/;
+                 $cert_alias = $_
+        }
+        else
+        {
+                 if ($writing_cert == 1)
+                 {
+                               print PEM $cert;
+                 }
+        }
+}
+
+# Check that the correct number of .pem files were produced.
+@pem_files = <*.pem>;
+if (@pem_files != $pem_file_number)
+{
+        die "Number of .pem files produced does not match".
+                 " number of certs read from $file.";
+}
+
+# Now store each cert in the 'cacerts' file using gkeytool.
+$certs_written_count = 0;
+foreach $pem_file (@pem_files)
+{
+        system "yes | gkeytool@gcc_suffix@ -import -alias `basename $pem_file .pem`".
+                 " -keystore cacerts -storepass '' -file $pem_file".
+                 " 2>&1 >/dev/null";
+        unlink($pem_file);
+        $certs_written_count++;
+}
+
+# Check that the correct number of certs were added to the keystore.
+if ($certs_written_count != $pem_file_number)
+{
+        die "Number of certs added to keystore does not match".
+                 " number of certs read from $file.";
+}
diff --git a/debian/gij.prerm b/debian/gij.prerm
new file mode 100644 (file)
index 0000000..b368ea4
--- /dev/null
@@ -0,0 +1,8 @@
+#! /bin/sh -e
+
+# make sure that no more alternatives are around from the libgcj2 package
+update-alternatives --remove gij /usr/bin/gij-3.0 >/dev/null 2>&1 || true
+
+#DEBHELPER#
+
+exit 0
diff --git a/debian/libgcj-bc.overrides b/debian/libgcj-bc.overrides
new file mode 100644 (file)
index 0000000..d5e53ef
--- /dev/null
@@ -0,0 +1 @@
+libgcj-bc: pkg-has-shlibs-control-file-but-no-actual-shared-libs
diff --git a/debian/libgcj-common.postinst b/debian/libgcj-common.postinst
new file mode 100644 (file)
index 0000000..cdffa42
--- /dev/null
@@ -0,0 +1,9 @@
+#! /bin/sh
+
+set -e
+
+rebuild-security-providers
+
+#DEBHELPER#
+
+exit 0
diff --git a/debian/libgcj-common.preinst b/debian/libgcj-common.preinst
new file mode 100644 (file)
index 0000000..38a71de
--- /dev/null
@@ -0,0 +1,21 @@
+#!/bin/sh
+
+set -e
+
+case "$1" in
+    install|upgrade)
+       if [ -L /usr/share/doc/libgcj-common ]; then
+           rm -f /usr/share/doc/libgcj-common
+       fi
+       ;;
+    abort-upgrade)
+       ;;
+    *)
+        echo "preinst called with unknown argument \`$1'" >&2
+        exit 1
+    ;;
+esac
+
+#DEBHELPER#
+
+exit 0
diff --git a/debian/libgcj-common.prerm b/debian/libgcj-common.prerm
new file mode 100644 (file)
index 0000000..9acef4a
--- /dev/null
@@ -0,0 +1,12 @@
+#! /bin/sh
+
+set -e
+
+case "$1" in
+    remove)
+       rm -f /var/lib/security/classpath.security
+esac
+
+#DEBHELPER#
+
+exit 0
diff --git a/debian/postinst-rebuild-gcj-db b/debian/postinst-rebuild-gcj-db
new file mode 100644 (file)
index 0000000..e1a745e
--- /dev/null
@@ -0,0 +1,3 @@
+if which rebuild-gcj-db >/dev/null 2>&1; then
+       rebuild-gcj-db
+fi
diff --git a/debian/postrm-rebuild-gcj-db b/debian/postrm-rebuild-gcj-db
new file mode 100644 (file)
index 0000000..e1a745e
--- /dev/null
@@ -0,0 +1,3 @@
+if which rebuild-gcj-db >/dev/null 2>&1; then
+       rebuild-gcj-db
+fi
diff --git a/debian/rebuild-gcj-db b/debian/rebuild-gcj-db
new file mode 100644 (file)
index 0000000..297a00b
--- /dev/null
@@ -0,0 +1,106 @@
+#! /bin/bash
+
+set -e
+
+if [ $# -gt 1 ]; then
+    cat 1>&2 <<-EOF
+       rebuild-gcj-db: re-build the gcj classmap database
+       
+       usage: $0 [install|remove]
+       EOF
+    exit 1
+fi
+
+mode=install
+case "$1" in
+    install|remove)
+       mode=$1;;
+esac
+
+uname=$(uname -m)
+
+rebuild_db()
+{
+    dbtool=$1; shift
+    dbLocation=$1; shift
+    dirs=
+
+    for dir; do [ -d $dir ] && dirs="$dirs $dir"; done
+    if [ -z "$dirs" ]; then
+       # no more dirs with .db files on the system
+       return 0
+    fi
+    mkdir -p $(dirname $dbLocation)
+    if $dbtool -n $dbLocation.tmp 64; then
+       :
+       #case "$uname" in parisc*)
+       #    echo >&2 "$dbtool succeeded unexpectedly"
+       #esac
+    else
+       case "$uname" in
+           m68k)
+               echo >&2 "ERROR: $dbtool did fail; known problem on $uname"
+               return 0;;
+           *)
+               exit 2
+       esac
+    fi
+    find $dirs -follow -name '*.db' -print0 | \
+       xargs -r -0 $dbtool -m $dbLocation.tmp $dbLocation.tmp || exit 1
+    mv $dbLocation.tmp $dbLocation
+}
+
+
+rebuild_databases()
+{
+    v=$1
+    dbtool=gcj-dbtool-$1
+    dbLocation=`$dbtool -p || true`
+
+    if [ -n "$dbLocation" ]; then
+       case "$uname" in m68k)
+           echo >&2 "$dbtool succeeded unexpectedly"
+       esac
+    else
+       case "$uname" in
+           m68k)
+               echo >&2 "ERROR: $dbtool did fail; known problem on $uname"
+               return 0;;
+           *)
+               exit 2
+       esac
+    fi
+
+    if [ "$mode" = remove ] && [ ! -f "$dbLocation" ]; then
+       # libgcj7-0 or libgcj8 are already removed; no need
+       # to rebuild anything
+       return 0
+    fi
+    rebuild_db \
+       $dbtool \
+       $dbLocation \
+       /usr/share/gcj/classmap.d \
+       /usr/share/gcj-$v/classmap.d
+}
+
+# still different databases for each gcj-4.x
+
+if which gcj-dbtool-4.9 >/dev/null 2>&1; then
+    rebuild_databases 4.9
+fi
+
+if which gcj-dbtool-4.8 >/dev/null 2>&1; then
+    rebuild_databases 4.8
+fi
+
+if which gcj-dbtool-4.7 >/dev/null 2>&1; then
+    rebuild_databases 4.7
+fi
+
+if which gcj-dbtool-4.6 >/dev/null 2>&1; then
+    rebuild_databases 4.6
+fi
+
+if which gcj-dbtool-4.4 >/dev/null 2>&1; then
+    rebuild_databases 4.4
+fi
diff --git a/debian/rebuild-security-providers b/debian/rebuild-security-providers
new file mode 100755 (executable)
index 0000000..bd33a66
--- /dev/null
@@ -0,0 +1,19 @@
+#! /bin/bash
+# Rebuild the list of security providers in classpath.security
+
+secfiles="/var/lib/security/classpath.security"
+
+for secfile in $secfiles; do
+  # check if this classpath.security file exists
+  #[ -f "$secfile" ] || continue
+
+  sed '/^security\.provider\./d' /etc/java/security/classpath.security \
+      > $secfile
+
+  count=0
+  for provider in $(ls /etc/java/security/security.d)
+  do
+    count=$((count + 1))
+    echo "security.provider.${count}=${provider#*-}" >> "$secfile"
+  done
+done
index 0cd8fbd07988ce0f4601b31b219322b1e01653e1..53c17e3fb40e87acb5f43e1f3407b839cd1a3905 100755 (executable)
@@ -177,7 +177,9 @@ REQV_33             := (>= 1:3.3.6-1)
 REQV_34                := (>= 3.4.6-1)
 REQV_40                := (>= 4.0.3-1)
 REQV_41                := (>= 4.1.2-1)
+REQV_41_GCJ    := (>= 4.1.2-1)
 REQV_42                := (>= 4.2.4-1)
+REQV_42_GCJ    := (>= 4.2.4-1)
 REQV_43                := (>= 4.3.5-1)
 REQV_44                := (>= 4.4.7-1~)
 REQV_45                := (>= 4.5.3-1)
@@ -189,6 +191,7 @@ REQV_49             := (>= 4.9.3-10~)
 REQV_5         := (>= 5.4.1-2~)
 REQV_6         := (>= 6.4.0-1~)
 REQV_7         := (>= 7.3.0-11~)
+REQV_LIBGCJ_BC := (>= 6.4.0-1~)
 REQV_8         := (>= 8.3.0-6~)
 REQV_9         := (>= 9.2.1-1~)
 
@@ -435,6 +438,16 @@ ifeq (,$(filter $(distrelease),lenny etch squeeze dapper hardy jaunty karmic luc
   with_multiarch_lib := yes
 endif
 
+LIBGCJ         = libgcj17
+LIBGCJ_PC      = libgcj17.pc
+LIBGCJ_SONAME  = 17
+
+ifneq (,$(filter $(DEB_HOST_ARCH),$(gcj5_archs)))
+  LIBGCJ       = libgcj16
+  LIBGCJ_PC    = libgcj16.pc
+  LIBGCJ_SONAME        = 16
+endif
+
 ifneq (,$(filter $(DEB_HOST_ARCH), $(multilib_archs)))
   with_multilib = yes
 endif
@@ -452,6 +465,11 @@ ifeq ($(with_native),yes)
     no_packages += gccgo
   endif
 
+  java_no_archs := arm
+  ifneq (,$(filter $(DEB_HOST_ARCH),$(java_no_archs)))
+    #no_packages += libgcj-bc gcj-jre-headless gcj-jre gcj-jdk
+  endif
+
   gdc_no_archs = s390
   ifneq (,$(filter $(DEB_HOST_ARCH),$(gdc_no_archs)))
     no_packages += gdc
@@ -512,29 +530,39 @@ endif
 packages := $(filter-out $(no_packages), $(all_packages))
 
 # derived version number (without release, e.g. 4.9.3, 5.2.1)
-$(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GDC V_GM2 V_BRIG V_OFFL, \
+$(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GCJ V_GIJ V_GDC V_BRIG V_OFFL, \
   $(eval $(v) = $(patsubst %-$(lastword $(subst -, ,$(call C$(v)))),%,$(call C$(v)))) \
 )
 $(foreach a, $(all_archs), \
-  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GDC V_GM2 V_BRIG V_OFFL, \
+  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GCJ V_GIJ V_GDC V_BRIG V_OFFL, \
     $(eval $(v)_$(a) = $(patsubst %-$(lastword $(subst -, ,$(call C$(v)_$(a)))),%,$(call C$(v)_$(a)))) \
 ))
 
 # number for the package name (e.g. 4.9, 5, 6)
-$(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GDC V_GM2 V_BRIG V_OFFL, \
+$(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GCJ V_GIJ V_GDC V_BRIG V_OFFL, \
   $(eval P$(v) = $(firstword $(subst -, ,$(subst ., ,$(call $(v)))))) \
 )
 $(foreach a, $(all_archs), \
-  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GDC V_GM2 V_BRIG V_OFFL, \
+  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GNAT V_GCJ V_GIJ V_GDC V_BRIG V_OFFL, \
     $(eval P$(v)_$(a) = $(firstword $(subst -,  ,$(subst ., ,$(call $(v)_$(a)))))) \
 ))
 
 ifneq (,$(filter $(DEB_HOST_ARCH), $(gcc49_archs)))
-  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GDC V_GM2 V_BRIG V_OFFL, \
+  $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GDC V_BRIG V_OFFL, \
     $(eval P$(v) = $(subst $(SPACE),.,$(wordlist 1,2,$(subst ., ,$(call $(v)))))) \
   )
   $(foreach a, $(gcc49_archs), \
-    $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GDC V_GM2 V_BRIG V_OFFL, \
+    $(foreach v, V_CPP V_GCC V_GPP V_GOBJC V_GOBJCXX V_GFORT V_GGO V_GDC V_BRIG V_OFFL, \
+      $(eval P$(v)_$(a) = $(subst $(SPACE),.,$(wordlist 1,2,$(subst ., ,$(call $(v)_$(a)))))) \
+  ))
+endif
+
+ifneq (,$(filter $(DEB_HOST_ARCH), $(gcj49_archs)))
+  $(foreach v, V_GCJ V_GIJ, \
+    $(eval P$(v) = $(subst $(SPACE),.,$(wordlist 1,2,$(subst ., ,$(call $(v)))))) \
+  )
+  $(foreach a, $(gcj49_archs), \
+    $(foreach v, V_GCJ V_GIJ, \
       $(eval P$(v)_$(a) = $(subst $(SPACE),.,$(wordlist 1,2,$(subst ., ,$(call $(v)_$(a)))))) \
   ))
 endif
@@ -565,6 +593,8 @@ README:
           -DV_GFORT=$(V_GFORT) -DPV_GFORT=$(PV_GFORT) \
           -DV_GGO=$(V_GGO)     -DPV_GGO=$(PV_GGO) \
           -DV_GNAT=$(V_GNAT)   -DPV_GNAT=$(PV_GNAT) \
+          -DV_GCJ=$(V_GCJ)     -DPV_GCJ=$(PV_GCJ) \
+          -DV_GIJ=$(V_GIJ)     -DPV_GIJ=$(PV_GIJ) \
           -DV_GDC=$(V_GDC)     -DPV_GDC=$(PV_GDC) \
           -DV_GM2=$(V_GM2)     -DPV_GM2=$(PV_GM2) \
           -DV_BRIG=$(V_BRIG)     -DPV_BRIG=$(PV_BRIG) \
@@ -586,11 +616,13 @@ substvars-native:
          echo 'version:gpp=$(EPOCH):$(CV_GPP)'; \
          echo 'version:gobjc=$(EPOCH):$(CV_GOBJC)'; \
          echo 'version:gobjcxx=$(EPOCH):$(CV_GOBJCXX)'; \
+         echo 'version:gij=$(EPOCH):$(CV_GIJ)'; \
+         echo 'version:gcj=$(EPOCH):$(CV_GCJ)'; \
          echo 'version:gfort=$(EPOCH):$(CV_GFORT)'; \
          echo 'version:ggo=$(EPOCH):$(CV_GGO)'; \
          echo 'version:gnat=$(EPOCH):$(CV_GNAT)'; \
          echo 'version:gdc=$(CV_GDC)'; \
-         echo 'version:gm2=$(CV_GM2)'; \
+         echo 'version:libgcjcommon=$(CV_LIBGCJCOMMON)'; \
          echo 'version:brig=$(CV_BRIG)'; \
          echo 'version:offl=$(CV_OFFL)'; \
          echo 'pv:cpp=$(PV_CPP)'; \
@@ -601,6 +633,8 @@ substvars-native:
          echo 'pv:gfort=$(PV_GFORT)'; \
          echo 'pv:ggo=$(PV_GGO)'; \
          echo 'pv:gnat=$(PV_GNAT)'; \
+         echo 'pv:gcj=$(PV_GCJ)'; \
+         echo 'pv:gij=$(PV_GIJ)'; \
          echo 'pv:gdc=$(PV_GDC)'; \
          echo 'pv:gm2=$(PV_GM2)'; \
          echo 'pv:brig=$(PV_BRIG)'; \
@@ -613,10 +647,15 @@ substvars-native:
          echo 'reqv:gfort=$(REQV_GFORT)'; \
          echo 'reqv:ggo=$(REQV_GGO)'; \
          echo 'reqv:gnat=$(REQV_GNAT)'; \
+         echo 'reqv:gcj=$(REQV_GCJ)'; \
+         echo 'reqv:gij=$(REQV_GIJ)'; \
          echo 'reqv:gdc=$(REQV_GDC)'; \
          echo 'reqv:gm2=$(REQV_GM2)'; \
          echo 'reqv:brig=$(REQV_BRIG)'; \
          echo 'reqv:offl=$(REQV_OFFL)'; \
+         echo 'pkg:libgcj=$(LIBGCJ)'; \
+         echo 'pkg:libgcjawt=$(LIBGCJ)-awt'; \
+         echo 'version:libgcjbc=$(CV_LIBGCJBC)'; \
          echo 'gcc:triplet=gcc-$(subst _,-,$(DEB_HOST_GNU_TYPE)) (= $(EPOCH):$(CV_GCC))'; \
          echo 'gpp:triplet=g++-$(subst _,-,$(DEB_HOST_GNU_TYPE)) (= $(EPOCH):$(CV_GPP))'; \
        ) > debian/substvars.native
@@ -631,6 +670,13 @@ ifeq ($(with_multilib),yes)
          echo 'pkgmulti:gdc=gdc-multilib'; \
        ) >> debian/substvars.native
 endif
+       ( \
+         echo 'dep:jrehl=gcj-$${pv:gij}-jre-headless $${reqv:gij}'; \
+         echo 'dep:jre=gcj-$${pv:gij}-jre $${reqv:gij}'; \
+         echo 'dep:jdk=gcj-$${pv:gcj}-jdk $${reqv:gcj}'; \
+         echo 'pkg:gjdoc=gjdoc'; \
+         echo 'ver:gcjconflict=4:4.4.0-2'; \
+       ) >> debian/substvars.native
 ifneq (,$(MOD_VER))
        echo 'fortran:mod-version=$(MOD_VER)' >> debian/substvars.native
 endif
@@ -645,6 +691,7 @@ substvars.%:
          echo 'version:gpp=$(EPOCH):$(CV_GPP_$(CROSS_ARCH))'; \
          echo 'version:gobjc=$(EPOCH):$(CV_GOBJC_$(CROSS_ARCH))'; \
          echo 'version:gobjcxx=$(EPOCH):$(CV_GOBJCXX_$(CROSS_ARCH))'; \
+         echo 'version:gcj=$(EPOCH):$(CV_GCJ_$(CROSS_ARCH))'; \
          echo 'version:gfort=$(EPOCH):$(CV_GFORT_$(CROSS_ARCH))'; \
          echo 'version:ggo=$(EPOCH):$(CV_GGO_$(CROSS_ARCH))'; \
          echo 'version:gdc=$(CV_GDC_$(CROSS_ARCH))'; \
@@ -656,6 +703,7 @@ substvars.%:
          echo 'pv:gobjcxx=$(PV_GOBJCXX_$(CROSS_ARCH))'; \
          echo 'pv:gfort=$(PV_GFORT_$(CROSS_ARCH))'; \
          echo 'pv:ggo=$(PV_GGO_$(CROSS_ARCH))'; \
+         echo 'pv:gcj=$(PV_GCJ_$(CROSS_ARCH))'; \
          echo 'pv:gdc=$(PV_GDC_$(CROSS_ARCH))'; \
          echo 'pv:gm2=$(PV_GM2_$(CROSS_ARCH))'; \
          echo 'reqv:cpp=$(REQV_CPP_$(CROSS_ARCH))'; \
@@ -665,6 +713,7 @@ substvars.%:
          echo 'reqv:gobjcxx=$(REQV_GOBJCXX_$(CROSS_ARCH))'; \
          echo 'reqv:gfort=$(REQV_GFORT_$(CROSS_ARCH))'; \
          echo 'reqv:ggo=$(REQV_GGO_$(CROSS_ARCH))'; \
+         echo 'reqv:gcj=$(REQV_GCJ_$(CROSS_ARCH))'; \
          echo 'reqv:gdc=$(REQV_GDC_$(CROSS_ARCH))'; \
          echo 'reqv:gm2=$(REQV_GM2_$(CROSS_ARCH))'; \
        ) > debian/substvars.$*
@@ -680,6 +729,9 @@ substvars.%:
            echo 'pkgmulti:gm2=gm2-multilib'; \
          ) >> debian/substvars.$*; \
        )
+       ( \
+         echo 'dep:gcj=gcj-$${pv:gcj} $${reqv:gcj}'; \
+       ) >> debian/substvars.$*
 ifneq (,$(MOD_VER))
        echo 'fortran:mod-version=$(MOD_VER)' >> debian/substvars.$*
 endif
@@ -740,7 +792,10 @@ clean:
        rm -rf build
        rm -f debian/control.tmp*
        rm -f debian/substvars.*
+       rm -f debian/lib*gcj-bc.shlibs
        rm -f debian/gcc.postinst debian/g++.postinst debian/gfortran.postinst
+       rm -f debian/generate-cacerts.pl
+       rm -f debian/dh_nativejava.1
        dh_clean
 
 pre-install: build substvars
@@ -963,6 +1018,163 @@ ifneq (,$(filter gccgo, $(packages)))
   endif
 endif
 
+ifneq (,$(filter gcj-jdk, $(packages)))
+       : # gcj-jre-headless
+       dh_installdirs -pgcj-jre-headless usr/bin /usr/share/man/man1 usr/share/doc
+       dh_link -pgcj-jre-headless \
+         /usr/share/doc/libgcj-common /usr/share/doc/gcj-jre-headless \
+         /usr/bin/gij-$(PV_GIJ) /usr/bin/gij \
+         /usr/bin/gcj-dbtool-$(PV_GIJ) /usr/bin/gcj-dbtool \
+         /usr/bin/gkeytool-$(PV_GIJ) /usr/bin/gkeytool \
+         /usr/bin/gorbd-$(PV_GIJ) /usr/bin/gorbd \
+         /usr/bin/grmid-$(PV_GIJ) /usr/bin/grmid \
+         /usr/bin/grmiregistry-$(PV_GIJ) /usr/bin/grmiregistry \
+
+       : # gcj-jdk
+       dh_installdirs -pgcj-jdk usr/bin /usr/share/man/man1 usr/share/doc
+       dh_link -pgcj-jdk \
+         /usr/share/doc/cpp /usr/share/doc/gcj-jdk \
+         /usr/bin/gjavah-$(PV_GCJ) /usr/bin/gjavah \
+         /usr/bin/gcj-$(PV_GCJ) /usr/bin/gcj \
+         /usr/bin/gcj-$(PV_GCJ) /usr/bin/$(DEB_HOST_GNU_TYPE)-gcj \
+         /usr/bin/gcjh-$(PV_GCJ) /usr/bin/gcjh \
+         /usr/bin/gjar-$(PV_GCJ) /usr/bin/gjar \
+         /usr/bin/gjarsigner-$(PV_GCJ) /usr/bin/gjarsigner \
+         /usr/bin/grmic-$(PV_GCJ) /usr/bin/grmic \
+         /usr/bin/jv-convert-$(PV_GCJ) /usr/bin/jv-convert \
+         /usr/bin/jcf-dump-$(PV_GCJ) /usr/bin/jcf-dump \
+         /usr/bin/gcj-wrapper-$(PV_GCJ) /usr/bin/gcj-wrapper \
+         /usr/bin/gtnameserv-$(PV_GCJ) /usr/bin/gtnameserv \
+         /usr/bin/gappletviewer-$(PV_GCJ) /usr/bin/gappletviewer \
+         /usr/bin/gserialver-$(PV_GIJ) /usr/bin/gserialver \
+         /usr/share/java/libgcj-$(PV_GCJ).jar /usr/share/java/libgcj.jar
+ifeq ($(with_multiarch_lib),yes)
+       dh_link -pgcj-jdk \
+         /usr/lib/$(DEB_HOST_MULTIARCH)/pkgconfig/$(LIBGCJ_PC) \
+         /usr/lib/$(DEB_HOST_MULTIARCH)/pkgconfig/libgcj.pc
+else
+       dh_link -pgcj-jdk \
+         /usr/lib/pkgconfig/$(LIBGCJ_PC) /usr/lib/pkgconfig/libgcj.pc
+endif
+
+       dh_link -pgcj-jre-headless \
+         /usr/share/man/man1/gkeytool-$(PV_GIJ).1.gz /usr/share/man/man1/gkeytool.1.gz \
+         /usr/share/man/man1/gorbd-$(PV_GIJ).1.gz /usr/share/man/man1/gorbd.1.gz \
+         /usr/share/man/man1/grmid-$(PV_GIJ).1.gz /usr/share/man/man1/grmid.1.gz \
+         /usr/share/man/man1/grmiregistry-$(PV_GIJ).1.gz /usr/share/man/man1/grmiregistry.1.gz
+
+       dh_link -pgcj-jdk \
+         /usr/share/man/man1/gjar-$(PV_GCJ).1.gz /usr/share/man/man1/gjar.1.gz \
+         /usr/share/man/man1/gjarsigner-$(PV_GCJ).1.gz /usr/share/man/man1/gjarsigner.1.gz \
+         /usr/share/man/man1/gjavah-$(PV_GCJ).1.gz /usr/share/man/man1/gjavah.1.gz \
+         /usr/share/man/man1/gnative2ascii-$(PV_GIJ).1.gz /usr/share/man/man1/gnative2ascii.1.gz \
+         /usr/share/man/man1/gtnameserv-$(PV_GCJ).1.gz /usr/share/man/man1/gtnameserv.1.gz \
+         /usr/share/man/man1/gappletviewer-$(PV_GCJ).1.gz /usr/share/man/man1/gappletviewer.1.gz \
+         /usr/share/man/man1/gserialver-$(PV_GIJ).1.gz /usr/share/man/man1/gserialver.1.gz
+
+  ifeq ($(with_gfdl_docs),yes)
+       dh_link -pgcj-jre-headless \
+         /usr/share/man/man1/gij-$(PV_GIJ).1.gz /usr/share/man/man1/gij.1.gz \
+         /usr/share/man/man1/gcj-dbtool-$(PV_GIJ).1.gz /usr/share/man/man1/gcj-dbtool.1.gz
+       dh_link -pgcj-jdk \
+         /usr/share/man/man1/gcj-$(PV_GCJ).1.gz /usr/share/man/man1/gcj.1.gz \
+         /usr/share/man/man1/gcj-$(PV_GCJ).1.gz /usr/share/man/man1/$(DEB_HOST_GNU_TYPE)-gcj.1.gz \
+         /usr/share/man/man1/gcjh-$(PV_GCJ).1.gz /usr/share/man/man1/gcjh.1.gz \
+         /usr/share/man/man1/grmic-$(PV_GCJ).1.gz /usr/share/man/man1/grmic.1.gz \
+         /usr/share/man/man1/jv-convert-$(PV_GCJ).1.gz /usr/share/man/man1/jv-convert.1.gz \
+         /usr/share/man/man1/jcf-dump-$(PV_GCJ).1.gz /usr/share/man/man1/jcf-dump.1.gz \
+         /usr/share/man/man1/gcj-wrapper-$(PV_GCJ).1.gz /usr/share/man/man1/gcj-wrapper.1.gz \
+         /usr/share/info/gcj-$(PV_GCJ).info.gz /usr/share/info/gcj.info.gz
+  endif
+
+       dh_link -pgcj-jdk \
+         /usr/bin/gjdoc-$(PV_GCJ) /usr/bin/gjdoc \
+         /usr/share/man/man1/gjdoc-$(PV_GCJ).1.gz /usr/share/man/man1/gjdoc.1.gz
+       cp -p debian/dh_javadoc debian/gcj-jdk/usr/bin/
+       pod2man -c Debhelper -r $(PV_GCJ) \
+               debian/dh_javadoc debian/gcj-jdk/usr/share/man/man1/dh_javadoc.1
+
+       : # libgcj-bc
+  ifeq ($(with_multiarch_lib),yes)
+       dh_installdirs -plibgcj-bc \
+               usr/lib/$(DEB_HOST_MULTIARCH) usr/share/doc usr/share/lintian/overrides
+       ln -s libgcj.so.$(LIBGCJ_SONAME) \
+               debian/libgcj-bc/usr/lib/$(DEB_HOST_MULTIARCH)/libgcj_bc.so.1
+  else
+       dh_installdirs -plibgcj-bc \
+               usr/lib usr/share/doc usr/share/lintian/overrides
+       ln -s libgcj.so.$(LIBGCJ_SONAME) \
+               debian/libgcj-bc/usr/lib/libgcj_bc.so.1
+  endif
+       dh_link -plibgcj-bc \
+         /usr/share/doc/libgcj-common /usr/share/doc/libgcj-bc
+
+       mkdir -p debian/libgcj-bc/usr/share/lintian/overrides
+       cp -p debian/libgcj-bc.overrides \
+               debian/libgcj-bc/usr/share/lintian/overrides/libgcj-bc
+
+       echo "libgcj_bc 1 libgcj-bc $(REQV_LIBGCJ_BC)" \
+               > debian/libgcj-bc.shlibs
+
+       : # gcj-jre-headless
+       dh_installdirs -pgcj-jre-headless \
+               usr/share/doc usr/lib/jvm
+       ln -sf java-1.5.0-gcj-$(PV_GCJ)-$(DEB_HOST_ARCH) \
+               debian/gcj-jre-headless/usr/lib/jvm/java-1.5.0-gcj
+       ln -sf java-gcj-$(PV_GCJ) \
+               debian/gcj-jre-headless/usr/lib/jvm/java-gcj
+endif
+
+ifneq (,$(gcj_archs))
+       : # libgcj-common
+       dh_installdirs -plibgcj-common \
+         /usr/bin \
+         /usr/sbin \
+         /etc/java/security/security.d \
+         /usr/lib/security \
+         /var/lib/security \
+         /usr/share/gcj
+       install -m644 classpath.security debian/libgcj-common/etc/java/security/
+       dh_link -plibgcj-common \
+         /var/lib/security/classpath.security /usr/lib/security/classpath.security
+       install -m755 debian/rebuild-gcj-db \
+               debian/libgcj-common/usr/bin/
+       install -m755 debian/rebuild-security-providers \
+               debian/libgcj-common/usr/sbin/
+       ( \
+         echo "# architectures with gcj support"; \
+         echo "gcj_archs = $(gcj_archs)"; \
+         echo "# architectures which should provide gcj native support"; \
+         echo "gcj_native_archs = $(gcj_native_archs)" \
+       ) > debian/libgcj-common/usr/share/gcj/debian_defaults
+
+       : # GNU security provider
+       for i in \
+         1000-gnu.java.security.provider.Gnu \
+         1001-gnu.javax.crypto.jce.GnuCrypto \
+         1002-gnu.javax.crypto.jce.GnuSasl \
+         1003-gnu.javax.net.ssl.provider.Jessie \
+         1004-gnu.javax.security.auth.callback.GnuCallbacks; \
+       do \
+         touch debian/libgcj-common/etc/java/security/security.d/$$i; \
+       done
+
+       : # aotcompile & dh_nativejava
+
+       mkdir -p debian/libgcj-common/usr/bin
+       install -m755 debian/aot-compile debian/libgcj-common/usr/bin/
+       mkdir -p debian/libgcj-common/usr/lib/gcc
+       install -m644 debian/*.py debian/libgcj-common/usr/lib/gcc
+
+       install -m755 debian/dh_nativejava debian/libgcj-common/usr/bin/
+       mkdir -p debian/libgcj-common/usr/share/debhelper/autoscripts
+       install -m 644 debian/p*-rebuild-gcj-db \
+               debian/libgcj-common/usr/share/debhelper/autoscripts/
+       pod2man -c Debhelper debian/dh_nativejava debian/dh_nativejava.1
+       mkdir -p debian/libgcj-common/usr/share/man/man1
+       install -m644 debian/dh_nativejava.1 debian/libgcj-common/usr/share/man/man1/
+endif
+
 ifneq (,$(filter gccbrig, $(packages)))
        : # gccbrig
        dh_installdirs -pgccbrig
@@ -1140,6 +1352,19 @@ install.%: pre-install
            ); \
        )
 
+ifneq (,$(gcj_archs))
+       : # gcj-$(CROSS_PKG_GNU_TYPE)
+       $(if $(filter gcj-$(CROSS_PKG_GNU_TYPE), $(packages)), \
+         dh_installdirs -pgcj-$(CROSS_PKG_GNU_TYPE); \
+         dh_link -pgcj-$(CROSS_PKG_GNU_TYPE) \
+           /usr/share/doc/cpp-$(CROSS_GNU_TYPE) /usr/share/doc/gcj-$(CROSS_GNU_TYPE) \
+           /usr/bin/$(CROSS_GNU_TYPE)-gcj-$(PV_GCJ_$(CROSS_ARCH)) /usr/bin/$(CROSS_GNU_TYPE)-gcj \
+           $(if $(filter yes, $(with_gfdl_docs)), \
+             /usr/share/man/man1/$(CROSS_GNU_TYPE)-gcj-$(PV_GCJ_$(CROSS_ARCH)).1.gz /usr/share/man/man1/$(CROSS_GNU_TYPE)-gcj.1.gz \
+           ); \
+       )
+endif
+
        : # gnat-$(CROSS_PKG_GNU_TYPE)
        $(if $(filter gnat-$(CROSS_PKG_GNU_TYPE), $(packages)), \
          dh_installdirs -pgnat-$(CROSS_PKG_GNU_TYPE); \
@@ -1174,20 +1399,42 @@ install.%: pre-install
            /usr/share/doc/cpp-$(CROSS_GNU_TYPE) /usr/share/doc/gnat-sjlj-$(CROSS_GNU_TYPE); \
        )
 
+cacerts-stamp:
+ifeq ($(with_native),yes)
+       dh_testdir
+       rm -rf build
+       mkdir -p build
+       sed 's/@gcc_suffix@//' debian/generate-cacerts.pl.in \
+               > debian/generate-cacerts.pl
+       cd build && perl ../debian/generate-cacerts.pl \
+               /etc/ssl/certs/ca-certificates.crt
+endif
+       touch $@
+
 nopkgs_native := $(foreach p, $(filter $(shell dh_listpackages -a), $(sort $(invalid_packages) $(no_packages) $(cross_packages))),-N$(p))
 
 binary-indep: build-indep install
 ifeq ($(with_native),yes)
        dh_testdir
        dh_testroot
+  ifneq (,$(gcj_archs))
        dh_installchangelogs -i
-       dh_installdocs -i
-       dh_compress -i
+
+       dh_installdocs -plibgcj-common
+       dh_installchangelogs -plibgcj-common
+       mv debian/libgcj-common/usr/share/doc/libgcj-common/changelog \
+               debian/libgcj-common/usr/share/doc/libgcj-common/changelog.Debian
+
+       install -m644 build/cacerts debian/libgcj-common/etc/java/cacerts-gcj
+
+       dh_compress -i -XREADME.Debian
        dh_fixperms -i
+       dh_python2 -plibgcj-common
        dh_installdeb -i
-       dh_gencontrol -i
+       dh_gencontrol -plibgcj-common -u-v$(CV_LIBGCJCOMMON)
        dh_md5sums -i
        dh_builddeb -i
+  endif
 endif
 
 binary-arch: binary-native $(foreach a,$(CROSS_ARCHS),binary.$(a))
@@ -1197,9 +1444,10 @@ ifeq ($(with_native),yes)
        dh_testroot
 #      dh_installdebconf
        dh_installdocs -pcpp
-       for p in `dh_listpackages $(nopkgs_native) -Ncpp $(if $(filter yes,$(with_gfdl_docs)),-Ncpp-doc -Ngcc-doc -Ngfortran-doc -Ngccgo-doc) -Ngdc -Nlibgphobos-dev`; do \
+       for p in `dh_listpackages $(nopkgs_native) -Ncpp $(if $(gcj_archs),-Nlibgcj-bc -Nlibgcj-common) $(if $(filter yes,$(with_gfdl_docs)),-Ncpp-doc -Ngcc-doc -Ngfortran-doc -Ngccgo-doc) -Ngdc -Nlibgphobos-dev`; do \
          case "$$p" in \
            *-gnu*|*-kfreebsd*|gcc-hppa64-linux-gnu) continue;; \
+           gij|gcj-*) t=libgcj-common;; \
            *) t=cpp; \
          esac; \
          echo ln -sf $$t debian/$$p/usr/share/doc/$$p; \
@@ -1249,7 +1497,7 @@ endif
 
        for p in $$(dh_listpackages -a); do \
          case $$p in \
-           cpp|g++|gcc|gccgo|gfortran|gcc-hppa64-linux-gnu) \
+           cpp|g++|gcc|gccgo|gcj-jdk|gcj-jre-headless|gfortran|gcc-hppa64-linux-gnu) \
              [ "$(with_gfdl_docs)" = yes ] && continue; \
              mkdir -p -m 755 debian/$$p/usr/share/lintian/overrides; \
              echo "$$p binary: binary-without-manpage" \
@@ -1304,6 +1552,11 @@ ifneq (,$(filter gccgo, $(packages)))
          $(if $(filter yes, $(with_gfdl_docs)),-pgccgo-doc) \
          -u-v$(EPOCH):$(CV_GGO)
 endif
+ifneq (,$(filter gcj-jdk, $(packages)))
+       dh_gencontrol -plibgcj-bc   -u-v$(CV_LIBGCJBC)
+       dh_gencontrol -pgcj-jre-headless -pgcj-jre -pgcj-jdk \
+               -u-v$(EPOCH):$(CV_GCJ)
+endif
 ifneq (,$(filter gccbrig, $(packages)))
        dh_gencontrol -pgccbrig \
          -u-v$(EPOCH):$(CV_BRIG)
@@ -1353,7 +1606,7 @@ binary.%: build-arch install
 
        for p in $(filter %-$(CROSS_PKG_GNU_TYPE),$(cross_packages)); do \
          case $$p in \
-           cpp-$(CROSS_PKG_GNU_TYPE)|g++-$(CROSS_PKG_GNU_TYPE)|gcc-$(CROSS_PKG_GNU_TYPE)|gccgo-$(CROSS_PKG_GNU_TYPE)|gfortran-$(CROSS_PKG_GNU_TYPE)) \
+           cpp-$(CROSS_PKG_GNU_TYPE)|g++-$(CROSS_PKG_GNU_TYPE)|gcc-$(CROSS_PKG_GNU_TYPE)|gccgo-$(CROSS_PKG_GNU_TYPE)|gcj-$(CROSS_PKG_GNU_TYPE)|gfortran-$(CROSS_PKG_GNU_TYPE)) \
              [ "$(with_gfdl_docs)" = yes ] && continue; \
              mkdir -p -m 755 debian/$$p/usr/share/lintian/overrides; \
              echo "$$p binary: binary-without-manpage" \
@@ -1409,6 +1662,11 @@ binary.%: build-arch install
            -u-v$(EPOCH):$(CV_GGO_$(CROSS_ARCH)) \
        )
 
+       $(if $(filter gcj-$(CROSS_PKG_GNU_TYPE), $(packages)), \
+         dh_gencontrol -pgcj-$(CROSS_PKG_GNU_TYPE) \
+               -u-v$(EPOCH):$(CV_GCJ_$(CROSS_ARCH)) \
+       )
+
        $(if $(filter gnat-$(CROSS_PKG_GNU_TYPE), $(packages)), \
          dh_gencontrol -pgnat-$(CROSS_PKG_GNU_TYPE) -pgnat-sjlj-$(CROSS_PKG_GNU_TYPE) \
                -u-v$(EPOCH):$(CV_GNAT_$(CROSS_ARCH)) \