<commit_before>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

//! The context within which CSS code is parsed.

#![deny(missing_docs)]

use cssparser::{Parser, SourcePosition, UnicodeRange};
use error_reporting::ParseErrorReporter;
use style_traits::OneOrMoreCommaSeparated;
use stylesheets::{Origin, UrlExtraData};

/// The data that the parser needs from outside in order to parse a stylesheet.
pub struct ParserContext<'a> {
    /// The `Origin` of the stylesheet, whether it's a user, author or
    /// user-agent stylesheet.
    pub stylesheet_origin: Origin,
    /// The extra data we need for resolving url values.
    pub url_data: &'a UrlExtraData,
    /// An error reporter to report syntax errors.
    pub error_reporter: &'a ParseErrorReporter,
}

impl<'a> ParserContext<'a> {
    /// Create a parser context.
    pub fn new(stylesheet_origin: Origin,
               url_data: &'a UrlExtraData,
               error_reporter: &'a ParseErrorReporter)
               -> ParserContext<'a> {
        ParserContext {
            stylesheet_origin: stylesheet_origin,
            url_data: url_data,
            error_reporter: error_reporter,
        }
    }

    /// Create a parser context for on-the-fly parsing in CSSOM
    pub fn new_for_cssom(url_data: &'a UrlExtraData,
                         error_reporter: &'a ParseErrorReporter)
                         -> ParserContext<'a> {
        Self::new(Origin::User, url_data, error_reporter)
    }
}

/// Defaults to a no-op.
/// Set a `RUST_LOG=style::errors` environment variable
/// to log CSS parse errors to stderr.
pub fn log_css_error(input: &mut Parser,
                     position: SourcePosition,
                     message: &str,
                     parsercontext: &ParserContext) {
    let url_data = parsercontext.url_data;
    parsercontext.error_reporter.report_error(input, position, message, url_data);
}

// XXXManishearth Replace all specified value parse impls with impls of this
// trait. This will make it easy to write more generic values in the future.
/// A trait to abstract parsing of a specified value given a `ParserContext` and
/// CSS input.
pub trait Parse : Sized {
    /// Parse a value of this type.
    ///
    /// Returns an error on failure.
    fn parse(context: &ParserContext, input: &mut Parser) -> Result<Self, ()>;
}

impl<T> Parse for Vec<T> where T: Parse + OneOrMoreCommaSeparated {
    fn parse(context: &ParserContext, input: &mut Parser) -> Result<Self, ()> {
        input.parse_comma_separated(|input| T::parse(context, input))
    }
}

/// Parse a non-empty space-separated or comma-separated list of objects parsed by parse_one
pub fn parse_space_or_comma_separated<F, T>(input: &mut Parser, mut parse_one: F)
        -> Result<Vec<T>, ()>
        where F: FnMut(&mut Parser) -> Result<T, ()> {
    let first = parse_one(input)?;
    let mut vec = vec![first];
    loop {
        let _ = input.try(|i| i.expect_comma());
        if let Ok(val) = input.try(|i| parse_one(i)) {
            vec.push(val)
        } else {
            break
        }
    }
    Ok(vec)
}
impl Parse for UnicodeRange {
    fn parse(_context: &ParserContext, input: &mut Parser) -> Result<Self, ()> {
        UnicodeRange::parse(input)
    }
}
<commit_msg>Auto merge of #16247 - servo:for_cssom, r=jdm<commit_after>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

//! The context within which CSS code is parsed.

#![deny(missing_docs)]

use cssparser::{Parser, SourcePosition, UnicodeRange};
use error_reporting::ParseErrorReporter;
use style_traits::OneOrMoreCommaSeparated;
use stylesheets::{Origin, UrlExtraData};

/// The data that the parser needs from outside in order to parse a stylesheet.
pub struct ParserContext<'a> {
    /// The `Origin` of the stylesheet, whether it's a user, author or
    /// user-agent stylesheet.
    pub stylesheet_origin: Origin,
    /// The extra data we need for resolving url values.
    pub url_data: &'a UrlExtraData,
    /// An error reporter to report syntax errors.
    pub error_reporter: &'a ParseErrorReporter,
}

impl<'a> ParserContext<'a> {
    /// Create a parser context.
    pub fn new(stylesheet_origin: Origin,
               url_data: &'a UrlExtraData,
               error_reporter: &'a ParseErrorReporter)
               -> ParserContext<'a> {
        ParserContext {
            stylesheet_origin: stylesheet_origin,
            url_data: url_data,
            error_reporter: error_reporter,
        }
    }

    /// Create a parser context for on-the-fly parsing in CSSOM
    pub fn new_for_cssom(url_data: &'a UrlExtraData,
                         error_reporter: &'a ParseErrorReporter)
                         -> ParserContext<'a> {
        Self::new(Origin::Author, url_data, error_reporter)
    }
}

/// Defaults to a no-op.
/// Set a `RUST_LOG=style::errors` environment variable
/// to log CSS parse errors to stderr.
pub fn log_css_error(input: &mut Parser,
                     position: SourcePosition,
                     message: &str,
                     parsercontext: &ParserContext) {
    let url_data = parsercontext.url_data;
    parsercontext.error_reporter.report_error(input, position, message, url_data);
}

// XXXManishearth Replace all specified value parse impls with impls of this
// trait. This will make it easy to write more generic values in the future.
/// A trait to abstract parsing of a specified value given a `ParserContext` and
/// CSS input.
pub trait Parse : Sized {
    /// Parse a value of this type.
    ///
    /// Returns an error on failure.
    fn parse(context: &ParserContext, input: &mut Parser) -> Result<Self, ()>;
}

impl<T> Parse for Vec<T> where T: Parse + OneOrMoreCommaSeparated {
    fn parse(context: &ParserContext, input: &mut Parser) -> Result<Self, ()> {
        input.parse_comma_separated(|input| T::parse(context, input))
    }
}

/// Parse a non-empty space-separated or comma-separated list of objects parsed by parse_one
pub fn parse_space_or_comma_separated<F, T>(input: &mut Parser, mut parse_one: F)
        -> Result<Vec<T>, ()>
        where F: FnMut(&mut Parser) -> Result<T, ()> {
    let first = parse_one(input)?;
    let mut vec = vec![first];
    loop {
        let _ = input.try(|i| i.expect_comma());
        if let Ok(val) = input.try(|i| parse_one(i)) {
            vec.push(val)
        } else {
            break
        }
    }
    Ok(vec)
}
impl Parse for UnicodeRange {
    fn parse(_context: &ParserContext, input: &mut Parser) -> Result<Self, ()> {
        UnicodeRange::parse(input)
    }
}
<|endoftext|>


<commit_before>extern crate wright;
use wright::lexer::*;
use wright::position::*;
use wright::lexer::error::LexerError;

#[test]
#[ignore]
fn print_err() {
    let mut lexer_err = LexerError::new(Position::new(), "Tested Line.".to_string())
        .set_info('t', Some('T'));
    lexer_err.set_module_name("TestModule".to_string());
    println!("{}", lexer_err);
}

#[test]
#[ignore]
fn print_err_vec() {
    let mut lexer_err = LexerError::new(Position::new(), "Tested Line.".to_string())
        .set_info_as_vec(vec!['t', 'T'], Some('T'));
    lexer_err.set_module_name("TestModule".to_string());
    println!("{}", lexer_err);
}

