<commit_before>// 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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

/*!

Operations on the ubiquitous `Option` type.

Type `Option` represents an optional value.

Every `Option<T>` value can either be `Some(T)` or `None`. Where in other
languages you might use a nullable type, in Rust you would use an option
type.

Options are most commonly used with pattern matching to query the presence
of a value and take action, always accounting for the `None` case.

# Example

~~~
let msg = Some(~"howdy");

// Take a reference to the contained string
match msg {
    Some(ref m) => io::println(m),
    None => ()
}

// Remove the contained string, destroying the Option
let unwrapped_msg = match move msg {
    Some(move m) => m,
    None => ~"default message"
};
~~~

*/

#[forbid(deprecated_mode)];
#[forbid(deprecated_pattern)];

use cmp::Eq;
use kinds::Copy;
use option;
use ptr;
use str;
use util;
use num::Zero;

/// The option type
#[deriving_eq]
pub enum Option<T> {
    None,
    Some(T),
}

pub pure fn get<T: Copy>(opt: Option<T>) -> T {
    /*!
    Gets the value out of an option

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
    */

    match opt {
      Some(copy x) => return x,
      None => fail ~"option::get none"
    }
}

pub pure fn get_ref<T>(opt: &r/Option<T>) -> &r/T {
    /*!
    Gets an immutable reference to the value inside an option.

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    match *opt {
        Some(ref x) => x,
        None => fail ~"option::get_ref none"
    }
}

pub pure fn map<T, U>(opt: &Option<T>, f: fn(x: &T) -> U) -> Option<U> {
    //! Maps a `some` value by reference from one type to another

    match *opt { Some(ref x) => Some(f(x)), None => None }
}

pub pure fn map_consume<T, U>(opt: Option<T>,
                              f: fn(v: T) -> U) -> Option<U> {
    /*!
     * As `map`, but consumes the option and gives `f` ownership to avoid
     * copying.
     */
    if opt.is_some() { Some(f(option::unwrap(move opt))) } else { None }
}

pub pure fn chain<T, U>(opt: Option<T>,
                        f: fn(t: T) -> Option<U>) -> Option<U> {
    /*!
     * Update an optional value by optionally running its content through a
     * function that returns an option.
     */

    match move opt {
        Some(move t) => f(move t),
        None => None
    }
}

pub pure fn chain_ref<T, U>(opt: &Option<T>,
                            f: fn(x: &T) -> Option<U>) -> Option<U> {
    /*!
     * Update an optional value by optionally running its content by reference
     * through a function that returns an option.
     */

    match *opt { Some(ref x) => f(x), None => None }
}

pub pure fn or<T>(opta: Option<T>, optb: Option<T>) -> Option<T> {
    /*!
     * Returns the leftmost some() value, or none if both are none.
     */
    match move opta {
        Some(move opta) => Some(move opta),
        _ => move optb
    }
}

#[inline(always)]
pub pure fn while_some<T>(x: Option<T>, blk: fn(v: T) -> Option<T>) {
    //! Applies a function zero or more times until the result is none.

    let mut opt = move x;
    while opt.is_some() {
        opt = blk(unwrap(move opt));
    }
}

pub pure fn is_none<T>(opt: &Option<T>) -> bool {
    //! Returns true if the option equals `none`

    match *opt { None => true, Some(_) => false }
}

pub pure fn is_some<T>(opt: &Option<T>) -> bool {
    //! Returns true if the option contains some value

    !is_none(opt)
}

pub pure fn get_or_zero<T: Copy Zero>(opt: Option<T>) -> T {
    //! Returns the contained value or zero (for this type)

    match opt { Some(copy x) => x, None => Zero::zero() }
}

pub pure fn get_or_default<T: Copy>(opt: Option<T>, def: T) -> T {
    //! Returns the contained value or a default

    match opt { Some(copy x) => x, None => def }
}

pub pure fn map_default<T, U>(opt: &Option<T>, def: U,
                              f: fn(x: &T) -> U) -> U {
    //! Applies a function to the contained value or returns a default

    match *opt { None => move def, Some(ref t) => f(t) }
}

pub pure fn iter<T>(opt: &Option<T>, f: fn(x: &T)) {
    //! Performs an operation on the contained value by reference
    match *opt { None => (), Some(ref t) => f(t) }
}

#[inline(always)]
pub pure fn unwrap<T>(opt: Option<T>) -> T {
    /*!
    Moves a value out of an option type and returns it.

    Useful primarily for getting strings, vectors and unique pointers out
    of option types without copying them.

    # Failure

    Fails if the value equals `None`.

    # Safety note

    In general, because this function may fail, its use is discouraged.
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    match move opt {
        Some(move x) => move x,
        None => fail ~"option::unwrap none"
    }
}

#[inline(always)]
pub fn swap_unwrap<T>(opt: &mut Option<T>) -> T {
    /*!
    The option dance. Moves a value out of an option type and returns it,
    replacing the original with `None`.

    # Failure

    Fails if the value equals `None`.
     */
    if opt.is_none() { fail ~"option::swap_unwrap none" }
    unwrap(util::replace(opt, None))
}

pub pure fn expect<T>(opt: Option<T>, reason: &str) -> T {
    //! As unwrap, but with a specified failure message.
    match move opt {
        Some(move val) => val,
        None => fail reason.to_owned(),
    }
}

impl<T> Option<T> {
    /// Returns true if the option equals `none`
    #[inline(always)]
    pure fn is_none(&self) -> bool { is_none(self) }

    /// Returns true if the option contains some value
    #[inline(always)]
    pure fn is_some(&self) -> bool { is_some(self) }

    /**
     * Update an optional value by optionally running its content by reference
     * through a function that returns an option.
     */
    #[inline(always)]
    pure fn chain_ref<U>(&self, f: fn(x: &T) -> Option<U>) -> Option<U> {
        chain_ref(self, f)
    }

    /// Maps a `some` value from one type to another by reference
    #[inline(always)]
    pure fn map<U>(&self, f: fn(x: &T) -> U) -> Option<U> { map(self, f) }

    /// Applies a function to the contained value or returns a default
    #[inline(always)]
    pure fn map_default<U>(&self, def: U, f: fn(x: &T) -> U) -> U {
        map_default(self, move def, f)
    }

    /// Performs an operation on the contained value by reference
    #[inline(always)]
    pure fn iter(&self, f: fn(x: &T)) { iter(self, f) }

    /**
    Gets an immutable reference to the value inside an option.

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    #[inline(always)]
    pure fn get_ref(&self) -> &self/T { get_ref(self) }

    /**
     * Gets the value out of an option without copying.
     *
     * # Failure
     *
     * Fails if the value equals `none`
     */
    #[inline(always)]
    pure fn unwrap(self) -> T { unwrap(self) }

    /**
     * Gets the value out of an option, printing a specified message on
     * failure
     *
     * # Failure
     *
     * Fails if the value equals `none`
     */
    #[inline(always)]
    pure fn expect(self, reason: &str) -> T { expect(self, reason) }
}

impl<T: Copy> Option<T> {
    /**
    Gets the value out of an option

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
    */
    #[inline(always)]
    pure fn get(self) -> T { get(self) }

    #[inline(always)]
    pure fn get_or_default(self, def: T) -> T { get_or_default(self, def) }

    /// Applies a function zero or more times until the result is none.
    #[inline(always)]
    pure fn while_some(self, blk: fn(v: T) -> Option<T>) {
        while_some(self, blk)
    }
}

impl<T: Copy Zero> Option<T> {
    #[inline(always)]
    pure fn get_or_zero(self) -> T { get_or_zero(self) }
}

#[test]
fn test_unwrap_ptr() {
    let x = ~0;
    let addr_x = ptr::addr_of(&(*x));
    let opt = Some(move x);
    let y = unwrap(move opt);
    let addr_y = ptr::addr_of(&(*y));
    assert addr_x == addr_y;
}

#[test]
fn test_unwrap_str() {
    let x = ~"test";
    let addr_x = str::as_buf(x, |buf, _len| buf);
    let opt = Some(move x);
    let y = unwrap(move opt);
    let addr_y = str::as_buf(y, |buf, _len| buf);
    assert addr_x == addr_y;
}

#[test]
fn test_unwrap_resource() {
    struct R {
       i: @mut int,
       drop { *(self.i) += 1; }
    }

    fn R(i: @mut int) -> R {
        R {
            i: i
        }
    }

    let i = @mut 0;
    {
        let x = R(i);
        let opt = Some(move x);
        let _y = unwrap(move opt);
    }
    assert *i == 1;
}

#[test]
fn test_option_dance() {
    let x = Some(());
    let mut y = Some(5);
    let mut y2 = 0;
    do x.iter |_x| {
        y2 = swap_unwrap(&mut y);
    }
    assert y2 == 5;
    assert y.is_none();
}
#[test] #[should_fail] #[ignore(cfg(windows))]
fn test_option_too_much_dance() {
    let mut y = Some(util::NonCopyable());
    let _y2 = swap_unwrap(&mut y);
    let _y3 = swap_unwrap(&mut y);
}

#[test]
fn test_option_while_some() {
    let mut i = 0;
    do Some(10).while_some |j| {
        i += 1;
        if (j > 0) {
            Some(j-1)
        } else {
            None
        }
    }
    assert i == 11;
}

#[test]
fn test_get_or_zero() {
    let some_stuff = Some(42);
    assert some_stuff.get_or_zero() == 42;
    let no_stuff: Option<int> = None;
    assert no_stuff.get_or_zero() == 0;
}

// Local Variables:
// mode: rust;
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// End:
<commit_msg>add Option methods for swap_unwrap and map_consume<commit_after>// 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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

/*!

Operations on the ubiquitous `Option` type.

Type `Option` represents an optional value.

Every `Option<T>` value can either be `Some(T)` or `None`. Where in other
languages you might use a nullable type, in Rust you would use an option
type.

Options are most commonly used with pattern matching to query the presence
of a value and take action, always accounting for the `None` case.

# Example

~~~
let msg = Some(~"howdy");

// Take a reference to the contained string
match msg {
    Some(ref m) => io::println(m),
    None => ()
}

// Remove the contained string, destroying the Option
let unwrapped_msg = match move msg {
    Some(move m) => m,
    None => ~"default message"
};
~~~

*/

#[forbid(deprecated_mode)];
#[forbid(deprecated_pattern)];

use cmp::Eq;
use kinds::Copy;
use option;
use ptr;
use str;
use util;
use num::Zero;

/// The option type
#[deriving_eq]
pub enum Option<T> {
    None,
    Some(T),
}

pub pure fn get<T: Copy>(opt: Option<T>) -> T {
    /*!
    Gets the value out of an option

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
    */

    match opt {
      Some(copy x) => return x,
      None => fail ~"option::get none"
    }
}

