<commit_before><commit_msg>add: Move common functions in 'install' and 'uninstall' to ops::utils<commit_after>use std::collections::{BTreeMap, BTreeSet};
use std::env;
use std::io::prelude::*;
use std::io::SeekFrom;
use std::path::{Path, PathBuf};

use semver::VersionReq;
use serde::{Deserialize, Serialize};

use crate::core::package::PackageSet;
use crate::core::source::SourceMap;
use crate::core::PackageId;
use crate::core::{Dependency, Package, Source, SourceId};
use crate::sources::PathSource;
use crate::util::errors::{CargoResult, CargoResultExt};
use crate::util::{internal, Config, ToSemver};
use crate::util::{FileLock, Filesystem};

#[derive(Deserialize, Serialize)]
#[serde(untagged)]
pub enum CrateListing {
    V1(CrateListingV1),
    Empty(Empty),
}

#[derive(Deserialize, Serialize)]
#[serde(deny_unknown_fields)]
pub struct Empty {}

#[derive(Deserialize, Serialize)]
pub struct CrateListingV1 {
    pub v1: BTreeMap<PackageId, BTreeSet<String>>,
}

pub fn resolve_root(flag: Option<&str>, config: &Config) -> CargoResult<Filesystem> {
    let config_root = config.get_path("install.root")?;
    Ok(flag
        .map(PathBuf::from)
        .or_else(|| env::var_os("CARGO_INSTALL_ROOT").map(PathBuf::from))
        .or_else(move || config_root.map(|v| v.val))
        .map(Filesystem::new)
        .unwrap_or_else(|| config.home().clone()))
}

pub fn path_source<'a>(source_id: SourceId, config: &'a Config) -> CargoResult<PathSource<'a>> {
    let path = source_id
        .url()
        .to_file_path()
        .map_err(|()| failure::format_err!("path sources must have a valid path"))?;
    Ok(PathSource::new(&path, source_id, config))
}

pub fn select_pkg<'a, T>(
    mut source: T,
    name: Option<&str>,
    vers: Option<&str>,
    config: &Config,
    needs_update: bool,
    list_all: &mut dyn FnMut(&mut T) -> CargoResult<Vec<Package>>,
) -> CargoResult<(Package, Box<dyn Source + 'a>)>
where
    T: Source + 'a,
{
    if needs_update {
        source.update()?;
    }

    match name {
        Some(name) => {
            let vers = match vers {
                Some(v) => {
                    // If the version begins with character <, >, =, ^, ~ parse it as a
                    // version range, otherwise parse it as a specific version
                    let first = v.chars().nth(0).ok_or_else(|| {
                        failure::format_err!("no version provided for the `--vers` flag")
                    })?;

                    match first {
                        '<' | '>' | '=' | '^' | '~' => match v.parse::<VersionReq>() {
                            Ok(v) => Some(v.to_string()),
                            Err(_) => failure::bail!(
                                "the `--vers` provided, `{}`, is \
                                       not a valid semver version requirement\n\n
                                       Please have a look at \
                                       http://doc.crates.io/specifying-dependencies.html \
                                       for the correct format",
                                v
                            ),
                        },
                        _ => match v.to_semver() {
                            Ok(v) => Some(format!("={}", v)),
                            Err(_) => {
                                let mut msg = format!(
                                    "\
                                     the `--vers` provided, `{}`, is \
                                     not a valid semver version\n\n\
                                     historically Cargo treated this \
                                     as a semver version requirement \
                                     accidentally\nand will continue \
                                     to do so, but this behavior \
                                     will be removed eventually",
                                    v
                                );

                                // If it is not a valid version but it is a valid version
                                // requirement, add a note to the warning
                                if v.parse::<VersionReq>().is_ok() {
                                    msg.push_str(&format!(
                                        "\nif you want to specify semver range, \
                                         add an explicit qualifier, like ^{}",
                                        v
                                    ));
                                }
                                config.shell().warn(&msg)?;
                                Some(v.to_string())
                            }
                        },
                    }
                }
                None => None,
            };
            let vers = vers.as_ref().map(|s| &**s);
            let vers_spec = if vers.is_none() && source.source_id().is_registry() {
                // Avoid pre-release versions from crate.io
                // unless explicitly asked for
                Some("*")
            } else {
                vers
            };
            let dep = Dependency::parse_no_deprecated(name, vers_spec, source.source_id())?;
            let deps = source.query_vec(&dep)?;
            let pkgid = match deps.iter().map(|p| p.package_id()).max() {
                Some(pkgid) => pkgid,
                None => {
                    let vers_info = vers
                        .map(|v| format!(" with version `{}`", v))
                        .unwrap_or_default();
                    failure::bail!(
                        "could not find `{}` in {}{}",
                        name,
                        source.source_id(),
                        vers_info
                    )
                }
            };

            let pkg = {
                let mut map = SourceMap::new();
                map.insert(Box::new(&mut source));
                PackageSet::new(&[pkgid], map, config)?
                    .get_one(pkgid)?
                    .clone()
            };
            Ok((pkg, Box::new(source)))
        }
        None => {
            let candidates = list_all(&mut source)?;
            let binaries = candidates
                .iter()
                .filter(|cand| cand.targets().iter().filter(|t| t.is_bin()).count() > 0);
            let examples = candidates
                .iter()
                .filter(|cand| cand.targets().iter().filter(|t| t.is_example()).count() > 0);
            let pkg = match one(binaries, |v| multi_err("binaries", v))? {
                Some(p) => p,
                None => match one(examples, |v| multi_err("examples", v))? {
                    Some(p) => p,
                    None => failure::bail!(
                        "no packages found with binaries or \
                         examples"
                    ),
                },
            };
            return Ok((pkg.clone(), Box::new(source)));

            fn multi_err(kind: &str, mut pkgs: Vec<&Package>) -> String {
                pkgs.sort_unstable_by_key(|a| a.name());
                format!(
                    "multiple packages with {} found: {}",
                    kind,
                    pkgs.iter()
                        .map(|p| p.name().as_str())
                        .collect::<Vec<_>>()
                        .join(", ")
                )
            }
        }
    }
}

pub fn one<I, F>(mut i: I, f: F) -> CargoResult<Option<I::Item>>
where
    I: Iterator,
    F: FnOnce(Vec<I::Item>) -> String,
{
    match (i.next(), i.next()) {
        (Some(i1), Some(i2)) => {
            let mut v = vec![i1, i2];
            v.extend(i);
            Err(failure::format_err!("{}", f(v)))
        }
        (Some(i), None) => Ok(Some(i)),
        (None, _) => Ok(None),
    }
}

pub fn read_crate_list(file: &FileLock) -> CargoResult<CrateListingV1> {
    let listing = (|| -> CargoResult<_> {
        let mut contents = String::new();
        file.file().read_to_string(&mut contents)?;
        let listing =
            toml::from_str(&contents).chain_err(|| internal("invalid TOML found for metadata"))?;
        match listing {
            CrateListing::V1(v1) => Ok(v1),
            CrateListing::Empty(_) => Ok(CrateListingV1 {
                v1: BTreeMap::new(),
            }),
        }
    })()
    .chain_err(|| {
        failure::format_err!(
            "failed to parse crate metadata at `{}`",
            file.path().to_string_lossy()
        )
    })?;
    Ok(listing)
}

pub fn write_crate_list(file: &FileLock, listing: CrateListingV1) -> CargoResult<()> {
    (|| -> CargoResult<_> {
        let mut file = file.file();
        file.seek(SeekFrom::Start(0))?;
        file.set_len(0)?;
        let data = toml::to_string(&CrateListing::V1(listing))?;
        file.write_all(data.as_bytes())?;
        Ok(())
    })()
    .chain_err(|| {
        failure::format_err!(
            "failed to write crate metadata at `{}`",
            file.path().to_string_lossy()
        )
    })?;
    Ok(())
}

pub fn metadata(config: &Config, root: &Filesystem) -> CargoResult<FileLock> {
    root.open_rw(Path::new(".crates.toml"), config, "crate metadata")
}
<|endoftext|>


<commit_before><commit_msg>adding default_handler.rs<commit_after>use bt_messages::Message;
//use bt_messages::Message::{Choke, Unchoke};
use buffered_reader::BufferedReader;
use std::net::TcpStream;
use std::sync::mpsc::Sender;

pub struct DefaultHandler;

/// Handles messages. This is a cheap way to force reactive style
pub trait Handler {
    type MessageType;
    fn handle(&mut self, message: Self::MessageType, peer: &mut Peer) -> Action;
}

impl DefaultHandler {
    pub fn new () -> DefaultHandler {
        DefaultHandler
    }
}

pub enum Action {
    None,
    Respond(Vec<u8>)
}

/// The default algorithm
impl Handler for DefaultHandler {
    type MessageType = Message;
    #[inline]
    fn handle (&mut self, message: Message, peer: &mut Peer) -> Action {
        println!("{:?}", message);
        match message {
            Message::Choke => {
                peer.set_choked(true);
                Action::None
            },
            Message::Unchoke => {
                peer.set_choked(false);
                Action::None
            },
            _ => {
                Action::None
            }
        }
    }
}

pub struct Peer {
    pub id: String,
    pub chan: Sender<Action>,
    stream: TcpStream,
    state: State
}

#[derive(Debug)]
struct State {
    choked: bool,
    //the intention is that eventually we will support growable files. so going with vector
    bitfield: Vec<u8>
}

impl Peer {
    pub fn new (id:String, chan: Sender<Action>, stream: TcpStream) -> Peer {
        Peer {
            id: id,
            chan: chan,
            stream: stream,
            state: State {
                choked: true,
                bitfield: Vec::new()
            }
        }
    }

    fn set_choked (&mut self, choked: bool) {
        self.state.choked = choked;
    }
}

<|endoftext|>


<commit_before>use std::collections::VecDeque;
use std::env::{set_current_dir, current_dir, home_dir};
use std::path::PathBuf;
use super::status::{SUCCESS, FAILURE};

pub struct DirectoryStack {
    dirs: VecDeque<PathBuf>, // The top is always the current directory
    max_size: usize,
}

impl DirectoryStack {
    pub fn new() -> Result<DirectoryStack, &'static str> {
        let mut dirs: VecDeque<PathBuf> = VecDeque::new();
        if let Ok(curr_dir) = current_dir() {
            dirs.push_front(curr_dir);
            Ok(DirectoryStack {
                dirs: dirs,
                max_size: 1000, // TODO don't hardcode this size, make it configurable
            })
        } else {
            Err("Failed to get current directory when building directory stack")
        }
    }

    pub fn popd<I: IntoIterator>(&mut self, _: I) -> i32
        where I::Item: AsRef<str>
    {
        if self.dirs.len() < 2 {
            println!("Directory stack is empty");
            return FAILURE;
        }
        if let Some(dir) = self.dirs.get(self.dirs.len() - 2) {
            if let Err(err) = set_current_dir(dir) {
                println!("{}: Failed to switch to directory {}", err, dir.display());
                return FAILURE;
            }
        }
        self.dirs.pop_back();
        self.print_dirs();
        SUCCESS
    }

    pub fn pushd<I: IntoIterator>(&mut self, args: I) -> i32
        where I::Item: AsRef<str>
    {
        if let Some(dir) = args.into_iter().nth(1) {
            let result = self.change_and_push_dir(dir.as_ref());
            self.print_dirs();
            result
        } else {
            println!("No directory provided");
            FAILURE
        }
    }

    pub fn cd<I: IntoIterator>(&mut self, args: I) -> i32
        where I::Item: AsRef<str>
    {
        if let Some(dir) = args.into_iter().nth(1) {
            let dir = dir.as_ref();
            self.change_and_push_dir(dir)
        } else {
            if let Some(home) = home_dir() {
                if let Some(home) = home.to_str() {
                    self.change_and_push_dir(home)
                } else {
                    println!("Failed to convert home directory to str");
                    FAILURE
                }
            } else {
                println!("Failed to get home directory");
                FAILURE
            }
        }
    }

    pub fn change_and_push_dir(&mut self, dir: &str) -> i32
    {
        match (set_current_dir(dir), current_dir()) {
            (Ok(()), Ok(cur_dir)) => {
                self.push_dir(cur_dir);
                SUCCESS
            }
            (Err(err), _) => {
                println!("Failed to set current dir to {}: {}", dir, err);
                FAILURE
            }
            (_, _) => FAILURE // This should not happen
        }
    }

    fn push_dir(&mut self, path: PathBuf) {
        self.dirs.push_front(path);
        self.dirs.truncate(self.max_size);
    }

    pub fn dirs<I: IntoIterator>(&self, _: I) -> i32
        where I::Item: AsRef<str>
    {
        self.print_dirs();
        SUCCESS
    }

    fn print_dirs(&self) {
        let dir = self.dirs.iter().fold(String::new(), |acc, dir| {
            acc + " " + dir.to_str().unwrap_or("No directory found")
        });
        println!("{}", dir.trim_left());
    }
}
<commit_msg>Add `cd -` and fix bug in `popd`<commit_after>use std::collections::VecDeque;
use std::env::{set_current_dir, current_dir, home_dir};
use std::path::PathBuf;
use super::status::{SUCCESS, FAILURE};

