Skip to content

Commit f34eae8

Browse files
committed
Translate slice-strings and make fixed-strings carry their null.
1 parent c720ffd commit f34eae8

File tree

5 files changed

+39
-31
lines changed

5 files changed

+39
-31
lines changed

src/rustc/middle/trans/base.rs

+9-2
Original file line numberDiff line numberDiff line change
@@ -1236,7 +1236,7 @@ fn copy_val_no_check(bcx: block, action: copy_action, dst: ValueRef,
12361236
let _icx = bcx.insn_ctxt("copy_val_no_check");
12371237
let ccx = bcx.ccx();
12381238
let mut bcx = bcx;
1239-
if ty::type_is_scalar(t) {
1239+
if ty::type_is_scalar(t) || ty::type_is_slice(t) {
12401240
Store(bcx, src, dst);
12411241
ret bcx;
12421242
}
@@ -1268,7 +1268,7 @@ fn move_val(cx: block, action: copy_action, dst: ValueRef,
12681268
let mut src_val = src.val;
12691269
let tcx = cx.tcx();
12701270
let mut cx = cx;
1271-
if ty::type_is_scalar(t) {
1271+
if ty::type_is_scalar(t) || ty::type_is_slice(t) {
12721272
if src.kind == owned { src_val = Load(cx, src_val); }
12731273
Store(cx, src_val, dst);
12741274
ret cx;
@@ -2294,6 +2294,13 @@ fn trans_index(cx: block, ex: @ast::expr, base: @ast::expr,
22942294
let body = GEPi(bcx, v, [0, 0]);
22952295
(lim, body)
22962296
}
2297+
ty::ty_estr(ty::vstore_slice(_)) |
2298+
ty::ty_evec(_, ty::vstore_slice(_)) {
2299+
let body = Load(bcx, GEPi(bcx, v, [0, 0]));
2300+
let lim = Load(bcx, GEPi(bcx, v, [0, 1]));
2301+
(lim, body)
2302+
}
2303+
22972304
ty::ty_estr(_) | ty::ty_evec(_, _) {
22982305
bcx.sess().unimpl(#fmt("unsupported evec/estr type trans_index"));
22992306
}

src/rustc/middle/trans/tvec.rs

+17-15
Original file line numberDiff line numberDiff line change
@@ -148,28 +148,30 @@ fn trans_vstore(bcx: block, e: @ast::expr,
148148
fn trans_estr(bcx: block, s: str, vstore: ast::vstore,
149149
sp: span, dest: dest) -> block {
150150
let _icx = bcx.insn_ctxt("tvec::trans_estr");
151-
alt vstore {
151+
let ccx = bcx.ccx();
152+
153+
let c = alt vstore {
152154
ast::vstore_fixed(_)
153155
{
154-
let c = str::as_bytes(s) {|bytes|
155-
// NB: The byte vector we have here includes the trailing \0,
156-
// but we are doing a fixed-size str, meaning we _exclude_
157-
// the trailing \0. And we don't let LLVM null-terminate
158-
// either.
159-
unsafe {
160-
lib::llvm::llvm::LLVMConstString(
161-
unsafe::reinterpret_cast(vec::unsafe::to_ptr(bytes)),
162-
(bytes.len() - 1u) as libc::c_uint, lib::llvm::True)
163-
}
164-
};
156+
// "hello"/_ => [i8 x 6] in llvm
157+
#debug("trans_estr: fixed: %s", s);
158+
C_postr(s)
159+
}
165160

166-
#debug("trans_estr: src %s",val_str(bcx.ccx().tn, c));
167-
ret base::store_in_dest(bcx, c, dest);
161+
ast::vstore_slice(_) {
162+
// "hello" => (*i8,uint) in llvm
163+
#debug("trans_estr: slice '%s'", s);
164+
let cs = PointerCast(bcx, C_cstr(ccx, s), T_ptr(T_i8()));
165+
C_struct([cs, C_uint(ccx, str::len(s))])
168166
}
167+
169168
_ {
170169
bcx.ccx().sess.span_unimpl(sp, "unhandled tvec::trans_estr");
171170
}
172-
}
171+
};
172+
173+
#debug("trans_estr: type: %s", val_str(ccx.tn, c));
174+
base::store_in_dest(bcx, c, dest)
173175
}
174176

175177
fn trans_str(bcx: block, s: str, dest: dest) -> block {

src/rustc/middle/trans/type_of.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ fn type_of(cx: @crate_ctxt, t: ty::t) -> TypeRef {
7272
}
7373

7474
ty::ty_estr(ty::vstore_fixed(n)) {
75-
T_array(T_i8(), n)
75+
T_array(T_i8(), n + 1u /* +1 for trailing null */)
7676
}
7777

7878
ty::ty_evec(mt, ty::vstore_fixed(n)) {

src/rustc/middle/ty.rs

+8-8
Original file line numberDiff line numberDiff line change
@@ -118,7 +118,7 @@ export type_is_sequence;
118118
export type_is_signed;
119119
export type_is_structural;
120120
export type_is_copyable;
121-
export type_is_tup_like;
121+
export type_is_slice;
122122
export type_is_unique;
123123
export type_is_c_like_enum;
124124
export type_structurally_contains;
@@ -858,13 +858,6 @@ fn sequence_element_type(cx: ctxt, ty: t) -> t {
858858
}
859859
}
860860

861-
pure fn type_is_tup_like(ty: t) -> bool {
862-
alt get(ty).struct {
863-
ty_rec(_) | ty_tup(_) { true }
864-
_ { false }
865-
}
866-
}
867-
868861
fn get_element_type(ty: t, i: uint) -> t {
869862
alt get(ty).struct {
870863
ty_rec(flds) { ret flds[i].mt.ty; }
@@ -887,6 +880,13 @@ pure fn type_is_boxed(ty: t) -> bool {
887880
}
888881
}
889882

883+
pure fn type_is_slice(ty: t) -> bool {
884+
alt get(ty).struct {
885+
ty_evec(_, vstore_slice(_)) | ty_estr(vstore_slice(_)) { true }
886+
_ { ret false; }
887+
}
888+
}
889+
890890
pure fn type_is_unique_box(ty: t) -> bool {
891891
alt get(ty).struct {
892892
ty_uniq(_) { ret true; }

src/test/run-pass/estr-slice.rs

+4-5
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,7 @@
1-
// xfail-test
21
fn main() {
3-
let x : str/& = "hello";
4-
let mut y = "there";
2+
let x = "hello"/&;
3+
let mut y = "there"/&;
54
y = x;
6-
assert y[1] == 'h' as u8;
7-
assert y[4] == 'e' as u8;
5+
assert y[0] == 'h' as u8;
6+
assert y[4] == 'o' as u8;
87
}

0 commit comments

Comments
 (0)