<commit_before>use std::fs::File;
use std::env;
use std::io::BufReader;
use std::io::BufRead;
use std::io::Write;
use std::collections::HashMap;
use std::collections::BTreeMap;
use std::collections::BTreeSet;

extern crate tools;
use tools::find_source_file;
use tools::analysis::{read_analysis, read_target, AnalysisKind};
use tools::config;

extern crate rustc_serialize;
use rustc_serialize::json::{Json, ToJson};

#[derive(Debug, RustcEncodable, RustcDecodable)]
struct SearchResult {
    lineno: u32,
    bounds: (u32, u32),
    line: String,
    context: String,
    contextsym: String,
}

impl ToJson for SearchResult {
    fn to_json(&self) -> Json {
        let (st, en) = self.bounds;
        let bounds = vec![st, en];

        let mut obj = BTreeMap::new();
        obj.insert("lno".to_string(), self.lineno.to_json());
        obj.insert("bounds".to_string(), bounds.to_json());
        obj.insert("line".to_string(), self.line.to_json());
        obj.insert("context".to_string(), self.context.to_json());
        obj.insert("contextsym".to_string(), self.contextsym.to_json());
        Json::Object(obj)
    }
}

fn main() {
    let args: Vec<_> = env::args().collect();

    let cfg = config::load(&args[1], false);

    let tree_name = &args[2];
    let tree_config = cfg.trees.get(tree_name).unwrap();

    let filenames_file = &args[3];

    let output_file = format!("{}/crossref", tree_config.paths.index_path);
    let jump_file = format!("{}/jumps", tree_config.paths.index_path);
    let id_file = format!("{}/identifiers", tree_config.paths.index_path);

    let mut table = HashMap::new();
    let mut pretty_table = HashMap::new();
    let mut id_table = HashMap::new();
    let mut jumps = Vec::new();

    {
        let mut process_file = |path: &str| {
            print!("File {}\n", path);

            let analysis_fname = format!("{}/analysis/{}", tree_config.paths.index_path, path);
            let analysis = read_analysis(&analysis_fname, &read_target);

            let source_fname = find_source_file(path, &tree_config.paths.files_path, &tree_config.paths.objdir_path);
            let source_file = match File::open(source_fname) {
                Ok(f) => f,
                Err(_) => {
                    println!("Unable to open source file");
                    return;
                },
            };
            let reader = BufReader::new(&source_file);
            let mut lines = Vec::new();
            for line in reader.lines() {
                match line {
                    Ok(l) => lines.push(l),
                    Err(_) => lines.push("".to_string()),
                }
            }

            for datum in analysis {
                for piece in datum.data {
                    let t1 = table.entry(piece.sym.to_owned()).or_insert(BTreeMap::new());
                    let t2 = t1.entry(piece.kind).or_insert(BTreeMap::new());
                    let t3 = t2.entry(path.to_owned()).or_insert(Vec::new());
                    let lineno = (datum.loc.lineno - 1) as usize;
                    if lineno >= lines.len() {
                        print!("Bad line number in file {} (line {})\n", path, lineno);
                        return;
                    }
                    let line = lines[lineno].clone();
                    let line_cut = line.trim_right();
                    let len = line_cut.len();
                    let line_cut = line_cut.trim_left();
                    let offset = (len - line_cut.len()) as u32;
                    let mut buf = String::new();
                    let mut i = 0;
                    for c in line_cut.chars() {
                        buf.push(c);
                        i += 1;
                        if i > 100 {
                            break;
                        }
                    }
                    t3.push(SearchResult {
                        lineno: datum.loc.lineno,
                        bounds: (datum.loc.col_start - offset, datum.loc.col_end - offset),
                        line: buf,
                        context: piece.context,
                        contextsym: piece.contextsym,
                    });

                    pretty_table.insert(piece.sym.to_owned(), piece.pretty.to_owned());

                    let ch = piece.sym.chars().nth(0).unwrap();
                    if !(ch >= '0' && ch <= '9') && !piece.sym.contains(' ') {
                        let t1 = id_table.entry(piece.pretty.to_owned()).or_insert(BTreeSet::new());
                        t1.insert(piece.sym.to_owned());
                    }
                }
            }
        };

        let f = File::open(filenames_file).unwrap();
        let file = BufReader::new(&f);
        for line in file.lines() {
            process_file(&line.unwrap());
        }
    }

    let mut outputf = File::create(output_file).unwrap();

    for (id, id_data) in table {
        let mut kindmap = BTreeMap::new();
        for (kind, kind_data) in &id_data {
            let mut result = Vec::new();
            for (path, results) in kind_data {
                let mut obj = BTreeMap::new();
                obj.insert("path".to_string(), path.to_json());
                obj.insert("lines".to_string(), results.to_json());
                result.push(Json::Object(obj));
            }
            let kindstr = match *kind {
                AnalysisKind::Use => "Uses",
                AnalysisKind::Def => "Definitions",
                AnalysisKind::Assign => "Assignments",
                AnalysisKind::Decl => "Declarations",
                AnalysisKind::Idl => "IDL",
            };
            kindmap.insert(kindstr.to_string(), Json::Array(result));
        }
        let kindmap = Json::Object(kindmap);

        let _ = outputf.write_all(format!("{}\n{}\n", id, kindmap.to_string()).as_bytes());

        if id_data.contains_key(&AnalysisKind::Def) {
            let defs = id_data.get(&AnalysisKind::Def).unwrap();
            if defs.len() == 1 {
                for (path, results) in defs {
                    if results.len() == 1 {
                        let mut v = Vec::new();
                        v.push(id.to_json());
                        v.push(path.to_json());
                        v.push(results[0].lineno.to_json());
                        let pretty = pretty_table.get(&id).unwrap();
                        v.push(pretty.to_json());
                        jumps.push(Json::Array(v));
                    }
                }
            }
        }
    }

    let mut jumpf = File::create(jump_file).unwrap();
    for jump in jumps {
        let _ = jumpf.write_all((jump.to_string() + "\n").as_bytes());
    }

    let mut idf = File::create(id_file).unwrap();
    for (id, syms) in id_table {
        for sym in syms {
            let components = id.split("::").collect::<Vec<_>>();
            for i in 0..components.len() {
                let sub = &components[i..components.len()];
                let sub = sub.join("::");

                if !sub.is_empty() {
                    let line = format!("{} {}\n", sub, sym);
                    let _ = idf.write_all(line.as_bytes());
                }
            }
        }
    }
}
<commit_msg>Bug 1298626 - SharedScriptData not indexed semantically<commit_after>use std::fs::File;
use std::env;
use std::io::BufReader;
use std::io::BufRead;
use std::io::Write;
use std::collections::HashMap;
use std::collections::BTreeMap;
use std::collections::BTreeSet;

extern crate tools;
use tools::find_source_file;
use tools::analysis::{read_analysis, read_target, AnalysisKind};
use tools::config;

extern crate rustc_serialize;
use rustc_serialize::json::{Json, ToJson};

#[derive(Debug, RustcEncodable, RustcDecodable)]
struct SearchResult {
    lineno: u32,
    bounds: (u32, u32),
    line: String,
    context: String,
    contextsym: String,
}

impl ToJson for SearchResult {
    fn to_json(&self) -> Json {
        let (st, en) = self.bounds;
        let bounds = vec![st, en];

        let mut obj = BTreeMap::new();
        obj.insert("lno".to_string(), self.lineno.to_json());
        obj.insert("bounds".to_string(), bounds.to_json());
        obj.insert("line".to_string(), self.line.to_json());
        obj.insert("context".to_string(), self.context.to_json());
        obj.insert("contextsym".to_string(), self.contextsym.to_json());
        Json::Object(obj)
    }
}

fn split_scopes(id: &str) -> Vec<String> {
    let mut result = Vec::new();
    let mut start = 0;
    let mut argument_nesting = 0;
    for (index, m) in id.match_indices(|c| c == ':' || c == '<' || c == '>') {
        if m == ":" && argument_nesting == 0 {
            if start != index {
                result.push(id[start .. index].to_owned());
                start = index + 1;
            } else {
                start = index + 1;
            }
        } else if m == "<" {
            argument_nesting += 1;
        } else if m == ">" {
            argument_nesting -= 1;
        }
    }
    result.push(id[start ..].to_owned());
    return result;
}

fn main() {
    let args: Vec<_> = env::args().collect();

    let cfg = config::load(&args[1], false);

    let tree_name = &args[2];
    let tree_config = cfg.trees.get(tree_name).unwrap();

    let filenames_file = &args[3];

    let output_file = format!("{}/crossref", tree_config.paths.index_path);
    let jump_file = format!("{}/jumps", tree_config.paths.index_path);
    let id_file = format!("{}/identifiers", tree_config.paths.index_path);

    let mut table = HashMap::new();
    let mut pretty_table = HashMap::new();
    let mut id_table = HashMap::new();
    let mut jumps = Vec::new();

    {
        let mut process_file = |path: &str| {
            print!("File {}\n", path);

            let analysis_fname = format!("{}/analysis/{}", tree_config.paths.index_path, path);
            let analysis = read_analysis(&analysis_fname, &read_target);

            let source_fname = find_source_file(path, &tree_config.paths.files_path, &tree_config.paths.objdir_path);
            let source_file = match File::open(source_fname) {
                Ok(f) => f,
                Err(_) => {
                    println!("Unable to open source file");
                    return;
                },
            };
            let reader = BufReader::new(&source_file);
            let mut lines = Vec::new();
            for line in reader.lines() {
                match line {
                    Ok(l) => lines.push(l),
                    Err(_) => lines.push("".to_string()),
                }
            }

            for datum in analysis {
                for piece in datum.data {
                    let t1 = table.entry(piece.sym.to_owned()).or_insert(BTreeMap::new());
                    let t2 = t1.entry(piece.kind).or_insert(BTreeMap::new());
                    let t3 = t2.entry(path.to_owned()).or_insert(Vec::new());
                    let lineno = (datum.loc.lineno - 1) as usize;
                    if lineno >= lines.len() {
                        print!("Bad line number in file {} (line {})\n", path, lineno);
                        return;
                    }
                    let line = lines[lineno].clone();
                    let line_cut = line.trim_right();
                    let len = line_cut.len();
                    let line_cut = line_cut.trim_left();
                    let offset = (len - line_cut.len()) as u32;
                    let mut buf = String::new();
                    let mut i = 0;
                    for c in line_cut.chars() {
                        buf.push(c);
                        i += 1;
                        if i > 100 {
                            break;
                        }
                    }
                    t3.push(SearchResult {
                        lineno: datum.loc.lineno,
                        bounds: (datum.loc.col_start - offset, datum.loc.col_end - offset),
                        line: buf,
                        context: piece.context,
                        contextsym: piece.contextsym,
                    });

                    pretty_table.insert(piece.sym.to_owned(), piece.pretty.to_owned());

                    let ch = piece.sym.chars().nth(0).unwrap();
                    if !(ch >= '0' && ch <= '9') && !piece.sym.contains(' ') {
                        let t1 = id_table.entry(piece.pretty.to_owned()).or_insert(BTreeSet::new());
                        t1.insert(piece.sym.to_owned());
                    }
                }
            }
        };

        let f = File::open(filenames_file).unwrap();
        let file = BufReader::new(&f);
        for line in file.lines() {
            process_file(&line.unwrap());
        }
    }

    let mut outputf = File::create(output_file).unwrap();

    for (id, id_data) in table {
        let mut kindmap = BTreeMap::new();
        for (kind, kind_data) in &id_data {
            let mut result = Vec::new();
            for (path, results) in kind_data {
                let mut obj = BTreeMap::new();
                obj.insert("path".to_string(), path.to_json());
                obj.insert("lines".to_string(), results.to_json());
                result.push(Json::Object(obj));
            }
            let kindstr = match *kind {
                AnalysisKind::Use => "Uses",
                AnalysisKind::Def => "Definitions",
                AnalysisKind::Assign => "Assignments",
                AnalysisKind::Decl => "Declarations",
                AnalysisKind::Idl => "IDL",
            };
            kindmap.insert(kindstr.to_string(), Json::Array(result));
        }
        let kindmap = Json::Object(kindmap);

        let _ = outputf.write_all(format!("{}\n{}\n", id, kindmap.to_string()).as_bytes());

        if id_data.contains_key(&AnalysisKind::Def) {
            let defs = id_data.get(&AnalysisKind::Def).unwrap();
            if defs.len() == 1 {
                for (path, results) in defs {
                    if results.len() == 1 {
                        let mut v = Vec::new();
                        v.push(id.to_json());
                        v.push(path.to_json());
                        v.push(results[0].lineno.to_json());
                        let pretty = pretty_table.get(&id).unwrap();
                        v.push(pretty.to_json());
                        jumps.push(Json::Array(v));
                    }
                }
            }
        }
    }

    let mut jumpf = File::create(jump_file).unwrap();
    for jump in jumps {
        let _ = jumpf.write_all((jump.to_string() + "\n").as_bytes());
    }

    let mut idf = File::create(id_file).unwrap();
    for (id, syms) in id_table {
        for sym in syms {
            let components = split_scopes(&id);
            for i in 0..components.len() {
                let sub = &components[i..components.len()];
                let sub = sub.join("::");

                if !sub.is_empty() {
                    let line = format!("{} {}\n", sub, sym);
                    let _ = idf.write_all(line.as_bytes());
                }
            }
        }
    }
}
<|endoftext|>