pub struct DirectoryStack {
    dirs: VecDeque<PathBuf>, // The top is always the current directory
    max_size: usize,
}

impl DirectoryStack {
    pub fn new() -> Result<DirectoryStack, &'static str> {
        let mut dirs: VecDeque<PathBuf> = VecDeque::new();
        if let Ok(curr_dir) = current_dir() {
            dirs.push_front(curr_dir);
            Ok(DirectoryStack {
                dirs: dirs,
                max_size: 1000, // TODO don't hardcode this size, make it configurable
            })
        } else {
            Err("Failed to get current directory when building directory stack")
        }
    }

    pub fn popd<I: IntoIterator>(&mut self, _: I) -> i32
        where I::Item: AsRef<str>
    {
        if let Some(dir) = self.get_previous_dir() {
            if let Err(err) = set_current_dir(dir) {
                println!("{}: Failed to switch to directory {}", err, dir.display());
                return FAILURE;
            }
        } else {
            println!("Directory stack is empty");
            return FAILURE;
        }
        self.dirs.pop_front();
        self.print_dirs();
        SUCCESS
    }

    pub fn pushd<I: IntoIterator>(&mut self, args: I) -> i32
        where I::Item: AsRef<str>
    {
        if let Some(dir) = args.into_iter().nth(1) {
            let result = self.change_and_push_dir(dir.as_ref());
            self.print_dirs();
            result
        } else {
            println!("No directory provided");
            FAILURE
        }
    }

    pub fn cd<I: IntoIterator>(&mut self, args: I) -> i32
        where I::Item: AsRef<str>
    {
        if let Some(dir) = args.into_iter().nth(1) {
            let dir = dir.as_ref();
            if dir == "-" {
                self.switch_to_previous_directory()
            } else {
                self.change_and_push_dir(dir)
            }
        } else {
            self.switch_to_home_directory()
        }
    }

    fn switch_to_home_directory(&mut self) -> i32 {
        if let Some(home) = home_dir() {
            if let Some(home) = home.to_str() {
                self.change_and_push_dir(home)
            } else {
                println!("Failed to convert home directory to str");
                FAILURE
            }
        } else {
            println!("Failed to get home directory");
            FAILURE
        }
    }

    fn switch_to_previous_directory(&mut self) -> i32 {
        if let Some(prev) = self.get_previous_dir()
                                .map(|path| path.to_string_lossy().to_string()) {
            println!("{}", prev);
            self.change_and_push_dir(&prev)
        } else {
            println!("No previous directory to switch to");
            FAILURE
        }
    }

    fn get_previous_dir(&self) -> Option<&PathBuf> {
        if self.dirs.len() < 2 {
            None
        } else {
            self.dirs.get(1)
        }
    }

    pub fn change_and_push_dir(&mut self, dir: &str) -> i32 {
        match (set_current_dir(dir), current_dir()) {
            (Ok(()), Ok(cur_dir)) => {
                self.push_dir(cur_dir);
                SUCCESS
            }
            (Err(err), _) => {
                println!("Failed to set current dir to {}: {}", dir, err);
                FAILURE
            }
            (_, _) => FAILURE // This should not happen
        }
    }

    fn push_dir(&mut self, path: PathBuf) {
        self.dirs.push_front(path);
        self.dirs.truncate(self.max_size);
    }

    pub fn dirs<I: IntoIterator>(&self, _: I) -> i32
        where I::Item: AsRef<str>
    {
        self.print_dirs();
        SUCCESS
    }

    fn print_dirs(&self) {
        let dir = self.dirs.iter().fold(String::new(), |acc, dir| {
            acc + " " + dir.to_str().unwrap_or("No directory found")
        });
        println!("{}", dir.trim_left());
    }
}
<|endoftext|>


<commit_before>#[macro_export]
macro_rules! generate_error_imports {
    () => {
        use std::error::Error;
        use std::fmt::Error as FmtError;
        use std::fmt::{Display, Formatter};

        use $crate::into::IntoError;
    }
}

#[macro_export]
macro_rules! generate_error_module {
    ( $exprs:item ) => {
        pub mod error {
            generate_error_imports!();
            $exprs
        }
    }
}

#[macro_export]
macro_rules! generate_custom_error_types {
    {
        $name: ident,
        $kindname: ident,
        $customMemberTypeName: ident,
        $($kind:ident => $string:expr),*
    } => {
        #[derive(Clone, Copy, Debug, PartialEq)]
        pub enum $kindname {
            $( $kind ),*
        }

        impl Display for $kindname {

            fn fmt(&self, fmt: &mut Formatter) -> Result<(), FmtError> {
                let s = match *self {
                    $( $kindname::$kind => $string ),*
                };
                try!(write!(fmt, "{}", s));
                Ok(())
            }

        }

        impl IntoError for $kindname {
            type Target = $name;

            fn into_error(self) -> Self::Target {
                $name::new(self, None)
            }

            fn into_error_with_cause(self, cause: Box<Error>) -> Self::Target {
                $name::new(self, Some(cause))
            }

        }

        #[derive(Debug)]
        pub struct $name {
            err_type: $kindname,
            cause: Option<Box<Error>>,
            custom_data: Option<$customMemberTypeName>,
        }

        impl $name {

            pub fn new(errtype: $kindname, cause: Option<Box<Error>>) -> $name {
                $name {
                    err_type: errtype,
                    cause: cause,
                    custom_data: None,
                }
            }

            pub fn err_type(&self) -> $kindname {
                self.err_type
            }

            pub fn with_custom_data(mut self, custom: $customMemberTypeName) -> $name {
                self.custom_data = Some(custom);
                self
            }

        }

        impl Into<$name> for $kindname {

            fn into(self) -> $name {
                $name::new(self, None)
            }

        }

        impl Display for $name {

            fn fmt(&self, fmt: &mut Formatter) -> Result<(), FmtError> {
                try!(write!(fmt, "[{}]", self.err_type));
                Ok(())
            }

        }

        impl Error for $name {

            fn description(&self) -> &str {
                match self.err_type {
                    $( $kindname::$kind => $string ),*
                }
            }

            fn cause(&self) -> Option<&Error> {
                self.cause.as_ref().map(|e| &**e)
            }

        }

    }
}

#[macro_export]
macro_rules! generate_result_helper {
    (
        $name: ident,
        $kindname: ident
    ) => {
        /// Trait to replace
        ///
        /// ```ignore
        /// foo.map_err(Box::new).map_err(|e| SomeType::SomeErrorKind.into_error_with_cause(e))
        /// // or:
        /// foo.map_err(|e| SomeType::SomeErrorKind.into_error_with_cause(Box::new(e)))
        /// ```
        ///
        /// with much nicer
        ///
        /// ```ignore
        /// foo.map_err_into(SomeType::SomeErrorKind)
        /// ```
        ///
        pub trait MapErrInto<T> {
            fn map_err_into(self, error_kind: $kindname) -> Result<T, $name>;
        }

        impl<T, E: Error + 'static> MapErrInto<T> for Result<T, E> {

            fn map_err_into(self, error_kind: $kindname) -> Result<T, $name> {
                self.map_err(Box::new)
                    .map_err(|e| error_kind.into_error_with_cause(e))
            }

        }
    }
}

#[macro_export]
macro_rules! generate_option_helper {
    (
        $name: ident,
        $kindname: ident
    ) => {
        /// Trait to replace
        ///
        /// ```ignore
        /// foo.ok_or(SomeType::SomeErrorKind.into_error())
        /// ```
        ///
        /// with
        ///
        /// ```ignore
        /// foo.ok_or_errkind(SomeType::SomeErrorKind)
        /// ```
        pub trait OkOrErr<T> {
            fn ok_or_errkind(self, kind: $kindname) -> Result<T, $name>;
        }

        impl<T> OkOrErr<T> for Option<T> {

            fn ok_or_errkind(self, kind: $kindname) -> Result<T, $name> {
                self.ok_or(kind.into_error())
            }

        }
    }
}

#[macro_export]
macro_rules! generate_error_types {
    (
        $name: ident,
        $kindname: ident,
        $($kind:ident => $string:expr),*
    ) => {
        #[derive(Debug, Clone, Eq, PartialEq, Ord, PartialOrd, Copy)]
        pub struct SomeNotExistingTypeWithATypeNameNoOneWillEverChoose {}
        generate_custom_error_types!($name, $kindname,
                                     SomeNotExistingTypeWithATypeNameNoOneWillEverChoose,
                                     $($kind => $string),*);

        generate_result_helper!($name, $kindname);
        generate_option_helper!($name, $kindname);
    }
}

#[cfg(test)]
mod test {

    generate_error_module!(
        generate_error_types!(TestError, TestErrorKind,
            TestErrorKindA => "testerrorkind a",
            TestErrorKindB => "testerrorkind B");
    );

    #[derive(Debug, Clone, Eq, PartialEq, Ord, PartialOrd, Copy)]
    pub struct CustomData {
        pub test: i32,
        pub othr: i64,
    }

    generate_error_imports!();