pub pure fn get_ref<T>(opt: &r/Option<T>) -> &r/T {
    /*!
    Gets an immutable reference to the value inside an option.

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    match *opt {
        Some(ref x) => x,
        None => fail ~"option::get_ref none"
    }
}

pub pure fn map<T, U>(opt: &Option<T>, f: fn(x: &T) -> U) -> Option<U> {
    //! Maps a `some` value by reference from one type to another

    match *opt { Some(ref x) => Some(f(x)), None => None }
}

pub pure fn map_consume<T, U>(opt: Option<T>,
                              f: fn(v: T) -> U) -> Option<U> {
    /*!
     * As `map`, but consumes the option and gives `f` ownership to avoid
     * copying.
     */
    if opt.is_some() { Some(f(option::unwrap(move opt))) } else { None }
}

pub pure fn chain<T, U>(opt: Option<T>,
                        f: fn(t: T) -> Option<U>) -> Option<U> {
    /*!
     * Update an optional value by optionally running its content through a
     * function that returns an option.
     */

    match move opt {
        Some(move t) => f(move t),
        None => None
    }
}

pub pure fn chain_ref<T, U>(opt: &Option<T>,
                            f: fn(x: &T) -> Option<U>) -> Option<U> {
    /*!
     * Update an optional value by optionally running its content by reference
     * through a function that returns an option.
     */

    match *opt { Some(ref x) => f(x), None => None }
}

pub pure fn or<T>(opta: Option<T>, optb: Option<T>) -> Option<T> {
    /*!
     * Returns the leftmost some() value, or none if both are none.
     */
    match move opta {
        Some(move opta) => Some(move opta),
        _ => move optb
    }
}

#[inline(always)]
pub pure fn while_some<T>(x: Option<T>, blk: fn(v: T) -> Option<T>) {
    //! Applies a function zero or more times until the result is none.

    let mut opt = move x;
    while opt.is_some() {
        opt = blk(unwrap(move opt));
    }
}

pub pure fn is_none<T>(opt: &Option<T>) -> bool {
    //! Returns true if the option equals `none`

    match *opt { None => true, Some(_) => false }
}

pub pure fn is_some<T>(opt: &Option<T>) -> bool {
    //! Returns true if the option contains some value

    !is_none(opt)
}

pub pure fn get_or_zero<T: Copy Zero>(opt: Option<T>) -> T {
    //! Returns the contained value or zero (for this type)

    match opt { Some(copy x) => x, None => Zero::zero() }
}

pub pure fn get_or_default<T: Copy>(opt: Option<T>, def: T) -> T {
    //! Returns the contained value or a default

    match opt { Some(copy x) => x, None => def }
}

pub pure fn map_default<T, U>(opt: &Option<T>, def: U,
                              f: fn(x: &T) -> U) -> U {
    //! Applies a function to the contained value or returns a default

    match *opt { None => move def, Some(ref t) => f(t) }
}

pub pure fn iter<T>(opt: &Option<T>, f: fn(x: &T)) {
    //! Performs an operation on the contained value by reference
    match *opt { None => (), Some(ref t) => f(t) }
}

#[inline(always)]
pub pure fn unwrap<T>(opt: Option<T>) -> T {
    /*!
    Moves a value out of an option type and returns it.

    Useful primarily for getting strings, vectors and unique pointers out
    of option types without copying them.

    # Failure

    Fails if the value equals `None`.

    # Safety note

    In general, because this function may fail, its use is discouraged.
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    match move opt {
        Some(move x) => move x,
        None => fail ~"option::unwrap none"
    }
}

#[inline(always)]
pub fn swap_unwrap<T>(opt: &mut Option<T>) -> T {
    /*!
    The option dance. Moves a value out of an option type and returns it,
    replacing the original with `None`.

    # Failure

    Fails if the value equals `None`.
     */
    if opt.is_none() { fail ~"option::swap_unwrap none" }
    unwrap(util::replace(opt, None))
}

pub pure fn expect<T>(opt: Option<T>, reason: &str) -> T {
    //! As unwrap, but with a specified failure message.
    match move opt {
        Some(move val) => val,
        None => fail reason.to_owned(),
    }
}

impl<T> Option<T> {
    /// Returns true if the option equals `none`
    #[inline(always)]
    pure fn is_none(&self) -> bool { is_none(self) }

    /// Returns true if the option contains some value
    #[inline(always)]
    pure fn is_some(&self) -> bool { is_some(self) }

    /**
     * Update an optional value by optionally running its content by reference
     * through a function that returns an option.
     */
    #[inline(always)]
    pure fn chain_ref<U>(&self, f: fn(x: &T) -> Option<U>) -> Option<U> {
        chain_ref(self, f)
    }

    /// Maps a `some` value from one type to another by reference
    #[inline(always)]
    pure fn map<U>(&self, f: fn(x: &T) -> U) -> Option<U> { map(self, f) }

    /// As `map`, but consumes the option and gives `f` ownership to avoid
    /// copying.
    #[inline(always)]
    pure fn map_consume<U>(self, f: fn(v: T) -> U) -> Option<U> {
        map_consume(self, f)
    }

    /// Applies a function to the contained value or returns a default
    #[inline(always)]
    pure fn map_default<U>(&self, def: U, f: fn(x: &T) -> U) -> U {
        map_default(self, move def, f)
    }

    /// Performs an operation on the contained value by reference
    #[inline(always)]
    pure fn iter(&self, f: fn(x: &T)) { iter(self, f) }

    /**
    Gets an immutable reference to the value inside an option.

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
     */
    #[inline(always)]
    pure fn get_ref(&self) -> &self/T { get_ref(self) }

    /**
     * Gets the value out of an option without copying.
     *
     * # Failure
     *
     * Fails if the value equals `none`
     */
    #[inline(always)]
    pure fn unwrap(self) -> T { unwrap(self) }

    /**
     * The option dance. Moves a value out of an option type and returns it,
     * replacing the original with `None`.
     *
     * # Failure
     *
     * Fails if the value equals `None`.
     */
    #[inline(always)]
    fn swap_unwrap(&mut self) -> T { swap_unwrap(self) }

    /**
     * Gets the value out of an option, printing a specified message on
     * failure
     *
     * # Failure
     *
     * Fails if the value equals `none`
     */
    #[inline(always)]
    pure fn expect(self, reason: &str) -> T { expect(self, reason) }
}

impl<T: Copy> Option<T> {
    /**
    Gets the value out of an option

    # Failure

    Fails if the value equals `None`

    # Safety note

    In general, because this function may fail, its use is discouraged
    (calling `get` on `None` is akin to dereferencing a null pointer).
    Instead, prefer to use pattern matching and handle the `None`
    case explicitly.
    */
    #[inline(always)]
    pure fn get(self) -> T { get(self) }

    #[inline(always)]
    pure fn get_or_default(self, def: T) -> T { get_or_default(self, def) }

    /// Applies a function zero or more times until the result is none.
    #[inline(always)]
    pure fn while_some(self, blk: fn(v: T) -> Option<T>) {
        while_some(self, blk)
    }
}

impl<T: Copy Zero> Option<T> {
    #[inline(always)]
    pure fn get_or_zero(self) -> T { get_or_zero(self) }
}

#[test]
fn test_unwrap_ptr() {
    let x = ~0;
    let addr_x = ptr::addr_of(&(*x));
    let opt = Some(move x);
    let y = unwrap(move opt);
    let addr_y = ptr::addr_of(&(*y));
    assert addr_x == addr_y;
}

#[test]
fn test_unwrap_str() {
    let x = ~"test";
    let addr_x = str::as_buf(x, |buf, _len| buf);
    let opt = Some(move x);
    let y = unwrap(move opt);
    let addr_y = str::as_buf(y, |buf, _len| buf);
    assert addr_x == addr_y;
}

#[test]
fn test_unwrap_resource() {
    struct R {
       i: @mut int,
       drop { *(self.i) += 1; }
    }

    fn R(i: @mut int) -> R {
        R {
            i: i
        }
    }

    let i = @mut 0;
    {
        let x = R(i);
        let opt = Some(move x);
        let _y = unwrap(move opt);
    }
    assert *i == 1;
}

#[test]
fn test_option_dance() {
    let x = Some(());
    let mut y = Some(5);
    let mut y2 = 0;
    do x.iter |_x| {
        y2 = swap_unwrap(&mut y);
    }
    assert y2 == 5;
    assert y.is_none();
}
#[test] #[should_fail] #[ignore(cfg(windows))]
fn test_option_too_much_dance() {
    let mut y = Some(util::NonCopyable());
    let _y2 = swap_unwrap(&mut y);
    let _y3 = swap_unwrap(&mut y);
}

#[test]
fn test_option_while_some() {
    let mut i = 0;
    do Some(10).while_some |j| {
        i += 1;
        if (j > 0) {
            Some(j-1)
        } else {
            None
        }
    }
    assert i == 11;
}

#[test]
fn test_get_or_zero() {
    let some_stuff = Some(42);
    assert some_stuff.get_or_zero() == 42;
    let no_stuff: Option<int> = None;
    assert no_stuff.get_or_zero() == 0;
}

// Local Variables:
// mode: rust;
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// End:
<|endoftext|>


<commit_before>// 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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

//! Interfaces to the operating system provided random number
//! generators.

use rand::Rng;
use ops::Drop;

#[cfg(unix)]
use rand::reader::ReaderRng;
#[cfg(unix)]
use rt::io::{file, Open, Read};

#[cfg(windows)]
use cast;

/// A random number generator that retrieves randomness straight from
/// the operating system. On Unix-like systems this reads from
/// `/dev/urandom`, on Windows this uses `CryptGenRandom`.
///
/// This does not block.
#[cfg(unix)]
pub struct OSRng {
    priv inner: ReaderRng<file::FileStream>
}
/// A random number generator that retrieves randomness straight from
/// the operating system. On Unix-like systems this reads from
/// `/dev/urandom`, on Windows this uses `CryptGenRandom`.
///
/// This does not block.
#[cfg(windows)]
pub struct OSRng {
    priv hcryptprov: raw::HCRYPTPROV
}

impl OSRng {
    /// Create a new `OSRng`.
    #[cfg(unix)]
    pub fn new() -> OSRng {
        let reader = file::open(& &"/dev/urandom", Open, Read).expect("Error opening /dev/urandom");
        let reader_rng = ReaderRng::new(reader);

        OSRng { inner: reader_rng }
    }

    /// Create a new `OSRng`.
    #[cfg(windows)]
    #[fixed_stack_segment] #[inline(never)]
    pub fn new() -> OSRng {
        let mut hcp = 0;
        unsafe {raw::rust_win32_rand_acquire(&mut hcp)};

        OSRng { hcryptprov: hcp }
    }
}

#[cfg(unix)]
impl Rng for OSRng {
    fn next_u32(&mut self) -> u32 {
        self.inner.next_u32()
    }
    fn next_u64(&mut self) -> u64 {
        self.inner.next_u64()
    }
    fn fill_bytes(&mut self, v: &mut [u8]) {
        self.inner.fill_bytes(v)
    }
}

