about summary refs log tree commit diff
diff options
context:
space:
mode:
authorPatrick Walton <pcwalton@mimiga.net>2011-07-18 18:00:45 -0700
committerPatrick Walton <pcwalton@mimiga.net>2011-07-18 18:00:45 -0700
commit07a68df3b73aeb56e3445b0f641b2e0c6b8ac22e (patch)
tree1117f8539c317b7a56e7f8c3e4e4929445e8b138
parent08eabde97b959f14aea05932c2c336ed71cecb4e (diff)
downloadrust-07a68df3b73aeb56e3445b0f641b2e0c6b8ac22e.tar.gz
rust-07a68df3b73aeb56e3445b0f641b2e0c6b8ac22e.zip
rustc: Skip null when translating string concatenation
-rw-r--r--src/comp/middle/trans_vec.rs6
-rw-r--r--src/comp/middle/ty.rs1
2 files changed, 6 insertions, 1 deletions
diff --git a/src/comp/middle/trans_vec.rs b/src/comp/middle/trans_vec.rs
index 682e4eefad4..de4be8060d0 100644
--- a/src/comp/middle/trans_vec.rs
+++ b/src/comp/middle/trans_vec.rs
@@ -127,8 +127,10 @@ fn trans_concat(&@block_ctxt cx, &dest in_dest, &span sp, ty::t t,
     // TODO: Detect "a + [ literal ]" and optimize to copying the literal
     //       elements in directly.
 
-    // Translate the LHS and RHS. Pull out their length and data.
     auto t = ty::expr_ty(bcx_tcx(bcx), lhs);
+    auto skip_null = ty::type_is_str(bcx_tcx(bcx), t);
+
+    // Translate the LHS and RHS. Pull out their length and data.
     auto lhs_tmp = trans_dps::dest_alias(bcx_tcx(bcx), t);
     bcx = trans_dps::trans_expr(bcx, lhs_tmp, lhs);
     auto lllhsptr = trans_dps::dest_ptr(lhs_tmp);
@@ -142,6 +144,8 @@ fn trans_concat(&@block_ctxt cx, &dest in_dest, &span sp, ty::t t,
     r0 = get_len_and_data(bcx, t, llrhsptr);
     bcx = r0._0; auto llrhslen = r0._1; auto llrhsdata = r0._2;
 
+    if skip_null { lllhslen = bcx.build.Sub(lllhslen, C_int(1)); }
+
     // Allocate the destination.
     auto r1 = trans_dps::spill_alias(bcx, in_dest, t);
     bcx = r1._0; auto dest = r1._1;
diff --git a/src/comp/middle/ty.rs b/src/comp/middle/ty.rs
index 0261e168073..b5242900faf 100644
--- a/src/comp/middle/ty.rs
+++ b/src/comp/middle/ty.rs
@@ -915,6 +915,7 @@ fn type_is_sequence(&ctxt cx, &t ty) -> bool {
 fn type_is_str(&ctxt cx, &t ty) -> bool {
     alt (struct(cx, ty)) {
         case (ty_str) { ret true; }
+        case (ty_istr) { ret true; }
         case (_) { ret false; }
     }
 }