From f2c5642d134df70755e0aede94074767cd3958eb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Wed, 19 Jun 2013 19:54:54 +0200 Subject: [PATCH 01/31] Fix get_tydesc() return type This fixes part of #3730, but not all. Also changes the TyDesc struct to be equivalent with the generated code, with the hope that the above issue may one day be closed for good, i.e. that the TyDesc type can completely be specified in the Rust sources and not be generated. --- src/librustc/front/intrinsic.rs | 16 ++++++++++++---- src/librustc/middle/trans/foreign.rs | 9 ++++++--- src/librustc/middle/trans/glue.rs | 5 ++--- src/librustc/middle/trans/type_.rs | 11 ++++++++--- src/librustc/middle/typeck/check/mod.rs | 10 ++++++++-- src/libstd/unstable/intrinsics.rs | 3 +++ 6 files changed, 39 insertions(+), 15 deletions(-) diff --git a/src/librustc/front/intrinsic.rs b/src/librustc/front/intrinsic.rs index fcb08180a5ea..f19e37062535 100644 --- a/src/librustc/front/intrinsic.rs +++ b/src/librustc/front/intrinsic.rs @@ -20,14 +20,22 @@ pub mod intrinsic { // version in sys is no longer present. pub fn get_tydesc() -> *TyDesc { unsafe { - rusti::get_tydesc::() as *TyDesc + rusti::get_tydesc::() } } + pub type GlueFn = extern "Rust" fn(**TyDesc, *i8); + + // NB: this has to be kept in sync with the Rust ABI. pub struct TyDesc { size: uint, - align: uint - // Remaining fields not listed + align: uint, + take_glue: GlueFn, + drop_glue: GlueFn, + free_glue: GlueFn, + visit_glue: GlueFn, + shape: *i8, + shape_tables: *i8 } pub enum Opaque { } @@ -133,7 +141,7 @@ pub mod intrinsic { #[abi = "rust-intrinsic"] pub extern "rust-intrinsic" { - pub fn get_tydesc() -> *(); + pub fn get_tydesc() -> *TyDesc; pub fn visit_tydesc(td: *TyDesc, tv: @TyVisitor); } } diff --git a/src/librustc/middle/trans/foreign.rs b/src/librustc/middle/trans/foreign.rs index 10e63e6af777..855610510bd9 100644 --- a/src/librustc/middle/trans/foreign.rs +++ b/src/librustc/middle/trans/foreign.rs @@ -681,9 +681,12 @@ pub fn trans_intrinsic(ccx: @mut CrateContext, let static_ti = get_tydesc(ccx, tp_ty); glue::lazily_emit_all_tydesc_glue(ccx, static_ti); - // FIXME (#3727): change this to ccx.tydesc_ty.ptr_to() when the - // core::sys copy of the get_tydesc interface dies off. - let td = PointerCast(bcx, static_ti.tydesc, Type::nil().ptr_to()); + // FIXME (#3730): ideally this shouldn't need a cast, + // but there's a circularity between translating rust types to llvm + // types and having a tydesc type available. So I can't directly access + // the llvm type of intrinsic::TyDesc struct. + let userland_tydesc_ty = type_of::type_of(ccx, output_type); + let td = PointerCast(bcx, static_ti.tydesc, userland_tydesc_ty); Store(bcx, td, fcx.llretptr.get()); } "init" => { diff --git a/src/librustc/middle/trans/glue.rs b/src/librustc/middle/trans/glue.rs index e9febb51005c..0930d3550353 100644 --- a/src/librustc/middle/trans/glue.rs +++ b/src/librustc/middle/trans/glue.rs @@ -789,7 +789,6 @@ pub fn emit_tydescs(ccx: &mut CrateContext) { }; } -fn type_of_glue_fn(ccx: &CrateContext) -> Type { - let tydescpp = ccx.tydesc_type.ptr_to().ptr_to(); - Type::func([ Type::nil().ptr_to(), tydescpp, Type::i8p() ], &Type::void()) +pub fn type_of_glue_fn(ccx: &CrateContext) -> Type { + Type::glue_fn(ccx.tydesc_type) } diff --git a/src/librustc/middle/trans/type_.rs b/src/librustc/middle/trans/type_.rs index 34a150331091..764bdb026f47 100644 --- a/src/librustc/middle/trans/type_.rs +++ b/src/librustc/middle/trans/type_.rs @@ -189,18 +189,23 @@ impl Type { None => () } + // Bit of a kludge: pick the fn typeref out of the tydesc.. let ty = cx.tydesc_type.get_field(abi::tydesc_field_drop_glue); cx.tn.associate_type("glue_fn", &ty); return ty; } + pub fn glue_fn(tydesc: Type) -> Type { + let tydescpp = tydesc.ptr_to().ptr_to(); + Type::func([ Type::nil().ptr_to(), tydescpp, Type::i8p() ], + &Type::void()) + } + pub fn tydesc(arch: Architecture) -> Type { let mut tydesc = Type::named_struct("tydesc"); - let tydescpp = tydesc.ptr_to().ptr_to(); let pvoid = Type::i8p(); - let glue_fn_ty = Type::func([ Type::nil().ptr_to(), tydescpp, pvoid ], - &Type::void()).ptr_to(); + let glue_fn_ty = Type::glue_fn(tydesc).ptr_to(); let int_ty = Type::int(arch); diff --git a/src/librustc/middle/typeck/check/mod.rs b/src/librustc/middle/typeck/check/mod.rs index fa7959c7872b..4c074ce197ed 100644 --- a/src/librustc/middle/typeck/check/mod.rs +++ b/src/librustc/middle/typeck/check/mod.rs @@ -3506,8 +3506,14 @@ pub fn check_intrinsic_type(ccx: @mut CrateCtxt, it: @ast::foreign_item) { } "get_tydesc" => { - // FIXME (#3730): return *intrinsic::tydesc, not *() - (1u, ~[], ty::mk_nil_ptr(ccx.tcx)) + let tydesc_name = special_idents::tydesc; + assert!(tcx.intrinsic_defs.contains_key(&tydesc_name)); + let (_, tydesc_ty) = tcx.intrinsic_defs.get_copy(&tydesc_name); + let td_ptr = ty::mk_ptr(ccx.tcx, ty::mt { + ty: tydesc_ty, + mutbl: ast::m_imm + }); + (1u, ~[], td_ptr) } "visit_tydesc" => { let tydesc_name = special_idents::tydesc; diff --git a/src/libstd/unstable/intrinsics.rs b/src/libstd/unstable/intrinsics.rs index c38b013a75aa..08fc90fa908c 100644 --- a/src/libstd/unstable/intrinsics.rs +++ b/src/libstd/unstable/intrinsics.rs @@ -209,6 +209,9 @@ pub extern "rust-intrinsic" { pub fn pref_align_of() -> uint; /// Get a static pointer to a type descriptor. + #[cfg(not(stage0))] + pub fn get_tydesc() -> *::intrinsic::TyDesc; + #[cfg(stage0)] pub fn get_tydesc() -> *(); /// Create a value initialized to zero. From 469f394b251feebfb16090303da59206ba25acc6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Thu, 20 Jun 2013 11:39:49 +0200 Subject: [PATCH 02/31] Remove intrinsic module To achieve this, the following changes were made: * Move TyDesc, TyVisitor and Opaque to std::unstable::intrinsics * Convert TyDesc, TyVisitor and Opaque to lang items instead of specially handling the intrinsics module * Removed TypeDesc, FreeGlue and get_type_desc() from sys Fixes #3475. --- src/libextra/arena.rs | 29 +++-- src/libextra/dbg.rs | 34 +++--- src/librustc/driver/driver.rs | 3 - src/librustc/front/intrinsic.rs | 148 ------------------------ src/librustc/front/intrinsic_inject.rs | 47 -------- src/librustc/middle/lang_items.rs | 24 +++- src/librustc/middle/trans/reflect.rs | 8 +- src/librustc/middle/ty.rs | 27 +++-- src/librustc/middle/typeck/check/mod.rs | 8 +- src/librustc/middle/typeck/collect.rs | 55 ++------- src/librustc/rustc.rc | 1 - src/libstd/at_vec.rs | 13 ++- src/libstd/cleanup.rs | 28 +++-- src/libstd/managed.rs | 2 +- src/libstd/reflect.rs | 6 +- src/libstd/repr.rs | 20 +++- src/libstd/rt/global_heap.rs | 10 +- src/libstd/sys.rs | 12 +- src/libstd/unstable/exchange_alloc.rs | 10 +- src/libstd/unstable/intrinsics.rs | 129 ++++++++++++++++++++- src/libstd/vec.rs | 15 ++- src/test/run-pass/extern-pub.rs | 6 +- src/test/run-pass/reflect-visit-data.rs | 20 ++-- 23 files changed, 298 insertions(+), 357 deletions(-) delete mode 100644 src/librustc/front/intrinsic.rs delete mode 100644 src/librustc/front/intrinsic_inject.rs diff --git a/src/libextra/arena.rs b/src/libextra/arena.rs index db4cf564babc..a7d5660cd2e4 100644 --- a/src/libextra/arena.rs +++ b/src/libextra/arena.rs @@ -43,20 +43,27 @@ use core::cast::{transmute, transmute_mut_region}; use core::cast; use core::libc::size_t; use core::ptr; -use core::sys::TypeDesc; use core::sys; use core::uint; use core::vec; use core::unstable::intrinsics; +#[cfg(stage0)] +use intrinsic::{get_tydesc, TyDesc}; +#[cfg(not(stage0))] +use core::unstable::intrinsics::{get_tydesc, TyDesc}; + pub mod rustrt { use core::libc::size_t; - use core::sys::TypeDesc; + #[cfg(stage0)] + use intrinsic::{TyDesc}; + #[cfg(not(stage0))] + use core::unstable::intrinsics::{TyDesc}; pub extern { #[rust_stack] unsafe fn rust_call_tydesc_glue(root: *u8, - tydesc: *TypeDesc, + tydesc: *TyDesc, field: size_t); } } @@ -136,7 +143,7 @@ unsafe fn destroy_chunk(chunk: &Chunk) { let (tydesc, is_done) = un_bitpack_tydesc_ptr(*tydesc_data); let (size, align) = ((*tydesc).size, (*tydesc).align); - let after_tydesc = idx + sys::size_of::<*TypeDesc>(); + let after_tydesc = idx + sys::size_of::<*TyDesc>(); let start = round_up_to(after_tydesc, align); @@ -148,7 +155,7 @@ unsafe fn destroy_chunk(chunk: &Chunk) { } // Find where the next tydesc lives - idx = round_up_to(start + size, sys::pref_align_of::<*TypeDesc>()); + idx = round_up_to(start + size, sys::pref_align_of::<*TyDesc>()); } } @@ -157,12 +164,12 @@ unsafe fn destroy_chunk(chunk: &Chunk) { // is necessary in order to properly do cleanup if a failure occurs // during an initializer. #[inline] -unsafe fn bitpack_tydesc_ptr(p: *TypeDesc, is_done: bool) -> uint { +unsafe fn bitpack_tydesc_ptr(p: *TyDesc, is_done: bool) -> uint { let p_bits: uint = transmute(p); p_bits | (is_done as uint) } #[inline] -unsafe fn un_bitpack_tydesc_ptr(p: uint) -> (*TypeDesc, bool) { +unsafe fn un_bitpack_tydesc_ptr(p: uint) -> (*TyDesc, bool) { (transmute(p & !1), p & 1 == 1) } @@ -202,7 +209,7 @@ impl Arena { #[inline] fn alloc_pod<'a, T>(&'a mut self, op: &fn() -> T) -> &'a T { unsafe { - let tydesc = sys::get_type_desc::(); + let tydesc = get_tydesc::(); let ptr = self.alloc_pod_inner((*tydesc).size, (*tydesc).align); let ptr: *mut T = transmute(ptr); intrinsics::move_val_init(&mut (*ptr), op()); @@ -230,13 +237,13 @@ impl Arena { let head = transmute_mut_region(&mut self.head); let tydesc_start = head.fill; - let after_tydesc = head.fill + sys::size_of::<*TypeDesc>(); + let after_tydesc = head.fill + sys::size_of::<*TyDesc>(); let start = round_up_to(after_tydesc, align); let end = start + n_bytes; if end > at_vec::capacity(head.data) { return self.alloc_nonpod_grow(n_bytes, align); } - head.fill = round_up_to(end, sys::pref_align_of::<*TypeDesc>()); + head.fill = round_up_to(end, sys::pref_align_of::<*TyDesc>()); //debug!("idx = %u, size = %u, align = %u, fill = %u", // start, n_bytes, align, head.fill); @@ -249,7 +256,7 @@ impl Arena { #[inline] fn alloc_nonpod<'a, T>(&'a mut self, op: &fn() -> T) -> &'a T { unsafe { - let tydesc = sys::get_type_desc::(); + let tydesc = get_tydesc::(); let (ty_ptr, ptr) = self.alloc_nonpod_inner((*tydesc).size, (*tydesc).align); let ty_ptr: *mut uint = transmute(ty_ptr); diff --git a/src/libextra/dbg.rs b/src/libextra/dbg.rs index cbd7cb5e3c08..43c4aecdd27f 100644 --- a/src/libextra/dbg.rs +++ b/src/libextra/dbg.rs @@ -13,56 +13,62 @@ #[allow(missing_doc)]; use core::cast::transmute; -use core::sys; +#[cfg(stage0)] +use intrinsic::{get_tydesc}; +#[cfg(not(stage0))] +use core::unstable::intrinsics::{get_tydesc}; pub mod rustrt { - use core::sys; + #[cfg(stage0)] + use intrinsic::{TyDesc}; + #[cfg(not(stage0))] + use core::unstable::intrinsics::{TyDesc}; #[abi = "cdecl"] pub extern { - pub unsafe fn debug_tydesc(td: *sys::TypeDesc); - pub unsafe fn debug_opaque(td: *sys::TypeDesc, x: *()); - pub unsafe fn debug_box(td: *sys::TypeDesc, x: *()); - pub unsafe fn debug_tag(td: *sys::TypeDesc, x: *()); - pub unsafe fn debug_fn(td: *sys::TypeDesc, x: *()); - pub unsafe fn debug_ptrcast(td: *sys::TypeDesc, x: *()) -> *(); + pub unsafe fn debug_tydesc(td: *TyDesc); + pub unsafe fn debug_opaque(td: *TyDesc, x: *()); + pub unsafe fn debug_box(td: *TyDesc, x: *()); + pub unsafe fn debug_tag(td: *TyDesc, x: *()); + pub unsafe fn debug_fn(td: *TyDesc, x: *()); + pub unsafe fn debug_ptrcast(td: *TyDesc, x: *()) -> *(); pub unsafe fn rust_dbg_breakpoint(); } } pub fn debug_tydesc() { unsafe { - rustrt::debug_tydesc(sys::get_type_desc::()); + rustrt::debug_tydesc(get_tydesc::()); } } pub fn debug_opaque(x: T) { unsafe { - rustrt::debug_opaque(sys::get_type_desc::(), transmute(&x)); + rustrt::debug_opaque(get_tydesc::(), transmute(&x)); } } pub fn debug_box(x: @T) { unsafe { - rustrt::debug_box(sys::get_type_desc::(), transmute(&x)); + rustrt::debug_box(get_tydesc::(), transmute(&x)); } } pub fn debug_tag(x: T) { unsafe { - rustrt::debug_tag(sys::get_type_desc::(), transmute(&x)); + rustrt::debug_tag(get_tydesc::(), transmute(&x)); } } pub fn debug_fn(x: T) { unsafe { - rustrt::debug_fn(sys::get_type_desc::(), transmute(&x)); + rustrt::debug_fn(get_tydesc::(), transmute(&x)); } } pub unsafe fn ptr_cast(x: @T) -> @U { transmute( - rustrt::debug_ptrcast(sys::get_type_desc::(), transmute(x))) + rustrt::debug_ptrcast(get_tydesc::(), transmute(x))) } /// Triggers a debugger breakpoint diff --git a/src/librustc/driver/driver.rs b/src/librustc/driver/driver.rs index 1a7041c08840..fbb273450df2 100644 --- a/src/librustc/driver/driver.rs +++ b/src/librustc/driver/driver.rs @@ -206,9 +206,6 @@ pub fn compile_rest(sess: Session, let mut crate = crate_opt.unwrap(); let (llcx, llmod, link_meta) = { - crate = time(time_passes, ~"intrinsic injection", || - front::intrinsic_inject::inject_intrinsic(sess, crate)); - crate = time(time_passes, ~"extra injection", || front::std_inject::maybe_inject_libstd_ref(sess, crate)); diff --git a/src/librustc/front/intrinsic.rs b/src/librustc/front/intrinsic.rs deleted file mode 100644 index f19e37062535..000000000000 --- a/src/librustc/front/intrinsic.rs +++ /dev/null @@ -1,148 +0,0 @@ -// Copyright 2012 The Rust Project Developers. See the COPYRIGHT -// file at the top-level directory of this distribution and at -// http://rust-lang.org/COPYRIGHT. -// -// Licensed under the Apache License, Version 2.0 or the MIT license -// , at your -// option. This file may not be copied, modified, or distributed -// except according to those terms. - -// NB: this file is include_str!'ed into the compiler, re-parsed -// and injected into each crate the compiler builds. Keep it small. - -pub mod intrinsic { - #[allow(missing_doc)]; - - pub use intrinsic::rusti::visit_tydesc; - - // FIXME (#3727): remove this when the interface has settled and the - // version in sys is no longer present. - pub fn get_tydesc() -> *TyDesc { - unsafe { - rusti::get_tydesc::() - } - } - - pub type GlueFn = extern "Rust" fn(**TyDesc, *i8); - - // NB: this has to be kept in sync with the Rust ABI. - pub struct TyDesc { - size: uint, - align: uint, - take_glue: GlueFn, - drop_glue: GlueFn, - free_glue: GlueFn, - visit_glue: GlueFn, - shape: *i8, - shape_tables: *i8 - } - - pub enum Opaque { } - - pub trait TyVisitor { - fn visit_bot(&self) -> bool; - fn visit_nil(&self) -> bool; - fn visit_bool(&self) -> bool; - - fn visit_int(&self) -> bool; - fn visit_i8(&self) -> bool; - fn visit_i16(&self) -> bool; - fn visit_i32(&self) -> bool; - fn visit_i64(&self) -> bool; - - fn visit_uint(&self) -> bool; - fn visit_u8(&self) -> bool; - fn visit_u16(&self) -> bool; - fn visit_u32(&self) -> bool; - fn visit_u64(&self) -> bool; - - fn visit_float(&self) -> bool; - fn visit_f32(&self) -> bool; - fn visit_f64(&self) -> bool; - - fn visit_char(&self) -> bool; - fn visit_str(&self) -> bool; - - fn visit_estr_box(&self) -> bool; - fn visit_estr_uniq(&self) -> bool; - fn visit_estr_slice(&self) -> bool; - fn visit_estr_fixed(&self, n: uint, sz: uint, align: uint) -> bool; - - fn visit_box(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_uniq(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_ptr(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_rptr(&self, mtbl: uint, inner: *TyDesc) -> bool; - - fn visit_vec(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_unboxed_vec(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_evec_box(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_evec_uniq(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_evec_slice(&self, mtbl: uint, inner: *TyDesc) -> bool; - fn visit_evec_fixed(&self, n: uint, sz: uint, align: uint, - mtbl: uint, inner: *TyDesc) -> bool; - - fn visit_enter_rec(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - fn visit_rec_field(&self, i: uint, name: &str, - mtbl: uint, inner: *TyDesc) -> bool; - fn visit_leave_rec(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - - fn visit_enter_class(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - fn visit_class_field(&self, i: uint, name: &str, - mtbl: uint, inner: *TyDesc) -> bool; - fn visit_leave_class(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - - fn visit_enter_tup(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - fn visit_tup_field(&self, i: uint, inner: *TyDesc) -> bool; - fn visit_leave_tup(&self, n_fields: uint, - sz: uint, align: uint) -> bool; - - fn visit_enter_enum(&self, n_variants: uint, - get_disr: extern unsafe fn(ptr: *Opaque) -> int, - sz: uint, align: uint) -> bool; - fn visit_enter_enum_variant(&self, variant: uint, - disr_val: int, - n_fields: uint, - name: &str) -> bool; - fn visit_enum_variant_field(&self, i: uint, offset: uint, inner: *TyDesc) -> bool; - fn visit_leave_enum_variant(&self, variant: uint, - disr_val: int, - n_fields: uint, - name: &str) -> bool; - fn visit_leave_enum(&self, n_variants: uint, - get_disr: extern unsafe fn(ptr: *Opaque) -> int, - sz: uint, align: uint) -> bool; - - fn visit_enter_fn(&self, purity: uint, proto: uint, - n_inputs: uint, retstyle: uint) -> bool; - fn visit_fn_input(&self, i: uint, mode: uint, inner: *TyDesc) -> bool; - fn visit_fn_output(&self, retstyle: uint, inner: *TyDesc) -> bool; - fn visit_leave_fn(&self, purity: uint, proto: uint, - n_inputs: uint, retstyle: uint) -> bool; - - fn visit_trait(&self) -> bool; - fn visit_var(&self) -> bool; - fn visit_var_integral(&self) -> bool; - fn visit_param(&self, i: uint) -> bool; - fn visit_self(&self) -> bool; - fn visit_type(&self) -> bool; - fn visit_opaque_box(&self) -> bool; - fn visit_constr(&self, inner: *TyDesc) -> bool; - fn visit_closure_ptr(&self, ck: uint) -> bool; - } - - pub mod rusti { - use super::{TyDesc, TyVisitor}; - - #[abi = "rust-intrinsic"] - pub extern "rust-intrinsic" { - pub fn get_tydesc() -> *TyDesc; - pub fn visit_tydesc(td: *TyDesc, tv: @TyVisitor); - } - } -} diff --git a/src/librustc/front/intrinsic_inject.rs b/src/librustc/front/intrinsic_inject.rs deleted file mode 100644 index 0caadc8572e9..000000000000 --- a/src/librustc/front/intrinsic_inject.rs +++ /dev/null @@ -1,47 +0,0 @@ -// Copyright 2012 The Rust Project Developers. See the COPYRIGHT -// file at the top-level directory of this distribution and at -// http://rust-lang.org/COPYRIGHT. -// -// Licensed under the Apache License, Version 2.0 or the MIT license -// , at your -// option. This file may not be copied, modified, or distributed -// except according to those terms. - -use core::prelude::*; - -use core::vec; -use driver::session::Session; -use syntax::parse; -use syntax::ast; -use syntax::codemap::spanned; - -pub fn inject_intrinsic(sess: Session, crate: @ast::crate) -> @ast::crate { - let intrinsic_module = include_str!("intrinsic.rs").to_managed(); - - let item = parse::parse_item_from_source_str(@"", - intrinsic_module, - /*bad*/copy sess.opts.cfg, - ~[], - sess.parse_sess); - let item = - match item { - Some(i) => i, - None => { - sess.fatal("no item found in intrinsic module"); - } - }; - - let items = vec::append(~[item], crate.node.module.items); - - @spanned { - node: ast::crate_ { - module: ast::_mod { - items: items, - .. /*bad*/copy crate.node.module - }, - .. /*bad*/copy crate.node - }, - .. /*bad*/copy *crate - } -} diff --git a/src/librustc/middle/lang_items.rs b/src/librustc/middle/lang_items.rs index 3a8d369469b1..d73b019c1ea7 100644 --- a/src/librustc/middle/lang_items.rs +++ b/src/librustc/middle/lang_items.rs @@ -76,16 +76,20 @@ pub enum LangItem { UnrecordBorrowFnLangItem, // 36 StartFnLangItem, // 37 + + TyDescStructLangItem, // 38 + TyVisitorTraitLangItem, // 39 + OpaqueStructLangItem, // 40 } pub struct LanguageItems { - items: [Option, ..38] + items: [Option, ..41] } impl LanguageItems { pub fn new() -> LanguageItems { LanguageItems { - items: [ None, ..38 ] + items: [ None, ..41 ] } } @@ -138,6 +142,10 @@ impl LanguageItems { 37 => "start", + 38 => "ty_desc", + 39 => "ty_visitor", + 40 => "opaque", + _ => "???" } } @@ -262,6 +270,15 @@ impl LanguageItems { pub fn start_fn(&const self) -> def_id { self.items[StartFnLangItem as uint].get() } + pub fn ty_desc(&const self) -> def_id { + self.items[TyDescStructLangItem as uint].get() + } + pub fn ty_visitor(&const self) -> def_id { + self.items[TyVisitorTraitLangItem as uint].get() + } + pub fn opaque(&const self) -> def_id { + self.items[OpaqueStructLangItem as uint].get() + } } fn LanguageItemCollector(crate: @crate, @@ -313,6 +330,9 @@ fn LanguageItemCollector(crate: @crate, item_refs.insert(@"record_borrow", RecordBorrowFnLangItem as uint); item_refs.insert(@"unrecord_borrow", UnrecordBorrowFnLangItem as uint); item_refs.insert(@"start", StartFnLangItem as uint); + item_refs.insert(@"ty_desc", TyDescStructLangItem as uint); + item_refs.insert(@"ty_visitor", TyVisitorTraitLangItem as uint); + item_refs.insert(@"opaque", OpaqueStructLangItem as uint); LanguageItemCollector { crate: crate, diff --git a/src/librustc/middle/trans/reflect.rs b/src/librustc/middle/trans/reflect.rs index cb68a2af92bb..9e5510fc6058 100644 --- a/src/librustc/middle/trans/reflect.rs +++ b/src/librustc/middle/trans/reflect.rs @@ -274,9 +274,7 @@ impl Reflector { let repr = adt::represent_type(bcx.ccx(), t); let variants = ty::substd_enum_variants(ccx.tcx, did, substs); let llptrty = type_of(ccx, t).ptr_to(); - let (_, opaquety) = - ccx.tcx.intrinsic_defs.find_copy(&ccx.sess.ident_of("Opaque")) - .expect("Failed to resolve intrinsic::Opaque"); + let opaquety = ty::get_opaque_ty(ccx.tcx); let opaqueptrty = ty::mk_ptr(ccx.tcx, ty::mt { ty: opaquety, mutbl: ast::m_imm }); let make_get_disr = || { @@ -373,10 +371,8 @@ pub fn emit_calls_to_trait_visit_ty(bcx: block, visitor_val: ValueRef, visitor_trait_id: def_id) -> block { - use syntax::parse::token::special_idents::tydesc; let final = sub_block(bcx, "final"); - assert!(bcx.ccx().tcx.intrinsic_defs.contains_key(&tydesc)); - let (_, tydesc_ty) = bcx.ccx().tcx.intrinsic_defs.get_copy(&tydesc); + let tydesc_ty = ty::get_tydesc_ty(bcx.ccx().tcx); let tydesc_ty = type_of(bcx.ccx(), tydesc_ty); let mut r = Reflector { visitor_val: visitor_val, diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index a367cf4c430a..f12ecebc6d5c 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -44,7 +44,6 @@ use syntax::attr; use syntax::codemap::span; use syntax::codemap; use syntax::parse::token; -use syntax::parse::token::special_idents; use syntax::{ast, ast_map}; use syntax::opt_vec::OptVec; use syntax::opt_vec; @@ -276,8 +275,7 @@ struct ctxt_ { trait_defs: @mut HashMap, items: ast_map::map, - intrinsic_defs: @mut HashMap, - intrinsic_traits: @mut HashMap, + intrinsic_defs: @mut HashMap, freevars: freevars::freevar_map, tcache: type_cache, rcache: creader_cache, @@ -953,7 +951,6 @@ pub fn mk_ctxt(s: session::Session, node_type_substs: @mut HashMap::new(), trait_refs: @mut HashMap::new(), trait_defs: @mut HashMap::new(), - intrinsic_traits: @mut HashMap::new(), items: amap, intrinsic_defs: @mut HashMap::new(), freevars: freevars, @@ -4449,10 +4446,26 @@ pub fn get_impl_id(tcx: ctxt, trait_id: def_id, self_ty: t) -> def_id { } } +pub fn get_tydesc_ty(tcx: ctxt) -> t { + let tydesc_lang_item = tcx.lang_items.ty_desc(); + tcx.intrinsic_defs.find_copy(&tydesc_lang_item) + .expect("Failed to resolve TyDesc") +} + +pub fn get_opaque_ty(tcx: ctxt) -> t { + let tydesc_lang_item = tcx.lang_items.opaque(); + tcx.intrinsic_defs.find_copy(&tydesc_lang_item) + .expect("Failed to resolve Opaque") +} + pub fn visitor_object_ty(tcx: ctxt) -> (@TraitRef, t) { - let ty_visitor_name = special_idents::ty_visitor; - assert!(tcx.intrinsic_traits.contains_key(&ty_visitor_name)); - let trait_ref = tcx.intrinsic_traits.get_copy(&ty_visitor_name); + let substs = substs { + self_r: None, + self_ty: None, + tps: ~[] + }; + let trait_lang_item = tcx.lang_items.ty_visitor(); + let trait_ref = @TraitRef { def_id: trait_lang_item, substs: substs }; (trait_ref, mk_trait(tcx, trait_ref.def_id, copy trait_ref.substs, BoxTraitStore, ast::m_imm)) } diff --git a/src/librustc/middle/typeck/check/mod.rs b/src/librustc/middle/typeck/check/mod.rs index 4c074ce197ed..821daee8bfbf 100644 --- a/src/librustc/middle/typeck/check/mod.rs +++ b/src/librustc/middle/typeck/check/mod.rs @@ -3506,9 +3506,7 @@ pub fn check_intrinsic_type(ccx: @mut CrateCtxt, it: @ast::foreign_item) { } "get_tydesc" => { - let tydesc_name = special_idents::tydesc; - assert!(tcx.intrinsic_defs.contains_key(&tydesc_name)); - let (_, tydesc_ty) = tcx.intrinsic_defs.get_copy(&tydesc_name); + let tydesc_ty = ty::get_tydesc_ty(ccx.tcx); let td_ptr = ty::mk_ptr(ccx.tcx, ty::mt { ty: tydesc_ty, mutbl: ast::m_imm @@ -3516,9 +3514,7 @@ pub fn check_intrinsic_type(ccx: @mut CrateCtxt, it: @ast::foreign_item) { (1u, ~[], td_ptr) } "visit_tydesc" => { - let tydesc_name = special_idents::tydesc; - assert!(tcx.intrinsic_defs.contains_key(&tydesc_name)); - let (_, tydesc_ty) = tcx.intrinsic_defs.get_copy(&tydesc_name); + let tydesc_ty = ty::get_tydesc_ty(ccx.tcx); let (_, visitor_object_ty) = ty::visitor_object_ty(tcx); let td_ptr = ty::mk_ptr(ccx.tcx, ty::mt { ty: tydesc_ty, diff --git a/src/librustc/middle/typeck/collect.rs b/src/librustc/middle/typeck/collect.rs index 7f820d11ac61..756bb4d1bb92 100644 --- a/src/librustc/middle/typeck/collect.rs +++ b/src/librustc/middle/typeck/collect.rs @@ -62,55 +62,16 @@ use syntax::opt_vec::OptVec; use syntax::opt_vec; pub fn collect_item_types(ccx: @mut CrateCtxt, crate: @ast::crate) { - - // FIXME (#2592): hooking into the "intrinsic" root module is crude. - // There ought to be a better approach. Attributes? - - for crate.node.module.items.iter().advance |crate_item| { - if crate_item.ident - == ::syntax::parse::token::special_idents::intrinsic { - - match crate_item.node { - ast::item_mod(ref m) => { - for m.items.iter().advance |intrinsic_item| { - let def_id = ast::def_id { crate: ast::local_crate, - node: intrinsic_item.id }; - let substs = substs { - self_r: None, - self_ty: None, - tps: ~[] - }; - - match intrinsic_item.node { - ast::item_trait(*) => { - let tref = @ty::TraitRef {def_id: def_id, - substs: substs}; - ccx.tcx.intrinsic_traits.insert - (intrinsic_item.ident, tref); - } - - ast::item_enum(*) => { - let ty = ty::mk_enum(ccx.tcx, def_id, substs); - ccx.tcx.intrinsic_defs.insert - (intrinsic_item.ident, (def_id, ty)); - } - - ast::item_struct(*) => { - let ty = ty::mk_struct(ccx.tcx, def_id, substs); - ccx.tcx.intrinsic_defs.insert - (intrinsic_item.ident, (def_id, ty)); - } - - _ => {} - } - } - } - _ => { } - } - break; - } + fn collect_intrinsic_type(ccx: @mut CrateCtxt, + lang_item: ast::def_id) { + let ty::ty_param_bounds_and_ty { ty: ty, _ } = + ccx.get_item_ty(lang_item); + ccx.tcx.intrinsic_defs.insert(lang_item, ty); } + collect_intrinsic_type(ccx, ccx.tcx.lang_items.ty_desc()); + collect_intrinsic_type(ccx, ccx.tcx.lang_items.opaque()); + visit::visit_crate( crate, ((), visit::mk_simple_visitor(@visit::SimpleVisitor { diff --git a/src/librustc/rustc.rc b/src/librustc/rustc.rc index d59a308beb53..20705b3d7975 100644 --- a/src/librustc/rustc.rc +++ b/src/librustc/rustc.rc @@ -86,7 +86,6 @@ pub mod front { pub mod config; pub mod test; pub mod std_inject; - pub mod intrinsic_inject; } pub mod back { diff --git a/src/libstd/at_vec.rs b/src/libstd/at_vec.rs index 2b846c923c48..52115692dbce 100644 --- a/src/libstd/at_vec.rs +++ b/src/libstd/at_vec.rs @@ -26,13 +26,16 @@ use vec::ImmutableVector; pub mod rustrt { use libc; - use sys; use vec; + #[cfg(stage0)] + use intrinsic::{TyDesc}; + #[cfg(not(stage0))] + use unstable::intrinsics::{TyDesc}; #[abi = "cdecl"] #[link_name = "rustrt"] pub extern { - pub unsafe fn vec_reserve_shared_actual(t: *sys::TypeDesc, + pub unsafe fn vec_reserve_shared_actual(t: *TyDesc, v: **vec::raw::VecRepr, n: libc::size_t); } @@ -198,6 +201,10 @@ pub mod raw { use uint; use unstable::intrinsics::{move_val_init}; use vec; + #[cfg(stage0)] + use intrinsic::{get_tydesc}; + #[cfg(not(stage0))] + use unstable::intrinsics::{get_tydesc}; pub type VecRepr = vec::raw::VecRepr; pub type SliceRepr = vec::raw::SliceRepr; @@ -259,7 +266,7 @@ pub mod raw { // Only make the (slow) call into the runtime if we have to if capacity(*v) < n { let ptr: **VecRepr = transmute(v); - rustrt::vec_reserve_shared_actual(sys::get_type_desc::(), + rustrt::vec_reserve_shared_actual(get_tydesc::(), ptr, n as libc::size_t); } } diff --git a/src/libstd/cleanup.rs b/src/libstd/cleanup.rs index d1460b7a3c96..28aab9adad2c 100644 --- a/src/libstd/cleanup.rs +++ b/src/libstd/cleanup.rs @@ -10,24 +10,18 @@ #[doc(hidden)]; -use libc::{c_char, c_void, intptr_t, uintptr_t}; -use ptr::mut_null; +use libc::{c_char, intptr_t, uintptr_t}; +use ptr::{mut_null, to_unsafe_ptr}; use repr::BoxRepr; -use sys::TypeDesc; use cast::transmute; #[cfg(not(test))] use unstable::lang::clear_task_borrow_list; -#[cfg(not(test))] use ptr::to_unsafe_ptr; - /** * Runtime structures * * NB: These must match the representation in the C++ runtime. */ -type DropGlue<'self> = &'self fn(**TypeDesc, *c_void); -type FreeGlue<'self> = &'self fn(**TypeDesc, *c_void); - type TaskID = uintptr_t; struct StackSegment { priv opaque: () } @@ -164,6 +158,20 @@ fn debug_mem() -> bool { false } +#[cfg(stage0)] +unsafe fn call_drop_glue(tydesc: *::std::unstable::intrinsics::TyDesc, data: *i8) { + use sys::TypeDesc; + + let tydesc: *TypeDesc = transmute(tydesc); + let drop_glue: extern "Rust" fn(**TypeDesc, *i8) = transmute((*tydesc).drop_glue); + drop_glue(to_unsafe_ptr(&tydesc), data); +} + +#[cfg(not(stage0))] +unsafe fn call_drop_glue(tydesc: *::std::unstable::intrinsics::TyDesc, data: *i8) { + ((*tydesc).drop_glue)(to_unsafe_ptr(&tydesc), data); +} + /// Destroys all managed memory (i.e. @ boxes) held by the current task. #[cfg(not(test))] #[lang="annihilate"] @@ -205,9 +213,7 @@ pub unsafe fn annihilate() { // callback, as the original value may have been freed. for each_live_alloc(false) |box, uniq| { if !uniq { - let tydesc: *TypeDesc = transmute(copy (*box).header.type_desc); - let drop_glue: DropGlue = transmute(((*tydesc).drop_glue, 0)); - drop_glue(to_unsafe_ptr(&tydesc), transmute(&(*box).data)); + call_drop_glue((*box).header.type_desc, transmute(&(*box).data)); } } diff --git a/src/libstd/managed.rs b/src/libstd/managed.rs index d514612b5afd..b71b3b503c2a 100644 --- a/src/libstd/managed.rs +++ b/src/libstd/managed.rs @@ -15,7 +15,7 @@ use ptr::to_unsafe_ptr; #[cfg(not(test))] use cmp::{Eq, Ord}; pub mod raw { - use intrinsic::TyDesc; + use std::unstable::intrinsics::TyDesc; pub static RC_EXCHANGE_UNIQUE : uint = (-1) as uint; pub static RC_MANAGED_UNIQUE : uint = (-2) as uint; diff --git a/src/libstd/reflect.rs b/src/libstd/reflect.rs index d276abf0c8b3..16ab4771d0de 100644 --- a/src/libstd/reflect.rs +++ b/src/libstd/reflect.rs @@ -16,8 +16,10 @@ Runtime type reflection #[allow(missing_doc)]; -use intrinsic::{TyDesc, TyVisitor}; -use intrinsic::Opaque; +#[cfg(stage0)] +use intrinsic::{Opaque, TyDesc, TyVisitor}; +#[cfg(not(stage0))] +use unstable::intrinsics::{Opaque, TyDesc, TyVisitor}; use libc::c_void; use sys; use vec; diff --git a/src/libstd/repr.rs b/src/libstd/repr.rs index ab3f83d34d59..f39b5a00ed05 100644 --- a/src/libstd/repr.rs +++ b/src/libstd/repr.rs @@ -19,9 +19,6 @@ More runtime type reflection use cast::transmute; use char; use container::Container; -use intrinsic; -use intrinsic::{TyDesc, TyVisitor, visit_tydesc}; -use intrinsic::Opaque; use io::{Writer, WriterUtil}; use iterator::IteratorUtil; use libc::c_void; @@ -34,6 +31,10 @@ use to_str::ToStr; use vec::raw::{VecRepr, SliceRepr}; use vec; use vec::{OwnedVector, UnboxedVecRepr}; +#[cfg(stage0)] +use intrinsic::{Opaque, TyDesc, TyVisitor, get_tydesc, visit_tydesc}; +#[cfg(not(stage0))] +use unstable::intrinsics::{Opaque, TyDesc, TyVisitor, get_tydesc, visit_tydesc}; #[cfg(test)] use io; @@ -564,6 +565,7 @@ impl TyVisitor for ReprVisitor { fn visit_self(&self) -> bool { true } fn visit_type(&self) -> bool { true } + #[cfg(not(stage0))] fn visit_opaque_box(&self) -> bool { self.writer.write_char('@'); do self.get::<&managed::raw::BoxRepr> |b| { @@ -571,6 +573,16 @@ impl TyVisitor for ReprVisitor { self.visit_ptr_inner(p, b.header.type_desc); } } + #[cfg(stage0)] + fn visit_opaque_box(&self) -> bool { + self.writer.write_char('@'); + do self.get::<&managed::raw::BoxRepr> |b| { + let p = ptr::to_unsafe_ptr(&b.data) as *c_void; + unsafe { + self.visit_ptr_inner(p, transmute(b.header.type_desc)); + } + } + } // Type no longer exists, vestigial function. fn visit_constr(&self, _inner: *TyDesc) -> bool { fail!(); } @@ -581,7 +593,7 @@ impl TyVisitor for ReprVisitor { pub fn write_repr(writer: @Writer, object: &T) { unsafe { let ptr = ptr::to_unsafe_ptr(object) as *c_void; - let tydesc = intrinsic::get_tydesc::(); + let tydesc = get_tydesc::(); let u = ReprVisitor(ptr, writer); let v = reflect::MovePtrAdaptor(u); visit_tydesc(tydesc, @v as @TyVisitor) diff --git a/src/libstd/rt/global_heap.rs b/src/libstd/rt/global_heap.rs index ce7ff87b4458..1e9f9aab8345 100644 --- a/src/libstd/rt/global_heap.rs +++ b/src/libstd/rt/global_heap.rs @@ -8,26 +8,22 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use sys::{TypeDesc, size_of}; +use sys::{size_of}; use libc::{c_void, size_t, uintptr_t}; use c_malloc = libc::malloc; use c_free = libc::free; use managed::raw::{BoxHeaderRepr, BoxRepr}; use cast::transmute; -use unstable::intrinsics::{atomic_xadd,atomic_xsub}; +use unstable::intrinsics::{atomic_xadd,atomic_xsub,TyDesc}; use ptr::null; -use intrinsic::TyDesc; -pub unsafe fn malloc(td: *TypeDesc, size: uint) -> *c_void { +pub unsafe fn malloc(td: *TyDesc, size: uint) -> *c_void { assert!(td.is_not_null()); let total_size = get_box_size(size, (*td).align); let p = c_malloc(total_size as size_t); assert!(p.is_not_null()); - // FIXME #3475: Converting between our two different tydesc types - let td: *TyDesc = transmute(td); - let box: &mut BoxRepr = transmute(p); box.header.ref_count = -1; // Exchange values not ref counted box.header.type_desc = td; diff --git a/src/libstd/sys.rs b/src/libstd/sys.rs index 79ea60cc2240..7f80375c2f6a 100644 --- a/src/libstd/sys.rs +++ b/src/libstd/sys.rs @@ -17,14 +17,13 @@ use cast; use gc; use io; use libc; -use libc::{c_void, c_char, size_t}; +use libc::{c_char, size_t}; use repr; use str; use unstable::intrinsics; -pub type FreeGlue<'self> = &'self fn(*TypeDesc, *c_void); - // Corresponds to runtime type_desc type +#[cfg(stage0)] pub struct TypeDesc { size: uint, align: uint, @@ -58,16 +57,11 @@ pub mod rustrt { * performing dark magick. */ #[inline] +#[cfg(stage0)] pub fn get_type_desc() -> *TypeDesc { unsafe { intrinsics::get_tydesc::() as *TypeDesc } } -/// Returns a pointer to a type descriptor. -#[inline] -pub fn get_type_desc_val(_val: &T) -> *TypeDesc { - get_type_desc::() -} - /// Returns the size of a type #[inline] pub fn size_of() -> uint { diff --git a/src/libstd/unstable/exchange_alloc.rs b/src/libstd/unstable/exchange_alloc.rs index 3b35c2fb8047..5c47901df480 100644 --- a/src/libstd/unstable/exchange_alloc.rs +++ b/src/libstd/unstable/exchange_alloc.rs @@ -8,7 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use sys::{TypeDesc, size_of}; +use sys::size_of; use libc::{c_void, size_t}; use c_malloc = libc::malloc; use c_free = libc::free; @@ -16,18 +16,18 @@ use managed::raw::{BoxHeaderRepr, BoxRepr}; use cast::transmute; use unstable::intrinsics::{atomic_xadd,atomic_xsub}; use ptr::null; +#[cfg(stage0)] use intrinsic::TyDesc; +#[cfg(not(stage0))] +use unstable::intrinsics::TyDesc; -pub unsafe fn malloc(td: *TypeDesc, size: uint) -> *c_void { +pub unsafe fn malloc(td: *TyDesc, size: uint) -> *c_void { assert!(td.is_not_null()); let total_size = get_box_size(size, (*td).align); let p = c_malloc(total_size as size_t); assert!(p.is_not_null()); - // FIXME #3475: Converting between our two different tydesc types - let td: *TyDesc = transmute(td); - let box: &mut BoxRepr = transmute(p); box.header.ref_count = -1; // Exchange values not ref counted box.header.type_desc = td; diff --git a/src/libstd/unstable/intrinsics.rs b/src/libstd/unstable/intrinsics.rs index 08fc90fa908c..a51ba05710b1 100644 --- a/src/libstd/unstable/intrinsics.rs +++ b/src/libstd/unstable/intrinsics.rs @@ -32,6 +32,128 @@ A quick refresher on memory ordering: */ +// This is needed to prevent duplicate lang item definitions. +#[cfg(test)] +pub use realstd::unstable::intrinsics::{TyDesc, Opaque, TyVisitor}; + +pub type GlueFn = extern "Rust" fn(**TyDesc, *i8); + +// NB: this has to be kept in sync with the Rust ABI. +#[lang="ty_desc"] +#[cfg(not(test))] +pub struct TyDesc { + size: uint, + align: uint, + take_glue: GlueFn, + drop_glue: GlueFn, + free_glue: GlueFn, + visit_glue: GlueFn, + shape: *i8, + shape_tables: *i8 +} + +#[lang="opaque"] +#[cfg(not(test))] +pub enum Opaque { } + +#[lang="ty_visitor"] +#[cfg(not(test))] +pub trait TyVisitor { + fn visit_bot(&self) -> bool; + fn visit_nil(&self) -> bool; + fn visit_bool(&self) -> bool; + + fn visit_int(&self) -> bool; + fn visit_i8(&self) -> bool; + fn visit_i16(&self) -> bool; + fn visit_i32(&self) -> bool; + fn visit_i64(&self) -> bool; + + fn visit_uint(&self) -> bool; + fn visit_u8(&self) -> bool; + fn visit_u16(&self) -> bool; + fn visit_u32(&self) -> bool; + fn visit_u64(&self) -> bool; + + fn visit_float(&self) -> bool; + fn visit_f32(&self) -> bool; + fn visit_f64(&self) -> bool; + + fn visit_char(&self) -> bool; + fn visit_str(&self) -> bool; + + fn visit_estr_box(&self) -> bool; + fn visit_estr_uniq(&self) -> bool; + fn visit_estr_slice(&self) -> bool; + fn visit_estr_fixed(&self, n: uint, sz: uint, align: uint) -> bool; + + fn visit_box(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_uniq(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_ptr(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_rptr(&self, mtbl: uint, inner: *TyDesc) -> bool; + + fn visit_vec(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_unboxed_vec(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_evec_box(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_evec_uniq(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_evec_slice(&self, mtbl: uint, inner: *TyDesc) -> bool; + fn visit_evec_fixed(&self, n: uint, sz: uint, align: uint, + mtbl: uint, inner: *TyDesc) -> bool; + + fn visit_enter_rec(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + fn visit_rec_field(&self, i: uint, name: &str, + mtbl: uint, inner: *TyDesc) -> bool; + fn visit_leave_rec(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + + fn visit_enter_class(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + fn visit_class_field(&self, i: uint, name: &str, + mtbl: uint, inner: *TyDesc) -> bool; + fn visit_leave_class(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + + fn visit_enter_tup(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + fn visit_tup_field(&self, i: uint, inner: *TyDesc) -> bool; + fn visit_leave_tup(&self, n_fields: uint, + sz: uint, align: uint) -> bool; + + fn visit_enter_enum(&self, n_variants: uint, + get_disr: extern unsafe fn(ptr: *Opaque) -> int, + sz: uint, align: uint) -> bool; + fn visit_enter_enum_variant(&self, variant: uint, + disr_val: int, + n_fields: uint, + name: &str) -> bool; + fn visit_enum_variant_field(&self, i: uint, offset: uint, inner: *TyDesc) -> bool; + fn visit_leave_enum_variant(&self, variant: uint, + disr_val: int, + n_fields: uint, + name: &str) -> bool; + fn visit_leave_enum(&self, n_variants: uint, + get_disr: extern unsafe fn(ptr: *Opaque) -> int, + sz: uint, align: uint) -> bool; + + fn visit_enter_fn(&self, purity: uint, proto: uint, + n_inputs: uint, retstyle: uint) -> bool; + fn visit_fn_input(&self, i: uint, mode: uint, inner: *TyDesc) -> bool; + fn visit_fn_output(&self, retstyle: uint, inner: *TyDesc) -> bool; + fn visit_leave_fn(&self, purity: uint, proto: uint, + n_inputs: uint, retstyle: uint) -> bool; + + fn visit_trait(&self) -> bool; + fn visit_var(&self) -> bool; + fn visit_var_integral(&self) -> bool; + fn visit_param(&self, i: uint) -> bool; + fn visit_self(&self) -> bool; + fn visit_type(&self) -> bool; + fn visit_opaque_box(&self) -> bool; + fn visit_constr(&self, inner: *TyDesc) -> bool; + fn visit_closure_ptr(&self, ck: uint) -> bool; +} + #[abi = "rust-intrinsic"] pub extern "rust-intrinsic" { @@ -210,7 +332,7 @@ pub extern "rust-intrinsic" { /// Get a static pointer to a type descriptor. #[cfg(not(stage0))] - pub fn get_tydesc() -> *::intrinsic::TyDesc; + pub fn get_tydesc() -> *TyDesc; #[cfg(stage0)] pub fn get_tydesc() -> *(); @@ -234,9 +356,8 @@ pub extern "rust-intrinsic" { /// Returns `true` if a type requires drop glue. pub fn needs_drop() -> bool; - // XXX: intrinsic uses legacy modes and has reference to TyDesc - // and TyVisitor which are in librustc - //fn visit_tydesc(++td: *TyDesc, &&tv: TyVisitor) -> (); + #[cfg(not(stage0))] + pub fn visit_tydesc(td: *TyDesc, tv: @TyVisitor); pub fn frame_address(f: &once fn(*u8)); diff --git a/src/libstd/vec.rs b/src/libstd/vec.rs index 17eb7e8e82be..fdf33df3a8a1 100644 --- a/src/libstd/vec.rs +++ b/src/libstd/vec.rs @@ -31,6 +31,10 @@ use sys; use sys::size_of; use uint; use unstable::intrinsics; +#[cfg(stage0)] +use intrinsic::{get_tydesc}; +#[cfg(not(stage0))] +use unstable::intrinsics::{get_tydesc}; use vec; use util; @@ -38,19 +42,22 @@ use util; pub mod rustrt { use libc; - use sys; use vec::raw; + #[cfg(stage0)] + use intrinsic::{TyDesc}; + #[cfg(not(stage0))] + use unstable::intrinsics::{TyDesc}; #[abi = "cdecl"] pub extern { // These names are terrible. reserve_shared applies // to ~[] and reserve_shared_actual applies to @[]. #[fast_ffi] - unsafe fn vec_reserve_shared(t: *sys::TypeDesc, + unsafe fn vec_reserve_shared(t: *TyDesc, v: **raw::VecRepr, n: libc::size_t); #[fast_ffi] - unsafe fn vec_reserve_shared_actual(t: *sys::TypeDesc, + unsafe fn vec_reserve_shared_actual(t: *TyDesc, v: **raw::VecRepr, n: libc::size_t); } @@ -79,7 +86,7 @@ pub fn reserve(v: &mut ~[T], n: uint) { if capacity(v) < n { unsafe { let ptr: **raw::VecRepr = cast::transmute(v); - let td = sys::get_type_desc::(); + let td = get_tydesc::(); if ((**ptr).box_header.ref_count == managed::raw::RC_MANAGED_UNIQUE) { rustrt::vec_reserve_shared_actual(td, ptr, n as libc::size_t); diff --git a/src/test/run-pass/extern-pub.rs b/src/test/run-pass/extern-pub.rs index 29b0457fc050..2d6cc2c78deb 100644 --- a/src/test/run-pass/extern-pub.rs +++ b/src/test/run-pass/extern-pub.rs @@ -1,11 +1,7 @@ use std::libc; -use std::sys; -use std::vec; extern { - pub unsafe fn vec_reserve_shared_actual(t: *sys::TypeDesc, - v: **vec::raw::VecRepr, - n: libc::size_t); + pub unsafe fn free(p: *libc::c_void); } pub fn main() { diff --git a/src/test/run-pass/reflect-visit-data.rs b/src/test/run-pass/reflect-visit-data.rs index a8571ab73254..176e49e0ea19 100644 --- a/src/test/run-pass/reflect-visit-data.rs +++ b/src/test/run-pass/reflect-visit-data.rs @@ -10,15 +10,14 @@ // xfail-fast -use std::bool; use std::int; use std::libc::c_void; use std::ptr; use std::sys; use std::vec::UnboxedVecRepr; -use intrinsic::{TyDesc, get_tydesc, visit_tydesc, TyVisitor, Opaque}; +use std::unstable::intrinsics::{TyDesc, get_tydesc, visit_tydesc, TyVisitor, Opaque}; -#[doc = "High-level interfaces to `intrinsic::visit_ty` reflection system."] +#[doc = "High-level interfaces to `std::unstable::intrinsics::visit_ty` reflection system."] /// Trait for visitor that wishes to reflect on data. trait movable_ptr { @@ -637,7 +636,9 @@ impl TyVisitor for my_visitor { } fn get_tydesc_for(_t: T) -> *TyDesc { - get_tydesc::() + unsafe { + get_tydesc::() + } } struct Triple { x: int, y: int, z: int } @@ -651,8 +652,8 @@ pub fn main() { vals: ~[]}); let v = ptr_visit_adaptor(Inner {inner: u}); let td = get_tydesc_for(r); - unsafe { error!("tydesc sz: %u, align: %u", - (*td).size, (*td).align); } + error!("tydesc sz: %u, align: %u", + (*td).size, (*td).align); let v = @v as @TyVisitor; visit_tydesc(td, v); @@ -661,8 +662,7 @@ pub fn main() { println(fmt!("val: %s", *s)); } error!("%?", u.vals.clone()); - assert!(u.vals == ~[ - ~"1", ~"2", ~"3", ~"true", ~"false", ~"5", ~"4", ~"3", ~"12" - ]); + assert_eq!(u.vals.clone(), + ~[ ~"1", ~"2", ~"3", ~"true", ~"false", ~"5", ~"4", ~"3", ~"12"]); } - } +} From 179ce398ea9e09920ace2264144422bb7e9efc02 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Thu, 20 Jun 2013 11:40:17 +0200 Subject: [PATCH 03/31] Fix and reenable the reflect-visit-type test --- src/test/run-pass/reflect-visit-type.rs | 171 +++++++++++++----------- 1 file changed, 91 insertions(+), 80 deletions(-) diff --git a/src/test/run-pass/reflect-visit-type.rs b/src/test/run-pass/reflect-visit-type.rs index 8a7fef956144..3b51abbd489b 100644 --- a/src/test/run-pass/reflect-visit-type.rs +++ b/src/test/run-pass/reflect-visit-type.rs @@ -8,141 +8,153 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// xfail-test -use intrinsic::{TyDesc, get_tydesc, visit_tydesc, TyVisitor}; -struct my_visitor(@mut { types: ~[str] }); +use std::unstable::intrinsics::{TyDesc, get_tydesc, visit_tydesc, TyVisitor, Opaque}; -impl TyVisitor for my_visitor { - fn visit_bot() -> bool { - self.types += ~["bot"]; +struct MyVisitor { + types: @mut ~[~str], +} + +impl TyVisitor for MyVisitor { + fn visit_bot(&self) -> bool { + self.types.push(~"bot"); error!("visited bot type"); true } - fn visit_nil() -> bool { - self.types += ~["nil"]; + fn visit_nil(&self) -> bool { + self.types.push(~"nil"); error!("visited nil type"); true } - fn visit_bool() -> bool { - self.types += ~["bool"]; + fn visit_bool(&self) -> bool { + self.types.push(~"bool"); error!("visited bool type"); true } - fn visit_int() -> bool { - self.types += ~["int"]; + fn visit_int(&self) -> bool { + self.types.push(~"int"); error!("visited int type"); true } - fn visit_i8() -> bool { - self.types += ~["i8"]; + fn visit_i8(&self) -> bool { + self.types.push(~"i8"); error!("visited i8 type"); true } - fn visit_i16() -> bool { - self.types += ~["i16"]; + fn visit_i16(&self) -> bool { + self.types.push(~"i16"); error!("visited i16 type"); true } - fn visit_i32() -> bool { true } - fn visit_i64() -> bool { true } + fn visit_i32(&self) -> bool { true } + fn visit_i64(&self) -> bool { true } - fn visit_uint() -> bool { true } - fn visit_u8() -> bool { true } - fn visit_u16() -> bool { true } - fn visit_u32() -> bool { true } - fn visit_u64() -> bool { true } + fn visit_uint(&self) -> bool { true } + fn visit_u8(&self) -> bool { true } + fn visit_u16(&self) -> bool { true } + fn visit_u32(&self) -> bool { true } + fn visit_u64(&self) -> bool { true } - fn visit_float() -> bool { true } - fn visit_f32() -> bool { true } - fn visit_f64() -> bool { true } + fn visit_float(&self) -> bool { true } + fn visit_f32(&self) -> bool { true } + fn visit_f64(&self) -> bool { true } - fn visit_char() -> bool { true } - fn visit_str() -> bool { true } + fn visit_char(&self) -> bool { true } + fn visit_str(&self) -> bool { true } - fn visit_estr_box() -> bool { true } - fn visit_estr_uniq() -> bool { true } - fn visit_estr_slice() -> bool { true } - fn visit_estr_fixed(_sz: uint, _sz: uint, + fn visit_estr_box(&self) -> bool { true } + fn visit_estr_uniq(&self) -> bool { true } + fn visit_estr_slice(&self) -> bool { true } + fn visit_estr_fixed(&self, + _sz: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_box(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_uniq(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_ptr(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_rptr(_mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_box(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_uniq(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_ptr(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_rptr(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_vec(_mtbl: uint, inner: *TyDesc) -> bool { - self.types += ~["["]; - visit_tydesc(inner, my_visitor(*self) as TyVisitor); - self.types += ~["]"]; + fn visit_vec(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_unboxed_vec(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_evec_box(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_evec_uniq(&self, _mtbl: uint, inner: *TyDesc) -> bool { + self.types.push(~"["); + unsafe { + visit_tydesc(inner, (@*self) as @TyVisitor); + } + self.types.push(~"]"); true } - fn visit_unboxed_vec(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_evec_box(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_evec_uniq(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_evec_slice(_mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_evec_fixed(_n: uint, _sz: uint, _align: uint, + fn visit_evec_slice(&self, _mtbl: uint, _inner: *TyDesc) -> bool { true } + fn visit_evec_fixed(&self, _n: uint, _sz: uint, _align: uint, _mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_enter_rec(_n_fields: uint, + fn visit_enter_rec(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_rec_field(_i: uint, _name: &str, + fn visit_rec_field(&self, _i: uint, _name: &str, _mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_leave_rec(_n_fields: uint, + fn visit_leave_rec(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_enter_class(_n_fields: uint, + fn visit_enter_class(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_class_field(_i: uint, _name: &str, + fn visit_class_field(&self, _i: uint, _name: &str, _mtbl: uint, _inner: *TyDesc) -> bool { true } - fn visit_leave_class(_n_fields: uint, + fn visit_leave_class(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_enter_tup(_n_fields: uint, + fn visit_enter_tup(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_tup_field(_i: uint, _inner: *TyDesc) -> bool { true } - fn visit_leave_tup(_n_fields: uint, + fn visit_tup_field(&self, _i: uint, _inner: *TyDesc) -> bool { true } + fn visit_leave_tup(&self, _n_fields: uint, _sz: uint, _align: uint) -> bool { true } - fn visit_enter_enum(_n_variants: uint, + fn visit_enter_enum(&self, _n_variants: uint, + _get_disr: extern unsafe fn(ptr: *Opaque) -> int, _sz: uint, _align: uint) -> bool { true } - fn visit_enter_enum_variant(_variant: uint, + fn visit_enter_enum_variant(&self, + _variant: uint, _disr_val: int, _n_fields: uint, _name: &str) -> bool { true } - fn visit_enum_variant_field(_i: uint, _inner: *TyDesc) -> bool { true } - fn visit_leave_enum_variant(_variant: uint, + fn visit_enum_variant_field(&self, _i: uint, _offset: uint, _inner: *TyDesc) -> bool { true } + fn visit_leave_enum_variant(&self, + _variant: uint, _disr_val: int, _n_fields: uint, _name: &str) -> bool { true } - fn visit_leave_enum(_n_variants: uint, + fn visit_leave_enum(&self, + _n_variants: uint, + _get_disr: extern unsafe fn(ptr: *Opaque) -> int, _sz: uint, _align: uint) -> bool { true } - fn visit_enter_fn(_purity: uint, _proto: uint, + fn visit_enter_fn(&self, _purity: uint, _proto: uint, _n_inputs: uint, _retstyle: uint) -> bool { true } - fn visit_fn_input(_i: uint, _mode: uint, _inner: *TyDesc) -> bool { true } - fn visit_fn_output(_retstyle: uint, _inner: *TyDesc) -> bool { true } - fn visit_leave_fn(_purity: uint, _proto: uint, + fn visit_fn_input(&self, _i: uint, _mode: uint, _inner: *TyDesc) -> bool { true } + fn visit_fn_output(&self, _retstyle: uint, _inner: *TyDesc) -> bool { true } + fn visit_leave_fn(&self, _purity: uint, _proto: uint, _n_inputs: uint, _retstyle: uint) -> bool { true } - fn visit_trait() -> bool { true } - fn visit_var() -> bool { true } - fn visit_var_integral() -> bool { true } - fn visit_param(_i: uint) -> bool { true } - fn visit_self() -> bool { true } - fn visit_type() -> bool { true } - fn visit_opaque_box() -> bool { true } - fn visit_constr(_inner: *TyDesc) -> bool { true } - fn visit_closure_ptr(_ck: uint) -> bool { true } + fn visit_trait(&self) -> bool { true } + fn visit_var(&self) -> bool { true } + fn visit_var_integral(&self) -> bool { true } + fn visit_param(&self, _i: uint) -> bool { true } + fn visit_self(&self) -> bool { true } + fn visit_type(&self) -> bool { true } + fn visit_opaque_box(&self) -> bool { true } + fn visit_constr(&self, _inner: *TyDesc) -> bool { true } + fn visit_closure_ptr(&self, _ck: uint) -> bool { true } } -fn visit_ty(v: TyVisitor) { - visit_tydesc(get_tydesc::(), v); +fn visit_ty(v: @TyVisitor) { + unsafe { + visit_tydesc(get_tydesc::(), v); + } } pub fn main() { - let v = my_visitor(@mut {types: ~[]}); - let vv = v as TyVisitor; + let v = @MyVisitor {types: @mut ~[]}; + let vv = v as @TyVisitor; visit_ty::(vv); visit_ty::(vv); @@ -150,9 +162,8 @@ pub fn main() { visit_ty::(vv); visit_ty::<~[int]>(vv); - for (v.types.clone()).each {|s| - io::println(fmt!("type: %s", s)); + for v.types.each |&s| { + println(fmt!("type: %s", s)); } - assert!(v.types == ["bool", "int", "i8", "i16", - "[", "int", "]"]); + assert_eq!((*v.types).clone(), ~[~"bool", ~"int", ~"i8", ~"i16", ~"[", ~"int", ~"]"]); } From 8bf00333455a572bc4c48f947777ed2e7b57af09 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Thu, 20 Jun 2013 14:45:10 +0200 Subject: [PATCH 04/31] Remove unused shape fields from typedescs --- src/librustc/back/abi.rs | 4 +--- src/librustc/middle/trans/glue.rs | 18 ++++++------------ src/librustc/middle/trans/type_.rs | 3 +-- src/libstd/unstable/intrinsics.rs | 2 -- src/rt/rust_builtin.cpp | 7 +++---- src/rt/rust_type.h | 2 -- src/rt/rust_util.cpp | 2 -- 7 files changed, 11 insertions(+), 27 deletions(-) diff --git a/src/librustc/back/abi.rs b/src/librustc/back/abi.rs index 004170dea7fe..8f15c74ed0ec 100644 --- a/src/librustc/back/abi.rs +++ b/src/librustc/back/abi.rs @@ -49,9 +49,7 @@ pub static tydesc_field_take_glue: uint = 2u; pub static tydesc_field_drop_glue: uint = 3u; pub static tydesc_field_free_glue: uint = 4u; pub static tydesc_field_visit_glue: uint = 5u; -pub static tydesc_field_shape: uint = 6u; -pub static tydesc_field_shape_tables: uint = 7u; -pub static n_tydesc_fields: uint = 8u; +pub static n_tydesc_fields: uint = 6u; // The two halves of a closure: code and environment. pub static fn_field_code: uint = 0u; diff --git a/src/librustc/middle/trans/glue.rs b/src/librustc/middle/trans/glue.rs index 0930d3550353..f9bffb4a36ec 100644 --- a/src/librustc/middle/trans/glue.rs +++ b/src/librustc/middle/trans/glue.rs @@ -765,19 +765,13 @@ pub fn emit_tydescs(ccx: &mut CrateContext) { } }; - - let shape = C_null(Type::i8p()); - let shape_tables = C_null(Type::i8p()); - let tydesc = C_named_struct(ccx.tydesc_type, - [ti.size, // size - ti.align, // align - take_glue, // take_glue - drop_glue, // drop_glue - free_glue, // free_glue - visit_glue, // visit_glue - shape, // shape - shape_tables]); // shape_tables + [ti.size, // size + ti.align, // align + take_glue, // take_glue + drop_glue, // drop_glue + free_glue, // free_glue + visit_glue]); // visit_glue unsafe { let gvar = ti.tydesc; diff --git a/src/librustc/middle/trans/type_.rs b/src/librustc/middle/trans/type_.rs index 764bdb026f47..fda8fb4a9016 100644 --- a/src/librustc/middle/trans/type_.rs +++ b/src/librustc/middle/trans/type_.rs @@ -211,8 +211,7 @@ impl Type { let elems = [ int_ty, int_ty, - glue_fn_ty, glue_fn_ty, glue_fn_ty, glue_fn_ty, - pvoid, pvoid + glue_fn_ty, glue_fn_ty, glue_fn_ty, glue_fn_ty ]; tydesc.set_struct_body(elems, false); diff --git a/src/libstd/unstable/intrinsics.rs b/src/libstd/unstable/intrinsics.rs index a51ba05710b1..84bb2a952f2d 100644 --- a/src/libstd/unstable/intrinsics.rs +++ b/src/libstd/unstable/intrinsics.rs @@ -48,8 +48,6 @@ pub struct TyDesc { drop_glue: GlueFn, free_glue: GlueFn, visit_glue: GlueFn, - shape: *i8, - shape_tables: *i8 } #[lang="opaque"] diff --git a/src/rt/rust_builtin.cpp b/src/rt/rust_builtin.cpp index e476fa0ad5e0..1a84325c7a93 100644 --- a/src/rt/rust_builtin.cpp +++ b/src/rt/rust_builtin.cpp @@ -732,10 +732,9 @@ rust_task_deref(rust_task *task) { // Must call on rust stack. extern "C" CDECL void rust_call_tydesc_glue(void *root, size_t *tydesc, size_t glue_index) { - void (*glue_fn)(void *, void *, void *) = - (void (*)(void *, void *, void *))tydesc[glue_index]; - if (glue_fn) - glue_fn(0, 0, root); + glue_fn *fn = (glue_fn*) tydesc[glue_index]; + if (fn) + fn(0, 0, root); } // Don't run on the Rust stack! diff --git a/src/rt/rust_type.h b/src/rt/rust_type.h index 6d36d2c960a2..70b5c1dc6bea 100644 --- a/src/rt/rust_type.h +++ b/src/rt/rust_type.h @@ -57,8 +57,6 @@ struct type_desc { glue_fn *drop_glue; glue_fn *free_glue; glue_fn *visit_glue; - const uint8_t *unused; - const uint8_t *unused2; }; extern "C" type_desc *rust_clone_type_desc(type_desc*); diff --git a/src/rt/rust_util.cpp b/src/rt/rust_util.cpp index 8d80a344063f..4a15830e529a 100644 --- a/src/rt/rust_util.cpp +++ b/src/rt/rust_util.cpp @@ -21,8 +21,6 @@ struct type_desc str_body_tydesc = { NULL, // drop_glue NULL, // free_glue NULL, // visit_glue - NULL, // shape - NULL, // shape_tables }; // From 273f90566c26309c13ebe10278f8745e978250b2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Thu, 20 Jun 2013 15:13:20 +0200 Subject: [PATCH 05/31] Small cleanups --- src/librustc/middle/trans/type_.rs | 7 +------ src/librustc/middle/ty.rs | 4 ++-- 2 files changed, 3 insertions(+), 8 deletions(-) diff --git a/src/librustc/middle/trans/type_.rs b/src/librustc/middle/trans/type_.rs index fda8fb4a9016..7b02030078c5 100644 --- a/src/librustc/middle/trans/type_.rs +++ b/src/librustc/middle/trans/type_.rs @@ -189,8 +189,7 @@ impl Type { None => () } - // Bit of a kludge: pick the fn typeref out of the tydesc.. - let ty = cx.tydesc_type.get_field(abi::tydesc_field_drop_glue); + let ty = Type::glue_fn(cx.tydesc_type).ptr_to(); cx.tn.associate_type("glue_fn", &ty); return ty; @@ -269,10 +268,6 @@ impl Type { cx.int_type } - pub fn captured_tydescs(ctx: &CrateContext, num: uint) -> Type { - Type::struct_(vec::from_elem(num, ctx.tydesc_type.ptr_to()), false) - } - pub fn opaque_trait(ctx: &CrateContext, store: ty::TraitStore) -> Type { let tydesc_ptr = ctx.tydesc_type.ptr_to(); match store { diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index f12ecebc6d5c..9e1a0def2eef 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -4453,8 +4453,8 @@ pub fn get_tydesc_ty(tcx: ctxt) -> t { } pub fn get_opaque_ty(tcx: ctxt) -> t { - let tydesc_lang_item = tcx.lang_items.opaque(); - tcx.intrinsic_defs.find_copy(&tydesc_lang_item) + let opaque_lang_item = tcx.lang_items.opaque(); + tcx.intrinsic_defs.find_copy(&opaque_lang_item) .expect("Failed to resolve Opaque") } From 976c0b3dfb6a0da8a70958f157507b5dcf7c5ceb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Fri, 21 Jun 2013 10:00:49 +0200 Subject: [PATCH 06/31] Remove rust_call_tydesc_glue Towards #4812. Also includes some minor cleanups. --- src/libextra/arena.rs | 32 ++++++++------------------------ src/libstd/cleanup.rs | 18 +++--------------- src/libstd/gc.rs | 15 +++++---------- src/libstd/sys.rs | 23 ----------------------- src/rt/rust_builtin.cpp | 8 -------- src/rt/rustrt.def.in | 3 +-- 6 files changed, 17 insertions(+), 82 deletions(-) diff --git a/src/libextra/arena.rs b/src/libextra/arena.rs index a7d5660cd2e4..3766af046563 100644 --- a/src/libextra/arena.rs +++ b/src/libextra/arena.rs @@ -41,37 +41,21 @@ use list::{MutList, MutCons, MutNil}; use core::at_vec; use core::cast::{transmute, transmute_mut_region}; use core::cast; -use core::libc::size_t; use core::ptr; use core::sys; use core::uint; use core::vec; use core::unstable::intrinsics; +use core::unstable::intrinsics::{TyDesc}; + +#[cfg(not(stage0))] +use core::unstable::intrinsics::{get_tydesc}; #[cfg(stage0)] -use intrinsic::{get_tydesc, TyDesc}; -#[cfg(not(stage0))] -use core::unstable::intrinsics::{get_tydesc, TyDesc}; - -pub mod rustrt { - use core::libc::size_t; - #[cfg(stage0)] - use intrinsic::{TyDesc}; - #[cfg(not(stage0))] - use core::unstable::intrinsics::{TyDesc}; - - pub extern { - #[rust_stack] - unsafe fn rust_call_tydesc_glue(root: *u8, - tydesc: *TyDesc, - field: size_t); - } +unsafe fn get_tydesc() -> *TyDesc { + intrinsics::get_tydesc::() as *TyDesc } -// This probably belongs somewhere else. Needs to be kept in sync with -// changes to glue... -static tydesc_drop_glue_index: size_t = 3 as size_t; - // The way arena uses arrays is really deeply awful. The arrays are // allocated, and have capacities reserved, but the fill for the array // will always stay at 0. @@ -150,8 +134,8 @@ unsafe fn destroy_chunk(chunk: &Chunk) { //debug!("freeing object: idx = %u, size = %u, align = %u, done = %b", // start, size, align, is_done); if is_done { - rustrt::rust_call_tydesc_glue( - ptr::offset(buf, start), tydesc, tydesc_drop_glue_index); + ((*tydesc).drop_glue)(&tydesc as **TyDesc, + ptr::offset(buf, start) as *i8); } // Find where the next tydesc lives diff --git a/src/libstd/cleanup.rs b/src/libstd/cleanup.rs index 28aab9adad2c..557a2fbc4aef 100644 --- a/src/libstd/cleanup.rs +++ b/src/libstd/cleanup.rs @@ -158,20 +158,6 @@ fn debug_mem() -> bool { false } -#[cfg(stage0)] -unsafe fn call_drop_glue(tydesc: *::std::unstable::intrinsics::TyDesc, data: *i8) { - use sys::TypeDesc; - - let tydesc: *TypeDesc = transmute(tydesc); - let drop_glue: extern "Rust" fn(**TypeDesc, *i8) = transmute((*tydesc).drop_glue); - drop_glue(to_unsafe_ptr(&tydesc), data); -} - -#[cfg(not(stage0))] -unsafe fn call_drop_glue(tydesc: *::std::unstable::intrinsics::TyDesc, data: *i8) { - ((*tydesc).drop_glue)(to_unsafe_ptr(&tydesc), data); -} - /// Destroys all managed memory (i.e. @ boxes) held by the current task. #[cfg(not(test))] #[lang="annihilate"] @@ -213,7 +199,9 @@ pub unsafe fn annihilate() { // callback, as the original value may have been freed. for each_live_alloc(false) |box, uniq| { if !uniq { - call_drop_glue((*box).header.type_desc, transmute(&(*box).data)); + let tydesc = (*box).header.type_desc; + let data = transmute(&(*box).data); + ((*tydesc).drop_glue)(to_unsafe_ptr(&tydesc), data); } } diff --git a/src/libstd/gc.rs b/src/libstd/gc.rs index 611b95a7745e..2a211484e736 100644 --- a/src/libstd/gc.rs +++ b/src/libstd/gc.rs @@ -40,12 +40,13 @@ with destructors. use cast; use container::{Map, Set}; use io; -use libc::{size_t, uintptr_t}; +use libc::{uintptr_t}; use option::{None, Option, Some}; use ptr; use hashmap::HashSet; use stackwalk::walk_stack; use sys; +use unstable::intrinsics::{TyDesc}; pub use stackwalk::Word; @@ -58,17 +59,11 @@ pub struct StackSegment { } pub mod rustrt { - use libc::size_t; use stackwalk::Word; use super::StackSegment; #[link_name = "rustrt"] pub extern { - #[rust_stack] - pub unsafe fn rust_call_tydesc_glue(root: *Word, - tydesc: *Word, - field: size_t); - #[rust_stack] pub unsafe fn rust_gc_metadata() -> *Word; @@ -125,7 +120,7 @@ unsafe fn is_safe_point(pc: *Word) -> Option { return None; } -type Visitor<'self> = &'self fn(root: **Word, tydesc: *Word) -> bool; +type Visitor<'self> = &'self fn(root: **Word, tydesc: *TyDesc) -> bool; // Walks the list of roots for the given safe point, and calls visitor // on each root. @@ -139,7 +134,7 @@ unsafe fn _walk_safe_point(fp: *Word, sp: SafePoint, visitor: Visitor) -> bool { let stack_roots: *u32 = bump(sp_meta, 2); let reg_roots: *u8 = bump(stack_roots, num_stack_roots); let addrspaces: *Word = align_to_pointer(bump(reg_roots, num_reg_roots)); - let tydescs: ***Word = bump(addrspaces, num_stack_roots); + let tydescs: ***TyDesc = bump(addrspaces, num_stack_roots); // Stack roots let mut sri = 0; @@ -364,7 +359,7 @@ pub fn cleanup_stack_for_failure() { // FIXME #4420: Destroy this box // FIXME #4330: Destroy this box } else { - rustrt::rust_call_tydesc_glue(*root, tydesc, 3 as size_t); + ((*tydesc).drop_glue)(&tydesc as **TyDesc, *root as *i8); } } } diff --git a/src/libstd/sys.rs b/src/libstd/sys.rs index 7f80375c2f6a..a1d6342323c6 100644 --- a/src/libstd/sys.rs +++ b/src/libstd/sys.rs @@ -22,17 +22,6 @@ use repr; use str; use unstable::intrinsics; -// Corresponds to runtime type_desc type -#[cfg(stage0)] -pub struct TypeDesc { - size: uint, - align: uint, - take_glue: uint, - drop_glue: uint, - free_glue: uint - // Remaining fields not listed -} - /// The representation of a Rust closure pub struct Closure { code: *(), @@ -50,18 +39,6 @@ pub mod rustrt { } } -/** - * Returns a pointer to a type descriptor. - * - * Useful for calling certain function in the Rust runtime or otherwise - * performing dark magick. - */ -#[inline] -#[cfg(stage0)] -pub fn get_type_desc() -> *TypeDesc { - unsafe { intrinsics::get_tydesc::() as *TypeDesc } -} - /// Returns the size of a type #[inline] pub fn size_of() -> uint { diff --git a/src/rt/rust_builtin.cpp b/src/rt/rust_builtin.cpp index 1a84325c7a93..8d771da32fc2 100644 --- a/src/rt/rust_builtin.cpp +++ b/src/rt/rust_builtin.cpp @@ -729,14 +729,6 @@ rust_task_deref(rust_task *task) { task->deref(); } -// Must call on rust stack. -extern "C" CDECL void -rust_call_tydesc_glue(void *root, size_t *tydesc, size_t glue_index) { - glue_fn *fn = (glue_fn*) tydesc[glue_index]; - if (fn) - fn(0, 0, root); -} - // Don't run on the Rust stack! extern "C" void rust_log_str(uint32_t level, const char *str, size_t size) { diff --git a/src/rt/rustrt.def.in b/src/rt/rustrt.def.in index ba7ada04a275..7fd948d2cd94 100644 --- a/src/rt/rustrt.def.in +++ b/src/rt/rustrt.def.in @@ -174,7 +174,6 @@ rust_set_task_local_data rust_task_local_data_atexit rust_task_ref rust_task_deref -rust_call_tydesc_glue tdefl_compress_mem_to_heap tinfl_decompress_mem_to_heap rust_gc_metadata @@ -239,4 +238,4 @@ rust_valgrind_stack_deregister rust_take_env_lock rust_drop_env_lock rust_update_log_settings -rust_running_on_valgrind \ No newline at end of file +rust_running_on_valgrind From 1b76bac41de9f52295a99db21abdd1ad5b0fc231 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Fri, 21 Jun 2013 13:01:15 +0200 Subject: [PATCH 07/31] syntax: Remove unused tokens TyDesc, TyVisitor and intrinsic are not used anymore. --- src/libsyntax/parse/token.rs | 200 +++++++++++++++++------------------ 1 file changed, 97 insertions(+), 103 deletions(-) diff --git a/src/libsyntax/parse/token.rs b/src/libsyntax/parse/token.rs index 273a59f0a3de..d40b96f077bb 100644 --- a/src/libsyntax/parse/token.rs +++ b/src/libsyntax/parse/token.rs @@ -331,21 +331,18 @@ pub mod special_idents { pub static str : ident = ident { name: 19, ctxt: 0}; // for the type /* outside of libsyntax */ - pub static ty_visitor : ident = ident { name: 20, ctxt: 0}; - pub static arg : ident = ident { name: 21, ctxt: 0}; - pub static descrim : ident = ident { name: 22, ctxt: 0}; - pub static clownshoe_abi : ident = ident { name: 23, ctxt: 0}; - pub static clownshoe_stack_shim : ident = ident { name: 24, ctxt: 0}; - pub static tydesc : ident = ident { name: 25, ctxt: 0}; - pub static main : ident = ident { name: 26, ctxt: 0}; - pub static opaque : ident = ident { name: 27, ctxt: 0}; - pub static blk : ident = ident { name: 28, ctxt: 0}; - pub static statik : ident = ident { name: 29, ctxt: 0}; - pub static intrinsic : ident = ident { name: 30, ctxt: 0}; - pub static clownshoes_foreign_mod: ident = ident { name: 31, ctxt: 0}; - pub static unnamed_field: ident = ident { name: 32, ctxt: 0}; - pub static c_abi: ident = ident { name: 33, ctxt: 0}; - pub static type_self: ident = ident { name: 34, ctxt: 0}; // `Self` + pub static arg : ident = ident { name: 20, ctxt: 0}; + pub static descrim : ident = ident { name: 21, ctxt: 0}; + pub static clownshoe_abi : ident = ident { name: 22, ctxt: 0}; + pub static clownshoe_stack_shim : ident = ident { name: 23, ctxt: 0}; + pub static main : ident = ident { name: 24, ctxt: 0}; + pub static opaque : ident = ident { name: 25, ctxt: 0}; + pub static blk : ident = ident { name: 26, ctxt: 0}; + pub static statik : ident = ident { name: 27, ctxt: 0}; + pub static clownshoes_foreign_mod: ident = ident { name: 28, ctxt: 0}; + pub static unnamed_field: ident = ident { name: 29, ctxt: 0}; + pub static c_abi: ident = ident { name: 30, ctxt: 0}; + pub static type_self: ident = ident { name: 31, ctxt: 0}; // `Self` } /** @@ -426,59 +423,56 @@ fn mk_fresh_ident_interner() -> @ident_interner { "tt", // 17 "matchers", // 18 "str", // 19 - "TyVisitor", // 20 - "arg", // 21 - "descrim", // 22 - "__rust_abi", // 23 - "__rust_stack_shim", // 24 - "TyDesc", // 25 - "main", // 26 - "", // 27 - "blk", // 28 - "static", // 29 - "intrinsic", // 30 - "__foreign_mod__", // 31 - "__field__", // 32 - "C", // 33 - "Self", // 34 + "arg", // 20 + "descrim", // 21 + "__rust_abi", // 22 + "__rust_stack_shim", // 23 + "main", // 24 + "", // 25 + "blk", // 26 + "static", // 27 + "__foreign_mod__", // 28 + "__field__", // 29 + "C", // 30 + "Self", // 31 - "as", // 35 - "break", // 36 - "const", // 37 - "copy", // 38 - "do", // 39 - "else", // 40 - "enum", // 41 - "extern", // 42 - "false", // 43 - "fn", // 44 - "for", // 45 - "if", // 46 - "impl", // 47 - "let", // 48 - "__log", // 49 - "loop", // 50 - "match", // 51 - "mod", // 52 - "mut", // 53 - "once", // 54 - "priv", // 55 - "pub", // 56 - "pure", // 57 - "ref", // 58 - "return", // 59 - "static", // 29 -- also a special ident + "as", // 32 + "break", // 33 + "const", // 34 + "copy", // 35 + "do", // 36 + "else", // 37 + "enum", // 38 + "extern", // 39 + "false", // 40 + "fn", // 41 + "for", // 42 + "if", // 43 + "impl", // 44 + "let", // 45 + "__log", // 46 + "loop", // 47 + "match", // 48 + "mod", // 49 + "mut", // 50 + "once", // 51 + "priv", // 52 + "pub", // 53 + "pure", // 54 + "ref", // 55 + "return", // 56 + "static", // 27 -- also a special ident "self", // 8 -- also a special ident - "struct", // 60 - "super", // 61 - "true", // 62 - "trait", // 63 - "type", // 64 - "unsafe", // 65 - "use", // 66 - "while", // 67 + "struct", // 57 + "super", // 58 + "true", // 59 + "trait", // 60 + "type", // 61 + "unsafe", // 62 + "use", // 63 + "while", // 64 - "be", // 68 + "be", // 65 ]; @ident_interner { @@ -612,42 +606,42 @@ pub mod keywords { impl Keyword { pub fn to_ident(&self) -> ident { match *self { - As => ident { name: 35, ctxt: 0 }, - Break => ident { name: 36, ctxt: 0 }, - Const => ident { name: 37, ctxt: 0 }, - Copy => ident { name: 38, ctxt: 0 }, - Do => ident { name: 39, ctxt: 0 }, - Else => ident { name: 40, ctxt: 0 }, - Enum => ident { name: 41, ctxt: 0 }, - Extern => ident { name: 42, ctxt: 0 }, - False => ident { name: 43, ctxt: 0 }, - Fn => ident { name: 44, ctxt: 0 }, - For => ident { name: 45, ctxt: 0 }, - If => ident { name: 46, ctxt: 0 }, - Impl => ident { name: 47, ctxt: 0 }, - Let => ident { name: 48, ctxt: 0 }, - __Log => ident { name: 49, ctxt: 0 }, - Loop => ident { name: 50, ctxt: 0 }, - Match => ident { name: 51, ctxt: 0 }, - Mod => ident { name: 52, ctxt: 0 }, - Mut => ident { name: 53, ctxt: 0 }, - Once => ident { name: 54, ctxt: 0 }, - Priv => ident { name: 55, ctxt: 0 }, - Pub => ident { name: 56, ctxt: 0 }, - Pure => ident { name: 57, ctxt: 0 }, - Ref => ident { name: 58, ctxt: 0 }, - Return => ident { name: 59, ctxt: 0 }, - Static => ident { name: 29, ctxt: 0 }, + As => ident { name: 32, ctxt: 0 }, + Break => ident { name: 33, ctxt: 0 }, + Const => ident { name: 34, ctxt: 0 }, + Copy => ident { name: 35, ctxt: 0 }, + Do => ident { name: 36, ctxt: 0 }, + Else => ident { name: 37, ctxt: 0 }, + Enum => ident { name: 38, ctxt: 0 }, + Extern => ident { name: 39, ctxt: 0 }, + False => ident { name: 40, ctxt: 0 }, + Fn => ident { name: 41, ctxt: 0 }, + For => ident { name: 42, ctxt: 0 }, + If => ident { name: 43, ctxt: 0 }, + Impl => ident { name: 44, ctxt: 0 }, + Let => ident { name: 45, ctxt: 0 }, + __Log => ident { name: 46, ctxt: 0 }, + Loop => ident { name: 47, ctxt: 0 }, + Match => ident { name: 48, ctxt: 0 }, + Mod => ident { name: 49, ctxt: 0 }, + Mut => ident { name: 50, ctxt: 0 }, + Once => ident { name: 51, ctxt: 0 }, + Priv => ident { name: 52, ctxt: 0 }, + Pub => ident { name: 53, ctxt: 0 }, + Pure => ident { name: 54, ctxt: 0 }, + Ref => ident { name: 55, ctxt: 0 }, + Return => ident { name: 56, ctxt: 0 }, + Static => ident { name: 27, ctxt: 0 }, Self => ident { name: 8, ctxt: 0 }, - Struct => ident { name: 60, ctxt: 0 }, - Super => ident { name: 61, ctxt: 0 }, - True => ident { name: 62, ctxt: 0 }, - Trait => ident { name: 63, ctxt: 0 }, - Type => ident { name: 64, ctxt: 0 }, - Unsafe => ident { name: 65, ctxt: 0 }, - Use => ident { name: 66, ctxt: 0 }, - While => ident { name: 67, ctxt: 0 }, - Be => ident { name: 68, ctxt: 0 }, + Struct => ident { name: 57, ctxt: 0 }, + Super => ident { name: 58, ctxt: 0 }, + True => ident { name: 59, ctxt: 0 }, + Trait => ident { name: 60, ctxt: 0 }, + Type => ident { name: 61, ctxt: 0 }, + Unsafe => ident { name: 62, ctxt: 0 }, + Use => ident { name: 63, ctxt: 0 }, + While => ident { name: 64, ctxt: 0 }, + Be => ident { name: 65, ctxt: 0 }, } } } @@ -663,7 +657,7 @@ pub fn is_keyword(kw: keywords::Keyword, tok: &Token) -> bool { pub fn is_any_keyword(tok: &Token) -> bool { match *tok { token::IDENT(sid, false) => match sid.name { - 8 | 29 | 35 .. 68 => true, + 8 | 27 | 32 .. 65 => true, _ => false, }, _ => false @@ -673,7 +667,7 @@ pub fn is_any_keyword(tok: &Token) -> bool { pub fn is_strict_keyword(tok: &Token) -> bool { match *tok { token::IDENT(sid, false) => match sid.name { - 8 | 29 | 35 .. 67 => true, + 8 | 27 | 32 .. 64 => true, _ => false, }, _ => false, @@ -683,7 +677,7 @@ pub fn is_strict_keyword(tok: &Token) -> bool { pub fn is_reserved_keyword(tok: &Token) -> bool { match *tok { token::IDENT(sid, false) => match sid.name { - 68 => true, + 65 => true, _ => false, }, _ => false, From e2f1049bd5f041f1f219d683e4e29e32ca30cd1c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Sat, 22 Jun 2013 21:36:00 +0200 Subject: [PATCH 08/31] Remove unused TyDesc parameter from the glue functions To remove the environment pointer, support for function pointers without an environment argument is needed (i.e. a fixed version of #6661). --- src/libextra/arena.rs | 16 ++++++++++++++-- src/librustc/back/abi.rs | 13 ------------- src/librustc/middle/trans/glue.rs | 14 ++++---------- src/librustc/middle/trans/type_.rs | 11 ++++------- src/libstd/cleanup.rs | 18 ++++++++++++++++-- src/libstd/gc.rs | 15 ++++++++++++++- src/libstd/unstable/intrinsics.rs | 4 ++++ src/rt/rust_task.cpp | 6 +++++- src/rt/rust_type.h | 6 +++++- 9 files changed, 66 insertions(+), 37 deletions(-) diff --git a/src/libextra/arena.rs b/src/libextra/arena.rs index 3766af046563..cec3a2c1e952 100644 --- a/src/libextra/arena.rs +++ b/src/libextra/arena.rs @@ -115,6 +115,19 @@ fn round_up_to(base: uint, align: uint) -> uint { (base + (align - 1)) & !(align - 1) } +#[inline] +#[cfg(not(stage0))] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + // This function should be inlined when stage0 is gone + ((*tydesc).drop_glue)(data); +} + +#[inline] +#[cfg(stage0)] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + ((*tydesc).drop_glue)(0 as **TyDesc, data); +} + // Walk down a chunk, running the destructors for any objects stored // in it. unsafe fn destroy_chunk(chunk: &Chunk) { @@ -134,8 +147,7 @@ unsafe fn destroy_chunk(chunk: &Chunk) { //debug!("freeing object: idx = %u, size = %u, align = %u, done = %b", // start, size, align, is_done); if is_done { - ((*tydesc).drop_glue)(&tydesc as **TyDesc, - ptr::offset(buf, start) as *i8); + call_drop_glue(tydesc, ptr::offset(buf, start) as *i8); } // Find where the next tydesc lives diff --git a/src/librustc/back/abi.rs b/src/librustc/back/abi.rs index 8f15c74ed0ec..05b6e90c682f 100644 --- a/src/librustc/back/abi.rs +++ b/src/librustc/back/abi.rs @@ -8,9 +8,6 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. - - - pub static rc_base_field_refcnt: uint = 0u; pub static task_field_refcnt: uint = 0u; @@ -69,14 +66,4 @@ pub static vec_elt_elems: uint = 2u; pub static slice_elt_base: uint = 0u; pub static slice_elt_len: uint = 1u; -pub static worst_case_glue_call_args: uint = 7u; - pub static abi_version: uint = 1u; - -pub fn memcpy_glue_name() -> ~str { return ~"rust_memcpy_glue"; } - -pub fn bzero_glue_name() -> ~str { return ~"rust_bzero_glue"; } - -pub fn yield_glue_name() -> ~str { return ~"rust_yield_glue"; } - -pub fn no_op_type_glue_name() -> ~str { return ~"rust_no_op_type_glue"; } diff --git a/src/librustc/middle/trans/glue.rs b/src/librustc/middle/trans/glue.rs index f9bffb4a36ec..75a1221cca52 100644 --- a/src/librustc/middle/trans/glue.rs +++ b/src/librustc/middle/trans/glue.rs @@ -232,7 +232,7 @@ pub fn lazily_emit_tydesc_glue(ccx: @mut CrateContext, field: uint, ti: @mut tydesc_info) { let _icx = push_ctxt("lazily_emit_tydesc_glue"); - let llfnty = type_of_glue_fn(ccx); + let llfnty = Type::glue_fn(); if lazily_emit_simplified_tydesc_glue(ccx, field, ti) { return; @@ -338,9 +338,7 @@ pub fn call_tydesc_glue_full(bcx: block, } }; - Call(bcx, llfn, [C_null(Type::nil().ptr_to()), - C_null(bcx.ccx().tydesc_type.ptr_to().ptr_to()), - llrawptr]); + Call(bcx, llfn, [C_null(Type::nil().ptr_to()), llrawptr]); } // See [Note-arg-mode] @@ -680,7 +678,7 @@ pub fn make_generic_glue_inner(ccx: @mut CrateContext, let bcx = top_scope_block(fcx, None); let lltop = bcx.llbb; - let rawptr0_arg = fcx.arg_pos(1u); + let rawptr0_arg = fcx.arg_pos(0u); let llrawptr0 = unsafe { llvm::LLVMGetParam(llfn, rawptr0_arg as c_uint) }; let llty = type_of(ccx, t); let llrawptr0 = PointerCast(bcx, llrawptr0, llty.ptr_to()); @@ -715,7 +713,7 @@ pub fn emit_tydescs(ccx: &mut CrateContext) { let _icx = push_ctxt("emit_tydescs"); // As of this point, allow no more tydescs to be created. ccx.finished_tydescs = true; - let glue_fn_ty = Type::generic_glue_fn(ccx); + let glue_fn_ty = Type::generic_glue_fn(ccx).ptr_to(); let tyds = &mut ccx.tydescs; for tyds.each_value |&val| { let ti = val; @@ -782,7 +780,3 @@ pub fn emit_tydescs(ccx: &mut CrateContext) { } }; } - -pub fn type_of_glue_fn(ccx: &CrateContext) -> Type { - Type::glue_fn(ccx.tydesc_type) -} diff --git a/src/librustc/middle/trans/type_.rs b/src/librustc/middle/trans/type_.rs index 7b02030078c5..64688ac41342 100644 --- a/src/librustc/middle/trans/type_.rs +++ b/src/librustc/middle/trans/type_.rs @@ -20,7 +20,6 @@ use middle::trans::base; use syntax::ast; use syntax::abi::{Architecture, X86, X86_64, Arm, Mips}; -use back::abi; use core::vec; use core::cast; @@ -189,22 +188,20 @@ impl Type { None => () } - let ty = Type::glue_fn(cx.tydesc_type).ptr_to(); + let ty = Type::glue_fn(); cx.tn.associate_type("glue_fn", &ty); return ty; } - pub fn glue_fn(tydesc: Type) -> Type { - let tydescpp = tydesc.ptr_to().ptr_to(); - Type::func([ Type::nil().ptr_to(), tydescpp, Type::i8p() ], + pub fn glue_fn() -> Type { + Type::func([ Type::nil().ptr_to(), Type::i8p() ], &Type::void()) } pub fn tydesc(arch: Architecture) -> Type { let mut tydesc = Type::named_struct("tydesc"); - let pvoid = Type::i8p(); - let glue_fn_ty = Type::glue_fn(tydesc).ptr_to(); + let glue_fn_ty = Type::glue_fn().ptr_to(); let int_ty = Type::int(arch); diff --git a/src/libstd/cleanup.rs b/src/libstd/cleanup.rs index 557a2fbc4aef..ee9fdd3c6200 100644 --- a/src/libstd/cleanup.rs +++ b/src/libstd/cleanup.rs @@ -11,9 +11,10 @@ #[doc(hidden)]; use libc::{c_char, intptr_t, uintptr_t}; -use ptr::{mut_null, to_unsafe_ptr}; +use ptr::{mut_null}; use repr::BoxRepr; use cast::transmute; +use unstable::intrinsics::TyDesc; #[cfg(not(test))] use unstable::lang::clear_task_borrow_list; /** @@ -158,6 +159,19 @@ fn debug_mem() -> bool { false } +#[inline] +#[cfg(not(stage0))] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + // This function should be inlined when stage0 is gone + ((*tydesc).drop_glue)(data); +} + +#[inline] +#[cfg(stage0)] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + ((*tydesc).drop_glue)(0 as **TyDesc, data); +} + /// Destroys all managed memory (i.e. @ boxes) held by the current task. #[cfg(not(test))] #[lang="annihilate"] @@ -201,7 +215,7 @@ pub unsafe fn annihilate() { if !uniq { let tydesc = (*box).header.type_desc; let data = transmute(&(*box).data); - ((*tydesc).drop_glue)(to_unsafe_ptr(&tydesc), data); + call_drop_glue(tydesc, data); } } diff --git a/src/libstd/gc.rs b/src/libstd/gc.rs index 2a211484e736..c9e33219fa50 100644 --- a/src/libstd/gc.rs +++ b/src/libstd/gc.rs @@ -316,6 +316,19 @@ fn expect_sentinel() -> bool { true } #[cfg(nogc)] fn expect_sentinel() -> bool { false } +#[inline] +#[cfg(not(stage0))] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + // This function should be inlined when stage0 is gone + ((*tydesc).drop_glue)(data); +} + +#[inline] +#[cfg(stage0)] +unsafe fn call_drop_glue(tydesc: *TyDesc, data: *i8) { + ((*tydesc).drop_glue)(0 as **TyDesc, data); +} + // Entry point for GC-based cleanup. Walks stack looking for exchange // heap and stack allocations requiring drop, and runs all // destructors. @@ -359,7 +372,7 @@ pub fn cleanup_stack_for_failure() { // FIXME #4420: Destroy this box // FIXME #4330: Destroy this box } else { - ((*tydesc).drop_glue)(&tydesc as **TyDesc, *root as *i8); + call_drop_glue(tydesc, *root as *i8); } } } diff --git a/src/libstd/unstable/intrinsics.rs b/src/libstd/unstable/intrinsics.rs index 84bb2a952f2d..bd34574c3b7a 100644 --- a/src/libstd/unstable/intrinsics.rs +++ b/src/libstd/unstable/intrinsics.rs @@ -36,6 +36,10 @@ A quick refresher on memory ordering: #[cfg(test)] pub use realstd::unstable::intrinsics::{TyDesc, Opaque, TyVisitor}; +#[cfg(not(stage0))] +pub type GlueFn = extern "Rust" fn(*i8); + +#[cfg(stage0)] pub type GlueFn = extern "Rust" fn(**TyDesc, *i8); // NB: this has to be kept in sync with the Rust ABI. diff --git a/src/rt/rust_task.cpp b/src/rt/rust_task.cpp index fe1b4622137e..81ae991623f8 100644 --- a/src/rt/rust_task.cpp +++ b/src/rt/rust_task.cpp @@ -183,7 +183,11 @@ void task_start_wrapper(spawn_args *a) if(env) { // free the environment (which should be a unique closure). const type_desc *td = env->td; - td->drop_glue(NULL, NULL, box_body(env)); + td->drop_glue(NULL, +#ifdef _RUST_STAGE0 + NULL, +#endif + box_body(env)); task->kernel->region()->free(env); } diff --git a/src/rt/rust_type.h b/src/rt/rust_type.h index 70b5c1dc6bea..30ff5f1fa54e 100644 --- a/src/rt/rust_type.h +++ b/src/rt/rust_type.h @@ -25,7 +25,11 @@ typedef void (*CDECL spawn_fn)(rust_opaque_box*, void *); struct type_desc; -typedef void CDECL (glue_fn)(void *, const type_desc **, void *); +typedef void CDECL (glue_fn)(void *, +#ifdef _RUST_STAGE0 + const type_desc **, +#endif + void *); // Corresponds to the boxed data in the @ region. The body follows the // header; you can obtain a ptr via box_body() below. From ce888a505524937ca9aa91370e204bb28fe6ef7f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philipp=20Br=C3=BCschweiler?= Date: Sun, 23 Jun 2013 17:15:37 +0200 Subject: [PATCH 09/31] Fix reflect-visit-type for iterator changes --- src/test/run-pass/reflect-visit-type.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/test/run-pass/reflect-visit-type.rs b/src/test/run-pass/reflect-visit-type.rs index 3b51abbd489b..bb1c92dfa8a7 100644 --- a/src/test/run-pass/reflect-visit-type.rs +++ b/src/test/run-pass/reflect-visit-type.rs @@ -162,7 +162,7 @@ pub fn main() { visit_ty::(vv); visit_ty::<~[int]>(vv); - for v.types.each |&s| { + for v.types.iter().advance |&s| { println(fmt!("type: %s", s)); } assert_eq!((*v.types).clone(), ~[~"bool", ~"int", ~"i8", ~"i16", ~"[", ~"int", ~"]"]); From 1841b31c61c2cca9c54264edd2a78b994b9638e9 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Fri, 21 Jun 2013 18:46:34 -0700 Subject: [PATCH 10/31] Add 'static mut' items to the language --- src/librustc/metadata/decoder.rs | 16 ++++--- src/librustc/metadata/encoder.rs | 10 ++-- src/librustc/middle/astencode.rs | 2 +- src/librustc/middle/check_const.rs | 6 +-- src/librustc/middle/check_match.rs | 10 ++-- src/librustc/middle/const_eval.rs | 6 +-- src/librustc/middle/effect.rs | 10 +++- src/librustc/middle/mem_categorization.rs | 28 +++++++---- src/librustc/middle/pat_util.rs | 2 +- src/librustc/middle/resolve.rs | 17 +++---- src/librustc/middle/trans/_match.rs | 9 ++-- src/librustc/middle/trans/base.rs | 12 +++-- src/librustc/middle/trans/callee.rs | 2 +- src/librustc/middle/trans/consts.rs | 12 +++-- src/librustc/middle/trans/expr.rs | 2 +- src/librustc/middle/trans/reachable.rs | 2 +- src/librustc/middle/ty.rs | 2 +- src/librustc/middle/typeck/check/mod.rs | 4 +- src/librustc/middle/typeck/collect.rs | 2 +- src/librustdoc/extract.rs | 2 +- src/librustdoc/tystr_pass.rs | 2 +- src/libsyntax/ast.rs | 4 +- src/libsyntax/ast_map.rs | 2 +- src/libsyntax/ast_util.rs | 2 +- src/libsyntax/fold.rs | 2 +- src/libsyntax/parse/parser.rs | 5 +- src/libsyntax/print/pprust.rs | 5 +- src/libsyntax/visit.rs | 2 +- src/test/auxiliary/static_mut_xc.rs | 1 + src/test/compile-fail/static-mut-bad-types.rs | 17 +++++++ .../compile-fail/static-mut-not-constant.rs | 13 ++++++ src/test/compile-fail/static-mut-not-pat.rs | 26 +++++++++++ .../static-mut-requires-unsafe.rs | 17 +++++++ src/test/run-pass/static-mut-xc.rs | 46 +++++++++++++++++++ 34 files changed, 230 insertions(+), 70 deletions(-) create mode 100644 src/test/auxiliary/static_mut_xc.rs create mode 100644 src/test/compile-fail/static-mut-bad-types.rs create mode 100644 src/test/compile-fail/static-mut-not-constant.rs create mode 100644 src/test/compile-fail/static-mut-not-pat.rs create mode 100644 src/test/compile-fail/static-mut-requires-unsafe.rs create mode 100644 src/test/run-pass/static-mut-xc.rs diff --git a/src/librustc/metadata/decoder.rs b/src/librustc/metadata/decoder.rs index 9ace8677dab7..83e59d980856 100644 --- a/src/librustc/metadata/decoder.rs +++ b/src/librustc/metadata/decoder.rs @@ -97,7 +97,8 @@ fn lookup_item(item_id: int, data: @~[u8]) -> ebml::Doc { #[deriving(Eq)] enum Family { - Const, // c + ImmStatic, // c + MutStatic, // b Fn, // f UnsafeFn, // u PureFn, // p @@ -122,7 +123,8 @@ enum Family { fn item_family(item: ebml::Doc) -> Family { let fam = reader::get_doc(item, tag_items_data_item_family); match reader::doc_as_u8(fam) as char { - 'c' => Const, + 'c' => ImmStatic, + 'b' => MutStatic, 'f' => Fn, 'u' => UnsafeFn, 'p' => PureFn, @@ -321,7 +323,8 @@ fn item_to_def_like(item: ebml::Doc, did: ast::def_id, cnum: ast::crate_num) -> def_like { let fam = item_family(item); match fam { - Const => dl_def(ast::def_const(did)), + ImmStatic => dl_def(ast::def_static(did, false)), + MutStatic => dl_def(ast::def_static(did, true)), Struct => dl_def(ast::def_struct(did)), UnsafeFn => dl_def(ast::def_fn(did, ast::unsafe_fn)), Fn => dl_def(ast::def_fn(did, ast::impure_fn)), @@ -900,8 +903,8 @@ pub fn get_item_visibility(cdata: cmd, id: ast::node_id) fn family_has_type_params(fam: Family) -> bool { match fam { - Const | ForeignType | Mod | ForeignMod | PublicField | PrivateField - | ForeignFn => false, + ImmStatic | ForeignType | Mod | ForeignMod | PublicField | PrivateField + | ForeignFn | MutStatic => false, _ => true } } @@ -931,7 +934,8 @@ fn describe_def(items: ebml::Doc, id: ast::def_id) -> ~str { fn item_family_to_str(fam: Family) -> ~str { match fam { - Const => ~"const", + ImmStatic => ~"static", + MutStatic => ~"static mut", Fn => ~"fn", UnsafeFn => ~"unsafe fn", PureFn => ~"pure fn", diff --git a/src/librustc/metadata/encoder.rs b/src/librustc/metadata/encoder.rs index 94cad18ece2c..96cf7284169d 100644 --- a/src/librustc/metadata/encoder.rs +++ b/src/librustc/metadata/encoder.rs @@ -785,7 +785,7 @@ fn encode_info_for_item(ecx: &EncodeContext, let must_write = match item.node { item_enum(_, _) | item_impl(*) | item_trait(*) | item_struct(*) | - item_mod(*) | item_foreign_mod(*) | item_const(*) => true, + item_mod(*) | item_foreign_mod(*) | item_static(*) => true, _ => false }; if !must_write && !reachable(ecx, item.id) { return; } @@ -800,11 +800,15 @@ fn encode_info_for_item(ecx: &EncodeContext, ecx.tcx.sess.codemap.span_to_str(item.span)); match item.node { - item_const(_, _) => { + item_static(_, m, _) => { add_to_index(); ebml_w.start_tag(tag_items_data_item); encode_def_id(ebml_w, local_def(item.id)); - encode_family(ebml_w, 'c'); + if m == ast::m_mutbl { + encode_family(ebml_w, 'b'); + } else { + encode_family(ebml_w, 'c'); + } encode_type(ecx, ebml_w, node_id_to_type(tcx, item.id)); encode_symbol(ecx, ebml_w, item.id); encode_path(ecx, ebml_w, path, ast_map::path_name(item.ident)); diff --git a/src/librustc/middle/astencode.rs b/src/librustc/middle/astencode.rs index 925b1f506d75..5aad0d894da4 100644 --- a/src/librustc/middle/astencode.rs +++ b/src/librustc/middle/astencode.rs @@ -384,7 +384,7 @@ impl tr for ast::def { ast::def_self(nid, i) => { ast::def_self(xcx.tr_id(nid), i) } ast::def_mod(did) => { ast::def_mod(did.tr(xcx)) } ast::def_foreign_mod(did) => { ast::def_foreign_mod(did.tr(xcx)) } - ast::def_const(did) => { ast::def_const(did.tr(xcx)) } + ast::def_static(did, m) => { ast::def_static(did.tr(xcx), m) } ast::def_arg(nid, b) => { ast::def_arg(xcx.tr_id(nid), b) } ast::def_local(nid, b) => { ast::def_local(xcx.tr_id(nid), b) } ast::def_variant(e_did, v_did) => { diff --git a/src/librustc/middle/check_const.rs b/src/librustc/middle/check_const.rs index 126d2db6879d..c1906820883c 100644 --- a/src/librustc/middle/check_const.rs +++ b/src/librustc/middle/check_const.rs @@ -43,7 +43,7 @@ pub fn check_item(sess: Session, (_is_const, v): (bool, visit::vt)) { match it.node { - item_const(_, ex) => { + item_static(_, _, ex) => { (v.visit_expr)(ex, (true, v)); check_item_recursion(sess, ast_map, def_map, it); } @@ -124,7 +124,7 @@ pub fn check_expr(sess: Session, items without type parameters"); } match def_map.find(&e.id) { - Some(&def_const(_)) | + Some(&def_static(*)) | Some(&def_fn(_, _)) | Some(&def_variant(_, _)) | Some(&def_struct(_)) => { } @@ -237,7 +237,7 @@ pub fn check_item_recursion(sess: Session, match e.node { expr_path(*) => { match env.def_map.find(&e.id) { - Some(&def_const(def_id)) => { + Some(&def_static(def_id, _)) => { if ast_util::is_local(def_id) { match env.ast_map.get_copy(&def_id.node) { ast_map::node_item(it, _) => { diff --git a/src/librustc/middle/check_match.rs b/src/librustc/middle/check_match.rs index a25324058707..b4c8a6b19c29 100644 --- a/src/librustc/middle/check_match.rs +++ b/src/librustc/middle/check_match.rs @@ -304,7 +304,7 @@ pub fn pat_ctor_id(cx: @MatchCheckCtxt, p: @pat) -> Option { pat_ident(_, _, _) | pat_enum(_, _) => { match cx.tcx.def_map.find(&pat.id) { Some(&def_variant(_, id)) => Some(variant(id)), - Some(&def_const(did)) => { + Some(&def_static(did, false)) => { let const_expr = lookup_const_by_id(cx.tcx, did).get(); Some(val(eval_const_expr(cx.tcx, const_expr))) } @@ -339,7 +339,7 @@ pub fn is_wild(cx: @MatchCheckCtxt, p: @pat) -> bool { pat_wild => { true } pat_ident(_, _, _) => { match cx.tcx.def_map.find(&pat.id) { - Some(&def_variant(_, _)) | Some(&def_const(*)) => { false } + Some(&def_variant(_, _)) | Some(&def_static(*)) => { false } _ => { true } } } @@ -499,7 +499,7 @@ pub fn specialize(cx: @MatchCheckCtxt, None } } - Some(&def_const(did)) => { + Some(&def_static(did, _)) => { let const_expr = lookup_const_by_id(cx.tcx, did).get(); let e_v = eval_const_expr(cx.tcx, const_expr); @@ -549,7 +549,7 @@ pub fn specialize(cx: @MatchCheckCtxt, } pat_enum(_, args) => { match cx.tcx.def_map.get_copy(&pat_id) { - def_const(did) => { + def_static(did, _) => { let const_expr = lookup_const_by_id(cx.tcx, did).get(); let e_v = eval_const_expr(cx.tcx, const_expr); @@ -790,7 +790,7 @@ pub fn is_refutable(cx: @MatchCheckCtxt, pat: &pat) -> bool { return true; } } - Some(&def_const(*)) => return true, + Some(&def_static(*)) => return true, _ => () } diff --git a/src/librustc/middle/const_eval.rs b/src/librustc/middle/const_eval.rs index 988ad519f42b..1a7cd856bede 100644 --- a/src/librustc/middle/const_eval.rs +++ b/src/librustc/middle/const_eval.rs @@ -166,7 +166,7 @@ pub fn classify(e: @expr, pub fn lookup_const(tcx: ty::ctxt, e: @expr) -> Option<@expr> { match tcx.def_map.find(&e.id) { - Some(&ast::def_const(def_id)) => lookup_const_by_id(tcx, def_id), + Some(&ast::def_static(def_id, false)) => lookup_const_by_id(tcx, def_id), _ => None } } @@ -178,7 +178,7 @@ pub fn lookup_const_by_id(tcx: ty::ctxt, match tcx.items.find(&def_id.node) { None => None, Some(&ast_map::node_item(it, _)) => match it.node { - item_const(_, const_expr) => Some(const_expr), + item_static(_, ast::m_imm, const_expr) => Some(const_expr), _ => None }, Some(_) => None @@ -195,7 +195,7 @@ pub fn lookup_const_by_id(tcx: ty::ctxt, match csearch::maybe_get_item_ast(tcx, def_id, |a, b, c, d| astencode::decode_inlined_item(a, b, maps, /*bar*/ copy c, d)) { csearch::found(ast::ii_item(item)) => match item.node { - item_const(_, const_expr) => Some(const_expr), + item_static(_, ast::m_imm, const_expr) => Some(const_expr), _ => None }, _ => None diff --git a/src/librustc/middle/effect.rs b/src/librustc/middle/effect.rs index d9481c26dad0..513b2015a834 100644 --- a/src/librustc/middle/effect.rs +++ b/src/librustc/middle/effect.rs @@ -17,7 +17,7 @@ use middle::typeck::method_map; use util::ppaux; use syntax::ast::{deref, expr_call, expr_inline_asm, expr_method_call}; -use syntax::ast::{expr_unary, node_id, unsafe_blk, unsafe_fn}; +use syntax::ast::{expr_unary, node_id, unsafe_blk, unsafe_fn, expr_path}; use syntax::ast; use syntax::codemap::span; use syntax::visit::{fk_item_fn, fk_method}; @@ -143,6 +143,14 @@ pub fn check_crate(tcx: ty::ctxt, expr_inline_asm(*) => { require_unsafe(expr.span, "use of inline assembly") } + expr_path(*) => { + match ty::resolve_expr(tcx, expr) { + ast::def_static(_, true) => { + require_unsafe(expr.span, "use of mutable static") + } + _ => {} + } + } _ => {} } diff --git a/src/librustc/middle/mem_categorization.rs b/src/librustc/middle/mem_categorization.rs index 2ced57dc885b..f93cb265d785 100644 --- a/src/librustc/middle/mem_categorization.rs +++ b/src/librustc/middle/mem_categorization.rs @@ -447,19 +447,29 @@ impl mem_categorization_ctxt { -> cmt { match def { ast::def_fn(*) | ast::def_static_method(*) | ast::def_mod(_) | - ast::def_foreign_mod(_) | ast::def_const(_) | + ast::def_foreign_mod(_) | ast::def_static(_, false) | ast::def_use(_) | ast::def_variant(*) | ast::def_trait(_) | ast::def_ty(_) | ast::def_prim_ty(_) | ast::def_ty_param(*) | ast::def_struct(*) | ast::def_typaram_binder(*) | ast::def_region(_) | ast::def_label(_) | ast::def_self_ty(*) => { - @cmt_ { - id:id, - span:span, - cat:cat_static_item, - mutbl: McImmutable, - ty:expr_ty - } + @cmt_ { + id:id, + span:span, + cat:cat_static_item, + mutbl: McImmutable, + ty:expr_ty + } + } + + ast::def_static(_, true) => { + @cmt_ { + id:id, + span:span, + cat:cat_static_item, + mutbl: McDeclared, + ty:expr_ty + } } ast::def_arg(vid, mutbl) => { @@ -894,7 +904,7 @@ impl mem_categorization_ctxt { self.cat_pattern(cmt_field, subpat, op); } } - Some(&ast::def_const(*)) => { + Some(&ast::def_static(*)) => { for subpats.iter().advance |&subpat| { self.cat_pattern(cmt, subpat, op); } diff --git a/src/librustc/middle/pat_util.rs b/src/librustc/middle/pat_util.rs index 1237e9fb4a26..5bd39e858637 100644 --- a/src/librustc/middle/pat_util.rs +++ b/src/librustc/middle/pat_util.rs @@ -45,7 +45,7 @@ pub fn pat_is_const(dm: resolve::DefMap, pat: &pat) -> bool { match pat.node { pat_ident(_, _, None) | pat_enum(*) => { match dm.find(&pat.id) { - Some(&def_const(*)) => true, + Some(&def_static(_, false)) => true, _ => false } } diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index eed0b12b9e12..7f9086be81d5 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -1146,12 +1146,13 @@ impl Resolver { } // These items live in the value namespace. - item_const(*) => { + item_static(_, m, _) => { let (name_bindings, _) = self.add_child(ident, parent, ForbidDuplicateValues, sp); + let mutbl = m == ast::m_mutbl; name_bindings.define_value - (privacy, def_const(local_def(item.id)), sp); + (privacy, def_static(local_def(item.id), mutbl), sp); } item_fn(_, purity, _, _, _) => { let (name_bindings, new_parent) = @@ -1566,7 +1567,7 @@ impl Resolver { } } foreign_item_const(*) => { - let def = def_const(local_def(foreign_item.id)); + let def = def_static(local_def(foreign_item.id), false); name_bindings.define_value(Public, def, foreign_item.span); visit_foreign_item(foreign_item, (new_parent, visitor)); @@ -1673,7 +1674,7 @@ impl Resolver { let privacy = variant_visibility_to_privacy(visibility, true); child_name_bindings.define_value(privacy, def, dummy_sp()); } - def_fn(*) | def_static_method(*) | def_const(*) => { + def_fn(*) | def_static_method(*) | def_static(*) => { debug!("(building reduced graph for external \ crate) building value %s", final_ident); child_name_bindings.define_value(privacy, def, dummy_sp()); @@ -3686,7 +3687,7 @@ impl Resolver { visitor); } - item_const(*) => { + item_static(*) => { self.with_constant_rib(|| { visit_item(item, ((), visitor)); }); @@ -4344,7 +4345,7 @@ impl Resolver { Some(def @ def_struct(*)) => { self.record_def(pattern.id, def); } - Some(def @ def_const(*)) => { + Some(def @ def_static(*)) => { self.enforce_default_binding_mode( pattern, binding_mode, @@ -4376,7 +4377,7 @@ impl Resolver { Some(def @ def_fn(*)) | Some(def @ def_variant(*)) | Some(def @ def_struct(*)) | - Some(def @ def_const(*)) => { + Some(def @ def_static(*)) => { self.record_def(pattern.id, def); } Some(_) => { @@ -4459,7 +4460,7 @@ impl Resolver { def @ def_variant(*) | def @ def_struct(*) => { return FoundStructOrEnumVariant(def); } - def @ def_const(*) => { + def @ def_static(_, false) => { return FoundConst(def); } _ => { diff --git a/src/librustc/middle/trans/_match.rs b/src/librustc/middle/trans/_match.rs index ab2f0c84d02e..71b416ffe85f 100644 --- a/src/librustc/middle/trans/_match.rs +++ b/src/librustc/middle/trans/_match.rs @@ -820,7 +820,7 @@ pub fn get_options(bcx: block, m: &[@Match], col: uint) -> ~[Opt] { add_to_set(ccx.tcx, &mut found, lit(UnitLikeStructLit(cur.id))); } - Some(&ast::def_const(const_did)) => { + Some(&ast::def_static(const_did, false)) => { add_to_set(ccx.tcx, &mut found, lit(ConstLit(const_did))); } @@ -836,7 +836,7 @@ pub fn get_options(bcx: block, m: &[@Match], col: uint) -> ~[Opt] { add_to_set(ccx.tcx, &mut found, variant_opt(bcx, cur.id)); } - Some(&ast::def_const(const_did)) => { + Some(&ast::def_static(const_did, false)) => { add_to_set(ccx.tcx, &mut found, lit(ConstLit(const_did))); } @@ -1831,8 +1831,9 @@ pub fn bind_irrefutable_pat(bcx: block, } } } - Some(&ast::def_const(*)) => { - bcx = bind_irrefutable_pat(bcx, pat, val, make_copy, binding_mode); + Some(&ast::def_static(_, false)) => { + bcx = bind_irrefutable_pat(bcx, pat, val, make_copy, + binding_mode); } _ => { // Nothing to do here. diff --git a/src/librustc/middle/trans/base.rs b/src/librustc/middle/trans/base.rs index ec77fe359b59..0f6c7dbe7543 100644 --- a/src/librustc/middle/trans/base.rs +++ b/src/librustc/middle/trans/base.rs @@ -2122,14 +2122,19 @@ pub fn trans_item(ccx: @mut CrateContext, item: &ast::item) { trans_enum_def(ccx, enum_definition, item.id, vi, &mut i); } } - ast::item_const(_, expr) => { - consts::trans_const(ccx, expr, item.id); + ast::item_static(_, m, expr) => { + consts::trans_const(ccx, m, item.id); // Do static_assert checking. It can't really be done much earlier because we need to get // the value of the bool out of LLVM for item.attrs.iter().advance |attr| { match attr.node.value.node { ast::meta_word(x) => { if x.slice(0, x.len()) == "static_assert" { + if m == ast::m_mutbl { + ccx.sess.span_fatal(expr.span, + "cannot have static_assert \ + on a mutable static"); + } let v = ccx.const_values.get_copy(&item.id); unsafe { if !(llvm::LLVMConstIntGetZExtValue(v) as bool) { @@ -2398,13 +2403,14 @@ pub fn get_item_val(ccx: @mut CrateContext, id: ast::node_id) -> ValueRef { let my_path = vec::append(/*bad*/copy *pth, [path_name(i.ident)]); match i.node { - ast::item_const(_, expr) => { + ast::item_static(_, m, expr) => { let typ = ty::node_id_to_type(ccx.tcx, i.id); let s = mangle_exported_name(ccx, my_path, typ); // We need the translated value here, because for enums the // LLVM type is not fully determined by the Rust type. let v = consts::const_expr(ccx, expr); ccx.const_values.insert(id, v); + exprt = m == ast::m_mutbl; unsafe { let llty = llvm::LLVMTypeOf(v); let g = str::as_c_str(s, |buf| { diff --git a/src/librustc/middle/trans/callee.rs b/src/librustc/middle/trans/callee.rs index 6120e1e65810..593d0beb88c7 100644 --- a/src/librustc/middle/trans/callee.rs +++ b/src/librustc/middle/trans/callee.rs @@ -143,7 +143,7 @@ pub fn trans(bcx: block, expr: @ast::expr) -> Callee { datum_callee(bcx, ref_expr) } ast::def_mod(*) | ast::def_foreign_mod(*) | ast::def_trait(*) | - ast::def_const(*) | ast::def_ty(*) | ast::def_prim_ty(*) | + ast::def_static(*) | ast::def_ty(*) | ast::def_prim_ty(*) | ast::def_use(*) | ast::def_typaram_binder(*) | ast::def_region(*) | ast::def_label(*) | ast::def_ty_param(*) | ast::def_self_ty(*) => { diff --git a/src/librustc/middle/trans/consts.rs b/src/librustc/middle/trans/consts.rs index e40534773c2d..98eb858be55f 100644 --- a/src/librustc/middle/trans/consts.rs +++ b/src/librustc/middle/trans/consts.rs @@ -164,9 +164,9 @@ pub fn get_const_val(cx: @mut CrateContext, mut def_id: ast::def_id) -> ValueRef } match cx.tcx.items.get_copy(&def_id.node) { ast_map::node_item(@ast::item { - node: ast::item_const(_, subexpr), _ + node: ast::item_static(_, ast::m_imm, _), _ }, _) => { - trans_const(cx, subexpr, def_id.node); + trans_const(cx, ast::m_imm, def_id.node); } _ => cx.tcx.sess.bug("expected a const to be an item") } @@ -538,7 +538,7 @@ fn const_expr_unadjusted(cx: @mut CrateContext, e: @ast::expr) -> ValueRef { base::get_item_val(cx, def_id.node) } } - Some(&ast::def_const(def_id)) => { + Some(&ast::def_static(def_id, false)) => { get_const_val(cx, def_id) } Some(&ast::def_variant(enum_did, variant_did)) => { @@ -587,7 +587,7 @@ fn const_expr_unadjusted(cx: @mut CrateContext, e: @ast::expr) -> ValueRef { } } -pub fn trans_const(ccx: @mut CrateContext, _e: @ast::expr, id: ast::node_id) { +pub fn trans_const(ccx: @mut CrateContext, m: ast::mutability, id: ast::node_id) { unsafe { let _icx = push_ctxt("trans_const"); let g = base::get_item_val(ccx, id); @@ -595,6 +595,8 @@ pub fn trans_const(ccx: @mut CrateContext, _e: @ast::expr, id: ast::node_id) { // constant's initializer to determine its LLVM type. let v = ccx.const_values.get_copy(&id); llvm::LLVMSetInitializer(g, v); - llvm::LLVMSetGlobalConstant(g, True); + if m != ast::m_mutbl { + llvm::LLVMSetGlobalConstant(g, True); + } } } diff --git a/src/librustc/middle/trans/expr.rs b/src/librustc/middle/trans/expr.rs index 7d86f743a8e4..1aebf73b81a8 100644 --- a/src/librustc/middle/trans/expr.rs +++ b/src/librustc/middle/trans/expr.rs @@ -945,7 +945,7 @@ fn trans_lvalue_unadjusted(bcx: block, expr: @ast::expr) -> DatumBlock { let _icx = push_ctxt("trans_def_lvalue"); let ccx = bcx.ccx(); match def { - ast::def_const(did) => { + ast::def_static(did, _) => { let const_ty = expr_ty(bcx, ref_expr); fn get_did(ccx: @mut CrateContext, did: ast::def_id) diff --git a/src/librustc/middle/trans/reachable.rs b/src/librustc/middle/trans/reachable.rs index 6a40c1f75e9e..e950c24c49e8 100644 --- a/src/librustc/middle/trans/reachable.rs +++ b/src/librustc/middle/trans/reachable.rs @@ -146,7 +146,7 @@ fn traverse_public_item(cx: @mut ctx, item: @item) { visit::mk_vt(@visit::Visitor {visit_ty: traverse_ty, ..*visit::default_visitor()}))) } - item_const(*) | + item_static(*) | item_enum(*) | item_trait(*) => (), item_mac(*) => fail!("item macros unimplemented") } diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 90cd8a8665ea..f3c0d4bd8f46 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -3269,7 +3269,7 @@ pub fn expr_kind(tcx: ctxt, // Note: there is actually a good case to be made that // def_args, particularly those of immediate type, ought to // considered rvalues. - ast::def_const(*) | + ast::def_static(*) | ast::def_binding(*) | ast::def_upvar(*) | ast::def_arg(*) | diff --git a/src/librustc/middle/typeck/check/mod.rs b/src/librustc/middle/typeck/check/mod.rs index fa7959c7872b..1acf806f21e9 100644 --- a/src/librustc/middle/typeck/check/mod.rs +++ b/src/librustc/middle/typeck/check/mod.rs @@ -585,7 +585,7 @@ pub fn check_item(ccx: @mut CrateCtxt, it: @ast::item) { let _indenter = indenter(); match it.node { - ast::item_const(_, e) => check_const(ccx, it.span, e, it.id), + ast::item_static(_, _, e) => check_const(ccx, it.span, e, it.id), ast::item_enum(ref enum_definition, _) => { check_enum_variants(ccx, it.span, @@ -3216,7 +3216,7 @@ pub fn ty_param_bounds_and_ty_for_def(fcx: @mut FnCtxt, } ast::def_fn(id, _) | ast::def_static_method(id, _, _) | - ast::def_const(id) | ast::def_variant(_, id) | + ast::def_static(id, _) | ast::def_variant(_, id) | ast::def_struct(id) => { return ty::lookup_item_type(fcx.ccx.tcx, id); } diff --git a/src/librustc/middle/typeck/collect.rs b/src/librustc/middle/typeck/collect.rs index 7f820d11ac61..aef148830a99 100644 --- a/src/librustc/middle/typeck/collect.rs +++ b/src/librustc/middle/typeck/collect.rs @@ -1060,7 +1060,7 @@ pub fn ty_of_item(ccx: &CrateCtxt, it: @ast::item) } let rp = tcx.region_paramd_items.find(&it.id).map_consume(|x| *x); match it.node { - ast::item_const(t, _) => { + ast::item_static(t, _, _) => { let typ = ccx.to_ty(&empty_rscope, t); let tpt = no_params(typ); tcx.tcache.insert(local_def(it.id), tpt); diff --git a/src/librustdoc/extract.rs b/src/librustdoc/extract.rs index b6131dce9c85..f12f612b036b 100644 --- a/src/librustdoc/extract.rs +++ b/src/librustdoc/extract.rs @@ -102,7 +102,7 @@ fn moddoc_from_mod( fndoc_from_fn(ItemDoc) )) } - ast::item_const(_, _) => { + ast::item_static(*) => { Some(doc::ConstTag( constdoc_from_const(ItemDoc) )) diff --git a/src/librustdoc/tystr_pass.rs b/src/librustdoc/tystr_pass.rs index e3abe6e926a5..459daaa468f9 100644 --- a/src/librustdoc/tystr_pass.rs +++ b/src/librustdoc/tystr_pass.rs @@ -96,7 +96,7 @@ fn fold_const( do astsrv::exec(srv) |ctxt| { match ctxt.ast_map.get_copy(&doc.id()) { ast_map::node_item(@ast::item { - node: ast::item_const(ty, _), _ + node: ast::item_static(ty, _, _), _ }, _) => { pprust::ty_to_str(ty, extract::interner()) } diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index 2e3d557daa90..012a1e76228a 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -190,7 +190,7 @@ pub enum def { def_self_ty(/* trait id */ node_id), def_mod(def_id), def_foreign_mod(def_id), - def_const(def_id), + def_static(def_id, bool /* is_mutbl */), def_arg(node_id, bool /* is_mutbl */), def_local(node_id, bool /* is_mutbl */), def_variant(def_id /* enum */, def_id /* variant */), @@ -1095,7 +1095,7 @@ pub struct item { #[deriving(Eq, Encodable, Decodable)] pub enum item_ { - item_const(@Ty, @expr), + item_static(@Ty, mutability, @expr), item_fn(fn_decl, purity, AbiSet, Generics, blk), item_mod(_mod), item_foreign_mod(foreign_mod), diff --git a/src/libsyntax/ast_map.rs b/src/libsyntax/ast_map.rs index a0e1ec69350c..421c4c566b56 100644 --- a/src/libsyntax/ast_map.rs +++ b/src/libsyntax/ast_map.rs @@ -339,7 +339,7 @@ pub fn node_id_to_str(map: map, id: node_id, itr: @ident_interner) -> ~str { Some(&node_item(item, path)) => { let path_str = path_ident_to_str(path, item.ident, itr); let item_str = match item.node { - item_const(*) => ~"const", + item_static(*) => ~"static", item_fn(*) => ~"fn", item_mod(*) => ~"mod", item_foreign_mod(*) => ~"foreign mod", diff --git a/src/libsyntax/ast_util.rs b/src/libsyntax/ast_util.rs index 24cf5662a36b..227d700452b6 100644 --- a/src/libsyntax/ast_util.rs +++ b/src/libsyntax/ast_util.rs @@ -59,7 +59,7 @@ pub fn variant_def_ids(d: def) -> Option<(def_id, def_id)> { pub fn def_id_of_def(d: def) -> def_id { match d { def_fn(id, _) | def_static_method(id, _, _) | def_mod(id) | - def_foreign_mod(id) | def_const(id) | + def_foreign_mod(id) | def_static(id, _) | def_variant(_, id) | def_ty(id) | def_ty_param(id, _) | def_use(id) | def_struct(id) | def_trait(id) => { id diff --git a/src/libsyntax/fold.rs b/src/libsyntax/fold.rs index 4bd2c0a3de1f..8a22dbe9178c 100644 --- a/src/libsyntax/fold.rs +++ b/src/libsyntax/fold.rs @@ -270,7 +270,7 @@ fn noop_fold_struct_field(sf: @struct_field, fld: @ast_fold) pub fn noop_fold_item_underscore(i: &item_, fld: @ast_fold) -> item_ { match *i { - item_const(t, e) => item_const(fld.fold_ty(t), fld.fold_expr(e)), + item_static(t, m, e) => item_static(fld.fold_ty(t), m, fld.fold_expr(e)), item_fn(ref decl, purity, abi, ref generics, ref body) => { item_fn( fold_fn_decl(decl, fld), diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index f2443f9e5335..a726b3b27d2e 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -34,7 +34,7 @@ use ast::{expr_vstore_slice, expr_vstore_box}; use ast::{expr_vstore_mut_slice, expr_while, extern_fn, field, fn_decl}; use ast::{expr_vstore_uniq, Onceness, Once, Many}; use ast::{foreign_item, foreign_item_const, foreign_item_fn, foreign_mod}; -use ast::{ident, impure_fn, inherited, item, item_, item_const}; +use ast::{ident, impure_fn, inherited, item, item_, item_static}; use ast::{item_enum, item_fn, item_foreign_mod, item_impl}; use ast::{item_mac, item_mod, item_struct, item_trait, item_ty, lit, lit_}; use ast::{lit_bool, lit_float, lit_float_unsuffixed, lit_int}; @@ -3556,13 +3556,14 @@ impl Parser { } fn parse_item_const(&self) -> item_info { + let m = if self.eat_keyword(keywords::Mut) {m_mutbl} else {m_imm}; let id = self.parse_ident(); self.expect(&token::COLON); let ty = self.parse_ty(false); self.expect(&token::EQ); let e = self.parse_expr(); self.expect(&token::SEMI); - (id, item_const(ty, e), None) + (id, item_static(ty, m, e), None) } // parse a mod { ...} item diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index fa22b7ceb710..c21c0a0afeed 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -477,8 +477,11 @@ pub fn print_item(s: @ps, item: @ast::item) { let ann_node = node_item(s, item); (s.ann.pre)(ann_node); match item.node { - ast::item_const(ty, expr) => { + ast::item_static(ty, m, expr) => { head(s, visibility_qualified(item.vis, "static")); + if m == ast::m_mutbl { + word_space(s, "mut"); + } print_ident(s, item.ident); word_space(s, ":"); print_type(s, ty); diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index 5aa38c0348c0..fd9350e00051 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -148,7 +148,7 @@ fn visit_trait_ref(tref: @ast::trait_ref, (e, v): (E, vt)) { pub fn visit_item(i: @item, (e, v): (E, vt)) { match i.node { - item_const(t, ex) => { + item_static(t, _, ex) => { (v.visit_ty)(t, (copy e, v)); (v.visit_expr)(ex, (copy e, v)); } diff --git a/src/test/auxiliary/static_mut_xc.rs b/src/test/auxiliary/static_mut_xc.rs new file mode 100644 index 000000000000..8dc45c681bfe --- /dev/null +++ b/src/test/auxiliary/static_mut_xc.rs @@ -0,0 +1 @@ +pub static mut a: int = 3; diff --git a/src/test/compile-fail/static-mut-bad-types.rs b/src/test/compile-fail/static-mut-bad-types.rs new file mode 100644 index 000000000000..7aed3ce30bc5 --- /dev/null +++ b/src/test/compile-fail/static-mut-bad-types.rs @@ -0,0 +1,17 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +static mut a: int = 3; + +fn main() { + unsafe { + a = true; //~ ERROR: mismatched types + } +} diff --git a/src/test/compile-fail/static-mut-not-constant.rs b/src/test/compile-fail/static-mut-not-constant.rs new file mode 100644 index 000000000000..61d3ed7fd18e --- /dev/null +++ b/src/test/compile-fail/static-mut-not-constant.rs @@ -0,0 +1,13 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +static mut a: ~int = ~3; //~ ERROR: disallowed operator in constant + +fn main() {} diff --git a/src/test/compile-fail/static-mut-not-pat.rs b/src/test/compile-fail/static-mut-not-pat.rs new file mode 100644 index 000000000000..997003a28d42 --- /dev/null +++ b/src/test/compile-fail/static-mut-not-pat.rs @@ -0,0 +1,26 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// Constants (static variables) can be used to match in patterns, but mutable +// statics cannot. This ensures that there's some form of error if this is +// attempted. + +static mut a: int = 3; + +fn main() { + // If they can't be matched against, then it's possible to capture the same + // name as a variable, hence this should be an unreachable pattern situation + // instead of spitting out a custom error about some identifier collisions + // (we should allow shadowing) + match 4 { + a => {} + _ => {} //~ ERROR: unreachable pattern + } +} diff --git a/src/test/compile-fail/static-mut-requires-unsafe.rs b/src/test/compile-fail/static-mut-requires-unsafe.rs new file mode 100644 index 000000000000..7337920cce68 --- /dev/null +++ b/src/test/compile-fail/static-mut-requires-unsafe.rs @@ -0,0 +1,17 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +static mut a: int = 3; + +fn main() { + a += 3; //~ ERROR: requires unsafe + a = 4; //~ ERROR: requires unsafe + let _b = a; //~ ERROR: requires unsafe +} diff --git a/src/test/run-pass/static-mut-xc.rs b/src/test/run-pass/static-mut-xc.rs new file mode 100644 index 000000000000..72f44fcd5010 --- /dev/null +++ b/src/test/run-pass/static-mut-xc.rs @@ -0,0 +1,46 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// Constants (static variables) can be used to match in patterns, but mutable +// statics cannot. This ensures that there's some form of error if this is +// attempted. + +// xfail-fast +// aux-build:static_mut_xc.rs + +extern mod static_mut_xc; + +unsafe fn static_bound(_: &'static int) {} + +fn static_bound_set(a: &'static mut int) { + *a = 3; +} + +unsafe fn run() { + assert!(static_mut_xc::a == 3); + static_mut_xc::a = 4; + assert!(static_mut_xc::a == 4); + static_mut_xc::a += 1; + assert!(static_mut_xc::a == 5); + static_mut_xc::a *= 3; + assert!(static_mut_xc::a == 15); + static_mut_xc::a = -3; + assert!(static_mut_xc::a == -3); + static_bound(&static_mut_xc::a); + static_bound_set(&mut static_mut_xc::a); +} + +fn main() { + unsafe { run() } +} + +pub mod inner { + pub static mut a: int = 4; +} From 8fdc8f392c3f5d1bdf601756bfe442b7698e6315 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Fri, 21 Jun 2013 22:46:27 -0700 Subject: [PATCH 11/31] Support foreign 'static mut' variables as well --- src/librustc/metadata/encoder.rs | 8 +++- src/librustc/middle/lint.rs | 48 ++++++++++--------- src/librustc/middle/resolve.rs | 6 +-- src/librustc/middle/trans/base.rs | 2 +- src/librustc/middle/trans/foreign.rs | 2 +- src/librustc/middle/typeck/collect.rs | 2 +- src/librustdoc/extract.rs | 2 +- src/libsyntax/ast.rs | 2 +- src/libsyntax/fold.rs | 4 +- src/libsyntax/parse/parser.rs | 5 +- src/libsyntax/print/pprust.rs | 5 +- src/libsyntax/visit.rs | 2 +- src/rt/rust_builtin.cpp | 10 ++++ src/rt/rustrt.def.in | 4 +- .../static-mut-foreign-requires-unsafe.rs | 21 ++++++++ src/test/run-pass/static-mut-foreign.rs | 46 ++++++++++++++++++ 16 files changed, 129 insertions(+), 40 deletions(-) create mode 100644 src/test/compile-fail/static-mut-foreign-requires-unsafe.rs create mode 100644 src/test/run-pass/static-mut-foreign.rs diff --git a/src/librustc/metadata/encoder.rs b/src/librustc/metadata/encoder.rs index 96cf7284169d..7d18bdb77efe 100644 --- a/src/librustc/metadata/encoder.rs +++ b/src/librustc/metadata/encoder.rs @@ -1111,9 +1111,13 @@ fn encode_info_for_foreign_item(ecx: &EncodeContext, } encode_path(ecx, ebml_w, path, ast_map::path_name(nitem.ident)); } - foreign_item_const(*) => { + foreign_item_static(_, mutbl) => { encode_def_id(ebml_w, local_def(nitem.id)); - encode_family(ebml_w, 'c'); + if mutbl { + encode_family(ebml_w, 'b'); + } else { + encode_family(ebml_w, 'c'); + } encode_type(ecx, ebml_w, node_id_to_type(ecx.tcx, nitem.id)); encode_symbol(ecx, ebml_w, nitem.id); encode_path(ecx, ebml_w, path, ast_map::path_name(nitem.ident)); diff --git a/src/librustc/middle/lint.rs b/src/librustc/middle/lint.rs index 821aed731c22..17ff5930078d 100644 --- a/src/librustc/middle/lint.rs +++ b/src/librustc/middle/lint.rs @@ -709,28 +709,31 @@ fn check_item_default_methods(cx: &Context, item: @ast::item) { } fn check_item_ctypes(cx: &Context, it: @ast::item) { + fn check_ty(cx: &Context, ty: @ast::Ty) { + match ty.node { + ast::ty_path(_, _, id) => { + match cx.tcx.def_map.get_copy(&id) { + ast::def_prim_ty(ast::ty_int(ast::ty_i)) => { + cx.span_lint(ctypes, ty.span, + "found rust type `int` in foreign module, while \ + libc::c_int or libc::c_long should be used"); + } + ast::def_prim_ty(ast::ty_uint(ast::ty_u)) => { + cx.span_lint(ctypes, ty.span, + "found rust type `uint` in foreign module, while \ + libc::c_uint or libc::c_ulong should be used"); + } + _ => () + } + } + _ => () + } + } fn check_foreign_fn(cx: &Context, decl: &ast::fn_decl) { let tys = vec::map(decl.inputs, |a| a.ty ); for vec::each(vec::append_one(tys, decl.output)) |ty| { - match ty.node { - ast::ty_path(_, _, id) => { - match cx.tcx.def_map.get_copy(&id) { - ast::def_prim_ty(ast::ty_int(ast::ty_i)) => { - cx.span_lint(ctypes, ty.span, - "found rust type `int` in foreign module, while \ - libc::c_int or libc::c_long should be used"); - } - ast::def_prim_ty(ast::ty_uint(ast::ty_u)) => { - cx.span_lint(ctypes, ty.span, - "found rust type `uint` in foreign module, while \ - libc::c_uint or libc::c_ulong should be used"); - } - _ => () - } - } - _ => () - } + check_ty(cx, *ty); } } @@ -738,11 +741,10 @@ fn check_item_ctypes(cx: &Context, it: @ast::item) { ast::item_foreign_mod(ref nmod) if !nmod.abis.is_intrinsic() => { for nmod.items.iter().advance |ni| { match ni.node { - ast::foreign_item_fn(ref decl, _, _) => { - check_foreign_fn(cx, decl); - } - // FIXME #4622: Not implemented. - ast::foreign_item_const(*) => {} + ast::foreign_item_fn(ref decl, _, _) => { + check_foreign_fn(cx, decl); + } + ast::foreign_item_static(t, _) => { check_ty(cx, t); } } } } diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 7f9086be81d5..ed385ae54215 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -1566,8 +1566,8 @@ impl Resolver { visit_foreign_item(foreign_item, (new_parent, visitor)); } } - foreign_item_const(*) => { - let def = def_static(local_def(foreign_item.id), false); + foreign_item_static(_, m) => { + let def = def_static(local_def(foreign_item.id), m); name_bindings.define_value(Public, def, foreign_item.span); visit_foreign_item(foreign_item, (new_parent, visitor)); @@ -3665,7 +3665,7 @@ impl Resolver { || visit_foreign_item(*foreign_item, ((), visitor))); } - foreign_item_const(_) => { + foreign_item_static(*) => { visit_foreign_item(*foreign_item, ((), visitor)); } diff --git a/src/librustc/middle/trans/base.rs b/src/librustc/middle/trans/base.rs index 0f6c7dbe7543..0e322c187af2 100644 --- a/src/librustc/middle/trans/base.rs +++ b/src/librustc/middle/trans/base.rs @@ -2463,7 +2463,7 @@ pub fn get_item_val(ccx: @mut CrateContext, id: ast::node_id) -> ValueRef { ni.id, ni.attrs) } - ast::foreign_item_const(*) => { + ast::foreign_item_static(*) => { let typ = ty::node_id_to_type(ccx.tcx, ni.id); let ident = token::ident_to_str(&ni.ident); let g = do str::as_c_str(ident) |buf| { diff --git a/src/librustc/middle/trans/foreign.rs b/src/librustc/middle/trans/foreign.rs index 10e63e6af777..54bfc25244f0 100644 --- a/src/librustc/middle/trans/foreign.rs +++ b/src/librustc/middle/trans/foreign.rs @@ -332,7 +332,7 @@ pub fn trans_foreign_mod(ccx: @mut CrateContext, } } } - ast::foreign_item_const(*) => { + ast::foreign_item_static(*) => { let ident = token::ident_to_str(&foreign_item.ident); ccx.item_symbols.insert(foreign_item.id, /* bad */ident.to_owned()); } diff --git a/src/librustc/middle/typeck/collect.rs b/src/librustc/middle/typeck/collect.rs index aef148830a99..33e483e552a7 100644 --- a/src/librustc/middle/typeck/collect.rs +++ b/src/librustc/middle/typeck/collect.rs @@ -1153,7 +1153,7 @@ pub fn ty_of_foreign_item(ccx: &CrateCtxt, generics, abis) } - ast::foreign_item_const(t) => { + ast::foreign_item_static(t, _) => { ty::ty_param_bounds_and_ty { generics: ty::Generics { type_param_defs: @~[], diff --git a/src/librustdoc/extract.rs b/src/librustdoc/extract.rs index f12f612b036b..b7b2b70769bb 100644 --- a/src/librustdoc/extract.rs +++ b/src/librustdoc/extract.rs @@ -150,7 +150,7 @@ fn nmoddoc_from_mod( ast::foreign_item_fn(*) => { fns.push(fndoc_from_fn(ItemDoc)); } - ast::foreign_item_const(*) => {} // XXX: Not implemented. + ast::foreign_item_static(*) => {} // XXX: Not implemented. } } doc::NmodDoc { diff --git a/src/libsyntax/ast.rs b/src/libsyntax/ast.rs index 012a1e76228a..c7f3b41475f0 100644 --- a/src/libsyntax/ast.rs +++ b/src/libsyntax/ast.rs @@ -1124,7 +1124,7 @@ pub struct foreign_item { #[deriving(Eq, Encodable, Decodable)] pub enum foreign_item_ { foreign_item_fn(fn_decl, purity, Generics), - foreign_item_const(@Ty) + foreign_item_static(@Ty, /* is_mutbl */ bool), } // The data we save and restore about an inlined item or method. This is not diff --git a/src/libsyntax/fold.rs b/src/libsyntax/fold.rs index 8a22dbe9178c..25839fb46339 100644 --- a/src/libsyntax/fold.rs +++ b/src/libsyntax/fold.rs @@ -236,8 +236,8 @@ fn noop_fold_foreign_item(ni: @foreign_item, fld: @ast_fold) purity, fold_generics(generics, fld)) } - foreign_item_const(t) => { - foreign_item_const(fld.fold_ty(t)) + foreign_item_static(t, m) => { + foreign_item_static(fld.fold_ty(t), m) } }, id: fld.new_id(ni.id), diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index a726b3b27d2e..cc4a1f457226 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -33,7 +33,7 @@ use ast::{expr_vec, expr_vstore, expr_vstore_mut_box}; use ast::{expr_vstore_slice, expr_vstore_box}; use ast::{expr_vstore_mut_slice, expr_while, extern_fn, field, fn_decl}; use ast::{expr_vstore_uniq, Onceness, Once, Many}; -use ast::{foreign_item, foreign_item_const, foreign_item_fn, foreign_mod}; +use ast::{foreign_item, foreign_item_static, foreign_item_fn, foreign_mod}; use ast::{ident, impure_fn, inherited, item, item_, item_static}; use ast::{item_enum, item_fn, item_foreign_mod, item_impl}; use ast::{item_mac, item_mod, item_struct, item_trait, item_ty, lit, lit_}; @@ -3684,6 +3684,7 @@ impl Parser { } else { self.expect_keyword(keywords::Static); } + let mutbl = self.eat_keyword(keywords::Mut); let ident = self.parse_ident(); self.expect(&token::COLON); @@ -3692,7 +3693,7 @@ impl Parser { self.expect(&token::SEMI); @ast::foreign_item { ident: ident, attrs: attrs, - node: foreign_item_const(ty), + node: foreign_item_static(ty, mutbl), id: self.get_id(), span: mk_sp(lo, hi), vis: vis } diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index c21c0a0afeed..1a3155337a5e 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -458,8 +458,11 @@ pub fn print_foreign_item(s: @ps, item: @ast::foreign_item) { word(s.s, ";"); end(s); // end the outer fn box } - ast::foreign_item_const(t) => { + ast::foreign_item_static(t, m) => { head(s, "static"); + if m { + word_space(s, "mut"); + } print_ident(s, item.ident); word_space(s, ":"); print_type(s, t); diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index fd9350e00051..d7914832835a 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -326,7 +326,7 @@ pub fn visit_foreign_item(ni: @foreign_item, (e, v): (E, vt)) { visit_fn_decl(fd, (copy e, v)); (v.visit_generics)(generics, (e, v)); } - foreign_item_const(t) => { + foreign_item_static(t, _) => { (v.visit_ty)(t, (e, v)); } } diff --git a/src/rt/rust_builtin.cpp b/src/rt/rust_builtin.cpp index e476fa0ad5e0..6ae5e978106e 100644 --- a/src/rt/rust_builtin.cpp +++ b/src/rt/rust_builtin.cpp @@ -154,6 +154,16 @@ debug_abi_2(floats f) { return ff; } +extern "C" int +debug_static_mut; + +int debug_static_mut = 3; + +extern "C" void +debug_static_mut_check_four() { + assert(debug_static_mut == 4); +} + /* Debug builtins for std::dbg. */ static void diff --git a/src/rt/rustrt.def.in b/src/rt/rustrt.def.in index ba7ada04a275..505de6e20b70 100644 --- a/src/rt/rustrt.def.in +++ b/src/rt/rustrt.def.in @@ -7,6 +7,8 @@ debug_tydesc debug_get_stk_seg debug_abi_1 debug_abi_2 +debug_static_mut +debug_static_mut_check_four get_task_id get_time rust_tzset @@ -239,4 +241,4 @@ rust_valgrind_stack_deregister rust_take_env_lock rust_drop_env_lock rust_update_log_settings -rust_running_on_valgrind \ No newline at end of file +rust_running_on_valgrind diff --git a/src/test/compile-fail/static-mut-foreign-requires-unsafe.rs b/src/test/compile-fail/static-mut-foreign-requires-unsafe.rs new file mode 100644 index 000000000000..7b371cf708dc --- /dev/null +++ b/src/test/compile-fail/static-mut-foreign-requires-unsafe.rs @@ -0,0 +1,21 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use std::libc; + +extern { + static mut a: libc::c_int; +} + +fn main() { + a += 3; //~ ERROR: requires unsafe + a = 4; //~ ERROR: requires unsafe + let _b = a; //~ ERROR: requires unsafe +} diff --git a/src/test/run-pass/static-mut-foreign.rs b/src/test/run-pass/static-mut-foreign.rs new file mode 100644 index 000000000000..66d34c7e454d --- /dev/null +++ b/src/test/run-pass/static-mut-foreign.rs @@ -0,0 +1,46 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// Constants (static variables) can be used to match in patterns, but mutable +// statics cannot. This ensures that there's some form of error if this is +// attempted. + +use std::libc; + +#[nolink] +extern { + static mut debug_static_mut: libc::c_int; + pub fn debug_static_mut_check_four(); +} + +unsafe fn static_bound(_: &'static libc::c_int) {} + +fn static_bound_set(a: &'static mut libc::c_int) { + *a = 3; +} + +unsafe fn run() { + assert!(debug_static_mut == 3); + debug_static_mut = 4; + assert!(debug_static_mut == 4); + debug_static_mut_check_four(); + debug_static_mut += 1; + assert!(debug_static_mut == 5); + debug_static_mut *= 3; + assert!(debug_static_mut == 15); + debug_static_mut = -3; + assert!(debug_static_mut == -3); + static_bound(&debug_static_mut); + static_bound_set(&mut debug_static_mut); +} + +fn main() { + unsafe { run() } +} From b94f89fffc0c31a2e9048a824a66ff121c908818 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Mon, 24 Jun 2013 07:42:22 -0700 Subject: [PATCH 12/31] Fix 'static mut' tests --- src/test/run-pass/static-mut-foreign.rs | 2 +- src/test/run-pass/static-mut-xc.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/test/run-pass/static-mut-foreign.rs b/src/test/run-pass/static-mut-foreign.rs index 66d34c7e454d..7af143a15292 100644 --- a/src/test/run-pass/static-mut-foreign.rs +++ b/src/test/run-pass/static-mut-foreign.rs @@ -41,6 +41,6 @@ unsafe fn run() { static_bound_set(&mut debug_static_mut); } -fn main() { +pub fn main() { unsafe { run() } } diff --git a/src/test/run-pass/static-mut-xc.rs b/src/test/run-pass/static-mut-xc.rs index 72f44fcd5010..ab6bdc20c491 100644 --- a/src/test/run-pass/static-mut-xc.rs +++ b/src/test/run-pass/static-mut-xc.rs @@ -37,7 +37,7 @@ unsafe fn run() { static_bound_set(&mut static_mut_xc::a); } -fn main() { +pub fn main() { unsafe { run() } } From 079b07df55636533db6d135f22cc235eb2e2b869 Mon Sep 17 00:00:00 2001 From: Fedor Indutny Date: Thu, 20 Jun 2013 13:44:42 +0200 Subject: [PATCH 13/31] libc: support functions from sys/mman.h Because its part of POSIX. Values are taken from FreeBSD, linux and OSX header files. --- src/libstd/libc.rs | 271 ++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 269 insertions(+), 2 deletions(-) diff --git a/src/libstd/libc.rs b/src/libstd/libc.rs index 988fb5cc9b15..2aaeda69326b 100644 --- a/src/libstd/libc.rs +++ b/src/libstd/libc.rs @@ -102,10 +102,12 @@ pub use libc::funcs::posix88::stdio::*; pub use libc::funcs::posix88::fcntl::*; pub use libc::funcs::posix88::dirent::*; pub use libc::funcs::posix88::unistd::*; +pub use libc::funcs::posix88::mman::*; pub use libc::funcs::posix01::stat_::*; pub use libc::funcs::posix01::unistd::*; pub use libc::funcs::posix01::glob::*; +pub use libc::funcs::posix01::mman::*; pub use libc::funcs::posix08::unistd::*; pub use libc::funcs::bsd44::*; @@ -1043,6 +1045,8 @@ pub mod consts { #[cfg(target_arch = "x86_64")] #[cfg(target_arch = "arm")] pub mod posix88 { + use libc::types::common::c95::c_void; + pub static O_RDONLY : int = 0; pub static O_WRONLY : int = 1; pub static O_RDWR : int = 2; @@ -1085,9 +1089,31 @@ pub mod consts { pub static SIGPIPE : int = 13; pub static SIGALRM : int = 14; pub static SIGTERM : int = 15; + + pub static PROT_NONE : int = 0; + pub static PROT_READ : int = 1; + pub static PROT_WRITE : int = 2; + pub static PROT_EXEC : int = 4; + + pub static MAP_FILE : int = 0x0000; + pub static MAP_SHARED : int = 0x0001; + pub static MAP_PRIVATE : int = 0x0002; + pub static MAP_FIXED : int = 0x0010; + pub static MAP_ANON : int = 0x1000; + + pub static MAP_FAILED : *c_void = -1 as *c_void; + + pub static MCL_CURRENT : int = 0x0001; + pub static MCL_FUTURE : int = 0x0002; + + pub static MS_ASYNC : int = 0x0001; + pub static MS_INVALIDATE : int = 0x0002; + pub static MS_SYNC : int = 0x0004; } #[cfg(target_arch = "mips")] pub mod posix88 { + use libc::types::common::c95::c_void; + pub static O_RDONLY : int = 0; pub static O_WRONLY : int = 1; pub static O_RDWR : int = 2; @@ -1130,6 +1156,26 @@ pub mod consts { pub static SIGPIPE : int = 13; pub static SIGALRM : int = 14; pub static SIGTERM : int = 15; + + pub static PROT_NONE : int = 0; + pub static PROT_READ : int = 1; + pub static PROT_WRITE : int = 2; + pub static PROT_EXEC : int = 4; + + pub static MAP_FILE : int = 0x0000; + pub static MAP_SHARED : int = 0x0001; + pub static MAP_PRIVATE : int = 0x0002; + pub static MAP_FIXED : int = 0x0010; + pub static MAP_ANON : int = 0x1000; + + pub static MAP_FAILED : *c_void = -1 as *c_void; + + pub static MCL_CURRENT : int = 0x0001; + pub static MCL_FUTURE : int = 0x0002; + + pub static MS_ASYNC : int = 0x0001; + pub static MS_INVALIDATE : int = 0x0002; + pub static MS_SYNC : int = 0x0004; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1145,10 +1191,27 @@ pub mod consts { pub static GLOB_NOSPACE : int = 1; pub static GLOB_ABORTED : int = 2; pub static GLOB_NOMATCH : int = 3; + + pub static POSIX_MADV_NORMAL : int = 0; + pub static POSIX_MADV_RANDOM : int = 1; + pub static POSIX_MADV_SEQUENTIAL : int = 2; + pub static POSIX_MADV_WILLNEED : int = 3; + pub static POSIX_MADV_DONTNEED : int = 4; } pub mod posix08 { } pub mod bsd44 { + pub static MADV_NORMAL : int = 0; + pub static MADV_RANDOM : int = 1; + pub static MADV_SEQUENTIAL : int = 2; + pub static MADV_WILLNEED : int = 3; + pub static MADV_DONTNEED : int = 4; + pub static MADV_REMOVE : int = 9; + pub static MADV_DONTFORK : int = 10; + pub static MADV_DOFORK : int = 11; + pub static MADV_MERGEABLE : int = 12; + pub static MADV_UNMERGEABLE : int = 13; + pub static MADV_HWPOISON : int = 100; } #[cfg(target_arch = "x86")] #[cfg(target_arch = "x86_64")] @@ -1157,12 +1220,42 @@ pub mod consts { pub static O_RSYNC : int = 1052672; pub static O_DSYNC : int = 4096; pub static O_SYNC : int = 1052672; + + pub static PROT_GROWSDOWN : int = 0x010000000; + pub static PROT_GROWSUP : int = 0x020000000; + + pub static MAP_TYPE : int = 0x000f; + pub static MAP_ANONONYMOUS : int = 0x1000; + pub static MAP_32BIT : int = 0x0040; + pub static MAP_GROWSDOWN : int = 0x0100; + pub static MAP_DENYWRITE : int = 0x0800; + pub static MAP_EXECUTABLE : int = 0x01000; + pub static MAP_LOCKED : int = 0x02000; + pub static MAP_NONRESERVE : int = 0x04000; + pub static MAP_POPULATE : int = 0x08000; + pub static MAP_NONBLOCK : int = 0x010000; + pub static MAP_STACK : int = 0x020000; } #[cfg(target_arch = "mips")] pub mod extra { pub static O_RSYNC : int = 16400; pub static O_DSYNC : int = 16; pub static O_SYNC : int = 16400; + + pub static PROT_GROWSDOWN : int = 0x010000000; + pub static PROT_GROWSUP : int = 0x020000000; + + pub static MAP_TYPE : int = 0x000f; + pub static MAP_ANONONYMOUS : int = 0x1000; + pub static MAP_32BIT : int = 0x0040; + pub static MAP_GROWSDOWN : int = 0x0100; + pub static MAP_DENYWRITE : int = 0x0800; + pub static MAP_EXECUTABLE : int = 0x01000; + pub static MAP_LOCKED : int = 0x02000; + pub static MAP_NONRESERVE : int = 0x04000; + pub static MAP_POPULATE : int = 0x08000; + pub static MAP_NONBLOCK : int = 0x010000; + pub static MAP_STACK : int = 0x020000; } } @@ -1188,6 +1281,8 @@ pub mod consts { pub mod c99 { } pub mod posix88 { + use libc::types::common::c95::c_void; + pub static O_RDONLY : int = 0; pub static O_WRONLY : int = 1; pub static O_RDWR : int = 2; @@ -1230,6 +1325,26 @@ pub mod consts { pub static SIGPIPE : int = 13; pub static SIGALRM : int = 14; pub static SIGTERM : int = 15; + + pub static PROT_NONE : int = 0; + pub static PROT_READ : int = 1; + pub static PROT_WRITE : int = 2; + pub static PROT_EXEC : int = 4; + + pub static MAP_FILE : int = 0x0000; + pub static MAP_SHARED : int = 0x0001; + pub static MAP_PRIVATE : int = 0x0002; + pub static MAP_FIXED : int = 0x0010; + pub static MAP_ANON : int = 0x1000; + + pub static MAP_FAILED : *c_void = -1 as *c_void; + + pub static MCL_CURRENT : int = 0x0001; + pub static MCL_FUTURE : int = 0x0002; + + pub static MS_SYNC : int = 0x0000; + pub static MS_ASYNC : int = 0x0001; + pub static MS_INVALIDATE : int = 0x0002; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1245,16 +1360,48 @@ pub mod consts { pub static GLOB_NOSPACE : int = -1; pub static GLOB_ABORTED : int = -2; pub static GLOB_NOMATCH : int = -3; + + pub static POSIX_MADV_NORMAL : int = 0; + pub static POSIX_MADV_RANDOM : int = 1; + pub static POSIX_MADV_SEQUENTIAL : int = 2; + pub static POSIX_MADV_WILLNEED : int = 3; + pub static POSIX_MADV_DONTNEED : int = 4; } pub mod posix08 { } pub mod bsd44 { + pub static MADV_NORMAL : int = 0; + pub static MADV_RANDOM : int = 1; + pub static MADV_SEQUENTIAL : int = 2; + pub static MADV_WILLNEED : int = 3; + pub static MADV_DONTNEED : int = 4; + pub static MADV_FREE : int = 5; + pub static MADV_NOSYNC : int = 6; + pub static MADV_AUTOSYNC : int = 7; + pub static MADV_NOCORE : int = 8; + pub static MADV_CORE : int = 9; + pub static MADV_PROTECT : int = 10; + + pub static MINCORE_INCORE : int = 0x1; + pub static MINCORE_REFERENCED : int = 0x2; + pub static MINCORE_MODIFIED : int = 0x4; + pub static MINCORE_REFERENCED_OTHER : int = 0x8; + pub static MINCORE_MODIFIED_OTHER : int = 0x10; + pub static MINCORE_SUPER : int = 0x20; } pub mod extra { pub static O_SYNC : int = 128; pub static CTL_KERN: int = 1; pub static KERN_PROC: int = 14; pub static KERN_PROC_PATHNAME: int = 12; + + pub static MAP_COPY : int = 0x0002; + pub static MAP_RENAME : int = 0x0020; + pub static MAP_NORESERVE : int = 0x0040; + pub static MAP_HASSEMAPHORE : int = 0x0200; + pub static MAP_STACK : int = 0x0400; + pub static MAP_NOSYNC : int = 0x0800; + pub static MAP_NOCORE : int = 0x020000; } } @@ -1280,6 +1427,8 @@ pub mod consts { pub mod c99 { } pub mod posix88 { + use libc::types::common::c95::c_void; + pub static O_RDONLY : int = 0; pub static O_WRONLY : int = 1; pub static O_RDWR : int = 2; @@ -1322,6 +1471,29 @@ pub mod consts { pub static SIGPIPE : int = 13; pub static SIGALRM : int = 14; pub static SIGTERM : int = 15; + + pub static PROT_NONE : int = 0; + pub static PROT_READ : int = 1; + pub static PROT_WRITE : int = 2; + pub static PROT_EXEC : int = 4; + + pub static MAP_FILE : int = 0x0000; + pub static MAP_SHARED : int = 0x0001; + pub static MAP_PRIVATE : int = 0x0002; + pub static MAP_FIXED : int = 0x0010; + pub static MAP_ANON : int = 0x1000; + + pub static MAP_FAILED : *c_void = -1 as *c_void; + + pub static MCL_CURRENT : int = 0x0001; + pub static MCL_FUTURE : int = 0x0002; + + pub static MS_ASYNC : int = 0x0001; + pub static MS_INVALIDATE : int = 0x0002; + pub static MS_SYNC : int = 0x0010; + + pub static MS_KILLPAGES : int = 0x0004; + pub static MS_DEACTIVATE : int = 0x0008; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1337,15 +1509,45 @@ pub mod consts { pub static GLOB_NOSPACE : int = -1; pub static GLOB_ABORTED : int = -2; pub static GLOB_NOMATCH : int = -3; + + pub static POSIX_MADV_NORMAL : int = 0; + pub static POSIX_MADV_RANDOM : int = 1; + pub static POSIX_MADV_SEQUENTIAL : int = 2; + pub static POSIX_MADV_WILLNEED : int = 3; + pub static POSIX_MADV_DONTNEED : int = 4; } pub mod posix08 { } pub mod bsd44 { + pub static MADV_NORMAL : int = 0; + pub static MADV_RANDOM : int = 1; + pub static MADV_SEQUENTIAL : int = 2; + pub static MADV_WILLNEED : int = 3; + pub static MADV_DONTNEED : int = 4; + pub static MADV_FREE : int = 5; + pub static MADV_ZERO_WIRED_PAGES : int = 6; + pub static MADV_FREE_REUSABLE : int = 7; + pub static MADV_FREE_REUSE : int = 8; + pub static MADV_CAN_REUSE : int = 9; + + pub static MINCORE_INCORE : int = 0x1; + pub static MINCORE_REFERENCED : int = 0x2; + pub static MINCORE_MODIFIED : int = 0x4; + pub static MINCORE_REFERENCED_OTHER : int = 0x8; + pub static MINCORE_MODIFIED_OTHER : int = 0x10; } pub mod extra { pub static O_DSYNC : int = 4194304; pub static O_SYNC : int = 128; pub static F_FULLFSYNC : int = 51; + + pub static MAP_COPY : int = 0x0002; + pub static MAP_RENAME : int = 0x0020; + pub static MAP_NORESERVE : int = 0x0040; + pub static MAP_NOEXTEND : int = 0x0100; + pub static MAP_HASSEMAPHORE : int = 0x0200; + pub static MAP_NOCACHE : int = 0x0400; + pub static MAP_JIT : int = 0x0800; } } } @@ -1658,6 +1860,9 @@ pub mod funcs { -> c_int; } } + + pub mod mman { + } } @@ -1835,6 +2040,38 @@ pub mod funcs { unsafe fn kill(pid: pid_t, sig: c_int) -> c_int; } } + + #[nolink] + #[abi = "cdecl"] + pub mod mman { + use libc::types::common::c95::{c_void}; + use libc::types::os::arch::c95::{size_t, c_int, c_char}; + use libc::types::os::arch::posix88::{mode_t, off_t}; + + pub extern { + unsafe fn mlock(addr: *c_void, len: size_t) -> c_int; + unsafe fn munlock(addr: *c_void, len: size_t) -> c_int; + unsafe fn mlockall(flags: c_int) -> c_int; + unsafe fn munlockall() -> c_int; + + unsafe fn mmap(addr: *c_void, + len: size_t, + prot: c_int, + flags: c_int, + fd: c_int, + offset: off_t) -> *mut c_void; + unsafe fn munmap(addr: *c_void, len: size_t) -> c_int; + + unsafe fn mprotect(addr: *c_void, len: size_t, prot: c_int) + -> c_int; + + unsafe fn msync(addr: *c_void, len: size_t, flags: c_int) + -> c_int; + unsafe fn shm_open(name: *c_char, oflag: c_int, mode: mode_t) + -> c_int; + unsafe fn shm_unlink(name: *c_char) -> c_int; + } + } } #[cfg(target_os = "linux")] @@ -1913,6 +2150,19 @@ pub mod funcs { unsafe fn globfree(pglob: *mut glob_t); } } + + #[nolink] + #[abi = "cdecl"] + pub mod mman { + use libc::types::common::c95::{c_void}; + use libc::types::os::arch::c95::{c_int, size_t}; + + pub extern { + unsafe fn posix_madvise(addr: *c_void, + len: size_t, + advice: c_int) -> c_int; + } + } } #[cfg(target_os = "win32")] @@ -1925,6 +2175,9 @@ pub mod funcs { pub mod glob { } + + pub mod mman { + } } @@ -1943,7 +2196,8 @@ pub mod funcs { #[cfg(target_os = "freebsd")] pub mod bsd44 { use libc::types::common::c95::{c_void}; - use libc::types::os::arch::c95::{c_char, c_int, c_uint, size_t}; + use libc::types::os::arch::c95::{c_char, c_uchar, c_int, c_uint, + size_t}; #[abi = "cdecl"] pub extern { @@ -1959,6 +2213,12 @@ pub mod funcs { sizep: *mut size_t) -> c_int; unsafe fn getdtablesize() -> c_int; + + unsafe fn madvise(addr: *c_void, len: size_t, advice: c_int) + -> c_int; + + unsafe fn mincore(addr: *c_void, len: size_t, vec: *c_uchar) + -> c_int; } } @@ -1966,11 +2226,18 @@ pub mod funcs { #[cfg(target_os = "linux")] #[cfg(target_os = "android")] pub mod bsd44 { - use libc::types::os::arch::c95::{c_int}; + use libc::types::common::c95::{c_void}; + use libc::types::os::arch::c95::{c_uchar, c_int, size_t}; #[abi = "cdecl"] pub extern { unsafe fn getdtablesize() -> c_int; + + unsafe fn madvise(addr: *c_void, len: size_t, advice: c_int) + -> c_int; + + unsafe fn mincore(addr: *c_void, len: size_t, vec: *c_uchar) + -> c_int; } } From ddd6f5928395c67b249ce3ec76a1ff4be303208d Mon Sep 17 00:00:00 2001 From: Fedor Indutny Date: Thu, 20 Jun 2013 16:41:50 +0200 Subject: [PATCH 14/31] libc: add POSIX-compatible sysconf consts Because its part of POSIX. Values are taken from FreeBSD, linux and OSX header files. --- src/libstd/libc.rs | 254 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 254 insertions(+) diff --git a/src/libstd/libc.rs b/src/libstd/libc.rs index 2aaeda69326b..9d6755fc22d3 100644 --- a/src/libstd/libc.rs +++ b/src/libstd/libc.rs @@ -1176,6 +1176,63 @@ pub mod consts { pub static MS_ASYNC : int = 0x0001; pub static MS_INVALIDATE : int = 0x0002; pub static MS_SYNC : int = 0x0004; + + pub static _SC_ARG_MAX : int = 0; + pub static _SC_CHILD_MAX : int = 1; + pub static _SC_CLK_TCK : int = 2; + pub static _SC_NGROUPS_MAX : int = 3; + pub static _SC_OPEN_MAX : int = 4; + pub static _SC_STREAM_MAX : int = 5; + pub static _SC_TZNAME_MAX : int = 6; + pub static _SC_JOB_CONTROL : int = 7; + pub static _SC_SAVED_IDS : int = 8; + pub static _SC_REALTIME_SIGNALS : int = 9; + pub static _SC_PRIORITY_SCHEDULING : int = 10; + pub static _SC_TIMERS : int = 11; + pub static _SC_ASYNCHRONOUS_IO : int = 12; + pub static _SC_PRIORITIZED_IO : int = 13; + pub static _SC_SYNCHRONIZED_IO : int = 14; + pub static _SC_FSYNC : int = 15; + pub static _SC_MAPPED_FILES : int = 16; + pub static _SC_MEMLOCK : int = 17; + pub static _SC_MEMLOCK_RANGE : int = 18; + pub static _SC_MEMORY_PROTECTION : int = 19; + pub static _SC_MESSAGE_PASSING : int = 20; + pub static _SC_SEMAPHORES : int = 21; + pub static _SC_SHARED_MEMORY_OBJECTS : int = 22; + pub static _SC_AIO_LISTIO_MAX : int = 23; + pub static _SC_AIO_MAX : int = 24; + pub static _SC_AIO_PRIO_DELTA_MAX : int = 25; + pub static _SC_DELAYTIMER_MAX : int = 26; + pub static _SC_MQ_OPEN_MAX : int = 27; + pub static _SC_VERSION : int = 29; + pub static _SC_PAGESIZE : int = 30; + pub static _SC_RTSIG_MAX : int = 31; + pub static _SC_SEM_NSEMS_MAX : int = 32; + pub static _SC_SEM_VALUE_MAX : int = 33; + pub static _SC_SIGQUEUE_MAX : int = 34; + pub static _SC_TIMER_MAX : int = 35; + pub static _SC_BC_BASE_MAX : int = 36; + pub static _SC_BC_DIM_MAX : int = 37; + pub static _SC_BC_SCALE_MAX : int = 38; + pub static _SC_BC_STRING_MAX : int = 39; + pub static _SC_COLL_WEIGHTS_MAX : int = 40; + pub static _SC_EXPR_NEST_MAX : int = 42; + pub static _SC_LINE_MAX : int = 43; + pub static _SC_RE_DUP_MAX : int = 44; + pub static _SC_2_VERSION : int = 46; + pub static _SC_2_C_BIND : int = 47; + pub static _SC_2_C_DEV : int = 48; + pub static _SC_2_FORT_DEV : int = 49; + pub static _SC_2_FORT_RUN : int = 50; + pub static _SC_2_SW_DEV : int = 51; + pub static _SC_2_LOCALEDEF : int = 52; + pub static _SC_2_CHAR_TERM : int = 95; + pub static _SC_2_C_VERSION : int = 96; + pub static _SC_2_UPE : int = 97; + pub static _SC_XBS5_ILP32_OFF32 : int = 125; + pub static _SC_XBS5_ILP32_OFFBIG : int = 126; + pub static _SC_XBS5_LPBIG_OFFBIG : int = 128; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1197,6 +1254,35 @@ pub mod consts { pub static POSIX_MADV_SEQUENTIAL : int = 2; pub static POSIX_MADV_WILLNEED : int = 3; pub static POSIX_MADV_DONTNEED : int = 4; + + pub static _SC_MQ_PRIO_MAX : int = 28; + pub static _SC_IOV_MAX : int = 60; + pub static _SC_GETGR_R_SIZE_MAX : int = 69; + pub static _SC_GETPW_R_SIZE_MAX : int = 70; + pub static _SC_LOGIN_NAME_MAX : int = 71; + pub static _SC_TTY_NAME_MAX : int = 72; + pub static _SC_THREADS : int = 67; + pub static _SC_THREAD_SAFE_FUNCTIONS : int = 68; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 73; + pub static _SC_THREAD_KEYS_MAX : int = 74; + pub static _SC_THREAD_STACK_MIN : int = 75; + pub static _SC_THREAD_THREADS_MAX : int = 76; + pub static _SC_THREAD_ATTR_STACKADDR : int = 77; + pub static _SC_THREAD_ATTR_STACKSIZE : int = 78; + pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 79; + pub static _SC_THREAD_PRIO_INHERIT : int = 80; + pub static _SC_THREAD_PRIO_PROTECT : int = 81; + pub static _SC_THREAD_PROCESS_SHARED : int = 82; + pub static _SC_ATEXIT_MAX : int = 87; + pub static _SC_XOPEN_VERSION : int = 89; + pub static _SC_XOPEN_XCU_VERSION : int = 90; + pub static _SC_XOPEN_UNIX : int = 91; + pub static _SC_XOPEN_CRYPT : int = 92; + pub static _SC_XOPEN_ENH_I18N : int = 93; + pub static _SC_XOPEN_SHM : int = 94; + pub static _SC_XOPEN_LEGACY : int = 129; + pub static _SC_XOPEN_REALTIME : int = 130; + pub static _SC_XOPEN_REALTIME_THREADS : int = 131; } pub mod posix08 { } @@ -1345,6 +1431,59 @@ pub mod consts { pub static MS_SYNC : int = 0x0000; pub static MS_ASYNC : int = 0x0001; pub static MS_INVALIDATE : int = 0x0002; + + pub static _SC_ARG_MAX : int = 1; + pub static _SC_CHILD_MAX : int = 2; + pub static _SC_CLK_TCK : int = 3; + pub static _SC_NGROUPS_MAX : int = 4; + pub static _SC_OPEN_MAX : int = 5; + pub static _SC_JOB_CONTROL : int = 6; + pub static _SC_SAVED_IDS : int = 7; + pub static _SC_VERSION : int = 8; + pub static _SC_BC_BASE_MAX : int = 9; + pub static _SC_BC_DIM_MAX : int = 10; + pub static _SC_BC_SCALE_MAX : int = 11; + pub static _SC_BC_STRING_MAX : int = 12; + pub static _SC_COLL_WEIGHTS_MAX : int = 13; + pub static _SC_EXPR_NEST_MAX : int = 14; + pub static _SC_LINE_MAX : int = 15; + pub static _SC_RE_DUP_MAX : int = 16; + pub static _SC_2_VERSION : int = 17; + pub static _SC_2_C_BIND : int = 18; + pub static _SC_2_C_DEV : int = 19; + pub static _SC_2_CHAR_TERM : int = 20; + pub static _SC_2_FORT_DEV : int = 21; + pub static _SC_2_FORT_RUN : int = 22; + pub static _SC_2_LOCALEDEF : int = 23; + pub static _SC_2_SW_DEV : int = 24; + pub static _SC_2_UPE : int = 25; + pub static _SC_STREAM_MAX : int = 26; + pub static _SC_TZNAME_MAX : int = 27; + pub static _SC_ASYNCHRONOUS_IO : int = 28; + pub static _SC_MAPPED_FILES : int = 29; + pub static _SC_MEMLOCK : int = 30; + pub static _SC_MEMLOCK_RANGE : int = 31; + pub static _SC_MEMORY_PROTECTION : int = 32; + pub static _SC_MESSAGE_PASSING : int = 33; + pub static _SC_PRIORITIZED_IO : int = 34; + pub static _SC_PRIORITY_SCHEDULING : int = 35; + pub static _SC_REALTIME_SIGNALS : int = 36; + pub static _SC_SEMAPHORES : int = 37; + pub static _SC_FSYNC : int = 38; + pub static _SC_SHARED_MEMORY_OBJECTS : int = 39; + pub static _SC_SYNCHRONIZED_IO : int = 40; + pub static _SC_TIMERS : int = 41; + pub static _SC_AIO_LISTIO_MAX : int = 42; + pub static _SC_AIO_MAX : int = 43; + pub static _SC_AIO_PRIO_DELTA_MAX : int = 44; + pub static _SC_DELAYTIMER_MAX : int = 45; + pub static _SC_MQ_OPEN_MAX : int = 46; + pub static _SC_PAGESIZE : int = 47; + pub static _SC_RTSIG_MAX : int = 48; + pub static _SC_SEM_NSEMS_MAX : int = 49; + pub static _SC_SEM_VALUE_MAX : int = 50; + pub static _SC_SIGQUEUE_MAX : int = 51; + pub static _SC_TIMER_MAX : int = 52; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1366,6 +1505,35 @@ pub mod consts { pub static POSIX_MADV_SEQUENTIAL : int = 2; pub static POSIX_MADV_WILLNEED : int = 3; pub static POSIX_MADV_DONTNEED : int = 4; + + pub static _SC_IOV_MAX : int = 56; + pub static _SC_GETGR_R_SIZE_MAX : int = 70; + pub static _SC_GETPW_R_SIZE_MAX : int = 71; + pub static _SC_LOGIN_NAME_MAX : int = 73; + pub static _SC_MQ_PRIO_MAX : int = 75; + pub static _SC_THREAD_ATTR_STACKADDR : int = 82; + pub static _SC_THREAD_ATTR_STACKSIZE : int = 83; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 85; + pub static _SC_THREAD_KEYS_MAX : int = 86; + pub static _SC_THREAD_PRIO_INHERIT : int = 87; + pub static _SC_THREAD_PRIO_PROTECT : int = 88; + pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 89; + pub static _SC_THREAD_PROCESS_SHARED : int = 90; + pub static _SC_THREAD_SAFE_FUNCTIONS : int = 91; + pub static _SC_THREAD_STACK_MIN : int = 93; + pub static _SC_THREAD_THREADS_MAX : int = 94; + pub static _SC_THREADS : int = 96; + pub static _SC_TTY_NAME_MAX : int = 101; + pub static _SC_ATEXIT_MAX : int = 107; + pub static _SC_XOPEN_CRYPT : int = 108; + pub static _SC_XOPEN_ENH_I18N : int = 109; + pub static _SC_XOPEN_LEGACY : int = 110; + pub static _SC_XOPEN_REALTIME : int = 111; + pub static _SC_XOPEN_REALTIME_THREADS : int = 112; + pub static _SC_XOPEN_SHM : int = 113; + pub static _SC_XOPEN_UNIX : int = 115; + pub static _SC_XOPEN_VERSION : int = 116; + pub static _SC_XOPEN_XCU_VERSION : int = 117; } pub mod posix08 { } @@ -1494,6 +1662,63 @@ pub mod consts { pub static MS_KILLPAGES : int = 0x0004; pub static MS_DEACTIVATE : int = 0x0008; + + pub static _SC_ARG_MAX : int = 1; + pub static _SC_CHILD_MAX : int = 2; + pub static _SC_CLK_TCK : int = 3; + pub static _SC_NGROUPS_MAX : int = 4; + pub static _SC_OPEN_MAX : int = 5; + pub static _SC_JOB_CONTROL : int = 6; + pub static _SC_SAVED_IDS : int = 7; + pub static _SC_VERSION : int = 8; + pub static _SC_BC_BASE_MAX : int = 9; + pub static _SC_BC_DIM_MAX : int = 10; + pub static _SC_BC_SCALE_MAX : int = 11; + pub static _SC_BC_STRING_MAX : int = 12; + pub static _SC_COLL_WEIGHTS_MAX : int = 13; + pub static _SC_EXPR_NEST_MAX : int = 14; + pub static _SC_LINE_MAX : int = 15; + pub static _SC_RE_DUP_MAX : int = 16; + pub static _SC_2_VERSION : int = 17; + pub static _SC_2_C_BIND : int = 18; + pub static _SC_2_C_DEV : int = 19; + pub static _SC_2_CHAR_TERM : int = 20; + pub static _SC_2_FORT_DEV : int = 21; + pub static _SC_2_FORT_RUN : int = 22; + pub static _SC_2_LOCALEDEF : int = 23; + pub static _SC_2_SW_DEV : int = 24; + pub static _SC_2_UPE : int = 25; + pub static _SC_STREAM_MAX : int = 26; + pub static _SC_TZNAME_MAX : int = 27; + pub static _SC_ASYNCHRONOUS_IO : int = 28; + pub static _SC_PAGESIZE : int = 29; + pub static _SC_MEMLOCK : int = 30; + pub static _SC_MEMLOCK_RANGE : int = 31; + pub static _SC_MEMORY_PROTECTION : int = 32; + pub static _SC_MESSAGE_PASSING : int = 33; + pub static _SC_PRIORITIZED_IO : int = 34; + pub static _SC_PRIORITY_SCHEDULING : int = 35; + pub static _SC_REALTIME_SIGNALS : int = 36; + pub static _SC_SEMAPHORES : int = 37; + pub static _SC_FSYNC : int = 38; + pub static _SC_SHARED_MEMORY_OBJECTS : int = 39; + pub static _SC_SYNCHRONIZED_IO : int = 40; + pub static _SC_TIMERS : int = 41; + pub static _SC_AIO_LISTIO_MAX : int = 42; + pub static _SC_AIO_MAX : int = 43; + pub static _SC_AIO_PRIO_DELTA_MAX : int = 44; + pub static _SC_DELAYTIMER_MAX : int = 45; + pub static _SC_MQ_OPEN_MAX : int = 46; + pub static _SC_MAPPED_FILES : int = 47; + pub static _SC_RTSIG_MAX : int = 48; + pub static _SC_SEM_NSEMS_MAX : int = 49; + pub static _SC_SEM_VALUE_MAX : int = 50; + pub static _SC_SIGQUEUE_MAX : int = 51; + pub static _SC_TIMER_MAX : int = 52; + pub static _SC_XBS5_ILP32_OFF32 : int = 122; + pub static _SC_XBS5_ILP32_OFFBIG : int = 123; + pub static _SC_XBS5_LP64_OFF64 : int = 124; + pub static _SC_XBS5_LPBIG_OFFBIG : int = 125; } pub mod posix01 { pub static SIGTRAP : int = 5; @@ -1515,6 +1740,35 @@ pub mod consts { pub static POSIX_MADV_SEQUENTIAL : int = 2; pub static POSIX_MADV_WILLNEED : int = 3; pub static POSIX_MADV_DONTNEED : int = 4; + + pub static _SC_IOV_MAX : int = 56; + pub static _SC_GETGR_R_SIZE_MAX : int = 70; + pub static _SC_GETPW_R_SIZE_MAX : int = 71; + pub static _SC_LOGIN_NAME_MAX : int = 73; + pub static _SC_MQ_PRIO_MAX : int = 75; + pub static _SC_THREAD_ATTR_STACKADDR : int = 82; + pub static _SC_THREAD_ATTR_STACKSIZE : int = 83; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 85; + pub static _SC_THREAD_KEYS_MAX : int = 86; + pub static _SC_THREAD_PRIO_INHERIT : int = 87; + pub static _SC_THREAD_PRIO_PROTECT : int = 88; + pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 89; + pub static _SC_THREAD_PROCESS_SHARED : int = 90; + pub static _SC_THREAD_SAFE_FUNCTIONS : int = 91; + pub static _SC_THREAD_STACK_MIN : int = 93; + pub static _SC_THREAD_THREADS_MAX : int = 94; + pub static _SC_THREADS : int = 96; + pub static _SC_TTY_NAME_MAX : int = 101; + pub static _SC_ATEXIT_MAX : int = 107; + pub static _SC_XOPEN_CRYPT : int = 108; + pub static _SC_XOPEN_ENH_I18N : int = 109; + pub static _SC_XOPEN_LEGACY : int = 110; + pub static _SC_XOPEN_REALTIME : int = 111; + pub static _SC_XOPEN_REALTIME_THREADS : int = 112; + pub static _SC_XOPEN_SHM : int = 113; + pub static _SC_XOPEN_UNIX : int = 115; + pub static _SC_XOPEN_VERSION : int = 116; + pub static _SC_XOPEN_XCU_VERSION : int = 121; } pub mod posix08 { } From f8ae3cdcaacb29c7b56e546a9ddab1396b615f8f Mon Sep 17 00:00:00 2001 From: Philipp Brueschweiler Date: Mon, 24 Jun 2013 19:14:20 +0200 Subject: [PATCH 15/31] Fix test failure on windows This patch ensures that the multiple extern definitions of `free` in the run-pass tests have the same declaration, working around #7352. --- src/test/run-pass/extern-pub.rs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/test/run-pass/extern-pub.rs b/src/test/run-pass/extern-pub.rs index 2d6cc2c78deb..27c45893930c 100644 --- a/src/test/run-pass/extern-pub.rs +++ b/src/test/run-pass/extern-pub.rs @@ -1,7 +1,5 @@ -use std::libc; - extern { - pub unsafe fn free(p: *libc::c_void); + pub unsafe fn free(p: *u8); } pub fn main() { From bc70edbb25487e539386c68bd6e821eedd704194 Mon Sep 17 00:00:00 2001 From: Fedor Indutny Date: Fri, 21 Jun 2013 16:39:37 +0200 Subject: [PATCH 16/31] libc: (u)int => c_(u)int for consts --- src/libstd/libc.rs | 1459 +++++++++++++++++++++++--------------------- src/libstd/os.rs | 2 +- 2 files changed, 748 insertions(+), 713 deletions(-) diff --git a/src/libstd/libc.rs b/src/libstd/libc.rs index 9d6755fc22d3..523645e69a52 100644 --- a/src/libstd/libc.rs +++ b/src/libstd/libc.rs @@ -287,7 +287,7 @@ pub mod types { #[cfg(target_arch = "x86")] #[cfg(target_arch = "mips")] pub mod posix01 { - use libc::types::os::arch::c95::{c_short, c_long, c_ulong, time_t}; + use libc::types::os::arch::c95::{c_short, c_long, time_t}; use libc::types::os::arch::posix88::{dev_t, gid_t, ino_t}; use libc::types::os::arch::posix88::{mode_t, off_t}; use libc::types::os::arch::posix88::{uid_t}; @@ -905,52 +905,56 @@ pub mod consts { #[cfg(target_os = "win32")] pub mod os { pub mod c95 { - pub static EXIT_FAILURE : int = 1; - pub static EXIT_SUCCESS : int = 0; - pub static RAND_MAX : int = 32767; - pub static EOF : int = -1; - pub static SEEK_SET : int = 0; - pub static SEEK_CUR : int = 1; - pub static SEEK_END : int = 2; - pub static _IOFBF : int = 0; - pub static _IONBF : int = 4; - pub static _IOLBF : int = 64; - pub static BUFSIZ : uint = 512_u; - pub static FOPEN_MAX : uint = 20_u; - pub static FILENAME_MAX : uint = 260_u; - pub static L_tmpnam : uint = 16_u; - pub static TMP_MAX : uint = 32767_u; + use libc::types::os::arch::c95::{c_int, c_uint}; + + pub static EXIT_FAILURE : c_int = 1; + pub static EXIT_SUCCESS : c_int = 0; + pub static RAND_MAX : c_int = 32767; + pub static EOF : c_int = -1; + pub static SEEK_SET : c_int = 0; + pub static SEEK_CUR : c_int = 1; + pub static SEEK_END : c_int = 2; + pub static _IOFBF : c_int = 0; + pub static _IONBF : c_int = 4; + pub static _IOLBF : c_int = 64; + pub static BUFSIZ : c_uint = 512_u32; + pub static FOPEN_MAX : c_uint = 20_u32; + pub static FILENAME_MAX : c_uint = 260_u32; + pub static L_tmpnam : c_uint = 16_u32; + pub static TMP_MAX : c_uint = 32767_u32; } pub mod c99 { } pub mod posix88 { - pub static O_RDONLY : int = 0; - pub static O_WRONLY : int = 1; - pub static O_RDWR : int = 2; - pub static O_APPEND : int = 8; - pub static O_CREAT : int = 256; - pub static O_EXCL : int = 1024; - pub static O_TRUNC : int = 512; - pub static S_IFIFO : int = 4096; - pub static S_IFCHR : int = 8192; - pub static S_IFBLK : int = 12288; - pub static S_IFDIR : int = 16384; - pub static S_IFREG : int = 32768; - pub static S_IFMT : int = 61440; - pub static S_IEXEC : int = 64; - pub static S_IWRITE : int = 128; - pub static S_IREAD : int = 256; - pub static S_IRWXU : int = 448; - pub static S_IXUSR : int = 64; - pub static S_IWUSR : int = 128; - pub static S_IRUSR : int = 256; - pub static F_OK : int = 0; - pub static R_OK : int = 4; - pub static W_OK : int = 2; - pub static X_OK : int = 1; - pub static STDIN_FILENO : int = 0; - pub static STDOUT_FILENO : int = 1; - pub static STDERR_FILENO : int = 2; + use libc::types::os::arch::c95::c_int; + + pub static O_RDONLY : c_int = 0; + pub static O_WRONLY : c_int = 1; + pub static O_RDWR : c_int = 2; + pub static O_APPEND : c_int = 8; + pub static O_CREAT : c_int = 256; + pub static O_EXCL : c_int = 1024; + pub static O_TRUNC : c_int = 512; + pub static S_IFIFO : c_int = 4096; + pub static S_IFCHR : c_int = 8192; + pub static S_IFBLK : c_int = 12288; + pub static S_IFDIR : c_int = 16384; + pub static S_IFREG : c_int = 32768; + pub static S_IFMT : c_int = 61440; + pub static S_IEXEC : c_int = 64; + pub static S_IWRITE : c_int = 128; + pub static S_IREAD : c_int = 256; + pub static S_IRWXU : c_int = 448; + pub static S_IXUSR : c_int = 64; + pub static S_IWUSR : c_int = 128; + pub static S_IRUSR : c_int = 256; + pub static F_OK : c_int = 0; + pub static R_OK : c_int = 4; + pub static W_OK : c_int = 2; + pub static X_OK : c_int = 1; + pub static STDIN_FILENO : c_int = 0; + pub static STDOUT_FILENO : c_int = 1; + pub static STDERR_FILENO : c_int = 2; } pub mod posix01 { } @@ -959,18 +963,19 @@ pub mod consts { pub mod bsd44 { } pub mod extra { + use libc::types::os::arch::c95::c_int; use libc::types::os::arch::extra::{DWORD, BOOL}; pub static TRUE : BOOL = 1; pub static FALSE : BOOL = 0; - pub static O_TEXT : int = 16384; - pub static O_BINARY : int = 32768; - pub static O_NOINHERIT: int = 128; + pub static O_TEXT : c_int = 16384; + pub static O_BINARY : c_int = 32768; + pub static O_NOINHERIT: c_int = 128; - pub static ERROR_SUCCESS : int = 0; - pub static ERROR_INSUFFICIENT_BUFFER : int = 122; - pub static INVALID_HANDLE_VALUE: int = -1; + pub static ERROR_SUCCESS : c_int = 0; + pub static ERROR_INSUFFICIENT_BUFFER : c_int = 122; + pub static INVALID_HANDLE_VALUE: c_int = -1; pub static DELETE : DWORD = 0x00010000; pub static READ_CONTROL : DWORD = 0x00020000; @@ -1023,21 +1028,23 @@ pub mod consts { #[cfg(target_os = "android")] pub mod os { pub mod c95 { - pub static EXIT_FAILURE : int = 1; - pub static EXIT_SUCCESS : int = 0; - pub static RAND_MAX : int = 2147483647; - pub static EOF : int = -1; - pub static SEEK_SET : int = 0; - pub static SEEK_CUR : int = 1; - pub static SEEK_END : int = 2; - pub static _IOFBF : int = 0; - pub static _IONBF : int = 2; - pub static _IOLBF : int = 1; - pub static BUFSIZ : uint = 8192_u; - pub static FOPEN_MAX : uint = 16_u; - pub static FILENAME_MAX : uint = 4096_u; - pub static L_tmpnam : uint = 20_u; - pub static TMP_MAX : uint = 238328_u; + use libc::types::os::arch::c95::{c_int, c_uint}; + + pub static EXIT_FAILURE : c_int = 1; + pub static EXIT_SUCCESS : c_int = 0; + pub static RAND_MAX : c_int = 2147483647; + pub static EOF : c_int = -1; + pub static SEEK_SET : c_int = 0; + pub static SEEK_CUR : c_int = 1; + pub static SEEK_END : c_int = 2; + pub static _IOFBF : c_int = 0; + pub static _IONBF : c_int = 2; + pub static _IOLBF : c_int = 1; + pub static BUFSIZ : c_uint = 8192_u32; + pub static FOPEN_MAX : c_uint = 16_u32; + pub static FILENAME_MAX : c_uint = 4096_u32; + pub static L_tmpnam : c_uint = 20_u32; + pub static TMP_MAX : c_uint = 238328_u32; } pub mod c99 { } @@ -1045,763 +1052,791 @@ pub mod consts { #[cfg(target_arch = "x86_64")] #[cfg(target_arch = "arm")] pub mod posix88 { + use libc::types::os::arch::c95::c_int; use libc::types::common::c95::c_void; - pub static O_RDONLY : int = 0; - pub static O_WRONLY : int = 1; - pub static O_RDWR : int = 2; - pub static O_APPEND : int = 1024; - pub static O_CREAT : int = 64; - pub static O_EXCL : int = 128; - pub static O_TRUNC : int = 512; - pub static S_IFIFO : int = 4096; - pub static S_IFCHR : int = 8192; - pub static S_IFBLK : int = 24576; - pub static S_IFDIR : int = 16384; - pub static S_IFREG : int = 32768; - pub static S_IFMT : int = 61440; - pub static S_IEXEC : int = 64; - pub static S_IWRITE : int = 128; - pub static S_IREAD : int = 256; - pub static S_IRWXU : int = 448; - pub static S_IXUSR : int = 64; - pub static S_IWUSR : int = 128; - pub static S_IRUSR : int = 256; - pub static F_OK : int = 0; - pub static R_OK : int = 4; - pub static W_OK : int = 2; - pub static X_OK : int = 1; - pub static STDIN_FILENO : int = 0; - pub static STDOUT_FILENO : int = 1; - pub static STDERR_FILENO : int = 2; - pub static F_LOCK : int = 1; - pub static F_TEST : int = 3; - pub static F_TLOCK : int = 2; - pub static F_ULOCK : int = 0; - pub static SIGHUP : int = 1; - pub static SIGINT : int = 2; - pub static SIGQUIT : int = 3; - pub static SIGILL : int = 4; - pub static SIGABRT : int = 6; - pub static SIGFPE : int = 8; - pub static SIGKILL : int = 9; - pub static SIGSEGV : int = 11; - pub static SIGPIPE : int = 13; - pub static SIGALRM : int = 14; - pub static SIGTERM : int = 15; + pub static O_RDONLY : c_int = 0; + pub static O_WRONLY : c_int = 1; + pub static O_RDWR : c_int = 2; + pub static O_APPEND : c_int = 1024; + pub static O_CREAT : c_int = 64; + pub static O_EXCL : c_int = 128; + pub static O_TRUNC : c_int = 512; + pub static S_IFIFO : c_int = 4096; + pub static S_IFCHR : c_int = 8192; + pub static S_IFBLK : c_int = 24576; + pub static S_IFDIR : c_int = 16384; + pub static S_IFREG : c_int = 32768; + pub static S_IFMT : c_int = 61440; + pub static S_IEXEC : c_int = 64; + pub static S_IWRITE : c_int = 128; + pub static S_IREAD : c_int = 256; + pub static S_IRWXU : c_int = 448; + pub static S_IXUSR : c_int = 64; + pub static S_IWUSR : c_int = 128; + pub static S_IRUSR : c_int = 256; + pub static F_OK : c_int = 0; + pub static R_OK : c_int = 4; + pub static W_OK : c_int = 2; + pub static X_OK : c_int = 1; + pub static STDIN_FILENO : c_int = 0; + pub static STDOUT_FILENO : c_int = 1; + pub static STDERR_FILENO : c_int = 2; + pub static F_LOCK : c_int = 1; + pub static F_TEST : c_int = 3; + pub static F_TLOCK : c_int = 2; + pub static F_ULOCK : c_int = 0; + pub static SIGHUP : c_int = 1; + pub static SIGINT : c_int = 2; + pub static SIGQUIT : c_int = 3; + pub static SIGILL : c_int = 4; + pub static SIGABRT : c_int = 6; + pub static SIGFPE : c_int = 8; + pub static SIGKILL : c_int = 9; + pub static SIGSEGV : c_int = 11; + pub static SIGPIPE : c_int = 13; + pub static SIGALRM : c_int = 14; + pub static SIGTERM : c_int = 15; - pub static PROT_NONE : int = 0; - pub static PROT_READ : int = 1; - pub static PROT_WRITE : int = 2; - pub static PROT_EXEC : int = 4; + pub static PROT_NONE : c_int = 0; + pub static PROT_READ : c_int = 1; + pub static PROT_WRITE : c_int = 2; + pub static PROT_EXEC : c_int = 4; - pub static MAP_FILE : int = 0x0000; - pub static MAP_SHARED : int = 0x0001; - pub static MAP_PRIVATE : int = 0x0002; - pub static MAP_FIXED : int = 0x0010; - pub static MAP_ANON : int = 0x1000; + pub static MAP_FILE : c_int = 0x0000; + pub static MAP_SHARED : c_int = 0x0001; + pub static MAP_PRIVATE : c_int = 0x0002; + pub static MAP_FIXED : c_int = 0x0010; + pub static MAP_ANON : c_int = 0x1000; pub static MAP_FAILED : *c_void = -1 as *c_void; - pub static MCL_CURRENT : int = 0x0001; - pub static MCL_FUTURE : int = 0x0002; + pub static MCL_CURRENT : c_int = 0x0001; + pub static MCL_FUTURE : c_int = 0x0002; - pub static MS_ASYNC : int = 0x0001; - pub static MS_INVALIDATE : int = 0x0002; - pub static MS_SYNC : int = 0x0004; + pub static MS_ASYNC : c_int = 0x0001; + pub static MS_INVALIDATE : c_int = 0x0002; + pub static MS_SYNC : c_int = 0x0004; } #[cfg(target_arch = "mips")] pub mod posix88 { + use libc::types::os::arch::c95::c_int; use libc::types::common::c95::c_void; - pub static O_RDONLY : int = 0; - pub static O_WRONLY : int = 1; - pub static O_RDWR : int = 2; - pub static O_APPEND : int = 8; - pub static O_CREAT : int = 256; - pub static O_EXCL : int = 1024; - pub static O_TRUNC : int = 512; - pub static S_IFIFO : int = 4096; - pub static S_IFCHR : int = 8192; - pub static S_IFBLK : int = 24576; - pub static S_IFDIR : int = 16384; - pub static S_IFREG : int = 32768; - pub static S_IFMT : int = 61440; - pub static S_IEXEC : int = 64; - pub static S_IWRITE : int = 128; - pub static S_IREAD : int = 256; - pub static S_IRWXU : int = 448; - pub static S_IXUSR : int = 64; - pub static S_IWUSR : int = 128; - pub static S_IRUSR : int = 256; - pub static F_OK : int = 0; - pub static R_OK : int = 4; - pub static W_OK : int = 2; - pub static X_OK : int = 1; - pub static STDIN_FILENO : int = 0; - pub static STDOUT_FILENO : int = 1; - pub static STDERR_FILENO : int = 2; - pub static F_LOCK : int = 1; - pub static F_TEST : int = 3; - pub static F_TLOCK : int = 2; - pub static F_ULOCK : int = 0; - pub static SIGHUP : int = 1; - pub static SIGINT : int = 2; - pub static SIGQUIT : int = 3; - pub static SIGILL : int = 4; - pub static SIGABRT : int = 6; - pub static SIGFPE : int = 8; - pub static SIGKILL : int = 9; - pub static SIGSEGV : int = 11; - pub static SIGPIPE : int = 13; - pub static SIGALRM : int = 14; - pub static SIGTERM : int = 15; + pub static O_RDONLY : c_int = 0; + pub static O_WRONLY : c_int = 1; + pub static O_RDWR : c_int = 2; + pub static O_APPEND : c_int = 8; + pub static O_CREAT : c_int = 256; + pub static O_EXCL : c_int = 1024; + pub static O_TRUNC : c_int = 512; + pub static S_IFIFO : c_int = 4096; + pub static S_IFCHR : c_int = 8192; + pub static S_IFBLK : c_int = 24576; + pub static S_IFDIR : c_int = 16384; + pub static S_IFREG : c_int = 32768; + pub static S_IFMT : c_int = 61440; + pub static S_IEXEC : c_int = 64; + pub static S_IWRITE : c_int = 128; + pub static S_IREAD : c_int = 256; + pub static S_IRWXU : c_int = 448; + pub static S_IXUSR : c_int = 64; + pub static S_IWUSR : c_int = 128; + pub static S_IRUSR : c_int = 256; + pub static F_OK : c_int = 0; + pub static R_OK : c_int = 4; + pub static W_OK : c_int = 2; + pub static X_OK : c_int = 1; + pub static STDIN_FILENO : c_int = 0; + pub static STDOUT_FILENO : c_int = 1; + pub static STDERR_FILENO : c_int = 2; + pub static F_LOCK : c_int = 1; + pub static F_TEST : c_int = 3; + pub static F_TLOCK : c_int = 2; + pub static F_ULOCK : c_int = 0; + pub static SIGHUP : c_int = 1; + pub static SIGINT : c_int = 2; + pub static SIGQUIT : c_int = 3; + pub static SIGILL : c_int = 4; + pub static SIGABRT : c_int = 6; + pub static SIGFPE : c_int = 8; + pub static SIGKILL : c_int = 9; + pub static SIGSEGV : c_int = 11; + pub static SIGPIPE : c_int = 13; + pub static SIGALRM : c_int = 14; + pub static SIGTERM : c_int = 15; - pub static PROT_NONE : int = 0; - pub static PROT_READ : int = 1; - pub static PROT_WRITE : int = 2; - pub static PROT_EXEC : int = 4; + pub static PROT_NONE : c_int = 0; + pub static PROT_READ : c_int = 1; + pub static PROT_WRITE : c_int = 2; + pub static PROT_EXEC : c_int = 4; - pub static MAP_FILE : int = 0x0000; - pub static MAP_SHARED : int = 0x0001; - pub static MAP_PRIVATE : int = 0x0002; - pub static MAP_FIXED : int = 0x0010; - pub static MAP_ANON : int = 0x1000; + pub static MAP_FILE : c_int = 0x0000; + pub static MAP_SHARED : c_int = 0x0001; + pub static MAP_PRIVATE : c_int = 0x0002; + pub static MAP_FIXED : c_int = 0x0010; + pub static MAP_ANON : c_int = 0x1000; pub static MAP_FAILED : *c_void = -1 as *c_void; - pub static MCL_CURRENT : int = 0x0001; - pub static MCL_FUTURE : int = 0x0002; + pub static MCL_CURRENT : c_int = 0x0001; + pub static MCL_FUTURE : c_int = 0x0002; - pub static MS_ASYNC : int = 0x0001; - pub static MS_INVALIDATE : int = 0x0002; - pub static MS_SYNC : int = 0x0004; + pub static MS_ASYNC : c_int = 0x0001; + pub static MS_INVALIDATE : c_int = 0x0002; + pub static MS_SYNC : c_int = 0x0004; - pub static _SC_ARG_MAX : int = 0; - pub static _SC_CHILD_MAX : int = 1; - pub static _SC_CLK_TCK : int = 2; - pub static _SC_NGROUPS_MAX : int = 3; - pub static _SC_OPEN_MAX : int = 4; - pub static _SC_STREAM_MAX : int = 5; - pub static _SC_TZNAME_MAX : int = 6; - pub static _SC_JOB_CONTROL : int = 7; - pub static _SC_SAVED_IDS : int = 8; - pub static _SC_REALTIME_SIGNALS : int = 9; - pub static _SC_PRIORITY_SCHEDULING : int = 10; - pub static _SC_TIMERS : int = 11; - pub static _SC_ASYNCHRONOUS_IO : int = 12; - pub static _SC_PRIORITIZED_IO : int = 13; - pub static _SC_SYNCHRONIZED_IO : int = 14; - pub static _SC_FSYNC : int = 15; - pub static _SC_MAPPED_FILES : int = 16; - pub static _SC_MEMLOCK : int = 17; - pub static _SC_MEMLOCK_RANGE : int = 18; - pub static _SC_MEMORY_PROTECTION : int = 19; - pub static _SC_MESSAGE_PASSING : int = 20; - pub static _SC_SEMAPHORES : int = 21; - pub static _SC_SHARED_MEMORY_OBJECTS : int = 22; - pub static _SC_AIO_LISTIO_MAX : int = 23; - pub static _SC_AIO_MAX : int = 24; - pub static _SC_AIO_PRIO_DELTA_MAX : int = 25; - pub static _SC_DELAYTIMER_MAX : int = 26; - pub static _SC_MQ_OPEN_MAX : int = 27; - pub static _SC_VERSION : int = 29; - pub static _SC_PAGESIZE : int = 30; - pub static _SC_RTSIG_MAX : int = 31; - pub static _SC_SEM_NSEMS_MAX : int = 32; - pub static _SC_SEM_VALUE_MAX : int = 33; - pub static _SC_SIGQUEUE_MAX : int = 34; - pub static _SC_TIMER_MAX : int = 35; - pub static _SC_BC_BASE_MAX : int = 36; - pub static _SC_BC_DIM_MAX : int = 37; - pub static _SC_BC_SCALE_MAX : int = 38; - pub static _SC_BC_STRING_MAX : int = 39; - pub static _SC_COLL_WEIGHTS_MAX : int = 40; - pub static _SC_EXPR_NEST_MAX : int = 42; - pub static _SC_LINE_MAX : int = 43; - pub static _SC_RE_DUP_MAX : int = 44; - pub static _SC_2_VERSION : int = 46; - pub static _SC_2_C_BIND : int = 47; - pub static _SC_2_C_DEV : int = 48; - pub static _SC_2_FORT_DEV : int = 49; - pub static _SC_2_FORT_RUN : int = 50; - pub static _SC_2_SW_DEV : int = 51; - pub static _SC_2_LOCALEDEF : int = 52; - pub static _SC_2_CHAR_TERM : int = 95; - pub static _SC_2_C_VERSION : int = 96; - pub static _SC_2_UPE : int = 97; - pub static _SC_XBS5_ILP32_OFF32 : int = 125; - pub static _SC_XBS5_ILP32_OFFBIG : int = 126; - pub static _SC_XBS5_LPBIG_OFFBIG : int = 128; + pub static _SC_ARG_MAX : c_int = 0; + pub static _SC_CHILD_MAX : c_int = 1; + pub static _SC_CLK_TCK : c_int = 2; + pub static _SC_NGROUPS_MAX : c_int = 3; + pub static _SC_OPEN_MAX : c_int = 4; + pub static _SC_STREAM_MAX : c_int = 5; + pub static _SC_TZNAME_MAX : c_int = 6; + pub static _SC_JOB_CONTROL : c_int = 7; + pub static _SC_SAVED_IDS : c_int = 8; + pub static _SC_REALTIME_SIGNALS : c_int = 9; + pub static _SC_PRIORITY_SCHEDULING : c_int = 10; + pub static _SC_TIMERS : c_int = 11; + pub static _SC_ASYNCHRONOUS_IO : c_int = 12; + pub static _SC_PRIORITIZED_IO : c_int = 13; + pub static _SC_SYNCHRONIZED_IO : c_int = 14; + pub static _SC_FSYNC : c_int = 15; + pub static _SC_MAPPED_FILES : c_int = 16; + pub static _SC_MEMLOCK : c_int = 17; + pub static _SC_MEMLOCK_RANGE : c_int = 18; + pub static _SC_MEMORY_PROTECTION : c_int = 19; + pub static _SC_MESSAGE_PASSING : c_int = 20; + pub static _SC_SEMAPHORES : c_int = 21; + pub static _SC_SHARED_MEMORY_OBJECTS : c_int = 22; + pub static _SC_AIO_LISTIO_MAX : c_int = 23; + pub static _SC_AIO_MAX : c_int = 24; + pub static _SC_AIO_PRIO_DELTA_MAX : c_int = 25; + pub static _SC_DELAYTIMER_MAX : c_int = 26; + pub static _SC_MQ_OPEN_MAX : c_int = 27; + pub static _SC_VERSION : c_int = 29; + pub static _SC_PAGESIZE : c_int = 30; + pub static _SC_RTSIG_MAX : c_int = 31; + pub static _SC_SEM_NSEMS_MAX : c_int = 32; + pub static _SC_SEM_VALUE_MAX : c_int = 33; + pub static _SC_SIGQUEUE_MAX : c_int = 34; + pub static _SC_TIMER_MAX : c_int = 35; + pub static _SC_BC_BASE_MAX : c_int = 36; + pub static _SC_BC_DIM_MAX : c_int = 37; + pub static _SC_BC_SCALE_MAX : c_int = 38; + pub static _SC_BC_STRING_MAX : c_int = 39; + pub static _SC_COLL_WEIGHTS_MAX : c_int = 40; + pub static _SC_EXPR_NEST_MAX : c_int = 42; + pub static _SC_LINE_MAX : c_int = 43; + pub static _SC_RE_DUP_MAX : c_int = 44; + pub static _SC_2_VERSION : c_int = 46; + pub static _SC_2_C_BIND : c_int = 47; + pub static _SC_2_C_DEV : c_int = 48; + pub static _SC_2_FORT_DEV : c_int = 49; + pub static _SC_2_FORT_RUN : c_int = 50; + pub static _SC_2_SW_DEV : c_int = 51; + pub static _SC_2_LOCALEDEF : c_int = 52; + pub static _SC_2_CHAR_TERM : c_int = 95; + pub static _SC_2_C_VERSION : c_int = 96; + pub static _SC_2_UPE : c_int = 97; + pub static _SC_XBS5_ILP32_OFF32 : c_int = 125; + pub static _SC_XBS5_ILP32_OFFBIG : c_int = 126; + pub static _SC_XBS5_LPBIG_OFFBIG : c_int = 128; } pub mod posix01 { - pub static SIGTRAP : int = 5; + use libc::types::os::arch::c95::c_int; - pub static GLOB_ERR : int = 1 << 0; - pub static GLOB_MARK : int = 1 << 1; - pub static GLOB_NOSORT : int = 1 << 2; - pub static GLOB_DOOFFS : int = 1 << 3; - pub static GLOB_NOCHECK : int = 1 << 4; - pub static GLOB_APPEND : int = 1 << 5; - pub static GLOB_NOESCAPE : int = 1 << 6; + pub static SIGTRAP : c_int = 5; - pub static GLOB_NOSPACE : int = 1; - pub static GLOB_ABORTED : int = 2; - pub static GLOB_NOMATCH : int = 3; + pub static GLOB_ERR : c_int = 1 << 0; + pub static GLOB_MARK : c_int = 1 << 1; + pub static GLOB_NOSORT : c_int = 1 << 2; + pub static GLOB_DOOFFS : c_int = 1 << 3; + pub static GLOB_NOCHECK : c_int = 1 << 4; + pub static GLOB_APPEND : c_int = 1 << 5; + pub static GLOB_NOESCAPE : c_int = 1 << 6; - pub static POSIX_MADV_NORMAL : int = 0; - pub static POSIX_MADV_RANDOM : int = 1; - pub static POSIX_MADV_SEQUENTIAL : int = 2; - pub static POSIX_MADV_WILLNEED : int = 3; - pub static POSIX_MADV_DONTNEED : int = 4; + pub static GLOB_NOSPACE : c_int = 1; + pub static GLOB_ABORTED : c_int = 2; + pub static GLOB_NOMATCH : c_int = 3; - pub static _SC_MQ_PRIO_MAX : int = 28; - pub static _SC_IOV_MAX : int = 60; - pub static _SC_GETGR_R_SIZE_MAX : int = 69; - pub static _SC_GETPW_R_SIZE_MAX : int = 70; - pub static _SC_LOGIN_NAME_MAX : int = 71; - pub static _SC_TTY_NAME_MAX : int = 72; - pub static _SC_THREADS : int = 67; - pub static _SC_THREAD_SAFE_FUNCTIONS : int = 68; - pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 73; - pub static _SC_THREAD_KEYS_MAX : int = 74; - pub static _SC_THREAD_STACK_MIN : int = 75; - pub static _SC_THREAD_THREADS_MAX : int = 76; - pub static _SC_THREAD_ATTR_STACKADDR : int = 77; - pub static _SC_THREAD_ATTR_STACKSIZE : int = 78; - pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 79; - pub static _SC_THREAD_PRIO_INHERIT : int = 80; - pub static _SC_THREAD_PRIO_PROTECT : int = 81; - pub static _SC_THREAD_PROCESS_SHARED : int = 82; - pub static _SC_ATEXIT_MAX : int = 87; - pub static _SC_XOPEN_VERSION : int = 89; - pub static _SC_XOPEN_XCU_VERSION : int = 90; - pub static _SC_XOPEN_UNIX : int = 91; - pub static _SC_XOPEN_CRYPT : int = 92; - pub static _SC_XOPEN_ENH_I18N : int = 93; - pub static _SC_XOPEN_SHM : int = 94; - pub static _SC_XOPEN_LEGACY : int = 129; - pub static _SC_XOPEN_REALTIME : int = 130; - pub static _SC_XOPEN_REALTIME_THREADS : int = 131; + pub static POSIX_MADV_NORMAL : c_int = 0; + pub static POSIX_MADV_RANDOM : c_int = 1; + pub static POSIX_MADV_SEQUENTIAL : c_int = 2; + pub static POSIX_MADV_WILLNEED : c_int = 3; + pub static POSIX_MADV_DONTNEED : c_int = 4; + + pub static _SC_MQ_PRIO_MAX : c_int = 28; + pub static _SC_IOV_MAX : c_int = 60; + pub static _SC_GETGR_R_SIZE_MAX : c_int = 69; + pub static _SC_GETPW_R_SIZE_MAX : c_int = 70; + pub static _SC_LOGIN_NAME_MAX : c_int = 71; + pub static _SC_TTY_NAME_MAX : c_int = 72; + pub static _SC_THREADS : c_int = 67; + pub static _SC_THREAD_SAFE_FUNCTIONS : c_int = 68; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : c_int = 73; + pub static _SC_THREAD_KEYS_MAX : c_int = 74; + pub static _SC_THREAD_STACK_MIN : c_int = 75; + pub static _SC_THREAD_THREADS_MAX : c_int = 76; + pub static _SC_THREAD_ATTR_STACKADDR : c_int = 77; + pub static _SC_THREAD_ATTR_STACKSIZE : c_int = 78; + pub static _SC_THREAD_PRIORITY_SCHEDULING : c_int = 79; + pub static _SC_THREAD_PRIO_INHERIT : c_int = 80; + pub static _SC_THREAD_PRIO_PROTECT : c_int = 81; + pub static _SC_THREAD_PROCESS_SHARED : c_int = 82; + pub static _SC_ATEXIT_MAX : c_int = 87; + pub static _SC_XOPEN_VERSION : c_int = 89; + pub static _SC_XOPEN_XCU_VERSION : c_int = 90; + pub static _SC_XOPEN_UNIX : c_int = 91; + pub static _SC_XOPEN_CRYPT : c_int = 92; + pub static _SC_XOPEN_ENH_I18N : c_int = 93; + pub static _SC_XOPEN_SHM : c_int = 94; + pub static _SC_XOPEN_LEGACY : c_int = 129; + pub static _SC_XOPEN_REALTIME : c_int = 130; + pub static _SC_XOPEN_REALTIME_THREADS : c_int = 131; } pub mod posix08 { } pub mod bsd44 { - pub static MADV_NORMAL : int = 0; - pub static MADV_RANDOM : int = 1; - pub static MADV_SEQUENTIAL : int = 2; - pub static MADV_WILLNEED : int = 3; - pub static MADV_DONTNEED : int = 4; - pub static MADV_REMOVE : int = 9; - pub static MADV_DONTFORK : int = 10; - pub static MADV_DOFORK : int = 11; - pub static MADV_MERGEABLE : int = 12; - pub static MADV_UNMERGEABLE : int = 13; - pub static MADV_HWPOISON : int = 100; + use libc::types::os::arch::c95::c_int; + + pub static MADV_NORMAL : c_int = 0; + pub static MADV_RANDOM : c_int = 1; + pub static MADV_SEQUENTIAL : c_int = 2; + pub static MADV_WILLNEED : c_int = 3; + pub static MADV_DONTNEED : c_int = 4; + pub static MADV_REMOVE : c_int = 9; + pub static MADV_DONTFORK : c_int = 10; + pub static MADV_DOFORK : c_int = 11; + pub static MADV_MERGEABLE : c_int = 12; + pub static MADV_UNMERGEABLE : c_int = 13; + pub static MADV_HWPOISON : c_int = 100; } #[cfg(target_arch = "x86")] #[cfg(target_arch = "x86_64")] #[cfg(target_arch = "arm")] pub mod extra { - pub static O_RSYNC : int = 1052672; - pub static O_DSYNC : int = 4096; - pub static O_SYNC : int = 1052672; + use libc::types::os::arch::c95::c_int; - pub static PROT_GROWSDOWN : int = 0x010000000; - pub static PROT_GROWSUP : int = 0x020000000; + pub static O_RSYNC : c_int = 1052672; + pub static O_DSYNC : c_int = 4096; + pub static O_SYNC : c_int = 1052672; - pub static MAP_TYPE : int = 0x000f; - pub static MAP_ANONONYMOUS : int = 0x1000; - pub static MAP_32BIT : int = 0x0040; - pub static MAP_GROWSDOWN : int = 0x0100; - pub static MAP_DENYWRITE : int = 0x0800; - pub static MAP_EXECUTABLE : int = 0x01000; - pub static MAP_LOCKED : int = 0x02000; - pub static MAP_NONRESERVE : int = 0x04000; - pub static MAP_POPULATE : int = 0x08000; - pub static MAP_NONBLOCK : int = 0x010000; - pub static MAP_STACK : int = 0x020000; + pub static PROT_GROWSDOWN : c_int = 0x010000000; + pub static PROT_GROWSUP : c_int = 0x020000000; + + pub static MAP_TYPE : c_int = 0x000f; + pub static MAP_ANONONYMOUS : c_int = 0x1000; + pub static MAP_32BIT : c_int = 0x0040; + pub static MAP_GROWSDOWN : c_int = 0x0100; + pub static MAP_DENYWRITE : c_int = 0x0800; + pub static MAP_EXECUTABLE : c_int = 0x01000; + pub static MAP_LOCKED : c_int = 0x02000; + pub static MAP_NONRESERVE : c_int = 0x04000; + pub static MAP_POPULATE : c_int = 0x08000; + pub static MAP_NONBLOCK : c_int = 0x010000; + pub static MAP_STACK : c_int = 0x020000; } #[cfg(target_arch = "mips")] pub mod extra { - pub static O_RSYNC : int = 16400; - pub static O_DSYNC : int = 16; - pub static O_SYNC : int = 16400; + use libc::types::os::arch::c95::c_int; - pub static PROT_GROWSDOWN : int = 0x010000000; - pub static PROT_GROWSUP : int = 0x020000000; + pub static O_RSYNC : c_int = 16400; + pub static O_DSYNC : c_int = 16; + pub static O_SYNC : c_int = 16400; - pub static MAP_TYPE : int = 0x000f; - pub static MAP_ANONONYMOUS : int = 0x1000; - pub static MAP_32BIT : int = 0x0040; - pub static MAP_GROWSDOWN : int = 0x0100; - pub static MAP_DENYWRITE : int = 0x0800; - pub static MAP_EXECUTABLE : int = 0x01000; - pub static MAP_LOCKED : int = 0x02000; - pub static MAP_NONRESERVE : int = 0x04000; - pub static MAP_POPULATE : int = 0x08000; - pub static MAP_NONBLOCK : int = 0x010000; - pub static MAP_STACK : int = 0x020000; + pub static PROT_GROWSDOWN : c_int = 0x010000000; + pub static PROT_GROWSUP : c_int = 0x020000000; + + pub static MAP_TYPE : c_int = 0x000f; + pub static MAP_ANONONYMOUS : c_int = 0x1000; + pub static MAP_32BIT : c_int = 0x0040; + pub static MAP_GROWSDOWN : c_int = 0x0100; + pub static MAP_DENYWRITE : c_int = 0x0800; + pub static MAP_EXECUTABLE : c_int = 0x01000; + pub static MAP_LOCKED : c_int = 0x02000; + pub static MAP_NONRESERVE : c_int = 0x04000; + pub static MAP_POPULATE : c_int = 0x08000; + pub static MAP_NONBLOCK : c_int = 0x010000; + pub static MAP_STACK : c_int = 0x020000; } } #[cfg(target_os = "freebsd")] pub mod os { pub mod c95 { - pub static EXIT_FAILURE : int = 1; - pub static EXIT_SUCCESS : int = 0; - pub static RAND_MAX : int = 2147483647; - pub static EOF : int = -1; - pub static SEEK_SET : int = 0; - pub static SEEK_CUR : int = 1; - pub static SEEK_END : int = 2; - pub static _IOFBF : int = 0; - pub static _IONBF : int = 2; - pub static _IOLBF : int = 1; - pub static BUFSIZ : uint = 1024_u; - pub static FOPEN_MAX : uint = 20_u; - pub static FILENAME_MAX : uint = 1024_u; - pub static L_tmpnam : uint = 1024_u; - pub static TMP_MAX : uint = 308915776_u; + use libc::types::os::arch::c95::{c_int, c_uint}; + + pub static EXIT_FAILURE : c_int = 1; + pub static EXIT_SUCCESS : c_int = 0; + pub static RAND_MAX : c_int = 2147483647; + pub static EOF : c_int = -1; + pub static SEEK_SET : c_int = 0; + pub static SEEK_CUR : c_int = 1; + pub static SEEK_END : c_int = 2; + pub static _IOFBF : c_int = 0; + pub static _IONBF : c_int = 2; + pub static _IOLBF : c_int = 1; + pub static BUFSIZ : c_uint = 1024_u32; + pub static FOPEN_MAX : c_uint = 20_u32; + pub static FILENAME_MAX : c_uint = 1024_u32; + pub static L_tmpnam : c_uint = 1024_u32; + pub static TMP_MAX : c_uint = 308915776_u32; } pub mod c99 { } pub mod posix88 { use libc::types::common::c95::c_void; + use libc::types::os::arch::c95::c_int; - pub static O_RDONLY : int = 0; - pub static O_WRONLY : int = 1; - pub static O_RDWR : int = 2; - pub static O_APPEND : int = 8; - pub static O_CREAT : int = 512; - pub static O_EXCL : int = 2048; - pub static O_TRUNC : int = 1024; - pub static S_IFIFO : int = 4096; - pub static S_IFCHR : int = 8192; - pub static S_IFBLK : int = 24576; - pub static S_IFDIR : int = 16384; - pub static S_IFREG : int = 32768; - pub static S_IFMT : int = 61440; - pub static S_IEXEC : int = 64; - pub static S_IWRITE : int = 128; - pub static S_IREAD : int = 256; - pub static S_IRWXU : int = 448; - pub static S_IXUSR : int = 64; - pub static S_IWUSR : int = 128; - pub static S_IRUSR : int = 256; - pub static F_OK : int = 0; - pub static R_OK : int = 4; - pub static W_OK : int = 2; - pub static X_OK : int = 1; - pub static STDIN_FILENO : int = 0; - pub static STDOUT_FILENO : int = 1; - pub static STDERR_FILENO : int = 2; - pub static F_LOCK : int = 1; - pub static F_TEST : int = 3; - pub static F_TLOCK : int = 2; - pub static F_ULOCK : int = 0; - pub static SIGHUP : int = 1; - pub static SIGINT : int = 2; - pub static SIGQUIT : int = 3; - pub static SIGILL : int = 4; - pub static SIGABRT : int = 6; - pub static SIGFPE : int = 8; - pub static SIGKILL : int = 9; - pub static SIGSEGV : int = 11; - pub static SIGPIPE : int = 13; - pub static SIGALRM : int = 14; - pub static SIGTERM : int = 15; + pub static O_RDONLY : c_int = 0; + pub static O_WRONLY : c_int = 1; + pub static O_RDWR : c_int = 2; + pub static O_APPEND : c_int = 8; + pub static O_CREAT : c_int = 512; + pub static O_EXCL : c_int = 2048; + pub static O_TRUNC : c_int = 1024; + pub static S_IFIFO : c_int = 4096; + pub static S_IFCHR : c_int = 8192; + pub static S_IFBLK : c_int = 24576; + pub static S_IFDIR : c_int = 16384; + pub static S_IFREG : c_int = 32768; + pub static S_IFMT : c_int = 61440; + pub static S_IEXEC : c_int = 64; + pub static S_IWRITE : c_int = 128; + pub static S_IREAD : c_int = 256; + pub static S_IRWXU : c_int = 448; + pub static S_IXUSR : c_int = 64; + pub static S_IWUSR : c_int = 128; + pub static S_IRUSR : c_int = 256; + pub static F_OK : c_int = 0; + pub static R_OK : c_int = 4; + pub static W_OK : c_int = 2; + pub static X_OK : c_int = 1; + pub static STDIN_FILENO : c_int = 0; + pub static STDOUT_FILENO : c_int = 1; + pub static STDERR_FILENO : c_int = 2; + pub static F_LOCK : c_int = 1; + pub static F_TEST : c_int = 3; + pub static F_TLOCK : c_int = 2; + pub static F_ULOCK : c_int = 0; + pub static SIGHUP : c_int = 1; + pub static SIGINT : c_int = 2; + pub static SIGQUIT : c_int = 3; + pub static SIGILL : c_int = 4; + pub static SIGABRT : c_int = 6; + pub static SIGFPE : c_int = 8; + pub static SIGKILL : c_int = 9; + pub static SIGSEGV : c_int = 11; + pub static SIGPIPE : c_int = 13; + pub static SIGALRM : c_int = 14; + pub static SIGTERM : c_int = 15; - pub static PROT_NONE : int = 0; - pub static PROT_READ : int = 1; - pub static PROT_WRITE : int = 2; - pub static PROT_EXEC : int = 4; + pub static PROT_NONE : c_int = 0; + pub static PROT_READ : c_int = 1; + pub static PROT_WRITE : c_int = 2; + pub static PROT_EXEC : c_int = 4; - pub static MAP_FILE : int = 0x0000; - pub static MAP_SHARED : int = 0x0001; - pub static MAP_PRIVATE : int = 0x0002; - pub static MAP_FIXED : int = 0x0010; - pub static MAP_ANON : int = 0x1000; + pub static MAP_FILE : c_int = 0x0000; + pub static MAP_SHARED : c_int = 0x0001; + pub static MAP_PRIVATE : c_int = 0x0002; + pub static MAP_FIXED : c_int = 0x0010; + pub static MAP_ANON : c_int = 0x1000; pub static MAP_FAILED : *c_void = -1 as *c_void; - pub static MCL_CURRENT : int = 0x0001; - pub static MCL_FUTURE : int = 0x0002; + pub static MCL_CURRENT : c_int = 0x0001; + pub static MCL_FUTURE : c_int = 0x0002; - pub static MS_SYNC : int = 0x0000; - pub static MS_ASYNC : int = 0x0001; - pub static MS_INVALIDATE : int = 0x0002; + pub static MS_SYNC : c_int = 0x0000; + pub static MS_ASYNC : c_int = 0x0001; + pub static MS_INVALIDATE : c_int = 0x0002; - pub static _SC_ARG_MAX : int = 1; - pub static _SC_CHILD_MAX : int = 2; - pub static _SC_CLK_TCK : int = 3; - pub static _SC_NGROUPS_MAX : int = 4; - pub static _SC_OPEN_MAX : int = 5; - pub static _SC_JOB_CONTROL : int = 6; - pub static _SC_SAVED_IDS : int = 7; - pub static _SC_VERSION : int = 8; - pub static _SC_BC_BASE_MAX : int = 9; - pub static _SC_BC_DIM_MAX : int = 10; - pub static _SC_BC_SCALE_MAX : int = 11; - pub static _SC_BC_STRING_MAX : int = 12; - pub static _SC_COLL_WEIGHTS_MAX : int = 13; - pub static _SC_EXPR_NEST_MAX : int = 14; - pub static _SC_LINE_MAX : int = 15; - pub static _SC_RE_DUP_MAX : int = 16; - pub static _SC_2_VERSION : int = 17; - pub static _SC_2_C_BIND : int = 18; - pub static _SC_2_C_DEV : int = 19; - pub static _SC_2_CHAR_TERM : int = 20; - pub static _SC_2_FORT_DEV : int = 21; - pub static _SC_2_FORT_RUN : int = 22; - pub static _SC_2_LOCALEDEF : int = 23; - pub static _SC_2_SW_DEV : int = 24; - pub static _SC_2_UPE : int = 25; - pub static _SC_STREAM_MAX : int = 26; - pub static _SC_TZNAME_MAX : int = 27; - pub static _SC_ASYNCHRONOUS_IO : int = 28; - pub static _SC_MAPPED_FILES : int = 29; - pub static _SC_MEMLOCK : int = 30; - pub static _SC_MEMLOCK_RANGE : int = 31; - pub static _SC_MEMORY_PROTECTION : int = 32; - pub static _SC_MESSAGE_PASSING : int = 33; - pub static _SC_PRIORITIZED_IO : int = 34; - pub static _SC_PRIORITY_SCHEDULING : int = 35; - pub static _SC_REALTIME_SIGNALS : int = 36; - pub static _SC_SEMAPHORES : int = 37; - pub static _SC_FSYNC : int = 38; - pub static _SC_SHARED_MEMORY_OBJECTS : int = 39; - pub static _SC_SYNCHRONIZED_IO : int = 40; - pub static _SC_TIMERS : int = 41; - pub static _SC_AIO_LISTIO_MAX : int = 42; - pub static _SC_AIO_MAX : int = 43; - pub static _SC_AIO_PRIO_DELTA_MAX : int = 44; - pub static _SC_DELAYTIMER_MAX : int = 45; - pub static _SC_MQ_OPEN_MAX : int = 46; - pub static _SC_PAGESIZE : int = 47; - pub static _SC_RTSIG_MAX : int = 48; - pub static _SC_SEM_NSEMS_MAX : int = 49; - pub static _SC_SEM_VALUE_MAX : int = 50; - pub static _SC_SIGQUEUE_MAX : int = 51; - pub static _SC_TIMER_MAX : int = 52; + pub static _SC_ARG_MAX : c_int = 1; + pub static _SC_CHILD_MAX : c_int = 2; + pub static _SC_CLK_TCK : c_int = 3; + pub static _SC_NGROUPS_MAX : c_int = 4; + pub static _SC_OPEN_MAX : c_int = 5; + pub static _SC_JOB_CONTROL : c_int = 6; + pub static _SC_SAVED_IDS : c_int = 7; + pub static _SC_VERSION : c_int = 8; + pub static _SC_BC_BASE_MAX : c_int = 9; + pub static _SC_BC_DIM_MAX : c_int = 10; + pub static _SC_BC_SCALE_MAX : c_int = 11; + pub static _SC_BC_STRING_MAX : c_int = 12; + pub static _SC_COLL_WEIGHTS_MAX : c_int = 13; + pub static _SC_EXPR_NEST_MAX : c_int = 14; + pub static _SC_LINE_MAX : c_int = 15; + pub static _SC_RE_DUP_MAX : c_int = 16; + pub static _SC_2_VERSION : c_int = 17; + pub static _SC_2_C_BIND : c_int = 18; + pub static _SC_2_C_DEV : c_int = 19; + pub static _SC_2_CHAR_TERM : c_int = 20; + pub static _SC_2_FORT_DEV : c_int = 21; + pub static _SC_2_FORT_RUN : c_int = 22; + pub static _SC_2_LOCALEDEF : c_int = 23; + pub static _SC_2_SW_DEV : c_int = 24; + pub static _SC_2_UPE : c_int = 25; + pub static _SC_STREAM_MAX : c_int = 26; + pub static _SC_TZNAME_MAX : c_int = 27; + pub static _SC_ASYNCHRONOUS_IO : c_int = 28; + pub static _SC_MAPPED_FILES : c_int = 29; + pub static _SC_MEMLOCK : c_int = 30; + pub static _SC_MEMLOCK_RANGE : c_int = 31; + pub static _SC_MEMORY_PROTECTION : c_int = 32; + pub static _SC_MESSAGE_PASSING : c_int = 33; + pub static _SC_PRIORITIZED_IO : c_int = 34; + pub static _SC_PRIORITY_SCHEDULING : c_int = 35; + pub static _SC_REALTIME_SIGNALS : c_int = 36; + pub static _SC_SEMAPHORES : c_int = 37; + pub static _SC_FSYNC : c_int = 38; + pub static _SC_SHARED_MEMORY_OBJECTS : c_int = 39; + pub static _SC_SYNCHRONIZED_IO : c_int = 40; + pub static _SC_TIMERS : c_int = 41; + pub static _SC_AIO_LISTIO_MAX : c_int = 42; + pub static _SC_AIO_MAX : c_int = 43; + pub static _SC_AIO_PRIO_DELTA_MAX : c_int = 44; + pub static _SC_DELAYTIMER_MAX : c_int = 45; + pub static _SC_MQ_OPEN_MAX : c_int = 46; + pub static _SC_PAGESIZE : c_int = 47; + pub static _SC_RTSIG_MAX : c_int = 48; + pub static _SC_SEM_NSEMS_MAX : c_int = 49; + pub static _SC_SEM_VALUE_MAX : c_int = 50; + pub static _SC_SIGQUEUE_MAX : c_int = 51; + pub static _SC_TIMER_MAX : c_int = 52; } pub mod posix01 { - pub static SIGTRAP : int = 5; + use libc::types::os::arch::c95::c_int; - pub static GLOB_APPEND : int = 0x0001; - pub static GLOB_DOOFFS : int = 0x0002; - pub static GLOB_ERR : int = 0x0004; - pub static GLOB_MARK : int = 0x0008; - pub static GLOB_NOCHECK : int = 0x0010; - pub static GLOB_NOSORT : int = 0x0020; - pub static GLOB_NOESCAPE : int = 0x2000; + pub static SIGTRAP : c_int = 5; - pub static GLOB_NOSPACE : int = -1; - pub static GLOB_ABORTED : int = -2; - pub static GLOB_NOMATCH : int = -3; + pub static GLOB_APPEND : c_int = 0x0001; + pub static GLOB_DOOFFS : c_int = 0x0002; + pub static GLOB_ERR : c_int = 0x0004; + pub static GLOB_MARK : c_int = 0x0008; + pub static GLOB_NOCHECK : c_int = 0x0010; + pub static GLOB_NOSORT : c_int = 0x0020; + pub static GLOB_NOESCAPE : c_int = 0x2000; - pub static POSIX_MADV_NORMAL : int = 0; - pub static POSIX_MADV_RANDOM : int = 1; - pub static POSIX_MADV_SEQUENTIAL : int = 2; - pub static POSIX_MADV_WILLNEED : int = 3; - pub static POSIX_MADV_DONTNEED : int = 4; + pub static GLOB_NOSPACE : c_int = -1; + pub static GLOB_ABORTED : c_int = -2; + pub static GLOB_NOMATCH : c_int = -3; - pub static _SC_IOV_MAX : int = 56; - pub static _SC_GETGR_R_SIZE_MAX : int = 70; - pub static _SC_GETPW_R_SIZE_MAX : int = 71; - pub static _SC_LOGIN_NAME_MAX : int = 73; - pub static _SC_MQ_PRIO_MAX : int = 75; - pub static _SC_THREAD_ATTR_STACKADDR : int = 82; - pub static _SC_THREAD_ATTR_STACKSIZE : int = 83; - pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 85; - pub static _SC_THREAD_KEYS_MAX : int = 86; - pub static _SC_THREAD_PRIO_INHERIT : int = 87; - pub static _SC_THREAD_PRIO_PROTECT : int = 88; - pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 89; - pub static _SC_THREAD_PROCESS_SHARED : int = 90; - pub static _SC_THREAD_SAFE_FUNCTIONS : int = 91; - pub static _SC_THREAD_STACK_MIN : int = 93; - pub static _SC_THREAD_THREADS_MAX : int = 94; - pub static _SC_THREADS : int = 96; - pub static _SC_TTY_NAME_MAX : int = 101; - pub static _SC_ATEXIT_MAX : int = 107; - pub static _SC_XOPEN_CRYPT : int = 108; - pub static _SC_XOPEN_ENH_I18N : int = 109; - pub static _SC_XOPEN_LEGACY : int = 110; - pub static _SC_XOPEN_REALTIME : int = 111; - pub static _SC_XOPEN_REALTIME_THREADS : int = 112; - pub static _SC_XOPEN_SHM : int = 113; - pub static _SC_XOPEN_UNIX : int = 115; - pub static _SC_XOPEN_VERSION : int = 116; - pub static _SC_XOPEN_XCU_VERSION : int = 117; + pub static POSIX_MADV_NORMAL : c_int = 0; + pub static POSIX_MADV_RANDOM : c_int = 1; + pub static POSIX_MADV_SEQUENTIAL : c_int = 2; + pub static POSIX_MADV_WILLNEED : c_int = 3; + pub static POSIX_MADV_DONTNEED : c_int = 4; + + pub static _SC_IOV_MAX : c_int = 56; + pub static _SC_GETGR_R_SIZE_MAX : c_int = 70; + pub static _SC_GETPW_R_SIZE_MAX : c_int = 71; + pub static _SC_LOGIN_NAME_MAX : c_int = 73; + pub static _SC_MQ_PRIO_MAX : c_int = 75; + pub static _SC_THREAD_ATTR_STACKADDR : c_int = 82; + pub static _SC_THREAD_ATTR_STACKSIZE : c_int = 83; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : c_int = 85; + pub static _SC_THREAD_KEYS_MAX : c_int = 86; + pub static _SC_THREAD_PRIO_INHERIT : c_int = 87; + pub static _SC_THREAD_PRIO_PROTECT : c_int = 88; + pub static _SC_THREAD_PRIORITY_SCHEDULING : c_int = 89; + pub static _SC_THREAD_PROCESS_SHARED : c_int = 90; + pub static _SC_THREAD_SAFE_FUNCTIONS : c_int = 91; + pub static _SC_THREAD_STACK_MIN : c_int = 93; + pub static _SC_THREAD_THREADS_MAX : c_int = 94; + pub static _SC_THREADS : c_int = 96; + pub static _SC_TTY_NAME_MAX : c_int = 101; + pub static _SC_ATEXIT_MAX : c_int = 107; + pub static _SC_XOPEN_CRYPT : c_int = 108; + pub static _SC_XOPEN_ENH_I18N : c_int = 109; + pub static _SC_XOPEN_LEGACY : c_int = 110; + pub static _SC_XOPEN_REALTIME : c_int = 111; + pub static _SC_XOPEN_REALTIME_THREADS : c_int = 112; + pub static _SC_XOPEN_SHM : c_int = 113; + pub static _SC_XOPEN_UNIX : c_int = 115; + pub static _SC_XOPEN_VERSION : c_int = 116; + pub static _SC_XOPEN_XCU_VERSION : c_int = 117; } pub mod posix08 { } pub mod bsd44 { - pub static MADV_NORMAL : int = 0; - pub static MADV_RANDOM : int = 1; - pub static MADV_SEQUENTIAL : int = 2; - pub static MADV_WILLNEED : int = 3; - pub static MADV_DONTNEED : int = 4; - pub static MADV_FREE : int = 5; - pub static MADV_NOSYNC : int = 6; - pub static MADV_AUTOSYNC : int = 7; - pub static MADV_NOCORE : int = 8; - pub static MADV_CORE : int = 9; - pub static MADV_PROTECT : int = 10; + use libc::types::os::arch::c95::c_int; - pub static MINCORE_INCORE : int = 0x1; - pub static MINCORE_REFERENCED : int = 0x2; - pub static MINCORE_MODIFIED : int = 0x4; - pub static MINCORE_REFERENCED_OTHER : int = 0x8; - pub static MINCORE_MODIFIED_OTHER : int = 0x10; - pub static MINCORE_SUPER : int = 0x20; + pub static MADV_NORMAL : c_int = 0; + pub static MADV_RANDOM : c_int = 1; + pub static MADV_SEQUENTIAL : c_int = 2; + pub static MADV_WILLNEED : c_int = 3; + pub static MADV_DONTNEED : c_int = 4; + pub static MADV_FREE : c_int = 5; + pub static MADV_NOSYNC : c_int = 6; + pub static MADV_AUTOSYNC : c_int = 7; + pub static MADV_NOCORE : c_int = 8; + pub static MADV_CORE : c_int = 9; + pub static MADV_PROTECT : c_int = 10; + + pub static MINCORE_INCORE : c_int = 0x1; + pub static MINCORE_REFERENCED : c_int = 0x2; + pub static MINCORE_MODIFIED : c_int = 0x4; + pub static MINCORE_REFERENCED_OTHER : c_int = 0x8; + pub static MINCORE_MODIFIED_OTHER : c_int = 0x10; + pub static MINCORE_SUPER : c_int = 0x20; } pub mod extra { - pub static O_SYNC : int = 128; - pub static CTL_KERN: int = 1; - pub static KERN_PROC: int = 14; - pub static KERN_PROC_PATHNAME: int = 12; + use libc::types::os::arch::c95::c_int; - pub static MAP_COPY : int = 0x0002; - pub static MAP_RENAME : int = 0x0020; - pub static MAP_NORESERVE : int = 0x0040; - pub static MAP_HASSEMAPHORE : int = 0x0200; - pub static MAP_STACK : int = 0x0400; - pub static MAP_NOSYNC : int = 0x0800; - pub static MAP_NOCORE : int = 0x020000; + pub static O_SYNC : c_int = 128; + pub static CTL_KERN: c_int = 1; + pub static KERN_PROC: c_int = 14; + pub static KERN_PROC_PATHNAME: c_int = 12; + + pub static MAP_COPY : c_int = 0x0002; + pub static MAP_RENAME : c_int = 0x0020; + pub static MAP_NORESERVE : c_int = 0x0040; + pub static MAP_HASSEMAPHORE : c_int = 0x0200; + pub static MAP_STACK : c_int = 0x0400; + pub static MAP_NOSYNC : c_int = 0x0800; + pub static MAP_NOCORE : c_int = 0x020000; } } #[cfg(target_os = "macos")] pub mod os { pub mod c95 { - pub static EXIT_FAILURE : int = 1; - pub static EXIT_SUCCESS : int = 0; - pub static RAND_MAX : int = 2147483647; - pub static EOF : int = -1; - pub static SEEK_SET : int = 0; - pub static SEEK_CUR : int = 1; - pub static SEEK_END : int = 2; - pub static _IOFBF : int = 0; - pub static _IONBF : int = 2; - pub static _IOLBF : int = 1; - pub static BUFSIZ : uint = 1024_u; - pub static FOPEN_MAX : uint = 20_u; - pub static FILENAME_MAX : uint = 1024_u; - pub static L_tmpnam : uint = 1024_u; - pub static TMP_MAX : uint = 308915776_u; + use libc::types::os::arch::c95::{c_int, c_uint}; + + pub static EXIT_FAILURE : c_int = 1; + pub static EXIT_SUCCESS : c_int = 0; + pub static RAND_MAX : c_int = 2147483647; + pub static EOF : c_int = -1; + pub static SEEK_SET : c_int = 0; + pub static SEEK_CUR : c_int = 1; + pub static SEEK_END : c_int = 2; + pub static _IOFBF : c_int = 0; + pub static _IONBF : c_int = 2; + pub static _IOLBF : c_int = 1; + pub static BUFSIZ : c_uint = 1024_u32; + pub static FOPEN_MAX : c_uint = 20_u32; + pub static FILENAME_MAX : c_uint = 1024_u32; + pub static L_tmpnam : c_uint = 1024_u32; + pub static TMP_MAX : c_uint = 308915776_u32; } pub mod c99 { } pub mod posix88 { use libc::types::common::c95::c_void; + use libc::types::os::arch::c95::c_int; - pub static O_RDONLY : int = 0; - pub static O_WRONLY : int = 1; - pub static O_RDWR : int = 2; - pub static O_APPEND : int = 8; - pub static O_CREAT : int = 512; - pub static O_EXCL : int = 2048; - pub static O_TRUNC : int = 1024; - pub static S_IFIFO : int = 4096; - pub static S_IFCHR : int = 8192; - pub static S_IFBLK : int = 24576; - pub static S_IFDIR : int = 16384; - pub static S_IFREG : int = 32768; - pub static S_IFMT : int = 61440; - pub static S_IEXEC : int = 64; - pub static S_IWRITE : int = 128; - pub static S_IREAD : int = 256; - pub static S_IRWXU : int = 448; - pub static S_IXUSR : int = 64; - pub static S_IWUSR : int = 128; - pub static S_IRUSR : int = 256; - pub static F_OK : int = 0; - pub static R_OK : int = 4; - pub static W_OK : int = 2; - pub static X_OK : int = 1; - pub static STDIN_FILENO : int = 0; - pub static STDOUT_FILENO : int = 1; - pub static STDERR_FILENO : int = 2; - pub static F_LOCK : int = 1; - pub static F_TEST : int = 3; - pub static F_TLOCK : int = 2; - pub static F_ULOCK : int = 0; - pub static SIGHUP : int = 1; - pub static SIGINT : int = 2; - pub static SIGQUIT : int = 3; - pub static SIGILL : int = 4; - pub static SIGABRT : int = 6; - pub static SIGFPE : int = 8; - pub static SIGKILL : int = 9; - pub static SIGSEGV : int = 11; - pub static SIGPIPE : int = 13; - pub static SIGALRM : int = 14; - pub static SIGTERM : int = 15; + pub static O_RDONLY : c_int = 0; + pub static O_WRONLY : c_int = 1; + pub static O_RDWR : c_int = 2; + pub static O_APPEND : c_int = 8; + pub static O_CREAT : c_int = 512; + pub static O_EXCL : c_int = 2048; + pub static O_TRUNC : c_int = 1024; + pub static S_IFIFO : c_int = 4096; + pub static S_IFCHR : c_int = 8192; + pub static S_IFBLK : c_int = 24576; + pub static S_IFDIR : c_int = 16384; + pub static S_IFREG : c_int = 32768; + pub static S_IFMT : c_int = 61440; + pub static S_IEXEC : c_int = 64; + pub static S_IWRITE : c_int = 128; + pub static S_IREAD : c_int = 256; + pub static S_IRWXU : c_int = 448; + pub static S_IXUSR : c_int = 64; + pub static S_IWUSR : c_int = 128; + pub static S_IRUSR : c_int = 256; + pub static F_OK : c_int = 0; + pub static R_OK : c_int = 4; + pub static W_OK : c_int = 2; + pub static X_OK : c_int = 1; + pub static STDIN_FILENO : c_int = 0; + pub static STDOUT_FILENO : c_int = 1; + pub static STDERR_FILENO : c_int = 2; + pub static F_LOCK : c_int = 1; + pub static F_TEST : c_int = 3; + pub static F_TLOCK : c_int = 2; + pub static F_ULOCK : c_int = 0; + pub static SIGHUP : c_int = 1; + pub static SIGINT : c_int = 2; + pub static SIGQUIT : c_int = 3; + pub static SIGILL : c_int = 4; + pub static SIGABRT : c_int = 6; + pub static SIGFPE : c_int = 8; + pub static SIGKILL : c_int = 9; + pub static SIGSEGV : c_int = 11; + pub static SIGPIPE : c_int = 13; + pub static SIGALRM : c_int = 14; + pub static SIGTERM : c_int = 15; - pub static PROT_NONE : int = 0; - pub static PROT_READ : int = 1; - pub static PROT_WRITE : int = 2; - pub static PROT_EXEC : int = 4; + pub static PROT_NONE : c_int = 0; + pub static PROT_READ : c_int = 1; + pub static PROT_WRITE : c_int = 2; + pub static PROT_EXEC : c_int = 4; - pub static MAP_FILE : int = 0x0000; - pub static MAP_SHARED : int = 0x0001; - pub static MAP_PRIVATE : int = 0x0002; - pub static MAP_FIXED : int = 0x0010; - pub static MAP_ANON : int = 0x1000; + pub static MAP_FILE : c_int = 0x0000; + pub static MAP_SHARED : c_int = 0x0001; + pub static MAP_PRIVATE : c_int = 0x0002; + pub static MAP_FIXED : c_int = 0x0010; + pub static MAP_ANON : c_int = 0x1000; pub static MAP_FAILED : *c_void = -1 as *c_void; - pub static MCL_CURRENT : int = 0x0001; - pub static MCL_FUTURE : int = 0x0002; + pub static MCL_CURRENT : c_int = 0x0001; + pub static MCL_FUTURE : c_int = 0x0002; - pub static MS_ASYNC : int = 0x0001; - pub static MS_INVALIDATE : int = 0x0002; - pub static MS_SYNC : int = 0x0010; + pub static MS_ASYNC : c_int = 0x0001; + pub static MS_INVALIDATE : c_int = 0x0002; + pub static MS_SYNC : c_int = 0x0010; - pub static MS_KILLPAGES : int = 0x0004; - pub static MS_DEACTIVATE : int = 0x0008; + pub static MS_KILLPAGES : c_int = 0x0004; + pub static MS_DEACTIVATE : c_int = 0x0008; - pub static _SC_ARG_MAX : int = 1; - pub static _SC_CHILD_MAX : int = 2; - pub static _SC_CLK_TCK : int = 3; - pub static _SC_NGROUPS_MAX : int = 4; - pub static _SC_OPEN_MAX : int = 5; - pub static _SC_JOB_CONTROL : int = 6; - pub static _SC_SAVED_IDS : int = 7; - pub static _SC_VERSION : int = 8; - pub static _SC_BC_BASE_MAX : int = 9; - pub static _SC_BC_DIM_MAX : int = 10; - pub static _SC_BC_SCALE_MAX : int = 11; - pub static _SC_BC_STRING_MAX : int = 12; - pub static _SC_COLL_WEIGHTS_MAX : int = 13; - pub static _SC_EXPR_NEST_MAX : int = 14; - pub static _SC_LINE_MAX : int = 15; - pub static _SC_RE_DUP_MAX : int = 16; - pub static _SC_2_VERSION : int = 17; - pub static _SC_2_C_BIND : int = 18; - pub static _SC_2_C_DEV : int = 19; - pub static _SC_2_CHAR_TERM : int = 20; - pub static _SC_2_FORT_DEV : int = 21; - pub static _SC_2_FORT_RUN : int = 22; - pub static _SC_2_LOCALEDEF : int = 23; - pub static _SC_2_SW_DEV : int = 24; - pub static _SC_2_UPE : int = 25; - pub static _SC_STREAM_MAX : int = 26; - pub static _SC_TZNAME_MAX : int = 27; - pub static _SC_ASYNCHRONOUS_IO : int = 28; - pub static _SC_PAGESIZE : int = 29; - pub static _SC_MEMLOCK : int = 30; - pub static _SC_MEMLOCK_RANGE : int = 31; - pub static _SC_MEMORY_PROTECTION : int = 32; - pub static _SC_MESSAGE_PASSING : int = 33; - pub static _SC_PRIORITIZED_IO : int = 34; - pub static _SC_PRIORITY_SCHEDULING : int = 35; - pub static _SC_REALTIME_SIGNALS : int = 36; - pub static _SC_SEMAPHORES : int = 37; - pub static _SC_FSYNC : int = 38; - pub static _SC_SHARED_MEMORY_OBJECTS : int = 39; - pub static _SC_SYNCHRONIZED_IO : int = 40; - pub static _SC_TIMERS : int = 41; - pub static _SC_AIO_LISTIO_MAX : int = 42; - pub static _SC_AIO_MAX : int = 43; - pub static _SC_AIO_PRIO_DELTA_MAX : int = 44; - pub static _SC_DELAYTIMER_MAX : int = 45; - pub static _SC_MQ_OPEN_MAX : int = 46; - pub static _SC_MAPPED_FILES : int = 47; - pub static _SC_RTSIG_MAX : int = 48; - pub static _SC_SEM_NSEMS_MAX : int = 49; - pub static _SC_SEM_VALUE_MAX : int = 50; - pub static _SC_SIGQUEUE_MAX : int = 51; - pub static _SC_TIMER_MAX : int = 52; - pub static _SC_XBS5_ILP32_OFF32 : int = 122; - pub static _SC_XBS5_ILP32_OFFBIG : int = 123; - pub static _SC_XBS5_LP64_OFF64 : int = 124; - pub static _SC_XBS5_LPBIG_OFFBIG : int = 125; + pub static _SC_ARG_MAX : c_int = 1; + pub static _SC_CHILD_MAX : c_int = 2; + pub static _SC_CLK_TCK : c_int = 3; + pub static _SC_NGROUPS_MAX : c_int = 4; + pub static _SC_OPEN_MAX : c_int = 5; + pub static _SC_JOB_CONTROL : c_int = 6; + pub static _SC_SAVED_IDS : c_int = 7; + pub static _SC_VERSION : c_int = 8; + pub static _SC_BC_BASE_MAX : c_int = 9; + pub static _SC_BC_DIM_MAX : c_int = 10; + pub static _SC_BC_SCALE_MAX : c_int = 11; + pub static _SC_BC_STRING_MAX : c_int = 12; + pub static _SC_COLL_WEIGHTS_MAX : c_int = 13; + pub static _SC_EXPR_NEST_MAX : c_int = 14; + pub static _SC_LINE_MAX : c_int = 15; + pub static _SC_RE_DUP_MAX : c_int = 16; + pub static _SC_2_VERSION : c_int = 17; + pub static _SC_2_C_BIND : c_int = 18; + pub static _SC_2_C_DEV : c_int = 19; + pub static _SC_2_CHAR_TERM : c_int = 20; + pub static _SC_2_FORT_DEV : c_int = 21; + pub static _SC_2_FORT_RUN : c_int = 22; + pub static _SC_2_LOCALEDEF : c_int = 23; + pub static _SC_2_SW_DEV : c_int = 24; + pub static _SC_2_UPE : c_int = 25; + pub static _SC_STREAM_MAX : c_int = 26; + pub static _SC_TZNAME_MAX : c_int = 27; + pub static _SC_ASYNCHRONOUS_IO : c_int = 28; + pub static _SC_PAGESIZE : c_int = 29; + pub static _SC_MEMLOCK : c_int = 30; + pub static _SC_MEMLOCK_RANGE : c_int = 31; + pub static _SC_MEMORY_PROTECTION : c_int = 32; + pub static _SC_MESSAGE_PASSING : c_int = 33; + pub static _SC_PRIORITIZED_IO : c_int = 34; + pub static _SC_PRIORITY_SCHEDULING : c_int = 35; + pub static _SC_REALTIME_SIGNALS : c_int = 36; + pub static _SC_SEMAPHORES : c_int = 37; + pub static _SC_FSYNC : c_int = 38; + pub static _SC_SHARED_MEMORY_OBJECTS : c_int = 39; + pub static _SC_SYNCHRONIZED_IO : c_int = 40; + pub static _SC_TIMERS : c_int = 41; + pub static _SC_AIO_LISTIO_MAX : c_int = 42; + pub static _SC_AIO_MAX : c_int = 43; + pub static _SC_AIO_PRIO_DELTA_MAX : c_int = 44; + pub static _SC_DELAYTIMER_MAX : c_int = 45; + pub static _SC_MQ_OPEN_MAX : c_int = 46; + pub static _SC_MAPPED_FILES : c_int = 47; + pub static _SC_RTSIG_MAX : c_int = 48; + pub static _SC_SEM_NSEMS_MAX : c_int = 49; + pub static _SC_SEM_VALUE_MAX : c_int = 50; + pub static _SC_SIGQUEUE_MAX : c_int = 51; + pub static _SC_TIMER_MAX : c_int = 52; + pub static _SC_XBS5_ILP32_OFF32 : c_int = 122; + pub static _SC_XBS5_ILP32_OFFBIG : c_int = 123; + pub static _SC_XBS5_LP64_OFF64 : c_int = 124; + pub static _SC_XBS5_LPBIG_OFFBIG : c_int = 125; } pub mod posix01 { - pub static SIGTRAP : int = 5; + use libc::types::os::arch::c95::c_int; - pub static GLOB_APPEND : int = 0x0001; - pub static GLOB_DOOFFS : int = 0x0002; - pub static GLOB_ERR : int = 0x0004; - pub static GLOB_MARK : int = 0x0008; - pub static GLOB_NOCHECK : int = 0x0010; - pub static GLOB_NOSORT : int = 0x0020; - pub static GLOB_NOESCAPE : int = 0x2000; + pub static SIGTRAP : c_int = 5; - pub static GLOB_NOSPACE : int = -1; - pub static GLOB_ABORTED : int = -2; - pub static GLOB_NOMATCH : int = -3; + pub static GLOB_APPEND : c_int = 0x0001; + pub static GLOB_DOOFFS : c_int = 0x0002; + pub static GLOB_ERR : c_int = 0x0004; + pub static GLOB_MARK : c_int = 0x0008; + pub static GLOB_NOCHECK : c_int = 0x0010; + pub static GLOB_NOSORT : c_int = 0x0020; + pub static GLOB_NOESCAPE : c_int = 0x2000; - pub static POSIX_MADV_NORMAL : int = 0; - pub static POSIX_MADV_RANDOM : int = 1; - pub static POSIX_MADV_SEQUENTIAL : int = 2; - pub static POSIX_MADV_WILLNEED : int = 3; - pub static POSIX_MADV_DONTNEED : int = 4; + pub static GLOB_NOSPACE : c_int = -1; + pub static GLOB_ABORTED : c_int = -2; + pub static GLOB_NOMATCH : c_int = -3; - pub static _SC_IOV_MAX : int = 56; - pub static _SC_GETGR_R_SIZE_MAX : int = 70; - pub static _SC_GETPW_R_SIZE_MAX : int = 71; - pub static _SC_LOGIN_NAME_MAX : int = 73; - pub static _SC_MQ_PRIO_MAX : int = 75; - pub static _SC_THREAD_ATTR_STACKADDR : int = 82; - pub static _SC_THREAD_ATTR_STACKSIZE : int = 83; - pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : int = 85; - pub static _SC_THREAD_KEYS_MAX : int = 86; - pub static _SC_THREAD_PRIO_INHERIT : int = 87; - pub static _SC_THREAD_PRIO_PROTECT : int = 88; - pub static _SC_THREAD_PRIORITY_SCHEDULING : int = 89; - pub static _SC_THREAD_PROCESS_SHARED : int = 90; - pub static _SC_THREAD_SAFE_FUNCTIONS : int = 91; - pub static _SC_THREAD_STACK_MIN : int = 93; - pub static _SC_THREAD_THREADS_MAX : int = 94; - pub static _SC_THREADS : int = 96; - pub static _SC_TTY_NAME_MAX : int = 101; - pub static _SC_ATEXIT_MAX : int = 107; - pub static _SC_XOPEN_CRYPT : int = 108; - pub static _SC_XOPEN_ENH_I18N : int = 109; - pub static _SC_XOPEN_LEGACY : int = 110; - pub static _SC_XOPEN_REALTIME : int = 111; - pub static _SC_XOPEN_REALTIME_THREADS : int = 112; - pub static _SC_XOPEN_SHM : int = 113; - pub static _SC_XOPEN_UNIX : int = 115; - pub static _SC_XOPEN_VERSION : int = 116; - pub static _SC_XOPEN_XCU_VERSION : int = 121; + pub static POSIX_MADV_NORMAL : c_int = 0; + pub static POSIX_MADV_RANDOM : c_int = 1; + pub static POSIX_MADV_SEQUENTIAL : c_int = 2; + pub static POSIX_MADV_WILLNEED : c_int = 3; + pub static POSIX_MADV_DONTNEED : c_int = 4; + + pub static _SC_IOV_MAX : c_int = 56; + pub static _SC_GETGR_R_SIZE_MAX : c_int = 70; + pub static _SC_GETPW_R_SIZE_MAX : c_int = 71; + pub static _SC_LOGIN_NAME_MAX : c_int = 73; + pub static _SC_MQ_PRIO_MAX : c_int = 75; + pub static _SC_THREAD_ATTR_STACKADDR : c_int = 82; + pub static _SC_THREAD_ATTR_STACKSIZE : c_int = 83; + pub static _SC_THREAD_DESTRUCTOR_ITERATIONS : c_int = 85; + pub static _SC_THREAD_KEYS_MAX : c_int = 86; + pub static _SC_THREAD_PRIO_INHERIT : c_int = 87; + pub static _SC_THREAD_PRIO_PROTECT : c_int = 88; + pub static _SC_THREAD_PRIORITY_SCHEDULING : c_int = 89; + pub static _SC_THREAD_PROCESS_SHARED : c_int = 90; + pub static _SC_THREAD_SAFE_FUNCTIONS : c_int = 91; + pub static _SC_THREAD_STACK_MIN : c_int = 93; + pub static _SC_THREAD_THREADS_MAX : c_int = 94; + pub static _SC_THREADS : c_int = 96; + pub static _SC_TTY_NAME_MAX : c_int = 101; + pub static _SC_ATEXIT_MAX : c_int = 107; + pub static _SC_XOPEN_CRYPT : c_int = 108; + pub static _SC_XOPEN_ENH_I18N : c_int = 109; + pub static _SC_XOPEN_LEGACY : c_int = 110; + pub static _SC_XOPEN_REALTIME : c_int = 111; + pub static _SC_XOPEN_REALTIME_THREADS : c_int = 112; + pub static _SC_XOPEN_SHM : c_int = 113; + pub static _SC_XOPEN_UNIX : c_int = 115; + pub static _SC_XOPEN_VERSION : c_int = 116; + pub static _SC_XOPEN_XCU_VERSION : c_int = 121; } pub mod posix08 { } pub mod bsd44 { - pub static MADV_NORMAL : int = 0; - pub static MADV_RANDOM : int = 1; - pub static MADV_SEQUENTIAL : int = 2; - pub static MADV_WILLNEED : int = 3; - pub static MADV_DONTNEED : int = 4; - pub static MADV_FREE : int = 5; - pub static MADV_ZERO_WIRED_PAGES : int = 6; - pub static MADV_FREE_REUSABLE : int = 7; - pub static MADV_FREE_REUSE : int = 8; - pub static MADV_CAN_REUSE : int = 9; + use libc::types::os::arch::c95::c_int; - pub static MINCORE_INCORE : int = 0x1; - pub static MINCORE_REFERENCED : int = 0x2; - pub static MINCORE_MODIFIED : int = 0x4; - pub static MINCORE_REFERENCED_OTHER : int = 0x8; - pub static MINCORE_MODIFIED_OTHER : int = 0x10; + pub static MADV_NORMAL : c_int = 0; + pub static MADV_RANDOM : c_int = 1; + pub static MADV_SEQUENTIAL : c_int = 2; + pub static MADV_WILLNEED : c_int = 3; + pub static MADV_DONTNEED : c_int = 4; + pub static MADV_FREE : c_int = 5; + pub static MADV_ZERO_WIRED_PAGES : c_int = 6; + pub static MADV_FREE_REUSABLE : c_int = 7; + pub static MADV_FREE_REUSE : c_int = 8; + pub static MADV_CAN_REUSE : c_int = 9; + + pub static MINCORE_INCORE : c_int = 0x1; + pub static MINCORE_REFERENCED : c_int = 0x2; + pub static MINCORE_MODIFIED : c_int = 0x4; + pub static MINCORE_REFERENCED_OTHER : c_int = 0x8; + pub static MINCORE_MODIFIED_OTHER : c_int = 0x10; } pub mod extra { - pub static O_DSYNC : int = 4194304; - pub static O_SYNC : int = 128; - pub static F_FULLFSYNC : int = 51; + use libc::types::os::arch::c95::c_int; - pub static MAP_COPY : int = 0x0002; - pub static MAP_RENAME : int = 0x0020; - pub static MAP_NORESERVE : int = 0x0040; - pub static MAP_NOEXTEND : int = 0x0100; - pub static MAP_HASSEMAPHORE : int = 0x0200; - pub static MAP_NOCACHE : int = 0x0400; - pub static MAP_JIT : int = 0x0800; + pub static O_DSYNC : c_int = 4194304; + pub static O_SYNC : c_int = 128; + pub static F_FULLFSYNC : c_int = 51; + + pub static MAP_COPY : c_int = 0x0002; + pub static MAP_RENAME : c_int = 0x0020; + pub static MAP_NORESERVE : c_int = 0x0040; + pub static MAP_NOEXTEND : c_int = 0x0100; + pub static MAP_HASSEMAPHORE : c_int = 0x0200; + pub static MAP_NOCACHE : c_int = 0x0400; + pub static MAP_JIT : c_int = 0x0800; } } } diff --git a/src/libstd/os.rs b/src/libstd/os.rs index 1ceb22b20ca6..e6b92c0ccc3f 100644 --- a/src/libstd/os.rs +++ b/src/libstd/os.rs @@ -758,7 +758,7 @@ pub fn list_dir(p: &Path) -> ~[~str] { FindFirstFileW( path_ptr, ::cast::transmute(wfd_ptr)); - if find_handle as int != INVALID_HANDLE_VALUE { + if find_handle as libc::c_int != INVALID_HANDLE_VALUE { let mut more_files = 1 as libc::c_int; while more_files != 0 { let fp_buf = rust_list_dir_wfd_fp_buf(wfd_ptr); From 0cca08a21a33b60f9a27a4bab119b5ec8261be56 Mon Sep 17 00:00:00 2001 From: James Miller Date: Sun, 23 Jun 2013 14:41:45 +1200 Subject: [PATCH 17/31] Add support for #[no_drop_flag] attribute --- src/librustc/middle/trans/adt.rs | 2 +- src/librustc/middle/trans/glue.rs | 57 ++++++++++++++++++++++++++----- src/librustc/middle/ty.rs | 15 ++++++-- 3 files changed, 63 insertions(+), 11 deletions(-) diff --git a/src/librustc/middle/trans/adt.rs b/src/librustc/middle/trans/adt.rs index 624c6607859e..9b7c7037f42a 100644 --- a/src/librustc/middle/trans/adt.rs +++ b/src/librustc/middle/trans/adt.rs @@ -135,7 +135,7 @@ fn represent_type_uncached(cx: &mut CrateContext, t: ty::t) -> Repr { ty::lookup_field_type(cx.tcx, def_id, field.id, substs) }; let packed = ty::lookup_packed(cx.tcx, def_id); - let dtor = ty::ty_dtor(cx.tcx, def_id).is_present(); + let dtor = ty::ty_dtor(cx.tcx, def_id).has_drop_flag(); let ftys = if dtor { ftys + [ty::mk_bool()] } else { ftys }; return Univariant(mk_struct(cx, ftys, packed), dtor) diff --git a/src/librustc/middle/trans/glue.rs b/src/librustc/middle/trans/glue.rs index d8ba524b2bd1..056e5b8cdf79 100644 --- a/src/librustc/middle/trans/glue.rs +++ b/src/librustc/middle/trans/glue.rs @@ -406,13 +406,8 @@ pub fn make_free_glue(bcx: block, v: ValueRef, t: ty::t) { build_return(bcx); } -pub fn trans_struct_drop(bcx: block, - t: ty::t, - v0: ValueRef, - dtor_did: ast::def_id, - class_did: ast::def_id, - substs: &ty::substs) - -> block { +pub fn trans_struct_drop_flag(bcx: block, t: ty::t, v0: ValueRef, dtor_did: ast::def_id, + class_did: ast::def_id, substs: &ty::substs) -> block { let repr = adt::represent_type(bcx.ccx(), t); let drop_flag = adt::trans_drop_flag_ptr(bcx, repr, v0); do with_cond(bcx, IsNotNull(bcx, Load(bcx, drop_flag))) |cx| { @@ -454,6 +449,49 @@ pub fn trans_struct_drop(bcx: block, } } +pub fn trans_struct_drop(mut bcx: block, t: ty::t, v0: ValueRef, dtor_did: ast::def_id, + class_did: ast::def_id, substs: &ty::substs) -> block { + let repr = adt::represent_type(bcx.ccx(), t); + + // Find and call the actual destructor + let dtor_addr = get_res_dtor(bcx.ccx(), dtor_did, + class_did, /*bad*/copy substs.tps); + + // The second argument is the "self" argument for drop + let params = unsafe { + let ty = Type::from_ref(llvm::LLVMTypeOf(dtor_addr)); + ty.element_type().func_params() + }; + + // Class dtors have no explicit args, so the params should + // just consist of the environment (self) + assert_eq!(params.len(), 1); + + // Take a reference to the class (because it's using the Drop trait), + // do so now. + let llval = alloca(bcx, val_ty(v0)); + Store(bcx, v0, llval); + + let self_arg = PointerCast(bcx, llval, params[0]); + let args = ~[self_arg]; + + Call(bcx, dtor_addr, args); + + // Drop the fields + let field_tys = ty::struct_fields(bcx.tcx(), class_did, substs); + for field_tys.iter().enumerate().advance |(i, fld)| { + let llfld_a = adt::trans_field_ptr(bcx, repr, v0, 0, i); + bcx = drop_ty(bcx, llfld_a, fld.mt.ty); + } + + // Zero out the struct + unsafe { + let ty = Type::from_ref(llvm::LLVMTypeOf(v0)); + memzero(bcx, v0, ty); + } + + bcx +} pub fn make_drop_glue(bcx: block, v0: ValueRef, t: ty::t) { // NB: v0 is an *alias* of type t here, not a direct value. @@ -474,7 +512,10 @@ pub fn make_drop_glue(bcx: block, v0: ValueRef, t: ty::t) { ty::ty_struct(did, ref substs) => { let tcx = bcx.tcx(); match ty::ty_dtor(tcx, did) { - ty::TraitDtor(dtor) => { + ty::TraitDtor(dtor, true) => { + trans_struct_drop_flag(bcx, t, v0, dtor, did, substs) + } + ty::TraitDtor(dtor, false) => { trans_struct_drop(bcx, t, v0, dtor, did, substs) } ty::NoDtor => { diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 90cd8a8665ea..424307502f21 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -3855,7 +3855,7 @@ pub fn item_path_str(cx: ctxt, id: ast::def_id) -> ~str { pub enum DtorKind { NoDtor, - TraitDtor(def_id) + TraitDtor(def_id, bool) } impl DtorKind { @@ -3869,13 +3869,24 @@ impl DtorKind { pub fn is_present(&const self) -> bool { !self.is_not_present() } + + pub fn has_drop_flag(&self) -> bool { + match self { + &NoDtor => false, + &TraitDtor(_, flag) => flag + } + } } /* If struct_id names a struct with a dtor, return Some(the dtor's id). Otherwise return none. */ pub fn ty_dtor(cx: ctxt, struct_id: def_id) -> DtorKind { match cx.destructor_for_type.find(&struct_id) { - Some(&method_def_id) => TraitDtor(method_def_id), + Some(&method_def_id) => { + let flag = has_attr(cx, struct_id, "no_drop_flag"); + + TraitDtor(method_def_id, flag) + } None => NoDtor, } } From d9f6dd263c16a21108c27dbf15a3d59a43a5b490 Mon Sep 17 00:00:00 2001 From: James Miller Date: Sun, 23 Jun 2013 16:13:29 +1200 Subject: [PATCH 18/31] Set #[no_drop_flag] on Rc and AtomicOption. Add Test --- src/libextra/rc.rs | 20 ++++++++++------- src/librustc/middle/ty.rs | 2 +- src/libstd/unstable/atomics.rs | 1 + src/test/run-pass/attr-no-drop-flag-size.rs | 25 +++++++++++++++++++++ 4 files changed, 39 insertions(+), 9 deletions(-) create mode 100644 src/test/run-pass/attr-no-drop-flag-size.rs diff --git a/src/libextra/rc.rs b/src/libextra/rc.rs index b90b0983dc24..555cceb5b44b 100644 --- a/src/libextra/rc.rs +++ b/src/libextra/rc.rs @@ -70,10 +70,12 @@ impl Rc { impl Drop for Rc { fn finalize(&self) { unsafe { - (*self.ptr).count -= 1; - if (*self.ptr).count == 0 { - ptr::replace_ptr(self.ptr, intrinsics::uninit()); - free(self.ptr as *c_void) + if self.ptr.is_not_null() { + (*self.ptr).count -= 1; + if (*self.ptr).count == 0 { + ptr::replace_ptr(self.ptr, intrinsics::uninit()); + free(self.ptr as *c_void) + } } } } @@ -220,10 +222,12 @@ impl RcMut { impl Drop for RcMut { fn finalize(&self) { unsafe { - (*self.ptr).count -= 1; - if (*self.ptr).count == 0 { - ptr::replace_ptr(self.ptr, uninit()); - free(self.ptr as *c_void) + if self.ptr.is_not_null() { + (*self.ptr).count -= 1; + if (*self.ptr).count == 0 { + ptr::replace_ptr(self.ptr, uninit()); + free(self.ptr as *c_void) + } } } } diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 424307502f21..d5a2ed7dbd0b 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -3883,7 +3883,7 @@ impl DtorKind { pub fn ty_dtor(cx: ctxt, struct_id: def_id) -> DtorKind { match cx.destructor_for_type.find(&struct_id) { Some(&method_def_id) => { - let flag = has_attr(cx, struct_id, "no_drop_flag"); + let flag = !has_attr(cx, struct_id, "no_drop_flag"); TraitDtor(method_def_id, flag) } diff --git a/src/libstd/unstable/atomics.rs b/src/libstd/unstable/atomics.rs index 6e7a7e2b129c..7a3a5f51d356 100644 --- a/src/libstd/unstable/atomics.rs +++ b/src/libstd/unstable/atomics.rs @@ -62,6 +62,7 @@ pub struct AtomicPtr { /** * An owned atomic pointer. Ensures that only a single reference to the data is held at any time. */ +#[no_drop_flag] pub struct AtomicOption { priv p: *mut c_void } diff --git a/src/test/run-pass/attr-no-drop-flag-size.rs b/src/test/run-pass/attr-no-drop-flag-size.rs new file mode 100644 index 000000000000..e6f05970cced --- /dev/null +++ b/src/test/run-pass/attr-no-drop-flag-size.rs @@ -0,0 +1,25 @@ +// Copyright 2012 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +use std::sys::size_of; + +#[no_drop_flag] +struct Test { + a: T +} + +#[unsafe_destructor] +impl Drop for Test { + fn finalize(&self) { } +} + +fn main() { + assert_eq!(size_of::(), size_of::>()); +} From 721164d5ec0c8b617bd72df36830fe1861e6362b Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 25 Jun 2013 16:39:56 +1200 Subject: [PATCH 19/31] Zero the struct in the take glue, not the drop glue --- src/librustc/middle/trans/glue.rs | 23 +++++++++++++++++------ 1 file changed, 17 insertions(+), 6 deletions(-) diff --git a/src/librustc/middle/trans/glue.rs b/src/librustc/middle/trans/glue.rs index 056e5b8cdf79..8ed3112b5206 100644 --- a/src/librustc/middle/trans/glue.rs +++ b/src/librustc/middle/trans/glue.rs @@ -484,12 +484,6 @@ pub fn trans_struct_drop(mut bcx: block, t: ty::t, v0: ValueRef, dtor_did: ast:: bcx = drop_ty(bcx, llfld_a, fld.mt.ty); } - // Zero out the struct - unsafe { - let ty = Type::from_ref(llvm::LLVMTypeOf(v0)); - memzero(bcx, v0, ty); - } - bcx } @@ -635,6 +629,23 @@ pub fn make_take_glue(bcx: block, v: ValueRef, t: ty::t) { ty::ty_opaque_closure_ptr(ck) => { closure::make_opaque_cbox_take_glue(bcx, ck, v) } + ty::ty_struct(did, ref substs) => { + let tcx = bcx.tcx(); + let bcx = iter_structural_ty(bcx, v, t, take_ty); + + match ty::ty_dtor(tcx, did) { + ty::TraitDtor(dtor, false) => { + // Zero out the struct + unsafe { + let ty = Type::from_ref(llvm::LLVMTypeOf(v)); + memzero(bcx, v, ty); + } + + } + _ => { } + } + bcx + } _ if ty::type_is_structural(t) => { iter_structural_ty(bcx, v, t, take_ty) } From 2afdf0d6a18bd0fb3369088eff1f8d9c707ad43d Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 25 Jun 2013 16:43:58 +1200 Subject: [PATCH 20/31] Update snapshots file --- src/snapshots.txt | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/src/snapshots.txt b/src/snapshots.txt index 1aaf5fee26ab..910de5f66b7f 100644 --- a/src/snapshots.txt +++ b/src/snapshots.txt @@ -1,3 +1,11 @@ +S 2013-06-23 f827561 + macos-i386 63ffbcf99b6853d7840bdfe01380068518d0e466 + macos-x86_64 b34fdf3845f8ef4760817007d8ef820cd32f2e07 + winnt-i386 6602150074ec442fd376fddb2eaf63f5da6fdff9 + freebsd-x86_64 a05bdda2d9ec0e66336d81b98bee8a95442a501f + linux-i386 b8f4a0f0c2250aa4d76ec1eb57c83bfae5725f93 + linux-x86_64 caea3402663334d0a3967c21f58a860c060d5474 + S 2013-06-21 6759ce4 macos-i386 6e5395d2fda1db356f64af28ba525031bf9871c7 macos-x86_64 7b8ded4e1ba1e999a5614eea3a4acacb2c7cef1d From caa50ce15d8ed8f0d50c9049053a5e2cd5a0d701 Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 25 Jun 2013 17:08:26 +1200 Subject: [PATCH 21/31] Remove stage0 cfgs --- src/libstd/iterator.rs | 5 ---- src/libstd/unstable/intrinsics.rs | 50 ------------------------------- src/libstd/vec.rs | 2 -- 3 files changed, 57 deletions(-) diff --git a/src/libstd/iterator.rs b/src/libstd/iterator.rs index d96191f296d7..9177ecabed6a 100644 --- a/src/libstd/iterator.rs +++ b/src/libstd/iterator.rs @@ -43,7 +43,6 @@ pub trait Iterator { /// Return a lower bound and upper bound on the remaining length of the iterator. /// /// The common use case for the estimate is pre-allocating space to store the results. - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { (None, None) } } @@ -610,7 +609,6 @@ impl, U: Iterator> Iterator for ChainIterator { } #[inline] - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { let (a_lower, a_upper) = self.a.size_hint(); let (b_lower, b_upper) = self.b.size_hint(); @@ -664,7 +662,6 @@ impl<'self, A, B, T: Iterator> Iterator for MapIterator<'self, A, B, T> { } #[inline] - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { self.iter.size_hint() } @@ -690,7 +687,6 @@ impl<'self, A, T: Iterator> Iterator for FilterIterator<'self, A, T> { } #[inline] - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { let (_, upper) = self.iter.size_hint(); (None, upper) // can't know a lower bound, due to the predicate @@ -716,7 +712,6 @@ impl<'self, A, B, T: Iterator> Iterator for FilterMapIterator<'self, A, B, } #[inline] - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { let (_, upper) = self.iter.size_hint(); (None, upper) // can't know a lower bound, due to the predicate diff --git a/src/libstd/unstable/intrinsics.rs b/src/libstd/unstable/intrinsics.rs index c38b013a75aa..109f665e41d7 100644 --- a/src/libstd/unstable/intrinsics.rs +++ b/src/libstd/unstable/intrinsics.rs @@ -42,9 +42,7 @@ pub extern "rust-intrinsic" { /// Atomic compare and exchange, release ordering. pub fn atomic_cxchg_rel(dst: &mut int, old: int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_cxchg_acqrel(dst: &mut int, old: int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_cxchg_relaxed(dst: &mut int, old: int, src: int) -> int; @@ -53,7 +51,6 @@ pub extern "rust-intrinsic" { /// Atomic load, acquire ordering. pub fn atomic_load_acq(src: &int) -> int; - #[cfg(not(stage0))] pub fn atomic_load_relaxed(src: &int) -> int; /// Atomic store, sequentially consistent. @@ -61,7 +58,6 @@ pub extern "rust-intrinsic" { /// Atomic store, release ordering. pub fn atomic_store_rel(dst: &mut int, val: int); - #[cfg(not(stage0))] pub fn atomic_store_relaxed(dst: &mut int, val: int); /// Atomic exchange, sequentially consistent. @@ -70,9 +66,7 @@ pub extern "rust-intrinsic" { pub fn atomic_xchg_acq(dst: &mut int, src: int) -> int; /// Atomic exchange, release ordering. pub fn atomic_xchg_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xchg_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xchg_relaxed(dst: &mut int, src: int) -> int; /// Atomic addition, sequentially consistent. @@ -81,9 +75,7 @@ pub extern "rust-intrinsic" { pub fn atomic_xadd_acq(dst: &mut int, src: int) -> int; /// Atomic addition, release ordering. pub fn atomic_xadd_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xadd_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xadd_relaxed(dst: &mut int, src: int) -> int; /// Atomic subtraction, sequentially consistent. @@ -92,97 +84,55 @@ pub extern "rust-intrinsic" { pub fn atomic_xsub_acq(dst: &mut int, src: int) -> int; /// Atomic subtraction, release ordering. pub fn atomic_xsub_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xsub_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xsub_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_and(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_and_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_and_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_and_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_and_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_nand(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_nand_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_nand_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_nand_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_nand_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_or(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_or_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_or_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_or_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_or_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xor(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xor_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xor_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xor_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_xor_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_max(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_max_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_max_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_max_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_max_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_min(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_min_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_min_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_min_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_min_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umin(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umin_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umin_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umin_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umin_relaxed(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umax(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umax_acq(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umax_rel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umax_acqrel(dst: &mut int, src: int) -> int; - #[cfg(not(stage0))] pub fn atomic_umax_relaxed(dst: &mut int, src: int) -> int; /// The size of a type in bytes. diff --git a/src/libstd/vec.rs b/src/libstd/vec.rs index 7b7a3020b939..e39dd262cd90 100644 --- a/src/libstd/vec.rs +++ b/src/libstd/vec.rs @@ -2446,7 +2446,6 @@ macro_rules! iterator { } #[inline] - #[cfg(not(stage0))] fn size_hint(&self) -> (Option, Option) { let exact = Some(((self.end as uint) - (self.ptr as uint)) / size_of::<$elem>()); (exact, exact) @@ -3929,7 +3928,6 @@ mod tests { } #[test] - #[cfg(not(stage0))] fn test_iterator() { use iterator::*; let xs = [1, 2, 5, 10, 11]; From 6ad31ffb53f9620f9063cb441de9c7338dfbb4de Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 25 Jun 2013 17:13:22 +1200 Subject: [PATCH 22/31] Warning police --- src/librustc/metadata/decoder.rs | 1 - src/librustc/middle/ty.rs | 2 +- src/librustc/middle/typeck/check/mod.rs | 2 +- src/librustc/middle/typeck/coherence.rs | 4 +--- src/librustc/util/ppaux.rs | 1 - src/libstd/to_str.rs | 2 -- src/libsyntax/parse/parser.rs | 2 +- 7 files changed, 4 insertions(+), 10 deletions(-) diff --git a/src/librustc/metadata/decoder.rs b/src/librustc/metadata/decoder.rs index 9ace8677dab7..db44ac5e4421 100644 --- a/src/librustc/metadata/decoder.rs +++ b/src/librustc/metadata/decoder.rs @@ -35,7 +35,6 @@ use extra::ebml; use extra::serialize::Decodable; use syntax::ast_map; use syntax::attr; -use syntax::diagnostic::span_handler; use syntax::parse::token::{ident_interner, special_idents}; use syntax::print::pprust; use syntax::{ast, ast_util}; diff --git a/src/librustc/middle/ty.rs b/src/librustc/middle/ty.rs index 90cd8a8665ea..632874025e77 100644 --- a/src/librustc/middle/ty.rs +++ b/src/librustc/middle/ty.rs @@ -21,7 +21,7 @@ use middle::ty; use middle::subst::Subst; use middle::typeck; use middle; -use util::ppaux::{note_and_explain_region, bound_region_to_str, bound_region_ptr_to_str}; +use util::ppaux::{note_and_explain_region, bound_region_ptr_to_str}; use util::ppaux::{trait_store_to_str, ty_to_str, vstore_to_str}; use util::ppaux::{Repr, UserString}; use util::common::{indenter}; diff --git a/src/librustc/middle/typeck/check/mod.rs b/src/librustc/middle/typeck/check/mod.rs index fa7959c7872b..76b7e651ff12 100644 --- a/src/librustc/middle/typeck/check/mod.rs +++ b/src/librustc/middle/typeck/check/mod.rs @@ -107,7 +107,7 @@ use middle::typeck::{isr_alist, lookup_def_ccx}; use middle::typeck::no_params; use middle::typeck::{require_same_types, method_map, vtable_map}; use util::common::{block_query, indenter, loop_query}; -use util::ppaux::{bound_region_to_str,bound_region_ptr_to_str}; +use util::ppaux::{bound_region_ptr_to_str}; use util::ppaux; diff --git a/src/librustc/middle/typeck/coherence.rs b/src/librustc/middle/typeck/coherence.rs index 7ad27077cd86..ae62e768ea2b 100644 --- a/src/librustc/middle/typeck/coherence.rs +++ b/src/librustc/middle/typeck/coherence.rs @@ -16,10 +16,8 @@ use core::prelude::*; -use driver; use metadata::csearch::{each_path, get_impl_trait}; use metadata::csearch::{get_impls_for_mod}; -use metadata::csearch; use metadata::cstore::{CStore, iter_crate_data}; use metadata::decoder::{dl_def, dl_field, dl_impl}; use middle::resolve::{Impl, MethodInfo}; @@ -39,7 +37,7 @@ use middle::typeck::infer::combine::Combine; use middle::typeck::infer::InferCtxt; use middle::typeck::infer::{new_infer_ctxt, resolve_ivar}; use middle::typeck::infer::{resolve_nested_tvar, resolve_type}; -use syntax::ast::{crate, def_id, def_mod, def_struct, def_trait, def_ty}; +use syntax::ast::{crate, def_id, def_mod, def_struct, def_ty}; use syntax::ast::{item, item_enum, item_impl, item_mod, item_struct}; use syntax::ast::{local_crate, method, trait_ref, ty_path}; use syntax::ast; diff --git a/src/librustc/util/ppaux.rs b/src/librustc/util/ppaux.rs index e25267f44412..3194df269c0e 100644 --- a/src/librustc/util/ppaux.rs +++ b/src/librustc/util/ppaux.rs @@ -32,7 +32,6 @@ use syntax::parse::token; use syntax::print::pprust; use syntax::{ast, ast_util}; -use core::str; use core::vec; /// Produces a string suitable for debugging output. diff --git a/src/libstd/to_str.rs b/src/libstd/to_str.rs index 9f8122886213..2e5c3c01adf4 100644 --- a/src/libstd/to_str.rs +++ b/src/libstd/to_str.rs @@ -18,11 +18,9 @@ use str::OwnedStr; use hashmap::HashMap; use hashmap::HashSet; use iterator::IteratorUtil; -use container::Map; use hash::Hash; use cmp::Eq; use vec::ImmutableVector; -use iterator::IteratorUtil; /// A generic trait for converting a value to a string pub trait ToStr { diff --git a/src/libsyntax/parse/parser.rs b/src/libsyntax/parse/parser.rs index f2443f9e5335..c9ef1a7a33c0 100644 --- a/src/libsyntax/parse/parser.rs +++ b/src/libsyntax/parse/parser.rs @@ -60,7 +60,7 @@ use ast::{view_item_, view_item_extern_mod, view_item_use}; use ast::{view_path, view_path_glob, view_path_list, view_path_simple}; use ast::visibility; use ast; -use ast_util::{as_prec, ident_to_path, operator_prec}; +use ast_util::{as_prec, operator_prec}; use ast_util; use codemap::{span, BytePos, spanned, mk_sp}; use codemap; From 122f25dd5e1dae124bdc8d3beeac55474d7a8ce5 Mon Sep 17 00:00:00 2001 From: James Miller Date: Tue, 25 Jun 2013 18:02:56 +1200 Subject: [PATCH 23/31] Add missing import to tests --- src/libstd/to_str.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/to_str.rs b/src/libstd/to_str.rs index 2e5c3c01adf4..4d5bc0f8842f 100644 --- a/src/libstd/to_str.rs +++ b/src/libstd/to_str.rs @@ -177,7 +177,7 @@ impl ToStr for @[A] { mod tests { use hashmap::HashMap; use hashmap::HashSet; - use container::Set; + use container::{Set,Map}; #[test] fn test_simple_types() { assert_eq!(1i.to_str(), ~"1"); From 42b44b21b11ded0a7dbbe196b1c9d338ef33b614 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Mon, 10 Jun 2013 13:00:38 -0700 Subject: [PATCH 24/31] Rename all files with the 'rc' extension --- Makefile.in | 16 ++++++++-------- mk/tools.mk | 14 +++++++------- .../{compiletest.rc => compiletest.rs} | 0 src/libextra/{std.rc => extra.rs} | 0 src/librust/{rust.rc => rust.rs} | 0 src/librustc/{rustc.rc => rustc.rs} | 0 src/librustdoc/{rustdoc.rc => rustdoc.rs} | 0 src/librusti/{rusti.rc => rusti.rs} | 0 src/librustpkg/{rustpkg.rc => rustpkg.rs} | 0 src/libstd/{core.rc => std.rs} | 0 src/libsyntax/{syntax.rc => syntax.rs} | 0 11 files changed, 15 insertions(+), 15 deletions(-) rename src/compiletest/{compiletest.rc => compiletest.rs} (100%) rename src/libextra/{std.rc => extra.rs} (100%) rename src/librust/{rust.rc => rust.rs} (100%) rename src/librustc/{rustc.rc => rustc.rs} (100%) rename src/librustdoc/{rustdoc.rc => rustdoc.rs} (100%) rename src/librusti/{rusti.rc => rusti.rs} (100%) rename src/librustpkg/{rustpkg.rc => rustpkg.rs} (100%) rename src/libstd/{core.rc => std.rs} (100%) rename src/libsyntax/{syntax.rc => syntax.rs} (100%) diff --git a/Makefile.in b/Makefile.in index baae56c4f409..fa6c78065813 100644 --- a/Makefile.in +++ b/Makefile.in @@ -239,29 +239,29 @@ $(foreach target,$(CFG_TARGET_TRIPLES),\ # Standard library variables ###################################################################### -STDLIB_CRATE := $(S)src/libstd/core.rc +STDLIB_CRATE := $(S)src/libstd/std.rs STDLIB_INPUTS := $(wildcard $(addprefix $(S)src/libstd/, \ - core.rc *.rs */*.rs */*/*rs */*/*/*rs)) + *.rs */*.rs */*/*rs */*/*/*rs)) ###################################################################### # Extra library variables ###################################################################### -EXTRALIB_CRATE := $(S)src/libextra/std.rc +EXTRALIB_CRATE := $(S)src/libextra/extra.rs EXTRALIB_INPUTS := $(wildcard $(addprefix $(S)src/libextra/, \ - std.rc *.rs */*.rs)) + *.rs */*.rs)) ###################################################################### # rustc crate variables ###################################################################### -COMPILER_CRATE := $(S)src/librustc/rustc.rc +COMPILER_CRATE := $(S)src/librustc/rustc.rs COMPILER_INPUTS := $(wildcard $(addprefix $(S)src/librustc/, \ - rustc.rc *.rs */*.rs */*/*.rs */*/*/*.rs)) + *.rs */*.rs */*/*.rs */*/*/*.rs)) -LIBSYNTAX_CRATE := $(S)src/libsyntax/syntax.rc +LIBSYNTAX_CRATE := $(S)src/libsyntax/syntax.rs LIBSYNTAX_INPUTS := $(wildcard $(addprefix $(S)src/libsyntax/, \ - syntax.rc *.rs */*.rs */*/*.rs)) + *.rs */*.rs */*/*.rs)) DRIVER_CRATE := $(S)src/driver/driver.rs diff --git a/mk/tools.mk b/mk/tools.mk index 8319d8d4e483..7b50441b3c7f 100644 --- a/mk/tools.mk +++ b/mk/tools.mk @@ -12,23 +12,23 @@ # and host architectures # The test runner that runs the cfail/rfail/rpass and bxench tests -COMPILETEST_CRATE := $(S)src/compiletest/compiletest.rc -COMPILETEST_INPUTS := $(wildcard $(S)src/compiletest/*rs) +COMPILETEST_CRATE := $(S)src/compiletest/compiletest.rs +COMPILETEST_INPUTS := $(wildcard $(S)src/compiletest/*.rs) # Rustpkg, the package manager and build system -RUSTPKG_LIB := $(S)src/librustpkg/rustpkg.rc -RUSTPKG_INPUTS := $(wildcard $(S)src/librustpkg/*rs) +RUSTPKG_LIB := $(S)src/librustpkg/rustpkg.rs +RUSTPKG_INPUTS := $(wildcard $(S)src/librustpkg/*.rs) # Rustdoc, the documentation tool -RUSTDOC_LIB := $(S)src/librustdoc/rustdoc.rc +RUSTDOC_LIB := $(S)src/librustdoc/rustdoc.rs RUSTDOC_INPUTS := $(wildcard $(S)src/librustdoc/*.rs) # Rusti, the JIT REPL -RUSTI_LIB := $(S)src/librusti/rusti.rc +RUSTI_LIB := $(S)src/librusti/rusti.rs RUSTI_INPUTS := $(wildcard $(S)src/librusti/*.rs) # Rust, the convenience tool -RUST_LIB := $(S)src/librust/rust.rc +RUST_LIB := $(S)src/librust/rust.rs RUST_INPUTS := $(wildcard $(S)src/librust/*.rs) # FIXME: These are only built for the host arch. Eventually we'll diff --git a/src/compiletest/compiletest.rc b/src/compiletest/compiletest.rs similarity index 100% rename from src/compiletest/compiletest.rc rename to src/compiletest/compiletest.rs diff --git a/src/libextra/std.rc b/src/libextra/extra.rs similarity index 100% rename from src/libextra/std.rc rename to src/libextra/extra.rs diff --git a/src/librust/rust.rc b/src/librust/rust.rs similarity index 100% rename from src/librust/rust.rc rename to src/librust/rust.rs diff --git a/src/librustc/rustc.rc b/src/librustc/rustc.rs similarity index 100% rename from src/librustc/rustc.rc rename to src/librustc/rustc.rs diff --git a/src/librustdoc/rustdoc.rc b/src/librustdoc/rustdoc.rs similarity index 100% rename from src/librustdoc/rustdoc.rc rename to src/librustdoc/rustdoc.rs diff --git a/src/librusti/rusti.rc b/src/librusti/rusti.rs similarity index 100% rename from src/librusti/rusti.rc rename to src/librusti/rusti.rs diff --git a/src/librustpkg/rustpkg.rc b/src/librustpkg/rustpkg.rs similarity index 100% rename from src/librustpkg/rustpkg.rc rename to src/librustpkg/rustpkg.rs diff --git a/src/libstd/core.rc b/src/libstd/std.rs similarity index 100% rename from src/libstd/core.rc rename to src/libstd/std.rs diff --git a/src/libsyntax/syntax.rc b/src/libsyntax/syntax.rs similarity index 100% rename from src/libsyntax/syntax.rc rename to src/libsyntax/syntax.rs From 92424f0670723e417a96a96310a6ad871994c6b7 Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Sat, 15 Jun 2013 20:58:11 -0700 Subject: [PATCH 25/31] Add the `warnings` lint attribute --- src/librustc/middle/lint.rs | 14 +++++++-- src/test/compile-fail/lint-change-warnings.rs | 30 +++++++++++++++++++ 2 files changed, 42 insertions(+), 2 deletions(-) create mode 100644 src/test/compile-fail/lint-change-warnings.rs diff --git a/src/librustc/middle/lint.rs b/src/librustc/middle/lint.rs index 17ff5930078d..5c36ab7750c8 100644 --- a/src/librustc/middle/lint.rs +++ b/src/librustc/middle/lint.rs @@ -96,6 +96,8 @@ pub enum lint { missing_doc, unreachable_code, + + warnings, } pub fn level_to_str(lv: level) -> &'static str { @@ -280,6 +282,13 @@ static lint_table: &'static [(&'static str, LintSpec)] = &[ desc: "detects unreachable code", default: warn }), + + ("warnings", + LintSpec { + lint: warnings, + desc: "mass-change the level for lints which produce warnings", + default: warn + }), ]; /* @@ -362,10 +371,11 @@ impl Context { fn span_lint(&self, lint: lint, span: span, msg: &str) { let (level, src) = match self.curr.find(&(lint as uint)) { + None => { return } + Some(&(warn, src)) => (self.get_level(warnings), src), Some(&pair) => pair, - None => { return; } }; - if level == allow { return; } + if level == allow { return } let mut note = None; let msg = match src { diff --git a/src/test/compile-fail/lint-change-warnings.rs b/src/test/compile-fail/lint-change-warnings.rs new file mode 100644 index 000000000000..977abc4dc0d1 --- /dev/null +++ b/src/test/compile-fail/lint-change-warnings.rs @@ -0,0 +1,30 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +#[deny(warnings)]; + +fn main() { + while true {} //~ ERROR: infinite +} + +#[allow(warnings)] +fn foo() { + while true {} +} + +#[warn(warnings)] +fn bar() { + while true {} //~ WARNING: infinite +} + +#[forbid(warnings)] +fn baz() { + while true {} //~ ERROR: warnings +} From 9f80591d84790a9571707a85cf4bc5d8f6df114d Mon Sep 17 00:00:00 2001 From: Ramkumar Ramachandra Date: Sun, 23 Jun 2013 22:18:43 +0530 Subject: [PATCH 26/31] resolve: report duplicate module definitions add_child() is responsible for reporting errors about type, value, and module duplicate definitions. Although it checks for all three, it uses namespace_to_str() to convert a Namespace value into a string before printing an error like: error: duplicate definition of type `foo` ^^^^ note: first definition of type foo here: ^^^^ Unfortunately, this string can only be one of "type" or "value" (corresponding to TypeNS and ValueNS respectively), and it reports duplicate modules as duplicate types. To alleviate the problem, define a special NamespaceError enum to define more specialized errors, and use it instead of attempting to reuse the Namespace enum. Reported-by: Corey Richardson Signed-off-by: Ramkumar Ramachandra --- src/librustc/middle/resolve.rs | 38 ++++++++++++++++++--------- src/test/compile-fail/issue-3099-b.rs | 2 +- 2 files changed, 27 insertions(+), 13 deletions(-) diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 8a08b3419e2e..5fb7cc9b9bda 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -101,6 +101,14 @@ pub enum Namespace { ValueNS } +#[deriving(Eq)] +pub enum NamespaceError { + NoError, + ModuleError, + TypeError, + ValueError +} + /// A NamespaceResult represents the result of resolving an import in /// a particular namespace. The result is either definitely-resolved, /// definitely- unresolved, or unknown. @@ -759,10 +767,12 @@ pub fn PrimitiveTypeTable() -> PrimitiveTypeTable { } -pub fn namespace_to_str(ns: Namespace) -> ~str { +pub fn namespace_error_to_str(ns: NamespaceError) -> &'static str { match ns { - TypeNS => ~"type", - ValueNS => ~"value", + NoError => "", + ModuleError => "module", + TypeError => "type", + ValueError => "value", } } @@ -993,21 +1003,25 @@ impl Resolver { // * If no duplicate checking was requested at all, do // nothing. - let mut is_duplicate = false; + let mut duplicate_type = NoError; let ns = match duplicate_checking_mode { ForbidDuplicateModules => { - is_duplicate = child.get_module_if_available().is_some(); + if (child.get_module_if_available().is_some()) { + duplicate_type = ModuleError; + } Some(TypeNS) } ForbidDuplicateTypes => { match child.def_for_namespace(TypeNS) { Some(def_mod(_)) | None => {} - Some(_) => is_duplicate = true + Some(_) => duplicate_type = TypeError } Some(TypeNS) } ForbidDuplicateValues => { - is_duplicate = child.defined_in_namespace(ValueNS); + if child.defined_in_namespace(ValueNS) { + duplicate_type = ValueError; + } Some(ValueNS) } ForbidDuplicateTypesAndValues => { @@ -1016,31 +1030,31 @@ impl Resolver { Some(def_mod(_)) | None => {} Some(_) => { n = Some(TypeNS); - is_duplicate = true; + duplicate_type = TypeError; } }; if child.defined_in_namespace(ValueNS) { - is_duplicate = true; + duplicate_type = ValueError; n = Some(ValueNS); } n } OverwriteDuplicates => None }; - if is_duplicate { + if (duplicate_type != NoError) { // Return an error here by looking up the namespace that // had the duplicate. let ns = ns.unwrap(); self.session.span_err(sp, fmt!("duplicate definition of %s `%s`", - namespace_to_str(ns), + namespace_error_to_str(duplicate_type), self.session.str_of(name))); { let r = child.span_for_namespace(ns); for r.iter().advance |sp| { self.session.span_note(*sp, fmt!("first definition of %s %s here:", - namespace_to_str(ns), + namespace_error_to_str(duplicate_type), self.session.str_of(name))); } } diff --git a/src/test/compile-fail/issue-3099-b.rs b/src/test/compile-fail/issue-3099-b.rs index 3d22a59d6bd4..5502b18f0941 100644 --- a/src/test/compile-fail/issue-3099-b.rs +++ b/src/test/compile-fail/issue-3099-b.rs @@ -10,6 +10,6 @@ pub mod a {} -pub mod a {} //~ ERROR duplicate definition of type `a` +pub mod a {} //~ ERROR duplicate definition of module `a` fn main() {} From f982f42f3c1c45ed1be4c0fd5a90e639e43e3f95 Mon Sep 17 00:00:00 2001 From: Ramkumar Ramachandra Date: Sun, 23 Jun 2013 22:20:00 +0530 Subject: [PATCH 27/31] resolve: make error message strings more consistent The "first definition of ..." error string reported by add_child() looks different from similar messages reported by other functions. Fix this. Signed-off-by: Ramkumar Ramachandra --- src/librustc/middle/resolve.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 5fb7cc9b9bda..f39889b5e2f9 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -1053,7 +1053,7 @@ impl Resolver { let r = child.span_for_namespace(ns); for r.iter().advance |sp| { self.session.span_note(*sp, - fmt!("first definition of %s %s here:", + fmt!("first definition of %s `%s` here", namespace_error_to_str(duplicate_type), self.session.str_of(name))); } From 5242e8d2bad01beec7c841d20952cb230bc9fd84 Mon Sep 17 00:00:00 2001 From: Daniel Micay Date: Mon, 24 Jun 2013 17:19:28 -0400 Subject: [PATCH 28/31] remove the redundant `each` method from OptVec --- src/librustc/metadata/encoder.rs | 4 ++-- src/librustc/middle/resolve.rs | 8 ++++---- src/librustc/middle/typeck/astconv.rs | 2 +- src/librustc/middle/typeck/collect.rs | 4 ++-- src/librustc/middle/typeck/rscope.rs | 2 +- src/libsyntax/ast_util.rs | 4 ++-- src/libsyntax/ext/deriving/generic.rs | 4 ++-- src/libsyntax/ext/pipes/pipec.rs | 4 ++-- src/libsyntax/opt_vec.rs | 7 ------- src/libsyntax/print/pprust.rs | 2 +- src/libsyntax/visit.rs | 4 ++-- 11 files changed, 19 insertions(+), 26 deletions(-) diff --git a/src/librustc/metadata/encoder.rs b/src/librustc/metadata/encoder.rs index d08342d8687d..9c28da10e40d 100644 --- a/src/librustc/metadata/encoder.rs +++ b/src/librustc/metadata/encoder.rs @@ -731,8 +731,8 @@ fn encode_info_for_method(ecx: &EncodeContext, } let mut combined_ty_params = opt_vec::Empty; - for owner_generics.ty_params.each |x| { combined_ty_params.push(copy *x) } - for method_generics.ty_params.each |x| { combined_ty_params.push(copy *x) } + for owner_generics.ty_params.iter().advance |x| { combined_ty_params.push(copy *x) } + for method_generics.ty_params.iter().advance |x| { combined_ty_params.push(copy *x) } let len = combined_ty_params.len(); encode_type_param_bounds(ebml_w, ecx, &combined_ty_params); diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index a8b837d869d3..3a54c224b523 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -3834,8 +3834,8 @@ impl Resolver { pub fn resolve_type_parameters(@mut self, type_parameters: &OptVec, visitor: ResolveVisitor) { - for type_parameters.each |type_parameter| { - for type_parameter.bounds.each |bound| { + for type_parameters.iter().advance |type_parameter| { + for type_parameter.bounds.iter().advance |bound| { self.resolve_type_parameter_bound(bound, visitor); } } @@ -4181,13 +4181,13 @@ impl Resolver { } } - for bounds.each |bound| { + for bounds.iter().advance |bound| { self.resolve_type_parameter_bound(bound, visitor); } } ty_closure(c) => { - for c.bounds.each |bound| { + for c.bounds.iter().advance |bound| { self.resolve_type_parameter_bound(bound, visitor); } visit_ty(ty, ((), visitor)); diff --git a/src/librustc/middle/typeck/astconv.rs b/src/librustc/middle/typeck/astconv.rs index 3b651451db84..5e6574850f1b 100644 --- a/src/librustc/middle/typeck/astconv.rs +++ b/src/librustc/middle/typeck/astconv.rs @@ -752,7 +752,7 @@ fn conv_builtin_bounds(tcx: ty::ctxt, //! legal. let mut builtin_bounds = ty::EmptyBuiltinBounds(); - for ast_bounds.each |ast_bound| { + for ast_bounds.iter().advance |ast_bound| { match *ast_bound { ast::TraitTyParamBound(b) => { match lookup_def_tcx(tcx, b.path.span, b.ref_id) { diff --git a/src/librustc/middle/typeck/collect.rs b/src/librustc/middle/typeck/collect.rs index 3554376902cb..7812a0ed0eba 100644 --- a/src/librustc/middle/typeck/collect.rs +++ b/src/librustc/middle/typeck/collect.rs @@ -775,7 +775,7 @@ pub fn ensure_no_ty_param_bounds(ccx: &CrateCtxt, span: span, generics: &ast::Generics, thing: &'static str) { - for generics.ty_params.each |ty_param| { + for generics.ty_params.iter().advance |ty_param| { if ty_param.bounds.len() > 0 { ccx.tcx.sess.span_err( span, @@ -1172,7 +1172,7 @@ pub fn ty_generics(ccx: &CrateCtxt, builtin_bounds: ty::EmptyBuiltinBounds(), trait_bounds: ~[] }; - for ast_bounds.each |ast_bound| { + for ast_bounds.iter().advance |ast_bound| { match *ast_bound { TraitTyParamBound(b) => { let ty = ty::mk_param(ccx.tcx, param_ty.idx, param_ty.def_id); diff --git a/src/librustc/middle/typeck/rscope.rs b/src/librustc/middle/typeck/rscope.rs index 16b490cd478d..dc9fc264f85d 100644 --- a/src/librustc/middle/typeck/rscope.rs +++ b/src/librustc/middle/typeck/rscope.rs @@ -57,7 +57,7 @@ impl RegionParamNames { } fn has_ident(&self, ident: ast::ident) -> bool { - for self.each |region_param_name| { + for self.iter().advance |region_param_name| { if *region_param_name == ident { return true; } diff --git a/src/libsyntax/ast_util.rs b/src/libsyntax/ast_util.rs index 227d700452b6..a233c330b64d 100644 --- a/src/libsyntax/ast_util.rs +++ b/src/libsyntax/ast_util.rs @@ -394,10 +394,10 @@ impl id_range { pub fn id_visitor(vfn: @fn(node_id, T)) -> visit::vt { let visit_generics: @fn(&Generics, T) = |generics, t| { - for generics.ty_params.each |p| { + for generics.ty_params.iter().advance |p| { vfn(p.id, copy t); } - for generics.lifetimes.each |p| { + for generics.lifetimes.iter().advance |p| { vfn(p.id, copy t); } }; diff --git a/src/libsyntax/ext/deriving/generic.rs b/src/libsyntax/ext/deriving/generic.rs index 981b28afd022..83e446fa4c68 100644 --- a/src/libsyntax/ext/deriving/generic.rs +++ b/src/libsyntax/ext/deriving/generic.rs @@ -324,11 +324,11 @@ impl<'self> TraitDef<'self> { let mut trait_generics = self.generics.to_generics(cx, span, type_ident, generics); // Copy the lifetimes - for generics.lifetimes.each |l| { + for generics.lifetimes.iter().advance |l| { trait_generics.lifetimes.push(copy *l) }; // Create the type parameters. - for generics.ty_params.each |ty_param| { + for generics.ty_params.iter().advance |ty_param| { // I don't think this can be moved out of the loop, since // a TyParamBound requires an ast id let mut bounds = opt_vec::from( diff --git a/src/libsyntax/ext/pipes/pipec.rs b/src/libsyntax/ext/pipes/pipec.rs index 55ac9c5ec1c8..da5455d43327 100644 --- a/src/libsyntax/ext/pipes/pipec.rs +++ b/src/libsyntax/ext/pipes/pipec.rs @@ -374,7 +374,7 @@ impl gen_init for protocol { fn buffer_ty_path(&self, cx: @ExtCtxt) -> @ast::Ty { let mut params: OptVec = opt_vec::Empty; for (copy self.states).iter().advance |s| { - for s.generics.ty_params.each |tp| { + for s.generics.ty_params.iter().advance |tp| { match params.iter().find_(|tpp| tp.ident == tpp.ident) { None => params.push(*tp), _ => () @@ -392,7 +392,7 @@ impl gen_init for protocol { let ext_cx = cx; let mut params: OptVec = opt_vec::Empty; let fields = do (copy self.states).iter().transform |s| { - for s.generics.ty_params.each |tp| { + for s.generics.ty_params.iter().advance |tp| { match params.iter().find_(|tpp| tp.ident == tpp.ident) { None => params.push(*tp), _ => () diff --git a/src/libsyntax/opt_vec.rs b/src/libsyntax/opt_vec.rs index 8917b481dc72..22b1d040d42e 100644 --- a/src/libsyntax/opt_vec.rs +++ b/src/libsyntax/opt_vec.rs @@ -38,13 +38,6 @@ pub fn from(t: ~[T]) -> OptVec { } impl OptVec { - fn each(&self, blk: &fn(v: &T) -> bool) -> bool { - match *self { - Empty => true, - Vec(ref v) => v.iter().advance(blk) - } - } - fn push(&mut self, t: T) { match *self { Vec(ref mut v) => { diff --git a/src/libsyntax/print/pprust.rs b/src/libsyntax/print/pprust.rs index 1a3155337a5e..d7b5e57a57f0 100644 --- a/src/libsyntax/print/pprust.rs +++ b/src/libsyntax/print/pprust.rs @@ -1743,7 +1743,7 @@ pub fn print_bounds(s: @ps, bounds: @OptVec) { if !bounds.is_empty() { word(s.s, ":"); let mut first = true; - for bounds.each |bound| { + for bounds.iter().advance |bound| { nbsp(s); if first { first = false; diff --git a/src/libsyntax/visit.rs b/src/libsyntax/visit.rs index d7914832835a..5e409be3e6cc 100644 --- a/src/libsyntax/visit.rs +++ b/src/libsyntax/visit.rs @@ -334,7 +334,7 @@ pub fn visit_foreign_item(ni: @foreign_item, (e, v): (E, vt)) { pub fn visit_ty_param_bounds(bounds: &OptVec, (e, v): (E, vt)) { - for bounds.each |bound| { + for bounds.iter().advance |bound| { match *bound { TraitTyParamBound(ty) => visit_trait_ref(ty, (copy e, v)), RegionTyParamBound => {} @@ -343,7 +343,7 @@ pub fn visit_ty_param_bounds(bounds: &OptVec, } pub fn visit_generics(generics: &Generics, (e, v): (E, vt)) { - for generics.ty_params.each |tp| { + for generics.ty_params.iter().advance |tp| { visit_ty_param_bounds(tp.bounds, (copy e, v)); } } From 64ee9668a2e3d4d75b859fd3bca1466a97fae2d8 Mon Sep 17 00:00:00 2001 From: Daniel Micay Date: Mon, 24 Jun 2013 17:45:00 -0400 Subject: [PATCH 29/31] container: remove internal iterators from Map the maps are being migrated to external iterators --- src/libextra/smallintmap.rs | 64 +++++++++---------- src/libextra/treemap.rs | 40 ++++++------ src/libstd/container.rs | 12 ---- src/libstd/hashmap.rs | 56 ++++++++-------- src/libstd/trie.rs | 48 +++++++------- .../class-impl-very-parameterized-trait.rs | 21 ------ 6 files changed, 104 insertions(+), 137 deletions(-) diff --git a/src/libextra/smallintmap.rs b/src/libextra/smallintmap.rs index 17126f0d32b5..1d163922955d 100644 --- a/src/libextra/smallintmap.rs +++ b/src/libextra/smallintmap.rs @@ -56,38 +56,6 @@ impl Map for SmallIntMap { self.find(key).is_some() } - /// Visit all key-value pairs in order - fn each<'a>(&'a self, it: &fn(&uint, &'a V) -> bool) -> bool { - for uint::range(0, self.v.len()) |i| { - match self.v[i] { - Some(ref elt) => if !it(&i, elt) { return false; }, - None => () - } - } - return true; - } - - /// Visit all keys in order - fn each_key(&self, blk: &fn(key: &uint) -> bool) -> bool { - self.each(|k, _| blk(k)) - } - - /// Visit all values in order - fn each_value<'a>(&'a self, blk: &fn(value: &'a V) -> bool) -> bool { - self.each(|_, v| blk(v)) - } - - /// Iterate over the map and mutate the contained values - fn mutate_values(&mut self, it: &fn(&uint, &mut V) -> bool) -> bool { - for uint::range(0, self.v.len()) |i| { - match self.v[i] { - Some(ref mut elt) => if !it(&i, elt) { return false; }, - None => () - } - } - return true; - } - /// Return a reference to the value corresponding to the key fn find<'a>(&'a self, key: &uint) -> Option<&'a V> { if *key < self.v.len() { @@ -156,6 +124,38 @@ impl SmallIntMap { /// Create an empty SmallIntMap pub fn new() -> SmallIntMap { SmallIntMap{v: ~[]} } + /// Visit all key-value pairs in order + pub fn each<'a>(&'a self, it: &fn(&uint, &'a V) -> bool) -> bool { + for uint::range(0, self.v.len()) |i| { + match self.v[i] { + Some(ref elt) => if !it(&i, elt) { return false; }, + None => () + } + } + return true; + } + + /// Visit all keys in order + pub fn each_key(&self, blk: &fn(key: &uint) -> bool) -> bool { + self.each(|k, _| blk(k)) + } + + /// Visit all values in order + pub fn each_value<'a>(&'a self, blk: &fn(value: &'a V) -> bool) -> bool { + self.each(|_, v| blk(v)) + } + + /// Iterate over the map and mutate the contained values + pub fn mutate_values(&mut self, it: &fn(&uint, &mut V) -> bool) -> bool { + for uint::range(0, self.v.len()) |i| { + match self.v[i] { + Some(ref mut elt) => if !it(&i, elt) { return false; }, + None => () + } + } + return true; + } + /// Visit all key-value pairs in reverse order pub fn each_reverse<'a>(&'a self, it: &fn(uint, &'a V) -> bool) -> bool { for uint::range_rev(self.v.len(), 0) |i| { diff --git a/src/libextra/treemap.rs b/src/libextra/treemap.rs index 4929dea9045b..fd83fd199167 100644 --- a/src/libextra/treemap.rs +++ b/src/libextra/treemap.rs @@ -107,26 +107,6 @@ impl Map for TreeMap { self.find(key).is_some() } - /// Visit all key-value pairs in order - fn each<'a>(&'a self, f: &fn(&'a K, &'a V) -> bool) -> bool { - each(&self.root, f) - } - - /// Visit all keys in order - fn each_key(&self, f: &fn(&K) -> bool) -> bool { - self.each(|k, _| f(k)) - } - - /// Visit all values in order - fn each_value<'a>(&'a self, f: &fn(&'a V) -> bool) -> bool { - self.each(|_, v| f(v)) - } - - /// Iterate over the map and mutate the contained values - fn mutate_values(&mut self, f: &fn(&K, &mut V) -> bool) -> bool { - mutate_values(&mut self.root, f) - } - /// Return a reference to the value corresponding to the key fn find<'a>(&'a self, key: &K) -> Option<&'a V> { let mut current: &'a Option<~TreeNode> = &self.root; @@ -184,6 +164,26 @@ impl TreeMap { /// Create an empty TreeMap pub fn new() -> TreeMap { TreeMap{root: None, length: 0} } + /// Visit all key-value pairs in order + pub fn each<'a>(&'a self, f: &fn(&'a K, &'a V) -> bool) -> bool { + each(&self.root, f) + } + + /// Visit all keys in order + pub fn each_key(&self, f: &fn(&K) -> bool) -> bool { + self.each(|k, _| f(k)) + } + + /// Visit all values in order + pub fn each_value<'a>(&'a self, f: &fn(&'a V) -> bool) -> bool { + self.each(|_, v| f(v)) + } + + /// Iterate over the map and mutate the contained values + pub fn mutate_values(&mut self, f: &fn(&K, &mut V) -> bool) -> bool { + mutate_values(&mut self.root, f) + } + /// Visit all key-value pairs in reverse order pub fn each_reverse<'a>(&'a self, f: &fn(&'a K, &'a V) -> bool) -> bool { each_reverse(&self.root, f) diff --git a/src/libstd/container.rs b/src/libstd/container.rs index c1b656f1cd9e..d6f4c26715a4 100644 --- a/src/libstd/container.rs +++ b/src/libstd/container.rs @@ -34,18 +34,6 @@ pub trait Map: Mutable { /// Return true if the map contains a value for the specified key fn contains_key(&self, key: &K) -> bool; - /// Visits all keys and values - fn each<'a>(&'a self, f: &fn(&K, &'a V) -> bool) -> bool; - - /// Visit all keys - fn each_key(&self, f: &fn(&K) -> bool) -> bool; - - /// Visit all values - fn each_value<'a>(&'a self, f: &fn(&'a V) -> bool) -> bool; - - /// Iterate over the map and mutate the contained values - fn mutate_values(&mut self, f: &fn(&K, &mut V) -> bool) -> bool; - /// Return a reference to the value corresponding to the key fn find<'a>(&'a self, key: &K) -> Option<&'a V>; diff --git a/src/libstd/hashmap.rs b/src/libstd/hashmap.rs index 7d55947e8188..962025915d24 100644 --- a/src/libstd/hashmap.rs +++ b/src/libstd/hashmap.rs @@ -307,34 +307,6 @@ impl Map for HashMap { } } - /// Visit all key-value pairs - fn each<'a>(&'a self, blk: &fn(&K, &'a V) -> bool) -> bool { - self.iter().advance(|(k, v)| blk(k, v)) - } - - /// Visit all keys - fn each_key(&self, blk: &fn(k: &K) -> bool) -> bool { - self.iter().advance(|(k, _)| blk(k)) - } - - /// Visit all values - fn each_value<'a>(&'a self, blk: &fn(v: &'a V) -> bool) -> bool { - self.iter().advance(|(_, v)| blk(v)) - } - - /// Iterate over the map and mutate the contained values - fn mutate_values(&mut self, blk: &fn(&K, &mut V) -> bool) -> bool { - for uint::range(0, self.buckets.len()) |i| { - match self.buckets[i] { - Some(Bucket{key: ref key, value: ref mut value, _}) => { - if !blk(key, value) { return false; } - } - None => () - } - } - return true; - } - /// Return a reference to the value corresponding to the key fn find<'a>(&'a self, k: &K) -> Option<&'a V> { match self.bucket_for_key(k) { @@ -516,6 +488,34 @@ impl HashMap { } } + /// Visit all key-value pairs + pub fn each<'a>(&'a self, blk: &fn(&K, &'a V) -> bool) -> bool { + self.iter().advance(|(k, v)| blk(k, v)) + } + + /// Visit all keys + pub fn each_key(&self, blk: &fn(k: &K) -> bool) -> bool { + self.iter().advance(|(k, _)| blk(k)) + } + + /// Visit all values + pub fn each_value<'a>(&'a self, blk: &fn(v: &'a V) -> bool) -> bool { + self.iter().advance(|(_, v)| blk(v)) + } + + /// Iterate over the map and mutate the contained values + pub fn mutate_values(&mut self, blk: &fn(&K, &mut V) -> bool) -> bool { + for uint::range(0, self.buckets.len()) |i| { + match self.buckets[i] { + Some(Bucket{key: ref key, value: ref mut value, _}) => { + if !blk(key, value) { return false; } + } + None => () + } + } + return true; + } + /// An iterator visiting all key-value pairs in arbitrary order. /// Iterator element type is (&'a K, &'a V). pub fn iter<'a>(&'a self) -> HashMapIterator<'a, K, V> { diff --git a/src/libstd/trie.rs b/src/libstd/trie.rs index e6449ef49229..8f70c75439a0 100644 --- a/src/libstd/trie.rs +++ b/src/libstd/trie.rs @@ -58,30 +58,6 @@ impl Map for TrieMap { self.find(key).is_some() } - /// Visit all key-value pairs in order - #[inline] - fn each<'a>(&'a self, f: &fn(&uint, &'a T) -> bool) -> bool { - self.root.each(f) - } - - /// Visit all keys in order - #[inline] - fn each_key(&self, f: &fn(&uint) -> bool) -> bool { - self.each(|k, _| f(k)) - } - - /// Visit all values in order - #[inline] - fn each_value<'a>(&'a self, f: &fn(&'a T) -> bool) -> bool { - self.each(|_, v| f(v)) - } - - /// Iterate over the map and mutate the contained values - #[inline] - fn mutate_values(&mut self, f: &fn(&uint, &mut T) -> bool) -> bool { - self.root.mutate_values(f) - } - /// Return a reference to the value corresponding to the key #[inline] fn find<'a>(&'a self, key: &uint) -> Option<&'a T> { @@ -158,6 +134,30 @@ impl TrieMap { self.root.each_reverse(f) } + /// Visit all key-value pairs in order + #[inline] + pub fn each<'a>(&'a self, f: &fn(&uint, &'a T) -> bool) -> bool { + self.root.each(f) + } + + /// Visit all keys in order + #[inline] + pub fn each_key(&self, f: &fn(&uint) -> bool) -> bool { + self.each(|k, _| f(k)) + } + + /// Visit all values in order + #[inline] + pub fn each_value<'a>(&'a self, f: &fn(&'a T) -> bool) -> bool { + self.each(|_, v| f(v)) + } + + /// Iterate over the map and mutate the contained values + #[inline] + pub fn mutate_values(&mut self, f: &fn(&uint, &mut T) -> bool) -> bool { + self.root.mutate_values(f) + } + /// Visit all keys in reverse order #[inline] pub fn each_key_reverse(&self, f: &fn(&uint) -> bool) -> bool { diff --git a/src/test/run-pass/class-impl-very-parameterized-trait.rs b/src/test/run-pass/class-impl-very-parameterized-trait.rs index c54b8db46c88..2805fec6fce2 100644 --- a/src/test/run-pass/class-impl-very-parameterized-trait.rs +++ b/src/test/run-pass/class-impl-very-parameterized-trait.rs @@ -61,29 +61,8 @@ impl Mutable for cat { } impl Map for cat { - fn each<'a>(&'a self, f: &fn(&int, &'a T) -> bool) -> bool { - let mut n = int::abs(self.meows); - while n > 0 { - if !f(&n, &self.name) { return false; } - n -= 1; - } - return true; - } - fn contains_key(&self, k: &int) -> bool { *k <= self.meows } - fn each_key(&self, f: &fn(v: &int) -> bool) -> bool { - self.each(|k, _| f(k)) - } - - fn each_value<'a>(&'a self, f: &fn(v: &'a T) -> bool) -> bool { - self.each(|_, v| f(v)) - } - - fn mutate_values(&mut self, _f: &fn(&int, &mut T) -> bool) -> bool { - fail!("nope") - } - fn insert(&mut self, k: int, _: T) -> bool { self.meows += k; true From e67c48a5912b85c286113e0d039aae85f18da1d7 Mon Sep 17 00:00:00 2001 From: Daniel Micay Date: Mon, 24 Jun 2013 18:34:20 -0400 Subject: [PATCH 30/31] remove `each` from vec, HashMap and HashSet --- doc/tutorial.md | 57 ++++++-- src/compiletest/runtest.rs | 2 +- src/libextra/arc.rs | 11 +- src/libextra/getopts.rs | 5 +- src/libextra/json.rs | 8 +- src/libextra/net_url.rs | 2 +- src/libextra/serialize.rs | 4 +- src/libextra/sync.rs | 3 +- src/libextra/workcache.rs | 4 +- src/librustc/metadata/cstore.rs | 2 +- src/librustc/middle/kind.rs | 3 +- src/librustc/middle/lang_items.rs | 2 +- src/librustc/middle/lint.rs | 7 +- src/librustc/middle/region.rs | 2 +- src/librustc/middle/resolve.rs | 24 ++-- src/librustc/middle/trans/_match.rs | 2 +- src/librustc/middle/trans/base.rs | 2 +- src/librustc/middle/trans/callee.rs | 4 +- src/librustc/middle/trans/type_use.rs | 3 +- .../middle/typeck/infer/region_inference.rs | 2 +- src/librustc/rustc.rs | 2 +- src/librusti/program.rs | 8 +- src/libstd/hashmap.rs | 11 -- src/libstd/task/spawn.rs | 2 +- src/libstd/vec.rs | 122 +----------------- src/test/bench/graph500-bfs.rs | 4 +- src/test/bench/msgsend-pipes-shared.rs | 2 +- src/test/bench/msgsend-pipes.rs | 2 +- src/test/bench/shootout-chameneos-redux.rs | 4 +- src/test/bench/shootout-k-nucleotide-pipes.rs | 2 +- .../block-must-not-have-result-for.rs | 4 +- .../borrowck-insert-during-each.rs | 2 +- src/test/compile-fail/issue-2151.rs | 7 +- src/test/compile-fail/liveness-issue-2163.rs | 2 +- src/test/run-pass/assignability-trait.rs | 6 +- src/test/run-pass/auto-loop.rs | 5 +- src/test/run-pass/block-arg.rs | 2 +- .../run-pass/borrowck-mut-vec-as-imm-slice.rs | 6 +- src/test/run-pass/break.rs | 6 +- src/test/run-pass/const-vec-of-fns.rs | 4 +- src/test/run-pass/for-destruct.rs | 3 +- src/test/run-pass/rcvr-borrowed-to-slice.rs | 2 +- src/test/run-pass/trait-generic.rs | 5 +- 43 files changed, 139 insertions(+), 223 deletions(-) diff --git a/doc/tutorial.md b/doc/tutorial.md index 9c61a04930ac..9e54622688b0 100644 --- a/doc/tutorial.md +++ b/doc/tutorial.md @@ -1552,13 +1552,6 @@ fn each(v: &[int], op: &fn(v: &int)) { } ~~~~ -As an aside, the reason we pass in a *pointer* to an integer rather -than the integer itself is that this is how the actual `each()` -function for vectors works. `vec::each` though is a -[generic](#generics) function, so must be efficient to use for all -types. Passing the elements by pointer avoids copying potentially -large objects. - As a caller, if we use a closure to provide the final operator argument, we can write it in a way that has a pleasant, block-like structure. @@ -1616,6 +1609,9 @@ To enable `debug!` logging, set the RUST_LOG environment variable to the name of ## For loops +> ***Note:*** The closure-based protocol used `for` loop is on the way out. The `for` loop will +> use iterator objects in the future instead. + The most common way to express iteration in Rust is with a `for` loop. Like `do`, `for` is a nice syntax for describing control flow with closures. Additionally, within a `for` loop, `break`, `loop`, @@ -1640,7 +1636,16 @@ fn each(v: &[int], op: &fn(v: &int) -> bool) -> bool { And using this function to iterate over a vector: ~~~~ -# use each = std::vec::each; +# fn each(v: &[int], op: &fn(v: &int) -> bool) -> bool { +# let mut n = 0; +# while n < v.len() { +# if !op(&v[n]) { +# return false; +# } +# n += 1; +# } +# return true; +# } each([2, 4, 8, 5, 16], |n| { if *n % 2 != 0 { println("found odd number!"); @@ -1656,7 +1661,16 @@ out of the loop, you just write `break`. To skip ahead to the next iteration, write `loop`. ~~~~ -# use each = std::vec::each; +# fn each(v: &[int], op: &fn(v: &int) -> bool) -> bool { +# let mut n = 0; +# while n < v.len() { +# if !op(&v[n]) { +# return false; +# } +# n += 1; +# } +# return true; +# } for each([2, 4, 8, 5, 16]) |n| { if *n % 2 != 0 { println("found odd number!"); @@ -1671,7 +1685,16 @@ normally allowed in closures, in a block that appears as the body of a the enclosing function, not just the loop body. ~~~~ -# use each = std::vec::each; +# fn each(v: &[int], op: &fn(v: &int) -> bool) -> bool { +# let mut n = 0; +# while n < v.len() { +# if !op(&v[n]) { +# return false; +# } +# n += 1; +# } +# return true; +# } fn contains(v: &[int], elt: int) -> bool { for each(v) |x| { if (*x == elt) { return true; } @@ -1686,7 +1709,16 @@ In these situations it can be convenient to lean on Rust's argument patterns to bind `x` to the actual value, not the pointer. ~~~~ -# use each = std::vec::each; +# fn each(v: &[int], op: &fn(v: &int) -> bool) -> bool { +# let mut n = 0; +# while n < v.len() { +# if !op(&v[n]) { +# return false; +# } +# n += 1; +# } +# return true; +# } # fn contains(v: &[int], elt: int) -> bool { for each(v) |&x| { if (x == elt) { return true; } @@ -1841,10 +1873,9 @@ vector consisting of the result of applying `function` to each element of `vector`: ~~~~ -# use std::vec; fn map(vector: &[T], function: &fn(v: &T) -> U) -> ~[U] { let mut accumulator = ~[]; - for vec::each(vector) |element| { + for vector.iter().advance |element| { accumulator.push(function(element)); } return accumulator; diff --git a/src/compiletest/runtest.rs b/src/compiletest/runtest.rs index fd56031ccf94..3e2f484ee53d 100644 --- a/src/compiletest/runtest.rs +++ b/src/compiletest/runtest.rs @@ -529,7 +529,7 @@ fn compose_and_run_compiler( let extra_link_args = ~[~"-L", aux_output_dir_name(config, testfile).to_str()]; - for vec::each(props.aux_builds) |rel_ab| { + for props.aux_builds.iter().advance |rel_ab| { let abs_ab = config.aux_base.push_rel(&Path(*rel_ab)); let aux_args = make_compile_args(config, props, ~[~"--lib"] + extra_link_args, diff --git a/src/libextra/arc.rs b/src/libextra/arc.rs index 32114f4037ec..c5fe07f21875 100644 --- a/src/libextra/arc.rs +++ b/src/libextra/arc.rs @@ -521,6 +521,7 @@ mod tests { use core::cell::Cell; use core::comm; use core::task; + use core::uint; #[test] fn manually_share_arc() { @@ -790,18 +791,20 @@ mod tests { } assert_eq!(*state, 42); *state = 31337; + // FIXME: #7372: hits type inference bug with iterators // send to other readers - for vec::each(reader_convos) |x| { - match *x { + for uint::range(0, reader_convos.len()) |i| { + match reader_convos[i] { (ref rc, _) => rc.send(()), } } } let read_mode = arc.downgrade(write_mode); do (&read_mode).read |state| { + // FIXME: #7372: hits type inference bug with iterators // complete handshake with other readers - for vec::each(reader_convos) |x| { - match *x { + for uint::range(0, reader_convos.len()) |i| { + match reader_convos[i] { (_, ref rp) => rp.recv(), } } diff --git a/src/libextra/getopts.rs b/src/libextra/getopts.rs index d97804722f25..9c416550eb78 100644 --- a/src/libextra/getopts.rs +++ b/src/libextra/getopts.rs @@ -418,10 +418,11 @@ pub fn opts_str(mm: &Matches, names: &[~str]) -> ~str { */ pub fn opt_strs(mm: &Matches, nm: &str) -> ~[~str] { let mut acc: ~[~str] = ~[]; - for vec::each(opt_vals(mm, nm)) |v| { + let r = opt_vals(mm, nm); + for r.iter().advance |v| { match *v { Val(ref s) => acc.push(copy *s), _ => () } } - return acc; + acc } /// Returns the string argument supplied to a matching option or none diff --git a/src/libextra/json.rs b/src/libextra/json.rs index 24c4c5b27c49..15553b035f65 100644 --- a/src/libextra/json.rs +++ b/src/libextra/json.rs @@ -1123,7 +1123,7 @@ impl Eq for Json { &Object(ref d1) => { if d0.len() == d1.len() { let mut equal = true; - for d0.each |k, v0| { + for d0.iter().advance |(k, v0)| { match d1.find(k) { Some(v1) if v0 == v1 => { }, _ => { equal = false; break } @@ -1186,12 +1186,12 @@ impl Ord for Json { let mut d1_flat = ~[]; // FIXME #4430: this is horribly inefficient... - for d0.each |k, v| { + for d0.iter().advance |(k, v)| { d0_flat.push((@copy *k, @copy *v)); } d0_flat.qsort(); - for d1.each |k, v| { + for d1.iter().advance |(k, v)| { d1_flat.push((@copy *k, @copy *v)); } d1_flat.qsort(); @@ -1326,7 +1326,7 @@ impl ToJson for ~[A] { impl ToJson for HashMap<~str, A> { fn to_json(&self) -> Json { let mut d = HashMap::new(); - for self.each |key, value| { + for self.iter().advance |(key, value)| { d.insert(copy *key, value.to_json()); } Object(~d) diff --git a/src/libextra/net_url.rs b/src/libextra/net_url.rs index dda4b85df4bf..5d3d31fdec47 100644 --- a/src/libextra/net_url.rs +++ b/src/libextra/net_url.rs @@ -207,7 +207,7 @@ pub fn encode_form_urlencoded(m: &HashMap<~str, ~[~str]>) -> ~str { let mut out = ~""; let mut first = true; - for m.each |key, values| { + for m.iter().advance |(key, values)| { let key = encode_plus(*key); for values.iter().advance |value| { diff --git a/src/libextra/serialize.rs b/src/libextra/serialize.rs index 34fd7e9f1ec1..345b217871cc 100644 --- a/src/libextra/serialize.rs +++ b/src/libextra/serialize.rs @@ -710,7 +710,7 @@ impl< fn encode(&self, e: &mut E) { do e.emit_map(self.len()) |e| { let mut i = 0; - for self.each |key, val| { + for self.iter().advance |(key, val)| { e.emit_map_elt_key(i, |e| key.encode(e)); e.emit_map_elt_val(i, |e| val.encode(e)); i += 1; @@ -744,7 +744,7 @@ impl< fn encode(&self, s: &mut S) { do s.emit_seq(self.len()) |s| { let mut i = 0; - for self.each |e| { + for self.iter().advance |e| { s.emit_seq_elt(i, |s| e.encode(s)); i += 1; } diff --git a/src/libextra/sync.rs b/src/libextra/sync.rs index 6990d35f0613..5cb52a7b9dfb 100644 --- a/src/libextra/sync.rs +++ b/src/libextra/sync.rs @@ -1094,7 +1094,8 @@ mod tests { }; assert!(result.is_err()); // child task must have finished by the time try returns - for vec::each(p.recv()) |p| { p.recv(); } // wait on all its siblings + let r = p.recv(); + for r.iter().advance |p| { p.recv(); } // wait on all its siblings do m.lock_cond |cond| { let woken = cond.broadcast(); assert_eq!(woken, 0); diff --git a/src/libextra/workcache.rs b/src/libextra/workcache.rs index ed675bf99e9d..a014293f0630 100644 --- a/src/libextra/workcache.rs +++ b/src/libextra/workcache.rs @@ -146,7 +146,7 @@ impl WorkMap { impl Encodable for WorkMap { fn encode(&self, s: &mut S) { let mut d = ~[]; - for self.each |k, v| { + for self.iter().advance |(k, v)| { d.push((copy *k, copy *v)) } sort::tim_sort(d); @@ -320,7 +320,7 @@ impl TPrep for Prep { } fn all_fresh(&self, cat: &str, map: &WorkMap) -> bool { - for map.each |k, v| { + for map.iter().advance |(k, v)| { if ! self.is_fresh(cat, k.kind, k.name, *v) { return false; } diff --git a/src/librustc/metadata/cstore.rs b/src/librustc/metadata/cstore.rs index c6c1ac720e8e..b0a955fef8f7 100644 --- a/src/librustc/metadata/cstore.rs +++ b/src/librustc/metadata/cstore.rs @@ -86,7 +86,7 @@ pub fn have_crate_data(cstore: &CStore, cnum: ast::crate_num) -> bool { pub fn iter_crate_data(cstore: &CStore, i: &fn(ast::crate_num, @crate_metadata)) { - for cstore.metas.each |&k, &v| { + for cstore.metas.iter().advance |(&k, &v)| { i(k, v); } } diff --git a/src/librustc/middle/kind.rs b/src/librustc/middle/kind.rs index 7f7a81fa974a..b0b2a16cf893 100644 --- a/src/librustc/middle/kind.rs +++ b/src/librustc/middle/kind.rs @@ -240,7 +240,8 @@ fn check_fn( // Check kinds on free variables: do with_appropriate_checker(cx, fn_id) |chk| { - for vec::each(*freevars::get_freevars(cx.tcx, fn_id)) |fv| { + let r = freevars::get_freevars(cx.tcx, fn_id); + for r.iter().advance |fv| { chk(cx, *fv); } } diff --git a/src/librustc/middle/lang_items.rs b/src/librustc/middle/lang_items.rs index d73b019c1ea7..9d4064e99bdb 100644 --- a/src/librustc/middle/lang_items.rs +++ b/src/librustc/middle/lang_items.rs @@ -436,7 +436,7 @@ impl LanguageItemCollector { } pub fn check_completeness(&self) { - for self.item_refs.each |&key, &item_ref| { + for self.item_refs.iter().advance |(&key, &item_ref)| { match self.items.items[item_ref] { None => { self.session.err(fmt!("no item found for `%s`", key)); diff --git a/src/librustc/middle/lint.rs b/src/librustc/middle/lint.rs index 5c36ab7750c8..6da10b7c2774 100644 --- a/src/librustc/middle/lint.rs +++ b/src/librustc/middle/lint.rs @@ -361,7 +361,7 @@ impl Context { } fn lint_to_str(&self, lint: lint) -> &'static str { - for self.dict.each |k, v| { + for self.dict.iter().advance |(k, v)| { if v.lint == lint { return *k; } @@ -742,7 +742,8 @@ fn check_item_ctypes(cx: &Context, it: @ast::item) { fn check_foreign_fn(cx: &Context, decl: &ast::fn_decl) { let tys = vec::map(decl.inputs, |a| a.ty ); - for vec::each(vec::append_one(tys, decl.output)) |ty| { + let r = vec::append_one(tys, decl.output); + for r.iter().advance |ty| { check_ty(cx, *ty); } } @@ -1171,7 +1172,7 @@ pub fn check_crate(tcx: ty::ctxt, crate: @ast::crate) { // If we missed any lints added to the session, then there's a bug somewhere // in the iteration code. - for tcx.sess.lints.each |_, v| { + for tcx.sess.lints.iter().advance |(_, v)| { for v.iter().advance |t| { match *t { (lint, span, ref msg) => diff --git a/src/librustc/middle/region.rs b/src/librustc/middle/region.rs index 0e6d8617ba42..7d3e895a0edd 100644 --- a/src/librustc/middle/region.rs +++ b/src/librustc/middle/region.rs @@ -948,7 +948,7 @@ pub fn determine_rp_in_crate(sess: Session, debug!("%s", { debug!("Region variance results:"); let region_paramd_items = cx.region_paramd_items; - for region_paramd_items.each |&key, &value| { + for region_paramd_items.iter().advance |(&key, &value)| { debug!("item %? (%s) is parameterized with variance %?", key, ast_map::node_id_to_str(ast_map, key, diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 3a54c224b523..096ab71e4246 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -1386,7 +1386,7 @@ impl Resolver { } let def_id = local_def(item.id); - for method_names.each |name, _| { + for method_names.iter().advance |(name, _)| { if !self.method_map.contains_key(name) { self.method_map.insert(*name, HashSet::new()); } @@ -1704,7 +1704,7 @@ impl Resolver { interned_method_names.insert(method_name); } } - for interned_method_names.each |name| { + for interned_method_names.iter().advance |name| { if !self.method_map.contains_key(name) { self.method_map.insert(*name, HashSet::new()); } @@ -2470,8 +2470,8 @@ impl Resolver { assert_eq!(containing_module.glob_count, 0); // Add all resolved imports from the containing module. - for containing_module.import_resolutions.each - |ident, target_import_resolution| { + for containing_module.import_resolutions.iter().advance + |(ident, target_import_resolution)| { debug!("(resolving glob import) writing module resolution \ %? into `%s`", @@ -2555,13 +2555,13 @@ impl Resolver { }; // Add all children from the containing module. - for containing_module.children.each |&ident, name_bindings| { + for containing_module.children.iter().advance |(&ident, name_bindings)| { merge_import_resolution(ident, *name_bindings); } // Add external module children from the containing module. - for containing_module.external_module_children.each - |&ident, module| { + for containing_module.external_module_children.iter().advance + |(&ident, module)| { let name_bindings = @mut Resolver::create_name_bindings_from_module(*module); merge_import_resolution(ident, name_bindings); @@ -3251,7 +3251,7 @@ impl Resolver { pub fn add_exports_for_module(@mut self, exports2: &mut ~[Export2], module_: @mut Module) { - for module_.children.each |ident, namebindings| { + for module_.children.iter().advance |(ident, namebindings)| { debug!("(computing exports) maybe export '%s'", self.session.str_of(*ident)); self.add_exports_of_namebindings(&mut *exports2, @@ -3266,7 +3266,7 @@ impl Resolver { false); } - for module_.import_resolutions.each |ident, importresolution| { + for module_.import_resolutions.iter().advance |(ident, importresolution)| { if importresolution.privacy != Public { debug!("(computing exports) not reexporting private `%s`", self.session.str_of(*ident)); @@ -4039,7 +4039,7 @@ impl Resolver { for arm.pats.iter().enumerate().advance |(i, p)| { let map_i = self.binding_mode_map(*p); - for map_0.each |&key, &binding_0| { + for map_0.iter().advance |(&key, &binding_0)| { match map_i.find(&key) { None => { self.session.span_err( @@ -4060,7 +4060,7 @@ impl Resolver { } } - for map_i.each |&key, &binding| { + for map_i.iter().advance |(&key, &binding)| { if !map_0.contains_key(&key) { self.session.span_err( binding.span, @@ -5355,7 +5355,7 @@ impl Resolver { } debug!("Import resolutions:"); - for module_.import_resolutions.each |name, import_resolution| { + for module_.import_resolutions.iter().advance |(name, import_resolution)| { let value_repr; match import_resolution.target_for_namespace(ValueNS) { None => { value_repr = ~""; } diff --git a/src/librustc/middle/trans/_match.rs b/src/librustc/middle/trans/_match.rs index 71b416ffe85f..63b39b8fe763 100644 --- a/src/librustc/middle/trans/_match.rs +++ b/src/librustc/middle/trans/_match.rs @@ -1673,7 +1673,7 @@ pub fn trans_match_inner(scope_cx: block, let mut arm_datas = ~[]; let mut matches = ~[]; - for vec::each(arms) |arm| { + for arms.iter().advance |arm| { let body = scope_block(bcx, arm.body.info(), "case_body"); let bindings_map = create_bindings_map(bcx, arm.pats[0]); let arm_data = @ArmData {bodycx: body, diff --git a/src/librustc/middle/trans/base.rs b/src/librustc/middle/trans/base.rs index 0e322c187af2..5bf0e596ca05 100644 --- a/src/librustc/middle/trans/base.rs +++ b/src/librustc/middle/trans/base.rs @@ -2945,7 +2945,7 @@ pub fn trans_crate(sess: session::Session, } if ccx.sess.count_llvm_insns() { - for ccx.stats.llvm_insns.each |&k, &v| { + for ccx.stats.llvm_insns.iter().advance |(&k, &v)| { io::println(fmt!("%-7u %s", v, k)); } } diff --git a/src/librustc/middle/trans/callee.rs b/src/librustc/middle/trans/callee.rs index 593d0beb88c7..cb4755506384 100644 --- a/src/librustc/middle/trans/callee.rs +++ b/src/librustc/middle/trans/callee.rs @@ -704,11 +704,11 @@ pub fn trans_args(cx: block, // now that all arguments have been successfully built, we can revoke any // temporary cleanups, as they are only needed if argument construction // should fail (for example, cleanup of copy mode args). - for vec::each(temp_cleanups) |c| { + for temp_cleanups.iter().advance |c| { revoke_clean(bcx, *c) } - return bcx; + bcx } pub enum AutorefArg { diff --git a/src/librustc/middle/trans/type_use.rs b/src/librustc/middle/trans/type_use.rs index f2446d1a1153..8cd776c99d69 100644 --- a/src/librustc/middle/trans/type_use.rs +++ b/src/librustc/middle/trans/type_use.rs @@ -213,7 +213,8 @@ pub fn type_needs_inner(cx: Context, ty::ty_enum(did, ref substs) => { if list::find(enums_seen, |id| *id == did).is_none() { let seen = @Cons(did, enums_seen); - for vec::each(*ty::enum_variants(cx.ccx.tcx, did)) |v| { + let r = ty::enum_variants(cx.ccx.tcx, did); + for r.iter().advance |v| { for v.args.iter().advance |aty| { let t = ty::subst(cx.ccx.tcx, &(*substs), *aty); type_needs_inner(cx, use_, t, seen); diff --git a/src/librustc/middle/typeck/infer/region_inference.rs b/src/librustc/middle/typeck/infer/region_inference.rs index d9add22479cc..0aad161a6788 100644 --- a/src/librustc/middle/typeck/infer/region_inference.rs +++ b/src/librustc/middle/typeck/infer/region_inference.rs @@ -1285,7 +1285,7 @@ impl RegionVarBindings { // It would be nice to write this using map(): let mut edges = vec::with_capacity(num_edges); - for self.constraints.each |constraint, span| { + for self.constraints.iter().advance |(constraint, span)| { edges.push(GraphEdge { next_edge: [uint::max_value, uint::max_value], constraint: *constraint, diff --git a/src/librustc/rustc.rs b/src/librustc/rustc.rs index 20705b3d7975..ca49d143d480 100644 --- a/src/librustc/rustc.rs +++ b/src/librustc/rustc.rs @@ -166,7 +166,7 @@ Available lint options: padded(max_key, "name"), "default", "meaning")); io::println(fmt!(" %s %7.7s %s\n", padded(max_key, "----"), "-------", "-------")); - for lint_dict.each |k, v| { + for lint_dict.iter().advance |(k, v)| { let k = k.replace("_", "-"); io::println(fmt!(" %s %7.7s %s", padded(max_key, k), diff --git a/src/librusti/program.rs b/src/librusti/program.rs index 91fde3e21ae0..f17777559deb 100644 --- a/src/librusti/program.rs +++ b/src/librusti/program.rs @@ -96,7 +96,7 @@ impl Program { code.push_str("fn main() {\n"); // It's easy to initialize things if we don't run things... - for self.local_vars.each |name, var| { + for self.local_vars.iter().advance |(name, var)| { let mt = var.mt(); code.push_str(fmt!("let%s %s: %s = fail!();\n", mt, *name, var.ty)); var.alter(*name, &mut code); @@ -149,7 +149,7 @@ impl Program { // Using this __tls_map handle, deserialize each variable binding that // we know about - for self.local_vars.each |name, var| { + for self.local_vars.iter().advance |(name, var)| { let mt = var.mt(); code.push_str(fmt!("let%s %s: %s = { let data = __tls_map.get_copy(&~\"%s\"); @@ -175,7 +175,7 @@ impl Program { // After the input code is run, we can re-serialize everything back out // into tls map (to be read later on by this task) - for self.local_vars.each |name, var| { + for self.local_vars.iter().advance |(name, var)| { code.push_str(fmt!("{ let local: %s = %s; let bytes = do ::std::io::with_bytes_writer |io| { @@ -237,7 +237,7 @@ impl Program { /// program starts pub fn set_cache(&self) { let map = @mut HashMap::new(); - for self.local_vars.each |name, value| { + for self.local_vars.iter().advance |(name, value)| { map.insert(copy *name, @copy value.data); } unsafe { diff --git a/src/libstd/hashmap.rs b/src/libstd/hashmap.rs index 962025915d24..bfa0f2fa124d 100644 --- a/src/libstd/hashmap.rs +++ b/src/libstd/hashmap.rs @@ -488,11 +488,6 @@ impl HashMap { } } - /// Visit all key-value pairs - pub fn each<'a>(&'a self, blk: &fn(&K, &'a V) -> bool) -> bool { - self.iter().advance(|(k, v)| blk(k, v)) - } - /// Visit all keys pub fn each_key(&self, blk: &fn(k: &K) -> bool) -> bool { self.iter().advance(|(k, _)| blk(k)) @@ -718,12 +713,6 @@ impl HashSet { self.map.contains_key_equiv(value) } - /// Visit all elements in arbitrary order - /// FIXME: #6978: Remove when all callers are converted - pub fn each(&self, f: &fn(&T) -> bool) -> bool { - self.iter().advance(f) - } - /// An iterator visiting all elements in arbitrary order. /// Iterator element type is &'a T. pub fn iter<'a>(&'a self) -> HashSetIterator<'a, T> { diff --git a/src/libstd/task/spawn.rs b/src/libstd/task/spawn.rs index 77053f396779..04c0dd79deda 100644 --- a/src/libstd/task/spawn.rs +++ b/src/libstd/task/spawn.rs @@ -111,7 +111,7 @@ fn taskset_remove(tasks: &mut TaskSet, task: *rust_task) { assert!(was_present); } pub fn taskset_each(tasks: &TaskSet, blk: &fn(v: *rust_task) -> bool) -> bool { - tasks.each(|k| blk(*k)) + tasks.iter().advance(|k| blk(*k)) } // One of these per group of linked-failure tasks. diff --git a/src/libstd/vec.rs b/src/libstd/vec.rs index 72b583078496..2e18a588fae3 100644 --- a/src/libstd/vec.rs +++ b/src/libstd/vec.rs @@ -444,7 +444,7 @@ pub fn partitioned(v: &[T], f: &fn(&T) -> bool) -> (~[T], ~[T]) { let mut lefts = ~[]; let mut rights = ~[]; - for each(v) |elt| { + for v.iter().advance |elt| { if f(elt) { lefts.push(copy *elt); } else { @@ -850,7 +850,7 @@ pub fn grow_set(v: &mut ~[T], index: uint, initval: &T, val: T) { /// Apply a function to each element of a vector and return the results pub fn map(v: &[T], f: &fn(t: &T) -> U) -> ~[U] { let mut result = with_capacity(v.len()); - for each(v) |elem| { + for v.iter().advance |elem| { result.push(f(elem)); } result @@ -886,7 +886,7 @@ pub fn mapi(v: &[T], f: &fn(uint, t: &T) -> U) -> ~[U] { */ pub fn flat_map(v: &[T], f: &fn(t: &T) -> ~[U]) -> ~[U] { let mut result = ~[]; - for each(v) |elem| { result.push_all_move(f(elem)); } + for v.iter().advance |elem| { result.push_all_move(f(elem)); } result } @@ -939,7 +939,7 @@ pub fn filter_mapped( */ let mut result = ~[]; - for each(v) |elem| { + for v.iter().advance |elem| { match f(elem) { None => {/* no-op */ } Some(result_elem) => { result.push(result_elem); } @@ -974,7 +974,7 @@ pub fn filter(v: ~[T], f: &fn(t: &T) -> bool) -> ~[T] { */ pub fn filtered(v: &[T], f: &fn(t: &T) -> bool) -> ~[T] { let mut result = ~[]; - for each(v) |elem| { + for v.iter().advance |elem| { if f(elem) { result.push(copy *elem); } } result @@ -1058,7 +1058,7 @@ impl<'self, T:Copy> VectorVector for &'self [&'self [T]] { /// Return true if a vector contains an element with the given value pub fn contains(v: &[T], x: &T) -> bool { - for each(v) |elt| { if *x == *elt { return true; } } + for v.iter().advance |elt| { if *x == *elt { return true; } } false } @@ -1209,7 +1209,7 @@ pub fn bsearch_elem(v: &[T], x: &T) -> Option { */ pub fn unzip_slice(v: &[(T, U)]) -> (~[T], ~[U]) { let mut (ts, us) = (~[], ~[]); - for each(v) |p| { + for v.iter().advance |p| { let (t, u) = copy *p; ts.push(t); us.push(u); @@ -1347,69 +1347,6 @@ pub fn reversed(v: &const [T]) -> ~[T] { rs } -/** - * Iterates over a vector, yielding each element to a closure. - * - * # Arguments - * - * * `v` - A vector, to be iterated over - * * `f` - A closure to do the iterating. Within this closure, return true to - * * continue iterating, false to break. - * - * # Examples - * - * ~~~ {.rust} - * [1,2,3].each(|&i| { - * io::println(int::str(i)); - * true - * }); - * ~~~ - * - * ~~~ {.rust} - * [1,2,3,4,5].each(|&i| { - * if i < 4 { - * io::println(int::str(i)); - * true - * } - * else { - * false - * } - * }); - * ~~~ - * - * You probably will want to use each with a `for`/`do` expression, depending - * on your iteration needs: - * - * ~~~ {.rust} - * for [1,2,3].each |&i| { - * io::println(int::str(i)); - * } - * ~~~ - */ -#[inline] -pub fn each<'r,T>(v: &'r [T], f: &fn(&'r T) -> bool) -> bool { - // ^^^^ - // NB---this CANNOT be &const [T]! The reason - // is that you are passing it to `f()` using - // an immutable. - - let mut broke = false; - do as_imm_buf(v) |p, n| { - let mut n = n; - let mut p = p; - while n > 0u { - unsafe { - let q = cast::copy_lifetime_vec(v, &*p); - if !f(q) { break; } - p = ptr::offset(p, 1u); - } - n -= 1u; - } - broke = n > 0; - } - return !broke; -} - /** * Iterate over all permutations of vector `v`. * @@ -3069,36 +3006,6 @@ mod tests { assert_eq!(v, ~[1, 3, 5]); } - #[test] - fn test_each_empty() { - for each::([]) |_v| { - fail!(); // should never be executed - } - } - - #[test] - fn test_each_nonempty() { - let mut i = 0; - for each([1, 2, 3]) |v| { - i += *v; - } - assert_eq!(i, 6); - } - - #[test] - fn test_each_ret_len0() { - let a0 : [int, .. 0] = []; - assert_eq!(each(a0, |_p| fail!()), true); - } - - #[test] - fn test_each_ret_len1() { - let a1 = [17]; - assert_eq!(each(a1, |_p| true), true); - assert_eq!(each(a1, |_p| false), false); - } - - #[test] fn test_each_permutation() { let mut results: ~[~[int]]; @@ -3854,21 +3761,6 @@ mod tests { }; } - #[test] - #[ignore(windows)] - #[should_fail] - fn test_each_fail() { - let v = [(~0, @0), (~0, @0), (~0, @0), (~0, @0)]; - let mut i = 0; - do each(v) |_elt| { - if i == 2 { - fail!() - } - i += 0; - false - }; - } - #[test] #[ignore(windows)] #[should_fail] diff --git a/src/test/bench/graph500-bfs.rs b/src/test/bench/graph500-bfs.rs index 14aa65219cd2..d21888f12ec6 100644 --- a/src/test/bench/graph500-bfs.rs +++ b/src/test/bench/graph500-bfs.rs @@ -86,7 +86,7 @@ fn make_graph(N: uint, edges: ~[(node_id, node_id)]) -> graph { HashSet::new() }; - for vec::each(edges) |e| { + for edges.iter().advance |e| { match *e { (i, j) => { graph[i].insert(j); @@ -441,7 +441,7 @@ fn main() { let stop = time::precise_time_s(); let mut total_edges = 0; - vec::each(graph, |edges| { total_edges += edges.len(); true }); + for graph.iter().advance |edges| { total_edges += edges.len(); } io::stdout().write_line(fmt!("Generated graph with %? edges in %? seconds.", total_edges / 2, diff --git a/src/test/bench/msgsend-pipes-shared.rs b/src/test/bench/msgsend-pipes-shared.rs index 7a9be7548849..102f7f170659 100644 --- a/src/test/bench/msgsend-pipes-shared.rs +++ b/src/test/bench/msgsend-pipes-shared.rs @@ -83,7 +83,7 @@ fn run(args: &[~str]) { server(&from_parent, &to_parent); } - for vec::each(worker_results) |r| { + for worker_results.iter().advance |r| { r.recv(); } diff --git a/src/test/bench/msgsend-pipes.rs b/src/test/bench/msgsend-pipes.rs index 796072c84858..b8d91bb93e2e 100644 --- a/src/test/bench/msgsend-pipes.rs +++ b/src/test/bench/msgsend-pipes.rs @@ -79,7 +79,7 @@ fn run(args: &[~str]) { server(&from_parent, &to_parent); } - for vec::each(worker_results) |r| { + for worker_results.iter().advance |r| { r.recv(); } diff --git a/src/test/bench/shootout-chameneos-redux.rs b/src/test/bench/shootout-chameneos-redux.rs index 3ff123b027ab..96c7e4e9b375 100644 --- a/src/test/bench/shootout-chameneos-redux.rs +++ b/src/test/bench/shootout-chameneos-redux.rs @@ -188,7 +188,7 @@ fn rendezvous(nn: uint, set: ~[color]) { // save each creature's meeting stats let mut report = ~[]; - for vec::each(to_creature) |_to_one| { + for to_creature.iter().advance |_to_one| { report.push(from_creatures_log.recv()); } @@ -196,7 +196,7 @@ fn rendezvous(nn: uint, set: ~[color]) { io::println(show_color_list(set)); // print each creature's stats - for vec::each(report) |rep| { + for report.iter().advance |rep| { io::println(*rep); } diff --git a/src/test/bench/shootout-k-nucleotide-pipes.rs b/src/test/bench/shootout-k-nucleotide-pipes.rs index c33c2258864f..20042aa0e918 100644 --- a/src/test/bench/shootout-k-nucleotide-pipes.rs +++ b/src/test/bench/shootout-k-nucleotide-pipes.rs @@ -56,7 +56,7 @@ fn sort_and_fmt(mm: &HashMap<~[u8], uint>, total: uint) -> ~str { let mut pairs = ~[]; // map -> [(k,%)] - for mm.each |&key, &val| { + for mm.iter().advance |(&key, &val)| { pairs.push((key, pct(val, total))); } diff --git a/src/test/compile-fail/block-must-not-have-result-for.rs b/src/test/compile-fail/block-must-not-have-result-for.rs index 778309122cba..1aa05a9477de 100644 --- a/src/test/compile-fail/block-must-not-have-result-for.rs +++ b/src/test/compile-fail/block-must-not-have-result-for.rs @@ -8,10 +8,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::vec; - fn main() { - for vec::each(~[0]) |_i| { //~ ERROR A for-loop body must return (), but + for 2.times { //~ ERROR A for-loop body must return (), but true } } diff --git a/src/test/compile-fail/borrowck-insert-during-each.rs b/src/test/compile-fail/borrowck-insert-during-each.rs index 1a0bec7d723b..189a0ef9d700 100644 --- a/src/test/compile-fail/borrowck-insert-during-each.rs +++ b/src/test/compile-fail/borrowck-insert-during-each.rs @@ -16,7 +16,7 @@ struct Foo { impl Foo { pub fn foo(&mut self, fun: &fn(&int)) { - for self.n.each |f| { + for self.n.iter().advance |f| { fun(f); } } diff --git a/src/test/compile-fail/issue-2151.rs b/src/test/compile-fail/issue-2151.rs index 8f4bbe4eabc7..5559ba344ed1 100644 --- a/src/test/compile-fail/issue-2151.rs +++ b/src/test/compile-fail/issue-2151.rs @@ -8,10 +8,7 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::vec; - fn main() { - for vec::each(fail!()) |i| { - let _ = i * 2; //~ ERROR the type of this value must be known - }; + let x = fail!(); + x.clone(); //~ ERROR the type of this value must be known in this context } diff --git a/src/test/compile-fail/liveness-issue-2163.rs b/src/test/compile-fail/liveness-issue-2163.rs index ec4f3f9a3fdb..fbb6d03b2200 100644 --- a/src/test/compile-fail/liveness-issue-2163.rs +++ b/src/test/compile-fail/liveness-issue-2163.rs @@ -12,7 +12,7 @@ use std::vec; fn main() { let a: ~[int] = ~[]; - vec::each(a, |_| -> bool { + a.iter().advance(|_| -> bool { //~^ ERROR mismatched types }); } diff --git a/src/test/run-pass/assignability-trait.rs b/src/test/run-pass/assignability-trait.rs index 5d2341ae42d3..b65b18e1ab3a 100644 --- a/src/test/run-pass/assignability-trait.rs +++ b/src/test/run-pass/assignability-trait.rs @@ -12,21 +12,19 @@ // making method calls, but only if there aren't any matches without // it. -use std::vec; - trait iterable { fn iterate(&self, blk: &fn(x: &A) -> bool) -> bool; } impl<'self,A> iterable for &'self [A] { fn iterate(&self, f: &fn(x: &A) -> bool) -> bool { - vec::each(*self, f) + self.iter().advance(f) } } impl iterable for ~[A] { fn iterate(&self, f: &fn(x: &A) -> bool) -> bool { - vec::each(*self, f) + self.iter().advance(f) } } diff --git a/src/test/run-pass/auto-loop.rs b/src/test/run-pass/auto-loop.rs index f148c509d4d0..185a5a6407c7 100644 --- a/src/test/run-pass/auto-loop.rs +++ b/src/test/run-pass/auto-loop.rs @@ -8,11 +8,10 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::vec; - pub fn main() { let mut sum = 0; - for vec::each(~[1, 2, 3, 4, 5]) |x| { + let xs = ~[1, 2, 3, 4, 5]; + for xs.iter().advance |x| { sum += *x; } assert_eq!(sum, 15); diff --git a/src/test/run-pass/block-arg.rs b/src/test/run-pass/block-arg.rs index d860c84dfcec..ff5d0e9f05c6 100644 --- a/src/test/run-pass/block-arg.rs +++ b/src/test/run-pass/block-arg.rs @@ -15,7 +15,7 @@ pub fn main() { let v = ~[-1f, 0f, 1f, 2f, 3f]; // Statement form does not require parentheses: - for vec::each(v) |i| { + for v.iter().advance |i| { info!("%?", *i); } diff --git a/src/test/run-pass/borrowck-mut-vec-as-imm-slice.rs b/src/test/run-pass/borrowck-mut-vec-as-imm-slice.rs index d63ebf7d24d4..8f74e6cdc299 100644 --- a/src/test/run-pass/borrowck-mut-vec-as-imm-slice.rs +++ b/src/test/run-pass/borrowck-mut-vec-as-imm-slice.rs @@ -8,12 +8,10 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -use std::vec; - fn want_slice(v: &[int]) -> int { let mut sum = 0; - for vec::each(v) |i| { sum += *i; } - return sum; + for v.iter().advance |i| { sum += *i; } + sum } fn has_mut_vec(v: ~[int]) -> int { diff --git a/src/test/run-pass/break.rs b/src/test/run-pass/break.rs index 2edb270762cc..85c6f90a742b 100644 --- a/src/test/run-pass/break.rs +++ b/src/test/run-pass/break.rs @@ -16,7 +16,8 @@ pub fn main() { assert_eq!(i, 10); loop { i += 1; if i == 20 { break; } } assert_eq!(i, 20); - for vec::each(~[1, 2, 3, 4, 5, 6]) |x| { + let xs = [1, 2, 3, 4, 5, 6]; + for xs.iter().advance |x| { if *x == 3 { break; } assert!((*x <= 3)); } i = 0; @@ -26,7 +27,8 @@ pub fn main() { i += 1; if i % 2 == 0 { loop; } assert!((i % 2 != 0)); if i >= 10 { break; } } - for vec::each(~[1, 2, 3, 4, 5, 6]) |x| { + let ys = ~[1, 2, 3, 4, 5, 6]; + for ys.iter().advance |x| { if *x % 2 == 0 { loop; } assert!((*x % 2 != 0)); } diff --git a/src/test/run-pass/const-vec-of-fns.rs b/src/test/run-pass/const-vec-of-fns.rs index 9fc68cd11275..a87d8f30e3ac 100644 --- a/src/test/run-pass/const-vec-of-fns.rs +++ b/src/test/run-pass/const-vec-of-fns.rs @@ -23,6 +23,6 @@ struct S<'self>(&'self fn()); static closures: &'static [S<'static>] = &[S(f), S(f)]; pub fn main() { - for std::vec::each(bare_fns) |&bare_fn| { bare_fn() } - for std::vec::each(closures) |&closure| { (*closure)() } + for bare_fns.iter().advance |&bare_fn| { bare_fn() } + for closures.iter().advance |&closure| { (*closure)() } } diff --git a/src/test/run-pass/for-destruct.rs b/src/test/run-pass/for-destruct.rs index 4926dbd00867..dd1cda22e653 100644 --- a/src/test/run-pass/for-destruct.rs +++ b/src/test/run-pass/for-destruct.rs @@ -8,10 +8,11 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. +// xfail-test: #3511: does not currently compile, due to rvalue issues + use std::vec; struct Pair { x: int, y: int } - pub fn main() { for vec::each(~[Pair {x: 10, y: 20}, Pair {x: 30, y: 0}]) |elt| { assert_eq!(elt.x + elt.y, 30); diff --git a/src/test/run-pass/rcvr-borrowed-to-slice.rs b/src/test/run-pass/rcvr-borrowed-to-slice.rs index 5eaf12f6a518..b62475ded54f 100644 --- a/src/test/run-pass/rcvr-borrowed-to-slice.rs +++ b/src/test/run-pass/rcvr-borrowed-to-slice.rs @@ -18,7 +18,7 @@ trait sum { impl<'self> sum for &'self [int] { fn sum(self) -> int { let mut sum = 0; - for vec::each(self) |e| { sum += *e; } + for self.iter().advance |e| { sum += *e; } return sum; } } diff --git a/src/test/run-pass/trait-generic.rs b/src/test/run-pass/trait-generic.rs index c25cdc85cb6a..dc6bdbf5c1a5 100644 --- a/src/test/run-pass/trait-generic.rs +++ b/src/test/run-pass/trait-generic.rs @@ -31,7 +31,10 @@ trait map { impl map for ~[T] { fn map(&self, f: &fn(&T) -> U) -> ~[U] { let mut r = ~[]; - for std::vec::each(*self) |x| { r += ~[f(x)]; } + // FIXME: #7355 generates bad code with Iterator + for std::uint::range(0, self.len()) |i| { + r += ~[f(&self[i])]; + } r } } From e44e33dfa999f4e3ce0b1811bc2ccdd5907b4a42 Mon Sep 17 00:00:00 2001 From: Daniel Micay Date: Tue, 25 Jun 2013 16:31:17 -0400 Subject: [PATCH 31/31] xfail test hitting a codegen bug (issue #7385) --- src/test/run-pass/const-vec-of-fns.rs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/test/run-pass/const-vec-of-fns.rs b/src/test/run-pass/const-vec-of-fns.rs index a87d8f30e3ac..45302363c380 100644 --- a/src/test/run-pass/const-vec-of-fns.rs +++ b/src/test/run-pass/const-vec-of-fns.rs @@ -8,7 +8,8 @@ // option. This file may not be copied, modified, or distributed // except according to those terms. -// xfail-fast +// xfail-test +// FIXME: #7385: hits a codegen bug on OS X x86_64 /*! * Try to double-check that static fns have the right size (with or