#[cfg(windows)]
impl Rng for OSRng {
    fn next_u32(&mut self) -> u32 {
        let mut v = [0u8, .. 4];
        self.fill_bytes(v);
        unsafe { cast::transmute(v) }
    }
    fn next_u64(&mut self) -> u64 {
        let mut v = [0u8, .. 8];
        self.fill_bytes(v);
        unsafe { cast::transmute(v) }
    }
    #[fixed_stack_segment] #[inline(never)]
    fn fill_bytes(&mut self, v: &mut [u8]) {
        use libc::DWORD;

        do v.as_mut_buf |ptr, len| {
            unsafe {raw::rust_win32_rand_gen(self.hcryptprov, len as DWORD, ptr)}
        }
    }
}

impl Drop for OSRng {
    #[cfg(unix)]
    fn drop(&mut self) {
        // ensure that OSRng is not implicitly copyable on all
        // platforms, for consistency.
    }

    #[cfg(windows)]
    #[fixed_stack_segment] #[inline(never)]
    fn drop(&mut self) {
        unsafe {raw::rust_win32_rand_release(self.hcryptprov)}
    }
}

#[cfg(windows)]
mod raw {
    use libc::{c_long, DWORD, BYTE};

    pub type HCRYPTPROV = c_long;

    // these functions are implemented so that they either succeed or
    // abort(), so we can just assume they work when we call them.
    extern {
        pub fn rust_win32_rand_acquire(phProv: *mut HCRYPTPROV);
        pub fn rust_win32_rand_gen(hProv: HCRYPTPROV, dwLen: DWORD, pbBuffer: *mut BYTE);
        pub fn rust_win32_rand_release(hProv: HCRYPTPROV);
    }
}

#[cfg(test)]
mod test {
    use super::*;
    use rand::Rng;

    #[test]
    fn test_os_rng() {
        let mut r = OSRng::new();

        r.next_u32();
        r.next_u64();

        let mut v = [0u8, .. 1000];
        r.fill_bytes(v);
    }

    #[test]
    fn test_os_rng_tasks() {
        use task;
        use comm;
        use comm::{GenericChan, GenericPort};
        use option::{None, Some};
        use iter::{Iterator, range};
        use vec::{ImmutableVector, OwnedVector};

        let mut chans = ~[];
        for _ in range(0, 20) {
            let (p, c) = comm::stream();
            chans.push(c);
            do task::spawn_with(p) |p| {
                // wait until all the tasks are ready to go.
                p.recv();

                // deschedule to attempt to interleave things as much
                // as possible (XXX: is this a good test?)
                let mut r = OSRng::new();
                task::deschedule();
                let mut v = [0u8, .. 1000];

                for _ in range(0, 100) {
                    r.next_u32();
                    task::deschedule();
                    r.next_u64();
                    task::deschedule();
                    r.fill_bytes(v);
                    task::deschedule();
                }
            }
        }

        // start all the tasks
        for c in chans.iter() {
            c.send(())
        }
    }
}
<commit_msg>std::rand::os: use the externfn! macro for the Windows RNG.<commit_after>// 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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

//! Interfaces to the operating system provided random number
//! generators.

use rand::Rng;
use ops::Drop;

#[cfg(unix)]
use rand::reader::ReaderRng;
#[cfg(unix)]
use rt::io::{file, Open, Read};

#[cfg(windows)]
use cast;
#[cfg(windows)]
use libc::{c_long, DWORD, BYTE};
#[cfg(windows)]
type HCRYPTPROV = c_long;
// the extern functions imported from the runtime on Windows are
// implemented so that they either succeed or abort(), so we can just
// assume they work when we call them.

/// A random number generator that retrieves randomness straight from
/// the operating system. On Unix-like systems this reads from
/// `/dev/urandom`, on Windows this uses `CryptGenRandom`.
///
/// This does not block.
#[cfg(unix)]
pub struct OSRng {
    priv inner: ReaderRng<file::FileStream>
}
/// A random number generator that retrieves randomness straight from
/// the operating system. On Unix-like systems this reads from
/// `/dev/urandom`, on Windows this uses `CryptGenRandom`.
///
/// This does not block.
#[cfg(windows)]
pub struct OSRng {
    priv hcryptprov: HCRYPTPROV
}

impl OSRng {
    /// Create a new `OSRng`.
    #[cfg(unix)]
    pub fn new() -> OSRng {
        let reader = file::open(& &"/dev/urandom", Open, Read).expect("Error opening /dev/urandom");
        let reader_rng = ReaderRng::new(reader);

        OSRng { inner: reader_rng }
    }

    /// Create a new `OSRng`.
    #[cfg(windows)]
    pub fn new() -> OSRng {
        externfn!(fn rust_win32_rand_acquire(phProv: *mut HCRYPTPROV))

        let mut hcp = 0;
        unsafe {rust_win32_rand_acquire(&mut hcp)};

        OSRng { hcryptprov: hcp }
    }
}

#[cfg(unix)]
impl Rng for OSRng {
    fn next_u32(&mut self) -> u32 {
        self.inner.next_u32()
    }
    fn next_u64(&mut self) -> u64 {
        self.inner.next_u64()
    }
    fn fill_bytes(&mut self, v: &mut [u8]) {
        self.inner.fill_bytes(v)
    }
}

#[cfg(windows)]
impl Rng for OSRng {
    fn next_u32(&mut self) -> u32 {
        let mut v = [0u8, .. 4];
        self.fill_bytes(v);
        unsafe { cast::transmute(v) }
    }
    fn next_u64(&mut self) -> u64 {
        let mut v = [0u8, .. 8];
        self.fill_bytes(v);
        unsafe { cast::transmute(v) }
    }
    fn fill_bytes(&mut self, v: &mut [u8]) {
        externfn!(fn rust_win32_rand_gen(hProv: HCRYPTPROV, dwLen: DWORD, pbBuffer: *mut BYTE))

        do v.as_mut_buf |ptr, len| {
            unsafe {rust_win32_rand_gen(self.hcryptprov, len as DWORD, ptr)}
        }
    }
}

impl Drop for OSRng {
    #[cfg(unix)]
    fn drop(&mut self) {
        // ensure that OSRng is not implicitly copyable on all
        // platforms, for consistency.
    }

    #[cfg(windows)]
    fn drop(&mut self) {
        externfn!(fn rust_win32_rand_release(hProv: HCRYPTPROV))

        unsafe {rust_win32_rand_release(self.hcryptprov)}
    }
}

#[cfg(test)]
mod test {
    use super::*;
    use rand::Rng;

    #[test]
    fn test_os_rng() {
        let mut r = OSRng::new();

        r.next_u32();
        r.next_u64();

        let mut v = [0u8, .. 1000];
        r.fill_bytes(v);
    }

    #[test]
    fn test_os_rng_tasks() {
        use task;
        use comm;
        use comm::{GenericChan, GenericPort};
        use option::{None, Some};
        use iter::{Iterator, range};
        use vec::{ImmutableVector, OwnedVector};

        let mut chans = ~[];
        for _ in range(0, 20) {
            let (p, c) = comm::stream();
            chans.push(c);
            do task::spawn_with(p) |p| {
                // wait until all the tasks are ready to go.
                p.recv();

                // deschedule to attempt to interleave things as much
                // as possible (XXX: is this a good test?)
                let mut r = OSRng::new();
                task::deschedule();
                let mut v = [0u8, .. 1000];

                for _ in range(0, 100) {
                    r.next_u32();
                    task::deschedule();
                    r.next_u64();
                    task::deschedule();
                    r.fill_bytes(v);
                    task::deschedule();
                }
            }
        }

        // start all the tasks
        for c in chans.iter() {
            c.send(())
        }
    }
}
<|endoftext|>


<commit_before><commit_msg>Start fake std<commit_after>extern crate core;
extern crate collections;

pub use core::*;
pub use collections;

/*
pub mod prelude {
    pub use ops::{ Drop, Fn, FnMut, FnOnce };
    pub use cmp::{ PartialEq, PartialOrd, Eq, Ord };
    pub use convert::{ AsRef, AsMut, Into, From };
    pub use option::Option::{ self, Some, None };
    pub use option::Result::{ self, Some, None };
    pub use collections::string::{ String, ToString };
    pub use Vec;
    // TODO: Box
    pub use iter::{ Iterator, Extend, IntoIterator, DoubleEndedIterator, ExactSizeIterator };
    pub use mem::drop;
    pub use clone::Clone;
    pub use default::Default;
}
*/

pub mod io;
pub mod fs;

<|endoftext|>


<commit_before><commit_msg>wow math<commit_after><|endoftext|>


<commit_before>extern crate getopts;

extern crate otp_cop;

use std::{env, thread};
use std::sync::{mpsc};

use otp_cop::service::{CreateServiceResult, ServiceFactory};

struct ParallelIter<T> {
    count: usize,
    pos: usize,
    rx: mpsc::Receiver<T>
}

impl<T> Iterator for ParallelIter<T> {
    type Item = T;

    fn next(&mut self) -> Option<T> {
        if self.pos < self.count {
            self.count += 1;
            return self.rx.recv().ok();
        } else {
            return None;
        }
    }
}

fn parallel<T, U, F1>(objs: Vec<T>, f1: F1) -> ParallelIter<U>
        where F1: 'static + Fn(T) -> U + Send, T: 'static + Send, U: 'static + Send {
    let (tx, rx) = mpsc::channel();
    let count = objs.len();
    for o in objs {
        let tx = tx.clone();
        thread::spawn(move || {
            tx.send(f1(o));
        });
    }

    return ParallelIter{count: count, pos: 0, rx: rx};
}

fn main() {
    let service_factories = vec![
        Box::new(otp_cop::SlackServiceFactory) as Box<ServiceFactory>,
        Box::new(otp_cop::GithubServiceFactory) as Box<ServiceFactory>,
    ];

    let mut opts = getopts::Options::new();

    for factory in service_factories.iter() {
        factory.add_options(&mut opts);
    }

    let matches = match opts.parse(env::args().skip(1)) {
        Ok(matches) => matches,
        Err(e) => panic!(e.to_string()),
    };

    let mut services = vec![];

    for factory in service_factories.iter() {
        match factory.create_service(&matches) {
            CreateServiceResult::Service(s) => services.push(s),
            CreateServiceResult::MissingArguments(arg) => panic!(format!("Missing arguments: {:?}", arg)),
            CreateServiceResult::None => continue,
        }
    }

    if services.is_empty() {
        print!("{}", opts.usage("otp-cop: <args>"));
    }

    let count = services.len();
    for (i, result) in parallel(services, |service| service.get_users()).enumerate() {
        println!("{}", result.service_name);
        println!("{}", "=".chars().cycle().take(result.service_name.len()).collect::<String>());
        println!("");
        for user in result.users {
            let email = match user.email {
                Some(email) => format!(" ({})", email),
                None => "".to_string(),
            };
            let details = match user.details {
                Some(details) => format!(" -- {}", details),
                None => "".to_string(),
            };
            println!("@{}{}{}", user.name, email, details);
        }
        if i + 1 != count {
            println!("");
            println!("");
        }
    }
}
<commit_msg>arc makes it work<commit_after>extern crate getopts;