#[test]
fn catch_double_char_err() {
    let mut test_lexer = Lexer::new("'ha'".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}

#[test]
fn catch_unended_char_err() {
    let mut test_lexer = Lexer::new("'h".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}

#[test]
fn escaped_char() {
    let mut test_lexer = Lexer::new("'\\a'".to_string());
    assert!(test_lexer.lex().is_ok());
}

#[test]
fn catch_long_char_err() {
    let mut test_lexer = Lexer::new("'hello world'".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}<commit_msg>Turn off unit testing on lexer.<commit_after>extern crate wright;
use wright::lexer::*;
use wright::position::*;
use wright::lexer::error::LexerError;

// overhaul due here soon
// todo!

#[test]
#[ignore]
fn print_err() {
    let mut lexer_err = LexerError::new(Position::new(), "Tested Line.".to_string())
        .set_info('t', Some('T'));
    lexer_err.set_module_name("TestModule".to_string());
    println!("{}", lexer_err);
}

#[test]
#[ignore]
fn print_err_vec() {
    let mut lexer_err = LexerError::new(Position::new(), "Tested Line.".to_string())
        .set_info_as_vec(vec!['t', 'T'], Some('T'));
    lexer_err.set_module_name("TestModule".to_string());
    println!("{}", lexer_err);
}

#[test]
#[ignore]
fn catch_double_char_err() {
    let mut test_lexer = Lexer::new("'ha'".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}

#[test]
#[ignore]
fn catch_unended_char_err() {
    let mut test_lexer = Lexer::new("'h".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}

#[test]
#[ignore]
fn escaped_char() {
    let mut test_lexer = Lexer::new("'\\a'".to_string());
    assert!(test_lexer.lex().is_ok());
}

#[test]
#[ignore]
fn catch_long_char_err() {
    let mut test_lexer = Lexer::new("'hello world'".to_string());
    let result = test_lexer.lex();
    assert!(result.is_err());
    //println!("{}", result.err().unwrap());
}<|endoftext|>


<commit_before>extern crate "pkg-config" as pkg_config;

use std::os;
use std::io::{mod, fs, Command};
use std::io::process::InheritFd;

fn main() {
    register_dep("SSH2");
    register_dep("OPENSSL");

    let mut opts = pkg_config::default_options("libgit2");
    opts.atleast_version = Some("0.21.0".to_string());
    match pkg_config::find_library_opts("libgit2", &opts) {
        Ok(()) => return,
        Err(..) => {}
    }

    let mut cflags = os::getenv("CFLAGS").unwrap_or(String::new());
    let target = os::getenv("TARGET").unwrap();
    let mingw = target.contains("windows-gnu");
    cflags.push_str(" -ffunction-sections -fdata-sections");

    if target.contains("i686") {
        cflags.push_str(" -m32");
    } else if target.as_slice().contains("x86_64") {
        cflags.push_str(" -m64");
    }
    if !target.contains("i686") {
        cflags.push_str(" -fPIC");
    }

    let src = Path::new(os::getenv("CARGO_MANIFEST_DIR").unwrap());
    let dst = Path::new(os::getenv("OUT_DIR").unwrap());
    let _ = fs::mkdir(&dst.join("build"), io::USER_DIR);

    let mut cmd = Command::new("cmake");
    cmd.arg(src.join("libgit2"))
       .cwd(&dst.join("build"));
    if mingw {
        cmd.arg("-G").arg("Unix Makefiles");
    }
    let profile = match os::getenv("PROFILE").unwrap().as_slice() {
        "bench" | "release" => "Release",
        _ => "Debug",
    };
    run(cmd.arg("-DTHREADSAFE=ON")
           .arg("-DBUILD_SHARED_LIBS=OFF")
           .arg("-DBUILD_CLAR=OFF")
           .arg(format!("-DCMAKE_BUILD_TYPE={}", profile))
           .arg(format!("-DCMAKE_INSTALL_PREFIX={}", dst.display()))
           .arg("-DBUILD_EXAMPLES=OFF")
           .arg(format!("-DCMAKE_C_FLAGS={}", cflags)));
    run(Command::new("cmake")
                .arg("--build").arg(".")
                .arg("--target").arg("install")
                .cwd(&dst.join("build")));

    println!("cargo:root={}", dst.display());
    if mingw || target.contains("windows") {
        println!("cargo:rustc-flags=-l winhttp -l rpcrt4 -l ole32 \
                                    -l ws2_32 -l bcrypt -l crypt32");
    } else if os::getenv("HOST") == os::getenv("TARGET") {
        opts.statik = true;
        opts.atleast_version = None;
        append("PKG_CONFIG_PATH", dst.join("lib/pkgconfig"));
        pkg_config::find_library_opts("libgit2", &opts).unwrap();
    } else {
        println!("cargo:rustc-flags=-l git2:static");
        println!("cargo:rustc-flags=-L {}", dst.join("lib").display());
        if target.contains("apple") {
            println!("cargo:rustc-flags:-l iconv");
        }
    }
}

fn run(cmd: &mut Command) {
    println!("running: {}", cmd);
    assert!(cmd.stdout(InheritFd(1))
               .stderr(InheritFd(2))
               .status()
               .unwrap()
               .success());

}

fn register_dep(dep: &str) {
    match os::getenv(format!("DEP_{}_ROOT", dep).as_slice()) {
        Some(s) => {
            append("CMAKE_PREFIX_PATH", Path::new(s.as_slice()));
            append("PKG_CONFIG_PATH", Path::new(s.as_slice()).join("lib/pkgconfig"));
        }
        None => {}
    }
}

fn append(var: &str, val: Path) {
    let prefix = os::getenv(var).unwrap_or(String::new());
    let mut v = os::split_paths(prefix.as_slice());
    v.push(val);
    os::setenv(var, os::join_paths(v.as_slice()).unwrap());
}
<commit_msg>Fix build on windows<commit_after>extern crate "pkg-config" as pkg_config;

use std::os;
use std::io::{mod, fs, Command};
use std::io::process::InheritFd;

fn main() {
    register_dep("SSH2");
    register_dep("OPENSSL");

    let mut opts = pkg_config::default_options("libgit2");
    opts.atleast_version = Some("0.21.0".to_string());
    match pkg_config::find_library_opts("libgit2", &opts) {
        Ok(()) => return,
        Err(..) => {}
    }

    let mut cflags = os::getenv("CFLAGS").unwrap_or(String::new());
    let target = os::getenv("TARGET").unwrap();
    let mingw = target.contains("windows-gnu");
    cflags.push_str(" -ffunction-sections -fdata-sections");

    if target.contains("i686") {
        cflags.push_str(" -m32");
    } else if target.as_slice().contains("x86_64") {
        cflags.push_str(" -m64");
    }
    if !target.contains("i686") {
        cflags.push_str(" -fPIC");
    }

    let src = Path::new(os::getenv("CARGO_MANIFEST_DIR").unwrap());
    let dst = Path::new(os::getenv("OUT_DIR").unwrap());
    let _ = fs::mkdir(&dst.join("build"), io::USER_DIR);

    let mut cmd = Command::new("cmake");
    cmd.arg(src.join("libgit2"))
       .cwd(&dst.join("build"));
    if mingw {
        cmd.arg("-G").arg("Unix Makefiles");
    }
    let profile = match os::getenv("PROFILE").unwrap().as_slice() {
        "bench" | "release" => "Release",
        _ => "Debug",
    };
    run(cmd.arg("-DTHREADSAFE=ON")
           .arg("-DBUILD_SHARED_LIBS=OFF")
           .arg("-DBUILD_CLAR=OFF")
           .arg(format!("-DCMAKE_BUILD_TYPE={}", profile))
           .arg(format!("-DCMAKE_INSTALL_PREFIX={}", dst.display()))
           .arg("-DBUILD_EXAMPLES=OFF")
           .arg(format!("-DCMAKE_C_FLAGS={}", cflags)));
    run(Command::new("cmake")
                .arg("--build").arg(".")
                .arg("--target").arg("install")
                .cwd(&dst.join("build")));

    println!("cargo:root={}", dst.display());
    if mingw || target.contains("windows") {
        println!("cargo:rustc-flags=-l winhttp -l rpcrt4 -l ole32 \
                                    -l ws2_32 -l bcrypt -l crypt32 \
                                    -l git2:static -L {}",
                 dst.join("lib").display());
    } else if os::getenv("HOST") == os::getenv("TARGET") {
        opts.statik = true;
        opts.atleast_version = None;
        append("PKG_CONFIG_PATH", dst.join("lib/pkgconfig"));
        pkg_config::find_library_opts("libgit2", &opts).unwrap();
    } else {
        println!("cargo:rustc-flags=-l git2:static");
        println!("cargo:rustc-flags=-L {}", dst.join("lib").display());
        if target.contains("apple") {
            println!("cargo:rustc-flags:-l iconv");
        }
    }
}

fn run(cmd: &mut Command) {
    println!("running: {}", cmd);
    assert!(cmd.stdout(InheritFd(1))
               .stderr(InheritFd(2))
               .status()
               .unwrap()
               .success());

}

fn register_dep(dep: &str) {
    match os::getenv(format!("DEP_{}_ROOT", dep).as_slice()) {
        Some(s) => {
            append("CMAKE_PREFIX_PATH", Path::new(s.as_slice()));
            append("PKG_CONFIG_PATH", Path::new(s.as_slice()).join("lib/pkgconfig"));
        }
        None => {}
    }
}

fn append(var: &str, val: Path) {
    let prefix = os::getenv(var).unwrap_or(String::new());
    let mut v = os::split_paths(prefix.as_slice());
    v.push(val);
    os::setenv(var, os::join_paths(v.as_slice()).unwrap());
}
<|endoftext|>


<commit_before>#![allow(unstable)]

use std::os;
use std::io::{Command};
use std::io::process::InheritFd;

static STATIC_LIB_NAME: &'static str = "liblmdb.a";

fn run(cmd: &mut Command) {
    println!("running: {}", cmd);
    assert!(cmd.stdout(InheritFd(1))
            .stderr(InheritFd(2))
            .status()
            .unwrap()
            .success());
}

fn ios_cflags(target: &str) -> String {
    let mut cflags = String::new();

    let (sdk_name, sdk_min_ver) = if target.contains("arm") {
        ("iphoneos", "ios-version-min")
    } else {
        ("iphonesimulator", "ios-simulator-version-min")
    };

    let sdk_output = Command::new("xcrun")
        .arg("--show-sdk-path")
        .arg("--sdk")
        .arg(sdk_name)
        .stderr(InheritFd(2))
        .output()
        .unwrap();
    let sdk_path = String::from_utf8_lossy(sdk_output.output.as_slice());

    let flags = format!(" -target {} -isysroot {} -m{}=7.0", target, sdk_path.as_slice().trim(), sdk_min_ver);
    cflags.push_str(flags.as_slice());

    // Actually only "arm" arch requires a little patching
    // other branches simply filter out invalid archs
    if !target.starts_with("arm-")
        && !target.starts_with("armv7-")
        && !target.starts_with("arm64-")
        && !target.starts_with("armv7s-")
        && !target.starts_with("x86_64-")
        && !target.starts_with("i386-") {
            panic!("Unsupported target for iOS: `{}`", target)
    }

    if target.starts_with("arm-") {
        cflags.push_str(format!(" -arch armv7").as_slice());
    }

    cflags
}

fn cflags() -> String {
    let mut cflags = os::getenv("CFLAGS").unwrap_or(String::new());

    let target = os::getenv("TARGET").unwrap();
    // let profile = os::getenv("PROFILE").unwrap();

    if target.contains("-ios") {
        cflags.push_str(" ");
        cflags.push_str(ios_cflags(target.as_slice()).as_slice());
    } else {
        if target.contains("i686") || target.contains("i386") {
            cflags.push_str(" -m32");
        } else if target.as_slice().contains("x86_64") {
            cflags.push_str(" -m64");
        }

        if !target.contains("i686") {
            cflags.push_str(" -fPIC");
        }
    }

    cflags
}

fn main() {
    let mut cmd = Command::new("make");

    let root = Path::new(os::getenv("CARGO_MANIFEST_DIR").unwrap());
    let dst = Path::new(os::getenv("OUT_DIR").unwrap());

    let mdb_root = root.join_many(vec!["mdb", "libraries", "liblmdb"].as_slice());
    let lib_dir = dst.clone();

    cmd.arg("-C").arg(mdb_root.clone());

    let mut clean_cmd = cmd.clone();
    clean_cmd.arg("clean");
    run(&mut clean_cmd);

    let mut build_cmd = cmd.clone();
    build_cmd.arg("liblmdb.a");
    build_cmd.arg(format!("XCFLAGS={}", cflags()));
    run(&mut build_cmd);

    run(Command::new("cp")
        .arg(mdb_root.join(STATIC_LIB_NAME))
        .arg(lib_dir.join(STATIC_LIB_NAME)));

    println!("cargo:rustc-flags=-L {} -l lmdb:static", lib_dir.display());
}
<commit_msg>Added arm64 synonim for iOS<commit_after>#![allow(unstable)]

use std::os;
use std::io::{Command};
use std::io::process::InheritFd;

static STATIC_LIB_NAME: &'static str = "liblmdb.a";

fn run(cmd: &mut Command) {
    println!("running: {}", cmd);
    assert!(cmd.stdout(InheritFd(1))
            .stderr(InheritFd(2))
            .status()
            .unwrap()
            .success());
}

fn ios_cflags(target: &str) -> String {
    let mut cflags = String::new();

    let (sdk_name, sdk_min_ver) = if target.contains("arm") {
        ("iphoneos", "ios-version-min")
    } else {
        ("iphonesimulator", "ios-simulator-version-min")
    };

    let sdk_output = Command::new("xcrun")
        .arg("--show-sdk-path")
        .arg("--sdk")
        .arg(sdk_name)
        .stderr(InheritFd(2))
        .output()
        .unwrap();
    let sdk_path = String::from_utf8_lossy(sdk_output.output.as_slice());

    let flags = format!(" -target {} -isysroot {} -m{}=7.0", target, sdk_path.as_slice().trim(), sdk_min_ver);
    cflags.push_str(flags.as_slice());

    // Actually only "arm" arch requires a little patching
    // other branches simply filter out invalid archs
    if !target.starts_with("arm-")
        && !target.starts_with("armv7-")
        && !target.starts_with("arm64-")
        && !target.starts_with("aarch64-")
        && !target.starts_with("armv7s-")
        && !target.starts_with("x86_64-")
        && !target.starts_with("i386-") {
            panic!("Unsupported target for iOS: `{}`", target)
    }

    if target.starts_with("arm-") {
        cflags.push_str(format!(" -arch armv7").as_slice());
    }

    cflags
}

fn cflags() -> String {
    let mut cflags = os::getenv("CFLAGS").unwrap_or(String::new());

    let target = os::getenv("TARGET").unwrap();
    // let profile = os::getenv("PROFILE").unwrap();

    if target.contains("-ios") {
        cflags.push_str(" ");
        cflags.push_str(ios_cflags(target.as_slice()).as_slice());
    } else {
        if target.contains("i686") || target.contains("i386") {
            cflags.push_str(" -m32");
        } else if target.as_slice().contains("x86_64") {
            cflags.push_str(" -m64");
        }

        if !target.contains("i686") {
            cflags.push_str(" -fPIC");
        }
    }

    cflags
}

fn main() {
    let mut cmd = Command::new("make");

    let root = Path::new(os::getenv("CARGO_MANIFEST_DIR").unwrap());
    let dst = Path::new(os::getenv("OUT_DIR").unwrap());

    let mdb_root = root.join_many(vec!["mdb", "libraries", "liblmdb"].as_slice());
    let lib_dir = dst.clone();

    cmd.arg("-C").arg(mdb_root.clone());

    let mut clean_cmd = cmd.clone();
    clean_cmd.arg("clean");
    run(&mut clean_cmd);

    let mut build_cmd = cmd.clone();
    build_cmd.arg("liblmdb.a");
    build_cmd.arg(format!("XCFLAGS={}", cflags()));
    run(&mut build_cmd);

    run(Command::new("cp")
        .arg(mdb_root.join(STATIC_LIB_NAME))
        .arg(lib_dir.join(STATIC_LIB_NAME)));

    println!("cargo:rustc-flags=-L {} -l lmdb:static", lib_dir.display());
}
<|endoftext|>


<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.

// compile-flags: -Z borrowck=compare

use std::cell::Cell;
use std::mem::swap;

// Just a grab bag of stuff that you wouldn't want to actually write.

fn strange() -> bool { let _x: bool = return true; }

fn funny() {
    fn f(_x: ()) { }
    f(return);
}

fn what() {
    fn the(x: &Cell<bool>) {
        return while !x.get() { x.set(true); };
    }
    let i = &Cell::new(false);
    let dont = {||the(i)};
    dont();
    assert!((i.get()));
}

fn zombiejesus() {
    loop {
        while (return) {
            if (return) {
                match (return) {
                    1 => {
                        if (return) {
                            return
                        } else {
                            return
                        }
                    }
                    _ => { return }
                };
            } else if (return) {
                return;
            }
        }
        if (return) { break; }
    }
}

fn notsure() {
    let mut _x: isize;
    let mut _y = (_x = 0) == (_x = 0);
    let mut _z = (_x = 0) < (_x = 0);
    let _a = (_x += 0) == (_x = 0);
    let _b = swap(&mut _y, &mut _z) == swap(&mut _y, &mut _z);
}

fn canttouchthis() -> usize {
    fn p() -> bool { true }
    let _a = (assert!((true)) == (assert!(p())));
    let _c = (assert!((p())) == ());
    let _b: bool = (println!("{}", 0) == (return 0));
}

fn angrydome() {
    loop { if break { } }
    let mut i = 0;
    loop { i += 1; if i == 1 { match (continue) { 1 => { }, _ => panic!("wat") } }
      break; }
}

fn evil_lincoln() { let _evil = println!("lincoln"); }

fn dots() {
    assert_eq!(String::from(".................................................."),
               format!("{:?}", .. .. .. .. .. .. .. .. .. .. .. .. ..
                               .. .. .. .. .. .. .. .. .. .. .. ..));
}

fn you_eight() {
    assert_eq!(8, {
        macro_rules! u8 {
            (u8) => {
                mod u8 {
                    pub fn u8<'u8>(u8: &'u8 u8) -> &'u8 u8 {
                        "u8";
                        u8
                    }
                }
            };
        }

        u8!(u8);
        let &u8: &u8 = u8::u8(&8u8);
        u8
    });
}

fn fishy() {
    assert_eq!(String::from("><>"),
               String::<>::from::<>("><>").chars::<>().rev::<>().collect::<String>());
}

fn union() {
    union union<'union> { union: &'union union<'union>, }
}

pub fn main() {
    strange();
    funny();
    what();
    zombiejesus();
    notsure();
    canttouchthis();
    angrydome();
    evil_lincoln();
    dots();
    you_eight();
    fishy();
    union();
}
<commit_msg>Rollup merge of #51059 - oberien:patch-1, r=nikomatsakis<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.

// compile-flags: -Z borrowck=compare

use std::cell::Cell;
use std::mem::swap;

// Just a grab bag of stuff that you wouldn't want to actually write.

fn strange() -> bool { let _x: bool = return true; }

fn funny() {
    fn f(_x: ()) { }
    f(return);
}

fn what() {
    fn the(x: &Cell<bool>) {
        return while !x.get() { x.set(true); };
    }
    let i = &Cell::new(false);
    let dont = {||the(i)};
    dont();
    assert!((i.get()));
}

fn zombiejesus() {
    loop {
        while (return) {
            if (return) {
                match (return) {
                    1 => {
                        if (return) {
                            return
                        } else {
                            return
                        }
                    }
                    _ => { return }
                };
            } else if (return) {
                return;
            }
        }
        if (return) { break; }
    }
}

fn notsure() {
    let mut _x: isize;
    let mut _y = (_x = 0) == (_x = 0);
    let mut _z = (_x = 0) < (_x = 0);
    let _a = (_x += 0) == (_x = 0);
    let _b = swap(&mut _y, &mut _z) == swap(&mut _y, &mut _z);
}

fn canttouchthis() -> usize {
    fn p() -> bool { true }
    let _a = (assert!((true)) == (assert!(p())));
    let _c = (assert!((p())) == ());
    let _b: bool = (println!("{}", 0) == (return 0));
}

fn angrydome() {
    loop { if break { } }
    let mut i = 0;
    loop { i += 1; if i == 1 { match (continue) { 1 => { }, _ => panic!("wat") } }
      break; }
}

fn evil_lincoln() { let _evil = println!("lincoln"); }

fn dots() {
    assert_eq!(String::from(".................................................."),
               format!("{:?}", .. .. .. .. .. .. .. .. .. .. .. .. ..
                               .. .. .. .. .. .. .. .. .. .. .. ..));
}

fn you_eight() {
    assert_eq!(8, {
        macro_rules! u8 {
            (u8) => {
                mod u8 {
                    pub fn u8<'u8>(u8: &'u8 u8) -> &'u8 u8 {
                        "u8";
                        u8
                    }
                }
            };
        }

        u8!(u8);
        let &u8: &u8 = u8::u8(&8u8);
        u8
    });
}

fn fishy() {
    assert_eq!(String::from("><>"),
               String::<>::from::<>("><>").chars::<>().rev::<>().collect::<String>());
}

fn union() {
    union union<'union> { union: &'union union<'union>, }
}

fn special_characters() {
    let val = !((|(..):(_,_),__@_|__)((&*"\\",'🤔')/**/,{})=={&[..=..][..];})//
    ;
    assert!(!val);
}

pub fn main() {
    strange();
    funny();
    what();
    zombiejesus();
    notsure();
    canttouchthis();
    angrydome();
    evil_lincoln();
    dots();
    you_eight();
    fishy();
    union();
    special_characters();
}
<|endoftext|>


<commit_before>// Copyright 2018 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.

#![crate_name = "foo"]

use std::fmt;

// @!has foo/struct.Bar.html '//h3[@id="impl-ToString"]//code' 'impl<T> ToString for T'
pub struct Bar;

// @has foo/struct.Foo.html '//h3[@id="impl-ToString"]//code' 'impl<T> ToString for T'
pub struct Foo;

impl fmt::Display for Foo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "Foo")
    }
}
<commit_msg>Strengthen tests<commit_after>// Copyright 2018 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.