<commit_before>#![feature(proc_macro_hygiene, decl_macro)]

#[macro_use]
extern crate rocket;

#[macro_use]
extern crate rocket_contrib;

// #[macro_use]
extern crate diesel;

mod schema;
// mod models;

use rocket_contrib::databases::diesel::PgConnection;

#[get("/")]
fn index() -> &'static str {
    "Hello, from Rust!"
}

#[database("rustydb")]
pub struct RustyDbConn(PgConnection);

fn main() {
    rocket::ignite()
        .attach(RustyDbConn::fairing())
        .mount("/api", routes![index])
        .launch();
}
<commit_msg>Add a sample (albeit unused) request guard parameter to the root api call.<commit_after>#![feature(proc_macro_hygiene, decl_macro)]

#[macro_use]
extern crate rocket;

#[macro_use]
extern crate rocket_contrib;

// #[macro_use]
extern crate diesel;

mod schema;
// mod models;

use rocket_contrib::databases::diesel::PgConnection;

#[get("/")]
fn index(_db_conn: RustyDbConn) -> &'static str {
    // Rocket uses the RustyDbConn request guard to provide us with a database
    // connection from a managed pool.
    "Hello, from Rust! (with a database connection!)"
}

#[database("rustydb")]
pub struct RustyDbConn(PgConnection);

fn main() {
    rocket::ignite()
        .attach(RustyDbConn::fairing())
        .mount("/api", routes![index])
        .launch();
}
<|endoftext|>


<commit_before>use std::io::MemWriter;
use std::str::from_utf8;

use parser::ArgumentParser;

#[cfg(test)]
pub fn check_ok(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Ok(()) => return,
        Err(x) => fail!(
            from_utf8(stderr.unwrap()).unwrap() +
            format!("Expected ok, but found Exit({})", x)),
    }
}

#[cfg(test)]
pub fn check_exit(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Err(0) => return,
        Err(x) => fail!(format!("Expected code {} got {}", 0, x)),
        Ok(()) => fail!(format!("Expected failure, got success")),
    }
}

#[cfg(test)]
pub fn check_err(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Err(2) => return,
        Err(x) => fail!(format!("Expected code {} got {}", 2, x)),
        Ok(()) => fail!(format!("Expected failure, got success")),
    }
}

#[test]
fn test_no_arg() {
    let ap = ArgumentParser::new();
    check_ok(&ap, ~[~"./argparse_test"]);
    check_err(&ap, ~[~"./argparse_test", ~"a"]);
    check_err(&ap, ~[~"./argparse_test", ~"-a"]);
    check_ok(&ap, ~[~"./argparse_test", ~"--an-option"]);
}

<commit_msg>Fix mistakenly broken test<commit_after>use std::io::MemWriter;
use std::str::from_utf8;

use parser::ArgumentParser;

#[cfg(test)]
pub fn check_ok(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Ok(()) => return,
        Err(x) => fail!(
            from_utf8(stderr.unwrap()).unwrap() +
            format!("Expected ok, but found Exit({})", x)),
    }
}

#[cfg(test)]
pub fn check_exit(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Err(0) => return,
        Err(x) => fail!(format!("Expected code {} got {}", 0, x)),
        Ok(()) => fail!(format!("Expected failure, got success")),
    }
}

#[cfg(test)]
pub fn check_err(ap: &ArgumentParser, args: ~[~str]) {
    let mut stdout = MemWriter::new();
    let mut stderr = MemWriter::new();
    let res = ap.parse(args, &mut stdout, &mut stderr);
    match res {
        Err(2) => return,
        Err(x) => fail!(format!("Expected code {} got {}", 2, x)),
        Ok(()) => fail!(format!("Expected failure, got success")),
    }
}

#[test]
fn test_no_arg() {
    let ap = ArgumentParser::new();
    check_ok(&ap, ~[~"./argparse_test"]);
    check_err(&ap, ~[~"./argparse_test", ~"a"]);
    check_err(&ap, ~[~"./argparse_test", ~"-a"]);
    check_err(&ap, ~[~"./argparse_test", ~"--an-option"]);
}

<|endoftext|>


<commit_before>use std::{collections::HashSet, fmt::Write, path::Path, time::Instant};

use ra_db::SourceDatabase;
use ra_hir::{Crate, HasSource, ImplItem, ModuleDef, Ty};
use ra_syntax::AstNode;

use crate::Result;

pub fn run(verbose: bool, memory_usage: bool, path: &Path, only: Option<&str>) -> Result<()> {
    let db_load_time = Instant::now();
    let (mut host, roots) = ra_batch::load_cargo(path)?;
    let db = host.raw_database();
    println!("Database loaded, {} roots, {:?}", roots.len(), db_load_time.elapsed());
    let analysis_time = Instant::now();
    let mut num_crates = 0;
    let mut visited_modules = HashSet::new();
    let mut visit_queue = Vec::new();
    for (source_root_id, project_root) in roots {
        if project_root.is_member() {
            for krate in Crate::source_root_crates(db, source_root_id) {
                num_crates += 1;
                let module =
                    krate.root_module(db).expect("crate in source root without root module");
                visit_queue.push(module);
            }
        }
    }
    println!("Crates in this dir: {}", num_crates);
    let mut num_decls = 0;
    let mut funcs = Vec::new();
    while let Some(module) = visit_queue.pop() {
        if visited_modules.insert(module) {
            visit_queue.extend(module.children(db));

            for decl in module.declarations(db) {
                num_decls += 1;
                if let ModuleDef::Function(f) = decl {
                    funcs.push(f);
                }
            }

            for impl_block in module.impl_blocks(db) {
                for item in impl_block.items(db) {
                    num_decls += 1;
                    if let ImplItem::Method(f) = item {
                        funcs.push(f);
                    }
                }
            }
        }
    }
    println!("Total modules found: {}", visited_modules.len());
    println!("Total declarations: {}", num_decls);
    println!("Total functions: {}", funcs.len());
    println!("Parsing: {:?}, {}", analysis_time.elapsed(), ra_prof::memory_usage());

    let inference_time = Instant::now();
    let bar = indicatif::ProgressBar::with_draw_target(
        funcs.len() as u64,
        indicatif::ProgressDrawTarget::stderr_nohz(),
    );
    bar.set_style(
        indicatif::ProgressStyle::default_bar().template("{wide_bar} {pos}/{len}\n{msg}"),
    );
    bar.tick();
    let mut num_exprs = 0;
    let mut num_exprs_unknown = 0;
    let mut num_exprs_partially_unknown = 0;
    for f in funcs {
        let name = f.name(db);
        let mut msg = format!("processing: {}", name);
        if verbose {
            let src = f.source(db);
            let original_file = src.file_id.original_file(db);
            let path = db.file_relative_path(original_file);
            let syntax_range = src.ast.syntax().text_range();
            write!(msg, " ({:?} {})", path, syntax_range).unwrap();
        }
        bar.set_message(&msg);
        if let Some(only_name) = only {
            if name.to_string() != only_name {
                continue;
            }
        }
        let body = f.body(db);
        let inference_result = f.infer(db);
        for (expr_id, _) in body.exprs() {
            let ty = &inference_result[expr_id];
            num_exprs += 1;
            if let Ty::Unknown = ty {
                num_exprs_unknown += 1;
            } else {
                let mut is_partially_unknown = false;
                ty.walk(&mut |ty| {
                    if let Ty::Unknown = ty {
                        is_partially_unknown = true;
                    }
                });
                if is_partially_unknown {
                    num_exprs_partially_unknown += 1;
                }
            }
        }
        bar.inc(1);
    }
    bar.finish_and_clear();
    println!("Total expressions: {}", num_exprs);
    println!(
        "Expressions of unknown type: {} ({}%)",
        num_exprs_unknown,
        (num_exprs_unknown * 100 / num_exprs)
    );
    println!(
        "Expressions of partially unknown type: {} ({}%)",
        num_exprs_partially_unknown,
        (num_exprs_partially_unknown * 100 / num_exprs)
    );
    println!("Inference: {:?}, {}", inference_time.elapsed(), ra_prof::memory_usage());
    println!("Total: {:?}, {}", analysis_time.elapsed(), ra_prof::memory_usage());

    if memory_usage {
        drop(db);
        for (name, bytes) in host.per_query_memory_usage() {
            println!("{:>8} {}", bytes, name)
        }
        let before = ra_prof::memory_usage();
        drop(host);
        println!("leftover: {}", before.allocated - ra_prof::memory_usage().allocated)
    }

    Ok(())
}
<commit_msg>Update crates/ra_cli/src/analysis_stats.rs<commit_after>use std::{collections::HashSet, fmt::Write, path::Path, time::Instant};

use ra_db::SourceDatabase;
use ra_hir::{Crate, HasSource, ImplItem, ModuleDef, Ty};
use ra_syntax::AstNode;

use crate::Result;