    generate_custom_error_types!(CustomTestError, CustomTestErrorKind,
        CustomData,
        CustomErrorKindA => "customerrorkind a",
        CustomErrorKindB => "customerrorkind B");

    impl CustomTestError {
        pub fn test(&self) -> i32 {
            match self.custom_data {
                Some(t) => t.test,
                None => 0,
            }
        }

        pub fn bar(&self) -> i64 {
            match self.custom_data {
                Some(t) => t.othr,
                None => 0,
            }
        }
    }

    #[test]
    fn test_a() {
        use self::error::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindA;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
    }

    #[test]
    fn test_b() {
        use self::error::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind B"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e));

    }

    #[test]
    fn test_ab() {
        use std::error::Error;
        use self::error::{TestError, TestErrorKind};

        let kinda = TestErrorKind::TestErrorKindA;
        let kindb = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kinda));
        assert_eq!(String::from("testerrorkind B"), format!("{}", kindb));

        let e = TestError::new(kinda, Some(Box::new(TestError::new(kindb, None))));
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
        assert_eq!(TestErrorKind::TestErrorKindA, e.err_type());
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e.cause().unwrap()));
    }

    pub mod anothererrormod {
        generate_error_imports!();
        generate_error_types!(TestError, TestErrorKind,
            TestErrorKindA => "testerrorkind a",
            TestErrorKindB => "testerrorkind B");
    }

    #[test]
    fn test_other_a() {
        use self::anothererrormod::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindA;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
    }

    #[test]
    fn test_other_b() {
        use self::anothererrormod::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind B"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e));

    }

    #[test]
    fn test_other_ab() {
        use std::error::Error;
        use self::anothererrormod::{TestError, TestErrorKind};

        let kinda = TestErrorKind::TestErrorKindA;
        let kindb = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kinda));
        assert_eq!(String::from("testerrorkind B"), format!("{}", kindb));

        let e = TestError::new(kinda, Some(Box::new(TestError::new(kindb, None))));
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
        assert_eq!(TestErrorKind::TestErrorKindA, e.err_type());
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e.cause().unwrap()));
    }

    #[test]
    fn test_error_kind_mapping() {
        use std::io::{Error, ErrorKind};
        use self::error::{OkOrErr, MapErrInto};
        use self::error::TestErrorKind;

        let err : Result<(), _> = Err(Error::new(ErrorKind::Other, ""));
        let err : Result<(), _> = err.map_err_into(TestErrorKind::TestErrorKindA);

        assert!(err.is_err());
        let err = err.unwrap_err();

        match err.err_type() {
            TestErrorKind::TestErrorKindA => assert!(true),
            _ => assert!(false),
        }
    }

    #[test]
    fn test_error_kind_double_mapping() {
        use std::io::{Error, ErrorKind};
        use self::error::{OkOrErr, MapErrInto};
        use self::error::TestErrorKind;

        let err : Result<(), _> = Err(Error::new(ErrorKind::Other, ""));
        let err : Result<(), _> = err.map_err_into(TestErrorKind::TestErrorKindA)
                                     .map_err_into(TestErrorKind::TestErrorKindB);

        assert!(err.is_err());
        let err = err.unwrap_err();
        match err.err_type() {
            TestErrorKind::TestErrorKindB => assert!(true),
            _ => assert!(false),
        }

        // not sure how to test that the inner error is of TestErrorKindA, actually...
        match err.cause() {
            Some(_) => assert!(true),
            None    => assert!(false),
        }

    }

    #[test]
    fn test_error_option_good() {
        use self::error::{OkOrErr, MapErrInto};
        use self::error::TestErrorKind;

        let something = Some(1);
        match something.ok_or_errkind(TestErrorKind::TestErrorKindA) {
            Ok(1) => assert!(true),
            _     => assert!(false),
        }
    }

    #[test]
    fn test_error_option_bad() {
        use self::error::{OkOrErr, MapErrInto};
        use self::error::TestErrorKind;

        let something : Option<i32> = None;
        match something.ok_or_errkind(TestErrorKind::TestErrorKindA) {
            Ok(_)  => assert!(false),
            Err(e) => assert!(true),
        }
    }

}
<commit_msg>libimagerror: Eliminate unused imports<commit_after>#[macro_export]
macro_rules! generate_error_imports {
    () => {
        use std::error::Error;
        use std::fmt::Error as FmtError;
        use std::fmt::{Display, Formatter};

        use $crate::into::IntoError;
    }
}

#[macro_export]
macro_rules! generate_error_module {
    ( $exprs:item ) => {
        pub mod error {
            generate_error_imports!();
            $exprs
        }
    }
}

#[macro_export]
macro_rules! generate_custom_error_types {
    {
        $name: ident,
        $kindname: ident,
        $customMemberTypeName: ident,
        $($kind:ident => $string:expr),*
    } => {
        #[derive(Clone, Copy, Debug, PartialEq)]
        pub enum $kindname {
            $( $kind ),*
        }

        impl Display for $kindname {

            fn fmt(&self, fmt: &mut Formatter) -> Result<(), FmtError> {
                let s = match *self {
                    $( $kindname::$kind => $string ),*
                };
                try!(write!(fmt, "{}", s));
                Ok(())
            }

        }

        impl IntoError for $kindname {
            type Target = $name;

            fn into_error(self) -> Self::Target {
                $name::new(self, None)
            }

            fn into_error_with_cause(self, cause: Box<Error>) -> Self::Target {
                $name::new(self, Some(cause))
            }

        }

        #[derive(Debug)]
        pub struct $name {
            err_type: $kindname,
            cause: Option<Box<Error>>,
            custom_data: Option<$customMemberTypeName>,
        }

        impl $name {

            pub fn new(errtype: $kindname, cause: Option<Box<Error>>) -> $name {
                $name {
                    err_type: errtype,
                    cause: cause,
                    custom_data: None,
                }
            }

            pub fn err_type(&self) -> $kindname {
                self.err_type
            }

            pub fn with_custom_data(mut self, custom: $customMemberTypeName) -> $name {
                self.custom_data = Some(custom);
                self
            }

        }

        impl Into<$name> for $kindname {

            fn into(self) -> $name {
                $name::new(self, None)
            }

        }

        impl Display for $name {

            fn fmt(&self, fmt: &mut Formatter) -> Result<(), FmtError> {
                try!(write!(fmt, "[{}]", self.err_type));
                Ok(())
            }

        }

        impl Error for $name {

            fn description(&self) -> &str {
                match self.err_type {
                    $( $kindname::$kind => $string ),*
                }
            }

            fn cause(&self) -> Option<&Error> {
                self.cause.as_ref().map(|e| &**e)
            }

        }

    }
}

#[macro_export]
macro_rules! generate_result_helper {
    (
        $name: ident,
        $kindname: ident
    ) => {
        /// Trait to replace
        ///
        /// ```ignore
        /// foo.map_err(Box::new).map_err(|e| SomeType::SomeErrorKind.into_error_with_cause(e))
        /// // or:
        /// foo.map_err(|e| SomeType::SomeErrorKind.into_error_with_cause(Box::new(e)))
        /// ```
        ///
        /// with much nicer
        ///
        /// ```ignore
        /// foo.map_err_into(SomeType::SomeErrorKind)
        /// ```
        ///
        pub trait MapErrInto<T> {
            fn map_err_into(self, error_kind: $kindname) -> Result<T, $name>;
        }

        impl<T, E: Error + 'static> MapErrInto<T> for Result<T, E> {

            fn map_err_into(self, error_kind: $kindname) -> Result<T, $name> {
                self.map_err(Box::new)
                    .map_err(|e| error_kind.into_error_with_cause(e))
            }

        }
    }
}

#[macro_export]
macro_rules! generate_option_helper {
    (
        $name: ident,
        $kindname: ident
    ) => {
        /// Trait to replace
        ///
        /// ```ignore
        /// foo.ok_or(SomeType::SomeErrorKind.into_error())
        /// ```
        ///
        /// with
        ///
        /// ```ignore
        /// foo.ok_or_errkind(SomeType::SomeErrorKind)
        /// ```
        pub trait OkOrErr<T> {
            fn ok_or_errkind(self, kind: $kindname) -> Result<T, $name>;
        }

        impl<T> OkOrErr<T> for Option<T> {

            fn ok_or_errkind(self, kind: $kindname) -> Result<T, $name> {
                self.ok_or(kind.into_error())
            }

        }
    }
}

#[macro_export]
macro_rules! generate_error_types {
    (
        $name: ident,
        $kindname: ident,
        $($kind:ident => $string:expr),*
    ) => {
        #[derive(Debug, Clone, Eq, PartialEq, Ord, PartialOrd, Copy)]
        pub struct SomeNotExistingTypeWithATypeNameNoOneWillEverChoose {}
        generate_custom_error_types!($name, $kindname,
                                     SomeNotExistingTypeWithATypeNameNoOneWillEverChoose,
                                     $($kind => $string),*);

        generate_result_helper!($name, $kindname);
        generate_option_helper!($name, $kindname);
    }
}

#[cfg(test)]
mod test {

    generate_error_module!(
        generate_error_types!(TestError, TestErrorKind,
            TestErrorKindA => "testerrorkind a",
            TestErrorKindB => "testerrorkind B");
    );

    #[derive(Debug, Clone, Eq, PartialEq, Ord, PartialOrd, Copy)]
    pub struct CustomData {
        pub test: i32,
        pub othr: i64,
    }

    generate_error_imports!();

    generate_custom_error_types!(CustomTestError, CustomTestErrorKind,
        CustomData,
        CustomErrorKindA => "customerrorkind a",
        CustomErrorKindB => "customerrorkind B");

    impl CustomTestError {
        pub fn test(&self) -> i32 {
            match self.custom_data {
                Some(t) => t.test,
                None => 0,
            }
        }

        pub fn bar(&self) -> i64 {
            match self.custom_data {
                Some(t) => t.othr,
                None => 0,
            }
        }
    }

    #[test]
    fn test_a() {
        use self::error::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindA;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
    }

    #[test]
    fn test_b() {
        use self::error::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind B"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e));

    }

