Skip to content

Commit e89d985

Browse files
committed
Fix vector indexing in consts so it works with the enum vector const fix.
1 parent de8dc02 commit e89d985

File tree

3 files changed

+38
-10
lines changed

3 files changed

+38
-10
lines changed

src/librustc/lib/llvm.rs

+1
Original file line numberDiff line numberDiff line change
@@ -382,6 +382,7 @@ pub extern mod llvm {
382382
pub unsafe fn LLVMGetUsedValue(U: UseRef) -> ValueRef;
383383

384384
/* Operations on Users */
385+
pub unsafe fn LLVMGetNumOperands(Val: ValueRef) -> c_int;
385386
pub unsafe fn LLVMGetOperand(Val: ValueRef, Index: c_uint) -> ValueRef;
386387
pub unsafe fn LLVMSetOperand(Val: ValueRef, Index: c_uint, Op: ValueRef);
387388

src/librustc/middle/trans/consts.rs

+12-10
Original file line numberDiff line numberDiff line change
@@ -285,15 +285,17 @@ pub fn const_expr(cx: @crate_ctxt, e: @ast::expr) -> ValueRef {
285285
// call. Despite that being "a const", it's not the kind of
286286
// const you can ask for the integer-value of, evidently. This
287287
// might be an LLVM bug, not sure. In any case, to work around
288-
// this we drop down to the array-type level here and just ask
289-
// how long the array-type itself is, ignoring the length we
290-
// pulled out of the slice. This in turn only works because we
291-
// picked out the original globalvar via const_deref and so can
292-
// recover the array-size of the underlying array, and all this
293-
// will hold together exactly as long as we _don't_ support
294-
// const sub-slices (that is, slices that represent something
295-
// other than a whole array). At that point we'll have more and
296-
// uglier work to do here, but for now this should work.
288+
// this we obtain the initializer and count how many elements it
289+
// has, ignoring the length we pulled out of the slice. (Note
290+
// that the initializer might be a struct rather than an array,
291+
// if enums are involved.) This only works because we picked out
292+
// the original globalvar via const_deref and so can recover the
293+
// array-size of the underlying array (or the element count of
294+
// the underlying struct), and all this will hold together
295+
// exactly as long as we _don't_ support const sub-slices (that
296+
// is, slices that represent something other than a whole
297+
// array). At that point we'll have more and uglier work to do
298+
// here, but for now this should work.
297299
//
298300
// In the future, what we should be doing here is the
299301
// moral equivalent of:
@@ -305,7 +307,7 @@ pub fn const_expr(cx: @crate_ctxt, e: @ast::expr) -> ValueRef {
305307
// not want to consider sizeof() a constant expression
306308
// we can get the value (as a number) out of.
307309

308-
let len = llvm::LLVMGetArrayLength(val_ty(arr)) as u64;
310+
let len = llvm::LLVMGetNumOperands(arr) as u64;
309311
let len = match ty::get(bt).sty {
310312
ty::ty_estr(*) => {assert len > 0; len - 1},
311313
_ => len
+25
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// Copyright 2013 The Rust Project Developers. See the COPYRIGHT
2+
// file at the top-level directory of this distribution and at
3+
// http://rust-lang.org/COPYRIGHT.
4+
//
5+
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6+
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7+
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8+
// option. This file may not be copied, modified, or distributed
9+
// except according to those terms.
10+
11+
enum E { V1(int), V0 }
12+
const C: &[E] = &[V0, V1(0xDEADBEE)];
13+
const C0: E = C[0];
14+
const C1: E = C[1];
15+
16+
fn main() {
17+
match C0 {
18+
V0 => (),
19+
_ => die!()
20+
}
21+
match C1 {
22+
V1(n) => assert(n == 0xDEADBEE),
23+
_ => die!()
24+
}
25+
}

0 commit comments

Comments
 (0)