pub fn run(verbose: bool, memory_usage: bool, path: &Path, only: Option<&str>) -> Result<()> {
    let db_load_time = Instant::now();
    let (mut host, roots) = ra_batch::load_cargo(path)?;
    let db = host.raw_database();
    println!("Database loaded, {} roots, {:?}", roots.len(), db_load_time.elapsed());
    let analysis_time = Instant::now();
    let mut num_crates = 0;
    let mut visited_modules = HashSet::new();
    let mut visit_queue = Vec::new();
    for (source_root_id, project_root) in roots {
        if project_root.is_member() {
            for krate in Crate::source_root_crates(db, source_root_id) {
                num_crates += 1;
                let module =
                    krate.root_module(db).expect("crate in source root without root module");
                visit_queue.push(module);
            }
        }
    }
    println!("Crates in this dir: {}", num_crates);
    let mut num_decls = 0;
    let mut funcs = Vec::new();
    while let Some(module) = visit_queue.pop() {
        if visited_modules.insert(module) {
            visit_queue.extend(module.children(db));

            for decl in module.declarations(db) {
                num_decls += 1;
                if let ModuleDef::Function(f) = decl {
                    funcs.push(f);
                }
            }

            for impl_block in module.impl_blocks(db) {
                for item in impl_block.items(db) {
                    num_decls += 1;
                    if let ImplItem::Method(f) = item {
                        funcs.push(f);
                    }
                }
            }
        }
    }
    println!("Total modules found: {}", visited_modules.len());
    println!("Total declarations: {}", num_decls);
    println!("Total functions: {}", funcs.len());
    println!("Item Collection: {:?}, {}", analysis_time.elapsed(), ra_prof::memory_usage());

    let inference_time = Instant::now();
    let bar = indicatif::ProgressBar::with_draw_target(
        funcs.len() as u64,
        indicatif::ProgressDrawTarget::stderr_nohz(),
    );
    bar.set_style(
        indicatif::ProgressStyle::default_bar().template("{wide_bar} {pos}/{len}\n{msg}"),
    );
    bar.tick();
    let mut num_exprs = 0;
    let mut num_exprs_unknown = 0;
    let mut num_exprs_partially_unknown = 0;
    for f in funcs {
        let name = f.name(db);
        let mut msg = format!("processing: {}", name);
        if verbose {
            let src = f.source(db);
            let original_file = src.file_id.original_file(db);
            let path = db.file_relative_path(original_file);
            let syntax_range = src.ast.syntax().text_range();
            write!(msg, " ({:?} {})", path, syntax_range).unwrap();
        }
        bar.set_message(&msg);
        if let Some(only_name) = only {
            if name.to_string() != only_name {
                continue;
            }
        }
        let body = f.body(db);
        let inference_result = f.infer(db);
        for (expr_id, _) in body.exprs() {
            let ty = &inference_result[expr_id];
            num_exprs += 1;
            if let Ty::Unknown = ty {
                num_exprs_unknown += 1;
            } else {
                let mut is_partially_unknown = false;
                ty.walk(&mut |ty| {
                    if let Ty::Unknown = ty {
                        is_partially_unknown = true;
                    }
                });
                if is_partially_unknown {
                    num_exprs_partially_unknown += 1;
                }
            }
        }
        bar.inc(1);
    }
    bar.finish_and_clear();
    println!("Total expressions: {}", num_exprs);
    println!(
        "Expressions of unknown type: {} ({}%)",
        num_exprs_unknown,
        (num_exprs_unknown * 100 / num_exprs)
    );
    println!(
        "Expressions of partially unknown type: {} ({}%)",
        num_exprs_partially_unknown,
        (num_exprs_partially_unknown * 100 / num_exprs)
    );
    println!("Inference: {:?}, {}", inference_time.elapsed(), ra_prof::memory_usage());
    println!("Total: {:?}, {}", analysis_time.elapsed(), ra_prof::memory_usage());

    if memory_usage {
        drop(db);
        for (name, bytes) in host.per_query_memory_usage() {
            println!("{:>8} {}", bytes, name)
        }
        let before = ra_prof::memory_usage();
        drop(host);
        println!("leftover: {}", before.allocated - ra_prof::memory_usage().allocated)
    }

    Ok(())
}
<|endoftext|>


<commit_before>use std::env;
use std::io::prelude::*;
use std::fs::File;
use std::path::Path;

extern crate toml;

#[macro_use]
extern crate serde_derive;

