diff --git a/aclocal.m4 b/aclocal.m4
index d873034..b1c5bd1 100644
--- a/aclocal.m4
+++ b/aclocal.m4
@@ -202,6 +202,9 @@ AC_DEFUN([FPTOOLS_SET_HASKELL_PLATFORM_VARS],
         darwin)
             test -z "[$]2" || eval "[$]2=OSDarwin"
             ;;
+        darwin10)
+            test -z "[$]2" || eval "[$]2=OSDarwin"
+            ;;
         solaris2)
             test -z "[$]2" || eval "[$]2=OSSolaris2"
             ;;
@@ -699,7 +702,7 @@ AC_CACHE_CHECK([leading underscore in symbol names], [fptools_cv_leading_undersc
 #
 # Another hack: cygwin doesn't come with nlist.h , so we hardwire
 # the underscoredness of that "platform"
-case $HostPlatform in
+case $TargetPlatform in
 *openbsd*) # x86 openbsd is ELF from 3.4 >, meaning no leading uscore
   case $build in
     i386-*2\.@<:@0-9@:>@ | i386-*3\.@<:@0-3@:>@ ) fptools_cv_leading_underscore=yes ;;
@@ -712,6 +715,7 @@ x86_64-unknown-mingw32) fptools_cv_leading_underscore=no;;
 
     # HACK: Apple doesn't seem to provide nlist in the 64-bit-libraries
 x86_64-apple-darwin*) fptools_cv_leading_underscore=yes;;
+arm-apple-darwin*) fptools_cv_leading_underscore=yes;;
 
 *) AC_RUN_IFELSE([AC_LANG_SOURCE([[#ifdef HAVE_NLIST_H
 #include <nlist.h>
@@ -1931,7 +1935,7 @@ case "$1" in
     $2="linux"
     ;;
   # As far as I'm aware, none of these have relevant variants
-  freebsd|netbsd|openbsd|dragonfly|osf1|osf3|hpux|linuxaout|kfreebsdgnu|freebsd2|solaris2|cygwin32|mingw32|darwin|gnu|nextstep2|nextstep3|sunos4|ultrix|irix|aix|haiku)
+  freebsd|netbsd|openbsd|dragonfly|osf1|osf3|hpux|linuxaout|kfreebsdgnu|freebsd2|solaris2|cygwin32|mingw32|darwin|darwin10|gnu|nextstep2|nextstep3|sunos4|ultrix|irix|aix|haiku)
     $2="$1"
     ;;
   freebsd*) # like i686-gentoo-freebsd7
diff --git a/alien b/alien
new file mode 100755
index 0000000..e57d770
--- /dev/null
+++ b/alien
@@ -0,0 +1,13 @@
+#!/bin/bash
+case $1 in
+    compile)
+        echo '>>>COMPILE>>>' $LOCAL_GCC $LOCAL_CPPFLAGS $LOCAL_CFLAGS "${@:2}"
+        exec $LOCAL_GCC $LOCAL_CPPFLAGS $LOCAL_CFLAGS "${@:2}"
+        ;;
+    run)
+        exec "${@:2}"
+        ;;
+    *)
+        echo "Unknown alien command: $1"
+        exit 1
+esac
diff --git a/bin/arm-apple-darwin10-ar b/bin/arm-apple-darwin10-ar
new file mode 100755
index 0000000..958b36b
--- /dev/null
+++ b/bin/arm-apple-darwin10-ar
@@ -0,0 +1,2 @@
+#!/bin/sh
+exec ar "$@"
diff --git a/bin/arm-apple-darwin10-gcc b/bin/arm-apple-darwin10-gcc
new file mode 100755
index 0000000..d9fb4d9
--- /dev/null
+++ b/bin/arm-apple-darwin10-gcc
@@ -0,0 +1,2 @@
+#!/bin/sh
+exec $TARGET_GCC "$@"
diff --git a/bin/arm-apple-darwin10-ld b/bin/arm-apple-darwin10-ld
new file mode 100755
index 0000000..ea76e85
--- /dev/null
+++ b/bin/arm-apple-darwin10-ld
@@ -0,0 +1,2 @@
+#!/bin/sh
+exec $TARGET_LD "$@"
diff --git a/bin/arm-apple-darwin10-nm b/bin/arm-apple-darwin10-nm
new file mode 100755
index 0000000..715ffbb
--- /dev/null
+++ b/bin/arm-apple-darwin10-nm
@@ -0,0 +1,2 @@
+#!/bin/sh
+exec $TARGET_BIN/nm "$@"
diff --git a/bin/arm-apple-darwin10-ranlib b/bin/arm-apple-darwin10-ranlib
new file mode 100755
index 0000000..2ed1ff2
--- /dev/null
+++ b/bin/arm-apple-darwin10-ranlib
@@ -0,0 +1,2 @@
+#!/bin/sh
+exec ranlib "$@"
diff --git a/compiler/deSugar/DsForeign.lhs b/compiler/deSugar/DsForeign.lhs
index be66b07..99b23c7 100644
--- a/compiler/deSugar/DsForeign.lhs
+++ b/compiler/deSugar/DsForeign.lhs
@@ -93,7 +93,7 @@ dsForeigns fos = do
       return (h, c, [], bs)
 
    do_decl (ForeignExport (L _ id) _ co (CExport (CExportStatic ext_nm cconv))) = do
-      (h, c, _, _) <- dsFExport id co ext_nm cconv False
+      (h, c, _, _) <- dsFExport id co ext_nm cconv False 32
       return (h, c, [id], [])
 \end{code}
 
@@ -158,8 +158,8 @@ dsCImport id co (CFunction target) cconv@PrimCallConv safety _
   = dsPrimCall id co (CCall (CCallSpec target cconv safety))
 dsCImport id co (CFunction target) cconv safety mHeader
   = dsFCall id co (CCall (CCallSpec target cconv safety)) mHeader
-dsCImport id co CWrapper cconv _ _
-  = dsFExportDynamic id co cconv
+dsCImport id co (CWrapper poolCapacity) cconv _ _
+  = dsFExportDynamic id co cconv poolCapacity
 
 -- For stdcall labels, if the type was a FunPtr or newtype thereof,
 -- then we need to calculate the size of the arguments in order to add
@@ -331,13 +331,14 @@ dsFExport :: Id                 -- Either the exported Id,
           -> Bool               -- True => foreign export dynamic
                                 --         so invoke IO action that's hanging off
                                 --         the first argument's stable pointer
+          -> Int                -- iPhone: Adjustor pool capacity
           -> DsM ( SDoc         -- contents of Module_stub.h
                  , SDoc         -- contents of Module_stub.c
                  , String       -- string describing type to pass to createAdj.
                  , Int          -- size of args to stub function
                  )
 
-dsFExport fn_id co ext_name cconv isDyn = do
+dsFExport fn_id co ext_name cconv isDyn poolCapacity = do
     let
        ty                              = pSnd $ coercionKind co
        (_tvs,sans_foralls)             = tcSplitForAllTys ty
@@ -360,7 +361,7 @@ dsFExport fn_id co ext_name cconv isDyn = do
     return $
       mkFExportCBits dflags ext_name
                      (if isDyn then Nothing else Just fn_id)
-                     fe_arg_tys res_ty is_IO_res_ty cconv
+                     fe_arg_tys res_ty is_IO_res_ty cconv poolCapacity
 \end{code}
 
 @foreign import "wrapper"@ (previously "foreign export dynamic") lets
@@ -397,8 +398,9 @@ f_helper(StablePtr s, HsBool b, HsInt i)
 dsFExportDynamic :: Id
                  -> Coercion
                  -> CCallConv
+                 -> Int  -- iPhone: Adjustor pool capacity
                  -> DsM ([Binding], SDoc, SDoc)
-dsFExportDynamic id co0 cconv = do
+dsFExportDynamic id co0 cconv poolCapacity = do
     fe_id <-  newSysLocalDs ty
     mod <- getModuleDs
     let
@@ -413,7 +415,7 @@ dsFExportDynamic id co0 cconv = do
         export_ty     = mkFunTy stable_ptr_ty arg_ty
     bindIOId <- dsLookupGlobalId bindIOName
     stbl_value <- newSysLocalDs stable_ptr_ty
-    (h_code, c_code, typestring, args_size) <- dsFExport id (Refl export_ty) fe_nm cconv True
+    (h_code, c_code, typestring, args_size) <- dsFExport id (Refl export_ty) fe_nm cconv True poolCapacity
     let
          {-
           The arguments to the external function which will
@@ -426,10 +428,12 @@ dsFExportDynamic id co0 cconv = do
                         , Var stbl_value
                         , Lit (MachLabel fe_nm mb_sz_args IsFunction)
                         , Lit (mkMachString typestring)
+                        , Lit (mkMachString $ unpackFS fe_nm)
+                        , Lit (MachLabel (fe_nm `appendFS` fsLit "_pool") Nothing IsData )
                         ]
           -- name of external entry point providing these services.
           -- (probably in the RTS.)
-        adjustor   = fsLit "createAdjustor"
+        adjustor   = fsLit "iPhoneCreateAdjustor"
 
           -- Determine the number of bytes of arguments to the stub function,
           -- so that we can attach the '@N' suffix to its label if it is a
@@ -485,12 +489,13 @@ mkFExportCBits :: DynFlags
                -> Type
                -> Bool          -- True <=> returns an IO type
                -> CCallConv
+               -> Int           -- iPhone: Number of adjustor pool entries
                -> (SDoc,
                    SDoc,
                    String,      -- the argument reps
                    Int          -- total size of arguments
                   )
-mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
+mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc poolCapacity
  = (header_bits, c_bits, type_string,
     sum [ widthInBytes (typeWidth rep) | (_,_,_,rep) <- aug_arg_info] -- all the args
          -- NB. the calculation here isn't strictly speaking correct.
@@ -520,7 +525,7 @@ mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
         | otherwise = text ('a':show n)
 
   -- generate a libffi-style stub if this is a "wrapper" and libffi is enabled
-  libffi = cLibFFI && isNothing maybe_target
+  libffi = False  -- iPhone: Use non-libffi style
 
   type_string
       -- libffi needs to know the result type too:
@@ -533,7 +538,7 @@ mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
   -- add some auxiliary args; the stable ptr in the wrapper case, and
   -- a slot for the dummy return address in the wrapper + ccall case
   aug_arg_info
-    | isNothing maybe_target = stable_ptr_arg : insertRetAddr dflags cc arg_info
+    | isNothing maybe_target = stable_ptr_arg : arg_info  -- iPhone: No dummy return address
     | otherwise              = arg_info
 
   stable_ptr_arg =
@@ -562,12 +567,19 @@ mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
   -- Now we can cook up the prototype for the exported function.
   pprCconv = ccallConvAttribute cc
 
-  header_bits = ptext (sLit "extern") <+> fun_proto <> semi
-
-  fun_args
-    | null aug_arg_info = text "void"
+  header_bits = ptext (sLit "extern") <+> fun_proto <> semi $$
+         (if isNothing maybe_target
+             then text "extern" <> pool_decl <> semi
+             else empty)
+
+  mkEntryName idx = text (unpackFS c_nm ++ "_entry" ++ show idx)
+  
+  fun_args = fun_args_ aug_arg_info
+  
+  fun_args_ args
+    | null args = text "void"
     | otherwise         = hsep $ punctuate comma
-                               $ map (\(nm,ty,_,_) -> ty <+> nm) aug_arg_info
+                               $ map (\(nm,ty,_,_) -> ty <+> nm) args
 
   fun_proto
     | libffi
@@ -607,6 +619,8 @@ mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
           Nothing -> empty
           Just hs_fn -> text "extern StgClosure " <> ppr hs_fn <> text "_closure" <> semi
 
+  pool_decl =
+      text "void* " <> ftext c_nm <> text "_pool[" <> text (show (poolCapacity*2+1)) <> text "]"
 
   -- finally, the whole darn thing
   c_bits =
@@ -643,7 +657,38 @@ mkFExportCBits dflags c_nm maybe_target arg_htys res_hty is_IO_res_ty cc
                        ptext (sLit "resp = cret;")
                   else ptext (sLit "return cret;")
      , rbrace
-     ]
+     ] $$ (
+         if isNothing maybe_target
+             then pool
+             else empty)
+
+  pool =
+    -- iPhone: Due to Apple's code signing policy, we can't do self-modifying
+    -- code on the iPhone.  So instead, we pre-compile a pool of adjustors.
+    text "extern StgStablePtr iPhoneLookupAdjustor(void*)" <> semi $$
+    text "extern " <> pool_decl <> semi $$
+    vcat (
+        flip map [0..poolCapacity-1] $ \poolIdx ->
+            cResType <+> mkEntryName poolIdx <> parens (fun_args_ arg_info) $$
+            lbrace $$ (
+                (if res_hty_is_unit
+                    then empty
+                    else text "return ") <>
+                ftext c_nm <> parens (
+                    text "iPhoneLookupAdjustor" <> parens (
+                        ftext c_nm <> text "_pool+" <> text (show (poolIdx :: Int)) <> text "*2")
+                    <> (if null arg_info
+                        then empty
+                        else comma <+> hsep (punctuate comma $ map (\(nm,ty,_,_) -> nm) arg_info))
+                ) <> semi
+            ) $$ rbrace
+    ) $$
+    pool_decl <> text " = " <> lbrace $$
+    vcat (punctuate comma $
+            flip map [0..poolCapacity-1] $ \poolIdx ->
+                text "  " <> mkEntryName poolIdx <> comma <+> text "NULL"
+        ) <> comma $$
+    text "  NULL" <> rbrace <> semi
 
 
 foreignExportInitialiser :: Id -> SDoc
@@ -711,6 +756,7 @@ typeTyCon ty = case tcSplitTyConApp_maybe (repType ty) of
                  Just (tc,_) -> tc
                  Nothing     -> pprPanic "DsForeign.typeTyCon" (ppr ty)
 