    #[test]
    fn test_ab() {
        use std::error::Error;
        use self::error::{TestError, TestErrorKind};

        let kinda = TestErrorKind::TestErrorKindA;
        let kindb = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kinda));
        assert_eq!(String::from("testerrorkind B"), format!("{}", kindb));

        let e = TestError::new(kinda, Some(Box::new(TestError::new(kindb, None))));
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
        assert_eq!(TestErrorKind::TestErrorKindA, e.err_type());
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e.cause().unwrap()));
    }

    pub mod anothererrormod {
        generate_error_imports!();
        generate_error_types!(TestError, TestErrorKind,
            TestErrorKindA => "testerrorkind a",
            TestErrorKindB => "testerrorkind B");
    }

    #[test]
    fn test_other_a() {
        use self::anothererrormod::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindA;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
    }

    #[test]
    fn test_other_b() {
        use self::anothererrormod::{TestError, TestErrorKind};

        let kind = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind B"), format!("{}", kind));

        let e = TestError::new(kind, None);
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e));

    }

    #[test]
    fn test_other_ab() {
        use std::error::Error;
        use self::anothererrormod::{TestError, TestErrorKind};

        let kinda = TestErrorKind::TestErrorKindA;
        let kindb = TestErrorKind::TestErrorKindB;
        assert_eq!(String::from("testerrorkind a"), format!("{}", kinda));
        assert_eq!(String::from("testerrorkind B"), format!("{}", kindb));

        let e = TestError::new(kinda, Some(Box::new(TestError::new(kindb, None))));
        assert_eq!(String::from("[testerrorkind a]"), format!("{}", e));
        assert_eq!(TestErrorKind::TestErrorKindA, e.err_type());
        assert_eq!(String::from("[testerrorkind B]"), format!("{}", e.cause().unwrap()));
    }

    #[test]
    fn test_error_kind_mapping() {
        use std::io::{Error, ErrorKind};
        use self::error::MapErrInto;
        use self::error::TestErrorKind;

        let err : Result<(), _> = Err(Error::new(ErrorKind::Other, ""));
        let err : Result<(), _> = err.map_err_into(TestErrorKind::TestErrorKindA);

        assert!(err.is_err());
        let err = err.unwrap_err();

        match err.err_type() {
            TestErrorKind::TestErrorKindA => assert!(true),
            _ => assert!(false),
        }
    }

    #[test]
    fn test_error_kind_double_mapping() {
        use std::io::{Error, ErrorKind};
        use self::error::MapErrInto;
        use self::error::TestErrorKind;

        let err : Result<(), _> = Err(Error::new(ErrorKind::Other, ""));
        let err : Result<(), _> = err.map_err_into(TestErrorKind::TestErrorKindA)
                                     .map_err_into(TestErrorKind::TestErrorKindB);

        assert!(err.is_err());
        let err = err.unwrap_err();
        match err.err_type() {
            TestErrorKind::TestErrorKindB => assert!(true),
            _ => assert!(false),
        }

        // not sure how to test that the inner error is of TestErrorKindA, actually...
        match err.cause() {
            Some(_) => assert!(true),
            None    => assert!(false),
        }

    }

    #[test]
    fn test_error_option_good() {
        use self::error::OkOrErr;
        use self::error::TestErrorKind;

        let something = Some(1);
        match something.ok_or_errkind(TestErrorKind::TestErrorKindA) {
            Ok(1) => assert!(true),
            _     => assert!(false),
        }
    }

    #[test]
    fn test_error_option_bad() {
        use self::error::OkOrErr;
        use self::error::TestErrorKind;

        let something : Option<i32> = None;
        match something.ok_or_errkind(TestErrorKind::TestErrorKindA) {
            Ok(_)  => assert!(false),
            Err(e) => assert!(true),
        }
    }

}
<|endoftext|>


<commit_before><commit_msg>chore: associated type within trait<commit_after><|endoftext|>


<commit_before><commit_msg>v0.3.3.5 - Testing<commit_after><|endoftext|>


<commit_before><commit_msg>Move back to a single-type model with an SSL field that is only present when the secure feature flag is used<commit_after><|endoftext|>


<commit_before>#![crate_name = "piston"]
#![deny(missing_docs)]
#![warn(dead_code)]
#![feature(default_type_params)]
#![feature(globs)]

//! A user friendly game engine written in Rust.

#[cfg(feature = "include_gfx")]
extern crate gfx;
#[cfg(feature = "include_gfx")]
extern crate gfx_graphics;
extern crate opengl_graphics;
extern crate sdl2;
extern crate sdl2_window;

// Crates used to reexport.
extern crate "ai_behavior" as ai_behavior_lib;
extern crate "vecmath" as vecmath_lib;
extern crate "shader_version" as shader_version_lib;
extern crate "image" as image_lib;
extern crate "graphics" as graphics_lib;
extern crate "input" as input_lib;
extern crate "event" as event_lib;
extern crate "window" as window_lib;
extern crate "cam" as cam_lib;
extern crate "current" as current_lib;
extern crate "quack" as quack_lib;
extern crate "fps_counter" as fps_counter_lib;
extern crate "drag_controller" as drag_controller_lib;
extern crate "read_color" as read_color_lib;
extern crate "select_color" as select_color_lib;

// Reexports.
pub use current_lib as current;
pub use quack_lib as quack;
pub use ai_behavior_lib as ai_behavior;
pub use shader_version_lib as shader_version;
pub use image_lib as image;
pub use graphics_lib as graphics;
pub use vecmath_lib as vecmath;
pub use input_lib as input;
pub use event_lib as event;
pub use window_lib as window;
pub use cam_lib as cam;
pub use fps_counter_lib as fps_counter;
pub use drag_controller_lib as drag_controller;

pub use sdl2_window::Sdl2Window as WindowBackEnd;
pub use event::{
    Event,
    Events,
    NoWindow,
    RenderArgs,
    UpdateArgs,
    WindowSettings,
};

pub use quack::{
    Action,
    ActOn,
    Get,
    GetFrom,
    Set,
    SetAt,
};
pub use current::{
    Current,
    CurrentGuard,
};

#[cfg(feature = "include_gfx")]
use gfx_graphics::G2D;
#[cfg(feature = "include_gfx")]
use gfx::{ DeviceHelper };
use opengl_graphics::Gl;
use fps_counter::FPSCounter;

use std::rc::Rc;
use std::cell::RefCell;

pub mod color {
    //! Rexported libraries for working with colors
    pub use read_color_lib as read_color;
    pub use select_color_lib as select_color;
}

fn start_window(
    opengl: shader_version::OpenGL,
    window_settings: WindowSettings,
    f: ||
) {
    let mut window = Rc::new(RefCell::new(WindowBackEnd::new(
        opengl,
        window_settings,
    )));
    let mut gl = Rc::new(RefCell::new(Gl::new(opengl)));
    let mut fps_counter = Rc::new(RefCell::new(FPSCounter::new()));

    let window_guard = CurrentGuard::new(&mut window);
    let gl_guard = CurrentGuard::new(&mut gl);
    let fps_counter_guard = CurrentGuard::new(&mut fps_counter);

    f();

    drop(window_guard);
    drop(gl_guard);
    drop(fps_counter_guard);
}

#[cfg(feature = "include_gfx")]
fn start_gfx(f: ||) {
    let window = current_window();

    let mut device = Rc::new(RefCell::new(gfx::GlDevice::new(|s| unsafe {
        std::mem::transmute(sdl2::video::gl_get_proc_address(s))
    })));
    let mut g2d = Rc::new(RefCell::new(G2D::new(device.borrow_mut().deref_mut())));
    let mut renderer = Rc::new(RefCell::new(device.borrow_mut().create_renderer()));
    let event::window::Size([w, h]) = window.get();
    let mut frame = Rc::new(RefCell::new(gfx::Frame::new(w as u16, h as u16)));

    let device_guard = CurrentGuard::new(&mut device);
    let g2d_guard = CurrentGuard::new(&mut g2d);
    let renderer_guard = CurrentGuard::new(&mut renderer);
    let frame_guard = CurrentGuard::new(&mut frame);

    f();

    drop(g2d_guard);
    drop(renderer_guard);
    drop(frame_guard);
    drop(device_guard);
}

#[cfg(not(feature = "include_gfx"))]
fn start_gfx(f: ||) {
    f();
}

/// Initializes window and sets up current objects.
pub fn start(
    opengl: shader_version::OpenGL,
    window_settings: WindowSettings,
    f: ||
) {
    start_window(opengl, window_settings, || {
        if cfg!(feature = "include_gfx") {
            start_gfx(|| f());
        } else {
            f();
        }
    });
}

/// The current window
pub fn current_window() -> Rc<RefCell<WindowBackEnd>> {
    unsafe {
        Current::<Rc<RefCell<WindowBackEnd>>>::new().clone()
    }
}
/// The current Gfx device
#[cfg(feature = "include_gfx")]
pub fn current_gfx_device() -> Rc<RefCell<gfx::GlDevice>> {
    unsafe {
        Current::<Rc<RefCell<gfx::GlDevice>>>::new().clone()
    }
}
/// The current opengl_graphics back-end
pub fn current_gl() -> Rc<RefCell<Gl>> {
    unsafe {
        Current::<Rc<RefCell<Gl>>>::new().clone()
    }
}
/// The current gfx_graphics back-end
#[cfg(feature = "include_gfx")]
pub fn current_g2d() -> Rc<RefCell<G2D>> {
    unsafe {
        Current::<Rc<RefCell<G2D>>>::new().clone()
    }
}
/// The current Gfx renderer
#[cfg(feature = "include_gfx")]
pub fn current_renderer() -> Rc<RefCell<gfx::Renderer<gfx::GlCommandBuffer>>> {
    unsafe {
        Current::<Rc<RefCell<gfx::Renderer<gfx::GlCommandBuffer>>>>::new().clone()
    }
}
/// The current Gfx frame
#[cfg(feature = "include_gfx")]
pub fn current_frame() -> Rc<RefCell<gfx::Frame>> {
    unsafe {
        Current::<Rc<RefCell<gfx::Frame>>>::new().clone()
    }
}
/// The current FPS counter
pub fn current_fps_counter() -> Rc<RefCell<FPSCounter>> {
    unsafe {
        Current::<Rc<RefCell<FPSCounter>>>::new().clone()
    }
}

/// Returns an event iterator for the event loop
pub fn events() -> event::Events<Rc<RefCell<WindowBackEnd>>> {
    Events::new(current_window())
}

/// Updates the FPS counter and gets the frames per second.
pub fn fps_tick() -> uint {
    current_fps_counter().borrow_mut().tick()
}

/// Sets title of the current window.
pub fn set_title(text: String) {
    current_window().set_mut(window::Title(text));
}

/// Returns true if the current window should be closed.
pub fn should_close() -> bool {
    use window::ShouldClose;
    let ShouldClose(val) = current_window().get();
    val
}

/// Renders 2D graphics using Gfx.
#[cfg(feature = "include_gfx")]
pub fn render_2d_gfx(
    bg_color: Option<[f32, ..4]>,
    f: |graphics::Context,
        &mut gfx_graphics::GraphicsBackEnd<gfx::GlCommandBuffer>|
) {
    use gfx::Device;

    let renderer = current_renderer();
    let mut renderer = renderer.borrow_mut();
    let renderer = renderer.deref_mut();
    current_g2d().borrow_mut().draw(
        renderer,
        current_frame().borrow_mut().deref_mut(),
        |c, g| {
            if let Some(bg_color) = bg_color {
                graphics::clear(bg_color, g);
            }
            f(c, g);
        });
    current_gfx_device().borrow_mut().submit(renderer.as_buffer());
    renderer.reset();
}

/// Renders 2D graphics using OpenGL.
///
/// Panics if called nested within the closure
/// to prevent mutable aliases to the graphics back-end.
pub fn render_2d_opengl(
    bg_color: Option<[f32, ..4]>,
    f: |graphics::Context,
        &mut opengl_graphics::Gl|
) {
    let window::Size([w, h]) = current_window().borrow().deref().get();
    current_gl().borrow_mut().draw([0, 0, w as i32, h as i32], |c, g| {
        use graphics::*;
        if let Some(bg_color) = bg_color {
            graphics::clear(bg_color, g);
        }
        f(c, g);
    });
}

