Merge branch 'master' of http://darcs.haskell.org/ghc into ghc-generics
authorJose Pedro Magalhaes <jpm@cs.uu.nl>
Mon, 2 May 2011 18:48:10 +0000 (20:48 +0200)
committerJose Pedro Magalhaes <jpm@cs.uu.nl>
Mon, 2 May 2011 18:48:10 +0000 (20:48 +0200)
49 files changed:
MAKEHELP
aclocal.m4
boot
boot-pkgs [deleted file]
compiler/cmm/CLabel.hs
compiler/cmm/CmmCPS.hs
compiler/cmm/CmmLint.hs
compiler/cmm/CmmOpt.hs
compiler/cmm/CmmProcPoint.hs
compiler/cmm/CmmStackLayout.hs
compiler/cmm/PprC.hs
compiler/ghc.cabal.in
compiler/ghc.mk
compiler/ghci/ByteCodeAsm.lhs
compiler/llvmGen/LlvmMangler.hs
compiler/main/CodeOutput.lhs
compiler/main/DriverPipeline.hs
compiler/main/DynFlags.hs
compiler/main/SysTools.lhs
compiler/nativeGen/Alpha/CodeGen.hs [deleted file]
compiler/nativeGen/Alpha/Instr.hs [deleted file]
compiler/nativeGen/Alpha/Ppr.hs-old [deleted file]
compiler/nativeGen/Alpha/RegInfo.hs [deleted file]
compiler/nativeGen/Alpha/Regs.hs [deleted file]
compiler/nativeGen/AsmCodeGen.lhs
compiler/nativeGen/PPC/CodeGen.hs
compiler/nativeGen/PPC/Instr.hs
compiler/nativeGen/PPC/Ppr.hs
compiler/nativeGen/PPC/Regs.hs
compiler/nativeGen/Platform.hs
compiler/nativeGen/RegAlloc/Linear/JoinToTargets.hs
compiler/nativeGen/SPARC/CodeGen.hs
compiler/nativeGen/SPARC/Instr.hs
compiler/nativeGen/SPARC/Ppr.hs
compiler/nativeGen/X86/CodeGen.hs
compiler/nativeGen/X86/Instr.hs
compiler/nativeGen/X86/Ppr.hs
compiler/nativeGen/X86/Regs.hs
compiler/prelude/primops.txt.pp
configure.ac
ghc/ghc.wrapper
includes/stg/SMP.h
mk/config.mk.in
rules/build-package-data.mk
rules/c-suffix-rules.mk
rules/package-config.mk
rules/shell-wrapper.mk
settings.in
sync-all

index 85497e9..c14767f 100644 (file)
--- a/MAKEHELP
+++ b/MAKEHELP
@@ -25,12 +25,6 @@ Common commands:
 
      Shows the targets available in <dir>
 
-  make html
-  make pdf
-  make ps
-
-     Make documentation
-
   make install
 
      Installs GHC, libraries and tools under $(prefix)
index 4b750ef..7433873 100644 (file)
@@ -105,6 +105,21 @@ AC_DEFUN([FPTOOLS_SET_C_LD_FLAGS],
         $4="$$4 -arch x86_64"
         $5="$$5 -m64"
         ;;
+    alpha-*)
+        # For now, to suppress the gcc warning "call-clobbered
+        # register used for global register variable", we simply
+        # disable all warnings altogether using the -w flag. Oh well.
+        $2="$$2 -w -mieee -D_REENTRANT"
+        $3="$$3 -w -mieee -D_REENTRANT"
+        $5="$$5 -w -mieee -D_REENTRANT"
+        ;;
+    hppa*)
+        # ___HPUX_SOURCE, not _HPUX_SOURCE, is #defined if -ansi!
+        # (very nice, but too bad the HP /usr/include files don't agree.)
+        $2="$$2 -D_HPUX_SOURCE"
+        $3="$$3 -D_HPUX_SOURCE"
+        $5="$$5 -D_HPUX_SOURCE"
+        ;;
     esac
 
     # If gcc knows about the stack protector, turn it off.
@@ -620,7 +635,7 @@ AC_SUBST([ArArgs], ["$fp_prog_ar_args"])
 # FP_PROG_AR_NEEDS_RANLIB
 # -----------------------
 # Sets the output variable RANLIB to "ranlib" if it is needed and found,
-# to ":" otherwise.
+# to "true" otherwise.
 AC_DEFUN([FP_PROG_AR_NEEDS_RANLIB],
 [AC_REQUIRE([FP_PROG_AR_IS_GNU])
 AC_REQUIRE([FP_PROG_AR_ARGS])
@@ -640,7 +655,7 @@ fi])
 if test $fp_cv_prog_ar_needs_ranlib = yes; then
    AC_PROG_RANLIB
 else
-  RANLIB=":"
+  RANLIB="true"
   AC_SUBST([RANLIB])
 fi
 ])# FP_PROG_AR_NEEDS_RANLIB
diff --git a/boot b/boot
index 66bff3e..0b67b17 100755 (executable)
--- a/boot
+++ b/boot
@@ -3,13 +3,19 @@
 use strict;
 
 use Cwd;
+use File::Path 'rmtree';
+use File::Basename;
 
 my %required_tag;
 my $validate;
+my $curdir;
 
 $required_tag{"-"} = 1;
 $validate = 0;
 
+$curdir = &cwd()
+    or die "Can't find current directory: $!";
+
 while ($#ARGV ne -1) {
     my $arg = shift @ARGV;
 
@@ -24,7 +30,7 @@ while ($#ARGV ne -1) {
     }
 }
 
-{
+sub sanity_check_line_endings {
     local $/ = undef;
     open FILE, "packages" or die "Couldn't open file: $!";
     binmode FILE;
@@ -42,59 +48,168 @@ EOF
     }
 }
 
-# Create libraries/*/{ghc.mk,GNUmakefile}
-system("/usr/bin/perl", "-w", "boot-pkgs") == 0
-    or die "Running boot-pkgs failed: $?";
+sub sanity_check_tree {
+    my $tag;
+    my $dir;
 
-my $tag;
-my $dir;
-my $curdir;
+    # Check that we have all boot packages.
+    open PACKAGES, "< packages";
+    while (<PACKAGES>) {
+        if (/^#/) {
+            # Comment; do nothing
+        }
+        elsif (/^([a-zA-Z0-9\/.-]+) +([^ ]+) +[^ ]+ +[^ ]+ +[^ ]+$/) {
+            $dir = $1;
+            $tag = $2;
+
+            # If $tag is not "-" then it is an optional repository, so its
+            # absence isn't an error.
+            if (defined($required_tag{$tag})) {
+                # We would like to just check for a .git directory here,
+                # but in an lndir tree we avoid making .git directories,
+                # so it doesn't exist. We therefore require that every repo
+                # has a LICENSE file instead.
+                if (! -f "$dir/LICENSE") {
+                    print STDERR "Error: $dir/LICENSE doesn't exist.\n";
+                    die "Maybe you haven't done './sync-all get'?";
+                }
+            }
+        }
+        else {
+            die "Bad line in packages file: $_";
+        }
+    }
+    close PACKAGES;
+}
 