#![crate_name = "foo"]

use std::fmt;

// @!has foo/struct.Bar.html '//h3[@id="impl-ToString"]//code' 'impl<T> ToString for T'
pub struct Bar;

// @has foo/struct.Foo.html '//h3[@id="impl-ToString"]//code' 'impl<T> ToString for T'
pub struct Foo;
// @has foo/struct.Foo.html '//div[@class="sidebar-links"]/a[@href="#impl-ToString"]' 'ToString'

impl fmt::Display for Foo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "Foo")
    }
}
<|endoftext|>


<commit_before>//! Reading proc-macro rustc version information from binary data

use std::{
    fs::File,
    io::{self, Read},
};

use memmap2::Mmap;
use object::read::{File as BinaryFile, Object, ObjectSection};
use paths::AbsPath;
use snap::read::FrameDecoder as SnapDecoder;

#[derive(Debug)]
pub struct RustCInfo {
    pub version: (usize, usize, usize),
    pub channel: String,
    pub commit: Option<String>,
    pub date: Option<String>,
}

/// Read rustc dylib information
pub fn read_dylib_info(dylib_path: &AbsPath) -> io::Result<RustCInfo> {
    macro_rules! err {
        ($e:literal) => {
            io::Error::new(io::ErrorKind::InvalidData, $e)
        };
    }

    let ver_str = read_version(dylib_path)?;
    let mut items = ver_str.split_whitespace();
    let tag = items.next().ok_or_else(|| err!("version format error"))?;
    if tag != "rustc" {
        return Err(err!("version format error (No rustc tag)"));
    }

    let version_part = items.next().ok_or_else(|| err!("no version string"))?;
    let mut version_parts = version_part.split('-');
    let version = version_parts.next().ok_or_else(|| err!("no version"))?;
    let channel = version_parts.next().unwrap_or_default().to_string();

    let commit = match items.next() {
        Some(commit) => {
            match commit.len() {
                0 => None,
                _ => Some(commit[1..].to_string() /* remove ( */)
            }
        },
        None => None
    };
    let date = match items.next() {
        Some(date) => {
            match date.len() {
                0 => None,
                _ => Some(date[0..date.len() - 2].to_string() /* remove ) */)
            }
        },
        None => None
    };

    let version_numbers = version
        .split('.')
        .map(|it| it.parse::<usize>())
        .collect::<Result<Vec<_>, _>>()
        .map_err(|_| err!("version number error"))?;

    if version_numbers.len() != 3 {
        return Err(err!("version number format error"));
    }
    let version = (version_numbers[0], version_numbers[1], version_numbers[2]);

    Ok(RustCInfo { version, channel, commit, date })
}

/// This is used inside read_version() to locate the ".rustc" section
/// from a proc macro crate's binary file.
fn read_section<'a>(dylib_binary: &'a [u8], section_name: &str) -> io::Result<&'a [u8]> {
    BinaryFile::parse(dylib_binary)
        .map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))?
        .section_by_name(section_name)
        .ok_or_else(|| io::Error::new(io::ErrorKind::InvalidData, "section read error"))?
        .data()
        .map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
}