<commit_msg>Upgrade to latest Rust<commit_after>#![crate_name = "piston"]
#![deny(missing_docs)]
#![warn(dead_code)]
#![feature(default_type_params)]
#![feature(globs)]

//! A user friendly game engine written in Rust.

#[cfg(feature = "include_gfx")]
extern crate gfx;
#[cfg(feature = "include_gfx")]
extern crate gfx_graphics;
extern crate opengl_graphics;
extern crate sdl2;
extern crate sdl2_window;

// Crates used to reexport.
extern crate "ai_behavior" as ai_behavior_lib;
extern crate "vecmath" as vecmath_lib;
extern crate "shader_version" as shader_version_lib;
extern crate "image" as image_lib;
extern crate "graphics" as graphics_lib;
extern crate "input" as input_lib;
extern crate "event" as event_lib;
extern crate "window" as window_lib;
extern crate "cam" as cam_lib;
extern crate "current" as current_lib;
extern crate "quack" as quack_lib;
extern crate "fps_counter" as fps_counter_lib;
extern crate "drag_controller" as drag_controller_lib;
extern crate "read_color" as read_color_lib;
extern crate "select_color" as select_color_lib;

// Reexports.
pub use current_lib as current;
pub use quack_lib as quack;
pub use ai_behavior_lib as ai_behavior;
pub use shader_version_lib as shader_version;
pub use image_lib as image;
pub use graphics_lib as graphics;
pub use vecmath_lib as vecmath;
pub use input_lib as input;
pub use event_lib as event;
pub use window_lib as window;
pub use cam_lib as cam;
pub use fps_counter_lib as fps_counter;
pub use drag_controller_lib as drag_controller;

pub use sdl2_window::Sdl2Window as WindowBackEnd;
pub use event::{
    Event,
    Events,
    NoWindow,
    RenderArgs,
    UpdateArgs,
    WindowSettings,
};

pub use quack::{
    Action,
    ActOn,
    Get,
    GetFrom,
    Set,
    SetAt,
};
pub use current::{
    Current,
    CurrentGuard,
};

#[cfg(feature = "include_gfx")]
use gfx_graphics::G2D;
#[cfg(feature = "include_gfx")]
use gfx::{ DeviceHelper };
use opengl_graphics::Gl;
use fps_counter::FPSCounter;

use std::rc::Rc;
use std::cell::RefCell;

pub mod color {
    //! Rexported libraries for working with colors
    pub use read_color_lib as read_color;
    pub use select_color_lib as select_color;
}

fn start_window(
    opengl: shader_version::OpenGL,
    window_settings: WindowSettings,
    f: ||
) {
    let mut window = Rc::new(RefCell::new(WindowBackEnd::new(
        opengl,
        window_settings,
    )));
    let mut gl = Rc::new(RefCell::new(Gl::new(opengl)));
    let mut fps_counter = Rc::new(RefCell::new(FPSCounter::new()));

    let window_guard = CurrentGuard::new(&mut window);
    let gl_guard = CurrentGuard::new(&mut gl);
    let fps_counter_guard = CurrentGuard::new(&mut fps_counter);

    f();

    drop(window_guard);
    drop(gl_guard);
    drop(fps_counter_guard);
}

#[cfg(feature = "include_gfx")]
fn start_gfx(f: ||) {
    let window = current_window();

    let mut device = Rc::new(RefCell::new(gfx::GlDevice::new(|s| unsafe {
        std::mem::transmute(sdl2::video::gl_get_proc_address(s))
    })));
    let mut g2d = Rc::new(RefCell::new(G2D::new(device.borrow_mut().deref_mut())));
    let mut renderer = Rc::new(RefCell::new(device.borrow_mut().create_renderer()));
    let event::window::Size([w, h]) = window.get();
    let mut frame = Rc::new(RefCell::new(gfx::Frame::new(w as u16, h as u16)));

    let device_guard = CurrentGuard::new(&mut device);
    let g2d_guard = CurrentGuard::new(&mut g2d);
    let renderer_guard = CurrentGuard::new(&mut renderer);
    let frame_guard = CurrentGuard::new(&mut frame);

    f();

    drop(g2d_guard);
    drop(renderer_guard);
    drop(frame_guard);
    drop(device_guard);
}

#[cfg(not(feature = "include_gfx"))]
fn start_gfx(f: ||) {
    f();
}

/// Initializes window and sets up current objects.
pub fn start(
    opengl: shader_version::OpenGL,
    window_settings: WindowSettings,
    f: ||
) {
    start_window(opengl, window_settings, || {
        if cfg!(feature = "include_gfx") {
            start_gfx(|| f());
        } else {
            f();
        }
    });
}

/// The current window
pub fn current_window() -> Rc<RefCell<WindowBackEnd>> {
    unsafe {
        Current::<Rc<RefCell<WindowBackEnd>>>::new().clone()
    }
}
/// The current Gfx device
#[cfg(feature = "include_gfx")]
pub fn current_gfx_device() -> Rc<RefCell<gfx::GlDevice>> {
    unsafe {
        Current::<Rc<RefCell<gfx::GlDevice>>>::new().clone()
    }
}
/// The current opengl_graphics back-end
pub fn current_gl() -> Rc<RefCell<Gl>> {
    unsafe {
        Current::<Rc<RefCell<Gl>>>::new().clone()
    }
}
/// The current gfx_graphics back-end
#[cfg(feature = "include_gfx")]
pub fn current_g2d() -> Rc<RefCell<G2D>> {
    unsafe {
        Current::<Rc<RefCell<G2D>>>::new().clone()
    }
}
/// The current Gfx renderer
#[cfg(feature = "include_gfx")]
pub fn current_renderer() -> Rc<RefCell<gfx::Renderer<gfx::GlCommandBuffer>>> {
    unsafe {
        Current::<Rc<RefCell<gfx::Renderer<gfx::GlCommandBuffer>>>>::new().clone()
    }
}
/// The current Gfx frame
#[cfg(feature = "include_gfx")]
pub fn current_frame() -> Rc<RefCell<gfx::Frame>> {
    unsafe {
        Current::<Rc<RefCell<gfx::Frame>>>::new().clone()
    }
}
/// The current FPS counter
pub fn current_fps_counter() -> Rc<RefCell<FPSCounter>> {
    unsafe {
        Current::<Rc<RefCell<FPSCounter>>>::new().clone()
    }
}

/// Returns an event iterator for the event loop
pub fn events<E>() -> event::Events<Rc<RefCell<WindowBackEnd>>, E> {
    Events::new(current_window())
}

/// Updates the FPS counter and gets the frames per second.
pub fn fps_tick() -> uint {
    current_fps_counter().borrow_mut().tick()
}

/// Sets title of the current window.
pub fn set_title(text: String) {
    current_window().set_mut(window::Title(text));
}

/// Returns true if the current window should be closed.
pub fn should_close() -> bool {
    use window::ShouldClose;
    let ShouldClose(val) = current_window().get();
    val
}

/// Renders 2D graphics using Gfx.
#[cfg(feature = "include_gfx")]
pub fn render_2d_gfx(
    bg_color: Option<[f32; 4]>,
    f: |graphics::Context,
        &mut gfx_graphics::GraphicsBackEnd<gfx::GlCommandBuffer>|
) {
    use gfx::Device;

    let renderer = current_renderer();
    let mut renderer = renderer.borrow_mut();
    let renderer = renderer.deref_mut();
    current_g2d().borrow_mut().draw(
        renderer,
        current_frame().borrow_mut().deref_mut(),
        |c, g| {
            if let Some(bg_color) = bg_color {
                graphics::clear(bg_color, g);
            }
            f(c, g);
        });
    current_gfx_device().borrow_mut().submit(renderer.as_buffer());
    renderer.reset();
}

/// Renders 2D graphics using OpenGL.
///
/// Panics if called nested within the closure
/// to prevent mutable aliases to the graphics back-end.
pub fn render_2d_opengl(
    bg_color: Option<[f32; 4]>,
    f: |graphics::Context,
        &mut opengl_graphics::Gl|
) {
    use std::ops::Deref;

    let window::Size([w, h]) = current_window().borrow().deref().get();
    current_gl().borrow_mut().draw([0, 0, w as i32, h as i32], |c, g| {
        use graphics::*;
        if let Some(bg_color) = bg_color {
            graphics::clear(bg_color, g);
        }
        f(c, g);
    });
}

<|endoftext|>


<commit_before>#![crate_id = "piston"]
#![deny(missing_doc)]
#![warn(dead_code)]

//! A user friendly graphics engine.
#[cfg(glfw)]
extern crate glfw;
#[cfg(sdl2)]
extern crate sdl2;
#[cfg(glfw)]
#[cfg(sdl2)]
extern crate gl;
extern crate time;

pub use Game = game::Game;

pub use Render = game_iterator::Render;
pub use Update = game_iterator::Update;
pub use KeyPress = game_iterator::KeyPress;
pub use KeyRelease = game_iterator::KeyRelease;
pub use MousePress = game_iterator::MousePress;
pub use MouseRelease = game_iterator::MouseRelease;
pub use MouseMove = game_iterator::MouseMove;
pub use MouseRelativeMove = game_iterator::MouseRelativeMove;

pub use GameEvent = game_iterator::GameEvent;
pub use GameIterator = game_iterator::GameIterator;
pub use GameIteratorSettings = game_iterator::GameIteratorSettings;
pub use RenderArgs = game_iterator::RenderArgs;
pub use UpdateArgs = game_iterator::UpdateArgs;
pub use KeyPressArgs = game_iterator::KeyPressArgs;
pub use KeyReleaseArgs = game_iterator::KeyReleaseArgs;
pub use MousePressArgs = game_iterator::MousePressArgs;
pub use MouseReleaseArgs = game_iterator::MouseReleaseArgs;
pub use MouseMoveArgs = game_iterator::MouseMoveArgs;
pub use MouseRelativeMoveArgs = game_iterator::MouseRelativeMoveArgs;

pub use GameWindow = game_window::GameWindow;
#[cfg(sdl2)]
pub use GameWindowSDL2 = game_window_sdl2::GameWindowSDL2;
#[cfg(glfw)]
pub use GameWindowGLFW = game_window_glfw::GameWindowGLFW;
pub use GameWindowSettings = game_window_settings::GameWindowSettings;
pub use AssetStore = asset_store::AssetStore;

pub mod game_window;
pub mod keyboard;
pub mod event;
pub mod mouse;

mod game;
mod game_iterator;
mod game_window_settings;
mod asset_store;

#[cfg(sdl2)]
mod game_window_sdl2;
#[cfg(glfw)]
mod game_window_glfw;

<commit_msg>Fix glfw build<commit_after>#![crate_id = "piston"]
#![deny(missing_doc)]
#![warn(dead_code)]

//! A user friendly graphics engine.
#[cfg(glfw)]
extern crate glfw;
#[cfg(sdl2)]
extern crate sdl2;
#[cfg(glfw)]
extern crate collections;
extern crate gl;
extern crate time;