-$curdir = &cwd()
-    or die "Can't find current directory: $!";
+# Create libraries/*/{ghc.mk,GNUmakefile}
+sub boot_pkgs {
+    my @library_dirs = ();
+    my @tarballs = glob("libraries/tarballs/*");
+
+    my $tarball;
+    my $package;
+    my $stamp;
+
+    for $tarball (@tarballs) {
+        $package = $tarball;
+        $package =~ s#^libraries/tarballs/##;
+        $package =~ s/-[0-9.]*(-snapshot)?\.tar\.gz$//;
+
+        # Sanity check, so we don't rmtree the wrong thing below
+        if (($package eq "") || ($package =~ m#[/.\\]#)) {
+            die "Bad package name: $package";
+        }
 
-# Check that we have all boot packages.
-open PACKAGES, "< packages";
-while (<PACKAGES>) {
-    if (/^#/) {
-        # Comment; do nothing
+        if (-d "libraries/$package/_darcs") {
+            print "Ignoring libraries/$package as it looks like a darcs checkout\n"
+        }
+        elsif (-d "libraries/$package/.git") {
+            print "Ignoring libraries/$package as it looks like a git checkout\n"
+        }
+        else {
+            if (! -d "libraries/stamp") {
+                mkdir "libraries/stamp";
+            }
+            $stamp = "libraries/stamp/$package";
+            if ((! -d "libraries/$package") || (! -f "$stamp")
+             || ((-M "libraries/stamp/$package") > (-M $tarball))) {
+                print "Unpacking $package\n";
+                if (-d "libraries/$package") {
+                    &rmtree("libraries/$package")
+                        or die "Can't remove libraries/$package: $!";
+                }
+                mkdir "libraries/$package"
+                    or die "Can't create libraries/$package: $!";
+                system ("sh", "-c", "cd 'libraries/$package' && { cat ../../$tarball | gzip -d | tar xf - ; } && mv */* .") == 0
+                    or die "Failed to unpack $package";
+                open STAMP, "> $stamp"
+                    or die "Failed to open stamp file: $!";
+                close STAMP
+                    or die "Failed to close stamp file: $!";
+            }
+        }
     }
-    elsif (/^([a-zA-Z0-9\/.-]+) +([^ ]+) +[^ ]+ +[^ ]+ +[^ ]+$/) {
-        $dir = $1;
-        $tag = $2;
-        
-        # If $tag is not "-" then it is an optional repository, so its
-        # absence isn't an error.
-        if (defined($required_tag{$tag})) {
-            # We would like to just check for a .git directory here,
-            # but in an lndir tree we avoid making .git directories,
-            # so it doesn't exist. We therefore require that every repo
-            # has a LICENSE file instead.
-            if (! -f "$dir/LICENSE") {
-                print STDERR "Error: $dir/LICENSE doesn't exist.\n";
-                die "Maybe you haven't done './sync-all get'?";
+
+    for $package (glob "libraries/*/") {
+        $package =~ s/\/$//;
+        my $pkgs = "$package/ghc-packages";
+        if (-f $pkgs) {
+            open PKGS, "< $pkgs"
+                or die "Failed to open $pkgs: $!";
+            while (<PKGS>) {
+                chomp;
+                s/\r//g;
+                if (/.+/) {
+                    push @library_dirs, "$package/$_";
+                }
             }
         }
+        else {
+            push @library_dirs, $package;
+        }
     }
-    else {
-        die "Bad line in packages file: $_";
+
+    for $package (@library_dirs) {
+        my $dir = &basename($package);
+        my @cabals = glob("$package/*.cabal");
+        if ($#cabals > 0) {
+            die "Too many .cabal file in $package\n";
+        }
+        if ($#cabals eq 0) {
+            my $cabal = $cabals[0];
+            my $pkg;
+            my $top;
+            if (-f $cabal) {
+                $pkg = $cabal;
+                $pkg =~ s#.*/##;
+                $pkg =~ s/\.cabal$//;
+                $top = $package;
+                $top =~ s#[^/]+#..#g;
+                $dir = $package;
+                $dir =~ s#^libraries/##g;
+
+                print "Creating $package/ghc.mk\n";
+                open GHCMK, "> $package/ghc.mk"
+                    or die "Opening $package/ghc.mk failed: $!";
+                print GHCMK "${package}_PACKAGE = ${pkg}\n";
+                print GHCMK "${package}_dist-install_GROUP = libraries\n";
+                print GHCMK "\$(eval \$(call build-package,${package},dist-install,\$(if \$(filter ${dir},\$(STAGE2_PACKAGES)),2,1)))\n";
+                close GHCMK
+                    or die "Closing $package/ghc.mk failed: $!";
+
+                print "Creating $package/GNUmakefile\n";
+                open GNUMAKEFILE, "> $package/GNUmakefile"
+                    or die "Opening $package/GNUmakefile failed: $!";
+                print GNUMAKEFILE "dir = ${package}\n";
+                print GNUMAKEFILE "TOP = ${top}\n";
+                print GNUMAKEFILE "include \$(TOP)/mk/sub-makefile.mk\n";
+                print GNUMAKEFILE "FAST_MAKE_OPTS += stage=0\n";
+                close GNUMAKEFILE
+                    or die "Closing $package/GNUmakefile failed: $!";
+            }
+        }
     }
 }
-close PACKAGES;
 
 # autoreconf everything that needs it.
-foreach $dir (".", glob("libraries/*/")) {
-    if (-f "$dir/configure.ac") {
-        print "Booting $dir\n";
-        chdir $dir or die "can't change to $dir: $!";
-        system("autoreconf") == 0
-            or die "Running autoreconf failed with exitcode $?";
-        chdir $curdir or die "can't change to $curdir: $!";
+sub autoreconf {
+    my $dir;
+
+    foreach $dir (".", glob("libraries/*/")) {
+        if (-f "$dir/configure.ac") {
+            print "Booting $dir\n";
+            chdir $dir or die "can't change to $dir: $!";
+            system("autoreconf") == 0
+                or die "Running autoreconf failed with exitcode $?";
+            chdir $curdir or die "can't change to $curdir: $!";
+        }
     }
 }
 
-if ($validate eq 0 && ! -f "mk/build.mk") {
-    print <<EOF;
+sub checkBuildMk {
+    if ($validate eq 0 && ! -f "mk/build.mk") {
+        print <<EOF;
 
 WARNING: You don't have a mk/build.mk file.
 
@@ -107,5 +222,12 @@ For information on creating a mk/build.mk file, please see:
     http://hackage.haskell.org/trac/ghc/wiki/Building/Using#Buildconfiguration
 
 EOF
+    }
 }
 
+&sanity_check_line_endings();
+&sanity_check_tree();
+&boot_pkgs();
+&autoreconf();
+&checkBuildMk();
+
diff --git a/boot-pkgs b/boot-pkgs
deleted file mode 100644 (file)
index de3008c..0000000
--- a/boot-pkgs
+++ /dev/null
@@ -1,114 +0,0 @@
-#!/usr/bin/perl -w
-
-use strict;
-
-use File::Path 'rmtree';
-use File::Basename;
-
-my @library_dirs = ();
-my @tarballs = glob("libraries/tarballs/*");
-
-my $tarball;
-my $package;
-my $stamp;
-
-for $tarball (@tarballs) {
-    $package = $tarball;
-    $package =~ s#^libraries/tarballs/##;
-    $package =~ s/-[0-9.]*(-snapshot)?\.tar\.gz$//;
-
-    # Sanity check, so we don't rmtree the wrong thing below
-    if (($package eq "") || ($package =~ m#[/.\\]#)) {
-        die "Bad package name: $package";
-    }
-
-    if (-d "libraries/$package/_darcs") {
-        print "Ignoring libraries/$package as it looks like a darcs checkout\n"
-    }
-    elsif (-d "libraries/$package/.git") {
-        print "Ignoring libraries/$package as it looks like a git checkout\n"
-    }
-    else {
-        if (! -d "libraries/stamp") {
-            mkdir "libraries/stamp";
-        }
-        $stamp = "libraries/stamp/$package";
-        if ((! -d "libraries/$package") || (! -f "$stamp")
-         || ((-M "libraries/stamp/$package") > (-M $tarball))) {
-            print "Unpacking $package\n";
-            if (-d "libraries/$package") {
-                &rmtree("libraries/$package")
-                    or die "Can't remove libraries/$package: $!";
-            }
-            mkdir "libraries/$package"
-                or die "Can't create libraries/$package: $!";
-            system ("sh", "-c", "cd 'libraries/$package' && { cat ../../$tarball | gzip -d | tar xf - ; } && mv */* .") == 0
-                or die "Failed to unpack $package";
-            open STAMP, "> $stamp"
-                or die "Failed to open stamp file: $!";
-            close STAMP
-                or die "Failed to close stamp file: $!";
-        }
-    }
-}
-
-for $package (glob "libraries/*/") {
-    $package =~ s/\/$//;
-    my $pkgs = "$package/ghc-packages";
-    if (-f $pkgs) {
-        open PKGS, "< $pkgs"
-            or die "Failed to open $pkgs: $!";
-        while (<PKGS>) {
-            chomp;
-            s/\r//g;
-            if (/.+/) {
-                push @library_dirs, "$package/$_";
-            }
-        }
-    }
-    else {
-        push @library_dirs, $package;
-    }
-}
-
-for $package (@library_dirs) {
-    my $dir = &basename($package);
-    my @cabals = glob("$package/*.cabal");
-    if ($#cabals > 0) {
-        die "Too many .cabal file in $package\n";
-    }
-    if ($#cabals eq 0) {
-        my $cabal = $cabals[0];
-        my $pkg;
-        my $top;
-        if (-f $cabal) {
-            $pkg = $cabal;
-            $pkg =~ s#.*/##;
-            $pkg =~ s/\.cabal$//;
-            $top = $package;
-            $top =~ s#[^/]+#..#g;
-            $dir = $package;
-            $dir =~ s#^libraries/##g;
-
-            print "Creating $package/ghc.mk\n";
-            open GHCMK, "> $package/ghc.mk"
-                or die "Opening $package/ghc.mk failed: $!";
-            print GHCMK "${package}_PACKAGE = ${pkg}\n";
-            print GHCMK "${package}_dist-install_GROUP = libraries\n";
-            print GHCMK "\$(eval \$(call build-package,${package},dist-install,\$(if \$(filter ${dir},\$(STAGE2_PACKAGES)),2,1)))\n";
-            close GHCMK
-                or die "Closing $package/ghc.mk failed: $!";
-
-            print "Creating $package/GNUmakefile\n";
-            open GNUMAKEFILE, "> $package/GNUmakefile"
-                or die "Opening $package/GNUmakefile failed: $!";
-            print GNUMAKEFILE "dir = ${package}\n";
-            print GNUMAKEFILE "TOP = ${top}\n";
-            print GNUMAKEFILE "include \$(TOP)/mk/sub-makefile.mk\n";
-            print GNUMAKEFILE "FAST_MAKE_OPTS += stage=0\n";
-            close GNUMAKEFILE
-                or die "Closing $package/GNUmakefile failed: $!";
-        }
-    }
-}
-
index 901b13b..3451c7d 100644 (file)
@@ -101,7 +101,7 @@ module CLabel (
         hasCAF,
        infoLblToEntryLbl, entryLblToInfoLbl, cvtToClosureLbl, cvtToSRTLbl,
        needsCDecl, isAsmTemp, maybeAsmTemp, externallyVisibleCLabel,
-        isMathFun, isCas,
+        isMathFun,
        isCFunctionLabel, isGcPtrLabel, labelDynamic,
 
        pprCLabel
@@ -590,14 +590,6 @@ maybeAsmTemp (AsmTempLabel uq)             = Just uq
 maybeAsmTemp _                                 = Nothing
 
 
--- | Check whether a label corresponds to our cas function.
---      We #include the prototype for this, so we need to avoid
---      generating out own C prototypes.
-isCas :: CLabel -> Bool
-isCas (CmmLabel pkgId fn _) = pkgId == rtsPackageId && fn == fsLit "cas"
-isCas _                     = False
-
-
 -- | Check whether a label corresponds to a C function that has 
 --      a prototype in a system header somehere, or is built-in
 --      to the C compiler. For these labels we avoid generating our
@@ -858,8 +850,8 @@ instance Outputable CLabel where
 
 pprCLabel :: CLabel -> SDoc
 
-#if ! OMIT_NATIVE_CODEGEN
 pprCLabel (AsmTempLabel u)
+ | cGhcWithNativeCodeGen == "YES"
   =  getPprStyle $ \ sty ->
      if asmStyle sty then 
        ptext asmTempLabelPrefix <> pprUnique u
@@ -867,23 +859,22 @@ pprCLabel (AsmTempLabel u)
        char '_' <> pprUnique u
 
 pprCLabel (DynamicLinkerLabel info lbl)
+ | cGhcWithNativeCodeGen == "YES"
    = pprDynamicLinkerAsmLabel info lbl
    
 pprCLabel PicBaseLabel
+ | cGhcWithNativeCodeGen == "YES"
    = ptext (sLit "1b")
    
 pprCLabel (DeadStripPreventer lbl)
+ | cGhcWithNativeCodeGen == "YES"
    = pprCLabel lbl <> ptext (sLit "_dsp")
-#endif
 
-pprCLabel lbl = 
-#if ! OMIT_NATIVE_CODEGEN
-    getPprStyle $ \ sty ->
-    if asmStyle sty then 
-       maybe_underscore (pprAsmCLbl lbl)
-    else
-#endif
-       pprCLbl lbl
+pprCLabel lbl
+   = getPprStyle $ \ sty ->
+     if cGhcWithNativeCodeGen == "YES" && asmStyle sty
+     then maybe_underscore (pprAsmCLbl lbl)
+     else pprCLbl lbl
 
 maybe_underscore doc
   | underscorePrefix = pp_cSEP <> doc
index b9f6db3..aad0037 100644 (file)
@@ -112,12 +112,13 @@ cpsTop hsc_env (CmmProc h@(TopInfo {stack_info=StackInfo {arg_space=entry_off}})
 
        --------------- Stack layout ----------------
        slotEnv <- run $ liveSlotAnal g
+       let spEntryMap = getSpEntryMap entry_off g
        mbpprTrace "live slot analysis results: " (ppr slotEnv) $ return ()
-       let areaMap = layout procPoints slotEnv entry_off g
+       let areaMap = layout procPoints spEntryMap slotEnv entry_off g
        mbpprTrace "areaMap" (ppr areaMap) $ return ()
 
        ------------  Manifest the stack pointer --------
-       g  <- run $ manifestSP areaMap entry_off g
+       g  <- run $ manifestSP spEntryMap areaMap entry_off g
        dump Opt_D_dump_cmmz "after manifestSP" g
        -- UGH... manifestSP can require updates to the procPointMap.
        -- We can probably do something quicker here for the update...
index c14ad65..32fead3 100644 (file)
@@ -153,6 +153,7 @@ lintTarget (CmmPrim {})    = return ()
 
 checkCond :: CmmExpr -> CmmLint ()
 checkCond (CmmMachOp mop _) | isComparisonMachOp mop = return ()
+checkCond (CmmLit (CmmInt x t)) | x == 0 || x == 1, t == wordWidth = return () -- constant values
 checkCond expr = cmmLintErr (hang (text "expression is not a conditional:") 2
                                    (ppr expr))
 
index c71f188..1c7e7e5 100644 (file)
@@ -14,6 +14,7 @@
 -----------------------------------------------------------------------------
 
 module CmmOpt (
+       cmmEliminateDeadBlocks,
        cmmMiniInline,
        cmmMachOpFold,
        cmmLoopifyForC,
@@ -30,10 +31,70 @@ import UniqFM
 import Unique
 import FastTypes
 import Outputable
+import BlockId
 
 import Data.Bits
 import Data.Word
 import Data.Int
+import Data.Maybe
+
+import Compiler.Hoopl hiding (Unique)
+
+-- -----------------------------------------------------------------------------
+-- Eliminates dead blocks
+
+{-
+We repeatedly expand the set of reachable blocks until we hit a
+fixpoint, and then prune any blocks that were not in this set.  This is
+actually a required optimization, as dead blocks can cause problems
+for invariants in the linear register allocator (and possibly other
+places.)
+-}
+
+-- Deep fold over statements could probably be abstracted out, but it
+-- might not be worth the effort since OldCmm is moribund
+cmmEliminateDeadBlocks :: [CmmBasicBlock] -> [CmmBasicBlock]
+cmmEliminateDeadBlocks [] = []
+cmmEliminateDeadBlocks blocks@(BasicBlock base_id _:_) =
+    let -- Calculate what's reachable from what block
+        -- We have to do a deep fold into CmmExpr because
+        -- there may be a BlockId in the CmmBlock literal.
+        reachableMap = foldl f emptyBlockMap blocks
+            where f m (BasicBlock block_id stmts) = mapInsert block_id (reachableFrom stmts) m
+        reachableFrom stmts = foldl stmt emptyBlockSet stmts
+            where
+                stmt m CmmNop = m
+                stmt m (CmmComment _) = m
+                stmt m (CmmAssign _ e) = expr m e
+                stmt m (CmmStore e1 e2) = expr (expr m e1) e2
+                stmt m (CmmCall c _ as _ _) = f (actuals m as) c
+                    where f m (CmmCallee e _) = expr m e
+                          f m (CmmPrim _) = m
+                stmt m (CmmBranch b) = setInsert b m
+                stmt m (CmmCondBranch e b) = setInsert b (expr m e)
+                stmt m (CmmSwitch e bs) = foldl (flip setInsert) (expr m e) (catMaybes bs)
+                stmt m (CmmJump e as) = expr (actuals m as) e
+                stmt m (CmmReturn as) = actuals m as
+                actuals m as = foldl (\m h -> expr m (hintlessCmm h)) m as
+                expr m (CmmLit l) = lit m l
+                expr m (CmmLoad e _) = expr m e
+                expr m (CmmReg _) = m
+                expr m (CmmMachOp _ es) = foldl expr m es
+                expr m (CmmStackSlot _ _) = m
+                expr m (CmmRegOff _ _) = m
+                lit m (CmmBlock b) = setInsert b m
+                lit m _ = m
+        -- Expand reachable set until you hit fixpoint
+        initReachable = setSingleton base_id :: BlockSet
+        expandReachable old_set new_set =
+            if setSize new_set > setSize old_set
+                then expandReachable new_set $ setFold
+                        (\x s -> maybe setEmpty id (mapLookup x reachableMap) `setUnion` s)
+                        new_set
+                        (setDifference new_set old_set)
+                else new_set -- fixpoint achieved
+        reachable = expandReachable setEmpty initReachable
+    in filter (\(BasicBlock block_id _) -> setMember block_id reachable) blocks
 
 -- -----------------------------------------------------------------------------
 -- The mini-inliner
index d0d54d9..fbe979b 100644 (file)
@@ -378,6 +378,8 @@ add_CopyOuts protos procPoints g = foldGraphBlocks mb_copy_out (return mapEmpty)
 -- 4. build info tables for the procedures -- and update the info table for
 --    the SRTs in the entry procedure as well.
 -- Input invariant: A block should only be reachable from a single ProcPoint.
+-- ToDo: use the _ret naming convention that the old code generator
+-- used. -- EZY
 splitAtProcPoints :: CLabel -> ProcPointSet-> ProcPointSet -> BlockEnv Status ->
                      CmmTop -> FuelUniqSM [CmmTop]
 splitAtProcPoints entry_label callPPs procPoints procMap
index 01543c4..c0fb6af 100644 (file)
@@ -13,7 +13,7 @@
 
 module CmmStackLayout
     ( SlotEnv, liveSlotAnal, liveSlotTransfers, removeLiveSlotDefs
-    , layout, manifestSP, igraph, areaBuilder
+    , getSpEntryMap, layout, manifestSP, igraph, areaBuilder
     , stubSlotsOnDeath ) -- to help crash early during debugging
 where
 
@@ -195,7 +195,7 @@ liveLastOut env l =
 type Set x = Map x ()
 data IGraphBuilder n =
   Builder { foldNodes     :: forall z. SubArea -> (n -> z -> z) -> z -> z
-          , _wordsOccupied :: AreaMap -> AreaMap -> n -> [Int]
+          , _wordsOccupied :: AreaSizeMap -> AreaMap -> n -> [Int]
           }
 
 areaBuilder :: IGraphBuilder Area
@@ -242,10 +242,13 @@ igraph builder env g = foldr interfere Map.empty (postorderDfs g)
 -- what's the highest offset (in bytes) used in each Area?
 -- We'll need to allocate that much space for each Area.
 
+-- Mapping of areas to area sizes (not offsets!)
+type AreaSizeMap = AreaMap
+
 -- JD: WHY CAN'T THIS COME FROM THE slot-liveness info?
-getAreaSize :: ByteOff -> CmmGraph -> AreaMap
+getAreaSize :: ByteOff -> CmmGraph -> AreaSizeMap
   -- The domain of the returned mapping consists only of Areas
-  -- used for (a) variable spill slots, and (b) parameter passing ares for calls
+  -- used for (a) variable spill slots, and (b) parameter passing areas for calls
 getAreaSize entry_off g =
   foldGraphBlocks (foldBlockNodesF3 (first, add_regslots, last))
               (Map.singleton (CallArea Old) entry_off) g
@@ -266,10 +269,11 @@ getAreaSize entry_off g =
        -- The 'max' is important.  Two calls, to f and g, might share a common
        -- continuation (and hence a common CallArea), but their number of overflow
        -- parameters might differ.
+        -- EZY: Ought to use insert with combining function...
 
 
 -- Find the Stack slots occupied by the subarea's conflicts
-conflictSlots :: Ord x => IGPair x -> AreaMap -> AreaMap -> SubArea -> Set Int
+conflictSlots :: Ord x => IGPair x -> AreaSizeMap -> AreaMap -> SubArea -> Set Int
 conflictSlots (ig, Builder foldNodes wordsOccupied) areaSize areaMap subarea =
   foldNodes subarea foldNode Map.empty
   where foldNode n set = Map.foldRightWithKey conflict set $ Map.findWithDefault Map.empty n ig
@@ -278,10 +282,10 @@ conflictSlots (ig, Builder foldNodes wordsOccupied) areaSize areaMap subarea =
         liveInSlots areaMap n set = foldr setAdd set (wordsOccupied areaSize areaMap n)
         setAdd w s = Map.insert w () s
 
--- Find any open space on the stack, starting from the offset.
--- If the area is a CallArea or a spill slot for a pointer, then it must
--- be word-aligned.
-freeSlotFrom :: Ord x => IGPair x -> AreaMap -> Int -> AreaMap -> Area -> Int
+-- Find any open space for 'area' on the stack, starting from the
+-- 'offset'.  If the area is a CallArea or a spill slot for a pointer,
+-- then it must be word-aligned.
+freeSlotFrom :: Ord x => IGPair x -> AreaSizeMap -> Int -> AreaMap -> Area -> Int
 freeSlotFrom ig areaSize offset areaMap area =
   let size = Map.lookup area areaSize `orElse` 0
       conflicts = conflictSlots ig areaSize areaMap (area, size, size)
@@ -299,11 +303,24 @@ freeSlotFrom ig areaSize offset areaMap area =
   in findSpace (align (offset + size)) size
 
 -- Find an open space on the stack, and assign it to the area.
-allocSlotFrom :: Ord x => IGPair x -> AreaMap -> Int -> AreaMap -> Area -> AreaMap
+allocSlotFrom :: Ord x => IGPair x -> AreaSizeMap -> Int -> AreaMap -> Area -> AreaMap
 allocSlotFrom ig areaSize from areaMap area =
   if Map.member area areaMap then areaMap
   else Map.insert area (freeSlotFrom ig areaSize from areaMap area) areaMap
 
+-- Figure out all of the offsets from the slot location; this will be
+-- non-zero for procpoints.
+type SpEntryMap = BlockEnv Int
+getSpEntryMap :: Int -> CmmGraph -> SpEntryMap
+getSpEntryMap entry_off g@(CmmGraph {g_entry = entry})
+    = foldGraphBlocks add_sp_off (mapInsert entry entry_off emptyBlockMap) g
+  where add_sp_off :: CmmBlock -> BlockEnv Int -> BlockEnv Int
+        add_sp_off b env =
+          case lastNode b of
+            CmmCall {cml_cont=Just succ, cml_ret_args=off} -> mapInsert succ off env
+            CmmForeignCall {succ=succ}                     -> mapInsert succ wORD_SIZE env
+            _                                              -> env
+
 -- | Greedy stack layout.
 -- Compute liveness, build the interference graph, and allocate slots for the areas.
 -- We visit each basic block in a (generally) forward order.
@@ -326,12 +343,16 @@ allocSlotFrom ig areaSize from areaMap area =
 -- Note: The stack pointer only has to be younger than the youngest live stack slot
 -- at proc points. Otherwise, the stack pointer can point anywhere.
 
-layout :: ProcPointSet -> SlotEnv -> ByteOff -> CmmGraph -> AreaMap
+layout :: ProcPointSet -> SpEntryMap -> SlotEnv -> ByteOff -> CmmGraph -> AreaMap
 -- The domain of the returned map includes an Area for EVERY block
 -- including each block that is not the successor of a call (ie is not a proc-point)
--- That's how we return the info of what the SP should be at the entry of every block
+-- That's how we return the info of what the SP should be at the entry of every non
+-- procpoint block.  However, note that procpoint blocks have their
+-- /slot/ stored, which is not necessarily the value of the SP on entry
+-- to the block (in fact, it probably isn't, due to argument passing).
+-- See [Procpoint Sp offset]
 
-layout procPoints env entry_off g =
+layout procPoints spEntryMap env entry_off g =
   let ig = (igraph areaBuilder env g, areaBuilder)
       env' bid = mapLookup bid env `orElse` panic "unknown blockId in igraph"
       areaSize = getAreaSize entry_off g
@@ -370,21 +391,87 @@ layout procPoints env entry_off g =
       allocMid m areaMap = foldSlotsDefd alloc' (foldSlotsUsed alloc' areaMap m) m
       allocLast bid l areaMap =
         foldr (setSuccSPs inSp) areaMap' (successors l)
-        where inSp = expectJust "sp in" $ Map.lookup (CallArea (Young bid)) areaMap
+        where inSp = slot + spOffset -- [Procpoint Sp offset]
+              -- If it's not in the map, we should use our previous
+              -- calculation unchanged.
+              spOffset = mapLookup bid spEntryMap `orElse` 0
+              slot = expectJust "slot in" $ Map.lookup (CallArea (Young bid)) areaMap
               areaMap' = foldSlotsDefd alloc' (foldSlotsUsed alloc' areaMap l) l
       alloc' areaMap (a@(RegSlot _), _, _) = allocVarSlot areaMap a
       alloc' areaMap _ = areaMap
 
-      initMap = Map.insert (CallArea (Young (g_entry g))) 0 $
-                  Map.insert (CallArea Old) 0 Map.empty
-                        
+      initMap = Map.insert (CallArea (Young (g_entry g))) 0
+              . Map.insert (CallArea Old)                 0
+              $ Map.empty
+
       areaMap = foldl layoutAreas initMap (postorderDfs g)
   in -- pprTrace "ProcPoints" (ppr procPoints) $
-        -- pprTrace "Area SizeMap" (ppr areaSize) $
-         -- pprTrace "Entry SP" (ppr entrySp) $
-           -- pprTrace "Area Map" (ppr areaMap) $
+     -- pprTrace "Area SizeMap" (ppr areaSize) $
+     -- pprTrace "Entry offset" (ppr entry_off) $
+     -- pprTrace "Area Map" (ppr areaMap) $
      areaMap
 
+{- Note [Procpoint Sp offset]
+
+The calculation of inSp is a little tricky.  (Un)fortunately, if you get
+it wrong, you will get inefficient but correct code.  You know you've
+got it wrong if the generated stack pointer bounces up and down for no
+good reason.
+
+Why can't we just set inSp to the location of the slot?  (This is what
+the code used to do.)  The trouble is when we actually hit the proc
+point the start of the slot will not be the same as the actual Sp due
+to argument passing:
+
+  a:
+      I32[(young<b> + 4)] = cde;
+      // Stack pointer is moved to young end (bottom) of young<b> for call
+      // +-------+
+      // | arg 1 |
+      // +-------+ <- Sp
+      call (I32[foobar::I32])(...) returns to Just b (4) (4) with update frame 4;
+  b:
+      // After call, stack pointer is above the old end (top) of
+      // young<b> (the difference is spOffset)
+      // +-------+ <- Sp
+      // | arg 1 |
+      // +-------+
+
+If we blithely set the Sp to be the same as the slot (the young end of
+young<b>), an adjustment will be necessary when we go to the next block.
+This is wasteful.  So, instead, for the next block after a procpoint,
+the actual Sp should be set to the same as the true Sp when we just
+entered the procpoint.  Then manifestSP will automatically do the right
+thing.
+
+Questions you may ask:
+
+1. Why don't we need to change the mapping for the procpoint itself?
+   Because manifestSP does its own calculation of the true stack value,
+   manifestSP will notice the discrepancy between the actual stack
+   pointer and the slot start, and adjust all of its memory accesses
+   accordingly.  So the only problem is when we adjust the Sp in
+   preparation for the successor block; that's why this code is here and
+   not in setSuccSPs.
+
+2. Why don't we make the procpoint call area and the true offset match
+   up?  If we did that, we would never use memory above the true value
+   of the stack pointer, thus wasting all of the stack we used to store
+   arguments.  You might think that some clever changes to the slot
+   offsets, using negative offsets, might fix it, but this does not make
+   semantic sense.
+
+3. If manifestSP is already calculating the true stack value, why we can't
+   do this trick inside manifestSP itself?  The reason is that if two
+   branches join with inconsistent SPs, one of them has to be fixed: we
+   can't know what the fix should be without already knowing what the
+   chosen location of SP is on the next successor.  (This is
+   the "succ already knows incoming SP" case), This calculation cannot
+   be easily done in manifestSP, since it processes the nodes
+   /backwards/.  So we need to have figured this out before we hit
+   manifestSP.
+-}
+
 -- After determining the stack layout, we can:
 -- 1. Replace references to stack Areas with addresses relative to the stack
 --    pointer.
@@ -394,8 +481,8 @@ layout procPoints env entry_off g =
 --    stack pointer to be younger than the live values on the stack at proc points.
 -- 3. Compute the maximum stack offset used in the procedure and replace
 --    the stack high-water mark with that offset.
-manifestSP :: AreaMap -> ByteOff -> CmmGraph -> FuelUniqSM CmmGraph
-manifestSP areaMap entry_off g@(CmmGraph {g_entry=entry}) =
+manifestSP :: SpEntryMap -> AreaMap -> ByteOff -> CmmGraph -> FuelUniqSM CmmGraph
+manifestSP spEntryMap areaMap entry_off g@(CmmGraph {g_entry=entry}) =
   ofBlockMap entry `liftM` foldl replB (return mapEmpty) (postorderDfs g)
   where slot a = -- pprTrace "slot" (ppr a) $
                    Map.lookup a areaMap `orElse` panic "unallocated Area"
@@ -404,13 +491,6 @@ manifestSP areaMap entry_off g@(CmmGraph {g_entry=entry}) =
         sp_high = maxSlot slot g
         proc_entry_sp = slot (CallArea Old) + entry_off
 
-        add_sp_off :: CmmBlock -> BlockEnv Int -> BlockEnv Int
-        add_sp_off b env =
-          case lastNode b of
-            CmmCall {cml_cont=Just succ, cml_ret_args=off} -> mapInsert succ off env
-            CmmForeignCall {succ=succ}                     -> mapInsert succ wORD_SIZE env
-            _                                              -> env
-        spEntryMap = foldGraphBlocks add_sp_off (mapInsert entry entry_off emptyBlockMap) g
         spOffset id = mapLookup id spEntryMap `orElse` 0
 
         sp_on_entry id | id == entry = proc_entry_sp
@@ -427,10 +507,26 @@ manifestSP areaMap entry_off g@(CmmGraph {g_entry=entry}) =
           where spIn = sp_on_entry (entryLabel block)
 
                 middle spOff m = mapExpDeep (replSlot spOff) m
+                -- XXX there shouldn't be any global registers in the
+                -- CmmCall, so there shouldn't be any slots in
+                -- CmmCall... check that...
                 last   spOff l = mapExpDeep (replSlot spOff) l
                 replSlot spOff (CmmStackSlot a i) = CmmRegOff (CmmGlobal Sp) (spOff - (slot a + i))
                 replSlot _ (CmmLit CmmHighStackMark) = -- replacing the high water mark
                   CmmLit (CmmInt (toInteger (max 0 (sp_high - proc_entry_sp))) (typeWidth bWord))
+                -- Invariant: Sp is always greater than SpLim.  Thus, if
+                -- the high water mark is zero, we can optimize away the
+                -- conditional branch.  Relies on dead code elimination
+                -- to get rid of the dead GC blocks.
+                -- EZY: Maybe turn this into a guard that checks if a
+                -- statement is stack-check ish?  Maybe we should make
+                -- an actual mach-op for it, so there's no chance of
+                -- mixing this up with something else...
+                replSlot _ (CmmMachOp (MO_U_Lt _)
+                              [CmmMachOp (MO_Sub _)
+                                         [ CmmReg (CmmGlobal Sp)
+                                         , CmmLit (CmmInt 0 _)],
+                               CmmReg (CmmGlobal SpLim)]) = CmmLit (CmmInt 0 wordWidth)
                 replSlot _ e = e
 
                 replLast :: MaybeC C (CmmNode C O) -> [CmmNode O O] -> CmmNode O C -> FuelUniqSM [CmmBlock]
index d363cef..10f4e8b 100644 (file)
@@ -248,7 +248,7 @@ pprStmt stmt = case stmt of
                 | CmmNeverReturns <- ret ->
                     let myCall = pprCall (pprCLabel lbl) cconv results args safety
                     in (real_fun_proto lbl, myCall)
-                | not (isMathFun lbl || isCas lbl) ->
+                | not (isMathFun lbl) ->
                     let myCall = braces (
                                      pprCFunType (char '*' <> text "ghcFunPtr") cconv results args <> semi
                                   $$ text "ghcFunPtr" <+> equals <+> cast_fn <> semi
index c509eb6..18a06b0 100644 (file)
@@ -36,11 +36,6 @@ Flag ghci
     Default: False
     Manual: True
 
-Flag ncg
-    Description: Build the NCG.
-    Default: False
-    Manual: True
-
 Flag stage1
     Description: Is this stage 1?
     Default: False
@@ -88,9 +83,6 @@ Library
         CPP-Options: -DGHCI
         Include-Dirs: ../libffi/build/include
 
-    if !flag(ncg)
-        CPP-Options: -DOMIT_NATIVE_CODEGEN
-
     Build-Depends: bin-package-db
     Build-Depends: hoopl
 
@@ -490,10 +482,7 @@ Library
         Vectorise.Exp
         Vectorise
 
-    -- We only need to expose more modules as some of the ncg code is used
-    -- by the LLVM backend so its always included
-    if flag(ncg)
-        Exposed-Modules:
+    Exposed-Modules:
             AsmCodeGen
             TargetReg
             NCGMonad
@@ -503,10 +492,6 @@ Library
             RegClass
             PIC
             Platform
-            Alpha.Regs
-            Alpha.RegInfo
-            Alpha.Instr
-            Alpha.CodeGen
             X86.Regs
             X86.RegInfo
             X86.Instr
index 76b393f..55ebb84 100644 (file)
@@ -96,6 +96,58 @@ compiler/stage%/build/Config.hs : mk/config.mk mk/project.mk | $$(dir $$@)/.
        @echo '#error Unknown target arch'                                  >> $@
        @echo '#endif'                                                      >> $@
        @echo                                                               >> $@
+# Sync this with checkOS in configure.ac
+       @echo 'cTargetOS :: OS'                                             >> $@
+       @echo '#if linux_TARGET_OS'                                         >> $@
+       @echo 'cTargetOS = Linux'                                           >> $@
+       @echo '#elif freebsd_TARGET_OS'                                     >> $@
+       @echo 'cTargetOS = FreeBSD'                                         >> $@
+       @echo '#elif netbsd_TARGET_OS'                                      >> $@
+       @echo 'cTargetOS = NetBSD'                                          >> $@
+       @echo '#elif openbsd_TARGET_OS'                                     >> $@
+       @echo 'cTargetOS = OpenBSD'                                         >> $@
+       @echo '#elif dragonfly_TARGET_OS'                                   >> $@
+       @echo 'cTargetOS = OtherOS "dragonfly"'                             >> $@
+       @echo '#elif osf1_TARGET_OS'                                        >> $@
+       @echo 'cTargetOS = OtherOS "osf"'                                   >> $@
+       @echo '#elif osf3_TARGET_OS'                                        >> $@
+       @echo 'cTargetOS = OtherOS "osf"'                                   >> $@
+       @echo '#elif hpux_TARGET_OS'                                        >> $@
+       @echo 'cTargetOS = HPUX'                                            >> $@
+       @echo '#elif linuxaout_TARGET_OS'                                   >> $@
+       @echo 'cTargetOS = Linux'                                           >> $@
+       @echo '#elif kfreebsdgnu_TARGET_OS'                                 >> $@
+       @echo 'cTargetOS = OtherOS "kfreebsdgnu"'                           >> $@
+       @echo '#elif freebsd2_TARGET_OS'                                    >> $@
+       @echo 'cTargetOS = FreeBSD'                                         >> $@
+       @echo '#elif solaris2_TARGET_OS'                                    >> $@
+       @echo 'cTargetOS = Solaris'                                         >> $@
+       @echo '#elif cygwin32_TARGET_OS'                                    >> $@
+       @echo 'cTargetOS = Windows'                                         >> $@
+       @echo '#elif mingw32_TARGET_OS'                                     >> $@
+       @echo 'cTargetOS = Windows'                                         >> $@
+       @echo '#elif darwin_TARGET_OS'                                      >> $@
+       @echo 'cTargetOS = OSX'                                             >> $@
+       @echo '#elif gnu_TARGET_OS'                                         >> $@
+       @echo 'cTargetOS = OtherOS "gnu"'                                   >> $@
+       @echo '#elif nextstep2_TARGET_OS'                                   >> $@
+       @echo 'cTargetOS = OtherOS "nextstep"'                              >> $@
+       @echo '#elif nextstep3_TARGET_OS'                                   >> $@
+       @echo 'cTargetOS = OtherOS "nextstep"'                              >> $@
+       @echo '#elif sunos4_TARGET_OS'                                      >> $@
+       @echo 'cTargetOS = Solaris'                                         >> $@
+       @echo '#elif ultrix_TARGET_OS'                                      >> $@
+       @echo 'cTargetOS = OtherOS "ultrix"'                                >> $@
+       @echo '#elif irix_TARGET_OS'                                        >> $@
+       @echo 'cTargetOS = IRIX'                                            >> $@
+       @echo '#elif aix_TARGET_OS'                                         >> $@
+       @echo 'cTargetOS = AIX'                                             >> $@
+       @echo '#elif haiku_TARGET_OS'                                       >> $@
+       @echo 'cTargetOS = OtherOS "haiku"'                                 >> $@
+       @echo '#else'                                                       >> $@
+       @echo '#error Unknown target OS'                                    >> $@
+       @echo '#endif'                                                      >> $@
+       @echo                                                               >> $@
        @echo 'cProjectName          :: String'                             >> $@
        @echo 'cProjectName          = "$(ProjectName)"'                    >> $@
        @echo 'cProjectVersion       :: String'                             >> $@
@@ -108,8 +160,6 @@ compiler/stage%/build/Config.hs : mk/config.mk mk/project.mk | $$(dir $$@)/.
        @echo 'cBooterVersion        = "$(GhcVersion)"'                     >> $@
        @echo 'cStage                :: String'                             >> $@
        @echo 'cStage                = show (STAGE :: Int)'                 >> $@
-       @echo 'cCcOpts               :: [String]'                           >> $@
-       @echo 'cCcOpts               = words "$(CONF_CC_OPTS_STAGE$*)"'     >> $@
        @echo 'cGccLinkerOpts        :: [String]'                           >> $@
        @echo 'cGccLinkerOpts        = words "$(CONF_GCC_LINKER_OPTS_STAGE$*)"' >> $@
        @echo 'cLdLinkerOpts         :: [String]'                           >> $@
@@ -373,12 +423,6 @@ endif
 
 endif
 
-ifeq "$(GhcWithNativeCodeGen)" "NO"
-# XXX This should logically be a CPP option, but there doesn't seem to
-# be a flag for that
-compiler_CONFIGURE_OPTS += --ghc-option=-DOMIT_NATIVE_CODEGEN
-endif
-
 ifeq "$(TargetOS_CPP)" "openbsd"
 compiler_CONFIGURE_OPTS += --ld-options=-E
 endif
index dfc77e5..2c7473b 100644 (file)
@@ -31,6 +31,7 @@ import Constants
 import FastString
 import SMRep
 import Outputable
+import Config
 
 import Control.Monad    ( foldM )
 import Control.Monad.ST ( runST )
@@ -44,6 +45,7 @@ import Data.Char        ( ord )
 import Data.List
 import Data.Map (Map)
 import qualified Data.Map as Map
+import Distribution.System
 
 import GHC.Base         ( ByteArray#, MutableByteArray#, RealWorld )
 
@@ -395,12 +397,11 @@ mkBits findLabel st proto_insns
           = do st_l1 <- addToSS st_l0 (BCONPtrItbl (getName dcon))
                return (sizeSS16 st_l0, (st_i0,st_l1,st_p0))
 
-#ifdef mingw32_TARGET_OS
        literal st (MachLabel fs (Just sz) _)
+        | cTargetOS == Windows
             = litlabel st (appendFS fs (mkFastString ('@':show sz)))
         -- On Windows, stdcall labels have a suffix indicating the no. of
         -- arg words, e.g. foo@8.  testcase: ffi012(ghci)
-#endif
        literal st (MachLabel fs _ _) = litlabel st fs
        literal st (MachWord w)     = int st (fromIntegral w)
        literal st (MachInt j)      = int st (fromIntegral j)
index 7b38ed8..ac187e0 100644 (file)
@@ -29,7 +29,7 @@ jmpInst    = B.pack "\n\tjmp"
 infoLen, spFix, labelStart :: Int
 infoLen = B.length infoSec
 spFix   = 4
-labelStart = B.length jmpInst + 1
+labelStart = B.length jmpInst
 
 -- Search Predicates
 eolPred, dollarPred, commaPred :: Char -> Bool
@@ -114,11 +114,13 @@ fixupStack f f' =
         (a', n) = B.breakEnd dollarPred a
         (n', x) = B.break commaPred n
         num     = B.pack $ show $ readInt n' + spFix
+        -- We need to avoid processing jumps to labels, they are of the form:
+        -- jmp\tL..., jmp\t_f..., jmpl\t_f..., jmpl\t*%eax..., jmpl *L...
+        targ = B.dropWhile ((==)'*') $ B.drop 1 $ B.dropWhile ((/=)'\t') $
+                B.drop labelStart c
     in if B.null c
           then f' `B.append` f
-          -- We need to avoid processing jumps to labels, they are of the form:
-          -- jmp\tL..., jmp\t_f..., jmpl\t_f..., jmpl\t*%eax...
-          else if B.index c labelStart == 'L'
+          else if B.head targ == 'L'
                 then fixupStack b $ f' `B.append` a `B.append` l
                 else fixupStack b $ f' `B.append` a' `B.append` num `B.append`
                                     x `B.append` l
index f503077..f5e3394 100644 (file)
@@ -8,9 +8,7 @@ module CodeOutput( codeOutput, outputForeignStubs ) where
 
 #include "HsVersions.h"
 
-#ifndef OMIT_NATIVE_CODEGEN
-import AsmCodeGen      ( nativeCodeGen )
-#endif
+import AsmCodeGen ( nativeCodeGen )
 import LlvmCodeGen ( llvmCodeGen )
 
 import UniqSupply      ( mkSplitUniqSupply )
@@ -149,24 +147,16 @@ outputC dflags filenm flat_absC packages
 
 \begin{code}
 outputAsm :: DynFlags -> FilePath -> [RawCmm] -> IO ()
-
-#ifndef OMIT_NATIVE_CODEGEN
-
 outputAsm dflags filenm flat_absC
+ | cGhcWithNativeCodeGen == "YES"
   = do ncg_uniqs <- mkSplitUniqSupply 'n'
 
        {-# SCC "OutputAsm" #-} doOutput filenm $
-          \f -> {-# SCC "NativeCodeGen" #-}
-                nativeCodeGen dflags f ncg_uniqs flat_absC
-  where
+           \f -> {-# SCC "NativeCodeGen" #-}
+                 nativeCodeGen dflags f ncg_uniqs flat_absC
 
-#else /* OMIT_NATIVE_CODEGEN */
-
-outputAsm _ _ _
-  = pprPanic "This compiler was built without a native code generator"
-            (text "Use -fvia-C instead")
-
-#endif
+ | otherwise
+  = panic "This compiler was built without a native code generator"
 \end{code}
 
 
index f92a411..03e3cf6 100644 (file)
@@ -55,6 +55,7 @@ import MonadUtils
 -- import Data.Either
 import Exception
 import Data.IORef       ( readIORef )
+import Distribution.System
 -- import GHC.Exts              ( Int(..) )
 import System.Directory
 import System.FilePath
@@ -269,11 +270,11 @@ link :: GhcLink                 -- interactive or batch
 -- exports main, i.e., we have good reason to believe that linking
 -- will succeed.
 
-#ifdef GHCI
 link LinkInMemory _ _ _
-    = do -- Not Linking...(demand linker will do the job)
-         return Succeeded
-#endif
+    = if cGhcWithInterpreter == "YES"
+      then -- Not Linking...(demand linker will do the job)
+           return Succeeded
+      else panicBadLink LinkInMemory
 
 link NoLink _ _ _
    = return Succeeded
@@ -284,11 +285,6 @@ link LinkBinary dflags batch_attempt_linking hpt
 link LinkDynLib dflags batch_attempt_linking hpt
    = link' dflags batch_attempt_linking hpt
 
-#ifndef GHCI
--- warning suppression
-link other _ _ _ = panicBadLink other
-#endif
-
 panicBadLink :: GhcLink -> a
 panicBadLink other = panic ("link: GHC not built to link this way: " ++
                             show other)
@@ -1027,7 +1023,6 @@ runPhase cc_phase input_fn dflags
         let include_paths = foldr (\ x xs -> "-I" : x : xs) []
                               (cmdline_include_paths ++ pkg_include_dirs)
 
-        let md_c_flags = machdepCCOpts dflags
         let gcc_extra_viac_flags = extraGccViaCFlags dflags
         let pic_c_flags = picCCOpts dflags
 
@@ -1062,15 +1057,14 @@ runPhase cc_phase input_fn dflags
 
         let
           more_hcc_opts =
-#if i386_TARGET_ARCH
                 -- on x86 the floating point regs have greater precision
                 -- than a double, which leads to unpredictable results.
                 -- By default, we turn this off with -ffloat-store unless
                 -- the user specified -fexcess-precision.
-                (if dopt Opt_ExcessPrecision dflags
-                        then []
-                        else [ "-ffloat-store" ]) ++
-#endif
+                (if cTargetArch == I386 &&
+                    not (dopt Opt_ExcessPrecision dflags)
+                        then [ "-ffloat-store" ]
+                        else []) ++
 
                 -- gcc's -fstrict-aliasing allows two accesses to memory
                 -- to be considered non-aliasing if they have different types.
@@ -1092,29 +1086,28 @@ runPhase cc_phase input_fn dflags
                         , SysTools.FileOption "" output_fn
                         ]
                        ++ map SysTools.Option (
-                          md_c_flags
-                       ++ pic_c_flags
+                          pic_c_flags
 
-#if    defined(mingw32_TARGET_OS)
                 -- Stub files generated for foreign exports references the runIO_closure
                 -- and runNonIO_closure symbols, which are defined in the base package.
                 -- These symbols are imported into the stub.c file via RtsAPI.h, and the
                 -- way we do the import depends on whether we're currently compiling
                 -- the base package or not.
-                       ++ (if thisPackage dflags == basePackageId
+                       ++ (if cTargetOS == Windows &&
+                              thisPackage dflags == basePackageId
                                 then [ "-DCOMPILING_BASE_PACKAGE" ]
                                 else [])
-#endif
 
-#ifdef sparc_TARGET_ARCH
         -- We only support SparcV9 and better because V8 lacks an atomic CAS
         -- instruction. Note that the user can still override this
         -- (e.g., -mcpu=ultrasparc) as GCC picks the "best" -mcpu flag
         -- regardless of the ordering.
         --
         -- This is a temporary hack.
-                       ++ ["-mcpu=v9"]
-#endif
+                       ++ (if cTargetArch == Sparc
+                           then ["-mcpu=v9"]
+                           else [])
+
                        ++ (if hcc
                              then gcc_extra_viac_flags ++ more_hcc_opts
                              else [])
@@ -1178,11 +1171,10 @@ runPhase As input_fn dflags
         -- might be a hierarchical module.
         io $ createDirectoryHierarchy (takeDirectory output_fn)
 
-        let md_c_flags = machdepCCOpts dflags
         io $ SysTools.runAs dflags
                        (map SysTools.Option as_opts
                        ++ [ SysTools.Option ("-I" ++ p) | p <- cmdline_include_paths ]
-#ifdef sparc_TARGET_ARCH
+
         -- We only support SparcV9 and better because V8 lacks an atomic CAS
         -- instruction so we have to make sure that the assembler accepts the
         -- instruction set. Note that the user can still override this
@@ -1190,14 +1182,15 @@ runPhase As input_fn dflags
         -- regardless of the ordering.
         --
         -- This is a temporary hack.
-                       ++ [ SysTools.Option "-mcpu=v9" ]
-#endif
+                       ++ (if cTargetArch == Sparc
+                           then [SysTools.Option "-mcpu=v9"]
+                           else [])
+
                        ++ [ SysTools.Option "-c"
                           , SysTools.FileOption "" input_fn
                           , SysTools.Option "-o"
                           , SysTools.FileOption "" output_fn
-                          ]
-                       ++ map SysTools.Option md_c_flags)
+                          ])
 
         return (next_phase, output_fn)
 
@@ -1233,11 +1226,10 @@ runPhase SplitAs _input_fn dflags
             split_obj n = split_odir </>
                           takeFileName base_o ++ "__" ++ show n <.> osuf
 
-        let md_c_flags = machdepCCOpts dflags
         let assemble_file n
               = SysTools.runAs dflags
                          (map SysTools.Option as_opts ++
-#ifdef sparc_TARGET_ARCH
+
         -- We only support SparcV9 and better because V8 lacks an atomic CAS
         -- instruction so we have to make sure that the assembler accepts the
         -- instruction set. Note that the user can still override this
@@ -1245,14 +1237,15 @@ runPhase SplitAs _input_fn dflags
         -- regardless of the ordering.
         --
         -- This is a temporary hack.
-                          [ SysTools.Option "-mcpu=v9" ] ++
-#endif
+                          (if cTargetArch == Sparc
+                           then [SysTools.Option "-mcpu=v9"]
+                           else []) ++
+
                           [ SysTools.Option "-c"
                           , SysTools.Option "-o"
                           , SysTools.FileOption "" (split_obj n)
                           , SysTools.FileOption "" (split_s n)
-                          ]
-                       ++ map SysTools.Option md_c_flags)
+                          ])
 
         io $ mapM_ assemble_file [1..n]
 
@@ -1322,11 +1315,9 @@ runPhase LlvmLlc input_fn dflags
   = do
     let lc_opts = getOpts dflags opt_lc
     let opt_lvl = max 0 (min 2 $ optLevel dflags)
-#if darwin_TARGET_OS
-    let nphase = LlvmMangle
-#else
-    let nphase = As
-#endif
+    let nphase = if cTargetOS == OSX
+                 then LlvmMangle
+                 else As
     let rmodel | opt_PIC        = "pic"
                | not opt_Static = "dynamic-no-pic"
                | otherwise      = "static"
@@ -1342,11 +1333,9 @@ runPhase LlvmLlc input_fn dflags
 
     return (nphase, output_fn)
   where
-#if darwin_TARGET_OS
-        llvmOpts = ["-O1", "-O2", "-O2"]
-#else
-        llvmOpts = ["-O1", "-O2", "-O3"]
-#endif
+        llvmOpts = if cTargetOS == OSX
+                   then ["-O1", "-O2", "-O2"]
+                   else ["-O1", "-O2", "-O3"]
 
 
 -----------------------------------------------------------------------------
@@ -1419,14 +1408,12 @@ mkExtraCObj dflags xs
       oFile <- newTempName dflags "o"
       writeFile cFile xs
       let rtsDetails = getPackageDetails (pkgState dflags) rtsPackageId
-          md_c_flags = machdepCCOpts dflags
       SysTools.runCc dflags
                      ([Option        "-c",
                        FileOption "" cFile,
                        Option        "-o",
                        FileOption "" oFile] ++
-                      map (FileOption "-I") (includeDirs rtsDetails) ++
-                      map Option md_c_flags)
+                      map (FileOption "-I") (includeDirs rtsDetails))
       return oFile
 
 mkExtraObjToLinkIntoBinary :: DynFlags -> [PackageId] -> IO FilePath
@@ -1654,20 +1641,20 @@ linkBinary dflags o_files dep_packages = do
 
     rc_objs <- maybeCreateManifest dflags output_fn
 
-    let md_c_flags = machdepCCOpts dflags
     SysTools.runLink dflags (
                        map SysTools.Option verbFlags
                       ++ [ SysTools.Option "-o"
                          , SysTools.FileOption "" output_fn
                          ]
                       ++ map SysTools.Option (
-                         md_c_flags
+                         []
 
-#ifdef mingw32_TARGET_OS
                       -- Permit the linker to auto link _symbol to _imp_symbol.
                       -- This lets us link against DLLs without needing an "import library".
-                      ++ ["-Wl,--enable-auto-import"]
-#endif
+                      ++ (if cTargetOS == Windows
+                          then ["-Wl,--enable-auto-import"]
+                          else [])
+
                       ++ o_files
                       ++ extra_ld_inputs
                       ++ lib_path_opts
@@ -1698,19 +1685,15 @@ linkBinary dflags o_files dep_packages = do
 exeFileName :: DynFlags -> FilePath
 exeFileName dflags
   | Just s <- outputFile dflags =
-#if defined(mingw32_HOST_OS)
-      if null (takeExtension s)
-        then s <.> "exe"
-        else s
-#else
-      s
-#endif
+      if cTargetOS == Windows
+      then if null (takeExtension s)
+           then s <.> "exe"
+           else s
+      else s
   | otherwise =
-#if defined(mingw32_HOST_OS)
-        "main.exe"
-#else
-        "a.out"
-#endif
+      if cTargetOS == Windows
+      then "main.exe"
+      else "a.out"
 
 maybeCreateManifest
    :: DynFlags
@@ -1806,7 +1789,6 @@ linkDynLib dflags o_files dep_packages = do
         -- probably _stub.o files
     extra_ld_inputs <- readIORef v_Ld_inputs
 
-    let md_c_flags = machdepCCOpts dflags
     let extra_ld_opts = getOpts dflags opt_l
 
     extraLinkObj <- mkExtraObjToLinkIntoBinary dflags dep_packages
@@ -1828,11 +1810,10 @@ linkDynLib dflags o_files dep_packages = do
             ]
          ++ map (SysTools.FileOption "") o_files
          ++ map SysTools.Option (
-            md_c_flags
 
          -- Permit the linker to auto link _symbol to _imp_symbol
          -- This lets us link against DLLs without needing an "import library"
-         ++ ["-Wl,--enable-auto-import"]
+            ["-Wl,--enable-auto-import"]
 
          ++ extra_ld_inputs
          ++ lib_path_opts
@@ -1884,8 +1865,7 @@ linkDynLib dflags o_files dep_packages = do
             , SysTools.FileOption "" output_fn
             ]
          ++ map SysTools.Option (
-            md_c_flags
-         ++ o_files
+            o_files
          ++ [ "-undefined", "dynamic_lookup", "-single_module",
 #if !defined(x86_64_TARGET_ARCH)
               "-Wl,-read_only_relocs,suppress",
@@ -1919,8 +1899,7 @@ linkDynLib dflags o_files dep_packages = do
             , SysTools.FileOption "" output_fn
             ]
          ++ map SysTools.Option (
-            md_c_flags
-         ++ o_files
+            o_files
          ++ [ "-shared" ]
          ++ bsymbolicFlag
             -- Set the library soname. We use -h rather than -soname as
@@ -1949,11 +1928,8 @@ doCpp dflags raw include_cc_opts input_fn output_fn = do
     let verbFlags = getVerbFlags dflags
 
     let cc_opts
-          | not include_cc_opts = []
-          | otherwise           = (optc ++ md_c_flags)
-                where
-                      optc = getOpts dflags opt_c
-                      md_c_flags = machdepCCOpts dflags
+          | include_cc_opts = getOpts dflags opt_c
+          | otherwise       = []
 
     let cpp_prog args | raw       = SysTools.runCpp dflags args
                       | otherwise = SysTools.runCc dflags (SysTools.Option "-E" : args)
@@ -2005,7 +1981,6 @@ joinObjectFiles dflags o_files output_fn = do
                             SysTools.Option ld_x_flag,
                             SysTools.Option "-o",
                             SysTools.FileOption "" output_fn ]
-                         ++ map SysTools.Option md_c_flags
                          ++ args)
 
       ld_x_flag | null cLD_X = ""
@@ -2017,8 +1992,6 @@ joinObjectFiles dflags o_files output_fn = do
       ld_build_id | cLdHasBuildId == "YES"  = "-Wl,--build-id=none"
                   | otherwise               = ""
 
-      md_c_flags = machdepCCOpts dflags
-  
   if cLdIsGNULd == "YES"
      then do
           script <- newTempName dflags "ldscript"
index 9b5670e..ed64fd0 100644 (file)
@@ -60,7 +60,7 @@ module DynFlags (
         supportedLanguagesAndExtensions,
 
         -- ** DynFlag C compiler options
-        machdepCCOpts, picCCOpts,
+        picCCOpts,
 
         -- * Configuration of the stg-to-stg passes
         StgToDo(..),
@@ -77,9 +77,7 @@ module DynFlags (
 
 #include "HsVersions.h"
 
-#ifndef OMIT_NATIVE_CODEGEN
 import Platform
-#endif
 import Module
 import PackageConfig
 import PrelNames        ( mAIN )
@@ -110,7 +108,7 @@ import Data.Char
 import Data.List
 import Data.Map (Map)
 import qualified Data.Map as Map
--- import Data.Maybe
+import Distribution.System
 import System.FilePath
 import System.IO        ( stderr, hPutChar )
 
@@ -403,9 +401,7 @@ data DynFlags = DynFlags {
   floatLamArgs          :: Maybe Int,   -- ^ Arg count for lambda floating
                                        --   See CoreMonad.FloatOutSwitches
 
-#ifndef OMIT_NATIVE_CODEGEN
-  targetPlatform       :: Platform,    -- ^ The platform we're compiling for. Used by the NCG.
-#endif
+  targetPlatform        :: Platform.Platform, -- ^ The platform we're compiling for. Used by the NCG.
   cmdlineHcIncludes     :: [String],    -- ^ @\-\#includes@
   importPaths           :: [FilePath],
   mainModIs             :: Module,
@@ -631,6 +627,14 @@ data HscTarget
   | HscNothing     -- ^ Don't generate any code.  See notes above.
   deriving (Eq, Show)
 
+showHscTargetFlag :: HscTarget -> String
+showHscTargetFlag HscC           = "-fvia-c"
+showHscTargetFlag HscAsm         = "-fasm"
+showHscTargetFlag HscLlvm        = "-fllvm"
+showHscTargetFlag HscJava        = panic "No flag for HscJava"
+showHscTargetFlag HscInterpreted = "-fbyte-code"
+showHscTargetFlag HscNothing     = "-fno-code"
+
 -- | Will this target result in an object file on the disk?
 isObjectTarget :: HscTarget -> Bool
 isObjectTarget HscC     = True
@@ -693,8 +697,9 @@ defaultHscTarget = defaultObjectTarget
 -- object files on the current platform.
 defaultObjectTarget :: HscTarget
 defaultObjectTarget
+  | cGhcUnregisterised    == "YES"      =  HscC
   | cGhcWithNativeCodeGen == "YES"      =  HscAsm
-  | otherwise                           =  HscC
+  | otherwise                           =  HscLlvm
 
 data DynLibLoader
   = Deployable
@@ -741,9 +746,7 @@ defaultDynFlags mySettings =
         floatLamArgs            = Just 0,      -- Default: float only if no fvs
         strictnessBefore        = [],
 
-#ifndef OMIT_NATIVE_CODEGEN
         targetPlatform          = defaultTargetPlatform,
-#endif
         cmdlineHcIncludes       = [],
         importPaths             = ["."],
         mainModIs               = mAIN,
@@ -1100,12 +1103,13 @@ parseDynamicFlags_ dflags0 args pkg_flags = do
   when (not (null errs)) $ ghcError $ errorsToGhcException errs
 
   let (pic_warns, dflags2)
-#if !(x86_64_TARGET_ARCH && linux_TARGET_OS)
-        | (not opt_Static || opt_PIC) && hscTarget dflags1 == HscLlvm
+        | not (cTargetArch == X86_64 && cTargetOS == Linux) &&
+          (not opt_Static || opt_PIC) &&
+          hscTarget dflags1 == HscLlvm
         = ([L noSrcSpan $ "Warning: -fllvm is incompatible with -fPIC and -"
-                ++ "dynamic on this platform;\n              ignoring -fllvm"],
-                dflags1{ hscTarget = HscAsm })
-#endif
+                       ++ "dynamic on this platform;\n"
+                       ++ "         using " ++ showHscTargetFlag defaultObjectTarget ++ " instead"],
+                dflags1{ hscTarget = defaultObjectTarget })
         | otherwise = ([], dflags1)
 
   return (dflags2, leftover, pic_warns ++ warns)
@@ -1346,10 +1350,11 @@ dynamic_flags = [
   , Flag "w"      (NoArg (mapM_ unSetDynFlag minuswRemovesOpts))
 
         ------ Optimisation flags ------------------------------------------
-  , Flag "O"      (noArg (setOptLevel 1))
-  , Flag "Onot"   (noArgDF (setOptLevel 0) "Use -O0 instead")
-  , Flag "Odph"   (noArg setDPHOpt)
-  , Flag "O"      (OptIntSuffix (\mb_n -> upd (setOptLevel (mb_n `orElse` 1))))
+  , Flag "O"      (noArgM (setOptLevel 1))
+  , Flag "Onot"   (noArgM (\dflags -> do deprecate "Use -O0 instead"
+                                         setOptLevel 0 dflags))
+  , Flag "Odph"   (noArgM setDPHOpt)
+  , Flag "O"      (optIntSuffixM (\mb_n -> setOptLevel (mb_n `orElse` 1)))
                 -- If the number is missing, use 1
 
   , Flag "fsimplifier-phases"          (intSuffix (\n d -> d{ simplPhases = n }))
@@ -1907,13 +1912,21 @@ checkTemplateHaskellOk _ = return ()
 type DynP = EwM (CmdLineP DynFlags)
 
 upd :: (DynFlags -> DynFlags) -> DynP ()
-upd f = liftEwM (do { dfs <- getCmdLineState
-                    ; putCmdLineState $! (f dfs) })
+upd f = liftEwM (do dflags <- getCmdLineState
+                    putCmdLineState $! f dflags)
+
+updM :: (DynFlags -> DynP DynFlags) -> DynP ()
+updM f = do dflags <- liftEwM getCmdLineState
+            dflags' <- f dflags
+            liftEwM $ putCmdLineState $! dflags'
 
 --------------- Constructor functions for OptKind -----------------
 noArg :: (DynFlags -> DynFlags) -> OptKind (CmdLineP DynFlags)
 noArg fn = NoArg (upd fn)
 
+noArgM :: (DynFlags -> DynP DynFlags) -> OptKind (CmdLineP DynFlags)
+noArgM fn = NoArg (updM fn)
+
 noArgDF :: (DynFlags -> DynFlags) -> String -> OptKind (CmdLineP DynFlags)
 noArgDF fn deprec = NoArg (upd fn >> deprecate deprec)
 
@@ -1927,6 +1940,10 @@ hasArgDF fn deprec = HasArg (\s -> do { upd (fn s)
 intSuffix :: (Int -> DynFlags -> DynFlags) -> OptKind (CmdLineP DynFlags)
 intSuffix fn = IntSuffix (\n -> upd (fn n))
 
+optIntSuffixM :: (Maybe Int -> DynFlags -> DynP DynFlags)
+              -> OptKind (CmdLineP DynFlags)
+optIntSuffixM fn = OptIntSuffix (\mi -> updM (fn mi))
+
 setDumpFlag :: DynFlag -> OptKind (CmdLineP DynFlags)
 setDumpFlag dump_flag = NoArg (setDumpFlag' dump_flag)
 
@@ -2025,20 +2042,36 @@ setTarget l = upd set
 -- not from bytecode to object-code.  The idea is that -fasm/-fllvm
 -- can be safely used in an OPTIONS_GHC pragma.
 setObjTarget :: HscTarget -> DynP ()
-setObjTarget l = upd set
+setObjTarget l = updM set
   where
-   set dfs
-     | isObjectTarget (hscTarget dfs) = dfs { hscTarget = l }
-     | otherwise = dfs
-
-setOptLevel :: Int -> DynFlags -> DynFlags
+   set dflags
+     | isObjectTarget (hscTarget dflags)
+       = case l of
+         HscC
+          | cGhcUnregisterised /= "YES" ->
+             do addWarn ("Compiler not unregisterised, so ignoring " ++
+                         showHscTargetFlag l)
+                return dflags
+         HscAsm
+          | cGhcWithNativeCodeGen /= "YES" ->
+             do addWarn ("Compiler has no native codegen, so ignoring " ++
+                         showHscTargetFlag l)
+                return dflags
+         HscLlvm
+          | cGhcUnregisterised == "YES" ->
+             do addWarn ("Compiler unregisterised, so ignoring " ++
+                         showHscTargetFlag l)
+                return dflags
+         _ -> return $ dflags { hscTarget = l }
+     | otherwise = return dflags
+
+setOptLevel :: Int -> DynFlags -> DynP DynFlags
 setOptLevel n dflags
    | hscTarget dflags == HscInterpreted && n > 0
-        = dflags
-            -- not in IO any more, oh well:
-            -- putStr "warning: -O conflicts with --interactive; -O ignored.\n"
+        = do addWarn "-O conflicts with --interactive; -O ignored."
+             return dflags
    | otherwise
-        = updOptLevel n dflags
+        = return (updOptLevel n dflags)
 
 
 -- -Odph is equivalent to
@@ -2047,7 +2080,7 @@ setOptLevel n dflags
 --    -fmax-simplifier-iterations20     this is necessary sometimes
 --    -fsimplifier-phases=3             we use an additional simplifier phase for fusion
 --
-setDPHOpt :: DynFlags -> DynFlags
+setDPHOpt :: DynFlags -> DynP DynFlags
 setDPHOpt dflags = setOptLevel 2 (dflags { maxSimplIterations  = 20
                                          , simplPhases         = 3
                                          })
@@ -2203,37 +2236,6 @@ setOptHpcDir arg  = upd $ \ d -> d{hpcDir = arg}
 -- The options below are not dependent on the version of gcc, only the
 -- platform.
 
-machdepCCOpts :: DynFlags -> [String] -- flags for all C compilations
-machdepCCOpts _ = cCcOpts ++ machdepCCOpts'
-
-machdepCCOpts' :: [String] -- flags for all C compilations
-machdepCCOpts'
-#if alpha_TARGET_ARCH
-        =       ["-w", "-mieee"
-#ifdef HAVE_THREADED_RTS_SUPPORT
-                    , "-D_REENTRANT"
-#endif
-                   ]
-        -- For now, to suppress the gcc warning "call-clobbered
-        -- register used for global register variable", we simply
-        -- disable all warnings altogether using the -w flag. Oh well.
-
-#elif hppa_TARGET_ARCH
-        -- ___HPUX_SOURCE, not _HPUX_SOURCE, is #defined if -ansi!
-        -- (very nice, but too bad the HP /usr/include files don't agree.)
-        = ["-D_HPUX_SOURCE"]
-
-#elif i386_TARGET_ARCH
-      -- -fno-defer-pop : basically the same game as for m68k
-      --
-      -- -fomit-frame-pointer : *must* in .hc files; because we're stealing
-      --   the fp (%ebp) for our register maps.
-        =  if opt_Static then ["-DDONT_WANT_WIN32_DLL_SUPPORT"] else []
-
-#else
-        = []
-#endif
-
 picCCOpts :: DynFlags -> [String]
 picCCOpts _dflags
 #if darwin_TARGET_OS
@@ -2303,7 +2305,6 @@ compilerInfo dflags
        ("Debug on",                    show debugIsOn),
        ("LibDir",                      topDir dflags),
        ("Global Package DB",           systemPackageConfig dflags),
-       ("C compiler flags",            show cCcOpts),
        ("Gcc Linker flags",            show cGccLinkerOpts),
        ("Ld Linker flags",             show cLdLinkerOpts)
       ]
index 2529dbf..97a6514 100644 (file)
@@ -182,6 +182,9 @@ initSysTools mbMinusB
         -- to make that possible, so for now you can't.
         ; gcc_prog <- if isWindowsHost then return $ installed_mingw_bin "gcc"
                                        else getSetting "C compiler command"
+        ; gcc_args_str <- if isWindowsHost then return []
+                                           else getSetting "C compiler flags"
+        ; let gcc_args = map Option (words gcc_args_str)
         ; perl_path <- if isWindowsHost
                        then return $ installed_perl_bin "perl"
                        else getSetting "perl command"
@@ -224,12 +227,16 @@ initSysTools mbMinusB
         -- cpp is derived from gcc on all platforms
         -- HACK, see setPgmP below. We keep 'words' here to remember to fix
         -- Config.hs one day.
-        ; let cpp_path  = (gcc_prog,
-                           (Option "-E"):(map Option (words cRAWCPP_FLAGS)))
+        ; let cpp_prog  = gcc_prog
+              cpp_args  = Option "-E"
+                        : map Option (words cRAWCPP_FLAGS)
+                       ++ gcc_args
 
         -- Other things being equal, as and ld are simply gcc
         ; let   as_prog  = gcc_prog
+                as_args  = gcc_args
                 ld_prog  = gcc_prog
+                ld_args  = gcc_args
 
         -- figure out llvm location. (TODO: Acutally implement).
         ; let lc_prog = "llc"
@@ -244,12 +251,12 @@ initSysTools mbMinusB
                         sExtraGccViaCFlags = words myExtraGccViaCFlags,
                         sSystemPackageConfig = pkgconfig_path,
                         sPgm_L   = unlit_path,
-                        sPgm_P   = cpp_path,
+                        sPgm_P   = (cpp_prog, cpp_args),
                         sPgm_F   = "",
-                        sPgm_c   = (gcc_prog,[]),
+                        sPgm_c   = (gcc_prog, gcc_args),
                         sPgm_s   = (split_prog,split_args),
-                        sPgm_a   = (as_prog,[]),
-                        sPgm_l   = (ld_prog,[]),
+                        sPgm_a   = (as_prog, as_args),
+                        sPgm_l   = (ld_prog, ld_args),
                         sPgm_dll = (mkdll_prog,mkdll_args),
                         sPgm_T   = touch_path,
                         sPgm_sysman = top_dir ++ "/ghc/rts/parallel/SysMan",
diff --git a/compiler/nativeGen/Alpha/CodeGen.hs b/compiler/nativeGen/Alpha/CodeGen.hs
deleted file mode 100644 (file)
index 4ce774f..0000000
+++ /dev/null
@@ -1,789 +0,0 @@
-module Alpha.CodeGen ()
-
-where
-
-{-
-
-getRegister :: CmmExpr -> NatM Register
-
-#if !x86_64_TARGET_ARCH
-    -- on x86_64, we have %rip for PicBaseReg, but it's not a full-featured
-    -- register, it can only be used for rip-relative addressing.
-getRegister (CmmReg (CmmGlobal PicBaseReg))
-  = do
-      reg <- getPicBaseNat wordSize
-      return (Fixed wordSize reg nilOL)
-#endif
-
-getRegister (CmmReg reg) 
-  = return (Fixed (cmmTypeSize (cmmRegType reg)) 
-                 (getRegisterReg reg) nilOL)
-
-getRegister tree@(CmmRegOff _ _) 
-  = getRegister (mangleIndexTree tree)
-
-
-#if WORD_SIZE_IN_BITS==32
-    -- for 32-bit architectuers, support some 64 -> 32 bit conversions:
-    -- TO_W_(x), TO_W_(x >> 32)
-
-getRegister (CmmMachOp (MO_UU_Conv W64 W32)
-             [CmmMachOp (MO_U_Shr W64) [x,CmmLit (CmmInt 32 _)]]) = do
-  ChildCode64 code rlo <- iselExpr64 x
-  return $ Fixed II32 (getHiVRegFromLo rlo) code
-
-getRegister (CmmMachOp (MO_SS_Conv W64 W32)
-             [CmmMachOp (MO_U_Shr W64) [x,CmmLit (CmmInt 32 _)]]) = do
-  ChildCode64 code rlo <- iselExpr64 x
-  return $ Fixed II32 (getHiVRegFromLo rlo) code
-
-getRegister (CmmMachOp (MO_UU_Conv W64 W32) [x]) = do
-  ChildCode64 code rlo <- iselExpr64 x
-  return $ Fixed II32 rlo code
-
-getRegister (CmmMachOp (MO_SS_Conv W64 W32) [x]) = do
-  ChildCode64 code rlo <- iselExpr64 x
-  return $ Fixed II32 rlo code       
-
-#endif
-
--- end of machine-"independent" bit; here we go on the rest...
-
-
-getRegister (StDouble d)
-  = getBlockIdNat                  `thenNat` \ lbl ->
-    getNewRegNat PtrRep            `thenNat` \ tmp ->
-    let code dst = mkSeqInstrs [
-           LDATA RoDataSegment lbl [
-                   DATA TF [ImmLab (rational d)]
-               ],
-           LDA tmp (AddrImm (ImmCLbl lbl)),
-           LD TF dst (AddrReg tmp)]
-    in
-       return (Any FF64 code)
-
-getRegister (StPrim primop [x]) -- unary PrimOps
-  = case primop of
-      IntNegOp -> trivialUCode (NEG Q False) x
-
-      NotOp    -> trivialUCode NOT x
-
-      FloatNegOp  -> trivialUFCode FloatRep (FNEG TF) x
-      DoubleNegOp -> trivialUFCode FF64 (FNEG TF) x
-
-      OrdOp -> coerceIntCode IntRep x
-      ChrOp -> chrCode x
-
-      Float2IntOp  -> coerceFP2Int    x
-      Int2FloatOp  -> coerceInt2FP pr x
-      Double2IntOp -> coerceFP2Int    x
-      Int2DoubleOp -> coerceInt2FP pr x
-
-      Double2FloatOp -> coerceFltCode x
-      Float2DoubleOp -> coerceFltCode x
-
-      other_op -> getRegister (StCall fn CCallConv FF64 [x])
-       where
-         fn = case other_op of
-                FloatExpOp    -> fsLit "exp"
-                FloatLogOp    -> fsLit "log"
-                FloatSqrtOp   -> fsLit "sqrt"
-                FloatSinOp    -> fsLit "sin"
-                FloatCosOp    -> fsLit "cos"
-                FloatTanOp    -> fsLit "tan"
-                FloatAsinOp   -> fsLit "asin"
-                FloatAcosOp   -> fsLit "acos"
-                FloatAtanOp   -> fsLit "atan"
-                FloatSinhOp   -> fsLit "sinh"
-                FloatCoshOp   -> fsLit "cosh"
-                FloatTanhOp   -> fsLit "tanh"
-                DoubleExpOp   -> fsLit "exp"
-                DoubleLogOp   -> fsLit "log"
-                DoubleSqrtOp  -> fsLit "sqrt"
-                DoubleSinOp   -> fsLit "sin"
-                DoubleCosOp   -> fsLit "cos"
-                DoubleTanOp   -> fsLit "tan"
-                DoubleAsinOp  -> fsLit "asin"
-                DoubleAcosOp  -> fsLit "acos"
-                DoubleAtanOp  -> fsLit "atan"
-                DoubleSinhOp  -> fsLit "sinh"
-                DoubleCoshOp  -> fsLit "cosh"
-                DoubleTanhOp  -> fsLit "tanh"
-  where
-    pr = panic "MachCode.getRegister: no primrep needed for Alpha"
-
-getRegister (StPrim primop [x, y]) -- dyadic PrimOps
-  = case primop of
-      CharGtOp -> trivialCode (CMP LTT) y x
-      CharGeOp -> trivialCode (CMP LE) y x
-      CharEqOp -> trivialCode (CMP EQQ) x y
-      CharNeOp -> int_NE_code x y
-      CharLtOp -> trivialCode (CMP LTT) x y
-      CharLeOp -> trivialCode (CMP LE) x y
-
-      IntGtOp  -> trivialCode (CMP LTT) y x
-      IntGeOp  -> trivialCode (CMP LE) y x
-      IntEqOp  -> trivialCode (CMP EQQ) x y
-      IntNeOp  -> int_NE_code x y
-      IntLtOp  -> trivialCode (CMP LTT) x y
-      IntLeOp  -> trivialCode (CMP LE) x y
-
-      WordGtOp -> trivialCode (CMP ULT) y x
-      WordGeOp -> trivialCode (CMP ULE) x y
-      WordEqOp -> trivialCode (CMP EQQ)  x y
-      WordNeOp -> int_NE_code x y
-      WordLtOp -> trivialCode (CMP ULT) x y
-      WordLeOp -> trivialCode (CMP ULE) x y
-
-      AddrGtOp -> trivialCode (CMP ULT) y x
-      AddrGeOp -> trivialCode (CMP ULE) y x
-      AddrEqOp -> trivialCode (CMP EQQ)  x y
-      AddrNeOp -> int_NE_code x y
-      AddrLtOp -> trivialCode (CMP ULT) x y
-      AddrLeOp -> trivialCode (CMP ULE) x y
-       
-      FloatGtOp -> cmpF_code (FCMP TF LE) EQQ x y
-      FloatGeOp -> cmpF_code (FCMP TF LTT) EQQ x y
-      FloatEqOp -> cmpF_code (FCMP TF EQQ) NE x y
-      FloatNeOp -> cmpF_code (FCMP TF EQQ) EQQ x y
-      FloatLtOp -> cmpF_code (FCMP TF LTT) NE x y
-      FloatLeOp -> cmpF_code (FCMP TF LE) NE x y
-
-      DoubleGtOp -> cmpF_code (FCMP TF LE) EQQ x y
-      DoubleGeOp -> cmpF_code (FCMP TF LTT) EQQ x y
-      DoubleEqOp -> cmpF_code (FCMP TF EQQ) NE x y
-      DoubleNeOp -> cmpF_code (FCMP TF EQQ) EQQ x y
-      DoubleLtOp -> cmpF_code (FCMP TF LTT) NE x y
-      DoubleLeOp -> cmpF_code (FCMP TF LE) NE x y
-
-      IntAddOp  -> trivialCode (ADD Q False) x y
-      IntSubOp  -> trivialCode (SUB Q False) x y
-      IntMulOp  -> trivialCode (MUL Q False) x y
-      IntQuotOp -> trivialCode (DIV Q False) x y
-      IntRemOp  -> trivialCode (REM Q False) x y
-
-      WordAddOp  -> trivialCode (ADD Q False) x y
-      WordSubOp  -> trivialCode (SUB Q False) x y
-      WordMulOp  -> trivialCode (MUL Q False) x y
-      WordQuotOp -> trivialCode (DIV Q True) x y
-      WordRemOp  -> trivialCode (REM Q True) x y
-
-      FloatAddOp -> trivialFCode  W32 (FADD TF) x y
-      FloatSubOp -> trivialFCode  W32 (FSUB TF) x y
-      FloatMulOp -> trivialFCode  W32 (FMUL TF) x y
-      FloatDivOp -> trivialFCode  W32 (FDIV TF) x y
-
-      DoubleAddOp -> trivialFCode  W64 (FADD TF) x y
-      DoubleSubOp -> trivialFCode  W64 (FSUB TF) x y
-      DoubleMulOp -> trivialFCode  W64 (FMUL TF) x y
-      DoubleDivOp -> trivialFCode  W64 (FDIV TF) x y
-
-      AddrAddOp  -> trivialCode (ADD Q False) x y
-      AddrSubOp  -> trivialCode (SUB Q False) x y
-      AddrRemOp  -> trivialCode (REM Q True) x y
-
-      AndOp  -> trivialCode AND x y
-      OrOp   -> trivialCode OR  x y
-      XorOp  -> trivialCode XOR x y
-      SllOp  -> trivialCode SLL x y
-      SrlOp  -> trivialCode SRL x y
-
-      ISllOp -> trivialCode SLL x y -- was: panic "AlphaGen:isll"
-      ISraOp -> trivialCode SRA x y -- was: panic "AlphaGen:isra"
-      ISrlOp -> trivialCode SRL x y -- was: panic "AlphaGen:isrl"
-
-      FloatPowerOp  -> getRegister (StCall (fsLit "pow") CCallConv FF64 [x,y])
-      DoublePowerOp -> getRegister (StCall (fsLit "pow") CCallConv FF64 [x,y])
-  where
-    {- ------------------------------------------------------------
-       Some bizarre special code for getting condition codes into
-       registers.  Integer non-equality is a test for equality
-       followed by an XOR with 1.  (Integer comparisons always set
-       the result register to 0 or 1.)  Floating point comparisons of
-       any kind leave the result in a floating point register, so we
-       need to wrangle an integer register out of things.
-    -}
-    int_NE_code :: StixTree -> StixTree -> NatM Register
-
-    int_NE_code x y
-      = trivialCode (CMP EQQ) x y      `thenNat` \ register ->
-       getNewRegNat IntRep             `thenNat` \ tmp ->
-       let
-           code = registerCode register tmp
-           src  = registerName register tmp
-           code__2 dst = code . mkSeqInstr (XOR src (RIImm (ImmInt 1)) dst)
-       in
-       return (Any IntRep code__2)
-
-    {- ------------------------------------------------------------
-       Comments for int_NE_code also apply to cmpF_code
-    -}
-    cmpF_code
-       :: (Reg -> Reg -> Reg -> Instr)
-       -> Cond
-       -> StixTree -> StixTree
-       -> NatM Register
-
-    cmpF_code instr cond x y
-      = trivialFCode pr instr x y      `thenNat` \ register ->
-       getNewRegNat FF64               `thenNat` \ tmp ->
-       getBlockIdNat                   `thenNat` \ lbl ->
-       let
-           code = registerCode register tmp
-           result  = registerName register tmp
-
-           code__2 dst = code . mkSeqInstrs [
-               OR zeroh (RIImm (ImmInt 1)) dst,
-               BF cond  result (ImmCLbl lbl),
-               OR zeroh (RIReg zeroh) dst,
-               NEWBLOCK lbl]
-       in
-       return (Any IntRep code__2)
-      where
-       pr = panic "trivialU?FCode: does not use PrimRep on Alpha"
-      ------------------------------------------------------------
-
-getRegister (CmmLoad pk mem)
-  = getAmode mem                   `thenNat` \ amode ->
-    let
-       code = amodeCode amode
-       src   = amodeAddr amode
-       size = primRepToSize pk
-       code__2 dst = code . mkSeqInstr (LD size dst src)
-    in
-    return (Any pk code__2)
-
-getRegister (StInt i)
-  | fits8Bits i
-  = let
-       code dst = mkSeqInstr (OR zeroh (RIImm src) dst)
-    in
-    return (Any IntRep code)
-  | otherwise
-  = let
-       code dst = mkSeqInstr (LDI Q dst src)
-    in
-    return (Any IntRep code)
-  where
-    src = ImmInt (fromInteger i)
-
-getRegister leaf
-  | isJust imm
-  = let
-       code dst = mkSeqInstr (LDA dst (AddrImm imm__2))
-    in
-    return (Any PtrRep code)
-  where
-    imm = maybeImm leaf
-    imm__2 = case imm of Just x -> x
-
-
-getAmode :: CmmExpr -> NatM Amode
-getAmode tree@(CmmRegOff _ _) = getAmode (mangleIndexTree tree)
-
--- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
-#if alpha_TARGET_ARCH
-
-getAmode (StPrim IntSubOp [x, StInt i])
-  = getNewRegNat PtrRep                `thenNat` \ tmp ->
-    getRegister x              `thenNat` \ register ->
-    let
-       code = registerCode register tmp
-       reg  = registerName register tmp
-       off  = ImmInt (-(fromInteger i))
-    in
-    return (Amode (AddrRegImm reg off) code)
-
-getAmode (StPrim IntAddOp [x, StInt i])
-  = getNewRegNat PtrRep                `thenNat` \ tmp ->
-    getRegister x              `thenNat` \ register ->
-    let
-       code = registerCode register tmp
-       reg  = registerName register tmp
-       off  = ImmInt (fromInteger i)
-    in
-    return (Amode (AddrRegImm reg off) code)
-
-getAmode leaf
-  | isJust imm
-  = return (Amode (AddrImm imm__2) id)
-  where
-    imm = maybeImm leaf
-    imm__2 = case imm of Just x -> x
-
-getAmode other
-  = getNewRegNat PtrRep                `thenNat` \ tmp ->
-    getRegister other          `thenNat` \ register ->
-    let
-       code = registerCode register tmp
-       reg  = registerName register tmp
-    in
-    return (Amode (AddrReg reg) code)
-
-#endif /* alpha_TARGET_ARCH */
-
-
--- -----------------------------------------------------------------------------
--- Generating assignments
-
--- Assignments are really at the heart of the whole code generation
--- business.  Almost all top-level nodes of any real importance are
--- assignments, which correspond to loads, stores, or register
--- transfers.  If we're really lucky, some of the register transfers
--- will go away, because we can use the destination register to
--- complete the code generation for the right hand side.  This only
--- fails when the right hand side is forced into a fixed register
--- (e.g. the result of a call).
-
-assignMem_IntCode :: Size -> CmmExpr -> CmmExpr -> NatM InstrBlock
-assignReg_IntCode :: Size -> CmmReg  -> CmmExpr -> NatM InstrBlock
-
-assignMem_FltCode :: Size -> CmmExpr -> CmmExpr -> NatM InstrBlock
-assignReg_FltCode :: Size -> CmmReg  -> CmmExpr -> NatM InstrBlock
-
-
-assignIntCode pk (CmmLoad dst _) src
-  = getNewRegNat IntRep            `thenNat` \ tmp ->
-    getAmode dst                   `thenNat` \ amode ->
-    getRegister src                `thenNat` \ register ->
-    let
-       code1   = amodeCode amode []
-       dst__2  = amodeAddr amode
-       code2   = registerCode register tmp []
-       src__2  = registerName register tmp
-       sz      = primRepToSize pk
-       code__2 = asmSeqThen [code1, code2] . mkSeqInstr (ST sz src__2 dst__2)
-    in
-    return code__2
-
-assignIntCode pk dst src
-  = getRegister dst                        `thenNat` \ register1 ->
-    getRegister src                        `thenNat` \ register2 ->
-    let
-       dst__2  = registerName register1 zeroh
-       code    = registerCode register2 dst__2
-       src__2  = registerName register2 dst__2
-       code__2 = if isFixed register2
-                 then code . mkSeqInstr (OR src__2 (RIReg src__2) dst__2)
-                 else code
-    in
-    return code__2
-
-assignFltCode pk (CmmLoad dst _) src
-  = getNewRegNat pk                `thenNat` \ tmp ->
-    getAmode dst                   `thenNat` \ amode ->
-    getRegister src                        `thenNat` \ register ->
-    let
-       code1   = amodeCode amode []
-       dst__2  = amodeAddr amode
-       code2   = registerCode register tmp []
-       src__2  = registerName register tmp
-       sz      = primRepToSize pk
-       code__2 = asmSeqThen [code1, code2] . mkSeqInstr (ST sz src__2 dst__2)
-    in
-    return code__2
-
-assignFltCode pk dst src
-  = getRegister dst                        `thenNat` \ register1 ->
-    getRegister src                        `thenNat` \ register2 ->
-    let
-       dst__2  = registerName register1 zeroh
-       code    = registerCode register2 dst__2
-       src__2  = registerName register2 dst__2
-       code__2 = if isFixed register2
-                 then code . mkSeqInstr (FMOV src__2 dst__2)
-                 else code
-    in
-    return code__2
-
-
--- -----------------------------------------------------------------------------
--- Generating an non-local jump
-
--- (If applicable) Do not fill the delay slots here; you will confuse the
--- register allocator.
-
-genJump :: CmmExpr{-the branch target-} -> NatM InstrBlock
-
--- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
-
-genJump (CmmLabel lbl)
-  | isAsmTemp lbl = returnInstr (BR target)
-  | otherwise     = returnInstrs [LDA pv (AddrImm target), JMP zeroh (AddrReg pv) 0]
-  where
-    target = ImmCLbl lbl
-
-genJump tree
-  = getRegister tree               `thenNat` \ register ->
-    getNewRegNat PtrRep            `thenNat` \ tmp ->
-    let
-       dst    = registerName register pv
-       code   = registerCode register pv
-       target = registerName register pv
-    in
-    if isFixed register then
-       returnSeq code [OR dst (RIReg dst) pv, JMP zeroh (AddrReg pv) 0]
-    else
-    return (code . mkSeqInstr (JMP zeroh (AddrReg pv) 0))
-
-
--- -----------------------------------------------------------------------------
---  Unconditional branches
-
-genBranch :: BlockId -> NatM InstrBlock
-
-genBranch = return . toOL . mkBranchInstr
-
-
--- -----------------------------------------------------------------------------
---  Conditional jumps
-
-{-
-Conditional jumps are always to local labels, so we can use branch
-instructions.  We peek at the arguments to decide what kind of
-comparison to do.
-
-ALPHA: For comparisons with 0, we're laughing, because we can just do
-the desired conditional branch.
-
--}
-
-
-genCondJump
-    :: BlockId     -- the branch target
-    -> CmmExpr      -- the condition on which to branch
-    -> NatM InstrBlock
-
--- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
-genCondJump id (StPrim op [x, StInt 0])
-  = getRegister x                          `thenNat` \ register ->
-    getNewRegNat (registerRep register)
-                                   `thenNat` \ tmp ->
-    let
-       code   = registerCode register tmp
-       value  = registerName register tmp
-       pk     = registerRep register
-       target = ImmCLbl lbl
-    in
-    returnSeq code [BI (cmpOp op) value target]
-  where
-    cmpOp CharGtOp = GTT
-    cmpOp CharGeOp = GE
-    cmpOp CharEqOp = EQQ
-    cmpOp CharNeOp = NE
-    cmpOp CharLtOp = LTT
-    cmpOp CharLeOp = LE
-    cmpOp IntGtOp = GTT
-    cmpOp IntGeOp = GE
-    cmpOp IntEqOp = EQQ
-    cmpOp IntNeOp = NE
-    cmpOp IntLtOp = LTT
-    cmpOp IntLeOp = LE
-    cmpOp WordGtOp = NE
-    cmpOp WordGeOp = ALWAYS
-    cmpOp WordEqOp = EQQ
-    cmpOp WordNeOp = NE
-    cmpOp WordLtOp = NEVER
-    cmpOp WordLeOp = EQQ
-    cmpOp AddrGtOp = NE
-    cmpOp AddrGeOp = ALWAYS
-    cmpOp AddrEqOp = EQQ
-    cmpOp AddrNeOp = NE
-    cmpOp AddrLtOp = NEVER
-    cmpOp AddrLeOp = EQQ
-
-genCondJump lbl (StPrim op [x, StDouble 0.0])
-  = getRegister x                          `thenNat` \ register ->
-    getNewRegNat (registerRep register)
-                                   `thenNat` \ tmp ->
-    let
-       code   = registerCode register tmp
-       value  = registerName register tmp
-       pk     = registerRep register
-       target = ImmCLbl lbl
-    in
-    return (code . mkSeqInstr (BF (cmpOp op) value target))
-  where
-    cmpOp FloatGtOp = GTT
-    cmpOp FloatGeOp = GE
-    cmpOp FloatEqOp = EQQ
-    cmpOp FloatNeOp = NE
-    cmpOp FloatLtOp = LTT
-    cmpOp FloatLeOp = LE
-    cmpOp DoubleGtOp = GTT
-    cmpOp DoubleGeOp = GE
-    cmpOp DoubleEqOp = EQQ
-    cmpOp DoubleNeOp = NE
-    cmpOp DoubleLtOp = LTT
-    cmpOp DoubleLeOp = LE
-
-genCondJump lbl (StPrim op [x, y])
-  | fltCmpOp op
-  = trivialFCode pr instr x y      `thenNat` \ register ->
-    getNewRegNat FF64              `thenNat` \ tmp ->
-    let
-       code   = registerCode register tmp
-       result = registerName register tmp
-       target = ImmCLbl lbl
-    in
-    return (code . mkSeqInstr (BF cond result target))
-  where
-    pr = panic "trivialU?FCode: does not use PrimRep on Alpha"
-
-    fltCmpOp op = case op of
-       FloatGtOp -> True
-       FloatGeOp -> True
-       FloatEqOp -> True
-       FloatNeOp -> True
-       FloatLtOp -> True
-       FloatLeOp -> True
-       DoubleGtOp -> True
-       DoubleGeOp -> True
-       DoubleEqOp -> True
-       DoubleNeOp -> True
-       DoubleLtOp -> True
-       DoubleLeOp -> True
-       _ -> False
-    (instr, cond) = case op of
-       FloatGtOp -> (FCMP TF LE, EQQ)
-       FloatGeOp -> (FCMP TF LTT, EQQ)
-       FloatEqOp -> (FCMP TF EQQ, NE)
-       FloatNeOp -> (FCMP TF EQQ, EQQ)
-       FloatLtOp -> (FCMP TF LTT, NE)
-       FloatLeOp -> (FCMP TF LE, NE)
-       DoubleGtOp -> (FCMP TF LE, EQQ)
-       DoubleGeOp -> (FCMP TF LTT, EQQ)
-       DoubleEqOp -> (FCMP TF EQQ, NE)
-       DoubleNeOp -> (FCMP TF EQQ, EQQ)
-       DoubleLtOp -> (FCMP TF LTT, NE)
-       DoubleLeOp -> (FCMP TF LE, NE)
-
-genCondJump lbl (StPrim op [x, y])
-  = trivialCode instr x y          `thenNat` \ register ->
-    getNewRegNat IntRep            `thenNat` \ tmp ->
-    let
-       code   = registerCode register tmp
-       result = registerName register tmp
-       target = ImmCLbl lbl
-    in
-    return (code . mkSeqInstr (BI cond result target))
-  where
-    (instr, cond) = case op of
-       CharGtOp -> (CMP LE, EQQ)
-       CharGeOp -> (CMP LTT, EQQ)
-       CharEqOp -> (CMP EQQ, NE)
-       CharNeOp -> (CMP EQQ, EQQ)
-       CharLtOp -> (CMP LTT, NE)
-       CharLeOp -> (CMP LE, NE)
-       IntGtOp -> (CMP LE, EQQ)
-       IntGeOp -> (CMP LTT, EQQ)
-       IntEqOp -> (CMP EQQ, NE)
-       IntNeOp -> (CMP EQQ, EQQ)
-       IntLtOp -> (CMP LTT, NE)
-       IntLeOp -> (CMP LE, NE)
-       WordGtOp -> (CMP ULE, EQQ)
-       WordGeOp -> (CMP ULT, EQQ)
-       WordEqOp -> (CMP EQQ, NE)
-       WordNeOp -> (CMP EQQ, EQQ)
-       WordLtOp -> (CMP ULT, NE)
-       WordLeOp -> (CMP ULE, NE)
-       AddrGtOp -> (CMP ULE, EQQ)
-       AddrGeOp -> (CMP ULT, EQQ)
-       AddrEqOp -> (CMP EQQ, NE)
-       AddrNeOp -> (CMP EQQ, EQQ)
-       AddrLtOp -> (CMP ULT, NE)
-       AddrLeOp -> (CMP ULE, NE)
-
--- -----------------------------------------------------------------------------
---  Generating C calls
-
--- Now the biggest nightmare---calls.  Most of the nastiness is buried in
--- @get_arg@, which moves the arguments to the correct registers/stack
--- locations.  Apart from that, the code is easy.
--- 
--- (If applicable) Do not fill the delay slots here; you will confuse the
--- register allocator.
-
-genCCall
-    :: CmmCallTarget           -- function to call
-    -> HintedCmmFormals                -- where to put the result
-    -> HintedCmmActuals                -- arguments (of mixed type)
-    -> NatM InstrBlock
-
--- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
-
-ccallResultRegs = 
-
-genCCall fn cconv result_regs args
-  = mapAccumLNat get_arg (allArgRegs, eXTRA_STK_ARGS_HERE) args
-                         `thenNat` \ ((unused,_), argCode) ->
-    let
-       nRegs = length allArgRegs - length unused
-       code = asmSeqThen (map ($ []) argCode)
-    in
-       returnSeq code [
-           LDA pv (AddrImm (ImmLab (ptext fn))),
-           JSR ra (AddrReg pv) nRegs,
-           LDGP gp (AddrReg ra)]
-  where
-    ------------------------
-    {- Try to get a value into a specific register (or registers) for
-       a call.  The first 6 arguments go into the appropriate
-       argument register (separate registers for integer and floating
-       point arguments, but used in lock-step), and the remaining
-       arguments are dumped to the stack, beginning at 0(sp).  Our
-       first argument is a pair of the list of remaining argument
-       registers to be assigned for this call and the next stack
-       offset to use for overflowing arguments.  This way,
-       @get_Arg@ can be applied to all of a call's arguments using
-       @mapAccumLNat@.
-    -}
-    get_arg
-       :: ([(Reg,Reg)], Int)   -- Argument registers and stack offset (accumulator)
-       -> StixTree             -- Current argument
-       -> NatM (([(Reg,Reg)],Int), InstrBlock) -- Updated accumulator and code
-
-    -- We have to use up all of our argument registers first...
-
-    get_arg ((iDst,fDst):dsts, offset) arg
-      = getRegister arg                            `thenNat` \ register ->
-       let
-           reg  = if isFloatType pk then fDst else iDst
-           code = registerCode register reg
-           src  = registerName register reg
-           pk   = registerRep register
-       in
-       return (
-           if isFloatType pk then
-               ((dsts, offset), if isFixed register then
-                   code . mkSeqInstr (FMOV src fDst)
-                   else code)
-           else
-               ((dsts, offset), if isFixed register then
-                   code . mkSeqInstr (OR src (RIReg src) iDst)
-                   else code))
-
-    -- Once we have run out of argument registers, we move to the
-    -- stack...
-
-    get_arg ([], offset) arg
-      = getRegister arg                        `thenNat` \ register ->
-       getNewRegNat (registerRep register)
-                                       `thenNat` \ tmp ->
-       let
-           code = registerCode register tmp
-           src  = registerName register tmp
-           pk   = registerRep register
-           sz   = primRepToSize pk
-       in
-       return (([], offset + 1), code . mkSeqInstr (ST sz src (spRel offset)))
-
-trivialCode instr x (StInt y)
-  | fits8Bits y
-  = getRegister x              `thenNat` \ register ->
-    getNewRegNat IntRep                `thenNat` \ tmp ->
-    let
-       code = registerCode register tmp
-       src1 = registerName register tmp
-       src2 = ImmInt (fromInteger y)
-       code__2 dst = code . mkSeqInstr (instr src1 (RIImm src2) dst)
-    in
-    return (Any IntRep code__2)
-
-trivialCode instr x y
-  = getRegister x              `thenNat` \ register1 ->
-    getRegister y              `thenNat` \ register2 ->
-    getNewRegNat IntRep                `thenNat` \ tmp1 ->
-    getNewRegNat IntRep                `thenNat` \ tmp2 ->
-    let
-       code1 = registerCode register1 tmp1 []
-       src1  = registerName register1 tmp1
-       code2 = registerCode register2 tmp2 []
-       src2  = registerName register2 tmp2
-       code__2 dst = asmSeqThen [code1, code2] .
-                    mkSeqInstr (instr src1 (RIReg src2) dst)
-    in
-    return (Any IntRep code__2)
-
-------------
-trivialUCode instr x
-  = getRegister x              `thenNat` \ register ->
-    getNewRegNat IntRep                `thenNat` \ tmp ->
-    let
-       code = registerCode register tmp
-       src  = registerName register tmp
-       code__2 dst = code . mkSeqInstr (instr (RIReg src) dst)
-    in
-    return (Any IntRep code__2)
-
-------------
-trivialFCode _ instr x y
-  = getRegister x              `thenNat` \ register1 ->
-    getRegister y              `thenNat` \ register2 ->
-    getNewRegNat FF64  `thenNat` \ tmp1 ->
-    getNewRegNat FF64  `thenNat` \ tmp2 ->
-    let
-       code1 = registerCode register1 tmp1
-       src1  = registerName register1 tmp1
-
-       code2 = registerCode register2 tmp2
-       src2  = registerName register2 tmp2
-
-       code__2 dst = asmSeqThen [code1 [], code2 []] .
-                     mkSeqInstr (instr src1 src2 dst)
-    in
-    return (Any FF64 code__2)
-
-trivialUFCode _ instr x
-  = getRegister x              `thenNat` \ register ->
-    getNewRegNat FF64  `thenNat` \ tmp ->
-    let
-       code = registerCode register tmp
-       src  = registerName register tmp
-       code__2 dst = code . mkSeqInstr (instr src dst)
-    in
-    return (Any FF64 code__2)
-
-#if alpha_TARGET_ARCH
-
-coerceInt2FP _ x
-  = getRegister x              `thenNat` \ register ->
-    getNewRegNat IntRep                `thenNat` \ reg ->
-    let
-       code = registerCode register reg
-       src  = registerName register reg
-
-       code__2 dst = code . mkSeqInstrs [
-           ST Q src (spRel 0),
-           LD TF dst (spRel 0),
-           CVTxy Q TF dst dst]
-    in
-    return (Any FF64 code__2)
-
--------------
-coerceFP2Int x
-  = getRegister x              `thenNat` \ register ->
-    getNewRegNat FF64  `thenNat` \ tmp ->
-    let
-       code = registerCode register tmp
-       src  = registerName register tmp
-
-       code__2 dst = code . mkSeqInstrs [
-           CVTxy TF Q src tmp,
-           ST TF tmp (spRel 0),
-           LD Q dst (spRel 0)]
-    in
-    return (Any IntRep code__2)
-
-#endif /* alpha_TARGET_ARCH */
-
-
--}
-
-
-
-
-
diff --git a/compiler/nativeGen/Alpha/Instr.hs b/compiler/nativeGen/Alpha/Instr.hs
deleted file mode 100644 (file)
index 990ea8b..0000000
+++ /dev/null
@@ -1,142 +0,0 @@
------------------------------------------------------------------------------
---
--- Machine-dependent assembly language
---
--- (c) The University of Glasgow 1993-2004
---
------------------------------------------------------------------------------
-
-#include "HsVersions.h"
-#include "nativeGen/NCG.h"
-
-module Alpha.Instr (
---     Cond(..),
---     Instr(..),
---     RI(..)
-)
-
-where
-
-{-
-import BlockId
-import Regs
-import Cmm
-import FastString
-import CLabel
-
-data Cond
-       = ALWAYS        -- For BI (same as BR)
-       | EQQ           -- For CMP and BI (NB: "EQ" is a 1.3 Prelude name)
-       | GE            -- For BI only
-       | GTT           -- For BI only (NB: "GT" is a 1.3 Prelude name)
-       | LE            -- For CMP and BI
-       | LTT           -- For CMP and BI (NB: "LT" is a 1.3 Prelude name)
-       | NE            -- For BI only
-       | NEVER         -- For BI (null instruction)
-       | ULE           -- For CMP only
-       | ULT           -- For CMP only
-       deriving Eq
-       
-
--- -----------------------------------------------------------------------------
--- Machine's assembly language
-
--- We have a few common "instructions" (nearly all the pseudo-ops) but
--- mostly all of 'Instr' is machine-specific.
-
--- Register or immediate
-data RI 
-       = RIReg Reg
-       | RIImm Imm
-
-data Instr
-       -- comment pseudo-op
-       = COMMENT FastString            
-
-       -- some static data spat out during code
-       -- generation.  Will be extracted before
-       -- pretty-printing.
-       | LDATA   Section [CmmStatic]   
-
-       -- start a new basic block.  Useful during
-       -- codegen, removed later.  Preceding 
-       -- instruction should be a jump, as per the
-       -- invariants for a BasicBlock (see Cmm).
-       | NEWBLOCK BlockId              
-
-       -- specify current stack offset for
-        -- benefit of subsequent passes
-       | DELTA   Int
-
-       -- | spill this reg to a stack slot
-       | SPILL   Reg Int
-
-       -- | reload this reg from a stack slot
-       | RELOAD  Int Reg
-
-       -- Loads and stores.
-       | LD          Size Reg AddrMode         -- size, dst, src
-       | LDA         Reg AddrMode              -- dst, src
-       | LDAH        Reg AddrMode              -- dst, src
-       | LDGP        Reg AddrMode              -- dst, src
-       | LDI         Size Reg Imm              -- size, dst, src
-       | ST          Size Reg AddrMode         -- size, src, dst
-
-       -- Int Arithmetic.
-       | CLR         Reg                       -- dst
-       | ABS         Size RI Reg               -- size, src, dst
-       | NEG         Size Bool RI Reg          -- size, overflow, src, dst
-       | ADD         Size Bool Reg RI Reg      -- size, overflow, src, src, dst
-       | SADD        Size Size Reg RI Reg      -- size, scale, src, src, dst
-       | SUB         Size Bool Reg RI Reg      -- size, overflow, src, src, dst
-       | SSUB        Size Size Reg RI Reg      -- size, scale, src, src, dst
-       | MUL         Size Bool Reg RI Reg      -- size, overflow, src, src, dst
-       | DIV         Size Bool Reg RI Reg      -- size, unsigned, src, src, dst
-       | REM         Size Bool Reg RI Reg      -- size, unsigned, src, src, dst
-
-       -- Simple bit-twiddling.
-       | NOT         RI Reg
-       | AND         Reg RI Reg
-       | ANDNOT      Reg RI Reg
-       | OR          Reg RI Reg
-       | ORNOT       Reg RI Reg
-       | XOR         Reg RI Reg
-       | XORNOT      Reg RI Reg
-       | SLL         Reg RI Reg
-       | SRL         Reg RI Reg
-       | SRA         Reg RI Reg
-
-       | ZAP         Reg RI Reg
-       | ZAPNOT      Reg RI Reg
-
-       | NOP
-
-       -- Comparison
-       | CMP         Cond Reg RI Reg
-
-       -- Float Arithmetic.
-       | FCLR        Reg
-       | FABS        Reg Reg
-       | FNEG        Size Reg Reg
-       | FADD        Size Reg Reg Reg
-       | FDIV        Size Reg Reg Reg
-       | FMUL        Size Reg Reg Reg
-       | FSUB        Size Reg Reg Reg
-       | CVTxy       Size Size Reg Reg
-       | FCMP        Size Cond Reg Reg Reg
-       | FMOV        Reg Reg
-
-       -- Jumping around.
-       | BI          Cond Reg Imm
-       | BF          Cond Reg Imm
-       | BR          Imm
-       | JMP         Reg AddrMode Int
-       | BSR         Imm Int
-       | JSR         Reg AddrMode Int
-
-       -- Alpha-specific pseudo-ops.
-       | FUNBEGIN CLabel
-       | FUNEND CLabel
-
-
--}
diff --git a/compiler/nativeGen/Alpha/Ppr.hs-old b/compiler/nativeGen/Alpha/Ppr.hs-old
deleted file mode 100644 (file)
index c14eef2..0000000
+++ /dev/null
@@ -1,562 +0,0 @@
-
-module Alpha.Ppr (
-{-
-       pprReg,
-       pprSize,
-       pprCond,
-       pprAddr,
-       pprSectionHeader,
-       pprTypeAndSizeDecl,
-       pprRI,
-       pprRegRIReg,
-       pprSizeRegRegReg
--}
-)
-
-where
-
-{-
-#include "nativeGen/NCG.h"
-#include "HsVersions.h"
-
-import BlockId
-import Cmm
-import Regs            -- may differ per-platform
-import Instrs
-
-import CLabel          ( CLabel, pprCLabel, externallyVisibleCLabel,
-                         labelDynamic, mkAsmTempLabel, entryLblToInfoLbl )
-
-#if HAVE_SUBSECTIONS_VIA_SYMBOLS
-import CLabel       ( mkDeadStripPreventer )
-#endif
-
-import Panic           ( panic )
-import Unique          ( pprUnique )
-import Pretty
-import FastString
-import qualified Outputable
-import Outputable      ( Outputable, pprPanic, ppr, docToSDoc)
-
-import Data.Array.ST
-import Data.Word       ( Word8 )
-import Control.Monad.ST
-import Data.Char       ( chr, ord )
-import Data.Maybe       ( isJust )
-
-
-
-pprReg :: Reg -> Doc
-pprReg r
-  = case r of
-      RealReg i      -> ppr_reg_no i
-      VirtualRegI  u  -> text "%vI_"  <> asmSDoc (pprUnique u)
-      VirtualRegHi u  -> text "%vHi_" <> asmSDoc (pprUnique u)
-      VirtualRegF  u  -> text "%vF_"  <> asmSDoc (pprUnique u)
-      VirtualRegD  u  -> text "%vD_"  <> asmSDoc (pprUnique u)
-  where
-    ppr_reg_no :: Int -> Doc
-    ppr_reg_no i = ptext
-      (case i of {
-        0 -> sLit "$0";    1 -> sLit "$1";
-        2 -> sLit "$2";    3 -> sLit "$3";
-        4 -> sLit "$4";    5 -> sLit "$5";
-        6 -> sLit "$6";    7 -> sLit "$7";
-        8 -> sLit "$8";    9 -> sLit "$9";
-       10 -> sLit "$10";  11 -> sLit "$11";
-       12 -> sLit "$12";  13 -> sLit "$13";
-       14 -> sLit "$14";  15 -> sLit "$15";
-       16 -> sLit "$16";  17 -> sLit "$17";
-       18 -> sLit "$18";  19 -> sLit "$19";
-       20 -> sLit "$20";  21 -> sLit "$21";
-       22 -> sLit "$22";  23 -> sLit "$23";
-       24 -> sLit "$24";  25 -> sLit "$25";
-       26 -> sLit "$26";  27 -> sLit "$27";
-       28 -> sLit "$28";  29 -> sLit "$29";
-       30 -> sLit "$30";  31 -> sLit "$31";
-       32 -> sLit "$f0";  33 -> sLit "$f1";
-       34 -> sLit "$f2";  35 -> sLit "$f3";
-       36 -> sLit "$f4";  37 -> sLit "$f5";
-       38 -> sLit "$f6";  39 -> sLit "$f7";
-       40 -> sLit "$f8";  41 -> sLit "$f9";
-       42 -> sLit "$f10"; 43 -> sLit "$f11";
-       44 -> sLit "$f12"; 45 -> sLit "$f13";
-       46 -> sLit "$f14"; 47 -> sLit "$f15";
-       48 -> sLit "$f16"; 49 -> sLit "$f17";
-       50 -> sLit "$f18"; 51 -> sLit "$f19";
-       52 -> sLit "$f20"; 53 -> sLit "$f21";
-       54 -> sLit "$f22"; 55 -> sLit "$f23";
-       56 -> sLit "$f24"; 57 -> sLit "$f25";
-       58 -> sLit "$f26"; 59 -> sLit "$f27";
-       60 -> sLit "$f28"; 61 -> sLit "$f29";
-       62 -> sLit "$f30"; 63 -> sLit "$f31";
-       _  -> sLit "very naughty alpha register"
-      })
-
-
-pprSize :: Size -> Doc
-pprSize x = ptext (case x of
-        B  -> sLit "b"
-        Bu -> sLit "bu"
---      W  -> sLit "w" UNUSED
---      Wu -> sLit "wu" UNUSED
-        L  -> sLit "l"
-        Q  -> sLit "q"
---      FF -> sLit "f" UNUSED
---      DF -> sLit "d" UNUSED
---      GF -> sLit "g" UNUSED
---      SF -> sLit "s" UNUSED
-        TF -> sLit "t"
-
-
-pprCond :: Cond -> Doc
-pprCond c 
- = ptext (case c of
-               EQQ  -> sLit "eq"
-               LTT  -> sLit "lt"
-               LE  -> sLit "le"
-               ULT -> sLit "ult"
-               ULE -> sLit "ule"
-               NE  -> sLit "ne"
-               GTT  -> sLit "gt"
-               GE  -> sLit "ge")
-
-
-pprAddr :: AddrMode -> Doc
-pprAddr (AddrReg r) = parens (pprReg r)
-pprAddr (AddrImm i) = pprImm i
-pprAddr (AddrRegImm r1 i)
-  = (<>) (pprImm i) (parens (pprReg r1))
-
-
-pprSectionHeader Text
-    = ptext    (sLit "\t.text\n\t.align 3")
-
-pprSectionHeader Data
-    = ptext    (sLit "\t.data\n\t.align 3")
-
-pprSectionHeader ReadOnlyData
-    = ptext    (sLit "\t.data\n\t.align 3")
-
-pprSectionHeader RelocatableReadOnlyData
-    = ptext    (sLit "\t.data\n\t.align 3")
-
-pprSectionHeader UninitialisedData
-    = ptext    (sLit "\t.bss\n\t.align 3")
-
-pprSectionHeader ReadOnlyData16
-    = ptext    (sLit "\t.data\n\t.align 4")
-
-pprSectionHeader (OtherSection sec)
-    = panic "PprMach.pprSectionHeader: unknown section"
-
-
-pprTypeAndSizeDecl :: CLabel -> Doc
-pprTypeAndSizeDecl lbl
-  = empty
-
-
-
-pprInstr :: Instr -> Doc
-
-pprInstr (DELTA d)
-   = pprInstr (COMMENT (mkFastString ("\tdelta = " ++ show d)))
-
-pprInstr (NEWBLOCK _)
-   = panic "PprMach.pprInstr: NEWBLOCK"
-
-pprInstr (LDATA _ _)
-   = panic "PprMach.pprInstr: LDATA"
-
-pprInstr (SPILL reg slot)
-   = hcat [
-       ptext (sLit "\tSPILL"),
-       char '\t',
-       pprReg reg,
-       comma,
-       ptext (sLit "SLOT") <> parens (int slot)]
-
-pprInstr (RELOAD slot reg)
-   = hcat [
-       ptext (sLit "\tRELOAD"),
-       char '\t',
-       ptext (sLit "SLOT") <> parens (int slot),
-       comma,
-       pprReg reg]
-
-pprInstr (LD size reg addr)
-  = hcat [
-       ptext (sLit "\tld"),
-       pprSize size,
-       char '\t',
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (LDA reg addr)
-  = hcat [
-       ptext (sLit "\tlda\t"),
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (LDAH reg addr)
-  = hcat [
-       ptext (sLit "\tldah\t"),
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (LDGP reg addr)
-  = hcat [
-       ptext (sLit "\tldgp\t"),
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (LDI size reg imm)
-  = hcat [
-       ptext (sLit "\tldi"),
-       pprSize size,
-       char '\t',
-       pprReg reg,
-       comma,
-       pprImm imm
-    ]
-
-pprInstr (ST size reg addr)
-  = hcat [
-       ptext (sLit "\tst"),
-       pprSize size,
-       char '\t',
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (CLR reg)
-  = hcat [
-       ptext (sLit "\tclr\t"),
-       pprReg reg
-    ]
-
-pprInstr (ABS size ri reg)
-  = hcat [
-       ptext (sLit "\tabs"),
-       pprSize size,
-       char '\t',
-       pprRI ri,
-       comma,
-       pprReg reg
-    ]
-
-pprInstr (NEG size ov ri reg)
-  = hcat [
-       ptext (sLit "\tneg"),
-       pprSize size,
-       if ov then ptext (sLit "v\t") else char '\t',
-       pprRI ri,
-       comma,
-       pprReg reg
-    ]
-
-pprInstr (ADD size ov reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\tadd"),
-       pprSize size,
-       if ov then ptext (sLit "v\t") else char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (SADD size scale reg1 ri reg2)
-  = hcat [
-       ptext (case scale of {{-UNUSED:L -> (sLit "\ts4");-} Q -> (sLit "\ts8")}),
-       ptext (sLit "add"),
-       pprSize size,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (SUB size ov reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\tsub"),
-       pprSize size,
-       if ov then ptext (sLit "v\t") else char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (SSUB size scale reg1 ri reg2)
-  = hcat [
-       ptext (case scale of {{-UNUSED:L -> (sLit "\ts4");-} Q -> (sLit "\ts8")}),
-       ptext (sLit "sub"),
-       pprSize size,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (MUL size ov reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\tmul"),
-       pprSize size,
-       if ov then ptext (sLit "v\t") else char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (DIV size uns reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\tdiv"),
-       pprSize size,
-       if uns then ptext (sLit "u\t") else char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (REM size uns reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\trem"),
-       pprSize size,
-       if uns then ptext (sLit "u\t") else char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (NOT ri reg)
-  = hcat [
-       ptext (sLit "\tnot"),
-       char '\t',
-       pprRI ri,
-       comma,
-       pprReg reg
-    ]
-
-pprInstr (AND reg1 ri reg2) = pprRegRIReg (sLit "and") reg1 ri reg2
-pprInstr (ANDNOT reg1 ri reg2) = pprRegRIReg (sLit "andnot") reg1 ri reg2
-pprInstr (OR reg1 ri reg2) = pprRegRIReg (sLit "or") reg1 ri reg2
-pprInstr (ORNOT reg1 ri reg2) = pprRegRIReg (sLit "ornot") reg1 ri reg2
-pprInstr (XOR reg1 ri reg2) = pprRegRIReg (sLit "xor") reg1 ri reg2
-pprInstr (XORNOT reg1 ri reg2) = pprRegRIReg (sLit "xornot") reg1 ri reg2
-
-pprInstr (SLL reg1 ri reg2) = pprRegRIReg (sLit "sll") reg1 ri reg2
-pprInstr (SRL reg1 ri reg2) = pprRegRIReg (sLit "srl") reg1 ri reg2
-pprInstr (SRA reg1 ri reg2) = pprRegRIReg (sLit "sra") reg1 ri reg2
-
-pprInstr (ZAP reg1 ri reg2) = pprRegRIReg (sLit "zap") reg1 ri reg2
-pprInstr (ZAPNOT reg1 ri reg2) = pprRegRIReg (sLit "zapnot") reg1 ri reg2
-
-pprInstr (NOP) = ptext (sLit "\tnop")
-
-pprInstr (CMP cond reg1 ri reg2)
-  = hcat [
-       ptext (sLit "\tcmp"),
-       pprCond cond,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (FCLR reg)
-  = hcat [
-       ptext (sLit "\tfclr\t"),
-       pprReg reg
-    ]
-
-pprInstr (FABS reg1 reg2)
-  = hcat [
-       ptext (sLit "\tfabs\t"),
-       pprReg reg1,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (FNEG size reg1 reg2)
-  = hcat [
-       ptext (sLit "\tneg"),
-       pprSize size,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (FADD size reg1 reg2 reg3) = pprSizeRegRegReg (sLit "add") size reg1 reg2 reg3
-pprInstr (FDIV size reg1 reg2 reg3) = pprSizeRegRegReg (sLit "div") size reg1 reg2 reg3
-pprInstr (FMUL size reg1 reg2 reg3) = pprSizeRegRegReg (sLit "mul") size reg1 reg2 reg3
-pprInstr (FSUB size reg1 reg2 reg3) = pprSizeRegRegReg (sLit "sub") size reg1 reg2 reg3
-
-pprInstr (CVTxy size1 size2 reg1 reg2)
-  = hcat [
-       ptext (sLit "\tcvt"),
-       pprSize size1,
-       case size2 of {Q -> ptext (sLit "qc"); _ -> pprSize size2},
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (FCMP size cond reg1 reg2 reg3)
-  = hcat [
-       ptext (sLit "\tcmp"),
-       pprSize size,
-       pprCond cond,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprReg reg2,
-       comma,
-       pprReg reg3
-    ]
-
-pprInstr (FMOV reg1 reg2)
-  = hcat [
-       ptext (sLit "\tfmov\t"),
-       pprReg reg1,
-       comma,
-       pprReg reg2
-    ]
-
-pprInstr (BI ALWAYS reg lab) = pprInstr (BR lab)
-
-pprInstr (BI NEVER reg lab) = empty
-
-pprInstr (BI cond reg lab)
-  = hcat [
-       ptext (sLit "\tb"),
-       pprCond cond,
-       char '\t',
-       pprReg reg,
-       comma,
-       pprImm lab
-    ]
-
-pprInstr (BF cond reg lab)
-  = hcat [
-       ptext (sLit "\tfb"),
-       pprCond cond,
-       char '\t',
-       pprReg reg,
-       comma,
-       pprImm lab
-    ]
-
-pprInstr (BR lab)
-  = (<>) (ptext (sLit "\tbr\t")) (pprImm lab)
-
-pprInstr (JMP reg addr hint)
-  = hcat [
-       ptext (sLit "\tjmp\t"),
-       pprReg reg,
-       comma,
-       pprAddr addr,
-       comma,
-       int hint
-    ]
-
-pprInstr (BSR imm n)
-  = (<>) (ptext (sLit "\tbsr\t")) (pprImm imm)
-
-pprInstr (JSR reg addr n)
-  = hcat [
-       ptext (sLit "\tjsr\t"),
-       pprReg reg,
-       comma,
-       pprAddr addr
-    ]
-
-pprInstr (FUNBEGIN clab)
-  = hcat [
-       if (externallyVisibleCLabel clab) then
-           hcat [ptext (sLit "\t.globl\t"), pp_lab, char '\n']
-       else
-           empty,
-       ptext (sLit "\t.ent "),
-       pp_lab,
-       char '\n',
-       pp_lab,
-       pp_ldgp,
-       pp_lab,
-       pp_frame
-    ]
-    where
-       pp_lab = pprCLabel_asm clab
-
-        -- NEVER use commas within those string literals, cpp will ruin your day
-       pp_ldgp  = hcat [ ptext (sLit ":\n\tldgp $29"), char ',', ptext (sLit "0($27)\n") ]
-       pp_frame = hcat [ ptext (sLit "..ng:\n\t.frame $30"), char ',',
-                          ptext (sLit "4240"), char ',',
-                          ptext (sLit "$26"), char ',',
-                          ptext (sLit "0\n\t.prologue 1") ]
-
-pprInstr (FUNEND clab)
-  = (<>) (ptext (sLit "\t.align 4\n\t.end ")) (pprCLabel_asm clab)
-
-
-pprRI :: RI -> Doc
-
-pprRI (RIReg r) = pprReg r
-pprRI (RIImm r) = pprImm r
-
-pprRegRIReg :: LitString -> Reg -> RI -> Reg -> Doc
-pprRegRIReg name reg1 ri reg2
-  = hcat [
-       char '\t',
-       ptext name,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprRI ri,
-       comma,
-       pprReg reg2
-    ]
-
-pprSizeRegRegReg :: LitString -> Size -> Reg -> Reg -> Reg -> Doc
-pprSizeRegRegReg name size reg1 reg2 reg3
-  = hcat [
-       char '\t',
-       ptext name,
-       pprSize size,
-       char '\t',
-       pprReg reg1,
-       comma,
-       pprReg reg2,
-       comma,
-       pprReg reg3
-    ]
-
--}
-
-
-
diff --git a/compiler/nativeGen/Alpha/RegInfo.hs b/compiler/nativeGen/Alpha/RegInfo.hs
deleted file mode 100644 (file)
index 7fdde4d..0000000
+++ /dev/null
@@ -1,218 +0,0 @@
-
------------------------------------------------------------------------------
---
--- (c) The University of Glasgow 1996-2004
---
------------------------------------------------------------------------------
-
-module Alpha.RegInfo (
-{-
-       RegUsage(..),
-       noUsage,
-       regUsage,
-       patchRegs,
-       jumpDests,
-       isJumpish,
-       patchJump,
-       isRegRegMove,
-
-        JumpDest, canShortcut, shortcutJump, shortcutStatic,
-
-       maxSpillSlots,
-       mkSpillInstr,
-       mkLoadInstr,
-       mkRegRegMoveInstr,
-       mkBranchInstr
--}
-)
-
-where
-
-{-
-#include "nativeGen/NCG.h"
-#include "HsVersions.h"
-
-
-import BlockId
-import Cmm
-import CLabel
-import Instrs
-import Regs
-import Outputable
-import Constants       ( rESERVED_C_STACK_BYTES )
-import FastBool
-
-data RegUsage = RU [Reg] [Reg]
-
-noUsage :: RegUsage
-noUsage  = RU [] []
-
-regUsage :: Instr -> RegUsage
-
-regUsage instr = case instr of
-    SPILL  reg slot    -> usage ([reg], [])
-    RELOAD slot reg    -> usage ([], [reg])
-    LD B reg addr      -> usage (regAddr addr, [reg, t9])
-    LD Bu reg addr     -> usage (regAddr addr, [reg, t9])
---  LD W reg addr      -> usage (regAddr addr, [reg, t9]) : UNUSED
---  LD Wu reg addr     -> usage (regAddr addr, [reg, t9]) : UNUSED
-    LD sz reg addr     -> usage (regAddr addr, [reg])
-    LDA reg addr       -> usage (regAddr addr, [reg])
-    LDAH reg addr      -> usage (regAddr addr, [reg])
-    LDGP reg addr      -> usage (regAddr addr, [reg])
-    LDI sz reg imm     -> usage ([], [reg])
-    ST B reg addr      -> usage (reg : regAddr addr, [t9, t10])
---  ST W reg addr      -> usage (reg : regAddr addr, [t9, t10]) : UNUSED
-    ST sz reg addr     -> usage (reg : regAddr addr, [])
-    CLR reg            -> usage ([], [reg])
-    ABS sz ri reg      -> usage (regRI ri, [reg])
-    NEG sz ov ri reg   -> usage (regRI ri, [reg])
-    ADD sz ov r1 ar r2 -> usage (r1 : regRI ar, [r2])
-    SADD sz sc r1 ar r2 -> usage (r1 : regRI ar, [r2])
-    SUB sz ov r1 ar r2 -> usage (r1 : regRI ar, [r2])
-    SSUB sz sc r1 ar r2 -> usage (r1 : regRI ar, [r2])
-    MUL sz ov r1 ar r2 -> usage (r1 : regRI ar, [r2])
-    DIV sz un r1 ar r2 -> usage (r1 : regRI ar, [r2, t9, t10, t11, t12])
-    REM sz un r1 ar r2 -> usage (r1 : regRI ar, [r2, t9, t10, t11, t12])
-    NOT ri reg         -> usage (regRI ri, [reg])
-    AND r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    ANDNOT r1 ar r2    -> usage (r1 : regRI ar, [r2])
-    OR r1 ar r2                -> usage (r1 : regRI ar, [r2])
-    ORNOT r1 ar r2     -> usage (r1 : regRI ar, [r2])
-    XOR r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    XORNOT r1 ar r2    -> usage (r1 : regRI ar, [r2])
-    SLL r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    SRL r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    SRA r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    ZAP r1 ar r2       -> usage (r1 : regRI ar, [r2])
-    ZAPNOT r1 ar r2    -> usage (r1 : regRI ar, [r2])
-    CMP co r1 ar r2    -> usage (r1 : regRI ar, [r2])
-    FCLR reg           -> usage ([], [reg])
-    FABS r1 r2         -> usage ([r1], [r2])
-    FNEG sz r1 r2      -> usage ([r1], [r2])
-    FADD sz r1 r2 r3   -> usage ([r1, r2], [r3])
-    FDIV sz r1 r2 r3   -> usage ([r1, r2], [r3])
-    FMUL sz r1 r2 r3   -> usage ([r1, r2], [r3])
-    FSUB sz r1 r2 r3   -> usage ([r1, r2], [r3])
-    CVTxy sz1 sz2 r1 r2 -> usage ([r1], [r2])
-    FCMP sz co r1 r2 r3 -> usage ([r1, r2], [r3])
-    FMOV r1 r2         -> usage ([r1], [r2])
-
-
-    -- We assume that all local jumps will be BI/BF/BR.         JMP must be out-of-line.
-    BI cond reg lbl    -> usage ([reg], [])
-    BF cond reg lbl    -> usage ([reg], [])
-    JMP reg addr hint  -> RU (mkRegSet (filter interesting (regAddr addr))) freeRegSet
-
-    BSR _ n            -> RU (argRegSet n) callClobberedRegSet
-    JSR reg addr n     -> RU (argRegSet n) callClobberedRegSet
-
-    _                  -> noUsage
-
-  where
-    usage (src, dst) = RU (mkRegSet (filter interesting src))
-                         (mkRegSet (filter interesting dst))
-
-    interesting (FixedReg _) = False
-    interesting _ = True
-
-    regAddr (AddrReg r1)      = [r1]
-    regAddr (AddrRegImm r1 _) = [r1]
-    regAddr (AddrImm _)              = []
-
-    regRI (RIReg r) = [r]
-    regRI  _   = []
-
-
-patchRegs :: Instr -> (Reg -> Reg) -> Instr
-patchRegs instr env = case instr of
-    SPILL  reg slot    -> SPILL (env reg) slot
-    RELOAD slot reg    -> RELOAD slot (env reg)
-    LD sz reg addr -> LD sz (env reg) (fixAddr addr)
-    LDA reg addr -> LDA (env reg) (fixAddr addr)
-    LDAH reg addr -> LDAH (env reg) (fixAddr addr)
-    LDGP reg addr -> LDGP (env reg) (fixAddr addr)
-    LDI sz reg imm -> LDI sz (env reg) imm
-    ST sz reg addr -> ST sz (env reg) (fixAddr addr)
-    CLR reg -> CLR (env reg)
-    ABS sz ar reg -> ABS sz (fixRI ar) (env reg)
-    NEG sz ov ar reg -> NEG sz ov (fixRI ar) (env reg)
-    ADD sz ov r1 ar r2 -> ADD sz ov (env r1) (fixRI ar) (env r2)
-    SADD sz sc r1 ar r2 -> SADD sz sc (env r1) (fixRI ar) (env r2)
-    SUB sz ov r1 ar r2 -> SUB sz ov (env r1) (fixRI ar) (env r2)
-    SSUB sz sc r1 ar r2 -> SSUB sz sc (env r1) (fixRI ar) (env r2)
-    MUL sz ov r1 ar r2 -> MUL sz ov (env r1) (fixRI ar) (env r2)
-    DIV sz un r1 ar r2 -> DIV sz un (env r1) (fixRI ar) (env r2)
-    REM sz un r1 ar r2 -> REM sz un (env r1) (fixRI ar) (env r2)
-    NOT ar reg -> NOT (fixRI ar) (env reg)
-    AND r1 ar r2 -> AND (env r1) (fixRI ar) (env r2)
-    ANDNOT r1 ar r2 -> ANDNOT (env r1) (fixRI ar) (env r2)
-    OR r1 ar r2 -> OR (env r1) (fixRI ar) (env r2)
-    ORNOT r1 ar r2 -> ORNOT (env r1) (fixRI ar) (env r2)
-    XOR r1 ar r2 -> XOR (env r1) (fixRI ar) (env r2)
-    XORNOT r1 ar r2 -> XORNOT (env r1) (fixRI ar) (env r2)
-    SLL r1 ar r2 -> SLL (env r1) (fixRI ar) (env r2)
-    SRL r1 ar r2 -> SRL (env r1) (fixRI ar) (env r2)
-    SRA r1 ar r2 -> SRA (env r1) (fixRI ar) (env r2)
-    ZAP r1 ar r2 -> ZAP (env r1) (fixRI ar) (env r2)
-    ZAPNOT r1 ar r2 -> ZAPNOT (env r1) (fixRI ar) (env r2)
-    CMP co r1 ar r2 -> CMP co (env r1) (fixRI ar) (env r2)
-    FCLR reg -> FCLR (env reg)
-    FABS r1 r2 -> FABS (env r1) (env r2)
-    FNEG s r1 r2 -> FNEG s (env r1) (env r2)
-    FADD s r1 r2 r3 -> FADD s (env r1) (env r2) (env r3)
-    FDIV s r1 r2 r3 -> FDIV s (env r1) (env r2) (env r3)
-    FMUL s r1 r2 r3 -> FMUL s (env r1) (env r2) (env r3)
-    FSUB s r1 r2 r3 -> FSUB s (env r1) (env r2) (env r3)
-    CVTxy s1 s2 r1 r2 -> CVTxy s1 s2 (env r1) (env r2)
-    FCMP s co r1 r2 r3 -> FCMP s co (env r1) (env r2) (env r3)
-    FMOV r1 r2 -> FMOV (env r1) (env r2)
-    BI cond reg lbl -> BI cond (env reg) lbl
-    BF cond reg lbl -> BF cond (env reg) lbl
-    JMP reg addr hint -> JMP (env reg) (fixAddr addr) hint
-    JSR reg addr i -> JSR (env reg) (fixAddr addr) i
-    _ -> instr
-  where
-    fixAddr (AddrReg r1)       = AddrReg (env r1)
-    fixAddr (AddrRegImm r1 i)  = AddrRegImm (env r1) i
-    fixAddr other             = other
-
-    fixRI (RIReg r) = RIReg (env r)
-    fixRI other        = other
-
-
-mkSpillInstr
-   :: Reg              -- register to spill
-   -> Int              -- current stack delta
-   -> Int              -- spill slot to use
-   -> Instr
-
-mkSpillInstr reg delta slot
-  = let        off     = spillSlotToOffset slot
-    in
-    -- Alpha: spill below the stack pointer (?)
-    ST sz dyn (spRel (- (off `div` 8)))
-
-
-mkLoadInstr
-   :: Reg              -- register to load
-   -> Int              -- current stack delta
-   -> Int              -- spill slot to use
-   -> Instr
-mkLoadInstr reg delta slot
-  = let off     = spillSlotToOffset slot
-    in
-        LD  sz dyn (spRel (- (off `div` 8)))
-
-
-mkBranchInstr
-    :: BlockId
-    -> [Instr]
-
-mkBranchInstr id = [BR id]
-
--}
-
-
-
-
diff --git a/compiler/nativeGen/Alpha/Regs.hs b/compiler/nativeGen/Alpha/Regs.hs
deleted file mode 100644 (file)
index ee49050..0000000
+++ /dev/null
@@ -1,323 +0,0 @@
--- -----------------------------------------------------------------------------
---
--- (c) The University of Glasgow 1994-2004
--- 
--- Alpha support is rotted and incomplete.
--- -----------------------------------------------------------------------------
-
-
-module Alpha.Regs (
-{-
-       Size(..),
-       AddrMode(..),
-       fits8Bits,
-       fReg,
-       gp, pv, ra, sp, t9, t10, t11, t12, v0, f0, zeroh
--}
-)
-
-where
-
-{-
-#include "nativeGen/NCG.h"
-#include "HsVersions.h"
-#include "../includes/stg/MachRegs.h"
-
-import RegsBase
-
-import BlockId
-import Cmm
-import CLabel           ( CLabel, mkMainCapabilityLabel )
-import Pretty
-import Outputable      ( Outputable(..), pprPanic, panic )
-import qualified Outputable
-import Unique
-import UniqSet
-import Constants
-import FastTypes
-import FastBool
-import UniqFM
-
-
-data Size
-       = B         -- byte
-       | Bu
---     | W         -- word (2 bytes): UNUSED
---     | Wu    -- : UNUSED
-       | L         -- longword (4 bytes)
-       | Q         -- quadword (8 bytes)
---     | FF    -- VAX F-style floating pt: UNUSED
---     | GF    -- VAX G-style floating pt: UNUSED
---     | DF    -- VAX D-style floating pt: UNUSED
---     | SF    -- IEEE single-precision floating pt: UNUSED
-       | TF    -- IEEE double-precision floating pt
-       deriving Eq
-
-
-data AddrMode
-       = AddrImm       Imm
-       | AddrReg       Reg
-       | AddrRegImm    Reg Imm
-
-
-addrOffset :: AddrMode -> Int -> Maybe AddrMode
-addrOffset addr off
-  = case addr of
-      _ -> panic "MachMisc.addrOffset not defined for Alpha"
-
-fits8Bits :: Integer -> Bool
-fits8Bits i = i >= -256 && i < 256
-
-
--- The Alpha has 64 registers of interest; 32 integer registers and 32 floating
--- point registers.  The mapping of STG registers to alpha machine registers
--- is defined in StgRegs.h.  We are, of course, prepared for any eventuality.
-
-fReg :: Int -> RegNo
-fReg x = (32 + x)
-
-v0, f0, ra, pv, gp, sp, zeroh :: Reg
-v0    = realReg 0
-f0    = realReg (fReg 0)
-ra    = FixedReg ILIT(26)
-pv    = t12
-gp    = FixedReg ILIT(29)
-sp    = FixedReg ILIT(30)
-zeroh = FixedReg ILIT(31) -- "zero" is used in 1.3 (MonadZero method)
-
-t9, t10, t11, t12 :: Reg
-t9  = realReg 23
-t10 = realReg 24
-t11 = realReg 25
-t12 = realReg 27
-
-
-#define f0 32
-#define f1 33
-#define f2 34
-#define f3 35
-#define f4 36
-#define f5 37
-#define f6 38
-#define f7 39
-#define f8 40
-#define f9 41
-#define f10 42
-#define f11 43
-#define f12 44
-#define f13 45
-#define f14 46
-#define f15 47
-#define f16 48
-#define f17 49
-#define f18 50
-#define f19 51
-#define f20 52
-#define f21 53
-#define f22 54
-#define f23 55
-#define f24 56
-#define f25 57
-#define f26 58
-#define f27 59
-#define f28 60
-#define f29 61
-#define f30 62
-#define f31 63
-
-
--- allMachRegs is the complete set of machine regs.
-allMachRegNos :: [RegNo]
-allMachRegNos  = [0..63]
-
-
--- these are the regs which we cannot assume stay alive over a
--- C call.  
-callClobberedRegs :: [Reg]
-callClobberedRegs
- =     [0, 1, 2, 3, 4, 5, 6, 7, 8,
-        16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29,
-        fReg 0, fReg 1, fReg 10, fReg 11, fReg 12, fReg 13, fReg 14, fReg 15,
-        fReg 16, fReg 17, fReg 18, fReg 19, fReg 20, fReg 21, fReg 22, fReg 23,
-        fReg 24, fReg 25, fReg 26, fReg 27, fReg 28, fReg 29, fReg 30]
-
-
--- argRegs is the set of regs which are read for an n-argument call to C.
--- For archs which pass all args on the stack (x86), is empty.
--- Sparc passes up to the first 6 args in regs.
--- Dunno about Alpha.
-argRegs :: RegNo -> [Reg]
-
-argRegs 0 = []
-argRegs 1 = freeMappedRegs [16, fReg 16]
-argRegs 2 = freeMappedRegs [16, 17, fReg 16, fReg 17]
-argRegs 3 = freeMappedRegs [16, 17, 18, fReg 16, fReg 17, fReg 18]
-argRegs 4 = freeMappedRegs [16, 17, 18, 19, fReg 16, fReg 17, fReg 18, fReg 19]
-argRegs 5 = freeMappedRegs [16, 17, 18, 19, 20, fReg 16, fReg 17, fReg 18, fReg 19, fReg 20]
-argRegs 6 = freeMappedRegs [16, 17, 18, 19, 20, 21, fReg 16, fReg 17, fReg 18, fReg 19, fReg 20, fReg 21]
-argRegs _ = panic "MachRegs.argRegs(alpha): don't know about >6 arguments!"
-
-
--- all of the arg regs ??
-allArgRegs :: [(Reg, Reg)]
-allArgRegs = [(realReg i, realReg (fReg i)) | i <- [16..21]]
-
-
--- horror show -----------------------------------------------------------------
-
-freeReg :: RegNo -> FastBool
-
-freeReg 26 = fastBool False  -- return address (ra)
-freeReg 28 = fastBool False  -- reserved for the assembler (at)
-freeReg 29 = fastBool False  -- global pointer (gp)
-freeReg 30 = fastBool False  -- stack pointer (sp)
-freeReg 31 = fastBool False  -- always zero (zeroh)
-freeReg 63 = fastBool False  -- always zero (f31)
-
-#ifdef REG_Base
-freeReg REG_Base = fastBool False
-#endif
-#ifdef REG_R1
-freeReg REG_R1   = fastBool False
-#endif 
-#ifdef REG_R2  
-freeReg REG_R2   = fastBool False
-#endif 
-#ifdef REG_R3  
-freeReg REG_R3   = fastBool False
-#endif 
-#ifdef REG_R4  
-freeReg REG_R4   = fastBool False
-#endif 
-#ifdef REG_R5  
-freeReg REG_R5   = fastBool False
-#endif 
-#ifdef REG_R6  
-freeReg REG_R6   = fastBool False
-#endif 
-#ifdef REG_R7  
-freeReg REG_R7   = fastBool False
-#endif 
-#ifdef REG_R8  
-freeReg REG_R8   = fastBool False
-#endif
-#ifdef REG_F1
-freeReg REG_F1 = fastBool False
-#endif
-#ifdef REG_F2
-freeReg REG_F2 = fastBool False
-#endif
-#ifdef REG_F3
-freeReg REG_F3 = fastBool False
-#endif
-#ifdef REG_F4
-freeReg REG_F4 = fastBool False
-#endif
-#ifdef REG_D1
-freeReg REG_D1 = fastBool False
-#endif
-#ifdef REG_D2
-freeReg REG_D2 = fastBool False
-#endif
-#ifdef REG_Sp 
-freeReg REG_Sp   = fastBool False
-#endif 
-#ifdef REG_Su
-freeReg REG_Su   = fastBool False
-#endif 
-#ifdef REG_SpLim 
-freeReg REG_SpLim = fastBool False
-#endif 
-#ifdef REG_Hp 
-freeReg REG_Hp   = fastBool False
-#endif
-#ifdef REG_HpLim
-freeReg REG_HpLim = fastBool False
-#endif
-freeReg n               = fastBool True
-
-
---  | Returns 'Nothing' if this global register is not stored
--- in a real machine register, otherwise returns @'Just' reg@, where
--- reg is the machine register it is stored in.
-
-globalRegMaybe :: GlobalReg -> Maybe Reg
-
-#ifdef REG_Base
-globalRegMaybe BaseReg                 = Just (RealReg REG_Base)
-#endif
-#ifdef REG_R1
-globalRegMaybe (VanillaReg 1 _)                = Just (RealReg REG_R1)
-#endif 
-#ifdef REG_R2 
-globalRegMaybe (VanillaReg 2 _)                = Just (RealReg REG_R2)
-#endif 
-#ifdef REG_R3 
-globalRegMaybe (VanillaReg 3 _)        = Just (RealReg REG_R3)
-#endif 
-#ifdef REG_R4 
-globalRegMaybe (VanillaReg 4 _)                = Just (RealReg REG_R4)
-#endif 
-#ifdef REG_R5 
-globalRegMaybe (VanillaReg 5 _)                = Just (RealReg REG_R5)
-#endif 
-#ifdef REG_R6 
-globalRegMaybe (VanillaReg 6 _)                = Just (RealReg REG_R6)
-#endif 
-#ifdef REG_R7 
-globalRegMaybe (VanillaReg 7 _)                = Just (RealReg REG_R7)
-#endif 
-#ifdef REG_R8 
-globalRegMaybe (VanillaReg 8 _)                = Just (RealReg REG_R8)
-#endif
-#ifdef REG_R9 
-globalRegMaybe (VanillaReg 9 _)                = Just (RealReg REG_R9)
-#endif
-#ifdef REG_R10 
-globalRegMaybe (VanillaReg 10 _)       = Just (RealReg REG_R10)
-#endif
-#ifdef REG_F1
-globalRegMaybe (FloatReg 1)            = Just (RealReg REG_F1)
-#endif                                 
-#ifdef REG_F2                          
-globalRegMaybe (FloatReg 2)            = Just (RealReg REG_F2)
-#endif                                 
-#ifdef REG_F3                          
-globalRegMaybe (FloatReg 3)            = Just (RealReg REG_F3)
-#endif                                 
-#ifdef REG_F4                          
-globalRegMaybe (FloatReg 4)            = Just (RealReg REG_F4)
-#endif                                 
-#ifdef REG_D1                          
-globalRegMaybe (DoubleReg 1)           = Just (RealReg REG_D1)
-#endif                                 
-#ifdef REG_D2                          
-globalRegMaybe (DoubleReg 2)           = Just (RealReg REG_D2)
-#endif
-#ifdef REG_Sp      
-globalRegMaybe Sp                      = Just (RealReg REG_Sp)
-#endif
-#ifdef REG_Lng1                                
-globalRegMaybe (LongReg 1)             = Just (RealReg REG_Lng1)
-#endif                                 
-#ifdef REG_Lng2                                
-globalRegMaybe (LongReg 2)             = Just (RealReg REG_Lng2)
-#endif
-#ifdef REG_SpLim                               
-globalRegMaybe SpLim                   = Just (RealReg REG_SpLim)
-#endif                                 
-#ifdef REG_Hp                          
-globalRegMaybe Hp                      = Just (RealReg REG_Hp)
-#endif                                 
-#ifdef REG_HpLim                       
-globalRegMaybe HpLim                   = Just (RealReg REG_HpLim)
-#endif                                 
-#ifdef REG_CurrentTSO                          
-globalRegMaybe CurrentTSO              = Just (RealReg REG_CurrentTSO)
-#endif                                 
-#ifdef REG_CurrentNursery                              
-globalRegMaybe CurrentNursery          = Just (RealReg REG_CurrentNursery)
-#endif                                 
-globalRegMaybe _                       = Nothing
-
--}
index 7a38540..06e6d6d 100644 (file)
@@ -13,13 +13,7 @@ module AsmCodeGen ( nativeCodeGen ) where
 #include "nativeGen/NCG.h"
 
 
-#if   alpha_TARGET_ARCH
-import Alpha.CodeGen
-import Alpha.Regs
-import Alpha.RegInfo
-import Alpha.Instr
-
-#elif i386_TARGET_ARCH || x86_64_TARGET_ARCH
+#if i386_TARGET_ARCH || x86_64_TARGET_ARCH
 import X86.CodeGen
 import X86.Regs
 import X86.Instr
@@ -64,7 +58,7 @@ import NCGMonad
 import BlockId
 import CgUtils         ( fixStgRegisters )
 import OldCmm
-import CmmOpt          ( cmmMiniInline, cmmMachOpFold )
+import CmmOpt          ( cmmEliminateDeadBlocks, cmmMiniInline, cmmMachOpFold )
 import OldPprCmm
 import CLabel
 
@@ -378,10 +372,15 @@ cmmNativeGen dflags us cmm count
                        , Nothing
                        , mPprStats)
 
+       ---- generate jump tables
+       let tabled      =
+               {-# SCC "generateJumpTables" #-}
+               alloced ++ generateJumpTables alloced
+
        ---- shortcut branches
        let shorted     =
                {-# SCC "shortcutBranches" #-}
-               shortcutBranches dflags alloced
+               shortcutBranches dflags tabled
 
        ---- sequence blocks
        let sequenced   =
@@ -609,6 +608,18 @@ makeFarBranches = id
 #endif
 
 -- -----------------------------------------------------------------------------
+-- Generate jump tables
+
+-- Analyzes all native code and generates data sections for all jump
+-- table instructions.
+generateJumpTables
+       :: [NatCmmTop Instr] -> [NatCmmTop Instr]
+generateJumpTables xs = concatMap f xs
+    where f (CmmProc _ _ (ListGraph xs)) = concatMap g xs
+          f _ = []
+          g (BasicBlock _ xs) = catMaybes (map generateJumpTableForInstr xs)
+
+-- -----------------------------------------------------------------------------
 -- Shortcut branches
 
 shortcutBranches 
@@ -718,10 +729,9 @@ Here we do:
              and position independent refs
         (ii) compile a list of imported symbols
 
-Ideas for other things we could do (ToDo):
+Ideas for other things we could do:
 
   - shortcut jumps-to-jumps
-  - eliminate dead code blocks
   - simple CSE: if an expr is assigned to a temp, then replace later occs of
     that expr with the temp, until the expr is no longer valid (can push through
     temp assignments, and certain assigns to mem...)
@@ -730,7 +740,7 @@ Ideas for other things we could do (ToDo):
 cmmToCmm :: DynFlags -> RawCmmTop -> (RawCmmTop, [CLabel])
 cmmToCmm _ top@(CmmData _ _) = (top, [])
 cmmToCmm dflags (CmmProc info lbl (ListGraph blocks)) = runCmmOpt dflags $ do
-  blocks' <- mapM cmmBlockConFold (cmmMiniInline blocks)
+  blocks' <- mapM cmmBlockConFold (cmmMiniInline (cmmEliminateDeadBlocks blocks))
   return $ CmmProc info lbl (ListGraph blocks')
 
 newtype CmmOptM a = CmmOptM (([CLabel], DynFlags) -> (# a, [CLabel] #))
index 29b9a54..c96badd 100644 (file)
@@ -15,6 +15,7 @@
 
 module PPC.CodeGen ( 
        cmmTopCodeGen, 
+       generateJumpTableForInstr,
        InstrBlock 
 ) 
 
@@ -798,7 +799,7 @@ genJump (CmmLit (CmmLabel lbl))
 genJump tree
   = do
         (target,code) <- getSomeReg tree
-        return (code `snocOL` MTCTR target `snocOL` BCTR [])
+        return (code `snocOL` MTCTR target `snocOL` BCTR [] Nothing)
 
 
 -- -----------------------------------------------------------------------------
@@ -1126,22 +1127,12 @@ genSwitch expr ids
         dflags <- getDynFlagsNat
         dynRef <- cmmMakeDynamicReference dflags addImportNat DataReference lbl
         (tableReg,t_code) <- getSomeReg $ dynRef
-        let
-            jumpTable = map jumpTableEntryRel ids
-            
-            jumpTableEntryRel Nothing
-                = CmmStaticLit (CmmInt 0 wordWidth)
-            jumpTableEntryRel (Just blockid)
-                = CmmStaticLit (CmmLabelDiffOff blockLabel lbl 0)
-                where blockLabel = mkAsmTempLabel (getUnique blockid)
-
-            code = e_code `appOL` t_code `appOL` toOL [
-                            LDATA ReadOnlyData (CmmDataLabel lbl : jumpTable),
+        let code = e_code `appOL` t_code `appOL` toOL [
                             SLW tmp reg (RIImm (ImmInt 2)),
                             LD II32 tmp (AddrRegReg tableReg tmp),
                             ADD tmp tmp (RIReg tableReg),
                             MTCTR tmp,
-                            BCTR [ id | Just id <- ids ]
+                            BCTR ids (Just lbl)
                     ]
         return code
   | otherwise
@@ -1149,19 +1140,27 @@ genSwitch expr ids
         (reg,e_code) <- getSomeReg expr
         tmp <- getNewRegNat II32
         lbl <- getNewLabelNat
-        let
-            jumpTable = map jumpTableEntry ids
-        
-            code = e_code `appOL` toOL [
-                            LDATA ReadOnlyData (CmmDataLabel lbl : jumpTable),
+        let code = e_code `appOL` toOL [
                             SLW tmp reg (RIImm (ImmInt 2)),
                             ADDIS tmp tmp (HA (ImmCLbl lbl)),
                             LD II32 tmp (AddrRegImm tmp (LO (ImmCLbl lbl))),
                             MTCTR tmp,
-                            BCTR [ id | Just id <- ids ]
+                            BCTR ids (Just lbl)
                     ]
         return code
 
+generateJumpTableForInstr :: Instr -> Maybe (NatCmmTop Instr)
+generateJumpTableForInstr (BCTR ids (Just lbl)) =
+    let jumpTable
+            | opt_PIC   = map jumpTableEntryRel ids
+            | otherwise = map jumpTableEntry ids
+                where jumpTableEntryRel Nothing
+                        = CmmStaticLit (CmmInt 0 wordWidth)
+                      jumpTableEntryRel (Just blockid)
+                        = CmmStaticLit (CmmLabelDiffOff blockLabel lbl 0)
+                            where blockLabel = mkAsmTempLabel (getUnique blockid)
+    in Just (CmmData ReadOnlyData (CmmDataLabel lbl : jumpTable))
+generateJumpTableForInstr _ = Nothing
 
 -- -----------------------------------------------------------------------------
 -- 'condIntReg' and 'condFltReg': condition codes into registers
index 6aeccd3..0288f1b 100644 (file)
@@ -104,7 +104,7 @@ data Instr
        | JMP     CLabel                -- same as branch,
                                         -- but with CLabel instead of block ID
        | MTCTR Reg
-       | BCTR    [BlockId]             -- with list of local destinations
+       | BCTR [Maybe BlockId] (Maybe CLabel) -- with list of local destinations, and jump table location if necessary
        | BL    CLabel [Reg]            -- with list of argument regs
        | BCTRL [Reg]
              
@@ -184,7 +184,7 @@ ppc_regUsageOfInstr instr
     BCC           _ _          -> noUsage
     BCCFAR _ _         -> noUsage
     MTCTR reg          -> usage ([reg],[])
-    BCTR  _            -> noUsage
+    BCTR  _ _          -> noUsage
     BL    _ params     -> usage (params, callClobberedRegs)
     BCTRL params       -> usage (params, callClobberedRegs)
     ADD          reg1 reg2 ri  -> usage (reg2 : regRI ri, [reg1])
@@ -257,7 +257,7 @@ ppc_patchRegsOfInstr instr env
     BCC          cond lbl      -> BCC cond lbl
     BCCFAR cond lbl    -> BCCFAR cond lbl
     MTCTR reg          -> MTCTR (env reg)
-    BCTR  targets      -> BCTR targets
+    BCTR  targets lbl  -> BCTR targets lbl
     BL    imm argRegs  -> BL imm argRegs       -- argument regs
     BCTRL argRegs      -> BCTRL argRegs        -- cannot be remapped
     ADD          reg1 reg2 ri  -> ADD (env reg1) (env reg2) (fixRI ri)
@@ -326,7 +326,7 @@ ppc_jumpDestsOfInstr insn
   = case insn of
         BCC _ id        -> [id]
         BCCFAR _ id     -> [id]
-        BCTR targets    -> targets
+        BCTR targets _  -> [id | Just id <- targets]
        _               -> []
        
        
@@ -338,7 +338,7 @@ ppc_patchJumpInstr insn patchF
   = case insn of
         BCC cc id      -> BCC cc (patchF id)
         BCCFAR cc id   -> BCCFAR cc (patchF id)
-        BCTR _         -> error "Cannot patch BCTR"
+        BCTR ids lbl   -> BCTR (map (fmap patchF) ids) lbl
        _               -> insn
 
 
index 9fb86c0..44a6a7c 100644 (file)
@@ -545,7 +545,7 @@ pprInstr (MTCTR reg) = hcat [
        char '\t',
        pprReg reg
     ]
-pprInstr (BCTR _) = hcat [
+pprInstr (BCTR _ _) = hcat [
        char '\t',
        ptext (sLit "bctr")
     ]
index 73e0c20..7a2a84b 100644 (file)
@@ -209,7 +209,6 @@ spRel n     = AddrRegImm sp (ImmInt (n * wORD_SIZE))
 -- argRegs is the set of regs which are read for an n-argument call to C.
 -- For archs which pass all args on the stack (x86), is empty.
 -- Sparc passes up to the first 6 args in regs.
--- Dunno about Alpha.
 argRegs :: RegNo -> [Reg]
 argRegs 0 = []
 argRegs 1 = map regSingle [3]
index 20cb5f5..7b2502d 100644 (file)
@@ -31,8 +31,7 @@ data Platform
 --     about what instruction set extensions an architecture might support.
 --
 data Arch
-       = ArchAlpha
-       | ArchX86
+       = ArchX86
        | ArchX86_64
        | ArchPPC
        | ArchPPC_64
@@ -70,9 +69,7 @@ defaultTargetPlatform
 
 -- | Move the evil TARGET_ARCH #ifdefs into Haskell land.
 defaultTargetArch :: Arch
-#if   alpha_TARGET_ARCH
-defaultTargetArch      = ArchAlpha
-#elif i386_TARGET_ARCH
+#if i386_TARGET_ARCH
 defaultTargetArch      = ArchX86
 #elif x86_64_TARGET_ARCH
 defaultTargetArch      = ArchX86_64
index 903082f..ef6ae9b 100644 (file)
@@ -190,7 +190,7 @@ joinToTargets_again
                 _      -> let  instr'  =  patchJumpInstr instr 
                                                (\bid -> if bid == dest 
                                                                then mkBlockId fixup_block_id 
-                                                               else dest)
+                                                               else bid) -- no change!
                                                
                           in   joinToTargets' block_live (block : new_blocks) block_id instr' dests
 
index d08d10d..beb48d6 100644 (file)
@@ -8,6 +8,7 @@
 
 module SPARC.CodeGen ( 
        cmmTopCodeGen, 
+       generateJumpTableForInstr,
        InstrBlock 
 ) 
 
@@ -299,15 +300,11 @@ genSwitch expr ids
                dst             <- getNewRegNat II32
 
                label           <- getNewLabelNat
-               let jumpTable   = map jumpTableEntry ids
 
                return $ e_code `appOL`
                 toOL   
-                       -- the jump table
-                       [ LDATA ReadOnlyData (CmmDataLabel label : jumpTable)
-
-                       -- load base of jump table
-                       , SETHI (HI (ImmCLbl label)) base_reg
+                       [ -- load base of jump table
+                         SETHI (HI (ImmCLbl label)) base_reg
                        , OR    False base_reg (RIImm $ LO $ ImmCLbl label) base_reg
                        
                        -- the addrs in the table are 32 bits wide..
@@ -315,6 +312,11 @@ genSwitch expr ids
 
                        -- load and jump to the destination
                        , LD      II32 (AddrRegReg base_reg offset_reg) dst
-                       , JMP_TBL (AddrRegImm dst (ImmInt 0)) [i | Just i <- ids]
+                       , JMP_TBL (AddrRegImm dst (ImmInt 0)) ids label
                        , NOP ]
 
+generateJumpTableForInstr :: Instr -> Maybe (NatCmmTop Instr)
+generateJumpTableForInstr (JMP_TBL _ ids label) =
+       let jumpTable = map jumpTableEntry ids
+       in Just (CmmData ReadOnlyData (CmmDataLabel label : jumpTable))
+generateJumpTableForInstr _ = Nothing
index 79b4629..93f4d27 100644 (file)
@@ -37,6 +37,7 @@ import RegClass
 import Reg
 import Size
 
+import CLabel
 import BlockId
 import OldCmm
 import FastString
@@ -194,7 +195,7 @@ data Instr
        -- With a tabled jump we know all the possible destinations.
        -- We also need this info so we can work out what regs are live across the jump.
        -- 
-       | JMP_TBL       AddrMode [BlockId]
+       | JMP_TBL       AddrMode [Maybe BlockId] CLabel
 
        | CALL          (Either Imm Reg) Int Bool       -- target, args, terminal
 
@@ -247,7 +248,7 @@ sparc_regUsageOfInstr instr
     FxTOy   _ _  r1 r2                 -> usage ([r1],                 [r2])
 
     JMP     addr               -> usage (regAddr addr, [])
-    JMP_TBL addr _             -> usage (regAddr addr, [])
+    JMP_TBL addr _ _           -> usage (regAddr addr, [])
 
     CALL  (Left _  )  _ True   -> noUsage
     CALL  (Left _  )  n False  -> usage (argRegs n, callClobberedRegs)
@@ -315,7 +316,7 @@ sparc_patchRegsOfInstr instr env = case instr of
     FxTOy s1 s2 r1 r2          -> FxTOy s1 s2 (env r1) (env r2)
 
     JMP     addr               -> JMP     (fixAddr addr)
-    JMP_TBL addr ids           -> JMP_TBL (fixAddr addr) ids
+    JMP_TBL addr ids l         -> JMP_TBL (fixAddr addr) ids l
 
     CALL  (Left i) n t         -> CALL (Left i) n t
     CALL  (Right r) n t        -> CALL (Right (env r)) n t
@@ -345,7 +346,7 @@ sparc_jumpDestsOfInstr insn
   = case insn of
        BI   _ _ id     -> [id]
        BF   _ _ id     -> [id]
-       JMP_TBL _ ids   -> ids
+       JMP_TBL _ ids _ -> [id | Just id <- ids]
        _               -> []
 
 
@@ -354,6 +355,7 @@ sparc_patchJumpInstr insn patchF
   = case insn of
        BI cc annul id  -> BI cc annul (patchF id)
        BF cc annul id  -> BF cc annul (patchF id)
+       JMP_TBL n ids l -> JMP_TBL n (map (fmap patchF) ids) l
        _               -> insn
 
 
index a63661f..0139680 100644 (file)
@@ -543,7 +543,7 @@ pprInstr (BF cond b blockid)
     ]
 
 pprInstr (JMP addr) = (<>) (ptext (sLit "\tjmp\t")) (pprAddr addr)
-pprInstr (JMP_TBL op _)  = pprInstr (JMP op)
+pprInstr (JMP_TBL op _ _)  = pprInstr (JMP op)
 
 pprInstr (CALL (Left imm) n _)
   = hcat [ ptext (sLit "\tcall\t"), pprImm imm, comma, int n ]
index 5df8f77..a6cc36f 100644 (file)
@@ -20,6 +20,7 @@
 
 module X86.CodeGen ( 
        cmmTopCodeGen, 
+       generateJumpTableForInstr,
        InstrBlock 
 ) 
 
@@ -1932,16 +1933,7 @@ genSwitch expr ids
         dflags <- getDynFlagsNat
         dynRef <- cmmMakeDynamicReference dflags addImportNat DataReference lbl
         (tableReg,t_code) <- getSomeReg $ dynRef
-        let
-            jumpTable = map jumpTableEntryRel ids
-            
-            jumpTableEntryRel Nothing
-                = CmmStaticLit (CmmInt 0 wordWidth)
-            jumpTableEntryRel (Just blockid)
-                = CmmStaticLit (CmmLabelDiffOff blockLabel lbl 0)
-                where blockLabel = mkAsmTempLabel (getUnique blockid)
-
-            op = OpAddr (AddrBaseIndex (EABaseReg tableReg)
+        let op = OpAddr (AddrBaseIndex (EABaseReg tableReg)
                                        (EAIndex reg wORD_SIZE) (ImmInt 0))
 
 #if x86_64_TARGET_ARCH
@@ -1954,8 +1946,7 @@ genSwitch expr ids
     
             code = e_code `appOL` t_code `appOL` toOL [
                             ADD (intSize wordWidth) op (OpReg tableReg),
-                            JMP_TBL (OpReg tableReg) [ id | Just id <- ids ],
-                            LDATA Text (CmmDataLabel lbl : jumpTable)
+                            JMP_TBL (OpReg tableReg) ids Text lbl
                     ]
 #else
     -- HACK: On x86_64 binutils<2.17 is only able to generate PC32
@@ -1965,20 +1956,18 @@ genSwitch expr ids
     -- conjunction with the hack in PprMach.hs/pprDataItem once
     -- binutils 2.17 is standard.
             code = e_code `appOL` t_code `appOL` toOL [
-                           LDATA ReadOnlyData (CmmDataLabel lbl : jumpTable),
                            MOVSxL II32
                                   (OpAddr (AddrBaseIndex (EABaseReg tableReg)
                                                          (EAIndex reg wORD_SIZE) (ImmInt 0)))
                                   (OpReg reg),
                            ADD (intSize wordWidth) (OpReg reg) (OpReg tableReg),
-                           JMP_TBL (OpReg tableReg) [ id | Just id <- ids ]
+                           JMP_TBL (OpReg tableReg) ids ReadOnlyData lbl
                   ]
 #endif
 #else
             code = e_code `appOL` t_code `appOL` toOL [
-                            LDATA ReadOnlyData (CmmDataLabel lbl : jumpTable),
                             ADD (intSize wordWidth) op (OpReg tableReg),
-                            JMP_TBL (OpReg tableReg) [ id | Just id <- ids ]
+                            JMP_TBL (OpReg tableReg) ids ReadOnlyData lbl
                     ]
 #endif
         return code
@@ -1987,15 +1976,28 @@ genSwitch expr ids
         (reg,e_code) <- getSomeReg expr
         lbl <- getNewLabelNat
         let
-            jumpTable = map jumpTableEntry ids
             op = OpAddr (AddrBaseIndex EABaseNone (EAIndex reg wORD_SIZE) (ImmCLbl lbl))
             code = e_code `appOL` toOL [
-                    LDATA ReadOnlyData (CmmDataLabel lbl : jumpTable),
-                    JMP_TBL op [ id | Just id <- ids ]
+                    JMP_TBL op ids ReadOnlyData lbl
                  ]
         -- in
         return code
 
+generateJumpTableForInstr :: Instr -> Maybe (NatCmmTop Instr)
+generateJumpTableForInstr (JMP_TBL _ ids section lbl) = Just (createJumpTable ids section lbl)
+generateJumpTableForInstr _ = Nothing
+
+createJumpTable ids section lbl
+    = let jumpTable
+            | opt_PIC =
+                  let jumpTableEntryRel Nothing
+                          = CmmStaticLit (CmmInt 0 wordWidth)
+                      jumpTableEntryRel (Just blockid)
+                          = CmmStaticLit (CmmLabelDiffOff blockLabel lbl 0)
+                          where blockLabel = mkAsmTempLabel (getUnique blockid)
+                  in map jumpTableEntryRel ids
+            | otherwise = map jumpTableEntry ids
+      in CmmData section (CmmDataLabel lbl : jumpTable)
 
 -- -----------------------------------------------------------------------------
 -- 'condIntReg' and 'condFltReg': condition codes into registers
index a96452b..e934a6d 100644 (file)
@@ -289,7 +289,11 @@ data Instr
        | JMP         Operand
        | JXX         Cond BlockId  -- includes unconditional branches
        | JXX_GBL     Cond Imm      -- non-local version of JXX
-       | JMP_TBL     Operand [BlockId]  -- table jump
+       -- Table jump
+       | JMP_TBL     Operand   -- Address to jump to
+                     [Maybe BlockId] -- Blocks in the jump table
+                     Section   -- Data section jump table should be put in
+                     CLabel    -- Label of jump table
        | CALL        (Either Imm Reg) [Reg]
 
        -- Other things.
@@ -350,7 +354,7 @@ x86_regUsageOfInstr instr
     JXX    _ _         -> mkRU [] []
     JXX_GBL _ _                -> mkRU [] []
     JMP     op         -> mkRUR (use_R op)
-    JMP_TBL op _        -> mkRUR (use_R op)
+    JMP_TBL op _ _ _    -> mkRUR (use_R op)
     CALL (Left _)  params   -> mkRU params callClobberedRegs
     CALL (Right reg) params -> mkRU (reg:params) callClobberedRegs
     CLTD   _           -> mkRU [eax] [edx]
@@ -482,7 +486,7 @@ x86_patchRegsOfInstr instr env
     POP  sz op         -> patch1 (POP  sz) op
     SETCC cond op      -> patch1 (SETCC cond) op
     JMP op             -> patch1 JMP op
-    JMP_TBL op ids      -> patch1 JMP_TBL op $ ids
+    JMP_TBL op ids s lbl-> JMP_TBL (patchOp op) ids s lbl
 
     GMOV src dst       -> GMOV (env src) (env dst)
     GLD  sz src dst    -> GLD sz (lookupAddr src) (env dst)
@@ -579,7 +583,7 @@ x86_jumpDestsOfInstr
 x86_jumpDestsOfInstr insn 
   = case insn of
        JXX _ id        -> [id]
-       JMP_TBL _ ids   -> ids
+       JMP_TBL _ ids _ _ -> [id | Just id <- ids]
        _               -> []
 
 
@@ -589,7 +593,8 @@ x86_patchJumpInstr
 x86_patchJumpInstr insn patchF
   = case insn of
        JXX cc id       -> JXX cc (patchF id)
-       JMP_TBL _ _     -> error "Cannot patch JMP_TBL"
+       JMP_TBL op ids section lbl
+         -> JMP_TBL op (map (fmap patchF) ids) section lbl
        _               -> insn
 
 
index 5fe78e1..4c3454d 100644 (file)
@@ -87,7 +87,17 @@ pprNatCmmTop (CmmProc info lbl (ListGraph blocks)) =
                       <+> pprCLabel_asm (mkDeadStripPreventer $ entryLblToInfoLbl lbl)
                     else empty
 #endif
+   $$ pprSizeDecl (if null info then lbl else entryLblToInfoLbl lbl)
 
+-- | Output the ELF .size directive.
+pprSizeDecl :: CLabel -> Doc
+#if elf_OBJ_FORMAT
+pprSizeDecl lbl =
+    ptext (sLit "\t.size") <+> pprCLabel_asm lbl
+    <> ptext (sLit ", .-") <> pprCLabel_asm lbl
+#else
+pprSizeDecl _ = empty
+#endif
 
 pprBasicBlock :: NatBasicBlock Instr -> Doc
 pprBasicBlock (BasicBlock blockid instrs) =
@@ -626,7 +636,7 @@ pprInstr (JXX_GBL cond imm) = pprCondInstr (sLit "j") cond (pprImm imm)
 
 pprInstr (JMP (OpImm imm)) = (<>) (ptext (sLit "\tjmp ")) (pprImm imm)
 pprInstr (JMP op)          = (<>) (ptext (sLit "\tjmp *")) (pprOperand archWordSize op)
-pprInstr (JMP_TBL op _)  = pprInstr (JMP op)
+pprInstr (JMP_TBL op _ _ _)  = pprInstr (JMP op)
 pprInstr (CALL (Left imm) _)    = (<>) (ptext (sLit "\tcall ")) (pprImm imm)
 pprInstr (CALL (Right reg) _)   = (<>) (ptext (sLit "\tcall *")) (pprReg archWordSize reg)
 
index 094b74d..dc0df49 100644 (file)
@@ -249,7 +249,6 @@ floatregnos = fakeregnos ++ xmmregnos;
 -- argRegs is the set of regs which are read for an n-argument call to C.
 -- For archs which pass all args on the stack (x86), is empty.
 -- Sparc passes up to the first 6 args in regs.
--- Dunno about Alpha.
 argRegs :: RegNo -> [Reg]
 argRegs _      = panic "MachRegs.argRegs(x86): should not be used!"
 
index 7d80db4..49f7a97 100644 (file)
@@ -1738,9 +1738,19 @@ primtype Any a
            but never enters a function value.  
 
        It's also used to instantiate un-constrained type variables after type
-       checking.  For example
+       checking.  For example, {\tt length} has type
 
-       {\tt length Any []}
+       {\tt length :: forall a. [a] -> Int}
+
+       and the list datacon for the empty list has type
+
+       {\tt [] :: forall a. [a]}
+
+       In order to compose these two terms as {\tt length []} a type
+       application is required, but there is no constraint on the
+       choice.  In this situation GHC uses {\tt Any}:
+
+       {\tt length Any ([] Any)}
 
        Annoyingly, we sometimes need {\tt Any}s of other kinds, such as {\tt (* -> *)} etc.
        This is a bit like tuples.   We define a couple of useful ones here,
index 9278126..4e9b548 100644 (file)
@@ -134,6 +134,9 @@ if test "$WithGhc" != ""; then
   AC_SUBST(ghc_ge_613)dnl
 
   BOOTSTRAPPING_GHC_INFO_FIELD([CC_STAGE0],[C compiler command],['$(CC)'])
+  BOOTSTRAPPING_GHC_INFO_FIELD([AR_STAGE0],[ar command],['$(AR)'])
+  BOOTSTRAPPING_GHC_INFO_FIELD([AR_OPTS_STAGE0],[ar flags],['$(AR_OPTS)'])
+  BOOTSTRAPPING_GHC_INFO_FIELD([ArSupportsAtFile_STAGE0],[ar supports at file],['$(ArSupportsAtFile)'])
 fi
 
 dnl ** Must have GHC to build GHC, unless --enable-hc-boot is on
@@ -262,6 +265,7 @@ checkVendor() {
     esac
 }
 
+# Sync this with cTargetOS in compiler/ghc.mk
 checkOS() {
     case $1 in
     linux|freebsd|netbsd|openbsd|dragonfly|osf1|osf3|hpux|linuxaout|kfreebsdgnu|freebsd2|solaris2|cygwin32|mingw32|darwin|gnu|nextstep2|nextstep3|sunos4|ultrix|irix|aix|haiku)
@@ -305,12 +309,15 @@ checkOS "$TargetOS"
 
 # Verify that the installed (bootstrap) GHC is capable of generating
 # code for the requested build platform.
-if test "$BuildPlatform" != "$bootstrap_target"
+if test "$BootingFromHc" = "NO"
 then
-    echo "This GHC (${WithGhc}) does not generate code for the build platform"
-    echo "   GHC target platform    : $bootstrap_target"
-    echo "   Desired build platform : $BuildPlatform"
-    exit 1
+    if test "$BuildPlatform" != "$bootstrap_target"
+    then
+        echo "This GHC (${WithGhc}) does not generate code for the build platform"
+        echo "   GHC target platform    : $bootstrap_target"
+        echo "   Desired build platform : $BuildPlatform"
+        exit 1
+    fi
 fi
 
 echo "GHC build  : $BuildPlatform"
index 5003f9a..083a66d 100644 (file)
@@ -1 +1 @@
-exec "$executablename" -B"$topdir" -pgmc "$pgmgcc" -pgma "$pgmgcc" -pgml "$pgmgcc" -pgmP "$pgmgcc -E -undef -traditional" ${1+"$@"}
+exec "$executablename" -B"$topdir" ${1+"$@"}
index f1b0422..52fd6f1 100644 (file)
@@ -306,6 +306,7 @@ load_load_barrier(void) {
 #define store_load_barrier() /* nothing */
 #define load_load_barrier()  /* nothing */
 
+#if !IN_STG_CODE || IN_STGCRUN
 INLINE_HEADER StgWord
 xchg(StgPtr p, StgWord w)
 {
@@ -337,6 +338,7 @@ atomic_dec(StgVolatilePtr p)
 {
     return --(*p);
 }
+#endif
 
 #define VOLATILE_LOAD(p) ((StgWord)*((StgWord*)(p)))
 
index f96302b..8796ad4 100644 (file)
@@ -548,6 +548,11 @@ CC_STAGE0       = @CC_STAGE0@
 CC_STAGE1       = $(CC)
 CC_STAGE2       = $(CC)
 CC_STAGE3       = $(CC)
+AS              = $(WhatGccIsCalled)
+AS_STAGE0       = @CC_STAGE0@
+AS_STAGE1       = $(AS)
+AS_STAGE2       = $(AS)
+AS_STAGE3       = $(AS)
 
 # C compiler and linker flags from configure (e.g. -m<blah> to select
 # correct C compiler backend). The stage number is the stage of GHC
@@ -599,11 +604,11 @@ AR                        = @ArCmd@
 AR_OPTS                        = @ArArgs@
 ArSupportsAtFile = @ArSupportsAtFile@
 
-AR_STAGE0 = $(AR)
+AR_STAGE0 = @AR_STAGE0@
 AR_STAGE1 = $(AR)
 AR_STAGE2 = $(AR)
 AR_STAGE3 = $(AR)
-AR_OPTS_STAGE0 = $(AR_OPTS)
+AR_OPTS_STAGE0 = @AR_OPTS_STAGE0@
 AR_OPTS_STAGE1 = $(AR_OPTS)
 AR_OPTS_STAGE2 = $(AR_OPTS)
 AR_OPTS_STAGE3 = $(AR_OPTS)
@@ -611,7 +616,7 @@ EXTRA_AR_ARGS_STAGE0 = $(EXTRA_AR_ARGS)
 EXTRA_AR_ARGS_STAGE1 = $(EXTRA_AR_ARGS)
 EXTRA_AR_ARGS_STAGE2 = $(EXTRA_AR_ARGS)
 EXTRA_AR_ARGS_STAGE3 = $(EXTRA_AR_ARGS)
-ArSupportsAtFile_STAGE0 = $(ArSupportsAtFile)
+ArSupportsAtFile_STAGE0 = @ArSupportsAtFile_STAGE0@
 ArSupportsAtFile_STAGE1 = $(ArSupportsAtFile)
 ArSupportsAtFile_STAGE2 = $(ArSupportsAtFile)
 ArSupportsAtFile_STAGE3 = $(ArSupportsAtFile)
index 86f9323..9a66d1b 100644 (file)
@@ -63,6 +63,11 @@ ifeq "$3" "0"
 $1_$2_CONFIGURE_OPTS += $$(BOOT_PKG_CONSTRAINTS)
 endif
 
+$1_$2_CONFIGURE_OPTS += --with-gcc="$$(CC_STAGE$3)"
+$1_$2_CONFIGURE_OPTS += --configure-option=--with-cc="$$(CC_STAGE$3)"
+$1_$2_CONFIGURE_OPTS += --with-ar="$$(AR_STAGE$3)"
+$1_$2_CONFIGURE_OPTS += --with-ranlib="$$(RANLIB)"
+
 ifneq "$$(BINDIST)" "YES"
 ifneq "$$(NO_GENERATED_MAKEFILE_RULES)" "YES"
 $1/$2/inplace-pkg-config : $1/$2/package-data.mk
@@ -72,7 +77,7 @@ $1/$2/build/autogen/cabal_macros.h : $1/$2/package-data.mk
 # for our build system, and registers the package for use in-place in
 # the build tree.
 $1/$2/package-data.mk : $$(GHC_CABAL_INPLACE) $$($1_$2_GHC_PKG_DEP) $1/$$($1_PACKAGE).cabal $$(wildcard $1/configure) $$($1_$2_HC_CONFIG_DEP)
-       "$$(GHC_CABAL_INPLACE)" configure --with-ghc="$$($1_$2_HC_CONFIG)" --with-ghc-pkg="$$($1_$2_GHC_PKG)" --with-gcc="$$(WhatGccIsCalled)" --configure-option=--with-cc="$$(WhatGccIsCalled)" $$($1_CONFIGURE_OPTS) $$($1_$2_CONFIGURE_OPTS) -- $2 $1
+       "$$(GHC_CABAL_INPLACE)" configure --with-ghc="$$($1_$2_HC_CONFIG)" --with-ghc-pkg="$$($1_$2_GHC_PKG)" $$($1_CONFIGURE_OPTS) $$($1_$2_CONFIGURE_OPTS) -- $2 $1
 ifeq "$$($1_$2_PROG)" ""
 ifneq "$$($1_$2_REGISTER_PACKAGE)" "NO"
        "$$($1_$2_GHC_PKG)" update --force $$($1_$2_GHC_PKG_OPTS) $1/$2/inplace-pkg-config
index bba73a8..a4a0b57 100644 (file)
@@ -49,7 +49,7 @@ $1/$2/build/%.$$($3_osuf) : $1/$2/build/%.c
        "$$($1_$2_CC)" $$($1_$2_$3_ALL_CC_OPTS) -c $$< -o $$@
 
 $1/$2/build/%.$$($3_osuf) : $1/$2/build/%.$$($3_way_)s
-       "$$(AS)" $$($1_$2_$3_ALL_AS_OPTS) -o $$@ $$<
+       "$$($1_$2_AS)" $$($1_$2_$3_ALL_AS_OPTS) -o $$@ $$<
 
 $1/$2/build/%.$$($3_osuf) : $1/%.S | $$$$(dir $$$$@)/.
        "$$($1_$2_CC)" $$($1_$2_$3_ALL_CC_OPTS) -c $$< -o $$@
index 7873157..177ca25 100644 (file)
@@ -17,6 +17,7 @@ $(call profStart, package-config($1,$2,$3))
 
 $1_$2_HC = $$(GHC_STAGE$3)
 $1_$2_CC = $$(CC_STAGE$3)
+$1_$2_AS = $$(AS_STAGE$3)
 $1_$2_AR = $$(AR_STAGE$3)
 $1_$2_AR_OPTS = $$(AR_OPTS_STAGE$3)
 $1_$2_EXTRA_AR_ARGS = $$(EXTRA_AR_ARGS_STAGE$3)
index 6433957..5cc10dc 100644 (file)
@@ -74,7 +74,6 @@ install_$1_$2_wrapper:
        echo 'datadir="$$(datadir)"'                             >> "$$(WRAPPER)"
        echo 'bindir="$$(bindir)"'                               >> "$$(WRAPPER)"
        echo 'topdir="$$(topdir)"'                               >> "$$(WRAPPER)"
-       echo 'pgmgcc="$$(WhatGccIsCalled)"'                      >> "$$(WRAPPER)"
        $$($1_$2_SHELL_WRAPPER_EXTRA)
        $$($1_$2_INSTALL_SHELL_WRAPPER_EXTRA)
        cat $$($1_$2_SHELL_WRAPPER_NAME)                         >> "$$(WRAPPER)"
index f4e922a..5d4e1d3 100644 (file)
@@ -1,4 +1,8 @@
 [("GCC extra via C opts", "@GccExtraViaCOpts@"),
  ("C compiler command", "@WhatGccIsCalled@"),
+ ("C compiler flags", "@CONF_CC_OPTS_STAGE2@"),
+ ("ar command", "@ArCmd@"),
+ ("ar flags", "@ArArgs@"),
+ ("ar supports at file", "@ArSupportsAtFile@"),
  ("perl command", "@PerlCmd@")]
 
index 7ccc71d..5dc6a40 100755 (executable)
--- a/sync-all
+++ b/sync-all
@@ -310,20 +310,14 @@ sub scmall {
             if (-d "$localpath/.git") {
                 die "Found both _darcs and .git in $localpath";
             }
-            else {
-                $scm = "darcs";
-            }
-        }
-        else {
-            if (-d "$localpath/.git") {
-                $scm = "git";
-            }
-            elsif ($tag eq "") {
-                die "Required repo $localpath is missing";
-            }
-            else {
-                message "== $localpath repo not present; skipping";
-            }
+            $scm = "darcs";
+        } elsif (-d "$localpath/.git") {
+            $scm = "git";
+        } elsif ($tag eq "") {
+            die "Required repo $localpath is missing";
+        } else {
+             message "== $localpath repo not present; skipping";
+             next;
         }
 
         # Work out the arguments we should give to the SCM
@@ -383,6 +377,12 @@ sub scmall {
             }
             scm ($localpath, $scm, @scm_args, @args);
         }
+        elsif ($command =~ /^checkout$/) {
+            # Not all repos are necessarily branched, so ignore failure
+            $ignore_failure = 1;
+            scm ($localpath, $scm, "checkout", @args)
+                unless $scm eq "darcs";
+        }
         elsif ($command =~ /^grep$/) {
             # Hack around 'git grep' failing if there are no matches
             $ignore_failure = 1;
@@ -429,6 +429,7 @@ Supported commands:
  * remote add <branch-name>
  * remote rm <branch-name>
  * remote set-url [--push] <branch-name>
+ * checkout
  * grep
  * clean
  * reset