// error in rust compiler.  Bugfix requested in Sept. 2017
// these are used, but the compiler is not seeing it for
// some reason
#[allow(unused_imports)]
#[macro_use]
extern crate serde_json;
// error in rust compiler.  Bugfix has been submitted in Sept. 2017
#[allow(unused_imports)]
#[macro_use]
extern crate serde;

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Tomlfile {
    contents: Contents,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Metadata {
    deb: Deb,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Deb {
    revision: Option<String>,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Package {
    name: String,
    version: Option<String>,
    metadata: Metadata,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Contents {
    package: Package,
    dependencies: Option<toml::Value>,
}

fn main() {
    let target = env::var("TARGET").unwrap();
    println!("target={}", target);

    if let Ok(_mode) = env::var("LIBINDY_STATIC") {
        let libindy_lib_path = env::var("LIBINDY_DIR").unwrap();
        println!("cargo:rustc-link-search=native={}",libindy_lib_path);
        println!("cargo:rustc-link-lib=static=indy");
    }else if target.contains("aarch64-linux-android") || target.contains("armv7-linux-androideabi") ||
        target.contains("arm-linux-androideabi") || target.contains("i686-linux-android") ||
        target.contains("x86_64-linux-android") || target.contains("aarch64-apple-ios") ||
        target.contains("armv7-apple-ios") || target.contains("armv7s-apple-ios") ||
        target.contains("i386-apple-ios") || target.contains("x86_64-apple-ios") {

        let libindy_lib_path = match env::var("LIBINDY_DIR"){
            Ok(val) => val,
            Err(..) => panic!("Missing required environment variable LIBINDY_DIR")
        };

        let openssl = match env::var("OPENSSL_LIB_DIR") {
            Ok(val) => val,
            Err(..) => match env::var("OPENSSL_DIR") {
                Ok(dir) => Path::new(&dir[..]).join("/lib").to_string_lossy().into_owned(),
                Err(..) => panic!("Missing required environment variables OPENSSL_DIR or OPENSSL_LIB_DIR")
            }
        };

        println!("cargo:rustc-link-search=native={}",libindy_lib_path);
        println!("cargo:rustc-link-lib=static=indy");
        println!("cargo:rustc-link-search=native={}", openssl);
        println!("cargo:rustc-link-lib=static=crypto");
        println!("cargo:rustc-link-lib=static=ssl");
        if cfg!(feature = "nullpay") {
            let libnullpay_lib_path = match env::var("LIBNULLPAY_DIR") {
                Ok(val) => val,
                Err(..) => panic!("Missing required environment variable LIBNULLPAY_DIR")
            };

            println!("cargo:rustc-link-search=native={}",libnullpay_lib_path);
            println!("cargo:rustc-link-lib=static=nullpay");
        } else if cfg!(feature = "sovtoken") {
            let libsovtoken_lib_path = match env::var("LIBSOVTOKEN_DIR") {
                Ok(val) => val,
                Err(..) => panic!("Missing required environment variable LIBSOVTOKEN_DIR")
            };

            println!("cargo:rustc-link-search=native={}",libsovtoken_lib_path);
            println!("cargo:rustc-link-lib=static=sovtoken");
        }
    }else if target.contains("darwin"){
        //OSX specific logic
        println!("cargo:rustc-link-lib=indy");
        //OSX does not allow 3rd party libs to be installed in /usr/lib. Instead install it in /usr/local/lib
        println!("cargo:rustc-link-search=native=/usr/local/lib");
        if cfg!(feature = "nullpay") {
          println!("cargo:rustc-link-lib=nullpay");
        } else if cfg!(feature = "sovtoken") {
            println!("cargo:rustc-link-lib=sovtoken");
        }
    }else if target.contains("-linux-"){
        //Linux specific logic
        println!("cargo:rustc-link-lib=indy");
        println!("cargo:rustc-link-search=native=/usr/lib");
        if cfg!(feature = "nullpay") {
          println!("cargo:rustc-link-lib=nullpay");
        } else if cfg!(feature = "sovtoken") {
            println!("cargo:rustc-link-lib=sovtoken");
        }
    }

    match env::var("CARGO_FEATURE_CI") {
        Ok(_) => {
            println!("injecting version information");
            // Leaving as unwrap, this is in the build script.
            let revision = get_revision().unwrap();
            write_variables(&revision);
        },
        Err(_) => {println!("NOT injecting version information"); },
    };
}

// Writes to the file 'src/utils/version_constants.rs' for use
// in outputing the version dynamically.
fn write_variables(revision:&str) {
    let out_dir = "src/utils/";
    let dest_path = Path::new(&out_dir).join("version_constants.rs");
    let mut f = File::create(&dest_path).unwrap();
    let s = format!("pub const VERSION: &'static str = env!(\"CARGO_PKG_VERSION\");\npub const REVISION: &'static str = \"{}\";\n", revision);
    if let Err(e) = f.write_all(s.as_bytes()) {
       panic!("Error creating version_constants.rs: {}", e);
    };

}

// Gets the revision number from the Cargo.toml file.
pub fn get_revision() -> Option<String> {
    let dir = match  env::var("CARGO_MANIFEST_DIR"){
        Ok(d) => d,
        Err(_) => panic!("Couldn't Manifest Directory"),
    };
    let filename = "Cargo.toml";
    let p = format!("{}/{}",dir,filename);
    let mut input = String::new();
    File::open(p).and_then(|mut f| {
        f.read_to_string(&mut input)}).unwrap();
    let tomlfile:Contents = toml::from_str(&input).unwrap();
    let revision:String = match tomlfile.package.metadata.deb.revision {
        Some(v) => v,
        None => String::from(""),
    };
    Some(format!("+{}", revision))
}

<commit_msg>Removing the libindy requirement because libsovtoken already has all of those .o files in it.<commit_after>use std::env;
use std::io::prelude::*;
use std::fs::File;
use std::path::Path;

extern crate toml;

#[macro_use]
extern crate serde_derive;

// error in rust compiler.  Bugfix requested in Sept. 2017
// these are used, but the compiler is not seeing it for
// some reason
#[allow(unused_imports)]
#[macro_use]
extern crate serde_json;
// error in rust compiler.  Bugfix has been submitted in Sept. 2017
#[allow(unused_imports)]
#[macro_use]
extern crate serde;

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Tomlfile {
    contents: Contents,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Metadata {
    deb: Deb,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Deb {
    revision: Option<String>,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Package {
    name: String,
    version: Option<String>,
    metadata: Metadata,
}

// used in formatting the Cargo.toml file
#[derive(Deserialize, Debug)]
struct Contents {
    package: Package,
    dependencies: Option<toml::Value>,
}

fn main() {
    let target = env::var("TARGET").unwrap();
    println!("target={}", target);

    if let Ok(_mode) = env::var("LIBINDY_STATIC") {
        let libindy_lib_path = env::var("LIBINDY_DIR").unwrap();
        println!("cargo:rustc-link-search=native={}",libindy_lib_path);
        println!("cargo:rustc-link-lib=static=indy");
    }else if target.contains("aarch64-linux-android") || target.contains("armv7-linux-androideabi") ||
        target.contains("arm-linux-androideabi") || target.contains("i686-linux-android") ||
        target.contains("x86_64-linux-android") || target.contains("aarch64-apple-ios") ||
        target.contains("armv7-apple-ios") || target.contains("armv7s-apple-ios") ||
        target.contains("i386-apple-ios") || target.contains("x86_64-apple-ios") {

        // let libindy_lib_path = match env::var("LIBINDY_DIR"){
        //     Ok(val) => val,
        //     Err(..) => panic!("Missing required environment variable LIBINDY_DIR")
        // };

        let openssl = match env::var("OPENSSL_LIB_DIR") {
            Ok(val) => val,
            Err(..) => match env::var("OPENSSL_DIR") {
                Ok(dir) => Path::new(&dir[..]).join("/lib").to_string_lossy().into_owned(),
                Err(..) => panic!("Missing required environment variables OPENSSL_DIR or OPENSSL_LIB_DIR")
            }
        };

        //println!("cargo:rustc-link-search=native={}",libindy_lib_path);
        //println!("cargo:rustc-link-lib=static=indy");
        println!("cargo:rustc-link-search=native={}", openssl);
        println!("cargo:rustc-link-lib=static=crypto");
        println!("cargo:rustc-link-lib=static=ssl");
        if cfg!(feature = "nullpay") {
            let libnullpay_lib_path = match env::var("LIBNULLPAY_DIR") {
                Ok(val) => val,
                Err(..) => panic!("Missing required environment variable LIBNULLPAY_DIR")
            };

            println!("cargo:rustc-link-search=native={}",libnullpay_lib_path);
            println!("cargo:rustc-link-lib=static=nullpay");
        } else if cfg!(feature = "sovtoken") {
            let libsovtoken_lib_path = match env::var("LIBSOVTOKEN_DIR") {
                Ok(val) => val,
                Err(..) => panic!("Missing required environment variable LIBSOVTOKEN_DIR")
            };

            println!("cargo:rustc-link-search=native={}",libsovtoken_lib_path);
            println!("cargo:rustc-link-lib=static=sovtoken");
        }
    }else if target.contains("darwin"){
        //OSX specific logic
        println!("cargo:rustc-link-lib=indy");
        //OSX does not allow 3rd party libs to be installed in /usr/lib. Instead install it in /usr/local/lib
        println!("cargo:rustc-link-search=native=/usr/local/lib");
        if cfg!(feature = "nullpay") {
          println!("cargo:rustc-link-lib=nullpay");
        } else if cfg!(feature = "sovtoken") {
            println!("cargo:rustc-link-lib=sovtoken");
        }
    }else if target.contains("-linux-"){
        //Linux specific logic
        println!("cargo:rustc-link-lib=indy");
        println!("cargo:rustc-link-search=native=/usr/lib");
        if cfg!(feature = "nullpay") {
          println!("cargo:rustc-link-lib=nullpay");
        } else if cfg!(feature = "sovtoken") {
            println!("cargo:rustc-link-lib=sovtoken");
        }
    }

    match env::var("CARGO_FEATURE_CI") {
        Ok(_) => {
            println!("injecting version information");
            // Leaving as unwrap, this is in the build script.
            let revision = get_revision().unwrap();
            write_variables(&revision);
        },
        Err(_) => {println!("NOT injecting version information"); },
    };
}

// Writes to the file 'src/utils/version_constants.rs' for use
// in outputing the version dynamically.
fn write_variables(revision:&str) {
    let out_dir = "src/utils/";
    let dest_path = Path::new(&out_dir).join("version_constants.rs");
    let mut f = File::create(&dest_path).unwrap();
    let s = format!("pub const VERSION: &'static str = env!(\"CARGO_PKG_VERSION\");\npub const REVISION: &'static str = \"{}\";\n", revision);
    if let Err(e) = f.write_all(s.as_bytes()) {
       panic!("Error creating version_constants.rs: {}", e);
    };

}

// Gets the revision number from the Cargo.toml file.
pub fn get_revision() -> Option<String> {
    let dir = match  env::var("CARGO_MANIFEST_DIR"){
        Ok(d) => d,
        Err(_) => panic!("Couldn't Manifest Directory"),
    };
    let filename = "Cargo.toml";
    let p = format!("{}/{}",dir,filename);
    let mut input = String::new();
    File::open(p).and_then(|mut f| {
        f.read_to_string(&mut input)}).unwrap();
    let tomlfile:Contents = toml::from_str(&input).unwrap();
    let revision:String = match tomlfile.package.metadata.deb.revision {
        Some(v) => v,
        None => String::from(""),
    };
    Some(format!("+{}", revision))
}

<|endoftext|>


<commit_before>fn empty_array() -> [u16; 0] {
    []
}

fn mini_array() -> [u16; 1] {
    [42]
}

fn big_array() -> [u16; 5] {
    [5, 4, 3, 2, 1]
}

fn array_array() -> [[u8; 2]; 3] {
    [[5, 4], [3, 2], [1, 0]]
}

fn index_unsafe() -> i32 {
    let a = [0, 10, 20, 30];
    unsafe { *a.get_unchecked(2) }
}

fn index() -> i32 {
    let a = [0, 10, 20, 30];
    a[2]
}

fn array_repeat() -> [u8; 8] {
    [42; 8]
}

fn slice_index() -> u8 {
    let arr: &[_] = &[101, 102, 103, 104, 105, 106];
    arr[5]
}

fn eq() {
    const N: usize = 16;
    type Array = [u8; N];
    let array1: Array = [0; N];
    let array2: Array = [0; N];
    let array3: Array = [1; N];
    assert_eq!(array1, array2);
    assert_ne!(array1, array3);
}

fn debug() {
    let array = [0u8, 42, 13, 71];
    println!("{:?}", array);
}

fn main() {
    assert_eq!(empty_array(), []);
    assert_eq!(index_unsafe(), 20);
    assert_eq!(index(), 20);
    assert_eq!(slice_index(), 106);
    assert_eq!(big_array(), [5, 4, 3, 2, 1]);
    assert_eq!(array_array(), [[5, 4], [3, 2], [1, 0]]);
    assert_eq!(array_repeat(), [42; 8]);
    assert_eq!(mini_array(), [42]);
    eq();
    debug();
}
<commit_msg>test arrray try_from (interesting const generic usage)<commit_after>use std::convert::TryFrom;

fn empty_array() -> [u16; 0] {
    []
}

fn mini_array() -> [u16; 1] {
    [42]
}

fn big_array() -> [u16; 5] {
    [5, 4, 3, 2, 1]
}

fn array_array() -> [[u8; 2]; 3] {
    [[5, 4], [3, 2], [1, 0]]
}

fn index_unsafe() -> i32 {
    let a = [0, 10, 20, 30];
    unsafe { *a.get_unchecked(2) }
}

fn index() -> i32 {
    let a = [0, 10, 20, 30];
    a[2]
}

fn array_repeat() -> [u8; 8] {
    [42; 8]
}

fn slice_index() -> u8 {
    let arr: &[_] = &[101, 102, 103, 104, 105, 106];
    arr[5]
}

fn try_from() {
    const N: usize = 16;
    type Array = [u8; N];
    let array: Array = [0; N];
    let slice: &[u8] = &array[..];

    let result = <&Array>::try_from(slice);
    assert_eq!(&array, result.unwrap());
}

fn eq() {
    const N: usize = 16;
    type Array = [u8; N];
    let array1: Array = [0; N];
    let array2: Array = [0; N];
    let array3: Array = [1; N];
    assert_eq!(array1, array2);
    assert_ne!(array1, array3);
}

fn debug() {
    let array = [0u8, 42, 13, 71];
    println!("{:?}", array);
}

fn main() {
    assert_eq!(empty_array(), []);
    assert_eq!(index_unsafe(), 20);
    assert_eq!(index(), 20);
    assert_eq!(slice_index(), 106);
    assert_eq!(big_array(), [5, 4, 3, 2, 1]);
    assert_eq!(array_array(), [[5, 4], [3, 2], [1, 0]]);
    assert_eq!(array_repeat(), [42; 8]);
    assert_eq!(mini_array(), [42]);
    try_from();
    eq();
    debug();
}
<|endoftext|>


<commit_before>use std::ops::{Mul,Add,Sub};
use num::traits::{Zero,One,Float};

#[derive(PartialEq,Debug)]
pub struct Vec3<T> where T: Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    pub x: T,
    pub y: T,
    pub z: T,
}

impl <T> Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    pub fn new(xx: T, yy: T, zz: T) -> Vec3<T> {
        Vec3 { x: xx, y: yy, z: zz }
    }

    pub fn zero() -> Vec3<T> {
        Vec3::new(T::zero(), T::zero(), T::zero())
    }

    pub fn diagonal(xx: T) -> Vec3<T> {
        Vec3::new(xx, xx, xx)
    }

    pub fn dot(self, rhs: Vec3<T>) -> T {
         self.x * rhs.x + self.y * rhs.y + self.z * rhs.z
    }

    pub fn cross(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.y * rhs.z - self.z * rhs.y,
            self.z * rhs.x - self.x * rhs.z,
            self.x * rhs.y - self.y * rhs.x,
            )
    }
}

impl <T> Add<Vec3<T>> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn add(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.x + rhs.x,
            self.y + rhs.y,
            self.z + rhs.z,
            )
    }
}

impl <T> Sub<Vec3<T>> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn sub(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.x - rhs.x,
            self.y - rhs.y,
            self.z - rhs.z,
            )
    }
}

impl <T> Mul<T> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn mul(self, rhs: T) -> Vec3<T> {
        Vec3::new(
            self.x * rhs,
            self.y * rhs,
            self.z * rhs,
            )
    }
}

impl <T> Vec3<T> where T: Mul<T, Output=T> + One + Zero + Float + Clone + Copy {
    #[allow(non_snake_case)]
    pub fn sphericalToCartesian(theta: T, phi: T) -> Vec3<T> {
        Vec3::new(phi.cos() * theta.sin(), phi.sin() * theta.sin(), theta.cos())
    }

    pub fn length(& self) -> T {
        (self.x * self.x + self.y * self.y + self.z * self.z).sqrt()
    }

    pub fn normalize(&mut self) {
        let length: T = self.length();
        if length > T::zero() {
            let inverse_length = T::one() / length;

            self.x = self.x * inverse_length;
            self.y = self.y * inverse_length;
            self.z = self.z * inverse_length;
        }
    }
}

#[cfg(test)]
mod tests {
    use super::Vec3;

    #[test]
    fn should_be_created_with_constructor() {
        let v: Vec3<f64> = Vec3::new(0.0, 1.0, 2.0);

        assert_eq!(v, Vec3 { x: 0.0, y: 1.0, z: 2.0 });
    }

    #[test]
    fn should_initialize_to_zero_vector() {
        let v: Vec3<f64> = Vec3::zero();

        assert_eq!(v, Vec3::<f64>{ x: 0.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_initialize_to_diagonal_vector() {
        let v: Vec3<f64> = Vec3::diagonal(1.0);

        assert_eq!(v, Vec3::<f64>{ x: 1.0, y: 1.0, z: 1.0 });
    }

    #[test]
    fn should_know_dot_product() {
        let u: Vec3<f64> = Vec3::diagonal(1.0);
        let v: Vec3<f64> = Vec3::new(0.0, 1.0, 2.0);

        let dot_product: f64 = u.dot(v);

        assert_eq!(dot_product, 3.0);
    }

    #[test]
    fn should_know_its_length() {
        let v: Vec3<f64> = Vec3 { x: 0.0, y: 0.0, z: 0.0 };

        assert_eq!(v.length(), 0.0);
    }

    #[test]
    fn should_be_able_to_normalize() {
        let mut v: Vec3<f64> = Vec3::new(3.0, 0.0, 0.0);
        v.normalize();

        assert_eq!(v, Vec3 { x: 1.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_know_cross_product() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let product = v.cross(w);

        assert_eq!(product, Vec3 { x: 0.0, y: 0.0, z: 1.0 });
    }

    #[test]
    fn should_form_vector_sum() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let sum = v + w;

        assert_eq!(sum, Vec3 { x: 1.0, y: 1.0, z: 0.0 });
    }

    #[test]
    fn should_form_vector_difference() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let sum = v - w;

        assert_eq!(sum, Vec3 { x: 1.0, y: -1.0, z: 0.0 });
    }

    #[test]
    fn should_form_scalar_multiplication() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let c: f64 = 2.0;

        let scalar = v * c;

        assert_eq!(scalar, Vec3 { x: 2.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_know_how_to_convert_from_polar_coordinates() {
        let v: Vec3<f64> = Vec3::sphericalToCartesian(0.0, 0.0);

        assert_eq!(v, Vec3 { x: 0.0, y: 0.0, z: 1.0 });
    }
}
<commit_msg>Implement trigonometry<commit_after>use std::ops::{Mul,Add,Sub};
use num::traits::{Zero,One,Float};

#[derive(PartialEq,Debug)]
pub struct Vec3<T> where T: Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    pub x: T,
    pub y: T,
    pub z: T,
}

impl <T> Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    pub fn new(xx: T, yy: T, zz: T) -> Vec3<T> {
        Vec3 { x: xx, y: yy, z: zz }
    }

    pub fn zero() -> Vec3<T> {
        Vec3::new(T::zero(), T::zero(), T::zero())
    }

    pub fn diagonal(xx: T) -> Vec3<T> {
        Vec3::new(xx, xx, xx)
    }

    pub fn dot(self, rhs: Vec3<T>) -> T {
         self.x * rhs.x + self.y * rhs.y + self.z * rhs.z
    }

    pub fn cross(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.y * rhs.z - self.z * rhs.y,
            self.z * rhs.x - self.x * rhs.z,
            self.x * rhs.y - self.y * rhs.x,
            )
    }
}

impl <T> Add<Vec3<T>> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn add(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.x + rhs.x,
            self.y + rhs.y,
            self.z + rhs.z,
            )
    }
}