+{-
 insertRetAddr :: DynFlags -> CCallConv
               -> [(SDoc, SDoc, Type, CmmType)]
               -> [(SDoc, SDoc, Type, CmmType)]
@@ -745,6 +791,7 @@ insertRetAddr dflags CCallConv args
           ret_addr_arg : args
     where platform = targetPlatform dflags
 insertRetAddr _ _ args = args
+-}
 
 ret_addr_arg :: (SDoc, SDoc, Type, CmmType)
 ret_addr_arg = (text "original_return_addr", text "void*", undefined,
diff --git a/compiler/deSugar/DsMeta.hs b/compiler/deSugar/DsMeta.hs
index 6d1520b..a14281e 100644
--- a/compiler/deSugar/DsMeta.hs
+++ b/compiler/deSugar/DsMeta.hs
@@ -381,7 +381,7 @@ repForD (L loc (ForeignImport name typ _ (CImport cc s mch cis)))
     conv_cimportspec (CFunction DynamicTarget) = return "dynamic"
     conv_cimportspec (CFunction (StaticTarget fs _ True)) = return (unpackFS fs)
     conv_cimportspec (CFunction (StaticTarget _  _ False)) = panic "conv_cimportspec: values not supported yet"
-    conv_cimportspec CWrapper = return "wrapper"
+    conv_cimportspec (CWrapper poolCapacity) = return ("wrapper "++show poolCapacity)
     static = case cis of
                  CFunction (StaticTarget _ _ _) -> "static "
                  _ -> ""
diff --git a/compiler/hsSyn/HsDecls.lhs b/compiler/hsSyn/HsDecls.lhs
index cf1c2c9..faeb861 100644
--- a/compiler/hsSyn/HsDecls.lhs
+++ b/compiler/hsSyn/HsDecls.lhs
@@ -991,8 +991,9 @@ data ForeignImport = -- import of a C entity
 --
 data CImportSpec = CLabel    CLabelString     -- import address of a C label
                  | CFunction CCallTarget      -- static or dynamic function
-                 | CWrapper                   -- wrapper to expose closures
+                 | CWrapper  Int              -- wrapper to expose closures
                                               -- (former f.e.d.)
+                                              -- iPhone: With adjustor pool capacity
   deriving (Data, Typeable)
 
 -- specification of an externally exported entity in dependence on the calling
@@ -1030,7 +1031,7 @@ instance Outputable ForeignImport where
         <+> ppr lbl
       pprCEntity (CFunction (DynamicTarget)) =
         ptext (sLit "dynamic")
-      pprCEntity (CWrapper) = ptext (sLit "wrapper")
+      pprCEntity (CWrapper cap) = ptext (sLit "wrapper ") <+> ptext (sLit $ show cap)
 
 instance Outputable ForeignExport where
   ppr (CExport  (CExportStatic lbl cconv)) = 
diff --git a/compiler/llvmGen/Llvm.hs b/compiler/llvmGen/Llvm.hs
index 32df9e3..3f8ae2f 100644
--- a/compiler/llvmGen/Llvm.hs
+++ b/compiler/llvmGen/Llvm.hs
@@ -32,7 +32,7 @@ module Llvm (
 
         -- * Variables and Type System
         LlvmVar(..), LlvmStatic(..), LlvmLit(..), LlvmType(..),
-        LlvmAlias, LMGlobal, LMString, LMSection, LMAlign,
+        LlvmAlias, LMGlobal, LMString, LMSection, LMAlign, Volatility(..),
 
         -- ** Some basic types
         i64, i32, i16, i8, i1, i8Ptr, llvmWord, llvmWordPtr,
diff --git a/compiler/llvmGen/Llvm/AbsSyn.hs b/compiler/llvmGen/Llvm/AbsSyn.hs
index 9133447..ec96dc5 100644
--- a/compiler/llvmGen/Llvm/AbsSyn.hs
+++ b/compiler/llvmGen/Llvm/AbsSyn.hs
@@ -207,7 +207,7 @@ data LlvmExpression
   {- |
     Load the value at location ptr
   -}
-  | Load LlvmVar
+  | Load Volatility LlvmVar
 
   {- |
     Navigate in an structure, selecting elements
diff --git a/compiler/llvmGen/Llvm/PpLlvm.hs b/compiler/llvmGen/Llvm/PpLlvm.hs
index c217778..359202f 100644
--- a/compiler/llvmGen/Llvm/PpLlvm.hs
+++ b/compiler/llvmGen/Llvm/PpLlvm.hs
@@ -235,7 +235,7 @@ ppLlvmExpression expr
         Cast       op from to       -> ppCast op from to
         Compare    op left right    -> ppCmpOp op left right
         GetElemPtr inb ptr indexes  -> ppGetElementPtr inb ptr indexes
-        Load       ptr              -> ppLoad ptr
+        Load       vol ptr          -> ppLoad vol ptr
         Malloc     tp amount        -> ppMalloc tp amount
         Phi        tp precessors    -> ppPhi tp precessors
         Asm        asm c ty v se sk -> ppAsm asm c ty v se sk
@@ -316,8 +316,9 @@ ppSyncOrdering SyncRelease   = text "release"
 ppSyncOrdering SyncAcqRel    = text "acq_rel"
 ppSyncOrdering SyncSeqCst    = text "seq_cst"
 
-ppLoad :: LlvmVar -> Doc
-ppLoad var = text "load" <+> texts var
+ppLoad :: Volatility -> LlvmVar -> Doc
+ppLoad NotVolatile var = text "load" <+> texts var
+ppLoad Volatile var = text "load volatile" <+> texts var
 
 
 ppStore :: LlvmVar -> LlvmVar -> Doc
diff --git a/compiler/llvmGen/Llvm/Types.hs b/compiler/llvmGen/Llvm/Types.hs
index 35de40b..e753e8f 100644
--- a/compiler/llvmGen/Llvm/Types.hs
+++ b/compiler/llvmGen/Llvm/Types.hs
@@ -820,3 +820,5 @@ fixEndian = id
 fixEndian = reverse
 #endif
 
+data Volatility = Volatile | NotVolatile deriving (Eq, Show)
+
diff --git a/compiler/llvmGen/LlvmCodeGen/CodeGen.hs b/compiler/llvmGen/LlvmCodeGen/CodeGen.hs
index 74311e0..b345dd7 100644
--- a/compiler/llvmGen/LlvmCodeGen/CodeGen.hs
+++ b/compiler/llvmGen/LlvmCodeGen/CodeGen.hs
@@ -318,7 +318,7 @@ genCall env target res args ret = do
 
                     (v2, s2) <- doExpr ty $ Cast op v1 ty
                     let s3 = Store v2 vreg
-                    return (env3, allStmts `snocOL` s2 `snocOL` s3
+                    return (env3, allStmts `snocOL` s2 `snocOL` Comment [fsLit "blah 1"] `snocOL` s3
                                 `appOL` retStmt, top1 ++ top2 ++ top3)
 
 
@@ -339,7 +339,7 @@ getFunPtr env funTy targ = case targ of
                               ++ " call! (" ++ show (ty) ++ ")"
 
         (v2,s1) <- doExpr (pLift fty) $ Cast cast v1 (pLift fty)
-        return (env', v2, stmts `snocOL` s1, top)
+        return (env', v2, stmts `snocOL` Comment [fsLit "blah 2"] `snocOL` s1, top)
 
     CmmPrim mop _ -> litCase $ cmmPrimOpFunctions env mop
 
@@ -357,9 +357,12 @@ getFunPtr env funTy targ = case targ of
                     let fty@(LMFunction sig) = funTy name
                         fun = LMGlobalVar name (pLift ty') (funcLinkage sig)
                                     Nothing Nothing False
-                    (v1, s1) <- doExpr (pLift fty)
-                                    $ Cast LM_Bitcast fun (pLift fty)
-                    return  (env, v1, unitOL s1, [])
+                    (v1, s1, ldata) <- indirectly name (pLift fty) fun False
+                    {-
+                    (v2, s2) <- doExpr (pLift fty)
+                                $ Cast LM_Bitcast v1 (pLift fty)
+                                -}
+                    return  (env, v1, s1 `snocOL` Comment [fsLit "blah 3"], ldata)
 
                 Nothing -> do
                     -- label not in module, create external reference
@@ -390,7 +393,7 @@ arg_vars env (CmmHinted e AddrHint:rest) (vars, stmts, tops)
                            ++ show a ++ ")"
 
        (v2, s1) <- doExpr i8Ptr $ Cast op v1 i8Ptr
-       arg_vars env' rest (vars ++ [v2], stmts `appOL` stmts' `snocOL` s1,
+       arg_vars env' rest (vars ++ [v2], stmts `appOL` stmts' `snocOL` Comment [fsLit "blah 4"] `snocOL` s1,
                                tops ++ top')
 
 arg_vars env (CmmHinted e _:rest) (vars, stmts, tops)
@@ -517,7 +520,7 @@ genJump env expr live = do
     (stgRegs, stgStmts) <- funEpilogue env live
     let s2 = Expr $ Call TailCall v1 stgRegs llvmStdFunAttrs
     let s3 = Return Nothing
-    return (env', stmts `snocOL` s1 `appOL` stgStmts `snocOL` s2 `snocOL` s3,
+    return (env', stmts `snocOL` s1 `appOL` stgStmts `snocOL` s2 `snocOL` Comment [fsLit "blah 5"] `snocOL` s3,
             top)
 
 
@@ -585,7 +588,7 @@ genStore_fast env addr r n val
     in case isPointer grt && rem == 0 of
             True -> do
                 (env', vval,  stmts, top) <- exprToVar env val
-                (gv,  s1) <- doExpr grt $ Load gr
+                (gv,  s1) <- doExpr grt $ Load NotVolatile gr
                 (ptr, s2) <- doExpr grt $ GetElemPtr True gv [toI32 ix]
                 -- We might need a different pointer type, so check
                 case pLower grt == getVarType vval of
@@ -601,7 +604,7 @@ genStore_fast env addr r n val
                          (ptr', s3) <- doExpr ty $ Cast LM_Bitcast ptr ty
                          let s4 = MetaStmt meta $ Store vval ptr'
                          return (env',  stmts `snocOL` s1 `snocOL` s2
-                                 `snocOL` s3 `snocOL` s4, top)
+                                 `snocOL` s3 `snocOL` Comment [fsLit "blah 6"] `snocOL` s4, top)
 
             -- If its a bit type then we use the slow method since
             -- we can't avoid casting anyway.
@@ -728,12 +731,12 @@ exprToVarOpt env opt e = case e of
     -- reg pointer, call getCmmReg directly.
     CmmReg r -> do
         let (env', vreg, stmts, top) = getCmmReg env r
-        (v1, s1) <- doExpr (pLower $ getVarType vreg) $ Load vreg
+        (v1, s1) <- doExpr (pLower $ getVarType vreg) $ Load NotVolatile vreg
         case (isPointer . getVarType) v1 of
              True  -> do
                  -- Cmm wants the value, so pointer types must be cast to ints
                  (v2, s2) <- doExpr llvmWord $ Cast LM_Ptrtoint v1 llvmWord
-                 return (env', v2, stmts `snocOL` s1 `snocOL` s2, top)
+                 return (env', v2, stmts `snocOL` s1 `snocOL` s2 `snocOL` Comment [fsLit "blah 10"], top)
 
              False -> return (env', v1, stmts `snocOL` s1, top)
 
@@ -867,10 +870,10 @@ genMachOp_fast env opt op r n e
         (ix,rem) = n `divMod` ((llvmWidthInBits . pLower) grt  `div` 8)
     in case isPointer grt && rem == 0 of
             True -> do
-                (gv,  s1) <- doExpr grt $ Load gr
+                (gv,  s1) <- doExpr grt $ Load NotVolatile gr
                 (ptr, s2) <- doExpr grt $ GetElemPtr True gv [toI32 ix]
                 (var, s3) <- doExpr llvmWord $ Cast LM_Ptrtoint ptr llvmWord
-                return (env, var, unitOL s1 `snocOL` s2 `snocOL` s3, [])
+                return (env, var, unitOL s1 `snocOL` s2 `snocOL` s3 `snocOL` Comment [fsLit "blah 11"], [])
 
             False -> genMachOp_slow env opt op e
 
@@ -1067,13 +1070,13 @@ genLoad_fast env e r n ty =
         (ix,rem) = n `divMod` ((llvmWidthInBits . pLower) grt  `div` 8)
     in case isPointer grt && rem == 0 of
             True  -> do
-                (gv,  s1) <- doExpr grt $ Load gr
+                (gv,  s1) <- doExpr grt $ Load NotVolatile gr
                 (ptr, s2) <- doExpr grt $ GetElemPtr True gv [toI32 ix]
                 -- We might need a different pointer type, so check
                 case grt == ty' of
                      -- were fine
                      True -> do
-                         (var, s3) <- doExpr ty' (MetaExpr meta $ Load ptr)
+                         (var, s3) <- doExpr ty' (MetaExpr meta $ Load NotVolatile ptr)
                          return (env, var, unitOL s1 `snocOL` s2 `snocOL` s3,
                                      [])
 
@@ -1081,8 +1084,8 @@ genLoad_fast env e r n ty =
                      False -> do
                          let pty = pLift ty'
                          (ptr', s3) <- doExpr pty $ Cast LM_Bitcast ptr pty
-                         (var, s4) <- doExpr ty' (MetaExpr meta $ Load ptr')
-                         return (env, var, unitOL s1 `snocOL` s2 `snocOL` s3
+                         (var, s4) <- doExpr ty' (MetaExpr meta $ Load NotVolatile ptr')
+                         return (env, var, unitOL s1 `snocOL` s2 `snocOL` s3 `snocOL` Comment [fsLit "blah 7"]
                                     `snocOL` s4, [])
 
             -- If its a bit type then we use the slow method since
@@ -1098,14 +1101,14 @@ genLoad_slow env e ty meta = do
     case getVarType iptr of
          LMPointer _ -> do
                     (dvar, load) <- doExpr (cmmToLlvmType ty)
-                                           (MetaExpr meta $ Load iptr)
+                                           (MetaExpr meta $ Load NotVolatile iptr)
                     return (env', dvar, stmts `snocOL` load, tops)
 
          i@(LMInt _) | i == llvmWord -> do
                     let pty = LMPointer $ cmmToLlvmType ty
                     (ptr, cast)  <- doExpr pty $ Cast LM_Inttoptr iptr pty
                     (dvar, load) <- doExpr (cmmToLlvmType ty)
-                                           (MetaExpr meta $ Load ptr)
+                                           (MetaExpr meta $ Load NotVolatile ptr)
                     return (env', dvar, stmts `snocOL` cast `snocOL` load, tops)
 
          other -> pprPanic "exprToVar: CmmLoad expression is not right type!"
@@ -1143,6 +1146,35 @@ allocReg (CmmLocal (LocalReg un ty))
 allocReg _ = panic $ "allocReg: Global reg encountered! Global registers should"
                     ++ " have been handled elsewhere!"
 
+-- iPhone: put references to external symbols into the data segment,
+-- otherwise if the iPhone loader sees certain definitions, like this one...
+--
+-- foreign import ccall unsafe "static stdlib.h &free"
+--       c_free_finalizer :: FunPtr (Ptr Word8 -> IO ())
+--
+-- ...then, presumably because free is external to the program, it tries
+-- to resolve it at runtime. Unfortunately, this makes the text segment
+-- writeable, and the dyld loader fails, because this operation is not
+-- allowed on iPhone due to Apple's policy against self-modifying code.
+--
+-- Here we work around it by fetching the reference to the external symbol
+-- from the data segment. This is really only necessary in the foreign
+-- import case, so that's an improvement we could make.
+indirectly :: LMString -> LlvmType -> LlvmVar -> Bool
+           -> UniqSM (LlvmVar, OrdList LlvmStatement, [LlvmCmmDecl])
+indirectly label lmty var isInteger = do
+    refLabel <- ((label `appendFS` fsLit "_ref_" `appendFS`) . (fsLit . show)) `fmap` getUniqueUs
+    let refTy = LMStruct [lmty]
+        ref = LMGlobalVar refLabel (LMPointer refTy)
+                Internal (Just $ fsLit "__DATA,__data") Nothing False
+        cast = if isInteger then LMPtoI else LMBitc
+        refGlob = (ref, Just $ LMStaticStruc [cast (LMStaticPointer var) lmty] refTy)
+        ldata = [CmmData Data [([refGlob], [])]]
+    (v1, s1) <- doExpr (LMPointer lmty) $ GetElemPtr False ref [toIWord 0, toIWord 0]
+    -- If we don't use Volatile here, then llvm can optimize it back into the .text
+    -- segment, and the problem isn't solved.
+    (v, s2) <- doExpr lmty $ Load Volatile v1
+    return (v, unitOL s1 `snocOL` s2, ldata)
 
 -- | Generate code for a literal
 genLit :: LlvmEnv -> CmmLit -> UniqSM ExprData
@@ -1161,18 +1193,17 @@ genLit env cmm@(CmmLabel l)
             -- Make generic external label definition and then pointer to it
             Nothing -> do
                 let glob@(var, _) = genStringLabelRef label
-                let ldata = [CmmData Data [([glob], [])]]
-                let env' = funInsert label (pLower $ getVarType var) env
-                (v1, s1) <- doExpr lmty $ Cast LM_Ptrtoint var llvmWord
-                return (env', v1, unitOL s1, ldata)
+                    env' = funInsert label (pLower $ getVarType var) env
+                (v1, s1, ldata) <- indirectly label lmty var True
+                return (env', v1, s1 `snocOL` Comment [fsLit "blah 9a"], [CmmData Data [([glob], [])]] ++ ldata)
 
             -- Referenced data exists in this module, retrieve type and make
             -- pointer to it.
             Just ty' -> do
                 let var = LMGlobalVar label (LMPointer ty')
                             ExternallyVisible Nothing Nothing False
-                (v1, s1) <- doExpr lmty $ Cast LM_Ptrtoint var llvmWord
-                return (env, v1, unitOL s1, [])
+                (v1, s1, ldata) <- indirectly label lmty var True
+                return (env, v1, s1 `snocOL` Comment [fsLit "blah 9b"], ldata)
 
 genLit env (CmmLabelOff label off) = do
     (env', vlbl, stmts, stat) <- genLit env (CmmLabel label)
@@ -1231,7 +1262,7 @@ funEpilogue env (Just live) | dopt Opt_RegLiveness (getDflags env) = do
   where
     loadExpr r | r `elem` alwaysLive || r `elem` live = do
         let reg  = lmGlobalRegVar r
-        (v,s) <- doExpr (pLower $ getVarType reg) $ Load reg
+        (v,s) <- doExpr (pLower $ getVarType reg) $ Load NotVolatile reg
         return (v, unitOL s)
     loadExpr r = do
         let ty = (pLower . getVarType $ lmGlobalRegVar r)
@@ -1245,7 +1276,7 @@ funEpilogue _ _ = do
   where
     loadExpr r = do
         let reg  = lmGlobalRegVar r
-        (v,s) <- doExpr (pLower $ getVarType reg) $ Load reg
+        (v,s) <- doExpr (pLower $ getVarType reg) $ Load NotVolatile reg
         return (v, unitOL s)
 
 
@@ -1291,7 +1322,7 @@ getHsFunc env lbl
                             Nothing Nothing False
             (v1, s1) <- doExpr (pLift llvmFunTy) $
                             Cast LM_Bitcast fun (pLift llvmFunTy)
-            return (env, v1, unitOL s1, [])
+            return (env, v1, unitOL s1 `snocOL` Comment [fsLit "blah 8"], [])
 
         -- label not in module, create external reference
         Nothing  -> do
diff --git a/compiler/llvmGen/LlvmCodeGen/Ppr.hs b/compiler/llvmGen/LlvmCodeGen/Ppr.hs
index 187d1ec..5e880f1 100644
--- a/compiler/llvmGen/LlvmCodeGen/Ppr.hs
+++ b/compiler/llvmGen/LlvmCodeGen/Ppr.hs
@@ -67,6 +67,9 @@ moduleLayout =
 #if linux_TARGET_OS
     text "target datalayout = \"e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:128-a0:0:64-n32\""
     $+$ text "target triple = \"arm-unknown-linux-gnueabi\""
+#elif darwin10_TARGET_OS
+    text "target datalayout = \"e-p:32:32:32-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:64:128-a0:0:64-n32\""
+    $+$ text "target triple = \"arm-apple-darwin10\""
 #endif
 
 #else
diff --git a/compiler/main/DriverPipeline.hs b/compiler/main/DriverPipeline.hs
index 335df4f..8d6f108 100644
--- a/compiler/main/DriverPipeline.hs
+++ b/compiler/main/DriverPipeline.hs
@@ -1174,7 +1174,8 @@ runPhase As input_fn dflags
         let whichAsProg | hscTarget dflags == HscLlvm &&
                           platformOS (targetPlatform dflags) == OSDarwin
                         = do
-                            llvmVer <- io $ figureLlvmVersion dflags
+                            --llvmVer <- io $ figureLlvmVersion dflags
+                            let llvmVer = Nothing :: Maybe Int  -- ###
                             return $ case llvmVer of
                                 -- using cGccLinkerOpts here but not clear if
                                 -- opt_c isn't a better choice
@@ -1737,7 +1738,7 @@ linkBinary dflags o_files dep_packages = do
     let
         thread_opts | WayThreaded `elem` ways = [
 #if !defined(mingw32_TARGET_OS) && !defined(freebsd_TARGET_OS) && !defined(openbsd_TARGET_OS) && !defined(netbsd_TARGET_OS) && !defined(haiku_TARGET_OS)
-                        "-lpthread"
+                        --"-lpthread"
 #endif
 #if defined(osf3_TARGET_OS)
                         , "-lexc"
@@ -1746,8 +1747,13 @@ linkBinary dflags o_files dep_packages = do
                     | otherwise               = []
 
     rc_objs <- maybeCreateManifest dflags output_fn
+    
+    let removeDynLibs opts = [ o | o <- opts,
+           case o of
+               SysTools.FileOption _ _ -> True
+               SysTools.Option opt -> opt `notElem` ["-ldl", "-liconv", "-lm"] ]
 
-    SysTools.runLink dflags (
+    SysTools.runLibtool dflags $ removeDynLibs (
                        map SysTools.Option verbFlags
                       ++ [ SysTools.Option "-o"
                          , SysTools.FileOption "" output_fn
@@ -1815,7 +1821,10 @@ exeFileName dflags
       then if null (takeExtension s)
            then s <.> "exe"
            else s
-      else s
+      else
+           let (path, file) = splitFileName s
+           in  combine path (file++".a")  -- For iPhone we must link the executable into Xcode
+
   | otherwise =
       if platformOS (targetPlatform dflags) == OSMinGW32
       then "main.exe"
diff --git a/compiler/main/Packages.lhs b/compiler/main/Packages.lhs
index cdda961..2994c0c 100644
--- a/compiler/main/Packages.lhs
+++ b/compiler/main/Packages.lhs
@@ -867,7 +867,11 @@ collectLinkOpts :: DynFlags -> [PackageConfig] -> [String]
 collectLinkOpts dflags ps = concat (map all_opts ps)
   where
         libs p     = packageHsLibs dflags p ++ extraLibraries p
-        all_opts p = map ("-l" ++) (libs p) ++ ldOptions p
+        -- on iPhone we are using libtool, which doesn't do the final link, and
+        -- which doesn't understand most ld options. Therefore we are just
+        -- discarding any specified in packages, and requiring these to be added
+        -- by hand to Xcode where necessary.
+        all_opts p = map ("-l" ++) (libs p) -- ++ ldOptions p
 
 packageHsLibs :: DynFlags -> PackageConfig -> [String]
 packageHsLibs dflags p = map (mkDynName . addSuffix) (hsLibraries p)
diff --git a/compiler/main/SysTools.lhs b/compiler/main/SysTools.lhs
index 848e02d..f417ed1 100644
--- a/compiler/main/SysTools.lhs
+++ b/compiler/main/SysTools.lhs
@@ -16,7 +16,7 @@ module SysTools (
         runUnlit, runCpp, runCc, -- [Option] -> IO ()
         runPp,                   -- [Option] -> IO ()
         runSplit,                -- [Option] -> IO ()
-        runAs, runLink,          -- [Option] -> IO ()
+        runAs, runLink, runLibtool, -- [Option] -> IO ()
         runMkDLL,
         runWindres,
         runLlvmOpt,
@@ -553,6 +553,13 @@ runLink dflags args = do
   mb_env <- getGccEnv args1
   runSomethingFiltered dflags id "Linker" p args1 mb_env
 
+runLibtool :: DynFlags -> [Option] -> IO ()
+runLibtool dflags args = do
+  let (p,args0) = ("libtool", [Option "-static"])
+      args1 = args0 ++ args
+  mb_env <- getGccEnv args1
+  runSomethingFiltered dflags id "Linker" p args1 mb_env
+
 runMkDLL :: DynFlags -> [Option] -> IO ()
 runMkDLL dflags args = do
   let (p,args0) = pgm_dll dflags
diff --git a/compiler/parser/Lexer.x b/compiler/parser/Lexer.x
index e40f7b2..f19f9f8 100644
--- a/compiler/parser/Lexer.x
+++ b/compiler/parser/Lexer.x
@@ -493,6 +493,7 @@ data Token
   | ITvect_prag
   | ITvect_scalar_prag
   | ITnovect_prag
+  | ITpoolsize_prag
   | ITctype
 
   | ITdotdot                    -- reserved symbols
@@ -2333,7 +2334,8 @@ oneWordPrags = Map.fromList([("rules", rulePrag),
                            ("ann", token ITann_prag),
                            ("vectorize", token ITvect_prag),
                            ("novectorize", token ITnovect_prag),
-                           ("ctype", token ITctype)])
+                           ("ctype", token ITctype),
+                           ("poolsize", token ITpoolsize_prag)])
 
 twoWordPrags = Map.fromList([("inline conlike", token (ITinline_prag Inline ConLike)),
                              ("notinline conlike", token (ITinline_prag NoInline ConLike)),
diff --git a/compiler/parser/Parser.y.pp b/compiler/parser/Parser.y.pp
index 759d544..c2da0d7 100644
--- a/compiler/parser/Parser.y.pp
+++ b/compiler/parser/Parser.y.pp
@@ -268,6 +268,7 @@ incorrect.
  '{-# VECTORISE_SCALAR'   { L _ ITvect_scalar_prag }
  '{-# NOVECTORISE'        { L _ ITnovect_prag }
  '{-# CTYPE'              { L _ ITctype }
+ '{-# POOLSIZE'           { L _ ITpoolsize_prag }
  '#-}'                                          { L _ ITclose_prag }
 
  '..'           { L _ ITdotdot }                        -- reserved symbols
@@ -945,13 +946,17 @@ safety :: { Safety }
         | 'safe'                        { PlaySafe }
         | 'interruptible'               { PlayInterruptible }
 
-fspec :: { Located (Located FastString, Located RdrName, LHsType RdrName) }
-       : STRING var '::' sigtypedoc     { LL (L (getLoc $1) (getSTRING $1), $2, $4) }
-       |        var '::' sigtypedoc     { LL (noLoc nilFS, $1, $3) }
+fspec :: { Located (Located FastString, Maybe Int, Located RdrName, LHsType RdrName) }
+       : STRING poolsize var '::' sigtypedoc     { LL (L (getLoc $1) (getSTRING $1), $2, $3, $5) }
+       |        poolsize var '::' sigtypedoc     { sL (comb2 $2 $>) (noLoc nilFS, $1, $2, $4) }
          -- if the entity string is missing, it defaults to the empty string;
          -- the meaning of an empty entity string depends on the calling
          -- convention
 
+poolsize :: { Maybe Int }
+          : '{-# POOLSIZE' INTEGER '#-}' { Just (fromInteger $ getINTEGER $2) }
+          | {- empty -}                  { Nothing }
+
 -----------------------------------------------------------------------------
 -- Type signatures
 
diff --git a/compiler/parser/RdrHsSyn.lhs b/compiler/parser/RdrHsSyn.lhs
index 350aedb..aced369 100644
--- a/compiler/parser/RdrHsSyn.lhs
+++ b/compiler/parser/RdrHsSyn.lhs
@@ -80,6 +80,7 @@ import Control.Applicative ((<$>))
 import Control.Monad
 import Text.ParserCombinators.ReadP as ReadP
 import Data.Char
+import Data.Maybe (fromMaybe)
 
 #include "HsVersions.h"
 \end{code}
@@ -854,25 +855,25 @@ mkInlinePragma (inl, match_info) mb_act
 --
 mkImport :: CCallConv
          -> Safety
-         -> (Located FastString, Located RdrName, LHsType RdrName)
+         -> (Located FastString, Maybe Int, Located RdrName, LHsType RdrName)
          -> P (HsDecl RdrName)
-mkImport cconv safety (L loc entity, v, ty)
+mkImport cconv safety (L loc entity, mPoolSize, v, ty)
   | cconv == PrimCallConv                      = do
   let funcTarget = CFunction (StaticTarget entity Nothing True)
       importSpec = CImport PrimCallConv safety Nothing funcTarget
   return (ForD (ForeignImport v ty noForeignImportCoercionYet importSpec))
 
   | otherwise = do
-    case parseCImport cconv safety (mkExtName (unLoc v)) (unpackFS entity) of
+    case parseCImport cconv safety mPoolSize (mkExtName (unLoc v)) (unpackFS entity) of
       Nothing         -> parseErrorSDoc loc (text "Malformed entity string")
       Just importSpec -> return (ForD (ForeignImport v ty noForeignImportCoercionYet importSpec))
 
 -- the string "foo" is ambigous: either a header or a C identifier.  The
 -- C identifier case comes first in the alternatives below, so we pick
 -- that one.
-parseCImport :: CCallConv -> Safety -> FastString -> String
+parseCImport :: CCallConv -> Safety -> Maybe Int -> FastString -> String
              -> Maybe ForeignImport
-parseCImport cconv safety nm str =
+parseCImport cconv safety mPoolSize nm str =
  listToMaybe $ map fst $ filter (null.snd) $
      readP_to_S parse str
  where
@@ -880,7 +881,7 @@ parseCImport cconv safety nm str =
        skipSpaces
        r <- choice [
           string "dynamic" >> return (mk Nothing (CFunction DynamicTarget)),
-          string "wrapper" >> return (mk Nothing CWrapper),
+          string "wrapper" >> return (mk Nothing (CWrapper $ fromMaybe 32 mPoolSize)),
           do optional (token "static" >> skipSpaces)
              ((mk Nothing <$> cimp nm) +++
               (do h <- munch1 hdr_char
@@ -925,9 +926,9 @@ parseCImport cconv safety nm str =
 -- construct a foreign export declaration
 --
 mkExport :: CCallConv
-         -> (Located FastString, Located RdrName, LHsType RdrName)
+         -> (Located FastString, Maybe Int, Located RdrName, LHsType RdrName)
          -> P (HsDecl RdrName)
-mkExport cconv (L _ entity, v, ty) = return $
+mkExport cconv (L _ entity, _, v, ty) = return $
   ForD (ForeignExport v ty noForeignExportCoercionYet (CExport (CExportStatic entity' cconv)))
   where
     entity' | nullFS entity = mkExtName (unLoc v)
diff --git a/compiler/typecheck/TcForeign.lhs b/compiler/typecheck/TcForeign.lhs
index e6586d8..c0d088d 100644
--- a/compiler/typecheck/TcForeign.lhs
+++ b/compiler/typecheck/TcForeign.lhs
@@ -212,7 +212,7 @@ tcCheckFIType sig_ty arg_tys res_ty (CImport cconv safety mh l@(CLabel _))
        cconv' <- checkCConv cconv
        return (CImport cconv' safety mh l)
 
-tcCheckFIType sig_ty arg_tys res_ty (CImport cconv safety mh CWrapper) = do
+tcCheckFIType sig_ty arg_tys res_ty (CImport cconv safety mh (CWrapper poolCapacity)) = do
         -- Foreign wrapper (former f.e.d.)
         -- The type must be of the form ft -> IO (FunPtr ft), where ft is a valid
         -- foreign type.  For legacy reasons ft -> IO (Ptr ft) is accepted, too.
@@ -226,7 +226,7 @@ tcCheckFIType sig_ty arg_tys res_ty (CImport cconv safety mh CWrapper) = do
                   where
                      (arg1_tys, res1_ty) = tcSplitFunTys arg1_ty
         _ -> addErrTc (illegalForeignTyErr empty sig_ty)
-    return (CImport cconv' safety mh CWrapper)
+    return (CImport cconv' safety mh (CWrapper poolCapacity))
 
 tcCheckFIType sig_ty arg_tys res_ty idecl@(CImport cconv safety mh (CFunction target))
   | isDynamicTarget target = do -- Foreign import dynamic
diff --git a/config.sh b/config.sh
new file mode 100755
index 0000000..6659b9a
--- /dev/null
+++ b/config.sh
@@ -0,0 +1,6 @@
+. env.sh
+CPPFLAGS="$TARGET_CPPFLAGS" CFLAGS="$TARGET_CFLAGS" LDFLAGS="$TARGET_LDFLAGS" ./configure \
+    --with-local-gcc=/usr/bin/gcc \
+    --target=arm-apple-darwin10 \
+    --with-alien=`pwd`/alien \
+    --prefix=/usr/local/ghc-iphone/
diff --git a/configure.ac b/configure.ac
index f631fd3..0ca44b9 100644
--- a/configure.ac
+++ b/configure.ac
@@ -434,6 +434,7 @@ dnl --------------------------------------------------------------
 FIND_GCC([WhatGccIsCalled], [gcc], [gcc])
 CC="$WhatGccIsCalled"
 export CC
+FIND_GCC([WhatLocalGccIsCalled], [local-gcc], [gcc])
 
 dnl ** Which ld to use?
 dnl --------------------------------------------------------------
@@ -542,6 +543,19 @@ FPTOOLS_SET_C_LD_FLAGS([target],[CONF_CC_OPTS_STAGE1],[CONF_GCC_LINKER_OPTS_STAG
 # Stage 3 won't be supported by cross-compilation
 FPTOOLS_SET_C_LD_FLAGS([target],[CONF_CC_OPTS_STAGE2],[CONF_GCC_LINKER_OPTS_STAGE2],[CONF_LD_LINKER_OPTS_STAGE2],[CONF_CPP_OPTS_STAGE2])
 
+CONF_CC_OPTS_STAGE1="$CONF_CC_OPTS_STAGE1 $TARGET_CFLAGS"
+CONF_CC_OPTS_STAGE2="$CONF_CC_OPTS_STAGE2 $TARGET_CFLAGS"
+CONF_CC_OPTS_STAGE3="$CONF_CC_OPTS_STAGE2 $TARGET_CFLAGS"
+CONF_GCC_LINKER_OPTS_STAGE1="$CONF_CC_OPTS_STAGE1 $TARGET_LDFLAGS"
+CONF_GCC_LINKER_OPTS_STAGE2="$CONF_CC_OPTS_STAGE2 $TARGET_LDFLAGS"
+CONF_GCC_LINKER_OPTS_STAGE3="$CONF_CC_OPTS_STAGE2 $TARGET_LDFLAGS"
+CONF_LD_LINKER_OPTS_STAGE1="$CONF_CC_OPTS_STAGE1 $TARGET_LDFLAGS"
+CONF_LD_LINKER_OPTS_STAGE2="$CONF_CC_OPTS_STAGE2 $TARGET_LDFLAGS"
+CONF_LD_LINKER_OPTS_STAGE3="$CONF_CC_OPTS_STAGE2 $TARGET_LDFLAGS"
+CONF_CPP_OPTS_STAGE1="$CONF_CC_OPTS_STAGE1 $TARGET_CPPFLAGS"
+CONF_CPP_OPTS_STAGE2="$CONF_CC_OPTS_STAGE2 $TARGET_CPPFLAGS"
+CONF_CPP_OPTS_STAGE3="$CONF_CC_OPTS_STAGE2 $TARGET_CPPFLAGS"
+
 FP_GCC_EXTRA_FLAGS
 
 dnl ** figure out how to invoke cpp directly (gcc -E is no good)
diff --git a/env.sh b/env.sh
new file mode 100644
index 0000000..db412dc
--- /dev/null
+++ b/env.sh
@@ -0,0 +1,23 @@
+export TARGET_PLATFORM=/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs/iPhoneOS6.0.sdk
+export TARGET_BIN="/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/usr/bin"
+export TARGET_GCC=$TARGET_BIN/arm-apple-darwin10-llvm-gcc-4.2
+export TARGET_CLANG=clang
+export TARGET_LD=$TARGET_CLANG
+
+export TARGET_CPPFLAGS="-I$TARGET_PLATFORM/usr/include/"
+export TARGET_CFLAGS="-isysroot $TARGET_PLATFORM -march=armv7 -mcpu=cortex-a8 -mfpu=neon"
+export TARGET_LDFLAGS="-L$TARGET_PLATFORM/usr/lib/"
+
+export LOCAL_PLATFORM=/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/SDKs/iPhoneSimulator6.0.sdk
+export LOCAL_BIN="/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneSimulator.platform/Developer/usr/bin"
+export LOCAL_GCC=$LOCAL_BIN/i686-apple-darwin11-llvm-gcc-4.2
+export LOCAL_LD=$TARGET_GCC
+export LOCAL_CPPFLAGS="-I$LOCAL_PLATFORM/usr/include/"
+export LOCAL_CFLAGS="-isysroot $LOCAL_PLATFORM -march=i386"
+export LOCAL_LDFLAGS="-L$LOCAL_PLATFORM/usr/lib/"
+
+sudo mkdir -p /Developer/usr/bin
+sudo rm -f /Developer/usr/bin/ar
+sudo ln -s /usr/bin/ar /Developer/usr/bin/ar
+
+export PATH="`pwd`/bin:$PATH"
diff --git a/ghc.mk b/ghc.mk
index 41371d0..f86e53a 100644
--- a/ghc.mk
+++ b/ghc.mk
@@ -309,7 +309,8 @@ endif
 # They do not say "this package will be built"; see $(PACKAGES_xx) for that
 
 # Packages that are built but not installed
-PKGS_THAT_ARE_INTREE_ONLY := haskeline transformers terminfo utf8-string xhtml
+#PKGS_THAT_ARE_INTREE_ONLY := haskeline transformers terminfo utf8-string xhtml
+PKGS_THAT_ARE_INTREE_ONLY := haskeline transformers mtl utf8-string xhtml
 
 PKGS_THAT_ARE_DPH := \
     dph/dph-base \
@@ -422,7 +423,7 @@ $(eval $(call addPackage,hoopl))
 $(eval $(call addPackage,transformers))
 $(eval $(call addPackage,utf8-string))
 $(eval $(call addPackage,xhtml))
-$(eval $(call addPackage,terminfo,($$(Windows),NO)))
+#$(eval $(call addPackage,terminfo,($$(Windows),NO)))
 $(eval $(call addPackage,haskeline))
 
 $(eval $(call extra-packages))
@@ -608,11 +609,13 @@ endif
 ifeq "$(BuildingCrossCompiler)-$(phase)" "YES-final"
 MAYBE_COMPILER=
 MAYBE_GHCTAGS=
+MAYBE_GHCPWD=
 MAYBE_HPC=
 MAYBE_RUNGHC=
 else
 MAYBE_COMPILER=compiler
 MAYBE_GHCTAGS=utils/ghctags
+MAYBE_GHCPWD=utils/ghc-pwd
 MAYBE_HPC=utils/hpc
 MAYBE_RUNGHC=utils/runghc
 endif
@@ -625,7 +628,7 @@ BUILD_DIRS += \
    $(GHC_PKG_DIR) \
    utils/testremove \
    $(MAYBE_GHCTAGS) \
-   utils/ghc-pwd \
+   $(MAYBE_GHCPWD) \
    $(GHC_CABAL_DIR) \
    $(MAYBE_HPC) \
    $(MAYBE_RUNGHC) \
@@ -639,7 +642,7 @@ endif
 endif
 
 BUILD_DIRS += utils/count_lines
-BUILD_DIRS += utils/compare_sizes
+#BUILD_DIRS += utils/compare_sizes
 
 ifneq "$(CLEANING)" "YES"
 # After compiler/, because these packages depend on it
diff --git a/includes/ghc.mk b/includes/ghc.mk
index 73704b4..bd00b25 100644
--- a/includes/ghc.mk
+++ b/includes/ghc.mk
@@ -150,7 +150,11 @@ includes/dist-derivedconstants/build/mkDerivedConstants.o : $(includes_H_CONFIG)
 
 ifneq "$(AlienScript)" ""
 $(INPLACE_BIN)/mkDerivedConstants$(exeext): includes/$(includes_dist-derivedconstants_C_SRCS) | $$(dir $$@)/.
+ifeq "$(AlienScript)" ""
 	$(WhatGccIsCalled) -o $@ $< $(CFLAGS) $(includes_CC_OPTS)
+else
+	$(AlienScript) compile -o $@ $< $(CFLAGS) $(includes_CC_OPTS)
+endif
 endif
 
 ifneq "$(BINDIST)" "YES"
@@ -190,7 +194,11 @@ includes/dist-ghcconstants/build/mkDerivedConstants.o : $(includes_H_CONFIG) $(i
 
 ifneq "$(AlienScript)" ""
 $(INPLACE_BIN)/mkGHCConstants$(exeext): includes/$(includes_dist-ghcconstants_C_SRCS) | $$(dir $$@)/.
+ifeq "$(AlienScript)" ""
 	$(WhatGccIsCalled) -o $@ $< $(CFLAGS) $(includes_CC_OPTS) $(includes_dist-ghcconstants_CC_OPTS)
+else
+	$(AlienScript) compile -o $@ $< $(CFLAGS) $(includes_CC_OPTS) $(includes_dist-ghcconstants_CC_OPTS)
+endif
 endif
 
 $(includes_GHCCONSTANTS) : $(INPLACE_BIN)/mkGHCConstants$(exeext) | $$(dir $$@)/.
diff --git a/libffi/ghc.mk b/libffi/ghc.mk
index fc474d2..629605e 100644
--- a/libffi/ghc.mk
+++ b/libffi/ghc.mk
@@ -53,6 +53,7 @@ $(libffi_STAMP_CONFIGURE): $(TOUCH_DEP)
 	$(call removeTrees,$(LIBFFI_DIR) libffi/build)
 	cat ghc-tarballs/libffi/libffi*.tar.gz | $(GZIP_CMD) -d | { cd libffi && $(TAR_CMD) -xf - ; }
 	mv libffi/libffi-* libffi/build
+	cat libffi/iphone.patch | (cd libffi/build && patch -p1)
 
 # We have to fake a non-working ln for configure, so that the fallback
 # option (cp -p) gets used instead.  Otherwise the libffi build system
diff --git a/mk/config.mk.in b/mk/config.mk.in
index 1cf8685..852873e 100644
--- a/mk/config.mk.in
+++ b/mk/config.mk.in
@@ -553,6 +553,7 @@ GHC_PACKAGE_DB_FLAG = @GHC_PACKAGE_DB_FLAG@
 # needs to know which gcc you're using in order to perform its tests.
 
 WhatGccIsCalled       = @WhatGccIsCalled@
+WhatLocalGccIsCalled  = @WhatLocalGccIsCalled@
 GccVersion            = @GccVersion@
 AlienScript           = @AlienScript@
 ifeq "$(phase)" "0"
@@ -566,12 +567,12 @@ TargetPlatformFull    = @TargetPlatformFull@
 GccLT34         = @GccLT34@
 GccLT46         = @GccLT46@
 CC              = $(WhatGccIsCalled)
-CC_STAGE0       = @CC_STAGE0@
+CC_STAGE0       = $(WhatLocalGccIsCalled)
 CC_STAGE1       = $(CC)
 CC_STAGE2       = $(CC)
 CC_STAGE3       = $(CC)
 AS              = $(WhatGccIsCalled)
-AS_STAGE0       = @CC_STAGE0@
+AS_STAGE0       = $(WhatLocalGccIsCalled)
 AS_STAGE1       = $(AS)
 AS_STAGE2       = $(AS)
 AS_STAGE3       = $(AS)
@@ -616,12 +617,26 @@ endif
 #     libraries\haskeline\.\System\Console\Haskeline\Backend\Win32.hsc:160
 #     directive "let" is not safe for cross-compilation
 ifneq "$(Windows)" "YES"
-SRC_HSC2HS_OPTS += --cross-safe
+SRC_HSC2HS_OPTS_STAGE0 += --cross-safe
+SRC_HSC2HS_OPTS_STAGE1 += --cross-safe
+SRC_HSC2HS_OPTS_STAGE2 += --cross-safe
 endif
-SRC_HSC2HS_OPTS += $(addprefix --cflag=,$(filter-out -O,$(SRC_CC_OPTS) $(CONF_CC_OPTS_STAGE0)))
-SRC_HSC2HS_OPTS += $(foreach d,$(GMP_INCLUDE_DIRS),-I$(d))
+SRC_HSC2HS_OPTS_STAGE0 += $(addprefix --cflag=,$(filter-out -O,$(SRC_CC_OPTS) $(CONF_CC_OPTS_STAGE0)))
+SRC_HSC2HS_OPTS_STAGE1 += $(addprefix --cflag=,$(filter-out -O,$(SRC_CC_OPTS) $(CONF_CC_OPTS_STAGE1)))
+SRC_HSC2HS_OPTS_STAGE2 += $(addprefix --cflag=,$(filter-out -O,$(SRC_CC_OPTS) $(CONF_CC_OPTS_STAGE2)))
+SRC_HSC2HS_OPTS_STAGE0 += $(addprefix --lflag=,$(CONF_GCC_LINKER_OPTS_STAGE0))
+SRC_HSC2HS_OPTS_STAGE1 += $(addprefix --lflag=,$(CONF_GCC_LINKER_OPTS_STAGE1))
+SRC_HSC2HS_OPTS_STAGE2 += $(addprefix --lflag=,$(CONF_GCC_LINKER_OPTS_STAGE2))
+SRC_HSC2HS_OPTS_STAGE0 += $(addprefix --cflag=,$(CONF_CPP_OPTS_STAGE0))
+SRC_HSC2HS_OPTS_STAGE1 += $(addprefix --cflag=,$(CONF_CPP_OPTS_STAGE1))
+SRC_HSC2HS_OPTS_STAGE2 += $(addprefix --cflag=,$(CONF_CPP_OPTS_STAGE2))
+SRC_HSC2HS_OPTS_STAGE0 += $(foreach d,$(GMP_INCLUDE_DIRS),-I$(d))
+SRC_HSC2HS_OPTS_STAGE1 += $(foreach d,$(GMP_INCLUDE_DIRS),-I$(d))
+SRC_HSC2HS_OPTS_STAGE2 += $(foreach d,$(GMP_INCLUDE_DIRS),-I$(d))
 ifeq "$(CrossCompiling)" "YES"
-SRC_HSC2HS_OPTS += --cross-compile
+SRC_HSC2HS_OPTS_STAGE0 += --cross-compile
+SRC_HSC2HS_OPTS_STAGE1 += --cross-compile
+SRC_HSC2HS_OPTS_STAGE2 += --cross-compile
 endif
 
 ifeq "$(TARGETPLATFORM)" "i386-unknown-mingw32"
diff --git a/packages b/packages
index 162d5ca..dd79608 100644
--- a/packages
+++ b/packages
@@ -68,7 +68,7 @@ libraries/old-time              -           packages/old-time.git
 libraries/pretty                -           packages/pretty.git                 git
 libraries/process               -           packages/process.git                git
 libraries/template-haskell      -           packages/template-haskell.git       git
-libraries/terminfo              -           packages/terminfo.git               git
+#libraries/terminfo              -           packages/terminfo.git               git
 libraries/transformers          -           packages/transformers.git           git
 libraries/unix                  -           packages/unix.git                   git
 libraries/utf8-string           -           packages/utf8-string.git            git
@@ -78,7 +78,7 @@ testsuite                       testsuite   testsuite.git
 nofib                           nofib       nofib.git                           git
 libraries/parallel              extra       packages/parallel.git               git
 libraries/stm                   extra       packages/stm.git                    git
-libraries/random                dph         packages/random.git                 git
-libraries/primitive             dph         packages/primitive.git              git
-libraries/vector                dph         packages/vector.git                 git
-libraries/dph                   dph         packages/dph.git                    git
+#libraries/random                dph         packages/random.git                 git
+#libraries/primitive             dph         packages/primitive.git              git
+#libraries/vector                dph         packages/vector.git                 git
+#libraries/dph                   dph         packages/dph.git                    git
diff --git a/rts/Adjustor.c b/rts/Adjustor.c
index 1a0bc28..f61aac9 100644
--- a/rts/Adjustor.c
+++ b/rts/Adjustor.c
@@ -42,7 +42,111 @@ Haskell side.
 #include "RtsUtils.h"
 #include "Stable.h"
 
-#if defined(USE_LIBFFI_FOR_ADJUSTORS)
+#if defined(darwin_HOST_OS) || defined(darwin10_HOST_OS)
+
+#include "Hash.h"
+#include "ffi.h"
+
+/* iPhone, iPhone, iPhone, tsk, tsk...
+ *
+ * The iPhone doesn't allow self-modifying code, so instead we allocate out of
+ * a pool of pre-compiled functions.
+ */
+
+struct iPhoneAdjustor;
+
+struct iPhoneAdjustorEntry {
+    void* func;
+    struct iPhoneAdjustor* adjustor;
+};
+
+struct iPhoneAdjustor
+{
+    struct iPhoneAdjustorEntry* poolEntry;
+    StgStablePtr hptr;
+    StgFunPtr wptr;
+};
+
+#if defined(THREADED_RTS)
+static Mutex iPhoneAdjustorMutex;
+#endif
+
+static HashTable* allocatedAdjustors;
+void iPhoneAdjustorInit(void);
+void* iPhoneCreateAdjustor(int cconv, 
+                StgStablePtr hptr,
+                StgFunPtr wptr,
+                char *typeString,
+                char* descr,
+                struct iPhoneAdjustorEntry* pool);
+StgStablePtr iPhoneLookupAdjustor(void* entry_);
+
+void
+iPhoneAdjustorInit()
+{
+#if defined(THREADED_RTS)
+    initMutex(&iPhoneAdjustorMutex);
+#endif
+    allocatedAdjustors = allocHashTable();
+}
+
+void*
+iPhoneCreateAdjustor(int cconv, 
+                StgStablePtr hptr,
+                StgFunPtr wptr,
+                char *typeString,
+                char* descr,
+                struct iPhoneAdjustorEntry* pool)
+{
+    int i;
+
+
+    ACQUIRE_LOCK(&iPhoneAdjustorMutex);
+    /* Look for a free slot in the function pool. */
+    for (i = 0; pool[i].func != NULL; i ++) {
+        if (pool[i].adjustor == NULL) {
+            struct iPhoneAdjustor* adj = stgMallocBytes(sizeof(struct iPhoneAdjustor),
+                                            "iPhoneAdjustor");
+            pool[i].adjustor = adj;
+            insertHashTable(allocatedAdjustors, (StgWord)pool[i].func, adj);
+            RELEASE_LOCK(&iPhoneAdjustorMutex);
+            adj->poolEntry = pool + i;
+            adj->hptr = hptr;
+            adj->wptr = wptr;
+            return pool[i].func;
+        }
+    }
+    RELEASE_LOCK(&iPhoneAdjustorMutex);
+    barf("iPhoneCreateAdjustor - adjustor pool '%s' is empty (capacity %d)", descr, i);
+}
+
+StgStablePtr iPhoneLookupAdjustor(void* entry_)
+{
+    struct iPhoneAdjustorEntry* entry = (struct iPhoneAdjustorEntry*) entry_;
+    return entry->adjustor->hptr;
+}
+
+void
+freeHaskellFunctionPtr(void* ptr)
+{
+    struct iPhoneAdjustor* adj;
+
+    ACQUIRE_LOCK(&iPhoneAdjustorMutex);
+    adj = lookupHashTable(allocatedAdjustors, (StgWord)ptr);
+    if (adj != NULL) {
+        removeHashTable(allocatedAdjustors, (StgWord)ptr, adj);
+        adj->poolEntry->adjustor = NULL;
+        RELEASE_LOCK(&iPhoneAdjustorMutex);
+
+        freeStablePtr(adj->hptr);
+        stgFree(adj);
+    }
+    else {
+        RELEASE_LOCK(&iPhoneAdjustorMutex);
+    }
+}
+
+#elif defined(USE_LIBFFI_FOR_ADJUSTORS)
 #include "ffi.h"
 #include <string.h>
 #endif
@@ -56,7 +160,7 @@ extern void adjustorCode(void);
 extern void *adjustorCode;
 #endif
 
-#if defined(USE_LIBFFI_FOR_ADJUSTORS)
+#if defined(USE_LIBFFI_FOR_ADJUSTORS) && !(defined(darwin_HOST_OS) || defined(darwin10_HOST_OS))
 void
 freeHaskellFunctionPtr(void* ptr)
 {
@@ -1199,7 +1303,7 @@ TODO: Depending on how much allocation overhead stgMallocBytes uses for
   return code;
 }
 
-
+#if !(defined(darwin_HOST_OS) || defined(darwin10_HOST_OS))
 void
 freeHaskellFunctionPtr(void* ptr)
 {
@@ -1282,5 +1386,6 @@ freeHaskellFunctionPtr(void* ptr)
 
  freeExec(ptr);
 }
+#endif
 
 #endif // !USE_LIBFFI_FOR_ADJUSTORS
diff --git a/rts/RtsStartup.c b/rts/RtsStartup.c
index f5c29f4..fa17b95 100644
--- a/rts/RtsStartup.c
+++ b/rts/RtsStartup.c
@@ -104,6 +104,10 @@ x86_init_fpu ( void )
 }
 #endif
 
+#if defined(darwin_HOST_OS) || defined(darwin10_HOST_OS)
+  void iPhoneAdjustorInit(void);
+#endif
+
 /* -----------------------------------------------------------------------------
    Starting up the RTS
    -------------------------------------------------------------------------- */
@@ -262,6 +266,10 @@ hs_init_ghc(int *argc, char **argv[], RtsConfig rts_config)
     ioManagerStart();
 #endif
 
+#if defined(darwin_HOST_OS) || defined(darwin10_HOST_OS)
+    iPhoneAdjustorInit();
+#endif
+
     /* Record initialization times */
     stat_endInit();
 }
diff --git a/rts/StgCRun.c b/rts/StgCRun.c
index b4c15e8..680c31a 100644
--- a/rts/StgCRun.c
+++ b/rts/StgCRun.c
@@ -658,6 +658,12 @@ StgRunIsImplementedInAssembler(void)
 #define THUMB_FUNC
 #endif
 
+#if defined(darwin_HOST_OS) || defined(darwin10_HOST_OS)
+#define STG_GLOBAL ".globl "
+#else
+#define STG_GLOBAL ".global "
+#endif
+
 StgRegTable *
 StgRun(StgFunPtr f, StgRegTable *basereg) {
     StgRegTable * r;
@@ -665,7 +671,7 @@ StgRun(StgFunPtr f, StgRegTable *basereg) {
         /*
          * save callee-saves registers on behalf of the STG code.
          */
-        "stmfd sp!, {r4-r10, fp, ip, lr}\n\t"
+        "stmfd sp!, {r4-r10, r11, ip, lr}\n\t"
 #if !defined(arm_HOST_ARCH_PRE_ARMv6)
         "vstmdb sp!, {d8-d11}\n\t"
 #endif
@@ -684,9 +690,12 @@ StgRun(StgFunPtr f, StgRegTable *basereg) {
          */
         "bx %1\n\t"
 
-        ".global " STG_RETURN "\n\t"
+        STG_GLOBAL STG_RETURN "\n\t"
         THUMB_FUNC
+#if defined(darwin_HOST_OS) || defined(darwin10_HOST_OS)
+#else
         ".type " STG_RETURN ", %%function\n"
+#endif
         STG_RETURN ":\n\t"
         /*
          * Free the space we allocated
@@ -702,7 +711,7 @@ StgRun(StgFunPtr f, StgRegTable *basereg) {
 #if !defined(arm_HOST_ARCH_PRE_ARMv6)
         "vldmia sp!, {d8-d11}\n\t"
 #endif
-        "ldmfd sp!, {r4-r10, fp, ip, lr}\n\t"
+        "ldmfd sp!, {r4-r10, r11, ip, lr}\n\t"
       : "=r" (r)
       : "r" (f), "r" (basereg), "i" (RESERVED_C_STACK_BYTES)
 #if !defined(__thumb__)
@@ -718,7 +727,7 @@ StgRun(StgFunPtr f, StgRegTable *basereg) {
            includes/stg/MachRegs.h Please note that Haskell code is
            compiled by GHC/LLVM into ARM code (not Thumb!), at least
            as of February 2012 */
-      : "%r4", "%r5", "%r6", "%r8", "%r9", "%r10", "%fp", "%ip", "%lr"
+      : "%r4", "%r5", "%r6", "%r8", "%r9", "%r10", "%r11", "%ip", "%lr"
 #endif
     );
     return r;
diff --git a/rts/ghc.mk b/rts/ghc.mk
index 5ae6b1a..6612c38 100644
--- a/rts/ghc.mk
+++ b/rts/ghc.mk
@@ -15,6 +15,7 @@
 
 # We build the RTS with stage 1
 rts_dist_HC = $(GHC_STAGE1)
+rts_dist_CC = $(CC_STAGE1)
 
 # merge GhcLibWays and GhcRTSWays but strip out duplicates
 rts_WAYS = $(GhcLibWays) $(filter-out $(GhcLibWays),$(GhcRTSWays))
@@ -505,6 +506,7 @@ rts_PACKAGE_CPP_OPTS += -DHAVE_LIBMINGWEX
 endif
 
 $(eval $(call manual-package-config,rts))
+$1_$2_CC = $$(CC_STAGE$3)
 
 ifneq "$(BootingFromHc)" "YES"
 rts/package.conf.inplace : $(includes_H_CONFIG) $(includes_H_PLATFORM)
diff --git a/rts/posix/Itimer.c b/rts/posix/Itimer.c
index 8c9b1f8..8fac115 100644
--- a/rts/posix/Itimer.c
+++ b/rts/posix/Itimer.c
@@ -44,6 +44,13 @@
 
 #include <string.h>
 
+#define USE_PTHREAD_FOR_ITIMER
+
+#if defined(USE_PTHREAD_FOR_ITIMER)
+#include <pthread.h>
+#include <unistd.h>
+#endif
+
 /*
  * We use a realtime timer by default.  I found this much more
  * reliable than a CPU timer:
@@ -89,6 +96,7 @@ static timer_t timer;
 
 static Time itimer_interval = DEFAULT_TICK_INTERVAL;
 
+#if !defined(USE_PTHREAD_FOR_ITIMER)
 static void install_vtalrm_handler(TickProc handle_tick)
 {
     struct sigaction action;
@@ -114,13 +122,31 @@ static void install_vtalrm_handler(TickProc handle_tick)
         stg_exit(EXIT_FAILURE);
     }
 }
+#endif
+
+#if defined(USE_PTHREAD_FOR_ITIMER)
+static volatile int itimer_enabled;
+static void *itimer_thread_func(void *_handle_tick)
+{
+    TickProc handle_tick = _handle_tick;
+    while (1) {
+        usleep(TimeToUS(itimer_interval));
+        if (itimer_enabled)
+            handle_tick(0);
+    }
+    return NULL;
+}
+#endif
 
 void
 initTicker (Time interval, TickProc handle_tick)
 {
     itimer_interval = interval;
 
-#if defined(USE_TIMER_CREATE)
+#if defined(USE_PTHREAD_FOR_ITIMER)
+    pthread_t tid;
+    pthread_create(&tid, NULL, itimer_thread_func, (void*)handle_tick);
+#elif defined(USE_TIMER_CREATE)
     {
         struct sigevent ev;
 
@@ -135,15 +161,18 @@ initTicker (Time interval, TickProc handle_tick)
             stg_exit(EXIT_FAILURE);
         }
     }
-#endif
-
     install_vtalrm_handler(handle_tick);
+#else
+    install_vtalrm_handler(handle_tick);
+#endif
 }
 
 void
 startTicker(void)
 {
-#if defined(USE_TIMER_CREATE)
+#if defined(USE_PTHREAD_FOR_ITIMER)
+    itimer_enabled = 1;
+#elif defined(USE_TIMER_CREATE)
     {
         struct itimerspec it;
         
@@ -175,7 +204,9 @@ startTicker(void)
 void
 stopTicker(void)
 {
-#if defined(USE_TIMER_CREATE)
+#if defined(USE_PTHREAD_FOR_ITIMER)
+    itimer_enabled = 0;
+#elif defined(USE_TIMER_CREATE)
     struct itimerspec it;
 
     it.it_value.tv_sec = 0;
diff --git a/rules/build-dependencies.mk b/rules/build-dependencies.mk
index a37ff16..f993237 100644
--- a/rules/build-dependencies.mk
+++ b/rules/build-dependencies.mk
@@ -125,7 +125,7 @@ endef
 #    to "i" on Windows and "" on any other platform.
 define addCFileDeps
 
-	$(CPP) $($1_$2_MKDEPENDC_OPTS) $($1_$2_v_ALL_CC_OPTS) $($(basename $4)_CC_OPTS) -MM $4 -MF $3.bit
+	"$($1_$2_CC)" -E $($1_$2_MKDEPENDC_OPTS) $($1_$2_v_ALL_CC_OPTS) $($(basename $4)_CC_OPTS) -MM $4 -MF $3.bit
 	$(foreach w,$5,sed -e 's|\\|/|g' -e 's| /$$| \\|' -e "1s|\.o|\.$($w_osuf)|" -e "1s|^|$(dir $4)|" -e "1s|$1/|$1/$2/build/|" -e "1s|$2/build/$2/build|$2/build|g" -e "s|$(TOP)/||g$(CASE_INSENSITIVE_SED)" $3.bit >> $3.tmp &&) true
 endef
 
diff --git a/rules/build-package-data.mk b/rules/build-package-data.mk
index 047efcb..32e8962 100644
--- a/rules/build-package-data.mk
+++ b/rules/build-package-data.mk
@@ -79,7 +79,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) $$(LAX_DEPS_FOLLOW) $$($1_$2_HC_CONFIG_DEP)
-	CROSS_COMPILE="$(CrossCompilePrefix)" "$$(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
+	CROSS_COMPILE="$(CrossCompilePrefix)" CFLAGS="$$(CONF_CC_OPTS_STAGE$3)" LDFLAGS="$$(CONF_GCC_LINKER_OPTS_STAGE$3)" CPPFLAGS="$$(CONF_CPP_OPTS_STAGE3)" "$$(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
diff --git a/rules/distdir-way-opts.mk b/rules/distdir-way-opts.mk
index bbd37d1..e484c19 100644
--- a/rules/distdir-way-opts.mk
+++ b/rules/distdir-way-opts.mk
@@ -183,10 +183,10 @@ $1_$2_$3_HSC2HS_LD_OPTS:=$$(shell for i in $$($1_$2_DIST_LD_OPTS); do echo \'--l
 endif
 
 $1_$2_$3_ALL_HSC2HS_OPTS = \
- --cc=$$(WhatGccIsCalled) \
- --ld=$$(WhatGccIsCalled) \
+ --cc=$$(CC_STAGE$4) \
+ --ld=$$(CC_STAGE$4) \
  $$(CONF_HSC2HS_OPTS) \
- $$(SRC_HSC2HS_OPTS) \
+ $$(SRC_HSC2HS_OPTS_STAGE$4) \
  $$(WAY_$3_HSC2HS_OPTS) \
  --cflag=-D__GLASGOW_HASKELL__=$$(if $$(filter 0,$4),$$(GhcCanonVersion),$$(ProjectVersionInt)) \
  --cflag=-D$$(HostArch_CPP)_HOST_ARCH=1 \
diff --git a/utils/ghc-pkg/Main.hs b/utils/ghc-pkg/Main.hs
index 83b5447..d438051 100644
--- a/utils/ghc-pkg/Main.hs
+++ b/utils/ghc-pkg/Main.hs
@@ -65,7 +65,7 @@ import System.Process(runInteractiveCommand)
 import qualified System.Info(os)
 #endif
 
-#if !defined(mingw32_HOST_OS) && !defined(BOOTSTRAPPING)
+#if !defined(mingw32_HOST_OS) && !defined(darwin10_HOST_OS) && !defined(BOOTSTRAPPING)
 import System.Console.Terminfo as Terminfo
 #endif
 
@@ -1002,7 +1002,7 @@ listPackages verbosity my_flags mPackageName mModuleName = do
 
   if simple_output then show_simple stack else do
 
-#if defined(mingw32_HOST_OS) || defined(BOOTSTRAPPING)
+#if defined(mingw32_HOST_OS) || defined(darwin10_HOST_OS) || defined(BOOTSTRAPPING)
   mapM_ show_normal stack
 #else
   let
diff --git a/utils/ghc-pkg/ghc-pkg.cabal b/utils/ghc-pkg/ghc-pkg.cabal
index 4f96dcc..a7bd0d3 100644
--- a/utils/ghc-pkg/ghc-pkg.cabal
+++ b/utils/ghc-pkg/ghc-pkg.cabal
@@ -26,8 +26,10 @@ Executable ghc-pkg
                    binary,
                    bin-package-db,
                    bytestring
-    if !os(windows)
+    if !os(windows) && !ios(darwin10)
         Build-Depends: unix,
                        terminfo
     if os(windows)
         c-sources: CRT_noglob.c
+    if os(darwin10)
+        Build-Depends: unix