/// Check the version of rustc that was used to compile a proc macro crate's
///
/// binary file.
/// A proc macro crate binary's ".rustc" section has following byte layout:
/// * [b'r',b'u',b's',b't',0,0,0,5] is the first 8 bytes
/// * ff060000 734e6150 is followed, it's the snappy format magic bytes,
///   means bytes from here(including this sequence) are compressed in
///   snappy compression format. Version info is inside here, so decompress
///   this.
/// The bytes you get after decompressing the snappy format portion has
/// following layout:
/// * [b'r',b'u',b's',b't',0,0,0,5] is the first 8 bytes(again)
/// * [crate root bytes] next 4 bytes is to store crate root position,
///   according to rustc's source code comment
/// * [length byte] next 1 byte tells us how many bytes we should read next
///   for the version string's utf8 bytes
/// * [version string bytes encoded in utf8] <- GET THIS BOI
/// * [some more bytes that we don really care but still there] :-)
/// Check this issue for more about the bytes layout:
/// <https://github.com/rust-analyzer/rust-analyzer/issues/6174>
fn read_version(dylib_path: &AbsPath) -> io::Result<String> {
    let dylib_file = File::open(dylib_path)?;
    let dylib_mmaped = unsafe { Mmap::map(&dylib_file) }?;

    let dot_rustc = read_section(&dylib_mmaped, ".rustc")?;

    let header = &dot_rustc[..8];
    const EXPECTED_HEADER: [u8; 8] = [b'r', b'u', b's', b't', 0, 0, 0, 5];
    // check if header is valid
    if header != EXPECTED_HEADER {
        return Err(io::Error::new(
            io::ErrorKind::InvalidData,
            format!("only metadata version 5 is supported, section header was: {:?}", header),
        ));
    }

    let snappy_portion = &dot_rustc[8..];

    let mut snappy_decoder = SnapDecoder::new(snappy_portion);

    // the bytes before version string bytes, so this basically is:
    // 8 bytes for [b'r',b'u',b's',b't',0,0,0,5]
    // 4 bytes for [crate root bytes]
    // 1 byte for length of version string
    // so 13 bytes in total, and we should check the 13th byte
    // to know the length
    let mut bytes_before_version = [0u8; 13];
    snappy_decoder.read_exact(&mut bytes_before_version)?;
    let length = bytes_before_version[12]; // what? can't use -1 indexing?

    let mut version_string_utf8 = vec![0u8; length as usize];
    snappy_decoder.read_exact(&mut version_string_utf8)?;
    let version_string = String::from_utf8(version_string_utf8);
    version_string.map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
}
<commit_msg>Fix formatting<commit_after>//! Reading proc-macro rustc version information from binary data

use std::{
    fs::File,
    io::{self, Read},
};

use memmap2::Mmap;
use object::read::{File as BinaryFile, Object, ObjectSection};
use paths::AbsPath;
use snap::read::FrameDecoder as SnapDecoder;

#[derive(Debug)]
pub struct RustCInfo {
    pub version: (usize, usize, usize),
    pub channel: String,
    pub commit: Option<String>,
    pub date: Option<String>,
}

/// Read rustc dylib information
pub fn read_dylib_info(dylib_path: &AbsPath) -> io::Result<RustCInfo> {
    macro_rules! err {
        ($e:literal) => {
            io::Error::new(io::ErrorKind::InvalidData, $e)
        };
    }

    let ver_str = read_version(dylib_path)?;
    let mut items = ver_str.split_whitespace();
    let tag = items.next().ok_or_else(|| err!("version format error"))?;
    if tag != "rustc" {
        return Err(err!("version format error (No rustc tag)"));
    }

    let version_part = items.next().ok_or_else(|| err!("no version string"))?;
    let mut version_parts = version_part.split('-');
    let version = version_parts.next().ok_or_else(|| err!("no version"))?;
    let channel = version_parts.next().unwrap_or_default().to_string();

    let commit = match items.next() {
        Some(commit) => {
            match commit.len() {
                0 => None,
                _ => Some(commit[1..].to_string() /* remove ( */),
            }
        }
        None => None,
    };
    let date = match items.next() {
        Some(date) => {
            match date.len() {
                0 => None,
                _ => Some(date[0..date.len() - 2].to_string() /* remove ) */),
            }
        }
        None => None,
    };

    let version_numbers = version
        .split('.')
        .map(|it| it.parse::<usize>())
        .collect::<Result<Vec<_>, _>>()
        .map_err(|_| err!("version number error"))?;

    if version_numbers.len() != 3 {
        return Err(err!("version number format error"));
    }
    let version = (version_numbers[0], version_numbers[1], version_numbers[2]);

    Ok(RustCInfo { version, channel, commit, date })
}

/// This is used inside read_version() to locate the ".rustc" section
/// from a proc macro crate's binary file.
fn read_section<'a>(dylib_binary: &'a [u8], section_name: &str) -> io::Result<&'a [u8]> {
    BinaryFile::parse(dylib_binary)
        .map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))?
        .section_by_name(section_name)
        .ok_or_else(|| io::Error::new(io::ErrorKind::InvalidData, "section read error"))?
        .data()
        .map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
}

/// Check the version of rustc that was used to compile a proc macro crate's
///
/// binary file.
/// A proc macro crate binary's ".rustc" section has following byte layout:
/// * [b'r',b'u',b's',b't',0,0,0,5] is the first 8 bytes
/// * ff060000 734e6150 is followed, it's the snappy format magic bytes,
///   means bytes from here(including this sequence) are compressed in
///   snappy compression format. Version info is inside here, so decompress
///   this.
/// The bytes you get after decompressing the snappy format portion has
/// following layout:
/// * [b'r',b'u',b's',b't',0,0,0,5] is the first 8 bytes(again)
/// * [crate root bytes] next 4 bytes is to store crate root position,
///   according to rustc's source code comment
/// * [length byte] next 1 byte tells us how many bytes we should read next
///   for the version string's utf8 bytes
/// * [version string bytes encoded in utf8] <- GET THIS BOI
/// * [some more bytes that we don really care but still there] :-)
/// Check this issue for more about the bytes layout:
/// <https://github.com/rust-analyzer/rust-analyzer/issues/6174>
fn read_version(dylib_path: &AbsPath) -> io::Result<String> {
    let dylib_file = File::open(dylib_path)?;
    let dylib_mmaped = unsafe { Mmap::map(&dylib_file) }?;

    let dot_rustc = read_section(&dylib_mmaped, ".rustc")?;

    let header = &dot_rustc[..8];
    const EXPECTED_HEADER: [u8; 8] = [b'r', b'u', b's', b't', 0, 0, 0, 5];
    // check if header is valid
    if header != EXPECTED_HEADER {
        return Err(io::Error::new(
            io::ErrorKind::InvalidData,
            format!("only metadata version 5 is supported, section header was: {:?}", header),
        ));
    }

    let snappy_portion = &dot_rustc[8..];

    let mut snappy_decoder = SnapDecoder::new(snappy_portion);

    // the bytes before version string bytes, so this basically is:
    // 8 bytes for [b'r',b'u',b's',b't',0,0,0,5]
    // 4 bytes for [crate root bytes]
    // 1 byte for length of version string
    // so 13 bytes in total, and we should check the 13th byte
    // to know the length
    let mut bytes_before_version = [0u8; 13];
    snappy_decoder.read_exact(&mut bytes_before_version)?;
    let length = bytes_before_version[12]; // what? can't use -1 indexing?

    let mut version_string_utf8 = vec![0u8; length as usize];
    snappy_decoder.read_exact(&mut version_string_utf8)?;
    let version_string = String::from_utf8(version_string_utf8);
    version_string.map_err(|e| io::Error::new(io::ErrorKind::InvalidData, e))
}
<|endoftext|>


<commit_before>//! A trait to represent a stream

use std::io;
use std::io::{ErrorKind, Read, Write};
use std::net::{SocketAddr, TcpStream};
use std::fmt;
use std::fmt::{Debug, Formatter};

use openssl::ssl::{SslContext, SslStream};

/// A trait for the concept of opening a stream
pub trait Connector {
    /// Opens a connection to the given IP socket
    fn connect(addr: &SocketAddr, ssl_context: Option<&SslContext>) -> io::Result<Self>;
    /// Upgrades to TLS connection
    fn upgrade_tls(&mut self, ssl_context: &SslContext) -> io::Result<()>;
}

impl Connector for NetworkStream {
    fn connect(addr: &SocketAddr, ssl_context: Option<&SslContext>) -> io::Result<NetworkStream> {
        let tcp_stream = try!(TcpStream::connect(addr));

        match ssl_context {
            Some(context) => match SslStream::new(&context, tcp_stream) {
                Ok(stream) => Ok(NetworkStream::Ssl(stream)),
                Err(err) => Err(io::Error::new(ErrorKind::Other, err)),
            },
            None => Ok(NetworkStream::Plain(tcp_stream)),
        }
    }

    fn upgrade_tls(&mut self, ssl_context: &SslContext) -> io::Result<()> {
        *self = match self.clone() {
            NetworkStream::Plain(stream) => match SslStream::new(ssl_context, stream) {
                Ok(ssl_stream) => NetworkStream::Ssl(ssl_stream),
                Err(err) => return Err(io::Error::new(ErrorKind::Other, err)),
            },
            NetworkStream::Ssl(stream) => NetworkStream::Ssl(stream),
        };
        Ok(())
    }
}

/// Represents the different types of underlying network streams
pub enum NetworkStream {
    /// Plain TCP
    Plain(TcpStream),
    /// SSL over TCP
    Ssl(SslStream<TcpStream>),
}

impl Clone for NetworkStream {
    #[inline]
    fn clone(&self) -> NetworkStream {
        match self {
            &NetworkStream::Plain(ref stream) => NetworkStream::Plain(stream.try_clone().unwrap()),
            &NetworkStream::Ssl(ref stream) => NetworkStream::Ssl(stream.try_clone().unwrap()),
        }
    }
}

impl Debug for NetworkStream {
    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
        f.write_str("NetworkStream(_)")
    }
}

impl Read for NetworkStream {
    #[inline]
    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.read(buf),
            NetworkStream::Ssl(ref mut stream) => stream.read(buf),
        }
    }
}

impl Write for NetworkStream {
    #[inline]
    fn write(&mut self, msg: &[u8]) -> io::Result<usize> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.write(msg),
            NetworkStream::Ssl(ref mut stream) => stream.write(msg),
        }
    }
    #[inline]
    fn flush(&mut self) -> io::Result<()> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.flush(),
            NetworkStream::Ssl(ref mut stream) => stream.flush(),
        }
    }
}
<commit_msg>Comply with RFC1214<commit_after>//! A trait to represent a stream

use std::io;
use std::io::{ErrorKind, Read, Write};
use std::net::{SocketAddr, TcpStream};
use std::fmt;
use std::fmt::{Debug, Formatter};

use openssl::ssl::{SslContext, SslStream};

/// A trait for the concept of opening a stream
pub trait Connector: Sized {
    /// Opens a connection to the given IP socket
    fn connect(addr: &SocketAddr, ssl_context: Option<&SslContext>) -> io::Result<Self>;
    /// Upgrades to TLS connection
    fn upgrade_tls(&mut self, ssl_context: &SslContext) -> io::Result<()>;
}

impl Connector for NetworkStream {
    fn connect(addr: &SocketAddr, ssl_context: Option<&SslContext>) -> io::Result<NetworkStream> {
        let tcp_stream = try!(TcpStream::connect(addr));

        match ssl_context {
            Some(context) => match SslStream::new(&context, tcp_stream) {
                Ok(stream) => Ok(NetworkStream::Ssl(stream)),
                Err(err) => Err(io::Error::new(ErrorKind::Other, err)),
            },
            None => Ok(NetworkStream::Plain(tcp_stream)),
        }
    }

    fn upgrade_tls(&mut self, ssl_context: &SslContext) -> io::Result<()> {
        *self = match self.clone() {
            NetworkStream::Plain(stream) => match SslStream::new(ssl_context, stream) {
                Ok(ssl_stream) => NetworkStream::Ssl(ssl_stream),
                Err(err) => return Err(io::Error::new(ErrorKind::Other, err)),
            },
            NetworkStream::Ssl(stream) => NetworkStream::Ssl(stream),
        };
        Ok(())
    }
}