impl <T> Sub<Vec3<T>> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn sub(self, rhs: Vec3<T>) -> Vec3<T> {
        Vec3::new(
            self.x - rhs.x,
            self.y - rhs.y,
            self.z - rhs.z,
            )
    }
}

impl <T> Mul<T> for Vec3<T> where T : Mul<T, Output = T> + Add<T, Output = T> + Sub<T, Output = T> + Zero + Copy + Clone {
    type Output = Vec3<T>;

    fn mul(self, rhs: T) -> Vec3<T> {
        Vec3::new(
            self.x * rhs,
            self.y * rhs,
            self.z * rhs,
            )
    }
}

impl <T> Vec3<T> where T: Mul<T, Output=T> + One + Zero + Float + Clone + Copy {
    #[allow(non_snake_case)]
    pub fn sphericalToCartesian(theta: T, phi: T) -> Vec3<T> {
        Vec3::new(phi.cos() * theta.sin(), phi.sin() * theta.sin(), theta.cos())
    }

    fn clamp(value: T, low: T, high: T) -> T {
        if value < low {
            return low
        }
        if value > high {
            return high
        }
        value
    }

    #[allow(non_snake_case)]
    pub fn sphericalTheta(v: &Vec3<T>) -> T {
       Vec3::clamp(v.z, -T::one(), T::one()).acos()
    }

    #[allow(non_snake_case)]
    pub fn sphericalPhi(v: &Vec3<T>) -> T {
        v.y.atan2(v.x) // TODO should be in range [0..2PI)
    }

    #[allow(non_snake_case)]
    pub fn cosTheta(v: &Vec3<T>) -> T {
        v.z
    }

    #[allow(non_snake_case)]
    pub fn sinTheta2(v: &Vec3<T>) -> T {
        let positive_result = T::one() - Vec3::cosTheta(&v) * Vec3::cosTheta(&v);
        if positive_result >= T::zero() {
            positive_result
        } else {
            T::zero()
        }
    }

    #[allow(non_snake_case)]
    pub fn sinTheta(v: &Vec3<T>) -> T {
        Vec3::sinTheta2(v).sqrt()
    }

    #[allow(non_snake_case)]
    pub fn cosPhi(v: &Vec3<T>) -> T {
        let sinTheta: T = Vec3::sinTheta(v);
        if sinTheta == T::zero() {
            T::one()
        } else {
            Vec3::clamp(v.x / sinTheta, -T::one(), T::one())
        }
    }

    #[allow(non_snake_case)]
    pub fn sinPhi(v: &Vec3<T>) -> T {
        let sinTheta: T = Vec3::sinTheta(v);
        if sinTheta == T::zero() {
            T::zero()
        } else {
            Vec3::clamp(v.y / sinTheta, -T::one(), T::one())
        }
    }

    pub fn length(& self) -> T {
        (self.x * self.x + self.y * self.y + self.z * self.z).sqrt()
    }

    pub fn normalize(&mut self) {
        let length: T = self.length();
        if length > T::zero() {
            let inverse_length = T::one() / length;

            self.x = self.x * inverse_length;
            self.y = self.y * inverse_length;
            self.z = self.z * inverse_length;
        }
    }
}

#[cfg(test)]
mod tests {
    use super::Vec3;

    #[test]
    fn should_be_created_with_constructor() {
        let v: Vec3<f64> = Vec3::new(0.0, 1.0, 2.0);

        assert_eq!(v, Vec3 { x: 0.0, y: 1.0, z: 2.0 });
    }

