From e371d23486a5b42f41cd220ebef1689d49e3fe94 Mon Sep 17 00:00:00 2001 From: jatinn Date: Wed, 21 Jan 2015 21:53:43 -0500 Subject: [PATCH 01/50] add next/prev section links in the book -- using js --- src/rustbook/css.rs | 9 +++++++++ src/rustbook/javascript.rs | 31 +++++++++++++++++++++++++++++++ 2 files changed, 40 insertions(+) diff --git a/src/rustbook/css.rs b/src/rustbook/css.rs index 65ba031a2d634..74219bc9bfc38 100644 --- a/src/rustbook/css.rs +++ b/src/rustbook/css.rs @@ -46,6 +46,7 @@ body { margin-left: auto; margin-right:auto; max-width: 750px; + padding-bottom: 50px; } .chapter { @@ -123,4 +124,12 @@ body { padding: 0; } +.left { + float: left; +} + +.right { + float: right; +} + "#; diff --git a/src/rustbook/javascript.rs b/src/rustbook/javascript.rs index eb4401e1835a2..d34887d2b08b5 100644 --- a/src/rustbook/javascript.rs +++ b/src/rustbook/javascript.rs @@ -38,6 +38,37 @@ document.addEventListener("DOMContentLoaded", function(event) { el.className = classes.join(' '); } } + + // The below code is used to add prev and next navigation links to the bottom + // of each of the sections. + // It works by extracting the current page based on the url and iterates over + // the menu links until it finds the menu item for the current page. We then + // create a copy of the preceeding and following menu links and add the + // correct css class and insert them into the bottom of the page. + var toc = document.getElementById('toc').getElementsByTagName('a'); + var href = document.location.pathname.split('/').pop(); + if (href === 'index.html' || href === '') { + href = 'README.html'; + } + + for (var i = 0; i < toc.length; i++) { + if (toc[i].attributes['href'].value === href) { + var nav = document.createElement('p'); + if (i > 0) { + var prevNode = toc[i-1].cloneNode(true); + prevNode.className = 'left'; + nav.appendChild(prevNode); + } + if (i < toc.length - 1) { + var nextNode = toc[i+1].cloneNode(true); + nextNode.className = 'right'; + nav.appendChild(nextNode); + } + document.getElementById('page').appendChild(nav); + break; + } + } + }); "#; From ab5c3303bf607df944e2fb814800db61bf62663e Mon Sep 17 00:00:00 2001 From: Tshepang Lekhonkhobe Date: Fri, 23 Jan 2015 00:47:17 +0200 Subject: [PATCH 02/50] str: make replace() example more simple --- src/libcollections/str.rs | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/src/libcollections/str.rs b/src/libcollections/str.rs index 6608d0ee9a7ec..fc8b9727cbb05 100644 --- a/src/libcollections/str.rs +++ b/src/libcollections/str.rs @@ -435,12 +435,9 @@ pub trait StrExt: Index { /// # Examples /// /// ```rust - /// let s = "Do you know the muffin man, - /// The muffin man, the muffin man, ...".to_string(); + /// let s = "this is old"; /// - /// assert_eq!(s.replace("muffin man", "little lamb"), - /// "Do you know the little lamb, - /// The little lamb, the little lamb, ...".to_string()); + /// assert_eq!(s.replace("old", "new"), "this is new"); /// /// // not found, so no change. /// assert_eq!(s.replace("cookie monster", "little lamb"), s); From ec4981ece86769c768d61a914093a7a39192522c Mon Sep 17 00:00:00 2001 From: Vojtech Kral Date: Tue, 27 Jan 2015 03:38:07 +0100 Subject: [PATCH 03/50] Thread native name setting, fix #10302 --- src/libstd/sys/unix/thread.rs | 40 ++++++++++++++++++++++++++++++++ src/libstd/sys/windows/thread.rs | 7 ++++++ src/libstd/thread.rs | 4 ++++ 3 files changed, 51 insertions(+) diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index ac51b68795fbe..3c34e1f9dd4c0 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -17,6 +17,7 @@ use ptr; use libc::consts::os::posix01::{PTHREAD_CREATE_JOINABLE, PTHREAD_STACK_MIN}; use libc; use thunk::Thunk; +use ffi::CString; use sys_common::stack::RED_ZONE; use sys_common::thread::*; @@ -206,6 +207,29 @@ pub unsafe fn create(stack: uint, p: Thunk) -> rust_thread { native } +#[cfg(any(target_os = "linux", target_os = "android"))] +pub unsafe fn set_name(name: &str) { + // Using prctl() rather than pthread_setname_np(), + // because pthread_setname_np() wasn't added until glibc 2.12 + // PR_SET_NAME since Linux 2.6.9 + let cname = CString::from_slice(name.as_bytes()); + prctl(15i32 /* = PR_SET_NAME */, cname.as_ptr() as u64, 0u64, 0u64, 0u64); +} + +#[cfg(any(target_os = "freebsd", target_os = "dragonfly"))] +pub unsafe fn set_name(name: &str) { + // pthread_set_name_np() since almost forever on all BSDs + let cname = CString::from_slice(name.as_bytes()); + pthread_set_name_np(pthread_self(), cname.as_ptr()); +} + +#[cfg(target_os = "macos")] +pub unsafe fn set_name(name: &str) { + // pthread_setname_np() since OS X 10.6 + let cname = CString::from_slice(name.as_bytes()); + pthread_setname_np(cname.as_ptr()); +} + pub unsafe fn join(native: rust_thread) { assert_eq!(pthread_join(native, ptr::null_mut()), 0); } @@ -246,6 +270,15 @@ fn min_stack_size(_: *const libc::pthread_attr_t) -> libc::size_t { PTHREAD_STACK_MIN } +#[cfg(any(target_os = "linux", target_os = "android"))] +extern { + fn prctl(option: libc::c_int, + arg2: libc::c_ulong, + arg3: libc::c_ulong, + arg4: libc::c_ulong, + arg5: libc::c_ulong) -> libc::c_int; +} + #[cfg(any(target_os = "linux"))] extern { pub fn pthread_self() -> libc::pthread_t; @@ -258,11 +291,18 @@ extern { stacksize: *mut libc::size_t) -> libc::c_int; } +#[cfg(any(target_os = "freebsd", target_os = "dragonfly"))] +extern { + pub fn pthread_self() -> libc::pthread_t; + fn pthread_set_name_np(tid: libc::pthread_t, name: *const c_char); +} + #[cfg(target_os = "macos")] extern { pub fn pthread_self() -> libc::pthread_t; pub fn pthread_get_stackaddr_np(thread: libc::pthread_t) -> *mut libc::c_void; pub fn pthread_get_stacksize_np(thread: libc::pthread_t) -> libc::size_t; + fn pthread_setname_np(name: *const c_char) -> libc::c_int; } extern { diff --git a/src/libstd/sys/windows/thread.rs b/src/libstd/sys/windows/thread.rs index 30707488b30ee..b6027ea2e7e8e 100644 --- a/src/libstd/sys/windows/thread.rs +++ b/src/libstd/sys/windows/thread.rs @@ -67,6 +67,13 @@ pub unsafe fn create(stack: uint, p: Thunk) -> rust_thread { return ret; } +pub unsafe fn set_name(name: &str) { + // Windows threads are nameless + // The names in MSVC debugger are obtained using a "magic" exception, + // which requires a use of C++ macros. + // See https://msdn.microsoft.com/en-us/library/xcb2z8hs.aspx +} + pub unsafe fn join(native: rust_thread) { use libc::consts::os::extra::INFINITE; WaitForSingleObject(native, INFINITE); diff --git a/src/libstd/thread.rs b/src/libstd/thread.rs index a86b82b8c62ec..0cab7e69928df 100644 --- a/src/libstd/thread.rs +++ b/src/libstd/thread.rs @@ -275,6 +275,10 @@ impl Builder { unsafe { stack::record_os_managed_stack_bounds(my_stack_bottom, my_stack_top); } + match their_thread.name() { + Some(thename) => unsafe { imp::set_name(thename.as_slice()); }, + None => {} + } thread_info::set( (my_stack_bottom, my_stack_top), unsafe { imp::guard::current() }, From c155208de42de5761231726e35614b4499b5a137 Mon Sep 17 00:00:00 2001 From: Vojtech Kral Date: Tue, 27 Jan 2015 16:00:26 +0100 Subject: [PATCH 04/50] Thread native name setting, fix #10302 --- src/libstd/sys/unix/thread.rs | 4 ++-- src/libstd/sys/windows/thread.rs | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index 3c34e1f9dd4c0..1fba6bedc7c4a 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -223,9 +223,9 @@ pub unsafe fn set_name(name: &str) { pthread_set_name_np(pthread_self(), cname.as_ptr()); } -#[cfg(target_os = "macos")] +#[cfg(any(target_os = "macos", target_os = "ios"))] pub unsafe fn set_name(name: &str) { - // pthread_setname_np() since OS X 10.6 + // pthread_setname_np() since OS X 10.6 and iOS 3.2 let cname = CString::from_slice(name.as_bytes()); pthread_setname_np(cname.as_ptr()); } diff --git a/src/libstd/sys/windows/thread.rs b/src/libstd/sys/windows/thread.rs index b6027ea2e7e8e..a94adcb3bc7b9 100644 --- a/src/libstd/sys/windows/thread.rs +++ b/src/libstd/sys/windows/thread.rs @@ -67,10 +67,10 @@ pub unsafe fn create(stack: uint, p: Thunk) -> rust_thread { return ret; } -pub unsafe fn set_name(name: &str) { +pub unsafe fn set_name(_name: &str) { // Windows threads are nameless // The names in MSVC debugger are obtained using a "magic" exception, - // which requires a use of C++ macros. + // which requires a use of MS C++ extensions. // See https://msdn.microsoft.com/en-us/library/xcb2z8hs.aspx } From 093926e841df9a715f35d194846ad24134bafd2c Mon Sep 17 00:00:00 2001 From: Niko Matsakis Date: Tue, 27 Jan 2015 14:52:54 -0500 Subject: [PATCH 05/50] Check and extract bindings from trait definitions. Fixes #21636. --- src/librustc/middle/traits/project.rs | 40 +++++++++++++++++ .../associated-types-binding-in-trait.rs | 44 +++++++++++++++++++ 2 files changed, 84 insertions(+) create mode 100644 src/test/run-pass/associated-types-binding-in-trait.rs diff --git a/src/librustc/middle/traits/project.rs b/src/librustc/middle/traits/project.rs index ffb38091a8735..f15132937263d 100644 --- a/src/librustc/middle/traits/project.rs +++ b/src/librustc/middle/traits/project.rs @@ -401,6 +401,11 @@ fn project_type<'cx,'tcx>( &obligation_trait_ref, &mut candidates); + assemble_candidates_from_trait_def(selcx, + obligation, + &obligation_trait_ref, + &mut candidates); + if let Err(e) = assemble_candidates_from_impls(selcx, obligation, &obligation_trait_ref, @@ -446,6 +451,41 @@ fn assemble_candidates_from_param_env<'cx,'tcx>( candidate_set, env_predicates); } +/// In the case of a nested projection like <::FooT as Bar>::BarT, we may find +/// that the definition of `Foo` has some clues: +/// +/// ```rust +/// trait Foo { +/// type FooT : Bar +/// } +/// ``` +/// +/// Here, for example, we could conclude that the result is `i32`. +fn assemble_candidates_from_trait_def<'cx,'tcx>( + selcx: &mut SelectionContext<'cx,'tcx>, + obligation: &ProjectionTyObligation<'tcx>, + obligation_trait_ref: &Rc>, + candidate_set: &mut ProjectionTyCandidateSet<'tcx>) +{ + // Check whether the self-type is itself a projection. + let trait_ref = match obligation_trait_ref.self_ty().sty { + ty::ty_projection(ref data) => data.trait_ref.clone(), + ty::ty_infer(ty::TyVar(_)) => { + // If the self-type is an inference variable, then it MAY wind up + // being a projected type, so induce an ambiguity. + candidate_set.ambiguous = true; + return; + } + _ => { return; } + }; + + // If so, extract what we know from the trait and try to come up with a good answer. + let trait_def = ty::lookup_trait_def(selcx.tcx(), trait_ref.def_id); + let bounds = trait_def.generics.to_bounds(selcx.tcx(), trait_ref.substs); + assemble_candidates_from_predicates(selcx, obligation, obligation_trait_ref, + candidate_set, bounds.predicates.into_vec()); +} + fn assemble_candidates_from_predicates<'cx,'tcx>( selcx: &mut SelectionContext<'cx,'tcx>, obligation: &ProjectionTyObligation<'tcx>, diff --git a/src/test/run-pass/associated-types-binding-in-trait.rs b/src/test/run-pass/associated-types-binding-in-trait.rs new file mode 100644 index 0000000000000..b47b0109bdf39 --- /dev/null +++ b/src/test/run-pass/associated-types-binding-in-trait.rs @@ -0,0 +1,44 @@ +// Copyright 2015 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. + +// Test a case where the associated type binding (to `bool`, in this +// case) is derived from the trait definition. Issue #21636. + +use std::vec; + +pub trait BitIter { + type Iter: Iterator; + fn bit_iter(self) -> ::Iter; +} + +impl BitIter for Vec { + type Iter = vec::IntoIter; + fn bit_iter(self) -> ::Iter { + self.into_iter() + } +} + +fn count(arg: T) -> usize + where T: BitIter +{ + let mut sum = 0; + for i in arg.bit_iter() { + if i { + sum += 1; + } + } + sum +} + +fn main() { + let v = vec![true, false, true]; + let c = count(v); + assert_eq!(c, 2); +} From 83f8088108053efd2079d8ba8d677577685e8f6f Mon Sep 17 00:00:00 2001 From: Jonathan Reem Date: Tue, 27 Jan 2015 18:17:04 -0500 Subject: [PATCH 06/50] Add an implementation of Zeroable for Unique This allows the use of `NonZero>` for owned, non-null raw pointers. cc https://github.com/Gankro/collect-rs/pull/103 --- src/libcore/nonzero.rs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/libcore/nonzero.rs b/src/libcore/nonzero.rs index abaf252932300..53c866c39dd14 100644 --- a/src/libcore/nonzero.rs +++ b/src/libcore/nonzero.rs @@ -11,12 +11,14 @@ //! Exposes the NonZero lang item which provides optimization hints. use ops::Deref; +use ptr::Unique; /// Unsafe trait to indicate what types are usable with the NonZero struct pub unsafe trait Zeroable {} unsafe impl Zeroable for *const T {} unsafe impl Zeroable for *mut T {} +unsafe impl Zeroable for Unique { } unsafe impl Zeroable for int {} unsafe impl Zeroable for uint {} unsafe impl Zeroable for i8 {} From 76d66baf72ee075e7671286f513efb2ce9cc14bc Mon Sep 17 00:00:00 2001 From: Huon Wilson Date: Wed, 28 Jan 2015 20:20:55 +1100 Subject: [PATCH 07/50] Use unsigned comparison operators for unsigned SIMD types. Previously comparisons of SIMD types were always signed, even unsigned comparisons, meaning 0xFFFF_FFFF_u32 < 0 inside a SIMD vector. Fixes #21719. --- src/librustc_trans/trans/base.rs | 43 +++++++++++++++++++------------- src/test/run-pass/simd-binop.rs | 25 ++++++++++--------- 2 files changed, 38 insertions(+), 30 deletions(-) diff --git a/src/librustc_trans/trans/base.rs b/src/librustc_trans/trans/base.rs index 5a98bc4da3682..faca4ce4103df 100644 --- a/src/librustc_trans/trans/base.rs +++ b/src/librustc_trans/trans/base.rs @@ -623,7 +623,7 @@ pub fn compare_simd_types<'blk, 'tcx>( size: uint, op: ast::BinOp) -> ValueRef { - match t.sty { + let cmp = match t.sty { ty::ty_float(_) => { // The comparison operators for floating point vectors are challenging. // LLVM outputs a `< size x i1 >`, but if we perform a sign extension @@ -632,25 +632,32 @@ pub fn compare_simd_types<'blk, 'tcx>( cx.sess().bug("compare_simd_types: comparison operators \ not supported for floating point SIMD types") }, - ty::ty_uint(_) | ty::ty_int(_) => { - let cmp = match op.node { - ast::BiEq => llvm::IntEQ, - ast::BiNe => llvm::IntNE, - ast::BiLt => llvm::IntSLT, - ast::BiLe => llvm::IntSLE, - ast::BiGt => llvm::IntSGT, - ast::BiGe => llvm::IntSGE, - _ => cx.sess().bug("compare_simd_types: must be a comparison operator"), - }; - let return_ty = Type::vector(&type_of(cx.ccx(), t), size as u64); - // LLVM outputs an `< size x i1 >`, so we need to perform a sign extension - // to get the correctly sized type. This will compile to a single instruction - // once the IR is converted to assembly if the SIMD instruction is supported - // by the target architecture. - SExt(cx, ICmp(cx, cmp, lhs, rhs), return_ty) + ty::ty_uint(_) => match op.node { + ast::BiEq => llvm::IntEQ, + ast::BiNe => llvm::IntNE, + ast::BiLt => llvm::IntULT, + ast::BiLe => llvm::IntULE, + ast::BiGt => llvm::IntUGT, + ast::BiGe => llvm::IntUGE, + _ => cx.sess().bug("compare_simd_types: must be a comparison operator"), + }, + ty::ty_int(_) => match op.node { + ast::BiEq => llvm::IntEQ, + ast::BiNe => llvm::IntNE, + ast::BiLt => llvm::IntSLT, + ast::BiLe => llvm::IntSLE, + ast::BiGt => llvm::IntSGT, + ast::BiGe => llvm::IntSGE, + _ => cx.sess().bug("compare_simd_types: must be a comparison operator"), }, _ => cx.sess().bug("compare_simd_types: invalid SIMD type"), - } + }; + let return_ty = Type::vector(&type_of(cx.ccx(), t), size as u64); + // LLVM outputs an `< size x i1 >`, so we need to perform a sign extension + // to get the correctly sized type. This will compile to a single instruction + // once the IR is converted to assembly if the SIMD instruction is supported + // by the target architecture. + SExt(cx, ICmp(cx, cmp, lhs, rhs), return_ty) } // Iterates through the elements of a structural type. diff --git a/src/test/run-pass/simd-binop.rs b/src/test/run-pass/simd-binop.rs index 482eea19823f1..779e507f43dfd 100644 --- a/src/test/run-pass/simd-binop.rs +++ b/src/test/run-pass/simd-binop.rs @@ -55,17 +55,18 @@ pub fn main() { // comparison operators - assert!(eq_u32x4(u32x4(1, 2, 3, 4) == u32x4(3, 2, 1, 0), u32x4(0, !0, 0, 0))); - assert!(eq_u32x4(u32x4(1, 2, 3, 4) != u32x4(3, 2, 1, 0), u32x4(!0, 0, !0, !0))); - assert!(eq_u32x4(u32x4(1, 2, 3, 4) < u32x4(3, 2, 1, 0), u32x4(!0, 0, 0, 0))); - assert!(eq_u32x4(u32x4(1, 2, 3, 4) <= u32x4(3, 2, 1, 0), u32x4(!0, !0, 0, 0))); - assert!(eq_u32x4(u32x4(1, 2, 3, 4) >= u32x4(3, 2, 1, 0), u32x4(0, !0, !0, !0))); - assert!(eq_u32x4(u32x4(1, 2, 3, 4) > u32x4(3, 2, 1, 0), u32x4(0, 0, !0, !0))); + // check !0/-1 to ensure operators are using the correct signedness. + assert!(eq_u32x4(u32x4(1, 2, 3, !0) == u32x4(3, 2, 1, 0), u32x4(0, !0, 0, 0))); + assert!(eq_u32x4(u32x4(1, 2, 3, !0) != u32x4(3, 2, 1, 0), u32x4(!0, 0, !0, !0))); + assert!(eq_u32x4(u32x4(1, 2, 3, !0) < u32x4(3, 2, 1, 0), u32x4(!0, 0, 0, 0))); + assert!(eq_u32x4(u32x4(1, 2, 3, !0) <= u32x4(3, 2, 1, 0), u32x4(!0, !0, 0, 0))); + assert!(eq_u32x4(u32x4(1, 2, 3, !0) >= u32x4(3, 2, 1, 0), u32x4(0, !0, !0, !0))); + assert!(eq_u32x4(u32x4(1, 2, 3, !0) > u32x4(3, 2, 1, 0), u32x4(0, 0, !0, !0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) == i32x4(3, 2, 1, 0), i32x4(0, !0, 0, 0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) != i32x4(3, 2, 1, 0), i32x4(!0, 0, !0, !0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) < i32x4(3, 2, 1, 0), i32x4(!0, 0, 0, 0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) <= i32x4(3, 2, 1, 0), i32x4(!0, !0, 0, 0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) >= i32x4(3, 2, 1, 0), i32x4(0, !0, !0, !0))); - assert!(eq_i32x4(i32x4(1, 2, 3, 4) > i32x4(3, 2, 1, 0), i32x4(0, 0, !0, !0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) == i32x4(3, 2, 1, 0), i32x4(0, !0, 0, 0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) != i32x4(3, 2, 1, 0), i32x4(!0, 0, !0, !0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) < i32x4(3, 2, 1, 0), i32x4(!0, 0, 0, !0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) <= i32x4(3, 2, 1, 0), i32x4(!0, !0, 0, !0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) >= i32x4(3, 2, 1, 0), i32x4(0, !0, !0, 0))); + assert!(eq_i32x4(i32x4(1, 2, 3, -1) > i32x4(3, 2, 1, 0), i32x4(0, 0, !0, 0))); } From 33a3d6d88f76bfae770983ee50e36e23cc4c7655 Mon Sep 17 00:00:00 2001 From: Vojtech Kral Date: Wed, 28 Jan 2015 13:48:27 +0100 Subject: [PATCH 08/50] Thread native name setting, fix #10302 --- src/libstd/sys/common/thread_info.rs | 4 ++++ src/libstd/sys/unix/thread.rs | 29 ++++++++++++++-------------- src/libstd/thread.rs | 4 ---- 3 files changed, 18 insertions(+), 19 deletions(-) diff --git a/src/libstd/sys/common/thread_info.rs b/src/libstd/sys/common/thread_info.rs index 92b936e74f654..7c9758ca9242d 100644 --- a/src/libstd/sys/common/thread_info.rs +++ b/src/libstd/sys/common/thread_info.rs @@ -56,6 +56,10 @@ pub fn stack_guard() -> uint { pub fn set(stack_bounds: (uint, uint), stack_guard: uint, thread: Thread) { THREAD_INFO.with(|c| assert!(c.borrow().is_none())); + match thread.name() { + Some(name) => unsafe { ::sys::thread::set_name(name.as_slice()); }, + None => {} + } THREAD_INFO.with(move |c| *c.borrow_mut() = Some(ThreadInfo{ stack_bounds: stack_bounds, stack_guard: stack_guard, diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index 1fba6bedc7c4a..59c2badaf626e 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -209,11 +209,19 @@ pub unsafe fn create(stack: uint, p: Thunk) -> rust_thread { #[cfg(any(target_os = "linux", target_os = "android"))] pub unsafe fn set_name(name: &str) { - // Using prctl() rather than pthread_setname_np(), - // because pthread_setname_np() wasn't added until glibc 2.12 - // PR_SET_NAME since Linux 2.6.9 + // pthread_setname_np() since glibc 2.12 + // availability autodetected via weak linkage let cname = CString::from_slice(name.as_bytes()); - prctl(15i32 /* = PR_SET_NAME */, cname.as_ptr() as u64, 0u64, 0u64, 0u64); + type F = unsafe extern "C" fn(libc::pthread_t, *const libc::c_char) -> libc::c_int; + extern { + #[linkage = "extern_weak"] + static pthread_setname_np: *const (); + } + if !pthread_setname_np.is_null() { + unsafe { + mem::transmute::<*const (), F>(pthread_setname_np)(pthread_self(), cname.as_ptr()); + } + } } #[cfg(any(target_os = "freebsd", target_os = "dragonfly"))] @@ -270,15 +278,6 @@ fn min_stack_size(_: *const libc::pthread_attr_t) -> libc::size_t { PTHREAD_STACK_MIN } -#[cfg(any(target_os = "linux", target_os = "android"))] -extern { - fn prctl(option: libc::c_int, - arg2: libc::c_ulong, - arg3: libc::c_ulong, - arg4: libc::c_ulong, - arg5: libc::c_ulong) -> libc::c_int; -} - #[cfg(any(target_os = "linux"))] extern { pub fn pthread_self() -> libc::pthread_t; @@ -294,7 +293,7 @@ extern { #[cfg(any(target_os = "freebsd", target_os = "dragonfly"))] extern { pub fn pthread_self() -> libc::pthread_t; - fn pthread_set_name_np(tid: libc::pthread_t, name: *const c_char); + fn pthread_set_name_np(tid: libc::pthread_t, name: *const libc::c_char); } #[cfg(target_os = "macos")] @@ -302,7 +301,7 @@ extern { pub fn pthread_self() -> libc::pthread_t; pub fn pthread_get_stackaddr_np(thread: libc::pthread_t) -> *mut libc::c_void; pub fn pthread_get_stacksize_np(thread: libc::pthread_t) -> libc::size_t; - fn pthread_setname_np(name: *const c_char) -> libc::c_int; + fn pthread_setname_np(name: *const libc::c_char) -> libc::c_int; } extern { diff --git a/src/libstd/thread.rs b/src/libstd/thread.rs index 0cab7e69928df..a86b82b8c62ec 100644 --- a/src/libstd/thread.rs +++ b/src/libstd/thread.rs @@ -275,10 +275,6 @@ impl Builder { unsafe { stack::record_os_managed_stack_bounds(my_stack_bottom, my_stack_top); } - match their_thread.name() { - Some(thename) => unsafe { imp::set_name(thename.as_slice()); }, - None => {} - } thread_info::set( (my_stack_bottom, my_stack_top), unsafe { imp::guard::current() }, From 7e67eba180eb2efb09e1487020a9a160335e7926 Mon Sep 17 00:00:00 2001 From: Vojtech Kral Date: Wed, 28 Jan 2015 14:01:14 +0100 Subject: [PATCH 09/50] Thread native name setting, fix #10302 --- src/libstd/sys/unix/thread.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index 59c2badaf626e..d8e281bf5abbc 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -296,7 +296,7 @@ extern { fn pthread_set_name_np(tid: libc::pthread_t, name: *const libc::c_char); } -#[cfg(target_os = "macos")] +#[cfg(any(target_os = "macos", target_os = "ios"))] extern { pub fn pthread_self() -> libc::pthread_t; pub fn pthread_get_stackaddr_np(thread: libc::pthread_t) -> *mut libc::c_void; From 9ee972ca32b1f91eb6880e1bc9c8bb5a4faf1f29 Mon Sep 17 00:00:00 2001 From: Vojtech Kral Date: Wed, 28 Jan 2015 16:52:53 +0100 Subject: [PATCH 10/50] Thread native name setting, fix #10302 --- src/libstd/sys/unix/thread.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/sys/unix/thread.rs b/src/libstd/sys/unix/thread.rs index d8e281bf5abbc..26a450b8599df 100644 --- a/src/libstd/sys/unix/thread.rs +++ b/src/libstd/sys/unix/thread.rs @@ -278,7 +278,7 @@ fn min_stack_size(_: *const libc::pthread_attr_t) -> libc::size_t { PTHREAD_STACK_MIN } -#[cfg(any(target_os = "linux"))] +#[cfg(any(target_os = "linux", target_os = "android"))] extern { pub fn pthread_self() -> libc::pthread_t; pub fn pthread_getattr_np(native: libc::pthread_t, From ca0e83cdeca6c0fc43d8e8017174e6531da4406e Mon Sep 17 00:00:00 2001 From: Michael Neumann Date: Thu, 29 Jan 2015 01:56:59 +0100 Subject: [PATCH 11/50] Fix wrong use std::io -> old_io --- src/libstd/sys/unix/os.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/sys/unix/os.rs b/src/libstd/sys/unix/os.rs index 5d5cda03f01a0..dd343baa7c9c3 100644 --- a/src/libstd/sys/unix/os.rs +++ b/src/libstd/sys/unix/os.rs @@ -196,7 +196,7 @@ pub fn load_self() -> Option> { #[cfg(target_os = "dragonfly")] pub fn load_self() -> Option> { - use std::io; + use old_io; match old_io::fs::readlink(&Path::new("/proc/curproc/file")) { Ok(path) => Some(path.into_vec()), From 26276f475134ca58a9872e175f964e4512f75d1a Mon Sep 17 00:00:00 2001 From: Steven Fackler Date: Wed, 28 Jan 2015 20:12:00 -0800 Subject: [PATCH 12/50] Fix up check to bypass internal buffer We don't care about how much space the allocation has, but the actual usable space in the buffer. --- src/libstd/old_io/buffered.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libstd/old_io/buffered.rs b/src/libstd/old_io/buffered.rs index 1590598c0b8a7..586cc1477f8dd 100644 --- a/src/libstd/old_io/buffered.rs +++ b/src/libstd/old_io/buffered.rs @@ -111,7 +111,7 @@ impl Buffer for BufferedReader { impl Reader for BufferedReader { fn read(&mut self, buf: &mut [u8]) -> IoResult { - if self.pos == self.cap && buf.len() >= self.buf.capacity() { + if self.pos == self.cap && buf.len() >= self.buf.len() { return self.inner.read(buf); } let nread = { From 017b3a543182006fa64bdc8c721969ae38c125f9 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Wed, 28 Jan 2015 23:56:49 -0500 Subject: [PATCH 13/50] Pull configs out into individual repositories As we grow, these don't belong in-tree. http://internals.rust-lang.org/t/moving-editor-highlighting-into-their-own-repos/1395 * https://github.com/rust-lang/rust.vim * https://github.com/rust-lang/rust-mode * https://github.com/rust-lang/gedit-config * https://github.com/rust-lang/kate-config * https://github.com/rust-lang/nano-config * https://github.com/rust-lang/zsh-config --- src/etc/emacs/README.md | 79 -- src/etc/emacs/run_rust_emacs_tests.sh | 14 - src/etc/emacs/rust-mode-tests.el | 896 ------------------ src/etc/emacs/rust-mode.el | 520 ---------- src/etc/gedit/readme.txt | 10 - .../language-specs/rust.lang | 340 ------- src/etc/gedit/share/mime/packages/rust.xml | 6 - src/etc/kate/rust.xml | 304 ------ src/etc/nano/rust.nanorc | 35 - src/etc/vim/after/syntax/rust.vim | 31 - src/etc/vim/autoload/rust.vim | 225 ----- src/etc/vim/compiler/cargo.vim | 65 -- src/etc/vim/compiler/rustc.vim | 33 - src/etc/vim/doc/rust.txt | 178 ---- src/etc/vim/ftdetect/rust.vim | 1 - src/etc/vim/ftplugin/rust.vim | 150 --- src/etc/vim/indent/rust.vim | 196 ---- src/etc/vim/plugin/rust.vim | 22 - src/etc/vim/syntax/rust.vim | 262 ----- src/etc/vim/syntax_checkers/rust/rustc.vim | 35 - src/etc/zsh/_rust | 215 ----- 21 files changed, 3617 deletions(-) delete mode 100644 src/etc/emacs/README.md delete mode 100755 src/etc/emacs/run_rust_emacs_tests.sh delete mode 100644 src/etc/emacs/rust-mode-tests.el delete mode 100644 src/etc/emacs/rust-mode.el delete mode 100644 src/etc/gedit/readme.txt delete mode 100644 src/etc/gedit/share/gtksourceview-3.0/language-specs/rust.lang delete mode 100644 src/etc/gedit/share/mime/packages/rust.xml delete mode 100644 src/etc/kate/rust.xml delete mode 100644 src/etc/nano/rust.nanorc delete mode 100644 src/etc/vim/after/syntax/rust.vim delete mode 100644 src/etc/vim/autoload/rust.vim delete mode 100644 src/etc/vim/compiler/cargo.vim delete mode 100644 src/etc/vim/compiler/rustc.vim delete mode 100644 src/etc/vim/doc/rust.txt delete mode 100644 src/etc/vim/ftdetect/rust.vim delete mode 100644 src/etc/vim/ftplugin/rust.vim delete mode 100644 src/etc/vim/indent/rust.vim delete mode 100644 src/etc/vim/plugin/rust.vim delete mode 100644 src/etc/vim/syntax/rust.vim delete mode 100644 src/etc/vim/syntax_checkers/rust/rustc.vim delete mode 100644 src/etc/zsh/_rust diff --git a/src/etc/emacs/README.md b/src/etc/emacs/README.md deleted file mode 100644 index 24470c258b375..0000000000000 --- a/src/etc/emacs/README.md +++ /dev/null @@ -1,79 +0,0 @@ -`rust-mode`: A major Emacs mode for editing Rust source code -============================================================ - -`rust-mode` makes editing [Rust](http://rust-lang.org) code with Emacs -enjoyable. - - -### Manual Installation - -To install manually, check out this repository and add this to your -`.emacs` file: - -```lisp -(add-to-list 'load-path "/path/to/rust-mode/") -(autoload 'rust-mode "rust-mode" nil t) -(add-to-list 'auto-mode-alist '("\\.rs\\'" . rust-mode)) -``` - -This associates `rust-mode` with `.rs` files. To enable it explicitly, do -M-x rust-mode. - -### `package.el` installation via Marmalade or MELPA - -It can be more convenient to use Emacs's package manager to handle -installation for you if you use many elisp libraries. If you have -`package.el` but haven't added Marmalade or MELPA, the community -package source, yet, add this to `~/.emacs.d/init.el`: - -Using Marmalade: - -```lisp -(require 'package) -(add-to-list 'package-archives - '("marmalade" . "http://marmalade-repo.org/packages/")) -(package-initialize) -``` - -Using MELPA: - -```lisp -(require 'package) -(add-to-list 'package-archives - '("melpa" . "http://melpa.milkbox.net/packages/") t) -(package-initialize) -``` - -Then do this to load the package listing: - -* M-x eval-buffer -* M-x package-refresh-contents - -If you use a version of Emacs prior to 24 that doesn't include -`package.el`, you can get it from [here](http://bit.ly/pkg-el23). - -If you have an older ELPA `package.el` installed from tromey.com, you -should upgrade in order to support installation from multiple sources. -The ELPA archive is deprecated and no longer accepting new packages, -so the version there (1.7.1) is very outdated. - -#### Install `rust-mode` - -One you have `package.el`, you can install `rust-mode` or any other -modes by choosing them from a list: - -* M-x package-list-packages - -Now, to install packages, move your cursor to them and press -i. This will mark the packages for installation. When -you're done with marking, press x, and ELPA will install -the packages for you (under `~/.emacs.d/elpa/`). - -* or using M-x package-install rust-mode - -### Tests via ERT - -The file `rust-mode-tests.el` contains tests that can be run via -[ERT](http://www.gnu.org/software/emacs/manual/html_node/ert/index.html). -You can use `run_rust_emacs_tests.sh` to run them in batch mode, if -Emacs is somewhere in your `$PATH`. diff --git a/src/etc/emacs/run_rust_emacs_tests.sh b/src/etc/emacs/run_rust_emacs_tests.sh deleted file mode 100755 index b35fcf870c4d3..0000000000000 --- a/src/etc/emacs/run_rust_emacs_tests.sh +++ /dev/null @@ -1,14 +0,0 @@ -#!/bin/sh -# Copyright 2014 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. -# -# This runs the test for emacs rust-mode. -# It must be possible to find emacs via PATH. -emacs -batch -l rust-mode.el -l rust-mode-tests.el -f ert-run-tests-batch-and-exit diff --git a/src/etc/emacs/rust-mode-tests.el b/src/etc/emacs/rust-mode-tests.el deleted file mode 100644 index f255dbf15071b..0000000000000 --- a/src/etc/emacs/rust-mode-tests.el +++ /dev/null @@ -1,896 +0,0 @@ -;;; rust-mode-tests.el --- ERT tests for rust-mode.el - -(require 'rust-mode) -(require 'ert) -(require 'cl) - -(setq rust-test-fill-column 32) - -(defun rust-compare-code-after-manip (original point-pos manip-func expected got) - (equal expected got)) - -(defun rust-test-explain-bad-manip (original point-pos manip-func expected got) - (if (equal expected got) - nil - (list - ;; The (goto-char) and (insert) business here is just for - ;; convenience--after an error, you can copy-paste that into emacs eval to - ;; insert the bare strings into a buffer - "Rust code was manipulated wrong after:" - `(insert ,original) - `(goto-char ,point-pos) - 'expected `(insert ,expected) - 'got `(insert ,got) - (loop for i from 0 to (max (length original) (length expected)) - for oi = (if (< i (length got)) (elt got i)) - for ei = (if (< i (length expected)) (elt expected i)) - while (equal oi ei) - finally return `(first-difference-at - (goto-char ,(+ 1 i)) - expected ,(char-to-string ei) - got ,(char-to-string oi)))))) -(put 'rust-compare-code-after-manip 'ert-explainer - 'rust-test-explain-bad-manip) - -(defun rust-test-manip-code (original point-pos manip-func expected) - (with-temp-buffer - (rust-mode) - (insert original) - (goto-char point-pos) - (funcall manip-func) - (should (rust-compare-code-after-manip - original point-pos manip-func expected (buffer-string))))) - -(defun test-fill-paragraph (unfilled expected &optional start-pos end-pos) - "We're going to run through many scenarios here--the point should be able to be anywhere from the start-pos (defaults to 1) through end-pos (defaults to the length of what was passed in) and (fill-paragraph) should return the same result. - -Also, the result should be the same regardless of whether the code is at the beginning or end of the file. (If you're not careful, that can make a difference.) So we test each position given above with the passed code at the beginning, the end, neither and both. So we do this a total of (end-pos - start-pos)*4 times. Oy." - (let* ((start-pos (or start-pos 1)) - (end-pos (or end-pos (length unfilled))) - (padding "\n \n") - (padding-len (length padding))) - (loop - for pad-at-beginning from 0 to 1 - do (loop for pad-at-end from 0 to 1 - with padding-beginning = (if (= 0 pad-at-beginning) "" padding) - with padding-end = (if (= 0 pad-at-end) "" padding) - with padding-adjust = (* padding-len pad-at-beginning) - with padding-beginning = (if (= 0 pad-at-beginning) "" padding) - with padding-end = (if (= 0 pad-at-end) "" padding) - ;; If we're adding space to the beginning, and our start position - ;; is at the very beginning, we want to test within the added space. - ;; Otherwise adjust the start and end for the beginning padding. - with start-pos = (if (= 1 start-pos) 1 (+ padding-adjust start-pos)) - with end-pos = (+ end-pos padding-adjust) - do (loop for pos from start-pos to end-pos - do (rust-test-manip-code - (concat padding-beginning unfilled padding-end) - pos - (lambda () - (let ((fill-column rust-test-fill-column)) - (fill-paragraph))) - (concat padding-beginning expected padding-end))))))) - -(ert-deftest fill-paragraph-top-level-multi-line-style-doc-comment-second-line () - (test-fill-paragraph - "/** - * This is a very very very very very very very long string - */" - "/** - * This is a very very very very - * very very very long string - */")) - - -(ert-deftest fill-paragraph-top-level-multi-line-style-doc-comment-first-line () - (test-fill-paragraph - "/** This is a very very very very very very very long string - */" - "/** This is a very very very - * very very very very long - * string - */")) - -(ert-deftest fill-paragraph-multi-paragraph-multi-line-style-doc-comment () - (let - ((multi-paragraph-unfilled - "/** - * This is the first really really really really really really really long paragraph - * - * This is the second really really really really really really long paragraph - */")) - (test-fill-paragraph - multi-paragraph-unfilled - "/** - * This is the first really - * really really really really - * really really long paragraph - * - * This is the second really really really really really really long paragraph - */" - 1 89) - (test-fill-paragraph - multi-paragraph-unfilled - "/** - * This is the first really really really really really really really long paragraph - * - * This is the second really - * really really really really - * really long paragraph - */" - 90))) - -(ert-deftest fill-paragraph-multi-paragraph-single-line-style-doc-comment () - (let - ((multi-paragraph-unfilled - "/// This is the first really really really really really really really long paragraph -/// -/// This is the second really really really really really really long paragraph")) - (test-fill-paragraph - multi-paragraph-unfilled - "/// This is the first really -/// really really really really -/// really really long paragraph -/// -/// This is the second really really really really really really long paragraph" - 1 86) - (test-fill-paragraph - multi-paragraph-unfilled - "/// This is the first really really really really really really really long paragraph -/// -/// This is the second really -/// really really really really -/// really long paragraph" - 87))) - -(ert-deftest fill-paragraph-multi-paragraph-single-line-style-indented () - (test-fill-paragraph - " // This is the first really really really really really really really long paragraph - // - // This is the second really really really really really really long paragraph" - " // This is the first really - // really really really - // really really really - // long paragraph - // - // This is the second really really really really really really long paragraph" 1 89)) - -(ert-deftest fill-paragraph-multi-line-style-inner-doc-comment () - (test-fill-paragraph - "/*! This is a very very very very very very very long string - */" - "/*! This is a very very very - * very very very very long - * string - */")) - -(ert-deftest fill-paragraph-single-line-style-inner-doc-comment () - (test-fill-paragraph - "//! This is a very very very very very very very long string" - "//! This is a very very very -//! very very very very long -//! string")) - -(ert-deftest fill-paragraph-prefixless-multi-line-doc-comment () - (test-fill-paragraph - "/** -This is my summary. Blah blah blah blah blah. Dilly dally dilly dally dilly dally doo. - -This is some more text. Fee fie fo fum. Humpty dumpty sat on a wall. -*/" - "/** -This is my summary. Blah blah -blah blah blah. Dilly dally -dilly dally dilly dally doo. - -This is some more text. Fee fie fo fum. Humpty dumpty sat on a wall. -*/" 4 90)) - -(ert-deftest fill-paragraph-with-no-space-after-star-prefix () - (test-fill-paragraph - "/** - *This is a very very very very very very very long string - */" - "/** - *This is a very very very very - *very very very long string - */")) - -(ert-deftest fill-paragraph-single-line-style-with-code-before () - (test-fill-paragraph - "fn foo() { } -/// This is my comment. This is more of my comment. This is even more." - "fn foo() { } -/// This is my comment. This is -/// more of my comment. This is -/// even more." 14)) - -(ert-deftest fill-paragraph-single-line-style-with-code-after () - (test-fill-paragraph - "/// This is my comment. This is more of my comment. This is even more. -fn foo() { }" - "/// This is my comment. This is -/// more of my comment. This is -/// even more. -fn foo() { }" 1 73)) - -(ert-deftest fill-paragraph-single-line-style-code-before-and-after () - (test-fill-paragraph - "fn foo() { } -/// This is my comment. This is more of my comment. This is even more. -fn bar() { }" - "fn foo() { } -/// This is my comment. This is -/// more of my comment. This is -/// even more. -fn bar() { }" 14 67)) - -(defun test-auto-fill (initial position inserted expected) - (rust-test-manip-code - initial - position - (lambda () - (unwind-protect - (progn - (let ((fill-column rust-test-fill-column)) - (auto-fill-mode) - (goto-char position) - (insert inserted) - (syntax-ppss-flush-cache 1) - (funcall auto-fill-function))) - (auto-fill-mode t))) - expected)) - -(ert-deftest auto-fill-multi-line-doc-comment () - (test-auto-fill - "/** - * - */" - 8 - "This is a very very very very very very very long string" - "/** - * This is a very very very very - * very very very long string - */")) - -(ert-deftest auto-fill-single-line-doc-comment () - (test-auto-fill - "/// This is the first really -/// really really really really -/// really really long paragraph -/// -/// " - 103 - "This is the second really really really really really really long paragraph" - "/// This is the first really -/// really really really really -/// really really long paragraph -/// -/// This is the second really -/// really really really really -/// really long paragraph" - )) - -(ert-deftest auto-fill-multi-line-prefixless () - (test-auto-fill - "/* - - */" - 4 - "This is a very very very very very very very long string" - "/* -This is a very very very very -very very very long string - */" - )) - -(defun test-indent (indented) - (let ((deindented (replace-regexp-in-string "^[[:blank:]]*" " " indented))) - (rust-test-manip-code - deindented - 1 - (lambda () (indent-region 1 (buffer-size))) - indented))) - - -(ert-deftest indent-struct-fields-aligned () - (test-indent - " -struct Foo { bar: int, - baz: int } - -struct Blah {x:int, - y:int, - z:String")) - -(ert-deftest indent-doc-comments () - (test-indent - " -/** - * This is a doc comment - * - */ - -/// So is this - -fn foo() { - /*! - * this is a nested doc comment - */ - - //! And so is this -}")) - -(ert-deftest indent-inside-braces () - (test-indent - " -// struct fields out one level: -struct foo { - a:int, - // comments too - b:char -} - -fn bar(x:Box) { // comment here should not affect the next indent - bla(); - bla(); -}")) - -(ert-deftest indent-top-level () - (test-indent - " -// Everything here is at the top level and should not be indented -#[attrib] -mod foo; - -pub static bar = Quux{a: b()} - -use foo::bar::baz; - -fn foo() { } -")) - -(ert-deftest indent-params-no-align () - (test-indent - " -// Indent out one level because no params appear on the first line -fn xyzzy( - a:int, - b:char) { } - -fn abcdef( - a:int, - b:char) - -> char -{ }")) - -(ert-deftest indent-params-align () - (test-indent - " -// Align the second line of params to the first -fn foo(a:int, - b:char) { } - -fn bar( a:int, - b:char) - -> int -{ } - -fn baz( a:int, // should work with a comment here - b:char) - -> int -{ } -")) - -(ert-deftest indent-square-bracket-alignment () - (test-indent - " -fn args_on_the_next_line( // with a comment - a:int, - b:String) { - let aaaaaa = [ - 1, - 2, - 3]; - let bbbbbbb = [1, 2, 3, - 4, 5, 6]; - let ccc = [ 10, 9, 8, - 7, 6, 5]; -} -")) - -(ert-deftest indent-nested-fns () - (test-indent - " -fn nexted_fns(a: fn(b:int, - c:char) - -> int, - d: int) - -> uint -{ - 0 -} -" - )) - -(ert-deftest indent-multi-line-expr () - (test-indent - " -fn foo() -{ - x(); - let a = - b(); -} -" - )) - -(ert-deftest indent-match () - (test-indent - " -fn foo() { - match blah { - Pattern => stuff(), - _ => whatever - } -} -" - )) - -(ert-deftest indent-match-multiline-pattern () - (test-indent - " -fn foo() { - match blah { - Pattern | - Pattern2 => { - hello() - }, - _ => whatever - } -} -" - )) - -(ert-deftest indent-indented-match () - (test-indent - " -fn foo() { - let x = - match blah { - Pattern | - Pattern2 => { - hello() - }, - _ => whatever - }; - y(); -} -" - )) - -(ert-deftest indent-curly-braces-within-parens () - (test-indent - " -fn foo() { - let x = - foo(bar(|x| { - only_one_indent_here(); - })); - y(); -} -" - )) - -(ert-deftest indent-weirdly-indented-block () - (rust-test-manip-code - " -fn foo() { - { -this_block_is_over_to_the_left_for_some_reason(); - } - -} -" - 16 - #'indent-for-tab-command - " -fn foo() { - { - this_block_is_over_to_the_left_for_some_reason(); - } - -} -" - )) - -(ert-deftest indent-multi-line-attrib () - (test-indent - " -#[attrib( - this, - that, - theotherthing)] -fn function_with_multiline_attribute() {} -" - )) - - -;; Make sure that in effort to cover match patterns we don't mistreat || or expressions -(ert-deftest indent-nonmatch-or-expression () - (test-indent - " -fn foo() { - let x = foo() || - bar(); -} -" - )) - -(setq rust-test-motion-string - " -fn fn1(arg: int) -> bool { - let x = 5; - let y = b(); - true -} - -fn fn2(arg: int) -> bool { - let x = 5; - let y = b(); - true -} - -pub fn fn3(arg: int) -> bool { - let x = 5; - let y = b(); - true -} - -struct Foo { - x: int -} -" - rust-test-region-string rust-test-motion-string - rust-test-indent-motion-string - " -fn blank_line(arg:int) -> bool { - -} - -fn indenting_closing_brace() { - if(true) { -} -} - -fn indenting_middle_of_line() { - if(true) { - push_me_out(); -} else { - pull_me_back_in(); -} -} - -fn indented_already() { - - // The previous line already has its spaces -} -" - - ;; Symbol -> (line column) - rust-test-positions-alist '((start-of-fn1 (2 0)) - (start-of-fn1-middle-of-line (2 15)) - (middle-of-fn1 (3 7)) - (end-of-fn1 (6 0)) - (between-fn1-fn2 (7 0)) - (start-of-fn2 (8 0)) - (middle-of-fn2 (10 4)) - (before-start-of-fn1 (1 0)) - (after-end-of-fn2 (13 0)) - (beginning-of-fn3 (14 0)) - (middle-of-fn3 (16 4)) - (middle-of-struct (21 10)) - (before-start-of-struct (19 0)) - (after-end-of-struct (23 0)) - (blank-line-indent-start (3 0)) - (blank-line-indent-target (3 4)) - (closing-brace-indent-start (8 1)) - (closing-brace-indent-target (8 5)) - (middle-push-indent-start (13 2)) - (middle-push-indent-target (13 9)) - (after-whitespace-indent-start (13 1)) - (after-whitespace-indent-target (13 8)) - (middle-pull-indent-start (15 19)) - (middle-pull-indent-target (15 12)) - (blank-line-indented-already-bol-start (20 0)) - (blank-line-indented-already-bol-target (20 4)) - (blank-line-indented-already-middle-start (20 2)) - (blank-line-indented-already-middle-target (20 4)) - (nonblank-line-indented-already-bol-start (21 0)) - (nonblank-line-indented-already-bol-target (21 4)) - (nonblank-line-indented-already-middle-start (21 2)) - (nonblank-line-indented-already-middle-target (21 4)))) - -(defun rust-get-buffer-pos (pos-symbol) - "Get buffer position from POS-SYMBOL. - -POS-SYMBOL is a symbol found in `rust-test-positions-alist'. -Convert the line-column information from that list into a buffer position value." - (interactive "P") - (pcase-let ((`(,line ,column) (cadr (assoc pos-symbol rust-test-positions-alist)))) - (save-excursion - (goto-line line) - (move-to-column column) - (point)))) - -;;; FIXME: Maybe add an ERT explainer function (something that shows the -;;; surrounding code of the final point, not just the position). -(defun rust-test-motion (source-code init-pos final-pos manip-func &optional &rest args) - "Test that MANIP-FUNC moves point from INIT-POS to FINAL-POS. - -If ARGS are provided, send them to MANIP-FUNC. - -INIT-POS, FINAL-POS are position symbols found in `rust-test-positions-alist'." - (with-temp-buffer - (rust-mode) - (insert source-code) - (goto-char (rust-get-buffer-pos init-pos)) - (apply manip-func args) - (should (equal (point) (rust-get-buffer-pos final-pos))))) - -(defun rust-test-region (source-code init-pos reg-beg reg-end manip-func &optional &rest args) - "Test that MANIP-FUNC marks region from REG-BEG to REG-END. - -INIT-POS is the initial position of point. -If ARGS are provided, send them to MANIP-FUNC. -All positions are position symbols found in `rust-test-positions-alist'." - (with-temp-buffer - (rust-mode) - (insert source-code) - (goto-char (rust-get-buffer-pos init-pos)) - (apply manip-func args) - (should (equal (list (region-beginning) (region-end)) - (list (rust-get-buffer-pos reg-beg) - (rust-get-buffer-pos reg-end)))))) - -(ert-deftest rust-beginning-of-defun-from-middle-of-fn () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn1 - 'start-of-fn1 - #'beginning-of-defun)) - -(ert-deftest rust-beginning-of-defun-from-end () - (rust-test-motion - rust-test-motion-string - 'end-of-fn1 - 'start-of-fn1 - #'beginning-of-defun)) - -(ert-deftest rust-beginning-of-defun-before-open-brace () - (rust-test-motion - rust-test-motion-string - 'start-of-fn1-middle-of-line - 'start-of-fn1 - #'beginning-of-defun)) - -(ert-deftest rust-beginning-of-defun-between-fns () - (rust-test-motion - rust-test-motion-string - 'between-fn1-fn2 - 'start-of-fn1 - #'beginning-of-defun)) - -(ert-deftest rust-beginning-of-defun-with-arg () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn2 - 'start-of-fn1 - #'beginning-of-defun 2)) - -(ert-deftest rust-beginning-of-defun-with-negative-arg () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn1 - 'beginning-of-fn3 - #'beginning-of-defun -2)) - -(ert-deftest rust-beginning-of-defun-pub-fn () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn3 - 'beginning-of-fn3 - #'beginning-of-defun)) - -(ert-deftest rust-end-of-defun-from-middle-of-fn () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn1 - 'between-fn1-fn2 - #'end-of-defun)) - -(ert-deftest rust-end-of-defun-from-beg () - (rust-test-motion - rust-test-motion-string - 'start-of-fn1 - 'between-fn1-fn2 - #'end-of-defun)) - -(ert-deftest rust-end-of-defun-before-open-brace () - (rust-test-motion - rust-test-motion-string - 'start-of-fn1-middle-of-line - 'between-fn1-fn2 - #'end-of-defun)) - -(ert-deftest rust-end-of-defun-between-fns () - (rust-test-motion - rust-test-motion-string - 'between-fn1-fn2 - 'after-end-of-fn2 - #'end-of-defun)) - -(ert-deftest rust-end-of-defun-with-arg () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn1 - 'after-end-of-fn2 - #'end-of-defun 2)) - -(ert-deftest rust-end-of-defun-with-negative-arg () - (rust-test-motion - rust-test-motion-string - 'middle-of-fn3 - 'between-fn1-fn2 - #'end-of-defun -2)) - -(ert-deftest rust-mark-defun-from-middle-of-fn () - (rust-test-region - rust-test-region-string - 'middle-of-fn2 - 'between-fn1-fn2 'after-end-of-fn2 - #'mark-defun)) - -(ert-deftest rust-mark-defun-from-end () - (rust-test-region - rust-test-region-string - 'end-of-fn1 - 'before-start-of-fn1 'between-fn1-fn2 - #'mark-defun)) - -(ert-deftest rust-mark-defun-start-of-defun () - (rust-test-region - rust-test-region-string - 'start-of-fn2 - 'between-fn1-fn2 'after-end-of-fn2 - #'mark-defun)) - -(ert-deftest rust-mark-defun-from-middle-of-struct () - (rust-test-region - rust-test-region-string - 'middle-of-struct - 'before-start-of-struct 'after-end-of-struct - #'mark-defun)) - -(ert-deftest indent-line-blank-line-motion () - (rust-test-motion - rust-test-indent-motion-string - 'blank-line-indent-start - 'blank-line-indent-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-closing-brace-motion () - (rust-test-motion - rust-test-indent-motion-string - 'closing-brace-indent-start - 'closing-brace-indent-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-middle-push-motion () - (rust-test-motion - rust-test-indent-motion-string - 'middle-push-indent-start - 'middle-push-indent-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-after-whitespace-motion () - (rust-test-motion - rust-test-indent-motion-string - 'after-whitespace-indent-start - 'after-whitespace-indent-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-middle-pull-motion () - (rust-test-motion - rust-test-indent-motion-string - 'middle-pull-indent-start - 'middle-pull-indent-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-blank-line-indented-already-bol () - (rust-test-motion - rust-test-indent-motion-string - 'blank-line-indented-already-bol-start - 'blank-line-indented-already-bol-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-blank-line-indented-already-middle () - (rust-test-motion - rust-test-indent-motion-string - 'blank-line-indented-already-middle-start - 'blank-line-indented-already-middle-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-nonblank-line-indented-already-bol () - (rust-test-motion - rust-test-indent-motion-string - 'nonblank-line-indented-already-bol-start - 'nonblank-line-indented-already-bol-target - #'indent-for-tab-command)) - -(ert-deftest indent-line-nonblank-line-indented-already-middle () - (rust-test-motion - rust-test-indent-motion-string - 'nonblank-line-indented-already-middle-start - 'nonblank-line-indented-already-middle-target - #'indent-for-tab-command)) - -(defun rust-test-fontify-string (str) - (with-temp-buffer - (rust-mode) - (insert str) - (font-lock-fontify-buffer) - (buffer-string))) - -(defun rust-test-group-str-by-face (str) - "Fontify `STR' in rust-mode and group it by face, returning a -list of substrings of `STR' each followed by its face." - (cl-loop with fontified = (rust-test-fontify-string str) - for start = 0 then end - while start - for end = (next-single-property-change start 'face fontified) - for prop = (get-text-property start 'face fontified) - for text = (substring-no-properties fontified start end) - if prop - append (list text prop))) - -(defun rust-test-font-lock (source face-groups) - "Test that `SOURCE' fontifies to the expected `FACE-GROUPS'" - (should (equal (rust-test-group-str-by-face source) - face-groups))) - -(ert-deftest font-lock-attribute-simple () - (rust-test-font-lock - "#[foo]" - '("#[foo]" font-lock-preprocessor-face))) - -(ert-deftest font-lock-attribute-inner () - (rust-test-font-lock - "#![foo]" - '("#![foo]" font-lock-preprocessor-face))) - -(ert-deftest font-lock-attribute-key-value () - (rust-test-font-lock - "#[foo = \"bar\"]" - '("#[foo = " font-lock-preprocessor-face - "\"bar\"" font-lock-string-face - "]" font-lock-preprocessor-face))) - -(ert-deftest font-lock-attribute-around-comment () - (rust-test-font-lock - "#[foo /* bar */]" - '("#[foo " font-lock-preprocessor-face - "/* " font-lock-comment-delimiter-face - "bar */" font-lock-comment-face - "]" font-lock-preprocessor-face))) - -(ert-deftest font-lock-attribute-inside-string () - (rust-test-font-lock - "\"#[foo]\"" - '("\"#[foo]\"" font-lock-string-face))) - -(ert-deftest font-lock-attribute-inside-comment () - (rust-test-font-lock - "/* #[foo] */" - '("/* " font-lock-comment-delimiter-face - "#[foo] */" font-lock-comment-face))) diff --git a/src/etc/emacs/rust-mode.el b/src/etc/emacs/rust-mode.el deleted file mode 100644 index dae685f3a540a..0000000000000 --- a/src/etc/emacs/rust-mode.el +++ /dev/null @@ -1,520 +0,0 @@ -;;; rust-mode.el --- A major emacs mode for editing Rust source code - -;; Version: 0.2.0 -;; Author: Mozilla -;; Url: https://github.com/rust-lang/rust -;; Keywords: languages - -;;; Commentary: -;; - -;;; Code: - -(eval-when-compile (require 'misc)) - -;; for GNU Emacs < 24.3 -(eval-when-compile - (unless (fboundp 'setq-local) - (defmacro setq-local (var val) - "Set variable VAR to value VAL in current buffer." - (list 'set (list 'make-local-variable (list 'quote var)) val)))) - -;; Syntax definitions and helpers -(defvar rust-mode-syntax-table - (let ((table (make-syntax-table))) - - ;; Operators - (dolist (i '(?+ ?- ?* ?/ ?& ?| ?^ ?! ?< ?> ?~ ?@)) - (modify-syntax-entry i "." table)) - - ;; Strings - (modify-syntax-entry ?\" "\"" table) - (modify-syntax-entry ?\\ "\\" table) - - ;; mark _ as a word constituent so that identifiers - ;; such as xyz_type don't cause type to be highlighted - ;; as a keyword - (modify-syntax-entry ?_ "w" table) - - ;; Comments - (modify-syntax-entry ?/ ". 124b" table) - (modify-syntax-entry ?* ". 23" table) - (modify-syntax-entry ?\n "> b" table) - (modify-syntax-entry ?\^m "> b" table) - - table)) - -(defgroup rust-mode nil - "Support for Rust code." - :link '(url-link "http://www.rust-lang.org/") - :group 'languages) - -(defcustom rust-indent-offset 4 - "Indent Rust code by this number of spaces." - :type 'integer - :group 'rust-mode) - -(defcustom rust-indent-method-chain nil - "Indent Rust method chains, aligned by the '.' operators" - :type 'boolean - :group 'rust-mode) - -(defun rust-paren-level () (nth 0 (syntax-ppss))) -(defun rust-in-str-or-cmnt () (nth 8 (syntax-ppss))) -(defun rust-rewind-past-str-cmnt () (goto-char (nth 8 (syntax-ppss)))) -(defun rust-rewind-irrelevant () - (let ((starting (point))) - (skip-chars-backward "[:space:]\n") - (if (looking-back "\\*/") (backward-char)) - (if (rust-in-str-or-cmnt) - (rust-rewind-past-str-cmnt)) - (if (/= starting (point)) - (rust-rewind-irrelevant)))) - -(defun rust-align-to-expr-after-brace () - (save-excursion - (forward-char) - ;; We don't want to indent out to the open bracket if the - ;; open bracket ends the line - (when (not (looking-at "[[:blank:]]*\\(?://.*\\)?$")) - (when (looking-at "[[:space:]]") - (forward-word 1) - (backward-word 1)) - (current-column)))) - -(defun rust-align-to-method-chain () - (save-excursion - (previous-line) - (end-of-line) - (backward-word 1) - (backward-char) - (when (looking-at "\\..+\(.*\)\n") - (- (current-column) rust-indent-offset)))) - -(defun rust-rewind-to-beginning-of-current-level-expr () - (let ((current-level (rust-paren-level))) - (back-to-indentation) - (while (> (rust-paren-level) current-level) - (backward-up-list) - (back-to-indentation)))) - -(defun rust-mode-indent-line () - (interactive) - (let ((indent - (save-excursion - (back-to-indentation) - ;; Point is now at beginning of current line - (let* ((level (rust-paren-level)) - (baseline - ;; Our "baseline" is one level out from the indentation of the expression - ;; containing the innermost enclosing opening bracket. That - ;; way if we are within a block that has a different - ;; indentation than this mode would give it, we still indent - ;; the inside of it correctly relative to the outside. - (if (= 0 level) - 0 - (or - (when rust-indent-method-chain - (rust-align-to-method-chain)) - (save-excursion - (backward-up-list) - (rust-rewind-to-beginning-of-current-level-expr) - (+ (current-column) rust-indent-offset)))))) - (cond - ;; A function return type is indented to the corresponding function arguments - ((looking-at "->") - (save-excursion - (backward-list) - (or (rust-align-to-expr-after-brace) - (+ baseline rust-indent-offset)))) - - ;; A closing brace is 1 level unindended - ((looking-at "}") (- baseline rust-indent-offset)) - - ;;Line up method chains by their .'s - ((when (and rust-indent-method-chain - (looking-at "\..+\(.*\);?\n")) - (or - (let ((method-indent (rust-align-to-method-chain))) - (when method-indent - (+ method-indent rust-indent-offset))) - (+ baseline rust-indent-offset)))) - - - ;; Doc comments in /** style with leading * indent to line up the *s - ((and (nth 4 (syntax-ppss)) (looking-at "*")) - (+ 1 baseline)) - - ;; If we're in any other token-tree / sexp, then: - (t - (or - ;; If we are inside a pair of braces, with something after the - ;; open brace on the same line and ending with a comma, treat - ;; it as fields and align them. - (when (> level 0) - (save-excursion - (rust-rewind-irrelevant) - (backward-up-list) - ;; Point is now at the beginning of the containing set of braces - (rust-align-to-expr-after-brace))) - - (progn - (back-to-indentation) - ;; Point is now at the beginning of the current line - (if (or - ;; If this line begins with "else" or "{", stay on the - ;; baseline as well (we are continuing an expression, - ;; but the "else" or "{" should align with the beginning - ;; of the expression it's in.) - (looking-at "\\\\|{") - - (save-excursion - (rust-rewind-irrelevant) - ;; Point is now at the end of the previous ine - (or - ;; If we are at the first line, no indentation is needed, so stay at baseline... - (= 1 (line-number-at-pos (point))) - ;; ..or if the previous line ends with any of these: - ;; { ? : ( , ; [ } - ;; then we are at the beginning of an expression, so stay on the baseline... - (looking-back "[(,:;?[{}]\\|[^|]|") - ;; or if the previous line is the end of an attribute, stay at the baseline... - (progn (rust-rewind-to-beginning-of-current-level-expr) (looking-at "#"))))) - baseline - - ;; Otherwise, we are continuing the same expression from the previous line, - ;; so add one additional indent level - (+ baseline rust-indent-offset)))))))))) - - ;; If we're at the beginning of the line (before or at the current - ;; indentation), jump with the indentation change. Otherwise, save the - ;; excursion so that adding the indentations will leave us at the - ;; equivalent position within the line to where we were before. - (if (<= (current-column) (current-indentation)) - (indent-line-to indent) - (save-excursion (indent-line-to indent))))) - - -;; Font-locking definitions and helpers -(defconst rust-mode-keywords - '("as" - "box" "break" - "const" "continue" "crate" - "do" - "else" "enum" "extern" - "false" "fn" "for" - "if" "impl" "in" - "let" "loop" - "match" "mod" "move" "mut" - "priv" "pub" - "ref" "return" - "self" "static" "struct" "super" - "true" "trait" "type" - "unsafe" "use" - "virtual" - "where" "while")) - -(defconst rust-special-types - '("u8" "i8" - "u16" "i16" - "u32" "i32" - "u64" "i64" - - "f32" "f64" - "float" "int" "uint" "isize" "usize" - "bool" - "str" "char")) - -(defconst rust-re-ident "[[:word:][:multibyte:]_][[:word:][:multibyte:]_[:digit:]]*") -(defconst rust-re-CamelCase "[[:upper:]][[:word:][:multibyte:]_[:digit:]]*") -(defun rust-re-word (inner) (concat "\\<" inner "\\>")) -(defun rust-re-grab (inner) (concat "\\(" inner "\\)")) -(defun rust-re-grabword (inner) (rust-re-grab (rust-re-word inner))) -(defun rust-re-item-def (itype) - (concat (rust-re-word itype) "[[:space:]]+" (rust-re-grab rust-re-ident))) - -(defvar rust-mode-font-lock-keywords - (append - `( - ;; Keywords proper - (,(regexp-opt rust-mode-keywords 'words) . font-lock-keyword-face) - - ;; Special types - (,(regexp-opt rust-special-types 'words) . font-lock-type-face) - - ;; Attributes like `#[bar(baz)]` or `#![bar(baz)]` or `#[bar = "baz"]` - (,(rust-re-grab (concat "#\\!?\\[" rust-re-ident "[^]]*\\]")) - 1 font-lock-preprocessor-face keep) - - ;; Syntax extension invocations like `foo!`, highlight including the ! - (,(concat (rust-re-grab (concat rust-re-ident "!")) "[({[:space:][]") - 1 font-lock-preprocessor-face) - - ;; Field names like `foo:`, highlight excluding the : - (,(concat (rust-re-grab rust-re-ident) ":[^:]") 1 font-lock-variable-name-face) - - ;; Module names like `foo::`, highlight including the :: - (,(rust-re-grab (concat rust-re-ident "::")) 1 font-lock-type-face) - - ;; Lifetimes like `'foo` - (,(concat "'" (rust-re-grab rust-re-ident) "[^']") 1 font-lock-variable-name-face) - - ;; Character constants, since they're not treated as strings - ;; in order to have sufficient leeway to parse 'lifetime above. - (,(rust-re-grab "'[^']'") 1 font-lock-string-face) - (,(rust-re-grab "'\\\\[nrt]'") 1 font-lock-string-face) - (,(rust-re-grab "'\\\\x[[:xdigit:]]\\{2\\}'") 1 font-lock-string-face) - (,(rust-re-grab "'\\\\u[[:xdigit:]]\\{4\\}'") 1 font-lock-string-face) - (,(rust-re-grab "'\\\\U[[:xdigit:]]\\{8\\}'") 1 font-lock-string-face) - - ;; CamelCase Means Type Or Constructor - (,(rust-re-grabword rust-re-CamelCase) 1 font-lock-type-face) - ) - - ;; Item definitions - (mapcar #'(lambda (x) - (list (rust-re-item-def (car x)) - 1 (cdr x))) - '(("enum" . font-lock-type-face) - ("struct" . font-lock-type-face) - ("type" . font-lock-type-face) - ("mod" . font-lock-type-face) - ("use" . font-lock-type-face) - ("fn" . font-lock-function-name-face) - ("static" . font-lock-constant-face))))) - -(defun rust-fill-prefix-for-comment-start (line-start) - "Determine what to use for `fill-prefix' based on what is at the beginning of a line." - (let ((result - ;; Replace /* with same number of spaces - (replace-regexp-in-string - "\\(?:/\\*+\\)[!*]" - (lambda (s) - ;; We want the * to line up with the first * of the comment start - (concat (make-string (- (length s) 2) ?\x20) "*")) - line-start))) - ;; Make sure we've got at least one space at the end - (if (not (= (aref result (- (length result) 1)) ?\x20)) - (setq result (concat result " "))) - result)) - -(defun rust-in-comment-paragraph (body) - ;; We might move the point to fill the next comment, but we don't want it - ;; seeming to jump around on the user - (save-excursion - ;; If we're outside of a comment, with only whitespace and then a comment - ;; in front, jump to the comment and prepare to fill it. - (when (not (nth 4 (syntax-ppss))) - (beginning-of-line) - (when (looking-at (concat "[[:space:]\n]*" comment-start-skip)) - (goto-char (match-end 0)))) - - ;; We need this when we're moving the point around and then checking syntax - ;; while doing paragraph fills, because the cache it uses isn't always - ;; invalidated during this. - (syntax-ppss-flush-cache 1) - ;; If we're at the beginning of a comment paragraph with nothing but - ;; whitespace til the next line, jump to the next line so that we use the - ;; existing prefix to figure out what the new prefix should be, rather than - ;; inferring it from the comment start. - (let ((next-bol (line-beginning-position 2))) - (while (save-excursion - (end-of-line) - (syntax-ppss-flush-cache 1) - (and (nth 4 (syntax-ppss)) - (save-excursion - (beginning-of-line) - (looking-at paragraph-start)) - (looking-at "[[:space:]]*$") - (nth 4 (syntax-ppss next-bol)))) - (goto-char next-bol))) - - (syntax-ppss-flush-cache 1) - ;; If we're on the last line of a multiline-style comment that started - ;; above, back up one line so we don't mistake the * of the */ that ends - ;; the comment for a prefix. - (when (save-excursion - (and (nth 4 (syntax-ppss (line-beginning-position 1))) - (looking-at "[[:space:]]*\\*/"))) - (goto-char (line-end-position 0))) - (funcall body))) - -(defun rust-with-comment-fill-prefix (body) - (let* - ((line-string (buffer-substring-no-properties - (line-beginning-position) (line-end-position))) - (line-comment-start - (when (nth 4 (syntax-ppss)) - (cond - ;; If we're inside the comment and see a * prefix, use it - ((string-match "^\\([[:space:]]*\\*+[[:space:]]*\\)" - line-string) - (match-string 1 line-string)) - ;; If we're at the start of a comment, figure out what prefix - ;; to use for the subsequent lines after it - ((string-match (concat "[[:space:]]*" comment-start-skip) line-string) - (rust-fill-prefix-for-comment-start - (match-string 0 line-string)))))) - (fill-prefix - (or line-comment-start - fill-prefix))) - (funcall body))) - -(defun rust-find-fill-prefix () - (rust-with-comment-fill-prefix (lambda () fill-prefix))) - -(defun rust-fill-paragraph (&rest args) - "Special wrapping for `fill-paragraph' to handle multi-line comments with a * prefix on each line." - (rust-in-comment-paragraph - (lambda () - (rust-with-comment-fill-prefix - (lambda () - (let - ((fill-paragraph-function - (if (not (eq fill-paragraph-function 'rust-fill-paragraph)) - fill-paragraph-function)) - (fill-paragraph-handle-comment t)) - (apply 'fill-paragraph args) - t)))))) - -(defun rust-do-auto-fill (&rest args) - "Special wrapping for `do-auto-fill' to handle multi-line comments with a * prefix on each line." - (rust-with-comment-fill-prefix - (lambda () - (apply 'do-auto-fill args) - t))) - -(defun rust-fill-forward-paragraph (arg) - ;; This is to work around some funny behavior when a paragraph separator is - ;; at the very top of the file and there is a fill prefix. - (let ((fill-prefix nil)) (forward-paragraph arg))) - -(defun rust-comment-indent-new-line (&optional arg) - (rust-with-comment-fill-prefix - (lambda () (comment-indent-new-line arg)))) - -;;; Imenu support -(defvar rust-imenu-generic-expression - (append (mapcar #'(lambda (x) - (list nil (rust-re-item-def x) 1)) - '("enum" "struct" "type" "mod" "fn" "trait")) - `(("Impl" ,(rust-re-item-def "impl") 1))) - "Value for `imenu-generic-expression' in Rust mode. - -Create a flat index of the item definitions in a Rust file. - -Imenu will show all the enums, structs, etc. at the same level. -Implementations will be shown under the `Impl` subheading. Use -idomenu (imenu with `ido-mode') for best mileage.") - -;;; Defun Motions - -;;; Start of a Rust item -(defvar rust-top-item-beg-re - (concat "^\\s-*\\(?:priv\\|pub\\)?\\s-*" - (regexp-opt - '("enum" "struct" "type" "mod" "use" "fn" "static" "impl" - "extern" "impl" "static" "trait")))) - -(defun rust-beginning-of-defun (&optional arg) - "Move backward to the beginning of the current defun. - -With ARG, move backward multiple defuns. Negative ARG means -move forward. - -This is written mainly to be used as `beginning-of-defun-function' for Rust. -Don't move to the beginning of the line. `beginning-of-defun', -which calls this, does that afterwards." - (interactive "p") - (re-search-backward (concat "^\\(" rust-top-item-beg-re "\\)\\_>") - nil 'move (or arg 1))) - -(defun rust-end-of-defun () - "Move forward to the next end of defun. - -With argument, do it that many times. -Negative argument -N means move back to Nth preceding end of defun. - -Assume that this is called after beginning-of-defun. So point is -at the beginning of the defun body. - -This is written mainly to be used as `end-of-defun-function' for Rust." - (interactive "p") - ;; Find the opening brace - (re-search-forward "[{]" nil t) - (goto-char (match-beginning 0)) - ;; Go to the closing brace - (forward-sexp)) - -;; For compatibility with Emacs < 24, derive conditionally -(defalias 'rust-parent-mode - (if (fboundp 'prog-mode) 'prog-mode 'fundamental-mode)) - - -;;;###autoload -(define-derived-mode rust-mode rust-parent-mode "Rust" - "Major mode for Rust code." - :group 'rust-mode - :syntax-table rust-mode-syntax-table - - ;; Indentation - (setq-local indent-line-function 'rust-mode-indent-line) - - ;; Fonts - (setq-local font-lock-defaults '(rust-mode-font-lock-keywords nil nil nil nil)) - - ;; Misc - (setq-local comment-start "// ") - (setq-local comment-end "") - (setq-local indent-tabs-mode nil) - - ;; Allow paragraph fills for comments - (setq-local comment-start-skip "\\(?://[/!]*\\|/\\*[*!]?\\)[[:space:]]*") - (setq-local paragraph-start - (concat "[[:space:]]*\\(?:" comment-start-skip "\\|\\*/?[[:space:]]*\\|\\)$")) - (setq-local paragraph-separate paragraph-start) - (setq-local normal-auto-fill-function 'rust-do-auto-fill) - (setq-local fill-paragraph-function 'rust-fill-paragraph) - (setq-local fill-forward-paragraph-function 'rust-fill-forward-paragraph) - (setq-local adaptive-fill-function 'rust-find-fill-prefix) - (setq-local comment-multi-line t) - (setq-local comment-line-break-function 'rust-comment-indent-new-line) - (setq-local imenu-generic-expression rust-imenu-generic-expression) - (setq-local beginning-of-defun-function 'rust-beginning-of-defun) - (setq-local end-of-defun-function 'rust-end-of-defun)) - -;;;###autoload -(add-to-list 'auto-mode-alist '("\\.rs\\'" . rust-mode)) - -(defun rust-mode-reload () - (interactive) - (unload-feature 'rust-mode) - (require 'rust-mode) - (rust-mode)) - -;; Issue #6887: Rather than inheriting the 'gnu compilation error -;; regexp (which is broken on a few edge cases), add our own 'rust -;; compilation error regexp and use it instead. -(defvar rustc-compilation-regexps - (let ((file "\\([^\n]+\\)") - (start-line "\\([0-9]+\\)") - (start-col "\\([0-9]+\\)") - (end-line "\\([0-9]+\\)") - (end-col "\\([0-9]+\\)") - (error-or-warning "\\(?:[Ee]rror\\|\\([Ww]arning\\)\\)")) - (let ((re (concat "^" file ":" start-line ":" start-col - ": " end-line ":" end-col - " \\(?:[Ee]rror\\|\\([Ww]arning\\)\\):"))) - (cons re '(1 (2 . 4) (3 . 5) (6))))) - "Specifications for matching errors in rustc invocations. -See `compilation-error-regexp-alist for help on their format.") - -(eval-after-load 'compile - '(progn - (add-to-list 'compilation-error-regexp-alist-alist - (cons 'rustc rustc-compilation-regexps)) - (add-to-list 'compilation-error-regexp-alist 'rustc))) - -(provide 'rust-mode) - -;;; rust-mode.el ends here diff --git a/src/etc/gedit/readme.txt b/src/etc/gedit/readme.txt deleted file mode 100644 index e394f1916088f..0000000000000 --- a/src/etc/gedit/readme.txt +++ /dev/null @@ -1,10 +0,0 @@ -Add syntax highlighting for Mozilla Rust in GtkSourceView (used by GEdit). - - -Instructions for Ubuntu Linux 12.04+ - -1) Close all instances of GEdit - -2) Copy the included "share" folder into "~/.local/" - -3) Open a shell in "~/.local/share/" and run "update-mime-database mime" diff --git a/src/etc/gedit/share/gtksourceview-3.0/language-specs/rust.lang b/src/etc/gedit/share/gtksourceview-3.0/language-specs/rust.lang deleted file mode 100644 index 8291b38a9bd0b..0000000000000 --- a/src/etc/gedit/share/gtksourceview-3.0/language-specs/rust.lang +++ /dev/null @@ -1,340 +0,0 @@ - - - - - - - text/x-rust - *.rs - // - /* - */ - - - -