/// Represents the different types of underlying network streams
pub enum NetworkStream {
    /// Plain TCP
    Plain(TcpStream),
    /// SSL over TCP
    Ssl(SslStream<TcpStream>),
}

impl Clone for NetworkStream {
    #[inline]
    fn clone(&self) -> NetworkStream {
        match self {
            &NetworkStream::Plain(ref stream) => NetworkStream::Plain(stream.try_clone().unwrap()),
            &NetworkStream::Ssl(ref stream) => NetworkStream::Ssl(stream.try_clone().unwrap()),
        }
    }
}

impl Debug for NetworkStream {
    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
        f.write_str("NetworkStream(_)")
    }
}

impl Read for NetworkStream {
    #[inline]
    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.read(buf),
            NetworkStream::Ssl(ref mut stream) => stream.read(buf),
        }
    }
}

impl Write for NetworkStream {
    #[inline]
    fn write(&mut self, msg: &[u8]) -> io::Result<usize> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.write(msg),
            NetworkStream::Ssl(ref mut stream) => stream.write(msg),
        }
    }
    #[inline]
    fn flush(&mut self) -> io::Result<()> {
        match *self {
            NetworkStream::Plain(ref mut stream) => stream.flush(),
            NetworkStream::Ssl(ref mut stream) => stream.flush(),
        }
    }
}
<|endoftext|>


<commit_before>use Data;
use dataflow::channels::pact::Pipeline;
use dataflow::{Stream, Scope};
use dataflow::operators::binary::Binary;

// NOTE : These used to have more exotic implementations that connected observers in a tangle.
// NOTE : It was defective when used with the Observer protocol, because it just forwarded open and
// NOTE : shut messages, without concern for the fact that there would be multiple opens and shuts,
// NOTE : from each of its inputs. This implementation does more staging of data, but should be
// NOTE : less wrong.

// NOTE : Observers don't exist any more, so maybe it could become a horrible tangle again! :D
// NOTE : Not clear that the tangle buys much, as buffers are simply passed along without copying.

pub trait Concat<G: Scope, D: Data> {
    fn concat(&self, &Stream<G, D>) -> Stream<G, D>;
}

impl<G: Scope, D: Data> Concat<G, D> for Stream<G, D> {
    fn concat(&self, other: &Stream<G, D>) -> Stream<G, D> {
        self.binary_stream(other, Pipeline, Pipeline, "Concat", |input1, input2, output| {
            while let Some((time, data)) = input1.next() {
                output.session(time).give_content(data);
            }
            while let Some((time, data)) = input2.next() {
                output.session(time).give_content(data);
            }
        })
    }
}

pub trait Concatenate<G: Scope, D: Data> {
    fn concatenate(&self, Vec<Stream<G, D>>) -> Stream<G, D>;
}

impl<G: Scope, D: Data> Concatenate<G, D> for G {
    fn concatenate(&self, mut sources: Vec<Stream<G, D>>) -> Stream<G, D> {
        if let Some(mut result) = sources.pop() {
            while let Some(next) = sources.pop() {
                result = result.concat(&next);
            }
            result
        }
        else {
            panic!("must pass at least one stream to concatenate");
        }
    }
}
<commit_msg>documentation<commit_after>//! Merges the contents of multiple streams.

use Data;
use dataflow::channels::pact::Pipeline;
use dataflow::{Stream, Scope};
use dataflow::operators::binary::Binary;

// NOTE : These used to have more exotic implementations that connected observers in a tangle.
// NOTE : It was defective when used with the Observer protocol, because it just forwarded open and
// NOTE : shut messages, without concern for the fact that there would be multiple opens and shuts,
// NOTE : from each of its inputs. This implementation does more staging of data, but should be
// NOTE : less wrong.

// NOTE : Observers don't exist any more, so maybe it could become a horrible tangle again! :D
// NOTE : Not clear that the tangle buys much, as buffers are simply passed along without copying.

/// Merge the contents of two streams.
pub trait Concat<G: Scope, D: Data> {
    /// Merge the contents of two streams.
    ///
    /// #Examples
    /// ```
    /// use timely::dataflow::operators::{ToStream, Concat, Inspect};
    ///
    /// timely::example(|scope| {
    ///
    ///     let stream = (0..10).to_stream(scope);
    ///     stream.concat(&stream)
    ///           .inspect(|x| println!("seen: {:?}", x));
    /// });
    /// ```
    fn concat(&self, &Stream<G, D>) -> Stream<G, D>;
}

impl<G: Scope, D: Data> Concat<G, D> for Stream<G, D> {
    fn concat(&self, other: &Stream<G, D>) -> Stream<G, D> {
        self.binary_stream(other, Pipeline, Pipeline, "Concat", |input1, input2, output| {
            input1.for_each(|time, data| { output.session(time).give_content(data); });
            input2.for_each(|time, data| { output.session(time).give_content(data); });
        })
    }
}

/// Merge the contents of multiple streams.
pub trait Concatenate<G: Scope, D: Data> {
    /// Merge the contents of multiple streams.
    ///
    /// #Examples
    /// ```
    /// use timely::dataflow::operators::{ToStream, Concatenate, Inspect};
    ///
    /// timely::example(|scope| {
    ///
    ///     let streams = vec![(0..10).to_stream(scope),
    ///                        (0..10).to_stream(scope),
    ///                        (0..10).to_stream(scope)];
    ///
    ///     scope.concatenate(streams)
    ///          .inspect(|x| println!("seen: {:?}", x));
    /// });
    /// ```
    fn concatenate(&self, Vec<Stream<G, D>>) -> Stream<G, D>;
}

impl<G: Scope, D: Data> Concatenate<G, D> for G {
    fn concatenate(&self, mut sources: Vec<Stream<G, D>>) -> Stream<G, D> {
        if let Some(mut result) = sources.pop() {
            while let Some(next) = sources.pop() {
                result = result.concat(&next);
            }
            result
        }
        else {
            panic!("must pass at least one stream to concatenate");
        }
    }
}
<|endoftext|>


<commit_before>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

use eutil::fptr_is_null;
use libc::{c_int};
use std::collections::TreeMap;
use std::mem;
use std::slice;
use std::str;
use std::string::String;
use string::{cef_string_userfree_utf8_alloc,cef_string_userfree_utf8_free,cef_string_utf8_set};
use types::{cef_string_map_t,cef_string_t};

fn string_map_to_treemap(sm: *mut cef_string_map_t) -> *mut TreeMap<String, *mut cef_string_t> {
    sm as *mut TreeMap<String, *mut cef_string_t>
}

//cef_string_map