    #[test]
    fn should_initialize_to_zero_vector() {
        let v: Vec3<f64> = Vec3::zero();

        assert_eq!(v, Vec3::<f64>{ x: 0.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_initialize_to_diagonal_vector() {
        let v: Vec3<f64> = Vec3::diagonal(1.0);

        assert_eq!(v, Vec3::<f64>{ x: 1.0, y: 1.0, z: 1.0 });
    }

    #[test]
    fn should_know_dot_product() {
        let u: Vec3<f64> = Vec3::diagonal(1.0);
        let v: Vec3<f64> = Vec3::new(0.0, 1.0, 2.0);

        let dot_product: f64 = u.dot(v);

        assert_eq!(dot_product, 3.0);
    }

    #[test]
    fn should_know_its_length() {
        let v: Vec3<f64> = Vec3 { x: 0.0, y: 0.0, z: 0.0 };

        assert_eq!(v.length(), 0.0);
    }

    #[test]
    fn should_be_able_to_normalize() {
        let mut v: Vec3<f64> = Vec3::new(3.0, 0.0, 0.0);
        v.normalize();

        assert_eq!(v, Vec3 { x: 1.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_know_cross_product() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let product = v.cross(w);

        assert_eq!(product, Vec3 { x: 0.0, y: 0.0, z: 1.0 });
    }

    #[test]
    fn should_form_vector_sum() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let sum = v + w;

        assert_eq!(sum, Vec3 { x: 1.0, y: 1.0, z: 0.0 });
    }

    #[test]
    fn should_form_vector_difference() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let w: Vec3<f64> = Vec3::new(0.0, 1.0, 0.0);

        let sum = v - w;

        assert_eq!(sum, Vec3 { x: 1.0, y: -1.0, z: 0.0 });
    }

    #[test]
    fn should_form_scalar_multiplication() {
        let v: Vec3<f64> = Vec3::new(1.0, 0.0, 0.0);
        let c: f64 = 2.0;

        let scalar = v * c;

        assert_eq!(scalar, Vec3 { x: 2.0, y: 0.0, z: 0.0 });
    }

    #[test]
    fn should_know_how_to_convert_from_polar_coordinates() {
        let v: Vec3<f64> = Vec3::sphericalToCartesian(0.0, 0.0);

        assert_eq!(v, Vec3 { x: 0.0, y: 0.0, z: 1.0 });
    }
}
<|endoftext|>


<commit_before>#[cfg(test)]
mod get_repos_should {
    use super::*;

    #[test]
    fn return_repos_with_app_name_hello_world_and_language_rust_and_program_type_lib_and_user_intrepion(
    ) {
        let expected = vec![GitHubRepository {
            app_name: "hello-world-library".to_string(),
            client_type: None,
            language: ProgrammingLanguage::Rust,
            program_type: ProgramType::Library,
            server_type: None,
            user: "intrepion".to_string(),
        }];

        let actual = get_repos(
            "intrepion",
            "hello-world",
            ProgrammingLanguage::Rust,
            ProgramType::Library,
        );

        assert_eq!(actual, expected);
    }

    #[test]
    fn return_repos_with_app_name_fizz_buzz_and_language_rust_and_program_type_lib_and_user_intrepion() {
        let expected = vec![GitHubRepository {
            app_name: "fizz-buzz-library".to_string(),
            client_type: None,
            language: ProgrammingLanguage::Rust,
            program_type: ProgramType::Library,
            server_type: None,
            user: "intrepion".to_string(),
        }];

        let actual = get_repos(
            "intrepion",
            "fizz-buzz",
            ProgrammingLanguage::Rust,
            ProgramType::Library,
        );

        assert_eq!(actual, expected);
    }
}

#[derive(Debug, PartialEq)]
enum ProgrammingLanguage {
    Rust,
}

#[derive(Debug, PartialEq)]
enum ProgramType {
    Library,
}

#[derive(Debug, PartialEq)]
struct GitHubRepository {
    app_name: String,
    client_type: Option<String>,
    language: ProgrammingLanguage,
    program_type: ProgramType,
    server_type: Option<String>,
    user: String,
}

fn get_repos(user: &str, app_name: &str, language: ProgrammingLanguage, program_type: ProgramType) -> Vec<GitHubRepository> {
    vec![GitHubRepository {
        app_name: "hello-world-library".to_string(),
        client_type: None,
        language: ProgrammingLanguage::Rust,
        program_type: ProgramType::Library,
        server_type: None,
        user: "intrepion".to_string()
    }]
}
<commit_msg>green<commit_after>#[cfg(test)]
mod get_repos_should {
    use super::*;

    #[test]
    fn return_repos_with_app_name_hello_world_and_language_rust_and_program_type_lib_and_user_intrepion(
    ) {
        let expected = vec![GitHubRepository {
            app_name: "hello-world-library".to_string(),
            client_type: None,
            language: ProgrammingLanguage::Rust,
            program_type: ProgramType::Library,
            server_type: None,
            user: "intrepion".to_string(),
        }];

        let actual = get_repos(
            "intrepion",
            "hello-world",
            ProgrammingLanguage::Rust,
            ProgramType::Library,
        );

        assert_eq!(actual, expected);
    }

    #[test]
    fn return_repos_with_app_name_fizz_buzz_and_language_rust_and_program_type_lib_and_user_intrepion() {
        let expected = vec![GitHubRepository {
            app_name: "fizz-buzz-library".to_string(),
            client_type: None,
            language: ProgrammingLanguage::Rust,
            program_type: ProgramType::Library,
            server_type: None,
            user: "intrepion".to_string(),
        }];

        let actual = get_repos(
            "intrepion",
            "fizz-buzz",
            ProgrammingLanguage::Rust,
            ProgramType::Library,
        );

        assert_eq!(actual, expected);
    }
}

#[derive(Debug, PartialEq)]
enum ProgrammingLanguage {
    Rust,
}

#[derive(Debug, PartialEq)]
enum ProgramType {
    Library,
}

#[derive(Debug, PartialEq)]
struct GitHubRepository {
    app_name: String,
    client_type: Option<String>,
    language: ProgrammingLanguage,
    program_type: ProgramType,
    server_type: Option<String>,
    user: String,
}

fn get_repos(user: &str, app_name: &str, language: ProgrammingLanguage, program_type: ProgramType) -> Vec<GitHubRepository> {
    vec![GitHubRepository {
        app_name: format!("{app_name}-library"),
        client_type: None,
        language: ProgrammingLanguage::Rust,
        program_type: ProgramType::Library,
        server_type: None,
        user: "intrepion".to_string()
    }]
}
<|endoftext|>


<commit_before>#![warn(clippy::manual_strip)]

fn main() {
    let s = "abc";

    if s.starts_with("ab") {
        str::to_string(&s["ab".len()..]);
        s["ab".len()..].to_string();

        str::to_string(&s[2..]);
        s[2..].to_string();
    }

    if s.ends_with("bc") {
        str::to_string(&s[..s.len() - "bc".len()]);
        s[..s.len() - "bc".len()].to_string();

        str::to_string(&s[..s.len() - 2]);
        s[..s.len() - 2].to_string();
    }

    // Character patterns
    if s.starts_with('a') {
        str::to_string(&s[1..]);
        s[1..].to_string();
    }

    // Variable prefix
    let prefix = "ab";
    if s.starts_with(prefix) {
        str::to_string(&s[prefix.len()..]);
    }

    // Constant prefix
    const PREFIX: &str = "ab";
    if s.starts_with(PREFIX) {
        str::to_string(&s[PREFIX.len()..]);
        str::to_string(&s[2..]);
    }

    // Constant target
    const TARGET: &str = "abc";
    if TARGET.starts_with(prefix) {
        str::to_string(&TARGET[prefix.len()..]);
    }

    // String target - not mutated.
    let s1: String = "abc".into();
    if s1.starts_with("ab") {
        s1[2..].to_uppercase();
    }

    // String target - mutated. (Don't lint.)
    let mut s2: String = "abc".into();
    if s2.starts_with("ab") {
        s2.push('d');
        s2[2..].to_uppercase();
    }
}
<commit_msg>manual-strip: Add additional test<commit_after>#![warn(clippy::manual_strip)]

fn main() {
    let s = "abc";

    if s.starts_with("ab") {
        str::to_string(&s["ab".len()..]);
        s["ab".len()..].to_string();

        str::to_string(&s[2..]);
        s[2..].to_string();
    }

    if s.ends_with("bc") {
        str::to_string(&s[..s.len() - "bc".len()]);
        s[..s.len() - "bc".len()].to_string();

        str::to_string(&s[..s.len() - 2]);
        s[..s.len() - 2].to_string();
    }

    // Character patterns
    if s.starts_with('a') {
        str::to_string(&s[1..]);
        s[1..].to_string();
    }

    // Variable prefix
    let prefix = "ab";
    if s.starts_with(prefix) {
        str::to_string(&s[prefix.len()..]);
    }

    // Constant prefix
    const PREFIX: &str = "ab";
    if s.starts_with(PREFIX) {
        str::to_string(&s[PREFIX.len()..]);
        str::to_string(&s[2..]);
    }

    // Constant target
    const TARGET: &str = "abc";
    if TARGET.starts_with(prefix) {
        str::to_string(&TARGET[prefix.len()..]);
    }

    // String target - not mutated.
    let s1: String = "abc".into();
    if s1.starts_with("ab") {
        s1[2..].to_uppercase();
    }

    // String target - mutated. (Don't lint.)
    let mut s2: String = "abc".into();
    if s2.starts_with("ab") {
        s2.push('d');
        s2[2..].to_uppercase();
    }

    // Target not stripped. (Don't lint.)
    let s3 = String::from("abcd");
    let s4 = String::from("efgh");
    if s3.starts_with("ab") {
        s4[2..].to_string();
    }
}
<|endoftext|>


<commit_before>extern crate scroll_phat_hd;

use scroll_phat_hd::display::*;
use scroll_phat_hd::scroller::*;

fn main() {
    println!("start");

    // let mut projector = I2CProjector::new(1);
    let mut display = TermDisplay::new();
    let mut scroller = Scroller::new(&mut display);

    scroller.set_text("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+=-_,.!?");
    for _ in 0..3000 {
        scroller.show();
        std::thread::sleep(std::time::Duration::from_millis(100));
        scroller.scroll();
    }

    println!("end");
}
<commit_msg>Fix example.<commit_after>extern crate scroll_phat_hd;

use scroll_phat_hd::display::*;
use scroll_phat_hd::scroller::*;

fn main() {
    println!("start");

    // let mut display = I2CDisplay::new(1);
    let mut display = TermDisplay::new();
    let mut scroller = Scroller::new(&mut display);

    scroller.set_text("ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+=-_,.!?");
    for _ in 0..3000 {
        scroller.show();
        std::thread::sleep(std::time::Duration::from_millis(100));
        scroller.scroll();
    }

    println!("end");
}
<|endoftext|>


<commit_before>#[macro_use]
extern crate version_sync;

#[test]
fn test_readme_deps() {
    assert_markdown_deps_updated!("README.md");
}

#[test]
fn test_readme_changelog() {
    assert_contains_regex!("README.md", r"^### Version {version} — .* \d\d?.., 20\d\d$");
}

#[test]
fn test_html_root_url() {
    assert_html_root_url_updated!("src/lib.rs");
}
<commit_msg>tests: reformat with rustfmt 1.0.0<commit_after>#[macro_use]
extern crate version_sync;

#[test]
fn test_readme_deps() {
    assert_markdown_deps_updated!("README.md");
}

#[test]
fn test_readme_changelog() {
    assert_contains_regex!(
        "README.md",
        r"^### Version {version} — .* \d\d?.., 20\d\d$"
    );
}

#[test]
fn test_html_root_url() {
    assert_html_root_url_updated!("src/lib.rs");
}
<|endoftext|>


<commit_before>#![feature(path_ext)]
extern crate rustc_serialize;
extern crate getopts;
extern crate xml;
extern crate colored;
extern crate flv_toolbox_rs;

use colored::*;
use rustc_serialize::json::Json;
use getopts::Options;

use flv_toolbox_rs::lib::*;
use flv_toolbox_rs::crc32::Crc32;

fn print_metatag(json: &Json) -> Result<(), Option<String>> {
    let event_name = json.as_array().ok_or(Some("meta is not array".to_string()))?[0].as_string().ok_or(Some("arr[0] is not string.".to_string()))?;
    println!("metadata: {}", event_name);

    let obj = &json.as_array().ok_or(Some("arr[1] is not array".to_string()))?[1];
    println!("{}", rustc_serialize::json::as_pretty_json(&obj));

    let times = obj.find_path(&["keyframes", "times"]).ok_or(None)?.as_array().ok_or(None)?;
    let times: Vec<f64> = times.iter().map(|val: &Json| {
        val.as_f64().unwrap()
    }).collect();
    let filepositions = obj.find_path(&["keyframes", "filepositions"]).ok_or(None)?.as_array().ok_or(None)?;
    let filepositions: Vec<u64> = filepositions.iter().map(|val: &Json| {
        val.as_f64().unwrap() as u64
    }).collect();

    for (i, (t, p)) in (0u32..).zip(times.iter().zip(filepositions.iter())) {
        println!("{:3} {} {:8}", i, format_seconds_ms((t * 1000f64) as u64), p);
    }
    Ok(())
}

fn flv_info(path: &String, show_meta: bool, all_frame: bool, video_frame: bool, audio_frame: bool) {
    use std::fs::File;
    use std::path::Path;
    use std::fs;
    use std::io::{ Read, self };

    let mut source: Box<Read>;
    let mut parser: FLVTagRead<Box<Read>>;

    if path == "-" { // stdin
        println!("show info for stdin");
        source = Box::new(io::stdin()) as Box<Read>;
        parser = FLVTagRead::new(&mut source);
    } else {
        let path = Path::new(path);
        if fs::metadata(path).is_err() {
            panic!(format!("file dosen't exist: {}", path.display()));
        }
        else {
            println!("show info for {}", path.display());
        }
        let mut file = File::open(path).unwrap();
        let file_meta = file.metadata().unwrap();
        let file_size = file_meta.len();
        println!("file size: {}", file_size);
        source = Box::new(file) as Box<Read>;
        parser = FLVTagRead::new(&mut source);//header has read
    }

    println!("\r\ntags: kf: key_frame cd: codec_id pt: packet_type", );
    if audio_frame {
        println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}", "id", "time", "offset", "size", "type", "kf", "cd", "sr", "cts", "dts", "pts", "ddts");
    }
    println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}", "id", "time", "offset", "size", "type", "kf", "cd", "pt", "cts", "dts", "pts", "ddts");
    let mut i = 0;
    let mut last_v_tag: Option<FLVTag> = None;
    let mut last_a_tag: Option<FLVTag> = None;
    let mut asc: Option<AudioSpecificConfig> = None;
    loop {
        let position = parser.get_position();
        let tag = parser.next();
        if tag.is_none() {
            break;
        }
        let tag = tag.unwrap();
        match tag.get_tag_type() {
            FLVTagType::TAG_TYPE_VIDEO => {
                let dts_delta: i64 = if last_v_tag.is_some() {
                    (tag.get_timestamp() as i64) - (last_v_tag.unwrap().get_timestamp() as i64)
                } else {
                    0
                };
                if tag.get_frame_type() == 1 && video_frame{// FRAME_TYPE_KEYFRAME
                    if tag.get_avc_packet_type() == 0 { // AVC_PACKET_TYPE_SEQUENCE_HEADER
                        println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}"     , i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), 0, 0, 0, dts_delta).on_red());
                        // println!("{:?}", tag.get_avcc());
                        i += 1;
                    } else { // AVC_PACKET_TYPE_NALU
                        println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | {}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), tag.get_avc_composition_time_offset(), tag.get_timestamp(), (tag.get_timestamp() as i64) + (tag.get_avc_composition_time_offset() as i64), dts_delta, tag.get_nal_uints_info()).on_blue());
                        // println!("{:?}", tag.get_nal_units());
                        i += 1;
                    }
                } else if all_frame && video_frame {
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | {}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), tag.get_avc_composition_time_offset(), tag.get_timestamp(), (tag.get_timestamp() as i64) + (tag.get_avc_composition_time_offset() as i64), dts_delta, tag.get_nal_uints_info()).on_magenta());
                    // println!("{:?}", tag.get_nal_units());
                    i += 1;
                }
                last_v_tag = Some(tag);
            },
            FLVTagType::TAG_TYPE_AUDIO => {
                let dts_delta: i64 = if last_a_tag.is_some() {
                    (tag.get_timestamp() as i64) - (last_a_tag.unwrap().get_timestamp() as i64)
                } else {
                    0
                };
                if tag.is_acc_sequence_header() && audio_frame {
                    asc = Some(tag.get_sound_audio_specific_config());
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | [{:>5} {:>5} {}]", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", tag.get_sound_format(), tag.get_sound_channels(), "", tag.get_timestamp(), "", dts_delta, tag.get_sound_frame_duration(asc.as_ref().unwrap()), asc.as_ref().unwrap().get_sample_rate(), tag.get_sound_size()).on_cyan());
                    // println!("{:?}", asc.as_ref().unwrap());
                    // println!("{:?}", FLVTag::get_sound_adts_header_data(asc.as_ref().unwrap(), 9 + 7));
                    i += 1;
                }
                else if all_frame && audio_frame {
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | [{:>5} {:>5} {}]", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", tag.get_sound_format(), tag.get_sound_channels(), "", tag.get_timestamp(), "", dts_delta, tag.get_sound_frame_duration(asc.as_ref().unwrap()), asc.as_ref().unwrap().get_sample_rate(), tag.get_sound_size()).on_yellow());
                    // println!("{:?}", FLVTag::get_sound_adts_header_data(asc.as_ref().unwrap(), tag.get_sound_data_size() + 7));
                    // println!("{:?}", tag.get_sound_data());
                    i += 1;
                }
                last_a_tag = Some(tag);
            },
            FLVTagType::TAG_TYPE_SCRIPTDATAOBJECT => {
                println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", "", "");
                if show_meta {
                    match print_metatag(&Json::Array(tag.get_objects())) {
                        Ok(_) => {}
                        Err(s) => {
                            println!("print meta err: {:?}", s);
                        }
                    }
                }
                i += 1;
            }
        };
    }
}

fn print_usage(program: &str, opts: Options) {
    let brief = format!("Usage: {} FILE [options]", program);
    print!("{}", opts.usage(&brief));
}

