diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 0c8a7d2728c3ce4accc04064344b887442e067d5..69b4b597f1e8270fa0ef2c866b8c2abd99aa6ad2 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,19 +1,25 @@
+2004-02-19  Zack Weinberg  <zack@codesourcery.com>
+
+	* config/ia64/ia64.c (ia64_function_arg): In big-endian mode,
+	when passing single SFmode quantities in general registers,
+	put them in the high half.
+
 2004-02-19  Aldy Hernandez  <aldyh@redhat.com>
- 
-        * doc/md.texi (Standard Names): Document additional dependency on
-        fix pattern.
- 
-        * optabs.c (ftruncify): Remove.
-        (expand_fix): Manually inline ftruncify above.
-        (can_fix_p): Add FIXME note.
+
+	* doc/md.texi (Standard Names): Document additional dependency on
+	fix pattern.
+
+	* optabs.c (ftruncify): Remove.
+	(expand_fix): Manually inline ftruncify above.
+	(can_fix_p): Add FIXME note.
 
 2004-02-19  Aldy Hernandez  <aldyh@redhat.com>
- 
-        * config/rs6000/spe.md (spe_fixunssfsi2): Rename to
-        spe_fixuns_truncsfsi2.
- 
-        * config/rs6000/rs6000.md (fixunssfsi2): Rename to
-        fixuns_truncsfsi2.
+
+	* config/rs6000/spe.md (spe_fixunssfsi2): Rename to
+	spe_fixuns_truncsfsi2.
+
+	* config/rs6000/rs6000.md (fixunssfsi2): Rename to
+	fixuns_truncsfsi2.
 
 2004-02-19  Steve Ellcey  <sje@cup.hp.com>
 
diff --git a/gcc/config/ia64/ia64.c b/gcc/config/ia64/ia64.c
index f7e5cc341c73df2e5f3ee67185b9d858bc5a520f..b790819ca3543c90a4b77a38ae25ac1ee230a01e 100644
--- a/gcc/config/ia64/ia64.c
+++ b/gcc/config/ia64/ia64.c
@@ -3786,21 +3786,34 @@ ia64_function_arg (CUMULATIVE_ARGS *cum, enum machine_mode mode, tree type,
      named, and in a GR register when unnamed.  */
   else if (cum->prototype)
     {
-      if (! named)
-	return gen_rtx_REG (mode, basereg + cum->words + offset);
-      else
+      if (named)
 	return gen_rtx_REG (mode, FR_ARG_FIRST + cum->fp_regs);
+      /* In big-endian mode, an anonymous SFmode value must be represented
+         as (parallel:SF [(expr_list (reg:DI n) (const_int 0))]) to force
+	 the value into the high half of the general register.  */
+      else if (BYTES_BIG_ENDIAN && mode == SFmode)
+	return gen_rtx_PARALLEL (mode,
+		 gen_rtvec (1,
+                   gen_rtx_EXPR_LIST (VOIDmode,
+		     gen_rtx_REG (DImode, basereg + cum->words + offset),
+				      const0_rtx)));
+      else
+	return gen_rtx_REG (mode, basereg + cum->words + offset);
     }
   /* If there is no prototype, then FP values go in both FR and GR
      registers.  */
   else
     {
+      /* See comment above.  */
+      enum machine_mode inner_mode =
+	(BYTES_BIG_ENDIAN && mode == SFmode) ? DImode : mode;
+
       rtx fp_reg = gen_rtx_EXPR_LIST (VOIDmode,
 				      gen_rtx_REG (mode, (FR_ARG_FIRST
 							  + cum->fp_regs)),
 				      const0_rtx);
       rtx gr_reg = gen_rtx_EXPR_LIST (VOIDmode,
-				      gen_rtx_REG (mode,
+				      gen_rtx_REG (inner_mode,
 						   (basereg + cum->words
 						    + offset)),
 				      const0_rtx);