pub use Game = game::Game;

pub use Render = game_iterator::Render;
pub use Update = game_iterator::Update;
pub use KeyPress = game_iterator::KeyPress;
pub use KeyRelease = game_iterator::KeyRelease;
pub use MousePress = game_iterator::MousePress;
pub use MouseRelease = game_iterator::MouseRelease;
pub use MouseMove = game_iterator::MouseMove;
pub use MouseRelativeMove = game_iterator::MouseRelativeMove;

pub use GameEvent = game_iterator::GameEvent;
pub use GameIterator = game_iterator::GameIterator;
pub use GameIteratorSettings = game_iterator::GameIteratorSettings;
pub use RenderArgs = game_iterator::RenderArgs;
pub use UpdateArgs = game_iterator::UpdateArgs;
pub use KeyPressArgs = game_iterator::KeyPressArgs;
pub use KeyReleaseArgs = game_iterator::KeyReleaseArgs;
pub use MousePressArgs = game_iterator::MousePressArgs;
pub use MouseReleaseArgs = game_iterator::MouseReleaseArgs;
pub use MouseMoveArgs = game_iterator::MouseMoveArgs;
pub use MouseRelativeMoveArgs = game_iterator::MouseRelativeMoveArgs;

pub use GameWindow = game_window::GameWindow;
#[cfg(sdl2)]
pub use GameWindowSDL2 = game_window_sdl2::GameWindowSDL2;
#[cfg(glfw)]
pub use GameWindowGLFW = game_window_glfw::GameWindowGLFW;
pub use GameWindowSettings = game_window_settings::GameWindowSettings;
pub use AssetStore = asset_store::AssetStore;

pub mod game_window;
pub mod keyboard;
pub mod event;
pub mod mouse;

mod game;
mod game_iterator;
mod game_window_settings;
mod asset_store;

#[cfg(sdl2)]
mod game_window_sdl2;
#[cfg(glfw)]
mod game_window_glfw;

<|endoftext|>


<commit_before>#![crate_name = "ui"]
#![deny(missing_doc)]

//! A flexible structure for user interactions
//! to be used in window frameworks and widgets libraries.

/// Time difference in seconds.
pub struct DeltaTime(pub f64);