fn main() {
    let args: Vec<String> = std::env::args().collect();
    let program = args[0].clone();

    let mut opts = Options::new();
    opts.optflag("m", "meta", "show metadata");
    opts.optflag("a", "all", "print all frames");
    opts.optflag("v", "video", "print video frames");
    opts.optflag("d", "audio", "print audio frames");
    opts.optflag("h", "help", "print this help menu");
    opts.optflag("c", "crc32", "calculate crc32 of tags");

    let matches = match opts.parse(&args[1..]) {
        Ok(m) => m,
        Err(f) => {
            panic!(f.to_string())
        }
    };
    if matches.opt_present("h") {
        print_usage(&program, opts);
        return;
    }
    let input = if !matches.free.is_empty() {
        matches.free[0].clone()
    } else {
        print_usage(&program, opts);
        return;
    };
    let show_meta = matches.opt_present("m");
    let crc32_file = matches.opt_present("c");
    let all_frame = matches.opt_present("a");
    let video_frame = matches.opt_present("v");
    let audio_frame = matches.opt_present("d");
    if crc32_file {
        flv_crc32(&input);
    } else {
        flv_info(&input, show_meta, all_frame, video_frame, audio_frame);
    }
}

fn flv_crc32(path: &String) {
    use std::fs::File;
    use std::io::Write;

    let mut file = File::open(&path).unwrap();
    let mut parser = FLVTagRead::new(&mut file);

    let mut i = 0;
    let mut key_time: f64 = 0f64;
    let mut key_pos: u64 = 0;
    let mut tmp: Vec<u32> = Vec::new();
    let mut ret: Vec<Json> = Vec::new();
    loop {
        let position = parser.get_position();
        let tag = parser.next();
        if tag.is_none() {
            break;
        }

        let tag = tag.unwrap();
        let mut bytes: Vec<u8> = Vec::with_capacity(tag.get_tag_size() as usize);
        tag.write(&mut bytes);
        let mut hash = Crc32::new();
        hash.update(&bytes);
        let crc32_hash: u32 = hash.finish();
        if tag.get_tag_type() == FLVTagType::TAG_TYPE_VIDEO && tag.get_frame_type() == 1 {
            if tmp.len() > 0 {
                ret.push(output_info(key_pos, key_time, &mut tmp));
            }
            key_pos = position;
            key_time = tag.get_timestamp() as f64 / 1000f64;
        }
        tmp.push(crc32_hash);
    }
    if tmp.len() > 0 {
        ret.push(output_info(key_pos, key_time, &mut tmp));
    }

    // println!("{}", rustc_serialize::json::as_pretty_json(&Json::Array(ret)));
    let output_path = format!("{}{}", path, ".crc32.json");
    let mut output_file = File::create(output_path).unwrap();
    write!(output_file, "{}", rustc_serialize::json::as_pretty_json(&Json::Array(ret)));
}

fn output_info(key_pos: u64, key_time: f64, crc_list: &mut Vec<u32>) -> Json {
    use std::collections::BTreeMap;
    let mut arr: Vec<Json> =
        vec![("time"  , Json::F64(key_time)),
             ("offset", Json::U64(key_pos)),
             ("tags"  , Json::Array(crc_list.iter().map(|i| Json::U64(*i as u64)).collect()))]
            .into_iter().map(|(key, json)| {
                let mut obj: BTreeMap<String, Json> = BTreeMap::new();
                obj.insert(key.to_string(), json);
                Json::Object(obj)
            }).collect();

    crc_list.clear();
    Json::Array(arr)
}<commit_msg>add error message when print metadata<commit_after>#![feature(path_ext)]
extern crate rustc_serialize;
extern crate getopts;
extern crate xml;
extern crate colored;
extern crate flv_toolbox_rs;

use colored::*;
use rustc_serialize::json::Json;
use getopts::Options;

use flv_toolbox_rs::lib::*;
use flv_toolbox_rs::crc32::Crc32;

fn print_metatag(json: &Json) -> Result<(), Option<String>> {
    let event_name = json.as_array().ok_or(Some("meta is not array".to_string()))?[0].as_string().ok_or(Some("arr[0] is not string.".to_string()))?;
    println!("metadata: {}", event_name);

    let obj = &json.as_array().ok_or(Some("arr[1] is not array".to_string()))?[1];
    println!("{}", rustc_serialize::json::as_pretty_json(&obj));

    let times = obj.find_path(&["keyframes", "times"]).ok_or(Some("no keyframes.times in meta".to_string()))?.as_array().ok_or(Some("keyframes.times is not an array".to_string()))?;
    let times: Vec<f64> = times.iter().map(|val: &Json| {
        val.as_f64().unwrap()
    }).collect();
    let filepositions = obj.find_path(&["keyframes", "filepositions"]).ok_or(Some("no keyframes.filepositions in meta".to_string()))?.as_array().ok_or(Some("keyframes.filepositions is not an array".to_string()))?;
    let filepositions: Vec<u64> = filepositions.iter().map(|val: &Json| {
        val.as_f64().unwrap() as u64
    }).collect();

    for (i, (t, p)) in (0u32..).zip(times.iter().zip(filepositions.iter())) {
        println!("{:3} {} {:8}", i, format_seconds_ms((t * 1000f64) as u64), p);
    }
    Ok(())
}

fn flv_info(path: &String, show_meta: bool, all_frame: bool, video_frame: bool, audio_frame: bool) {
    use std::fs::File;
    use std::path::Path;
    use std::fs;
    use std::io::{ Read, self };

    let mut source: Box<Read>;
    let mut parser: FLVTagRead<Box<Read>>;

    if path == "-" { // stdin
        println!("show info for stdin");
        source = Box::new(io::stdin()) as Box<Read>;
        parser = FLVTagRead::new(&mut source);
    } else {
        let path = Path::new(path);
        if fs::metadata(path).is_err() {
            panic!(format!("file dosen't exist: {}", path.display()));
        }
        else {
            println!("show info for {}", path.display());
        }
        let mut file = File::open(path).unwrap();
        let file_meta = file.metadata().unwrap();
        let file_size = file_meta.len();
        println!("file size: {}", file_size);
        source = Box::new(file) as Box<Read>;
        parser = FLVTagRead::new(&mut source);//header has read
    }

    println!("\r\ntags: kf: key_frame cd: codec_id pt: packet_type", );
    if audio_frame {
        println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}", "id", "time", "offset", "size", "type", "kf", "cd", "sr", "cts", "dts", "pts", "ddts");
    }
    println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}", "id", "time", "offset", "size", "type", "kf", "cd", "pt", "cts", "dts", "pts", "ddts");
    let mut i = 0;
    let mut last_v_tag: Option<FLVTag> = None;
    let mut last_a_tag: Option<FLVTag> = None;
    let mut asc: Option<AudioSpecificConfig> = None;
    loop {
        let position = parser.get_position();
        let tag = parser.next();
        if tag.is_none() {
            break;
        }
        let tag = tag.unwrap();
        match tag.get_tag_type() {
            FLVTagType::TAG_TYPE_VIDEO => {
                let dts_delta: i64 = if last_v_tag.is_some() {
                    (tag.get_timestamp() as i64) - (last_v_tag.unwrap().get_timestamp() as i64)
                } else {
                    0
                };
                if tag.get_frame_type() == 1 && video_frame{// FRAME_TYPE_KEYFRAME
                    if tag.get_avc_packet_type() == 0 { // AVC_PACKET_TYPE_SEQUENCE_HEADER
                        println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6}"     , i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), 0, 0, 0, dts_delta).on_red());
                        // println!("{:?}", tag.get_avcc());
                        i += 1;
                    } else { // AVC_PACKET_TYPE_NALU
                        println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | {}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), tag.get_avc_composition_time_offset(), tag.get_timestamp(), (tag.get_timestamp() as i64) + (tag.get_avc_composition_time_offset() as i64), dts_delta, tag.get_nal_uints_info()).on_blue());
                        // println!("{:?}", tag.get_nal_units());
                        i += 1;
                    }
                } else if all_frame && video_frame {
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | {}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, tag.get_frame_type(), tag.get_codec_id(), tag.get_avc_packet_type(), tag.get_avc_composition_time_offset(), tag.get_timestamp(), (tag.get_timestamp() as i64) + (tag.get_avc_composition_time_offset() as i64), dts_delta, tag.get_nal_uints_info()).on_magenta());
                    // println!("{:?}", tag.get_nal_units());
                    i += 1;
                }
                last_v_tag = Some(tag);
            },
            FLVTagType::TAG_TYPE_AUDIO => {
                let dts_delta: i64 = if last_a_tag.is_some() {
                    (tag.get_timestamp() as i64) - (last_a_tag.unwrap().get_timestamp() as i64)
                } else {
                    0
                };
                if tag.is_acc_sequence_header() && audio_frame {
                    asc = Some(tag.get_sound_audio_specific_config());
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | [{:>5} {:>5} {}]", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", tag.get_sound_format(), tag.get_sound_channels(), "", tag.get_timestamp(), "", dts_delta, tag.get_sound_frame_duration(asc.as_ref().unwrap()), asc.as_ref().unwrap().get_sample_rate(), tag.get_sound_size()).on_cyan());
                    // println!("{:?}", asc.as_ref().unwrap());
                    // println!("{:?}", FLVTag::get_sound_adts_header_data(asc.as_ref().unwrap(), 9 + 7));
                    i += 1;
                }
                else if all_frame && audio_frame {
                    println!("{}", format!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2} | {:>4} | {:>6} | {:>6} | {:>6} | [{:>5} {:>5} {}]", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", tag.get_sound_format(), tag.get_sound_channels(), "", tag.get_timestamp(), "", dts_delta, tag.get_sound_frame_duration(asc.as_ref().unwrap()), asc.as_ref().unwrap().get_sample_rate(), tag.get_sound_size()).on_yellow());
                    // println!("{:?}", FLVTag::get_sound_adts_header_data(asc.as_ref().unwrap(), tag.get_sound_data_size() + 7));
                    // println!("{:?}", tag.get_sound_data());
                    i += 1;
                }
                last_a_tag = Some(tag);
            },
            FLVTagType::TAG_TYPE_SCRIPTDATAOBJECT => {
                println!("{:>6} | {:>10} | {:>10} | {:>6} | {:>4} | {:>2} | {:>2} | {:>2}", i, format_seconds_ms(tag.get_timestamp()), position, tag.get_tag_size(), tag.get_tag_type() as usize, "", "", "");
                if show_meta {
                    match print_metatag(&Json::Array(tag.get_objects())) {
                        Ok(_) => {}
                        Err(s) => {
                            println!("print meta err: {:?}", s);
                        }
                    }
                }
                i += 1;
            }
        };
    }
}

fn print_usage(program: &str, opts: Options) {
    let brief = format!("Usage: {} FILE [options]", program);
    print!("{}", opts.usage(&brief));
}

fn main() {
    let args: Vec<String> = std::env::args().collect();
    let program = args[0].clone();

    let mut opts = Options::new();
    opts.optflag("m", "meta", "show metadata");
    opts.optflag("a", "all", "print all frames");
    opts.optflag("v", "video", "print video frames");
    opts.optflag("d", "audio", "print audio frames");
    opts.optflag("h", "help", "print this help menu");
    opts.optflag("c", "crc32", "calculate crc32 of tags");

    let matches = match opts.parse(&args[1..]) {
        Ok(m) => m,
        Err(f) => {
            panic!(f.to_string())
        }
    };
    if matches.opt_present("h") {
        print_usage(&program, opts);
        return;
    }
    let input = if !matches.free.is_empty() {
        matches.free[0].clone()
    } else {
        print_usage(&program, opts);
        return;
    };
    let show_meta = matches.opt_present("m");
    let crc32_file = matches.opt_present("c");
    let all_frame = matches.opt_present("a");
    let video_frame = matches.opt_present("v");
    let audio_frame = matches.opt_present("d");
    if crc32_file {
        flv_crc32(&input);
    } else {
        flv_info(&input, show_meta, all_frame, video_frame, audio_frame);
    }
}