extern crate otp_cop;

use std::{env, thread};
use std::sync::{mpsc, Arc};

use otp_cop::service::{CreateServiceResult, ServiceFactory};

struct ParallelIter<T> {
    count: usize,
    pos: usize,
    rx: mpsc::Receiver<T>
}

impl<T> Iterator for ParallelIter<T> {
    type Item = T;

    fn next(&mut self) -> Option<T> {
        if self.pos < self.count {
            self.count += 1;
            return self.rx.recv().ok();
        } else {
            return None;
        }
    }
}

fn parallel<T, U, F1>(objs: Vec<T>, f1: F1) -> ParallelIter<U>
        where F1: 'static + Fn(T) -> U + Send + Sync, T: 'static + Send, U: 'static + Send {
    let (tx, rx) = mpsc::channel();
    let count = objs.len();
    let shared_f1 = Arc::new(f1);
    for o in objs {
        let f1 = shared_f1.clone();
        let tx = tx.clone();
        thread::spawn(move || {
            tx.send(f1(o)).unwrap();
        });
    }

    return ParallelIter{count: count, pos: 0, rx: rx};
}

fn main() {
    let service_factories = vec![
        Box::new(otp_cop::SlackServiceFactory) as Box<ServiceFactory>,
        Box::new(otp_cop::GithubServiceFactory) as Box<ServiceFactory>,
    ];

    let mut opts = getopts::Options::new();

    for factory in service_factories.iter() {
        factory.add_options(&mut opts);
    }

    let matches = match opts.parse(env::args().skip(1)) {
        Ok(matches) => matches,
        Err(e) => panic!(e.to_string()),
    };

    let mut services = vec![];

    for factory in service_factories.iter() {
        match factory.create_service(&matches) {
            CreateServiceResult::Service(s) => services.push(s),
            CreateServiceResult::MissingArguments(arg) => panic!(format!("Missing arguments: {:?}", arg)),
            CreateServiceResult::None => continue,
        }
    }

    if services.is_empty() {
        print!("{}", opts.usage("otp-cop: <args>"));
    }

    let count = services.len();
    for (i, result) in parallel(services, |service| service.get_users()).enumerate() {
        println!("{}", result.service_name);
        println!("{}", "=".chars().cycle().take(result.service_name.len()).collect::<String>());
        println!("");
        for user in result.users {
            let email = match user.email {
                Some(email) => format!(" ({})", email),
                None => "".to_string(),
            };
            let details = match user.details {
                Some(details) => format!(" -- {}", details),
                None => "".to_string(),
            };
            println!("@{}{}{}", user.name, email, details);
        }
        if i + 1 != count {
            println!("");
            println!("");
        }
    }
}
<|endoftext|>


<commit_before>#![crate_name = "clog"]
#![feature(plugin)]
#![plugin(regex_macros)]

extern crate regex;
extern crate time;

extern crate clap;

use git::LogReaderConfig;
use log_writer::{ LogWriter, LogWriterOptions };
use std::fs::File;
use std::io::Read;
use std::path::Path;
use std::borrow::ToOwned;

use clap::{App, Arg};

mod common;
mod git;
mod log_writer;
mod section_builder;
mod format_util;

fn main () {
    // Pull version from Cargo.toml
    let version = format!("{}.{}.{}{}",
                          env!("CARGO_PKG_VERSION_MAJOR"),
                          env!("CARGO_PKG_VERSION_MINOR"),
                          env!("CARGO_PKG_VERSION_PATCH"),
                          option_env!("CARGO_PKG_VERSION_PRE").unwrap_or(""));
    let matches = App::new("clog")
        .version(&version[..])
        .about("a conventional changelog for the rest of us")
        .arg(Arg::new("repository")
            .short("r")
            .long("repository")
            .takes_value(true)
            .help("e.g. https://github.com/thoughtram/clog"))
        .arg(Arg::new("setversion")
            .long("setversion")
            .help("e.g. 1.0.1")
            .takes_value(true))
        .arg(Arg::new("subtitle")
            .long("subtitle")
            .help("e.g. crazy-release-title")
            .takes_value(true))
        .arg(Arg::new("from")
            .help("e.g. 12a8546")
            .long("from")
            .takes_value(true))
        .arg(Arg::new("to")
            .long("to")
            .help("e.g. 8057684")
            .takes_value(true))
        .arg(Arg::new("from-latest-tag")
            .long("from-latest-tag")
            .help("uses the latest tag as starting point (ignores other --from parameters)")
            .mutually_excludes("from"))
        .get_matches();

    let start_nsec = time::get_time().nsec;

    let log_reader_config = LogReaderConfig {
        grep: "^feat|^fix|BREAKING'".to_owned(),
        format: "%H%n%s%n%b%n==END==".to_owned(),
        from: if matches.is_present("from-latest-tag") { Some(git::get_latest_tag()) } else { matches.value_of("from").map(|v| v.to_owned()) },
        to: matches.value_of("to").unwrap_or("").to_owned()
    };

    let commits = git::get_log_entries(log_reader_config);

    let sections = section_builder::build_sections(commits.clone());

    let mut contents = String::new();
    match File::open(&Path::new("changelog.md")).ok().expect("couldn't open changelog.md").read_to_string(&mut contents) {
        Ok(_) => (),
        Err(_) => contents = "".to_owned()
    }

    let mut file = File::create(&Path::new("changelog.md")).ok().unwrap();
    let mut writer = LogWriter::new(&mut file, LogWriterOptions {
        repository_link: matches.value_of("repository").unwrap_or(""),
        version: if matches.is_present("setversion") {
                    matches.value_of("setversion").unwrap().to_owned()
                } else {
                    format_util::get_short_hash(&git::get_last_commit()[..]).to_owned()
                },
        subtitle: matches.value_of("subtitle").unwrap_or("").to_owned()
    });

    writer.write_header().ok().expect("failed to write header");
    writer.write_section("Bug Fixes", &sections.fixes).ok().expect("failed to write bugfixes");;
    writer.write_section("Features", &sections.features).ok().expect("failed to write features");;
    writer.write(&contents[..]).ok().expect("failed to write contents");;

    let end_nsec = time::get_time().nsec;
    let elapsed_mssec = (end_nsec - start_nsec) / 1000000;
    println!("changelog updated. (took {} ms)", elapsed_mssec);
}
<commit_msg>fix(main): create changelog.md if it doesn't exist<commit_after>#![crate_name = "clog"]
#![feature(plugin)]
#![plugin(regex_macros)]

extern crate regex;
extern crate time;

extern crate clap;

use git::LogReaderConfig;
use log_writer::{ LogWriter, LogWriterOptions };
use std::fs::File;
use std::io::Read;
use std::path::Path;
use std::borrow::ToOwned;

use clap::{App, Arg};

mod common;
mod git;
mod log_writer;
mod section_builder;
mod format_util;

fn main () {
    // Pull version from Cargo.toml
    let version = format!("{}.{}.{}{}",
                          env!("CARGO_PKG_VERSION_MAJOR"),
                          env!("CARGO_PKG_VERSION_MINOR"),
                          env!("CARGO_PKG_VERSION_PATCH"),
                          option_env!("CARGO_PKG_VERSION_PRE").unwrap_or(""));
    let matches = App::new("clog")
        .version(&version[..])
        .about("a conventional changelog for the rest of us")
        .arg(Arg::new("repository")
            .short("r")
            .long("repository")
            .takes_value(true)
            .help("e.g. https://github.com/thoughtram/clog"))
        .arg(Arg::new("setversion")
            .long("setversion")
            .help("e.g. 1.0.1")
            .takes_value(true))
        .arg(Arg::new("subtitle")
            .long("subtitle")
            .help("e.g. crazy-release-title")
            .takes_value(true))
        .arg(Arg::new("from")
            .help("e.g. 12a8546")
            .long("from")
            .takes_value(true))
        .arg(Arg::new("to")
            .long("to")
            .help("e.g. 8057684")
            .takes_value(true))
        .arg(Arg::new("from-latest-tag")
            .long("from-latest-tag")
            .help("uses the latest tag as starting point (ignores other --from parameters)")
            .mutually_excludes("from"))
        .get_matches();

    let start_nsec = time::get_time().nsec;

    let log_reader_config = LogReaderConfig {
        grep: "^feat|^fix|BREAKING'".to_owned(),
        format: "%H%n%s%n%b%n==END==".to_owned(),
        from: if matches.is_present("from-latest-tag") { Some(git::get_latest_tag()) } else { matches.value_of("from").map(|v| v.to_owned()) },
        to: matches.value_of("to").unwrap_or("").to_owned()
    };

    let commits = git::get_log_entries(log_reader_config);

    let sections = section_builder::build_sections(commits.clone());

    let mut contents = String::new();

    File::open(&Path::new("changelog.md")).map(|mut f| f.read_to_string(&mut contents).ok()).ok();
    //
    // match File::open(&Path::new("changelog.md")) {
    //     Ok(mut file) => { file.read_to_string(&mut contents).ok(); },
    //     Err(_) => { contents = "".to_owned(); }
    // }

    let mut file = File::create(&Path::new("changelog.md")).ok().unwrap();
    let mut writer = LogWriter::new(&mut file, LogWriterOptions {
        repository_link: matches.value_of("repository").unwrap_or(""),
        version: if matches.is_present("setversion") {
                    matches.value_of("setversion").unwrap().to_owned()
                } else {
                    format_util::get_short_hash(&git::get_last_commit()[..]).to_owned()
                },
        subtitle: matches.value_of("subtitle").unwrap_or("").to_owned()
    });

    writer.write_header().ok().expect("failed to write header");
    writer.write_section("Bug Fixes", &sections.fixes).ok().expect("failed to write bugfixes");;
    writer.write_section("Features", &sections.features).ok().expect("failed to write features");;
    writer.write(&contents[..]).ok().expect("failed to write contents");;

    let end_nsec = time::get_time().nsec;
    let elapsed_mssec = (end_nsec - start_nsec) / 1000000;
    println!("changelog updated. (took {} ms)", elapsed_mssec);
}
<|endoftext|>


<commit_before>//! Defines useful macros for glium usage.