/// Describes a device.
///
/// To create a custom device, use `Device::new`.
pub struct Device(&'static str);

pub static MOUSE: Device = Device("_mouse");
pub static KEYBOARD: Device = Device("_keyboard");

impl Device {
    /// Creates a new custom device.
    ///
    /// Returns `Err(String)` if the id is reserved.
    pub fn new(id: &'static str) -> Result<Device, String> {
        let device = Device(id);
        match device {
              MOUSE
            | KEYBOARD
            => Err(format!("The device id '{}' is reserved", id)),
            _ => Ok(device)
        }
    }
}

/// Describes a button on a device.
pub struct Button {
    /// The device that contains the button.
    pub device: Device,
    /// The key that identifies the button.
    pub key: &'static str,
    /// A non-zero id if device contains more than one.
    pub axis_id: uint,
    /// The user id.
    pub user_id: uint,
}

/// A user input signal is a 3D data of some sort.
///
/// This can be absolute or relative depending on the usage.
pub struct Signal {
    /// The device where the signal came from.
    pub device: Device,
    /// The coordinates received from signal.
    pub xyz: [f64, ..3],
    /// A non-zero id if device contains more than one.
    pub id: uint,
}

impl Signal {
    /// Gets the `x` and `y` component.
    pub fn xy(&self) -> (f64, f64) {
        (self.xyz[0], self.xyz[1])
    }
}

/// Can be sent to a widget from window or parent widget.
pub enum Input {
    /// Press button or key.
    Press(Button),
    /// Release button or key.
    Release(Button),
    /// Repeat button or key.
    ///
    /// The frequency of repeating is implementation dependent.
    Repeat(Button),
    /// Position input event from device.
    Position(Device, [f64, ..3]),
    /// Move input event from device.
    Move(Device, [f64, ..3]),
    /// Scroll input event from device.
    Scroll(Device, [f64, ..3]),
    /// Resize input event from device.
    Resize(Device, [f64, ..3]),
    /// Orient input event from device.
    Orient(Device, [f64, ..3]),
    /// Rotate input event from device.
    Rotate(Device, [f64, ..3]),
    /// Scale input event from device.
    Scale(Device, [f64, ..3]),
    /// Select all items.
    SelectAll,
    /// Deselect all items.
    SelectNone,
    /// Select an item.
    Select(uint),
    /// Deselect an item.
    Deselect(uint),
    /// Select range of items.
    SelectRange(uint, uint),
    /// Navigate to item.
    NavigateTo(uint),
    /// Focus attention on widget.
    Focus,
    /// Shift focus away from widget.
    Defocus,
    /// Enable the widget for handling user input.
    Enable,
    /// Disable the widget from handling user input.
    Disable,
    /// Shw the child widgets.
    Expand,
    /// Hide the child widgets.
    Collapse,
    /// Play video/audio content.
    Play,
    /// Pause video/audio content.
    Pause,
    /// Skip seconds of video/audio content.
    ///
    /// This can be negative.
    Skip(DeltaTime),
    /// Set the current time of video/audio content.
    SetTime(DeltaTime),
    /// Update widget with delta time in seconds.
    Update(DeltaTime),
    /// Render the widget with computed extrapolated time for smoothness.
    Render(DeltaTime),
    /// Pastes a string in widget.
    PasteString(String),
    /// Pastes a blob of data in widget.
    PasteBlob(Vec<u8>),
    /// A unicode character, usually handled by text widgets.
    UnicodeChar(char),
}

/// Can be sent to parent of a widget.
pub enum Output {
    /// Capture a device.
    ///
    /// This is used by games to hide mouse cursor.
    Capture(Device),
    /// Free the captured device.
    Free(Device),
    /// Put a string on the clipboard.
    CopyString(String),
    /// Put a blob of data on the clipboard.
    CopyBlob(Vec<u8>),
    /// Request a size for the widget content to fit on screen.
    RequestSize([f64, ..3]),
    /// Ask to go to full screen mode.
    RequestFullscreen,
    /// Ask to go to window mode.
    RequestWindow,
    /// The number of items in widget has changed.
    ///
    /// This is used by widgets that streams data.
    Count(uint),
    /// The length of video/audio content in seconds.
    Length(DeltaTime),
    /// A warning message.
    Warning(String),
    /// A critical message.
    Alert(String),
    /// A message to notify the user.
    Notify(String),
    /// An error occured.
    Error(String),
    /// Invalid input, used by widgets that require specific format.
    Invalid(String),
}

pub mod mouse;
pub mod keyboard;
<commit_msg>Renamed from `Signal` to `Motion`<commit_after>#![crate_name = "ui"]
#![deny(missing_doc)]

//! A flexible structure for user interactions
//! to be used in window frameworks and widgets libraries.

/// Time difference in seconds.
pub struct DeltaTime(pub f64);

/// Describes a device.
///
/// To create a custom device, use `Device::new`.
pub struct Device(&'static str);

pub static MOUSE: Device = Device("_mouse");
pub static KEYBOARD: Device = Device("_keyboard");

impl Device {
    /// Creates a new custom device.
    ///
    /// Returns `Err(String)` if the id is reserved.
    pub fn new(id: &'static str) -> Result<Device, String> {
        let device = Device(id);
        match device {
              MOUSE
            | KEYBOARD
            => Err(format!("The device id '{}' is reserved", id)),
            _ => Ok(device)
        }
    }
}

/// Describes a button on a device.
pub struct Button {
    /// The device that contains the button.
    pub device: Device,
    /// The key that identifies the button.
    pub key: &'static str,
    /// A non-zero id if device contains more than one.
    pub axis_id: uint,
    /// The user id.
    pub user_id: uint,
}

/// A device input motion.
///
/// Coordinates can be absolute or relative depending on the usage.
/// The coordinates depends on usage.
pub struct Motion {
    /// The device where the motion came from.
    pub device: Device,
    /// The coordinates describing the motion.
    ///
    /// For rotation the coordinates are usually yaw, pitch and roll.
    pub xyz: [f64, ..3],
    /// A non-zero id if device contains more than one.
    pub axis_id: uint,
    /// The user id.
    pub user_id: uint,
}

impl Motion {
    /// Gets the `x` and `y` component.
    pub fn get_xy(&self) -> (f64, f64) {
        (self.xyz[0], self.xyz[1])
    }
}

/// Can be sent to a widget from window or parent widget.
pub enum Input {
    /// Press button or key.
    Press(Button),
    /// Release button or key.
    Release(Button),
    /// Repeat button or key.
    ///
    /// The frequency of repeating is implementation dependent.
    Repeat(Button),
    /// Position input event from device.
    Position(Motion),
    /// Move input event from device.
    Move(Motion),
    /// Scroll input event from device.
    Scroll(Motion),
    /// Resize input event from device.
    Resize(Motion),
    /// Orient input event from device.
    Orient(Motion),
    /// Rotate input event from device.
    Rotate(Motion),
    /// Scale input event from device.
    Scale(Motion),
    /// Select all items.
    SelectAll,
    /// Deselect all items.
    SelectNone,
    /// Select an item.
    Select(uint),
    /// Deselect an item.
    Deselect(uint),
    /// Select range of items.
    SelectRange(uint, uint),
    /// Navigate to item.
    NavigateTo(uint),
    /// Focus attention on widget.
    Focus,
    /// Shift focus away from widget.
    Defocus,
    /// Enable the widget for handling user input.
    Enable,
    /// Disable the widget from handling user input.
    Disable,
    /// Shw the child widgets.
    Expand,
    /// Hide the child widgets.
    Collapse,
    /// Play video/audio content.
    Play,
    /// Pause video/audio content.
    Pause,
    /// Skip seconds of video/audio content.
    ///
    /// This can be negative.
    Skip(DeltaTime),
    /// Set the current time of video/audio content.
    SetTime(DeltaTime),
    /// Update widget with delta time in seconds.
    Update(DeltaTime),
    /// Render the widget with computed extrapolated time for smoothness.
    Render(DeltaTime),
    /// Pastes a string in widget.
    PasteString(String),
    /// Pastes a blob of data in widget.
    PasteBlob(Vec<u8>),
    /// A unicode character, usually handled by text widgets.
    UnicodeChar(char),
}

/// Can be sent to parent of a widget.
pub enum Output {
    /// Capture a device.
    ///
    /// This is used by games to hide mouse cursor.
    Capture(Device),
    /// Free the captured device.
    Free(Device),
    /// Put a string on the clipboard.
    CopyString(String),
    /// Put a blob of data on the clipboard.
    CopyBlob(Vec<u8>),
    /// Request a size for the widget content to fit on screen.
    RequestSize([f64, ..3]),
    /// Ask to go to full screen mode.
    RequestFullscreen,
    /// Ask to go to window mode.
    RequestWindow,
    /// The number of items in widget has changed.
    ///
    /// This is used by widgets that streams data.
    Count(uint),
    /// The length of video/audio content in seconds.
    Length(DeltaTime),
    /// A warning message.
    Warning(String),
    /// A critical message.
    Alert(String),
    /// A message to notify the user.
    Notify(String),
    /// An error occured.
    Error(String),
    /// Invalid input, used by widgets that require specific format.
    Invalid(String),
}

pub mod mouse;
pub mod keyboard;
<|endoftext|>


<commit_before><commit_msg>docs: Fix byte offsets mentioned in Archive::read_kind<commit_after><|endoftext|>


<commit_before><commit_msg>command work<commit_after><|endoftext|>


<commit_before><commit_msg>simplified segment chunking<commit_after><|endoftext|>


<commit_before><commit_msg>Auto merge of #239 - frewsxcv:doc-examples, r=SimonSapin<commit_after><|endoftext|>


<commit_before><commit_msg>Relax bounce to FnOnce<commit_after><|endoftext|>


<commit_before><commit_msg>updated to pull from my repo by default<commit_after><|endoftext|>


<commit_before><commit_msg>Snake case<commit_after><|endoftext|>


<commit_before>use std::collections::HashMap;
use std::error::Error;
use std::fmt::{Debug, Display, Formatter};
use std::fmt;

use serde_json::{Value, from_str};
use serde_json::error::Result as R;
use serde_json::Serializer;
use serde::ser::Serialize;
use serde::ser::Serializer as Ser;

use storage::parser::{FileHeaderParser, ParserError};
use storage::file::header::spec::FileHeaderSpec;
use storage::file::header::data::FileHeaderData;

pub struct JsonHeaderParser {
    spec: Option<FileHeaderSpec>,
}

impl JsonHeaderParser {

    pub fn new(spec: Option<FileHeaderSpec>) -> JsonHeaderParser {
        JsonHeaderParser {
            spec: spec
        }
    }

}

impl Display for JsonHeaderParser {

    fn fmt(&self, fmt: &mut Formatter) -> fmt::Result {
        try!(write!(fmt, "JsonHeaderParser"));
        Ok(())
    }

}

impl Debug for JsonHeaderParser {

    fn fmt(&self, fmt: &mut Formatter) -> fmt::Result {
        try!(write!(fmt, "JsonHeaderParser, Spec: {:?}", self.spec));
        Ok(())
    }

}

impl FileHeaderParser for JsonHeaderParser {

    fn read(&self, string: Option<String>)
        -> Result<FileHeaderData, ParserError>
    {
        if string.is_some() {
            let s = string.unwrap();
            debug!("Deserializing: {}", s);
            let fromstr : R<Value> = from_str(&s[..]);
            if let Ok(ref content) = fromstr {
                return Ok(visit_json(&content))
            }
            let oe = fromstr.err().unwrap();
            let s = format!("JSON parser error: {}", oe.description());
            let e = ParserError::short(&s[..], s.clone(), 0);
            Err(e)
        } else {
            Ok(FileHeaderData::Null)
        }
    }

    fn write(&self, data: &FileHeaderData) -> Result<String, ParserError> {
        let mut s = Vec::<u8>::new();
        {
            let mut ser = Serializer::pretty(&mut s);
            data.serialize(&mut ser).map_err(|e| {
                debug!("Serializer error: {:?}", e);
            }).ok();
        }

        String::from_utf8(s).or(
            Err(ParserError::short("Cannot parse utf8 bytes",
                                   String::from("<not printable>"),
                                   0)))
    }

}

// TODO: This function must be able to return a parser error
fn visit_json(v: &Value) -> FileHeaderData {
    match v {
        &Value::Null             => FileHeaderData::Null,
        &Value::Bool(b)          => FileHeaderData::Bool(b),
        &Value::I64(i)           => FileHeaderData::Integer(i),
        &Value::U64(u)           => FileHeaderData::UInteger(u),
        &Value::F64(f)           => FileHeaderData::Float(f),
        &Value::String(ref s)        => FileHeaderData::Text(s.clone()),
        &Value::Array(ref vec)       => {
            FileHeaderData::Array {
                values: Box::new(vec.clone().into_iter().map(|i| visit_json(&i)).collect())
            }
        },
        &Value::Object(ref btree)    => {
            let btree = btree.clone();
            FileHeaderData::Map{
                keys: btree.into_iter().map(|(k, v)|
                    FileHeaderData::Key {
                        name: k,
                        value: Box::new(visit_json(&v)),
                    }
                ).collect()
            }
        }
    }
}

impl Serialize for FileHeaderData {

    fn serialize<S>(&self, ser: &mut S) -> Result<(), S::Error>
        where S: Ser
    {
        match self {
            &FileHeaderData::Null               => {
                let o : Option<bool> = None;
                o.serialize(ser)
            },
            &FileHeaderData::Bool(ref b)            => b.serialize(ser),
            &FileHeaderData::Integer(ref i)         => i.serialize(ser),
            &FileHeaderData::UInteger(ref u)        => u.serialize(ser),
            &FileHeaderData::Float(ref f)           => f.serialize(ser),
            &FileHeaderData::Text(ref s)            => (&s[..]).serialize(ser),
            &FileHeaderData::Array{values: ref vs}  => vs.serialize(ser),
            &FileHeaderData::Map{keys: ref ks}      => {
                let mut hm = HashMap::new();

                for key in ks {
                    if let &FileHeaderData::Key{name: ref n, value: ref v} = key {
                        hm.insert(n, v);
                    } else {
                        panic!("Not a key: {:?}", key);
                    }
                }

                hm.serialize(ser)
            },
            &FileHeaderData::Key{name: _, value: _} => unreachable!(),

        }
    }

}

#[cfg(test)]
mod test {

    use std::ops::Deref;

    use super::JsonHeaderParser;
    use storage::parser::FileHeaderParser;
    use storage::file::header::data::FileHeaderData as FHD;
    use storage::file::header::spec::FileHeaderSpec as FHS;

    #[test]
    fn test_deserialization() {
        let text = String::from("{\"a\": 1, \"b\": -2}");
        let spec = FHS::Map {
            keys: vec![
                FHS::Key {
                    name: String::from("a"),
                    value_type: Box::new(FHS::UInteger)
                },
                FHS::Key {
                    name: String::from("b"),
                    value_type: Box::new(FHS::Integer)
                }
            ]
        };

        let parser = JsonHeaderParser::new(Some(spec));
        let parsed = parser.read(Some(text));
        assert!(parsed.is_ok(), "Parsed is not ok: {:?}", parsed);

        match parsed.ok() {
            Some(FHD::Map{keys: keys}) => {
                for k in keys {
                    match k {
                        FHD::Key{name: name, value: value} => {
                            assert!(name == "a" || name == "b", "Key unknown");
                            match value.deref() {
                                &FHD::UInteger(u) => assert_eq!(u, 1),
                                &FHD::Integer(i) => assert_eq!(i, -2),
                                _ => assert!(false, "Integers are not here"),
                            }
                        },
                        _ => assert!(false, "Key is not a Key"),
                    }
                }
            },

            _ => assert!(false, "Parsed is not a map"),
        }
    }

    #[test]
    fn test_deserialization_without_spec() {
        let text    = String::from("{\"a\": [1], \"b\": {\"c\": -2}}");
        let parser  = JsonHeaderParser::new(None);
        let parsed  = parser.read(Some(text));

        assert!(parsed.is_ok(), "Parsed is not ok: {:?}", parsed);

        match parsed.ok() {
            Some(FHD::Map{keys: keys}) => {
                for k in keys {
                    match_key(&k);
                }
            },

            _ => assert!(false, "Parsed is not a map"),
        }
    }

    fn match_key(k: &FHD) {
        use std::ops::Deref;

        match k {
            &FHD::Key{name: ref name, value: ref value} => {
                assert!(name == "a" || name == "b", "Key unknown");
                match value.deref() {
                    &FHD::Array{values: ref vs} => {
                        for value in vs.iter() {
                            match value {
                                &FHD::UInteger(u) => assert_eq!(u, 1),
                                _ => assert!(false, "UInt is not an UInt"),
                            }
                        }
                    }

                    &FHD::Map{keys: ref ks} => {
                        for key in ks.iter() {
                            match key {
                                &FHD::Key{name: ref name, value: ref value} => {
                                    match value.deref() {
                                        &FHD::Integer(i) => {
                                            assert_eq!(i, -2);
                                            assert_eq!(name, "c");
                                        },
                                        _ => assert!(false, "Int is not an Int"),
                                    };
                                },
                                _ => assert!(false, "Key is not a Key"),
                            }
                        }
                    }
                    _ => assert!(false, "Integers are not here"),
                }
            },
            _ => assert!(false, "Key in main Map is not a Key"),
        }
    }

    #[test]
    fn test_desser() {
        use serde_json::error::Result as R;
        use serde_json::{Value, from_str};

        let text    = String::from("{\"a\": [1], \"b\": {\"c\": -2}}");
        let parser  = JsonHeaderParser::new(None);

        let des = parser.read(Some(text.clone()));
        assert!(des.is_ok(), "Deserializing failed");

        let ser = parser.write(&des.unwrap());
        assert!(ser.is_ok(), "Parser error when serializing deserialized text");

        let json_text : R<Value> = from_str(&text[..]);
        let json_ser  : R<Value> = from_str(&ser.unwrap()[..]);

        assert!(json_text.is_ok(), "Could not use serde to serialize text for comparison");
        assert!(json_ser.is_ok(),  "Could not use serde to serialize serialized-deserialized text for comparison");
        assert_eq!(json_text.unwrap(), json_ser.unwrap());
    }

}
<commit_msg>Remove unneeded shorthand field pattern<commit_after>use std::collections::HashMap;
use std::error::Error;
use std::fmt::{Debug, Display, Formatter};
use std::fmt;

use serde_json::{Value, from_str};
use serde_json::error::Result as R;
use serde_json::Serializer;
use serde::ser::Serialize;
use serde::ser::Serializer as Ser;

use storage::parser::{FileHeaderParser, ParserError};
use storage::file::header::spec::FileHeaderSpec;
use storage::file::header::data::FileHeaderData;

pub struct JsonHeaderParser {
    spec: Option<FileHeaderSpec>,
}

impl JsonHeaderParser {

    pub fn new(spec: Option<FileHeaderSpec>) -> JsonHeaderParser {
        JsonHeaderParser {
            spec: spec
        }
    }

}

impl Display for JsonHeaderParser {

    fn fmt(&self, fmt: &mut Formatter) -> fmt::Result {
        try!(write!(fmt, "JsonHeaderParser"));
        Ok(())
    }

}

impl Debug for JsonHeaderParser {

    fn fmt(&self, fmt: &mut Formatter) -> fmt::Result {
        try!(write!(fmt, "JsonHeaderParser, Spec: {:?}", self.spec));
        Ok(())
    }

}

impl FileHeaderParser for JsonHeaderParser {

    fn read(&self, string: Option<String>)
        -> Result<FileHeaderData, ParserError>
    {
        if string.is_some() {
            let s = string.unwrap();
            debug!("Deserializing: {}", s);
            let fromstr : R<Value> = from_str(&s[..]);
            if let Ok(ref content) = fromstr {
                return Ok(visit_json(&content))
            }
            let oe = fromstr.err().unwrap();
            let s = format!("JSON parser error: {}", oe.description());
            let e = ParserError::short(&s[..], s.clone(), 0);
            Err(e)
        } else {
            Ok(FileHeaderData::Null)
        }
    }

    fn write(&self, data: &FileHeaderData) -> Result<String, ParserError> {
        let mut s = Vec::<u8>::new();
        {
            let mut ser = Serializer::pretty(&mut s);
            data.serialize(&mut ser).map_err(|e| {
                debug!("Serializer error: {:?}", e);
            }).ok();
        }

        String::from_utf8(s).or(
            Err(ParserError::short("Cannot parse utf8 bytes",
                                   String::from("<not printable>"),
                                   0)))
    }

}

// TODO: This function must be able to return a parser error
fn visit_json(v: &Value) -> FileHeaderData {
    match v {
        &Value::Null             => FileHeaderData::Null,
        &Value::Bool(b)          => FileHeaderData::Bool(b),
        &Value::I64(i)           => FileHeaderData::Integer(i),
        &Value::U64(u)           => FileHeaderData::UInteger(u),
        &Value::F64(f)           => FileHeaderData::Float(f),
        &Value::String(ref s)        => FileHeaderData::Text(s.clone()),
        &Value::Array(ref vec)       => {
            FileHeaderData::Array {
                values: Box::new(vec.clone().into_iter().map(|i| visit_json(&i)).collect())
            }
        },
        &Value::Object(ref btree)    => {
            let btree = btree.clone();
            FileHeaderData::Map{
                keys: btree.into_iter().map(|(k, v)|
                    FileHeaderData::Key {
                        name: k,
                        value: Box::new(visit_json(&v)),
                    }
                ).collect()
            }
        }
    }
}

impl Serialize for FileHeaderData {

    fn serialize<S>(&self, ser: &mut S) -> Result<(), S::Error>
        where S: Ser
    {
        match self {
            &FileHeaderData::Null               => {
                let o : Option<bool> = None;
                o.serialize(ser)
            },
            &FileHeaderData::Bool(ref b)            => b.serialize(ser),
            &FileHeaderData::Integer(ref i)         => i.serialize(ser),
            &FileHeaderData::UInteger(ref u)        => u.serialize(ser),
            &FileHeaderData::Float(ref f)           => f.serialize(ser),
            &FileHeaderData::Text(ref s)            => (&s[..]).serialize(ser),
            &FileHeaderData::Array{values: ref vs}  => vs.serialize(ser),
            &FileHeaderData::Map{keys: ref ks}      => {
                let mut hm = HashMap::new();

                for key in ks {
                    if let &FileHeaderData::Key{name: ref n, value: ref v} = key {
                        hm.insert(n, v);
                    } else {
                        panic!("Not a key: {:?}", key);
                    }
                }

                hm.serialize(ser)
            },
            &FileHeaderData::Key{name: _, value: _} => unreachable!(),

        }
    }

}

#[cfg(test)]
mod test {

    use std::ops::Deref;

    use super::JsonHeaderParser;
    use storage::parser::FileHeaderParser;
    use storage::file::header::data::FileHeaderData as FHD;
    use storage::file::header::spec::FileHeaderSpec as FHS;

    #[test]
    fn test_deserialization() {
        let text = String::from("{\"a\": 1, \"b\": -2}");
        let spec = FHS::Map {
            keys: vec![
                FHS::Key {
                    name: String::from("a"),
                    value_type: Box::new(FHS::UInteger)
                },
                FHS::Key {
                    name: String::from("b"),
                    value_type: Box::new(FHS::Integer)
                }
            ]
        };

        let parser = JsonHeaderParser::new(Some(spec));
        let parsed = parser.read(Some(text));
        assert!(parsed.is_ok(), "Parsed is not ok: {:?}", parsed);

        match parsed.ok() {
            Some(FHD::Map{keys}) => {
                for k in keys {
                    match k {
                        FHD::Key{name: name, value: value} => {
                            assert!(name == "a" || name == "b", "Key unknown");
                            match value.deref() {
                                &FHD::UInteger(u) => assert_eq!(u, 1),
                                &FHD::Integer(i) => assert_eq!(i, -2),
                                _ => assert!(false, "Integers are not here"),
                            }
                        },
                        _ => assert!(false, "Key is not a Key"),
                    }
                }
            },

            _ => assert!(false, "Parsed is not a map"),
        }
    }

    #[test]
    fn test_deserialization_without_spec() {
        let text    = String::from("{\"a\": [1], \"b\": {\"c\": -2}}");
        let parser  = JsonHeaderParser::new(None);
        let parsed  = parser.read(Some(text));

        assert!(parsed.is_ok(), "Parsed is not ok: {:?}", parsed);

        match parsed.ok() {
            Some(FHD::Map{keys: keys}) => {
                for k in keys {
                    match_key(&k);
                }
            },

            _ => assert!(false, "Parsed is not a map"),
        }
    }

    fn match_key(k: &FHD) {
        use std::ops::Deref;

        match k {
            &FHD::Key{name: ref name, value: ref value} => {
                assert!(name == "a" || name == "b", "Key unknown");
                match value.deref() {
                    &FHD::Array{values: ref vs} => {
                        for value in vs.iter() {
                            match value {
                                &FHD::UInteger(u) => assert_eq!(u, 1),
                                _ => assert!(false, "UInt is not an UInt"),
                            }
                        }
                    }

                    &FHD::Map{keys: ref ks} => {
                        for key in ks.iter() {
                            match key {
                                &FHD::Key{name: ref name, value: ref value} => {
                                    match value.deref() {
                                        &FHD::Integer(i) => {
                                            assert_eq!(i, -2);
                                            assert_eq!(name, "c");
                                        },
                                        _ => assert!(false, "Int is not an Int"),
                                    };
                                },
                                _ => assert!(false, "Key is not a Key"),
                            }
                        }
                    }
                    _ => assert!(false, "Integers are not here"),
                }
            },
            _ => assert!(false, "Key in main Map is not a Key"),
        }
    }

    #[test]
    fn test_desser() {
        use serde_json::error::Result as R;
        use serde_json::{Value, from_str};

        let text    = String::from("{\"a\": [1], \"b\": {\"c\": -2}}");
        let parser  = JsonHeaderParser::new(None);

        let des = parser.read(Some(text.clone()));
        assert!(des.is_ok(), "Deserializing failed");

        let ser = parser.write(&des.unwrap());
        assert!(ser.is_ok(), "Parser error when serializing deserialized text");

        let json_text : R<Value> = from_str(&text[..]);
        let json_ser  : R<Value> = from_str(&ser.unwrap()[..]);

        assert!(json_text.is_ok(), "Could not use serde to serialize text for comparison");
        assert!(json_ser.is_ok(),  "Could not use serde to serialize serialized-deserialized text for comparison");
        assert_eq!(json_text.unwrap(), json_ser.unwrap());
    }

}
<|endoftext|>


<commit_before><commit_msg>Add initial network benchmark<commit_after>#![feature(test)]

extern crate test;
extern crate exonum;
extern crate time;

use std::{thread};
use std::net::SocketAddr;

use time::Duration;
use test::Bencher;

use exonum::events::{Events, Reactor, EventsConfiguration, Event, Timeout};
use exonum::events::{Network, NetworkConfiguration};
use exonum::messages::{MessageWriter, RawMessage};
use exonum::crypto::gen_keypair;

trait EventsBench {
    fn with_addr(addr: SocketAddr) -> Events;
    fn wait_for_msg(&mut self) -> Option<RawMessage>;
    fn gen_message(id: u16, len: usize) -> RawMessage;
    fn wait_for_messages(&mut self, mut count: usize, timeout: Duration) -> Result<(), String>;
}

impl EventsBench for Events {
    fn with_addr(addr: SocketAddr) -> Events {
        let network = Network::with_config(NetworkConfiguration {
            listen_address: addr,
            max_incoming_connections: 128,
            max_outgoing_connections: 128
        });
        Events::with_config(EventsConfiguration::new(), network).unwrap()
    }

    fn wait_for_msg(&mut self) -> Option<RawMessage> {
        let time = self.get_time() + Duration::milliseconds(10000);
        self.add_timeout(Timeout::Status, time);
        loop {
            match self.poll() {
                Event::Incoming(msg) => return Some(msg),
                Event::Timeout(_) => return None,
                Event::Error(_) => return None,
                _ => {}
            }
        }
    }

    fn wait_for_messages(&mut self, mut count: usize, timeout: Duration) -> Result<(), String> {
        let time = self.get_time() + timeout;
        self.add_timeout(Timeout::Status, time);
        loop {
            match self.poll() {
                Event::Incoming(_) => { count = count - 1; }
                Event::Timeout(_) => return Err(format!("Timeout exceeded, {} messages is not received", count)),
                Event::Error(_) => return Err(format!("An error occured, {} messages is not received", count)),
                _ => {}
            }
            if count == 0 {
                return Ok(())
            }
        }
    }

    fn gen_message(id: u16, len: usize) -> RawMessage {
        let writer = MessageWriter::new(id, len);
        RawMessage::new(writer.sign(&gen_keypair().1))
    }
}

fn bench_network(b: &mut Bencher, addrs: [SocketAddr; 2], times: usize, len: usize) {
    b.iter(|| {
        let mut e1 = Events::with_addr(addrs[0]);
        let mut e2 = Events::with_addr(addrs[1]);
        e1.bind().unwrap();
        e2.bind().unwrap();

        let timeout = Duration::seconds(120);
        let t1 = thread::spawn(move || {
                for _ in 0..times {
                    let msg = Events::gen_message(0, len);
                    e1.send_to(&addrs[1], msg).unwrap();
                }
                e1.wait_for_messages(times, timeout).unwrap();
        });
        let t2 = thread::spawn(move || {
                for _ in 0..times {
                    let msg = Events::gen_message(1, len);
                    e2.send_to(&addrs[0], msg).unwrap();
                }
                e2.wait_for_messages(times, timeout).unwrap();
        });
        t1.join().unwrap();
        t2.join().unwrap();
    })
}

#[bench]
fn bench_msg_short_100(b: &mut Bencher) {
    let addrs = [
        "127.0.0.1:9990".parse().unwrap(),
        "127.0.0.1:9991".parse().unwrap()
    ];
    bench_network(b, addrs, 100, 100);
}

#[bench]
fn bench_msg_short_1000(b: &mut Bencher) {
    let addrs = [
        "127.0.0.1:9992".parse().unwrap(),
        "127.0.0.1:9993".parse().unwrap()
    ];
    bench_network(b, addrs, 1000, 100);
}

#[bench]
fn bench_msg_long_10(b: &mut Bencher) {
    let addrs = [
        "127.0.0.1:9994".parse().unwrap(),
        "127.0.0.1:9995".parse().unwrap()
    ];
    bench_network(b, addrs, 10, 100000);
}
<|endoftext|>


<commit_before><commit_msg>error safe?<commit_after><|endoftext|>


<commit_before><commit_msg>fast stdout<commit_after><|endoftext|>