#[no_mangle]
pub extern "C" fn cef_string_map_alloc() -> *mut cef_string_map_t {
    unsafe {
         let sm: Box<TreeMap<String, *mut cef_string_t>> = box TreeMap::new();
         mem::transmute(sm)
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_size(sm: *mut cef_string_map_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        (*v).len() as c_int
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_append(sm: *mut cef_string_map_t, key: *const cef_string_t, value: *const cef_string_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        slice::raw::buf_as_slice(mem::transmute((*key).str), (*key).length as uint, |result| {
            match str::from_utf8(result) {
                Some(k) => {
                    let s = String::from_str(k);
                    let csv = cef_string_userfree_utf8_alloc();
                    cef_string_utf8_set(mem::transmute((*value).str), (*value).length, csv, 1);
                    (*v).insert(s, csv);
                    1
                },
                None => 0
            }
        })
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_find(sm: *mut cef_string_map_t, key: *const cef_string_t, value: *mut cef_string_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        slice::raw::buf_as_slice(mem::transmute((*key).str), (*key).length as uint, |result| {
            match str::from_utf8(result) {
                Some(k) => {
                    match (*v).find(&String::from_str(k)) {
                        Some(s) => {
                            cef_string_utf8_set(mem::transmute((**s).str), (**s).length, value, 1);
                            1
                        }
                        None => 0
                    }
                },
                None => 0
            }
        })
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_key(sm: *mut cef_string_map_t, index: c_int, value: *mut cef_string_t) -> c_int {
    unsafe {
        if index < 0 || fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        if index as uint > (*v).len() - 1 { return 0; }

        for (i, k) in (*v).keys().enumerate() {
            if i == index as uint {
                cef_string_utf8_set(k.as_bytes().as_ptr(), k.len() as u64, value, 1);
                return 1;
            }
        }
    }
    0
}

#[no_mangle]
pub extern "C" fn cef_string_map_value(sm: *mut cef_string_map_t, index: c_int, value: *mut cef_string_t) -> c_int {
    unsafe {
        if index < 0 || fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        if index as uint > (*v).len() - 1 { return 0; }

        for (i, val) in (*v).values().enumerate() {
            if i == index as uint {
                cef_string_utf8_set(mem::transmute((**val).str), (**val).length, value, 1);
                return 1;
            }
        }
    }
    0
}
<commit_msg>embedding: cef_string_map_clear()<commit_after>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

use eutil::fptr_is_null;
use libc::{c_int};
use std::collections::TreeMap;
use std::mem;
use std::slice;
use std::str;
use std::string::String;
use string::{cef_string_userfree_utf8_alloc,cef_string_userfree_utf8_free,cef_string_utf8_set};
use types::{cef_string_map_t,cef_string_t};

fn string_map_to_treemap(sm: *mut cef_string_map_t) -> *mut TreeMap<String, *mut cef_string_t> {
    sm as *mut TreeMap<String, *mut cef_string_t>
}

//cef_string_map

#[no_mangle]
pub extern "C" fn cef_string_map_alloc() -> *mut cef_string_map_t {
    unsafe {
         let sm: Box<TreeMap<String, *mut cef_string_t>> = box TreeMap::new();
         mem::transmute(sm)
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_size(sm: *mut cef_string_map_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        (*v).len() as c_int
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_append(sm: *mut cef_string_map_t, key: *const cef_string_t, value: *const cef_string_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        slice::raw::buf_as_slice(mem::transmute((*key).str), (*key).length as uint, |result| {
            match str::from_utf8(result) {
                Some(k) => {
                    let s = String::from_str(k);
                    let csv = cef_string_userfree_utf8_alloc();
                    cef_string_utf8_set(mem::transmute((*value).str), (*value).length, csv, 1);
                    (*v).insert(s, csv);
                    1
                },
                None => 0
            }
        })
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_find(sm: *mut cef_string_map_t, key: *const cef_string_t, value: *mut cef_string_t) -> c_int {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        slice::raw::buf_as_slice(mem::transmute((*key).str), (*key).length as uint, |result| {
            match str::from_utf8(result) {
                Some(k) => {
                    match (*v).find(&String::from_str(k)) {
                        Some(s) => {
                            cef_string_utf8_set(mem::transmute((**s).str), (**s).length, value, 1);
                            1
                        }
                        None => 0
                    }
                },
                None => 0
            }
        })
    }
}

#[no_mangle]
pub extern "C" fn cef_string_map_key(sm: *mut cef_string_map_t, index: c_int, value: *mut cef_string_t) -> c_int {
    unsafe {
        if index < 0 || fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        if index as uint > (*v).len() - 1 { return 0; }

        for (i, k) in (*v).keys().enumerate() {
            if i == index as uint {
                cef_string_utf8_set(k.as_bytes().as_ptr(), k.len() as u64, value, 1);
                return 1;
            }
        }
    }
    0
}

#[no_mangle]
pub extern "C" fn cef_string_map_value(sm: *mut cef_string_map_t, index: c_int, value: *mut cef_string_t) -> c_int {
    unsafe {
        if index < 0 || fptr_is_null(mem::transmute(sm)) { return 0; }
        let v = string_map_to_treemap(sm);
        if index as uint > (*v).len() - 1 { return 0; }

        for (i, val) in (*v).values().enumerate() {
            if i == index as uint {
                cef_string_utf8_set(mem::transmute((**val).str), (**val).length, value, 1);
                return 1;
            }
        }
    }
    0
}

#[no_mangle]
pub extern "C" fn cef_string_map_clear(sm: *mut cef_string_map_t) {
    unsafe {
        if fptr_is_null(mem::transmute(sm)) { return; }
        let v = string_map_to_treemap(sm);
        if (*v).len() == 0 { return; }
        for val in (*v).values() {
            cef_string_userfree_utf8_free((*val));
        }
        (*v).clear();
    }
}
<|endoftext|>


<commit_before>extern crate rand;

use rand::{thread_rng, Rng};

fn get_hsp(w1: &String, w2: &String, match_scr: i32, mism_scr: i32, gap_scr: i32) -> i32 {
    let mut hsp = 0;

    let mut chars2 = w2.chars();
    for c1 in w1.chars() {
        let c2 = chars2.next().unwrap();
        hsp += if c1 == '_' || c2 == '_' {
            gap_scr
        } else if c1 == c2 {
            match_scr
        } else {
            mism_scr
        }
    }

    hsp
}

fn ver_crossover(s1: &mut String, s2: &mut String, crosspoint: usize) {
    let mut post_s1 = s1.split_off(crosspoint);

    let chars = s1.replace("_", "");

    let mut ch_indx = 0;
    let mut indx = 0;
    while ch_indx < chars.len() {
        if s2.chars().nth(indx).unwrap() == chars.chars().nth(ch_indx).unwrap() {
            ch_indx += 1;
        }
        indx += 1;
    }

    let mut post_s2 = s2.split_off(indx);
    *s1 += post_s2.as_ref();
    *s2 += post_s1.as_ref();
}

fn adjust_to_size(len: usize, s: &mut String) {
    let mut s_len = s.len();
    let mut rng = thread_rng();
    while s_len != len {
        let indx = rng.gen_range(0, s_len);
        if s_len > len {
            if s.chars().nth(indx).unwrap() == '_' {
                s.remove(indx);
            }
        } else {
            s.insert_str(indx, "_");
        }
        s_len = s.len();
    }
}

// pub trait Cromosome {
//     fn new(size: usize, input: Vec<String>) -> Cromosome;
//     fn random(&mut self);
//     fn fitness(&self) -> u32;
//     fn crossover(&mut self, parent2: &mut Cromosome, crosspoint: usize);
//     fn mutate(&mut self);
// }

#[derive(Debug)]
pub struct Cromosome {
    size: usize,
    genotype: Vec<String>,
}

impl Cromosome {
    pub fn new(size: usize, input: &Vec<&str>) -> Cromosome {
        let mut st_gen = Vec::new();
        for align in input.iter() {
            st_gen.push(String::from(*align));
        }

        let mut rng = thread_rng();
        for align in st_gen.iter_mut() {
            let mut current_len = align.len();
            while current_len < size {
                align.insert_str(rng.gen_range(0, current_len), "_");
                current_len = align.len();
            }
        }

        Cromosome {
            size: size,
            genotype: st_gen,
        }
    }

    pub fn fitness(&self) -> i32 {
        let mut fitness = 0;
        let size = self.genotype.len();
        for i in 0..size {
            for j in i+1..size {
                fitness += get_hsp(&self.genotype[i], &self.genotype[j], 3, 1, 0);
            }
        }

        fitness
    }

    pub fn crossover(&mut self, parent2: &mut Cromosome, crosspoint: usize) {
        let len = self.genotype.len();
        if len != parent2.genotype.len() {
            panic!("Can't cross this pair of Cromosomes");
        }

        for i in 0..len {
            ver_crossover(&mut self.genotype[i], &mut parent2.genotype[i], crosspoint);
            adjust_to_size(self.size, &mut self.genotype[i]);
            adjust_to_size(self.size, &mut parent2.genotype[i]);
        }
    }

    pub fn mutate(&mut self) {
        for seq in self.genotype.iter_mut() {
            print!("{} -> ", seq);
            let mut c_seq = seq.replace("_", "");
            adjust_to_size(self.size, &mut c_seq);
            *seq = c_seq;
            println!("{}", seq);
        }
    }
}

#[derive(Debug)]
pub struct Population {
    pob_size: usize,
    crom_size: usize,
    population: Vec<Cromosome>,
    ruleta_vec: Vec<f32>,
}

impl Population {
    pub fn new(pob_size: usize, crom_size: usize) -> Population {
        Population {
            pob_size: pob_size,
            crom_size: crom_size,
            population: Vec::new(),
            ruleta_vec: Vec::new(),
        }
    }

    pub fn generate(&mut self, input: &Vec<&str>) {
        println!("\nGenerando Población inicial");

        for _ in 0..self.pob_size {
            let mut crom = Cromosome::new(self.crom_size, input);
            self.population.push(crom);
        }

        for i in 0..self.pob_size {
            println!("{}) {:?}", i + 1, self.population[i].genotype);
        }
    }

    pub fn eval(&self) {
        println!("Evaluando Individuos");
        for i in 0..self.pob_size {
            println!("{}) {:?} - {}",
                     i + 1,
                     self.population[i].genotype,
                     self.population[i].fitness());
        }
    }

    pub fn ruleta(&mut self) {
        println!("Selección de Individuos - Método de la Ruleta");
        let mut sum_ruleta = 0;
        self.ruleta_vec = Vec::new();

        for i in 0..self.pob_size {
            sum_ruleta += self.population[i].fitness();
        }

        for i in 0..self.pob_size {
            self.ruleta_vec
                .push((self.population[i].fitness() as f32 * 100.0) / sum_ruleta as f32);
        }

        for i in 0..self.pob_size {
            println!("{}) {:?} - {} - {}",
                     i + 1,
                     self.population[i].genotype,
                     self.population[i].fitness(),
                     self.ruleta_vec[i]);
        }
    }

    pub fn random_parent_index(&self) -> usize {
        let mut rng = rand::thread_rng();
        let num = rng.gen::<f32>() * 100.0;
        let mut s = 0.0;

        for i in 0..self.ruleta_vec.len() {
            s += self.ruleta_vec[i];
            if num < s {
                return i;
            }
        }

        self.ruleta_vec.len()
    }

    pub fn crossover(&mut self, crossover_prob: f32, crossover_point: usize) {
        let parent1 = self.random_parent_index();
        let mut parent2 = self.random_parent_index();

        while parent2 == parent1 {
            let mut rng = rand::thread_rng();
            parent2 = rng.gen::<usize>() % self.pob_size;
        }

        println!("Padre: {}", parent1 + 1);
        println!("Madre: {}", parent2 + 1);

        let mut child1 = Cromosome {
            // size: self.population[parent1].size,
            size: self.crom_size,
            genotype: self.population[parent1].genotype.clone(),
        };

        let mut child2 = Cromosome {
            // size: self.population[parent2].size,
            size: self.crom_size,
            genotype: self.population[parent2].genotype.clone(),
        };

        let mut rng = rand::thread_rng();
        if rng.gen::<f32>() < crossover_prob {
            println!("Cruzamiento");
            child1.crossover(&mut child2, crossover_point + 1);
        } else {
            println!("Sin cruzamiento");
        }

        self.population.push(child1);
        self.population.push(child2);
    }

    pub fn mutate(&mut self, chance: f32) {
        for i in 0..self.population.len() {
            let mut rng = rand::thread_rng();
            if rng.gen::<f32>() > chance {
                return;
            }
            println!("Mutó {}", i + 1);
            self.population[i].mutate();
        }
    }

    pub fn selection(&mut self) {
        println!("Selección de Siguiente Población");
        let mut new_population: Vec<(i32, Vec<String>)> = Vec::new();
        for i in 0..self.population.len() {
            let fitness = self.population[i].fitness();
            let gen = self.population[i].genotype.clone();
            println!("{}) {:?} - {}", i + 1, gen, fitness);
            new_population.push((fitness, gen));
        }

        new_population.sort_by(|a, b| b.0.partial_cmp(&a.0).unwrap());

        self.population.clear();
        for i in 0..self.pob_size {
            self.population
                .push(Cromosome {
                        //   size: new_population[i].1.len(),
                          size: self.crom_size,
                          genotype: new_population[i].1.clone(),
                      });
        }

        // println!("{:?}", new_population);
    }
}

#[derive(Debug)]
pub struct Solver {
    population: Population,
    iterations: usize,
    crossover_prob: f32,
    crossover_point: usize,
    mutation_prob: f32,
}

impl Solver {
    pub fn new(pob_size: usize,
               crom_size: usize,
               iterations: usize,
               crossover_prob: f32,
               crossover_point: usize,
               mutation_prob: f32)
               -> Solver {
        println!("run:");
        println!("Tamaño de la Población: {}", pob_size);
        println!("Tamaño de los Cromosomas: {}", crom_size);
        println!("Cantidad de Iteraciones: {}", iterations);
        println!("Probabilidad de Cruzamiento: {}", crossover_prob);
        println!("Cruzamiento de un Punto - Punto {}", crossover_point);
        println!("Probabilidad de Mutación: {}", mutation_prob);
        println!("Mutación Simple");

        let mut population = Population::new(pob_size, crom_size);

        Solver {
            population: population,
            iterations: iterations,
            crossover_prob: crossover_prob,
            crossover_point: crossover_point,
            mutation_prob: mutation_prob,
        }
    }

    pub fn evolve(&mut self, input: Vec<&str>) {
        self.population.generate(&input);

        for i in 0..self.iterations {
            println!("\nIteración: {}", i);
            self.population.eval();
            self.population.ruleta();
            let pob_size = self.population.pob_size / 2;
            for _ in 0..pob_size {
            self.population.crossover(self.crossover_prob, self.crossover_point);
            self.population.mutate(self.mutation_prob);
            }
            self.population.selection();
        }

        println!("\nIteración: {}", self.iterations);
        self.population.eval();

        println!("\nFin del Proceso");
    }
}

fn main() {
    let mut solver = Solver::new(6, 9, 10, 0.9, 3, 0.2);
    solver.evolve(vec!["AGTCATTAATTGCGGTTAG", "CCAATTGTAGTT", "AGCATTCGTAGTT", "GTTCAAGGGAGTT"]);
    // solver.evolve(vec!["ADSDAAC", "ADTTC", "ADTCD"]);

    // let mut cro1 = Cromosome::new(9, vec!["ADSDAAC", "ADTTC"]);
    // let mut cro2 = Cromosome::new(9, vec!["ADASAC", "AADTC"]);
    // println!("{:#?}\n{}", cro1, cro1.fitness());
    // println!("{:#?}\n{}", cro2, cro1.fitness());
    // cro1.mutate();
    // cro2.mutate();
    // println!("{:#?}\n{}", cro1, cro1.fitness());
    // println!("{:#?}\n{}", cro2, cro1.fitness());
    // println!("{:#?}", Cromosome::new(22, vec!["AGTCATTAATTGCGGTTAG", "CCAATTGTAGTT", "AGCATTCGTAGTT", "GTTCAAGGGAGTT"]));
}
<commit_msg>Finished!<commit_after>extern crate rand;

use rand::{thread_rng, Rng};

fn get_hsp(w1: &String, w2: &String, match_scr: i32, mism_scr: i32, gap_scr: i32) -> i32 {
    let mut hsp = 0;

    let mut chars2 = w2.chars();
    for c1 in w1.chars() {
        let c2 = chars2.next().unwrap();
        hsp += if c1 == '_' || c2 == '_' {
            gap_scr
        } else if c1 == c2 {
            match_scr
        } else {
            mism_scr
        }
    }

    hsp
}

fn ver_crossover(s1: &mut String, s2: &mut String, crosspoint: usize) {
    let mut post_s1 = s1.split_off(crosspoint);

    let chars = s1.replace("_", "");

    let mut ch_indx = 0;
    let mut indx = 0;
    while ch_indx < chars.len() {
        if s2.chars().nth(indx).unwrap() == chars.chars().nth(ch_indx).unwrap() {
            ch_indx += 1;
        }
        indx += 1;
    }

    let mut post_s2 = s2.split_off(indx);
    *s1 += post_s2.as_ref();
    *s2 += post_s1.as_ref();
}

fn adjust_to_size(len: usize, s: &mut String) {
    let mut s_len = s.len();
    let mut rng = thread_rng();
    while s_len != len {
        let indx = rng.gen_range(0, s_len);
        if s_len > len {
            if s.chars().nth(indx).unwrap() == '_' {
                s.remove(indx);
            }
        } else {
            s.insert_str(indx, "_");
        }
        s_len = s.len();
    }
}

// pub trait Cromosome {
//     fn new(size: usize, input: Vec<String>) -> Cromosome;
//     fn random(&mut self);
//     fn fitness(&self) -> u32;
//     fn crossover(&mut self, parent2: &mut Cromosome, crosspoint: usize);
//     fn mutate(&mut self);
// }

#[derive(Debug)]
pub struct Cromosome {
    size: usize,
    genotype: Vec<String>,
}

impl Cromosome {
    pub fn new(size: usize, input: &Vec<&str>) -> Cromosome {
        let mut st_gen = Vec::new();
        for align in input.iter() {
            st_gen.push(String::from(*align));
        }

        let mut rng = thread_rng();
        for align in st_gen.iter_mut() {
            let mut current_len = align.len();
            while current_len < size {
                align.insert_str(rng.gen_range(0, current_len), "_");
                current_len = align.len();
            }
        }

        Cromosome {
            size: size,
            genotype: st_gen,
        }
    }

    pub fn fitness(&self) -> i32 {
        let mut fitness = 0;
        let size = self.genotype.len();
        for i in 0..size {
            for j in i+1..size {
                fitness += get_hsp(&self.genotype[i], &self.genotype[j], 3, 1, 0);
            }
        }

        fitness
    }

    pub fn crossover(&mut self, parent2: &mut Cromosome, crosspoint: usize) {
        let len = self.genotype.len();
        if len != parent2.genotype.len() {
            panic!("Can't cross this pair of Cromosomes");
        }

        for i in 0..len {
            ver_crossover(&mut self.genotype[i], &mut parent2.genotype[i], crosspoint);
            adjust_to_size(self.size, &mut self.genotype[i]);
            adjust_to_size(self.size, &mut parent2.genotype[i]);
        }
    }

    pub fn mutate(&mut self) {
        for seq in self.genotype.iter_mut() {
            print!("{} -> ", seq);
            let mut c_seq = seq.replace("_", "");
            adjust_to_size(self.size, &mut c_seq);
            *seq = c_seq;
            println!("{}", seq);
        }
    }
}

#[derive(Debug)]
pub struct Population {
    pob_size: usize,
    crom_size: usize,
    population: Vec<Cromosome>,
    ruleta_vec: Vec<f32>,
}

impl Population {
    pub fn new(pob_size: usize, crom_size: usize) -> Population {
        Population {
            pob_size: pob_size,
            crom_size: crom_size,
            population: Vec::new(),
            ruleta_vec: Vec::new(),
        }
    }

    pub fn generate(&mut self, input: &Vec<&str>) {
        println!("\nGenerando Población inicial");

        for _ in 0..self.pob_size {
            let mut crom = Cromosome::new(self.crom_size, input);
            self.population.push(crom);
        }

        for i in 0..self.pob_size {
            println!("{}) {:?}", i + 1, self.population[i].genotype);
        }
    }

    pub fn eval(&self) {
        println!("Evaluando Individuos");
        for i in 0..self.pob_size {
            println!("{}) {:?} - {}",
                     i + 1,
                     self.population[i].genotype,
                     self.population[i].fitness());
        }
    }

    pub fn ruleta(&mut self) {
        println!("Selección de Individuos - Método de la Ruleta");
        let mut sum_ruleta = 0;
        self.ruleta_vec = Vec::new();

        for i in 0..self.pob_size {
            sum_ruleta += self.population[i].fitness();
        }

        for i in 0..self.pob_size {
            self.ruleta_vec
                .push((self.population[i].fitness() as f32 * 100.0) / sum_ruleta as f32);
        }

        for i in 0..self.pob_size {
            println!("{}) {:?} - {} - {}",
                     i + 1,
                     self.population[i].genotype,
                     self.population[i].fitness(),
                     self.ruleta_vec[i]);
        }
    }

    pub fn random_parent_index(&self) -> usize {
        let mut rng = rand::thread_rng();
        let num = rng.gen::<f32>() * 100.0;
        let mut s = 0.0;

        for i in 0..self.ruleta_vec.len() {
            s += self.ruleta_vec[i];
            if num < s {
                return i;
            }
        }

        self.ruleta_vec.len()
    }

    pub fn crossover(&mut self, crossover_prob: f32, crossover_point: usize) {
        let parent1 = self.random_parent_index();
        let mut parent2 = self.random_parent_index();

        while parent2 == parent1 {
            let mut rng = rand::thread_rng();
            parent2 = rng.gen::<usize>() % self.pob_size;
        }

        println!("Padre: {}", parent1 + 1);
        println!("Madre: {}", parent2 + 1);

        let mut child1 = Cromosome {
            // size: self.population[parent1].size,
            size: self.crom_size,
            genotype: self.population[parent1].genotype.clone(),
        };

        let mut child2 = Cromosome {
            // size: self.population[parent2].size,
            size: self.crom_size,
            genotype: self.population[parent2].genotype.clone(),
        };

        let mut rng = rand::thread_rng();
        if rng.gen::<f32>() < crossover_prob {
            println!("Cruzamiento");
            child1.crossover(&mut child2, crossover_point + 1);
        } else {
            println!("Sin cruzamiento");
        }

        self.population.push(child1);
        self.population.push(child2);
    }

    pub fn mutate(&mut self, chance: f32) {
        for i in 0..self.population.len() {
            let mut rng = rand::thread_rng();
            if rng.gen::<f32>() > chance {
                return;
            }
            println!("Mutó {}", i + 1);
            self.population[i].mutate();
        }
    }

    pub fn selection(&mut self) {
        println!("Selección de Siguiente Población");
        let mut new_population: Vec<(i32, Vec<String>)> = Vec::new();
        for i in 0..self.population.len() {
            let fitness = self.population[i].fitness();
            let gen = self.population[i].genotype.clone();
            println!("{}) {:?} - {}", i + 1, gen, fitness);
            new_population.push((fitness, gen));
        }

        new_population.sort_by(|a, b| b.0.partial_cmp(&a.0).unwrap());

        self.population.clear();
        for i in 0..self.pob_size {
            self.population
                .push(Cromosome {
                        //   size: new_population[i].1.len(),
                          size: self.crom_size,
                          genotype: new_population[i].1.clone(),
                      });
        }

        // println!("{:?}", new_population);
    }
}

#[derive(Debug)]
pub struct Solver {
    population: Population,
    iterations: usize,
    crossover_prob: f32,
    crossover_point: usize,
    mutation_prob: f32,
}

impl Solver {
    pub fn new(pob_size: usize,
               crom_size: usize,
               iterations: usize,
               crossover_prob: f32,
               crossover_point: usize,
               mutation_prob: f32)
               -> Solver {
        println!("run:");
        println!("Tamaño de la Población: {}", pob_size);
        println!("Tamaño de los Cromosomas: {}", crom_size);
        println!("Cantidad de Iteraciones: {}", iterations);
        println!("Probabilidad de Cruzamiento: {}", crossover_prob);
        println!("Cruzamiento de un Punto - Punto {}", crossover_point);
        println!("Probabilidad de Mutación: {}", mutation_prob);
        println!("Mutación Simple");

        let mut population = Population::new(pob_size, crom_size);

        Solver {
            population: population,
            iterations: iterations,
            crossover_prob: crossover_prob,
            crossover_point: crossover_point,
            mutation_prob: mutation_prob,
        }
    }

    pub fn evolve(&mut self, input: Vec<&str>) {
        self.population.generate(&input);

        for i in 0..self.iterations {
            println!("\nIteración: {}", i);
            self.population.eval();
            self.population.ruleta();
            let pob_size = self.population.pob_size / 2;
            for _ in 0..pob_size {
            self.population.crossover(self.crossover_prob, self.crossover_point);
            self.population.mutate(self.mutation_prob);
            }
            self.population.selection();
        }

        println!("\nIteración: {}", self.iterations);
        self.population.eval();

        println!("\nFin del Proceso");
    }
}

fn main() {
    let mut solver = Solver::new(100, 22, 100, 0.9, 3, 0.2);
    solver.evolve(vec!["AGTCATTAATTGCGGTTAG", "CCAATTGTAGTT", "AGCATTCGTAGTT", "GTTCAAGGGAGTT"]);
    // let mut solver = Solver::new(6, 9, 10, 0.9, 3, 0.2);
    // solver.evolve(vec!["ADSDAAC", "ADTTC", "ADTCD"]);
}
<|endoftext|>


<commit_before>use redox::*;

pub struct Editor {
    url: String,
    file: Option<File>,
    string: String,
    offset: usize,
    scroll_x: isize,
    scroll_y: isize,
}

impl Editor {
    #[inline(never)]
    pub fn new() -> Self {
        Editor {
            url: String::new(),
            file: Option::None,
            string: String::new(),
            offset: 0,
            scroll_x: 0,
            scroll_y: 0,
        }
    }

    fn reload(&mut self, window: &mut Window) {
        window.set_title(&format!("{}{}{}","Editor (", &self.url, ")"));
        self.offset = 0;
        self.scroll_x = 0;
        self.scroll_y = 0;

        match self.file {
            Option::Some(ref mut file) => {
                file.seek(Seek::Start(0));
                let mut vec: Vec<u8> = Vec::new();
                file.read_to_end(&mut vec);
                self.string = unsafe { String::from_utf8_unchecked(vec) };
            }
            Option::None => self.string = String::new(),
        }
    }

    fn save(&mut self, window: &mut Window) {
        match self.file {
            Option::Some(ref mut file) => {
                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Saved"));
                file.seek(Seek::Start(0));
                file.write(&self.string.as_bytes());
                file.sync();
            }
            Option::None => {
                //TODO: Ask for file to save to
                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") No Open File"));
            }
        }
    }

    fn draw_content(&mut self, window: &mut Window) {
        let mut redraw = false;

        {
            window.set([0, 0, 0, 196]);

            let scroll_x = self.scroll_x;
            let scroll_y = self.scroll_y;

            let mut offset = 0;

            let mut col = -scroll_x;
            let cols = window.width() as isize / 8;

            let mut row = -scroll_y;
            let rows = window.height() as isize / 16;

            for c in self.string.chars() {
                if offset == self.offset {
                    if col >= 0 && col < cols && row >= 0 && row < rows {
                        window.char(8 * col, 16 * row, '_', [128, 128, 128, 255]);
                    } else {
                        if col < 0 { //Too far to the left
                            self.scroll_x += col;
                        } else if col >= cols { //Too far to the right
                            self.scroll_x += cols - col + 1;
                        }
                        if row < 0 { //Too far up
                            self.scroll_y += row;
                        } else if row >= rows { //Too far down
                            self.scroll_y += rows - row + 1;
                        }

                        redraw = true;
                    }
                }

                if c == '\n' {
                    col = -scroll_x;
                    row += 1;
                } else if c == '\t' {
                    col += 8 - col % 8;
                } else {
                    if col >= 0 && col < cols && row >= 0 && row < rows {
                        window.char(8 * col, 16 * row, c, [255, 255, 255, 255]);
                    }
                    col += 1;
                }

                offset += 1;
            }

            if offset == self.offset {
                if col >= 0 && col < cols && row >= 0 && row < rows {
                    window.char(8 * col, 16 * row, '_', [128, 128, 128, 255]);
                } else {
                    if col < 0 { //Too far to the left
                        self.scroll_x += col;
                    } else if col >= cols { //Too far to the right
                        self.scroll_x += cols - col + 1;
                    }
                    if row < 0 { //Too far up
                        self.scroll_y += row;
                    } else if row >= rows { //Too far down
                        self.scroll_y += rows - row + 1;
                    }

                    redraw = true;
                }
            }

            window.sync();
        }

        if redraw {
            self.draw_content(window);
        }
    }

    fn main(&mut self, url: &str) {
        let mut window = Window::new((rand() % 400 + 50) as isize,
                                    (rand() % 300 + 50) as isize,
                                    576,
                                    400,
                                     "Editor (Loading)");

        self.url = url.to_string();
        self.file = Option::Some(File::open(&self.url));

        self.reload(&mut window);
        self.draw_content(&mut window);

        while let Option::Some(event) = window.poll() {
            match event.to_option() {
                EventOption::Key(key_event) => {
                    if key_event.pressed {
                        match key_event.scancode {
                            K_ESC => break,
                            K_BKSP => if self.offset > 0 {
                                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                self.string = self.string[0 .. self.offset - 1].to_string() +
                                              &self.string[self.offset .. self.string.len()];
                                self.offset -= 1;
                            },
                            K_DEL => if self.offset < self.string.len() {
                                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                self.string = self.string[0 .. self.offset].to_string() +
                                              &self.string[self.offset + 1 .. self.string.len() - 1];
                            },
                            K_F5 => self.reload(&mut window),
                            K_F6 => self.save(&mut window),
                            K_HOME => self.offset = 0,
                            K_UP => {
                                let mut new_offset = 0;
                                for i in 2..self.offset {
                                    match self.string.as_bytes()[self.offset - i] {
                                        0 => break,
                                        10 => {
                                            new_offset = self.offset - i + 1;
                                            break;
                                        }
                                        _ => (),
                                    }
                                }
                                self.offset = new_offset;
                            }
                            K_LEFT => if self.offset > 0 {
                                self.offset -= 1;
                            },
                            K_RIGHT => if self.offset < self.string.len() {
                                self.offset += 1;
                            },
                            K_END => self.offset = self.string.len(),
                            K_DOWN => {
                                let mut new_offset = self.string.len();
                                for i in self.offset..self.string.len() {
                                    match self.string.as_bytes()[i] {
                                        0 => break,
                                        10 => {
                                            new_offset = i + 1;
                                            break;
                                        }
                                        _ => (),
                                    }
                                }
                                self.offset = new_offset;
                            }
                            _ => match key_event.character {
                                '\0' => (),
                                _ => {
                                    window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                    self.string = self.string[0 .. self.offset].to_string() +
                                                  &key_event.character.to_string() +
                                                  &self.string[self.offset .. self.string.len()];
                                    self.offset += 1;
                                }
                            },
                        }

                        self.draw_content(&mut window);
                    }
                }
                _ => (),
            }
        }
    }
}

pub fn main() {
    match args().get(1) {
        Option::Some(arg) => Editor::new().main(&arg),
        Option::None => Editor::new().main("none://"),
    }
}
<commit_msg>Formatize more `&str.to_string` concats<commit_after>use redox::*;

pub struct Editor {
    url: String,
    file: Option<File>,
    string: String,
    offset: usize,
    scroll_x: isize,
    scroll_y: isize,
}

impl Editor {
    #[inline(never)]
    pub fn new() -> Self {
        Editor {
            url: String::new(),
            file: Option::None,
            string: String::new(),
            offset: 0,
            scroll_x: 0,
            scroll_y: 0,
        }
    }

    fn reload(&mut self, window: &mut Window) {
        window.set_title(&format!("{}{}{}","Editor (", &self.url, ")"));
        self.offset = 0;
        self.scroll_x = 0;
        self.scroll_y = 0;

        match self.file {
            Option::Some(ref mut file) => {
                file.seek(Seek::Start(0));
                let mut vec: Vec<u8> = Vec::new();
                file.read_to_end(&mut vec);
                self.string = unsafe { String::from_utf8_unchecked(vec) };
            }
            Option::None => self.string = String::new(),
        }
    }

    fn save(&mut self, window: &mut Window) {
        match self.file {
            Option::Some(ref mut file) => {
                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Saved"));
                file.seek(Seek::Start(0));
                file.write(&self.string.as_bytes());
                file.sync();
            }
            Option::None => {
                //TODO: Ask for file to save to
                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") No Open File"));
            }
        }
    }

    fn draw_content(&mut self, window: &mut Window) {
        let mut redraw = false;

        {
            window.set([0, 0, 0, 196]);

            let scroll_x = self.scroll_x;
            let scroll_y = self.scroll_y;

            let mut offset = 0;

            let mut col = -scroll_x;
            let cols = window.width() as isize / 8;

            let mut row = -scroll_y;
            let rows = window.height() as isize / 16;

            for c in self.string.chars() {
                if offset == self.offset {
                    if col >= 0 && col < cols && row >= 0 && row < rows {
                        window.char(8 * col, 16 * row, '_', [128, 128, 128, 255]);
                    } else {
                        if col < 0 { //Too far to the left
                            self.scroll_x += col;
                        } else if col >= cols { //Too far to the right
                            self.scroll_x += cols - col + 1;
                        }
                        if row < 0 { //Too far up
                            self.scroll_y += row;
                        } else if row >= rows { //Too far down
                            self.scroll_y += rows - row + 1;
                        }

                        redraw = true;
                    }
                }

                if c == '\n' {
                    col = -scroll_x;
                    row += 1;
                } else if c == '\t' {
                    col += 8 - col % 8;
                } else {
                    if col >= 0 && col < cols && row >= 0 && row < rows {
                        window.char(8 * col, 16 * row, c, [255, 255, 255, 255]);
                    }
                    col += 1;
                }

                offset += 1;
            }

            if offset == self.offset {
                if col >= 0 && col < cols && row >= 0 && row < rows {
                    window.char(8 * col, 16 * row, '_', [128, 128, 128, 255]);
                } else {
                    if col < 0 { //Too far to the left
                        self.scroll_x += col;
                    } else if col >= cols { //Too far to the right
                        self.scroll_x += cols - col + 1;
                    }
                    if row < 0 { //Too far up
                        self.scroll_y += row;
                    } else if row >= rows { //Too far down
                        self.scroll_y += rows - row + 1;
                    }

                    redraw = true;
                }
            }

            window.sync();
        }

        if redraw {
            self.draw_content(window);
        }
    }

    fn main(&mut self, url: &str) {
        let mut window = Window::new((rand() % 400 + 50) as isize,
                                     (rand() % 300 + 50) as isize,
                                     576,
                                     400,
                                      "Editor (Loading)");

        self.url = url.to_string();
        self.file = Option::Some(File::open(&self.url));

        self.reload(&mut window);
        self.draw_content(&mut window);

        while let Option::Some(event) = window.poll() {
            match event.to_option() {
                EventOption::Key(key_event) => {
                    if key_event.pressed {
                        match key_event.scancode {
                            K_ESC => break,
                            K_BKSP => if self.offset > 0 {
                                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                self.string = format!("{}{}",
                                                      &self.string[0 .. self.offset - 1],
                                                      &self.string[self.offset .. self.string.len()]);
                                self.offset -= 1;
                            },
                            K_DEL => if self.offset < self.string.len() {
                                window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                self.string = format!("{}{}",
                                                      &self.string[0 .. self.offset],
                                                      &self.string[self.offset + 1 .. self.string.len() - 1]);
                            },
                            K_F5 => self.reload(&mut window),
                            K_F6 => self.save(&mut window),
                            K_HOME => self.offset = 0,
                            K_UP => {
                                let mut new_offset = 0;
                                for i in 2..self.offset {
                                    match self.string.as_bytes()[self.offset - i] {
                                        0 => break,
                                        10 => {
                                            new_offset = self.offset - i + 1;
                                            break;
                                        }
                                        _ => (),
                                    }
                                }
                                self.offset = new_offset;
                            }
                            K_LEFT => if self.offset > 0 {
                                self.offset -= 1;
                            },
                            K_RIGHT => if self.offset < self.string.len() {
                                self.offset += 1;
                            },
                            K_END => self.offset = self.string.len(),
                            K_DOWN => {
                                let mut new_offset = self.string.len();
                                for i in self.offset..self.string.len() {
                                    match self.string.as_bytes()[i] {
                                        0 => break,
                                        10 => {
                                            new_offset = i + 1;
                                            break;
                                        }
                                        _ => (),
                                    }
                                }
                                self.offset = new_offset;
                            }
                            _ => match key_event.character {
                                '\0' => (),
                                _ => {
                                    window.set_title(&format!("{}{}{}","Editor (", &self.url, ") Changed"));
                                    self.string = format!("{}{}{}",
                                                          &self.string[0 .. self.offset],
                                                          key_event.character,
                                                          &self.string[self.offset .. self.string.len()]);
                                    self.offset += 1;
                                }
                            },
                        }

                        self.draw_content(&mut window);
                    }
                }
                _ => (),
            }
        }
    }
}

pub fn main() {
    match args().get(1) {
        Option::Some(arg) => Editor::new().main(&arg),
        Option::None => Editor::new().main("none://"),
    }
}
<|endoftext|>