/// Returns an implementation-defined type which implements the `Uniform` trait.
///
/// ## Example
///
/// ```rust
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// let uniforms = uniform! {
///     color: [1.0, 1.0, 0.0, 1.0],
///     some_value: 12i32
/// };
/// # }
/// ```
#[macro_export]
macro_rules! uniform {
    () => {
        $crate::uniforms::EmptyUniforms
    };

    ($field:ident: $value:expr) => {
        $crate::uniforms::UniformsStorage::new(stringify!($field), $value)
    };

    ($field1:ident: $value1:expr, $($field:ident: $value:expr),+) => {
        {
            let uniforms = $crate::uniforms::UniformsStorage::new(stringify!($field1), $value1);
            $(
                let uniforms = uniforms.add(stringify!($field), $value);
            )+
            uniforms
        }
    };

    ($($field:ident: $value:expr),*,) => {
        uniform!($($field: $value),*)
    };
}

/// Implements the `glium::vertex::Vertex` trait for the given type.
///
/// The parameters must be the name of the struct and the names of its fields.
///
/// ## Example
///
/// ```
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// #[derive(Copy, Clone)]
/// struct Vertex {
///     position: [f32; 3],
///     tex_coords: [f32; 2],
/// }
///
/// implement_vertex!(Vertex, position, tex_coords);
/// # }
/// ```
///
#[macro_export]
macro_rules! implement_vertex {
    ($struct_name:ident, $($field_name:ident),+) => (
        impl $crate::vertex::Vertex for $struct_name {
            fn build_bindings() -> $crate::vertex::VertexFormat {
                use std::borrow::Cow;

                vec![
                    $(
                        (
                            Cow::Borrowed(stringify!($field_name)),
                            {
                                let dummy: &$struct_name = unsafe { ::std::mem::transmute(0usize) };
                                let dummy_field = &dummy.$field_name;
                                let dummy_field: usize = unsafe { ::std::mem::transmute(dummy_field) };
                                dummy_field
                            },
                            {
                                fn attr_type_of_val<T: $crate::vertex::Attribute>(_: &T)
                                    -> $crate::vertex::AttributeType
                                {
                                    <T as $crate::vertex::Attribute>::get_type()
                                }
                                let dummy: &$struct_name = unsafe { ::std::mem::transmute(0usize) };
                                attr_type_of_val(&dummy.$field_name)
                            },
                        )
                    ),+
                ]
            }
        }
    );

    ($struct_name:ident, $($field_name:ident),+,) => (
        implement_vertex!($struct_name, $($field_name),+);
    );
}

/// Builds a program depending on the GLSL version supported by the backend.
///
/// This is implemented with successive calls to `is_glsl_version_supported()`.
///
/// ## Example
///
/// ```ignore       // TODO: no_run instead
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// # let display: glium::Display = unsafe { std::mem::uninitialized() };
/// let program = program!(&display,
///     300 => {
///         vertex: r#"
///             #version 300
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 300
///
///             out vec4 color;
///             fn main() {
///                 color = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
///     110 => {
///         vertex: r#"
///             #version 110
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 110
///
///             fn main() {
///                 gl_FragColor = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
///     300 es => {
///         vertex: r#"
///             #version 110
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 110
///
///             fn main() {
///                 gl_FragColor = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
/// );
/// # }
/// ```
///
#[macro_export]
macro_rules! program {
    ($facade:expr,) => (
        panic!("No version found");     // TODO: handle better
    );

    ($facade:expr,,$($rest:tt)*) => (
        program!($facade,$($rest)*)
    );

    ($facade:expr, $num:tt => $($rest:tt)*) => (
        {
            let context = $crate::backend::Facade::get_context($facade);
            let version = program!(_parse_num_gl $num);
            program!(_inner, context, version, $($rest)*)
        }
    );

    ($facade:expr, $num:tt es => $($rest:tt)*) => (
        {
            let context = $crate::backend::Facade::get_context($facade);
            let version = program!(_parse_num_gles $num);
            program!(_inner, context, version, $($rest)*)
        }
    );

    (_inner, $context:ident, $vers:ident, {$($ty:ident:$src:expr),+}$($rest:tt)*) => (
        if $context.is_glsl_version_supported(&$vers) {
            let _vertex_shader: &str = "";
            let _tessellation_control_shader: Option<&str> = None;
            let _tessellation_evaluation_shader: Option<&str> = None;
            let _geometry_shader: Option<&str> = None;
            let _fragment_shader: &str = "";

            $(
                program!(_program_ty $ty, $src, _vertex_shader, _tessellation_control_shader,
                         _tessellation_evaluation_shader, _geometry_shader, _fragment_shader);
            )+

            let input = $crate::program::ProgramCreationInput::SourceCode {
                vertex_shader: _vertex_shader,
                tessellation_control_shader: _tessellation_control_shader,
                tessellation_evaluation_shader: _tessellation_evaluation_shader,
                geometry_shader: _geometry_shader,
                fragment_shader: _fragment_shader,
                transform_feedback_varyings: None,
            };

            $crate::program::Program::new($context, input)

        } else {
            program!($context, $($rest)*)
        }
    );

    (_inner, $context:ident, $vers:ident, {$($ty:ident:$src:expr),+,}$($rest:tt)*) => (
        program!(_inner, $context, $vers, {$($ty:$src),+} $($rest)*);
    );

    (_program_ty vertex, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $vs = $src;
    );

    (_program_ty tessellation_control, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $tcs = Some($src);
    );

    (_program_ty tessellation_evaluation, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $tes = Some($src);
    );

    (_program_ty geometry, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $gs = Some($src);
    );

    (_program_ty fragment, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $fs = $src;
    );

    (_parse_num_gl $num:expr) => ($crate::Version($crate::Api::Gl, $num / 100, ($num % 100) / 10));
    (_parse_num_gl 100) => ($crate::Version($crate::Api::GlEs, 1, 0));
    (_parse_num_gles $num:expr) => ($crate::Version($crate::Api::GlEs, $num / 100, ($num % 100) / 10));
}

#[cfg(test)]
mod tests {
    #[test]
    fn trailing_comma_impl_uniforms() {
        let u = uniform!{ a: 5, b: 6, };
    }

    #[test]
    fn trailing_comma_impl_vertex() {
        #[derive(Copy, Clone)]
        struct Foo {
            pos: [f32; 2],
        }

        implement_vertex!(Foo, pos,);
    }
}
<commit_msg>Fix the program! macro with `100`<commit_after>//! Defines useful macros for glium usage.

/// Returns an implementation-defined type which implements the `Uniform` trait.
///
/// ## Example
///
/// ```rust
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// let uniforms = uniform! {
///     color: [1.0, 1.0, 0.0, 1.0],
///     some_value: 12i32
/// };
/// # }
/// ```
#[macro_export]
macro_rules! uniform {
    () => {
        $crate::uniforms::EmptyUniforms
    };

    ($field:ident: $value:expr) => {
        $crate::uniforms::UniformsStorage::new(stringify!($field), $value)
    };

    ($field1:ident: $value1:expr, $($field:ident: $value:expr),+) => {
        {
            let uniforms = $crate::uniforms::UniformsStorage::new(stringify!($field1), $value1);
            $(
                let uniforms = uniforms.add(stringify!($field), $value);
            )+
            uniforms
        }
    };

    ($($field:ident: $value:expr),*,) => {
        uniform!($($field: $value),*)
    };
}

/// Implements the `glium::vertex::Vertex` trait for the given type.
///
/// The parameters must be the name of the struct and the names of its fields.
///
/// ## Example
///
/// ```
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// #[derive(Copy, Clone)]
/// struct Vertex {
///     position: [f32; 3],
///     tex_coords: [f32; 2],
/// }
///
/// implement_vertex!(Vertex, position, tex_coords);
/// # }
/// ```
///
#[macro_export]
macro_rules! implement_vertex {
    ($struct_name:ident, $($field_name:ident),+) => (
        impl $crate::vertex::Vertex for $struct_name {
            fn build_bindings() -> $crate::vertex::VertexFormat {
                use std::borrow::Cow;

                vec![
                    $(
                        (
                            Cow::Borrowed(stringify!($field_name)),
                            {
                                let dummy: &$struct_name = unsafe { ::std::mem::transmute(0usize) };
                                let dummy_field = &dummy.$field_name;
                                let dummy_field: usize = unsafe { ::std::mem::transmute(dummy_field) };
                                dummy_field
                            },
                            {
                                fn attr_type_of_val<T: $crate::vertex::Attribute>(_: &T)
                                    -> $crate::vertex::AttributeType
                                {
                                    <T as $crate::vertex::Attribute>::get_type()
                                }
                                let dummy: &$struct_name = unsafe { ::std::mem::transmute(0usize) };
                                attr_type_of_val(&dummy.$field_name)
                            },
                        )
                    ),+
                ]
            }
        }
    );

    ($struct_name:ident, $($field_name:ident),+,) => (
        implement_vertex!($struct_name, $($field_name),+);
    );
}

/// Builds a program depending on the GLSL version supported by the backend.
///
/// This is implemented with successive calls to `is_glsl_version_supported()`.
///
/// ## Example
///
/// ```ignore       // TODO: no_run instead
/// # #[macro_use]
/// # extern crate glium;
/// # fn main() {
/// # let display: glium::Display = unsafe { std::mem::uninitialized() };
/// let program = program!(&display,
///     300 => {
///         vertex: r#"
///             #version 300
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 300
///
///             out vec4 color;
///             fn main() {
///                 color = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
///     110 => {
///         vertex: r#"
///             #version 110
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 110
///
///             fn main() {
///                 gl_FragColor = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
///     300 es => {
///         vertex: r#"
///             #version 110
///
///             fn main() {
///                 gl_Position = vec4(0.0, 0.0, 0.0, 1.0);
///             }
///         "#,
///         fragment: r#"
///             #version 110
///
///             fn main() {
///                 gl_FragColor = vec4(1.0, 1.0, 0.0, 1.0);
///             }
///         "#,
///     },
/// );
/// # }
/// ```
///
#[macro_export]
macro_rules! program {
    ($facade:expr,) => (
        panic!("No version found");     // TODO: handle better
    );

    ($facade:expr,,$($rest:tt)*) => (
        program!($facade,$($rest)*)
    );

    ($facade:expr, $num:tt => $($rest:tt)*) => (
        {
            let context = $crate::backend::Facade::get_context($facade);
            let version = program!(_parse_num_gl $num);
            program!(_inner, context, version, $($rest)*)
        }
    );

    ($facade:expr, $num:tt es => $($rest:tt)*) => (
        {
            let context = $crate::backend::Facade::get_context($facade);
            let version = program!(_parse_num_gles $num);
            program!(_inner, context, version, $($rest)*)
        }
    );

    (_inner, $context:ident, $vers:ident, {$($ty:ident:$src:expr),+}$($rest:tt)*) => (
        if $context.is_glsl_version_supported(&$vers) {
            let _vertex_shader: &str = "";
            let _tessellation_control_shader: Option<&str> = None;
            let _tessellation_evaluation_shader: Option<&str> = None;
            let _geometry_shader: Option<&str> = None;
            let _fragment_shader: &str = "";

            $(
                program!(_program_ty $ty, $src, _vertex_shader, _tessellation_control_shader,
                         _tessellation_evaluation_shader, _geometry_shader, _fragment_shader);
            )+

            let input = $crate::program::ProgramCreationInput::SourceCode {
                vertex_shader: _vertex_shader,
                tessellation_control_shader: _tessellation_control_shader,
                tessellation_evaluation_shader: _tessellation_evaluation_shader,
                geometry_shader: _geometry_shader,
                fragment_shader: _fragment_shader,
                transform_feedback_varyings: None,
            };

            $crate::program::Program::new($context, input)

        } else {
            program!($context, $($rest)*)
        }
    );

    (_inner, $context:ident, $vers:ident, {$($ty:ident:$src:expr),+,}$($rest:tt)*) => (
        program!(_inner, $context, $vers, {$($ty:$src),+} $($rest)*);
    );

    (_program_ty vertex, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $vs = $src;
    );

    (_program_ty tessellation_control, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $tcs = Some($src);
    );

    (_program_ty tessellation_evaluation, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $tes = Some($src);
    );

    (_program_ty geometry, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $gs = Some($src);
    );

    (_program_ty fragment, $src:expr, $vs:ident, $tcs:ident, $tes:ident, $gs:ident, $fs:ident) => (
        let $fs = $src;
    );

    (_parse_num_gl $num:expr) => (
        if $num == 100 {
            $crate::Version($crate::Api::GlEs, 1, 0)
        } else {
            $crate::Version($crate::Api::Gl, $num / 100, ($num % 100) / 10)
        }
    );

    (_parse_num_gles $num:expr) => ($crate::Version($crate::Api::GlEs, $num / 100, ($num % 100) / 10));
}