fn flv_crc32(path: &String) {
    use std::fs::File;
    use std::io::Write;

    let mut file = File::open(&path).unwrap();
    let mut parser = FLVTagRead::new(&mut file);

    let mut i = 0;
    let mut key_time: f64 = 0f64;
    let mut key_pos: u64 = 0;
    let mut tmp: Vec<u32> = Vec::new();
    let mut ret: Vec<Json> = Vec::new();
    loop {
        let position = parser.get_position();
        let tag = parser.next();
        if tag.is_none() {
            break;
        }

        let tag = tag.unwrap();
        let mut bytes: Vec<u8> = Vec::with_capacity(tag.get_tag_size() as usize);
        tag.write(&mut bytes);
        let mut hash = Crc32::new();
        hash.update(&bytes);
        let crc32_hash: u32 = hash.finish();
        if tag.get_tag_type() == FLVTagType::TAG_TYPE_VIDEO && tag.get_frame_type() == 1 {
            if tmp.len() > 0 {
                ret.push(output_info(key_pos, key_time, &mut tmp));
            }
            key_pos = position;
            key_time = tag.get_timestamp() as f64 / 1000f64;
        }
        tmp.push(crc32_hash);
    }
    if tmp.len() > 0 {
        ret.push(output_info(key_pos, key_time, &mut tmp));
    }

    // println!("{}", rustc_serialize::json::as_pretty_json(&Json::Array(ret)));
    let output_path = format!("{}{}", path, ".crc32.json");
    let mut output_file = File::create(output_path).unwrap();
    write!(output_file, "{}", rustc_serialize::json::as_pretty_json(&Json::Array(ret)));
}

fn output_info(key_pos: u64, key_time: f64, crc_list: &mut Vec<u32>) -> Json {
    use std::collections::BTreeMap;
    let mut arr: Vec<Json> =
        vec![("time"  , Json::F64(key_time)),
             ("offset", Json::U64(key_pos)),
             ("tags"  , Json::Array(crc_list.iter().map(|i| Json::U64(*i as u64)).collect()))]
            .into_iter().map(|(key, json)| {
                let mut obj: BTreeMap<String, Json> = BTreeMap::new();
                obj.insert(key.to_string(), json);
                Json::Object(obj)
            }).collect();

    crc_list.clear();
    Json::Array(arr)
}<|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.

use infer::InferCtxt;
use smallvec::SmallVec;
use traits::{EvaluationResult, PredicateObligation, SelectionContext,
             TraitQueryMode, OverflowError};

impl<'cx, 'gcx, 'tcx> InferCtxt<'cx, 'gcx, 'tcx> {
    /// Evaluates whether the predicate can be satisfied (by any means)
    /// in the given `ParamEnv`.
    pub fn predicate_may_hold(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> bool {
        self.evaluate_obligation(obligation).may_apply()
    }

    /// Evaluates whether the predicate can be satisfied in the given
    /// `ParamEnv`, and returns `false` if not certain. However, this is
    /// not entirely accurate if inference variables are involved.
    pub fn predicate_must_hold(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> bool {
        self.evaluate_obligation(obligation) == EvaluationResult::EvaluatedToOk
    }

    // Helper function that canonicalizes and runs the query, as well as handles
    // overflow.
    fn evaluate_obligation(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> EvaluationResult {
        let mut _orig_values = SmallVec::new();
        let c_pred = self.canonicalize_query(&obligation.param_env.and(obligation.predicate),
                                             &mut _orig_values);
        // Run canonical query. If overflow occurs, rerun from scratch but this time
        // in standard trait query mode so that overflow is handled appropriately
        // within `SelectionContext`.
        match self.tcx.global_tcx().evaluate_obligation(c_pred) {
            Ok(result) => result,
            Err(OverflowError) => {
                let mut selcx =
                    SelectionContext::with_query_mode(&self, TraitQueryMode::Standard);
                selcx.evaluate_obligation_recursively(obligation)
                     .expect("Overflow should be caught earlier in standard query mode")
            }
        }
    }
}
<commit_msg>give a more informative failure in this case<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.

use infer::InferCtxt;
use smallvec::SmallVec;
use traits::{EvaluationResult, PredicateObligation, SelectionContext,
             TraitQueryMode, OverflowError};

impl<'cx, 'gcx, 'tcx> InferCtxt<'cx, 'gcx, 'tcx> {
    /// Evaluates whether the predicate can be satisfied (by any means)
    /// in the given `ParamEnv`.
    pub fn predicate_may_hold(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> bool {
        self.evaluate_obligation(obligation).may_apply()
    }

    /// Evaluates whether the predicate can be satisfied in the given
    /// `ParamEnv`, and returns `false` if not certain. However, this is
    /// not entirely accurate if inference variables are involved.
    pub fn predicate_must_hold(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> bool {
        self.evaluate_obligation(obligation) == EvaluationResult::EvaluatedToOk
    }

    // Helper function that canonicalizes and runs the query, as well as handles
    // overflow.
    fn evaluate_obligation(
        &self,
        obligation: &PredicateObligation<'tcx>,
    ) -> EvaluationResult {
        let mut _orig_values = SmallVec::new();
        let c_pred = self.canonicalize_query(&obligation.param_env.and(obligation.predicate),
                                             &mut _orig_values);
        // Run canonical query. If overflow occurs, rerun from scratch but this time
        // in standard trait query mode so that overflow is handled appropriately
        // within `SelectionContext`.
        match self.tcx.global_tcx().evaluate_obligation(c_pred) {
            Ok(result) => result,
            Err(OverflowError) => {
                let mut selcx =
                    SelectionContext::with_query_mode(&self, TraitQueryMode::Standard);
                selcx.evaluate_obligation_recursively(obligation)
                    .unwrap_or_else(|r| {
                        span_bug!(
                            obligation.cause.span,
                            "Overflow should be caught earlier in standard query mode: {:?}, {:?}",
                            obligation,
                            r,
                        )
                    })
            }
        }
    }
}
<|endoftext|>


<commit_before>extern crate sfml;
extern crate nalgebra as na;

use sfml::system::Vector2f;
use sfml::window::{ContextSettings, VideoMode, event, Close};
use sfml::graphics::{RenderWindow, RenderTarget, Texture, Sprite, Color};

use na::{Vec2};

fn main() {
    let mut env = SFMLEnv::new(800, 600);

    while env.win.is_open() {
        for event in env.win.events() {
            match event {
                event::Closed => env.win.close(),
                _ => { }
            }
        }

        env.clear();

        env.win.display();
    }
}

struct SFMLEnv {
    win: RenderWindow,
    width: u32,
    height: u32,
    shipTexture: Texture
}

impl SFMLEnv {
    fn new(width: u32, height: u32) -> SFMLEnv {
        let mut window = RenderWindow::new(VideoMode::new_init(width, height, 32),
                                           "SFML Example",
                                           Close,
                                           &ContextSettings::default())
            .expect("Cannot create a new Render Window.");
        window.set_vertical_sync_enabled(true);
        let mut t = Texture::new_from_file("plane.png")
            .expect("Cannot create Texture");
        t.set_smooth(true);
        SFMLEnv {
            win: window,
            width: width,
            height: height,
            shipTexture: t
        }
    }

    fn clear(&mut self) {
        self.win.clear(&Color::black());
    }
}

struct Boid<'a> {
    pos: Vec2<f32>,
    vel: Vec2<f32>,
    acc: Vec2<f32>,
    sprite: Sprite<'a>,
    maxSpeed: f32,
    maxSteer: f32
}

fn angle(vec: Vec2<f32>) -> f32 {
    vec.y.atan2(vec.x)
}

impl<'a> Boid<'a> {

    fn new(env: &'a SFMLEnv) -> Boid<'a> {
        let mut s = Sprite::new_with_texture(&env.shipTexture).expect("Cannot create ship sprite.");
        let rect = s.get_local_bounds();
        s.set_origin2f(rect.width / 2.0,
                       rect.height / 2.0);
        Boid {
            pos: Vec2::new(0.0, 0.0),
            vel: Vec2::new(0.0, 0.0),
            acc: Vec2::new(0.0, 0.0),
            sprite: s,
            maxSpeed: 5.0,
            maxSteer: 0.2
        }
    }

    fn render(&mut self, env: &SFMLEnv) {
        let angle = 90.0 + angle(self.vel) * 57.29;
        self.sprite.set_rotation(angle);
        self.sprite.set_position(&Vector2f::new(self.pos.x, self.pos.y));
        env.win.draw(self.sprite)
    }

}
<commit_msg>more fiddle<commit_after>extern crate sfml;
extern crate nalgebra as na;

use sfml::system::Vector2f;
use sfml::window::{ContextSettings, VideoMode, event, Close};
use sfml::graphics::{RenderWindow, RenderTarget, Texture, Sprite, Color};

use na::{Vec2};

fn main() {
    let mut env = SFMLEnv::new(800, 600);

    while env.win.is_open() {
        for event in env.win.events() {
            match event {
                event::Closed => env.win.close(),
                _ => { }
            }
        }

        env.clear();

        env.win.display();
    }
}

struct SFMLEnv {
    win: RenderWindow,
    width: u32,
    height: u32,
    shipTexture: Texture
}

impl SFMLEnv {
    fn new(width: u32, height: u32) -> SFMLEnv {
        let mut window = RenderWindow::new(VideoMode::new_init(width, height, 32),
                                           "SFML Example",
                                           Close,
                                           &ContextSettings::default())
            .expect("Cannot create a new Render Window.");
        window.set_vertical_sync_enabled(true);
        let mut t = Texture::new_from_file("plane.png")
            .expect("Cannot create Texture");
        t.set_smooth(true);
        SFMLEnv {
            win: window,
            width: width,
            height: height,
            shipTexture: t
        }
    }

    fn clear(&mut self) {
        self.win.clear(&Color::black());
    }
}

struct Boid<'a> {
    pos: Vec2<f32>,
    vel: Vec2<f32>,
    acc: Vec2<f32>,
    sprite: &'a Sprite<'a>,
    maxSpeed: f32,
    maxSteer: f32
}

fn angle(vec: Vec2<f32>) -> f32 {
    vec.y.atan2(vec.x)
}

impl<'a> Boid<'a> {

    fn new(env: &'a SFMLEnv) -> Boid<'a> {
        let mut s = Sprite::new_with_texture(&env.shipTexture).expect("Cannot create ship sprite.");
        let rect = s.get_local_bounds();
        s.set_origin2f(rect.width / 2.0,
                       rect.height / 2.0);
        Boid {
            pos: Vec2::new(0.0, 0.0),
            vel: Vec2::new(0.0, 0.0),
            acc: Vec2::new(0.0, 0.0),
            sprite: &s,
            maxSpeed: 5.0,
            maxSteer: 0.2
        }
    }

    fn render(&mut self, env: &SFMLEnv) {
        let angle = 90.0 + angle(self.vel) * 57.29;
        self.sprite.set_rotation(angle);
        self.sprite.set_position(&Vector2f::new(self.pos.x, self.pos.y));
        env.win.draw_sprite(self.sprite)
    }

}
<|endoftext|>