#[cfg(test)]
mod tests {
    #[test]
    fn trailing_comma_impl_uniforms() {
        let u = uniform!{ a: 5, b: 6, };
    }

    #[test]
    fn trailing_comma_impl_vertex() {
        #[derive(Copy, Clone)]
        struct Foo {
            pos: [f32; 2],
        }

        implement_vertex!(Foo, pos,);
    }
}
<|endoftext|>


<commit_before><commit_msg>Do not add newline to error message.<commit_after><|endoftext|>


<commit_before><commit_msg>added stdlib assert function<commit_after>use std::process::exit;

extern "C" {
    fn assert(val: bool) {
        if !val {
            exit(1);
        }
    }
}
<|endoftext|>


<commit_before>use std::cast;
use glfw;
use gl;
use gl::types::*;
use nalgebra::na::{Vec3, Mat4, Iso3};
use nalgebra::na;
use event;

/// Trait every camera must implement.
pub trait Camera {
    /*
     * Event handling.
     */
    /// Handle a mouse event.
    fn handle_event(&mut self, &glfw::Window, &event::Event);

    /*
     * Transformation-related methods.
     */
    /// The camera position.
    fn eye(&self) -> Vec3<f64>; // FIXME: should this be here?
    /// The camera view transform.
    fn view_transform(&self) -> Iso3<f64>;
    /// The transformation applied by the camera to transform a point in world coordinates to
    /// a point in device coordinates.
    fn transformation(&self) -> Mat4<f64>;
    /// The transformation applied by the camera to transform point in device coordinates to a
    /// point in world coordinate.
    fn inv_transformation(&self) -> Mat4<f64>;
    /// The clipping planes, aka. (`znear`, `zfar`).
    fn clip_planes(&self) -> (f64, f64); // FIXME: should this be here?

    /*
     * Update & upload
     */
    // FIXME: dont use glfw::Window
    /// Update the camera. This is called once at the beginning of the render loop.
    fn update(&mut self, window: &glfw::Window);

    /// Upload the camera transfomation to the gpu. This cam be called multiple times on the render
    /// loop.
    fn upload(&self, _pass: uint, view_location: i32) {
        self.upload_mat(view_location, self.transformation());
    }

    // TODO: is there an extra copy here? or does rust avoid it?
    fn upload_mat(&self, view_location: i32, homo_base: Mat4<f64>) {
        let mut homo = homo_base.clone();
        na::transpose(&mut homo);

        let homo32: Mat4<GLfloat> = na::cast(homo);

        unsafe {
            gl::UniformMatrix4fv(
                view_location,
                1,
                gl::FALSE as u8,
                cast::transmute(&homo32));
        }
    }

    fn num_passes(&self) -> uint { 1u }

    fn start_pass(&self, _pass: uint, _window: &glfw::Window) { }

    fn render_complete(&self, _window: &glfw::Window) { }
}
<commit_msg>Remove an unnecessary clone.<commit_after>use std::cast;
use glfw;
use gl;
use gl::types::*;
use nalgebra::na::{Vec3, Mat4, Iso3};
use nalgebra::na;
use event;

/// Trait every camera must implement.
pub trait Camera {
    /*
     * Event handling.
     */
    /// Handle a mouse event.
    fn handle_event(&mut self, &glfw::Window, &event::Event);

    /*
     * Transformation-related methods.
     */
    /// The camera position.
    fn eye(&self) -> Vec3<f64>; // FIXME: should this be here?
    /// The camera view transform.
    fn view_transform(&self) -> Iso3<f64>;
    /// The transformation applied by the camera to transform a point in world coordinates to
    /// a point in device coordinates.
    fn transformation(&self) -> Mat4<f64>;
    /// The transformation applied by the camera to transform point in device coordinates to a
    /// point in world coordinate.
    fn inv_transformation(&self) -> Mat4<f64>;
    /// The clipping planes, aka. (`znear`, `zfar`).
    fn clip_planes(&self) -> (f64, f64); // FIXME: should this be here?

    /*
     * Update & upload
     */
    // FIXME: dont use glfw::Window
    /// Update the camera. This is called once at the beginning of the render loop.
    fn update(&mut self, window: &glfw::Window);

    /// Upload the camera transfomation to the gpu. This cam be called multiple times on the render
    /// loop.
    fn upload(&self, _pass: uint, view_location: i32) {
        self.upload_mat(view_location, self.transformation());
    }

    // TODO: is there an extra copy here? or does rust avoid it?
    fn upload_mat(&self, view_location: i32, homo_base: Mat4<f64>) {
        let mut homo = homo_base;
        na::transpose(&mut homo);

        let homo32: Mat4<GLfloat> = na::cast(homo);

        unsafe {
            gl::UniformMatrix4fv(
                view_location,
                1,
                gl::FALSE as u8,
                cast::transmute(&homo32));
        }
    }

    fn num_passes(&self) -> uint { 1u }

    fn start_pass(&self, _pass: uint, _window: &glfw::Window) { }

    fn render_complete(&self, _window: &glfw::Window) { }
}
<|endoftext|>


<commit_before><commit_msg>Rewrite if-let binding to simple if<commit_after><|endoftext|>


<commit_before><commit_msg>chore(Kernels): Add a "mini-CLI" for development purposes<commit_after>//! Mini CLI for testing this crate at the command line without compiling the whole `stencila` binary.
//! Run using `cargo run --all-features` in this crate (`--all-features` is needed to include optional dependencies)
//! The `cfg` flags are just to prevent clippy complaining when running `cargo clippy` without
//! the `--features=cli` flag.

#[cfg(feature = "cli")]
use kernels::commands::Command;

#[cfg(feature = "cli")]
cli_utils::mini_main!(Command);

#[cfg(not(feature = "cli"))]
fn main() {}
<|endoftext|>


<commit_before><commit_msg>new_data_error is now private to bitmap module.<commit_after><|endoftext|>


<commit_before>// FIXME: The way this module sets up tests is a relic and more convoluted
// than it needs to be

import option;
import std::getopts;
import std::test;
import str;
import vec;
import task;

import core::result;
import result::{ok, err};

import comm::port;
import comm::chan;
import comm::send;
import comm::recv;

import common::config;
import common::mode_run_pass;
import common::mode_run_fail;
import common::mode_compile_fail;
import common::mode_pretty;
import common::mode;
import util::logv;

fn main(args: [str]) {
    let config = parse_config(args);
    log_config(config);
    run_tests(config);
}

fn parse_config(args: [str]) -> config {
    let opts =
        [getopts::reqopt("compile-lib-path"), getopts::reqopt("run-lib-path"),
         getopts::reqopt("rustc-path"), getopts::reqopt("src-base"),
         getopts::reqopt("build-base"), getopts::reqopt("aux-base"),
         getopts::reqopt("stage-id"),
         getopts::reqopt("mode"), getopts::optflag("ignored"),
         getopts::optopt("runtool"), getopts::optopt("rustcflags"),
         getopts::optflag("verbose")];

    check (vec::is_not_empty(args));
    let args_ = vec::tail(args);
    let match =
        alt getopts::getopts(args_, opts) {
          ok(m) { m }
          err(f) { fail getopts::fail_str(f) }
        };

    ret {compile_lib_path: getopts::opt_str(match, "compile-lib-path"),
         run_lib_path: getopts::opt_str(match, "run-lib-path"),
         rustc_path: getopts::opt_str(match, "rustc-path"),
         src_base: getopts::opt_str(match, "src-base"),
         build_base: getopts::opt_str(match, "build-base"),
         aux_base: getopts::opt_str(match, "aux-base"),
         stage_id: getopts::opt_str(match, "stage-id"),
         mode: str_mode(getopts::opt_str(match, "mode")),
         run_ignored: getopts::opt_present(match, "ignored"),
         filter:
             if vec::len(match.free) > 0u {
                 option::some(match.free[0])
             } else { option::none },
         runtool: getopts::opt_maybe_str(match, "runtool"),
         rustcflags: getopts::opt_maybe_str(match, "rustcflags"),
         verbose: getopts::opt_present(match, "verbose")};
}

fn log_config(config: config) {
    let c = config;
    logv(c, #fmt["configuration:"]);
    logv(c, #fmt["compile_lib_path: %s", config.compile_lib_path]);
    logv(c, #fmt["run_lib_path: %s", config.run_lib_path]);
    logv(c, #fmt["rustc_path: %s", config.rustc_path]);
    logv(c, #fmt["src_base: %s", config.src_base]);
    logv(c, #fmt["build_base: %s", config.build_base]);
    logv(c, #fmt["stage_id: %s", config.stage_id]);
    logv(c, #fmt["mode: %s", mode_str(config.mode)]);
    logv(c, #fmt["run_ignored: %b", config.run_ignored]);
    logv(c, #fmt["filter: %s", opt_str(config.filter)]);
    logv(c, #fmt["runtool: %s", opt_str(config.runtool)]);
    logv(c, #fmt["rustcflags: %s", opt_str(config.rustcflags)]);
    logv(c, #fmt["verbose: %b", config.verbose]);
    logv(c, #fmt["\n"]);
}

fn opt_str(maybestr: option<str>) -> str {
    alt maybestr { option::some(s) { s } option::none { "(none)" } }
}

fn str_opt(maybestr: str) -> option<str> {
    if maybestr != "(none)" { option::some(maybestr) } else { option::none }
}

fn str_mode(s: str) -> mode {
    alt s {
      "compile-fail" { mode_compile_fail }
      "run-fail" { mode_run_fail }
      "run-pass" { mode_run_pass }
      "pretty" { mode_pretty }
      _ { fail "invalid mode" }
    }
}

fn mode_str(mode: mode) -> str {
    alt mode {
      mode_compile_fail { "compile-fail" }
      mode_run_fail { "run-fail" }
      mode_run_pass { "run-pass" }
      mode_pretty { "pretty" }
    }
}

fn run_tests(config: config) {
    let opts = test_opts(config);
    let tests = make_tests(config);
    let res = test::run_tests_console(opts, tests);
    if !res { fail "Some tests failed"; }
}

fn test_opts(config: config) -> test::test_opts {
    {filter:
         alt config.filter {
           option::some(s) { option::some(s) }
           option::none { option::none }
         },
     run_ignored: config.run_ignored}
}

fn make_tests(config: config) -> [test::test_desc] {
    #debug("making tests from %s", config.src_base);
    let tests = [];
    for file: str in os::list_dir(config.src_base) {
        let file = file;
        #debug("inspecting file %s", file);
        if is_test(config, file) {
            tests += [make_test(config, file)]
        }
    }
    ret tests;
}

fn is_test(config: config, testfile: str) -> bool {
    // Pretty-printer does not work with .rc files yet
    let valid_extensions =
        alt config.mode { mode_pretty { [".rs"] } _ { [".rc", ".rs"] } };
    let invalid_prefixes = [".", "#", "~"];
    let name = path::basename(testfile);

    let valid = false;

    for ext in valid_extensions {
        if str::ends_with(name, ext) { valid = true; }
    }

    for pre in invalid_prefixes {
        if str::starts_with(name, pre) { valid = false; }
    }

    ret valid;
}

fn make_test(config: config, testfile: str) ->
   test::test_desc {
    {
        name: make_test_name(config, testfile),
        fn: make_test_closure(config, testfile),
        ignore: header::is_test_ignored(config, testfile),
        should_fail: false
    }
}

fn make_test_name(config: config, testfile: str) -> str {
    #fmt["[%s] %s", mode_str(config.mode), testfile]
}

fn make_test_closure(config: config, testfile: str) -> test::test_fn {
    ret {||
        runtest::run(config, copy testfile);
    };
}

// Local Variables:
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// End:
<commit_msg>Associate FIXME with an issue in compiletest.rs<commit_after>// FIXME (Issue #1984): The way this module sets up tests is a relic and more
// convoluted than it needs to be

import option;
import std::getopts;
import std::test;
import str;
import vec;
import task;

import core::result;
import result::{ok, err};

import comm::port;
import comm::chan;
import comm::send;
import comm::recv;

import common::config;
import common::mode_run_pass;
import common::mode_run_fail;
import common::mode_compile_fail;
import common::mode_pretty;
import common::mode;
import util::logv;

fn main(args: [str]) {
    let config = parse_config(args);
    log_config(config);
    run_tests(config);
}

fn parse_config(args: [str]) -> config {
    let opts =
        [getopts::reqopt("compile-lib-path"), getopts::reqopt("run-lib-path"),
         getopts::reqopt("rustc-path"), getopts::reqopt("src-base"),
         getopts::reqopt("build-base"), getopts::reqopt("aux-base"),
         getopts::reqopt("stage-id"),
         getopts::reqopt("mode"), getopts::optflag("ignored"),
         getopts::optopt("runtool"), getopts::optopt("rustcflags"),
         getopts::optflag("verbose")];

    check (vec::is_not_empty(args));
    let args_ = vec::tail(args);
    let match =
        alt getopts::getopts(args_, opts) {
          ok(m) { m }
          err(f) { fail getopts::fail_str(f) }
        };

    ret {compile_lib_path: getopts::opt_str(match, "compile-lib-path"),
         run_lib_path: getopts::opt_str(match, "run-lib-path"),
         rustc_path: getopts::opt_str(match, "rustc-path"),
         src_base: getopts::opt_str(match, "src-base"),
         build_base: getopts::opt_str(match, "build-base"),
         aux_base: getopts::opt_str(match, "aux-base"),
         stage_id: getopts::opt_str(match, "stage-id"),
         mode: str_mode(getopts::opt_str(match, "mode")),
         run_ignored: getopts::opt_present(match, "ignored"),
         filter:
             if vec::len(match.free) > 0u {
                 option::some(match.free[0])
             } else { option::none },
         runtool: getopts::opt_maybe_str(match, "runtool"),
         rustcflags: getopts::opt_maybe_str(match, "rustcflags"),
         verbose: getopts::opt_present(match, "verbose")};
}

fn log_config(config: config) {
    let c = config;
    logv(c, #fmt["configuration:"]);
    logv(c, #fmt["compile_lib_path: %s", config.compile_lib_path]);
    logv(c, #fmt["run_lib_path: %s", config.run_lib_path]);
    logv(c, #fmt["rustc_path: %s", config.rustc_path]);
    logv(c, #fmt["src_base: %s", config.src_base]);
    logv(c, #fmt["build_base: %s", config.build_base]);
    logv(c, #fmt["stage_id: %s", config.stage_id]);
    logv(c, #fmt["mode: %s", mode_str(config.mode)]);
    logv(c, #fmt["run_ignored: %b", config.run_ignored]);
    logv(c, #fmt["filter: %s", opt_str(config.filter)]);
    logv(c, #fmt["runtool: %s", opt_str(config.runtool)]);
    logv(c, #fmt["rustcflags: %s", opt_str(config.rustcflags)]);
    logv(c, #fmt["verbose: %b", config.verbose]);
    logv(c, #fmt["\n"]);
}

fn opt_str(maybestr: option<str>) -> str {
    alt maybestr { option::some(s) { s } option::none { "(none)" } }
}

fn str_opt(maybestr: str) -> option<str> {
    if maybestr != "(none)" { option::some(maybestr) } else { option::none }
}

fn str_mode(s: str) -> mode {
    alt s {
      "compile-fail" { mode_compile_fail }
      "run-fail" { mode_run_fail }
      "run-pass" { mode_run_pass }
      "pretty" { mode_pretty }
      _ { fail "invalid mode" }
    }
}

fn mode_str(mode: mode) -> str {
    alt mode {
      mode_compile_fail { "compile-fail" }
      mode_run_fail { "run-fail" }
      mode_run_pass { "run-pass" }
      mode_pretty { "pretty" }
    }
}

fn run_tests(config: config) {
    let opts = test_opts(config);
    let tests = make_tests(config);
    let res = test::run_tests_console(opts, tests);
    if !res { fail "Some tests failed"; }
}

fn test_opts(config: config) -> test::test_opts {
    {filter:
         alt config.filter {
           option::some(s) { option::some(s) }
           option::none { option::none }
         },
     run_ignored: config.run_ignored}
}

fn make_tests(config: config) -> [test::test_desc] {
    #debug("making tests from %s", config.src_base);
    let tests = [];
    for file: str in os::list_dir(config.src_base) {
        let file = file;
        #debug("inspecting file %s", file);
        if is_test(config, file) {
            tests += [make_test(config, file)]
        }
    }
    ret tests;
}

fn is_test(config: config, testfile: str) -> bool {
    // Pretty-printer does not work with .rc files yet
    let valid_extensions =
        alt config.mode { mode_pretty { [".rs"] } _ { [".rc", ".rs"] } };
    let invalid_prefixes = [".", "#", "~"];
    let name = path::basename(testfile);

    let valid = false;

    for ext in valid_extensions {
        if str::ends_with(name, ext) { valid = true; }
    }

    for pre in invalid_prefixes {
        if str::starts_with(name, pre) { valid = false; }
    }

    ret valid;
}

fn make_test(config: config, testfile: str) ->
   test::test_desc {
    {
        name: make_test_name(config, testfile),
        fn: make_test_closure(config, testfile),
        ignore: header::is_test_ignored(config, testfile),
        should_fail: false
    }
}

fn make_test_name(config: config, testfile: str) -> str {
    #fmt["[%s] %s", mode_str(config.mode), testfile]
}

fn make_test_closure(config: config, testfile: str) -> test::test_fn {
    ret {||
        runtest::run(config, copy testfile);
    };
}

// Local Variables:
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// End:
<|endoftext|>


<commit_before>// Copyright 2012-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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

/*!
 * Atomic types
 */

use unstable::intrinsics;
use cast;
use option::{Option,Some,None};

pub struct AtomicFlag {
    priv v:int
}

pub struct AtomicBool {
    priv v:uint
}

pub struct AtomicInt {
    priv v:int
}

pub struct AtomicUint {
    priv v:uint
}

pub struct AtomicPtr<T> {
    priv p:~T
}

pub enum Ordering {
    Release,
    Acquire,
    SeqCst
}

impl AtomicFlag {

    fn new() -> AtomicFlag {
        AtomicFlag { v: 0 }
    }

    /**
     * Clears the atomic flag
     */
    #[inline(always)]
    fn clear(&mut self, order:Ordering) {
        unsafe {atomic_store(&mut self.v, 0, order)}
    }

    #[inline(always)]
    /**
     * Sets the flag if it was previously unset, returns the previous value of the
     * flag.
     */
    fn test_and_set(&mut self, order:Ordering) -> bool {
        unsafe {atomic_compare_and_swap(&mut self.v, 0, 1, order) > 0}
    }
}

impl AtomicBool {
    fn new(v:bool) -> AtomicBool {
        AtomicBool { v: if v { 1 } else { 0 } }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> bool {
        unsafe { atomic_load(&self.v, order) > 0 }
    }

    #[inline(always)]
    fn store(&mut self, val:bool, order:Ordering) {
        let val = if val { 1 } else { 0 };

        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:bool, order:Ordering) -> bool {
        let val = if val { 1 } else { 0 };

        unsafe { atomic_swap(&mut self.v, val, order) > 0}
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: bool, new: bool, order:Ordering) -> bool {
        let old = if old { 1 } else { 0 };
        let new = if new { 1 } else { 0 };

        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) > 0 }
    }
}

impl AtomicInt {
    fn new(v:int) -> AtomicInt {
        AtomicInt { v:v }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> int {
        unsafe { atomic_load(&self.v, order) }
    }

    #[inline(always)]
    fn store(&mut self, val:int, order:Ordering) {
        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_swap(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: int, new: int, order:Ordering) -> int {
        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) }
    }

    #[inline(always)]
    fn fetch_add(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_add(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn fetch_sub(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_sub(&mut self.v, val, order) }
    }
}

impl AtomicUint {
    fn new(v:uint) -> AtomicUint {
        AtomicUint { v:v }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> uint {
        unsafe { atomic_load(&self.v, order) }
    }

    #[inline(always)]
    fn store(&mut self, val:uint, order:Ordering) {
        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_swap(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: uint, new: uint, order:Ordering) -> uint {
        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) }
    }

    #[inline(always)]
    fn fetch_add(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_add(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn fetch_sub(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_sub(&mut self.v, val, order) }
    }
}

impl<T> AtomicPtr<T> {
    fn new(p:~T) -> AtomicPtr<T> {
        AtomicPtr { p:p }
    }

    /**
     * Atomically swaps the stored pointer with the one given.
     *
     * Returns None if the pointer stored has been taken
     */
    #[inline(always)]
    fn swap(&mut self, ptr:~T, order:Ordering) -> Option<~T> {
        unsafe {
            let p = atomic_swap(&mut self.p, ptr, order);
            let pv : &uint = cast::transmute(&p);

            if *pv == 0 {
                None
            } else {
                Some(p)
            }
        }
    }

    /**
     * Atomically takes the stored pointer out.
     *
     * Returns None if it was already taken.
     */
    #[inline(always)]
    fn take(&mut self, order:Ordering) -> Option<~T> {
        unsafe { self.swap(cast::transmute(0), order) }
    }

    /**
     * Atomically stores the given pointer, this will overwrite
     * and previous value stored.
     */
    #[inline(always)]
    fn give(&mut self, ptr:~T, order:Ordering) {
        let _ = self.swap(ptr, order);
    }

    /**
     * Checks to see if the stored pointer has been taken.
     */
    fn taken(&self, order:Ordering) -> bool {
        unsafe {
            let p : ~T = atomic_load(&self.p, order);

            let pv : &uint = cast::transmute(&p);

            cast::forget(p);
            *pv == 0
        }
    }
}

#[inline(always)]
pub unsafe fn atomic_store<T>(dst: &mut T, val: T, order:Ordering) {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    match order {
        Release => intrinsics::atomic_store_rel(dst, val),
        _       => intrinsics::atomic_store(dst, val)
    }
}

#[inline(always)]
pub unsafe fn atomic_load<T>(dst: &T, order:Ordering) -> T {
    let dst = cast::transmute(dst);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_load_acq(dst),
        _       => intrinsics::atomic_load(dst)
    })
}

#[inline(always)]
pub unsafe fn atomic_swap<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xchg_acq(dst, val),
        Release => intrinsics::atomic_xchg_rel(dst, val),
        _       => intrinsics::atomic_xchg(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_add<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xadd_acq(dst, val),
        Release => intrinsics::atomic_xadd_rel(dst, val),
        _       => intrinsics::atomic_xadd(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_sub<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xsub_acq(dst, val),
        Release => intrinsics::atomic_xsub_rel(dst, val),
        _       => intrinsics::atomic_xsub(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_compare_and_swap<T>(dst:&mut T, old:T, new:T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let old = cast::transmute(old);
    let new = cast::transmute(new);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_cxchg_acq(dst, old, new),
        Release => intrinsics::atomic_cxchg_rel(dst, old, new),
        _       => intrinsics::atomic_cxchg(dst, old, new),
    })
}

#[cfg(test)]
mod test {
    use option::*;
    use super::*;

    #[test]
    fn flag() {
        let mut flg = AtomicFlag::new();
        assert!(!flg.test_and_set(SeqCst));
        assert!(flg.test_and_set(SeqCst));

        flg.clear(SeqCst);
        assert!(!flg.test_and_set(SeqCst));
    }

    #[test]
    fn pointer_swap() {
        let mut p = AtomicPtr::new(~1);
        let a = ~2;

        let b = p.swap(a, SeqCst);

        assert_eq!(b, Some(~1));
        assert_eq!(p.take(SeqCst), Some(~2));
    }

    #[test]
    fn pointer_take() {
        let mut p = AtomicPtr::new(~1);

        assert_eq!(p.take(SeqCst), Some(~1));
        assert_eq!(p.take(SeqCst), None);
        assert!(p.taken(SeqCst));

        let p2 = ~2;
        p.give(p2, SeqCst);

        assert_eq!(p.take(SeqCst), Some(~2));
    }

}
<commit_msg>Make AtomicPtr use *mut, instead of ~<commit_after>// Copyright 2012-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 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

/*!
 * Atomic types
 */

use unstable::intrinsics;
use cast;
use option::{Option,Some,None};

pub struct AtomicFlag {
    priv v: int
}

pub struct AtomicBool {
    priv v: uint
}

pub struct AtomicInt {
    priv v: int
}

pub struct AtomicUint {
    priv v: uint
}

pub struct AtomicPtr<T> {
    priv p: *mut T
}

pub enum Ordering {
    Release,
    Acquire,
    SeqCst
}

impl AtomicFlag {

    fn new() -> AtomicFlag {
        AtomicFlag { v: 0 }
    }

    /**
     * Clears the atomic flag
     */
    #[inline(always)]
    fn clear(&mut self, order:Ordering) {
        unsafe {atomic_store(&mut self.v, 0, order)}
    }

    #[inline(always)]
    /**
     * Sets the flag if it was previously unset, returns the previous value of the
     * flag.
     */
    fn test_and_set(&mut self, order:Ordering) -> bool {
        unsafe {atomic_compare_and_swap(&mut self.v, 0, 1, order) > 0}
    }
}

impl AtomicBool {
    fn new(v:bool) -> AtomicBool {
        AtomicBool { v: if v { 1 } else { 0 } }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> bool {
        unsafe { atomic_load(&self.v, order) > 0 }
    }

    #[inline(always)]
    fn store(&mut self, val:bool, order:Ordering) {
        let val = if val { 1 } else { 0 };

        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:bool, order:Ordering) -> bool {
        let val = if val { 1 } else { 0 };

        unsafe { atomic_swap(&mut self.v, val, order) > 0}
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: bool, new: bool, order:Ordering) -> bool {
        let old = if old { 1 } else { 0 };
        let new = if new { 1 } else { 0 };

        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) > 0 }
    }
}

impl AtomicInt {
    fn new(v:int) -> AtomicInt {
        AtomicInt { v:v }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> int {
        unsafe { atomic_load(&self.v, order) }
    }

    #[inline(always)]
    fn store(&mut self, val:int, order:Ordering) {
        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_swap(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: int, new: int, order:Ordering) -> int {
        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) }
    }

    #[inline(always)]
    fn fetch_add(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_add(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn fetch_sub(&mut self, val:int, order:Ordering) -> int {
        unsafe { atomic_sub(&mut self.v, val, order) }
    }
}

impl AtomicUint {
    fn new(v:uint) -> AtomicUint {
        AtomicUint { v:v }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> uint {
        unsafe { atomic_load(&self.v, order) }
    }

    #[inline(always)]
    fn store(&mut self, val:uint, order:Ordering) {
        unsafe { atomic_store(&mut self.v, val, order); }
    }

    #[inline(always)]
    fn swap(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_swap(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: uint, new: uint, order:Ordering) -> uint {
        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) }
    }

    #[inline(always)]
    fn fetch_add(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_add(&mut self.v, val, order) }
    }

    #[inline(always)]
    fn fetch_sub(&mut self, val:uint, order:Ordering) -> uint {
        unsafe { atomic_sub(&mut self.v, val, order) }
    }
}

impl<T> AtomicPtr<T> {
    fn new(p:*mut T) -> AtomicPtr<T> {
        AtomicPtr { p:p }
    }

    #[inline(always)]
    fn load(&self, order:Ordering) -> *mut T {
        unsafe { atomic_load(&self.p, order) }
    }

    #[inline(always)]
    fn store(&mut self, ptr:*mut T, order:Ordering) {
        unsafe { atomic_store(&mut self.p, ptr, order); }
    }

    #[inline(always)]
    fn swap(&mut self, ptr:*mut T, order:Ordering) -> *mut T {
        unsafe { atomic_swap(&mut self.p, ptr, order) }
    }

    #[inline(always)]
    fn compare_and_swap(&mut self, old: *mut T, new: *mut T, order:Ordering) -> *mut T {
        unsafe { atomic_compare_and_swap(&mut self.v, old, new, order) }
    }
}

#[inline(always)]
pub unsafe fn atomic_store<T>(dst: &mut T, val: T, order:Ordering) {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    match order {
        Release => intrinsics::atomic_store_rel(dst, val),
        _       => intrinsics::atomic_store(dst, val)
    }
}

#[inline(always)]
pub unsafe fn atomic_load<T>(dst: &T, order:Ordering) -> T {
    let dst = cast::transmute(dst);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_load_acq(dst),
        _       => intrinsics::atomic_load(dst)
    })
}

#[inline(always)]
pub unsafe fn atomic_swap<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xchg_acq(dst, val),
        Release => intrinsics::atomic_xchg_rel(dst, val),
        _       => intrinsics::atomic_xchg(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_add<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xadd_acq(dst, val),
        Release => intrinsics::atomic_xadd_rel(dst, val),
        _       => intrinsics::atomic_xadd(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_sub<T>(dst: &mut T, val: T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let val = cast::transmute(val);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_xsub_acq(dst, val),
        Release => intrinsics::atomic_xsub_rel(dst, val),
        _       => intrinsics::atomic_xsub(dst, val)
    })
}

#[inline(always)]
pub unsafe fn atomic_compare_and_swap<T>(dst:&mut T, old:T, new:T, order: Ordering) -> T {
    let dst = cast::transmute(dst);
    let old = cast::transmute(old);
    let new = cast::transmute(new);

    cast::transmute(match order {
        Acquire => intrinsics::atomic_cxchg_acq(dst, old, new),
        Release => intrinsics::atomic_cxchg_rel(dst, old, new),
        _       => intrinsics::atomic_cxchg(dst, old, new),
    })
}

#[cfg(test)]
mod test {
    use option::*;
    use super::*;

    #[test]
    fn flag() {
        let mut flg = AtomicFlag::new();
        assert!(!flg.test_and_set(SeqCst));
        assert!(flg.test_and_set(SeqCst));

        flg.clear(SeqCst);
        assert!(!flg.test_and_set(SeqCst));
    }

    #[test]
    fn pointer_swap() {
        let mut p = AtomicPtr::new(~1);
        let a = ~2;

        let b = p.swap(a, SeqCst);

        assert_eq!(b, Some(~1));
        assert_eq!(p.take(SeqCst), Some(~2));
    }

    #[test]
    fn pointer_take() {
        let mut p = AtomicPtr::new(~1);

        assert_eq!(p.take(SeqCst), Some(~1));
        assert_eq!(p.take(SeqCst), None);
        assert!(p.taken(SeqCst));

        let p2 = ~2;
        p.give(p2, SeqCst);

        assert_eq!(p.take(SeqCst), Some(~2));
    }

}
<|endoftext|>


<commit_before><commit_msg>Improve chiptune formatting<commit_after><|endoftext|>


<commit_before><commit_msg>Revert disastrous api change<commit_after><|endoftext|>


<commit_before><commit_msg>fn change(&[(event::Event, event::Action)]) -> io::Result<()>;<commit_after><|endoftext|>