<commit_before>extern crate loc;

extern crate clap;
extern crate deque;
extern crate itertools;
extern crate num_cpus;
extern crate walkdir;

use clap::{Arg, App, AppSettings};
use walkdir::WalkDir;

use std::collections::HashMap;
use std::collections::hash_map::Entry;
use std::thread;

use deque::{Stealer, Stolen};

use loc as c;

enum Work {
    File(String),
    Quit,
}

struct Worker {
    chan: Stealer<Work>,
}

// TODO(cgag): name this (lang, path, count) tuple concept and make it a struct
impl Worker {
    fn run(self) -> Vec<(c::Lang, String, c::Count)> {
        let mut v: Vec<(c::Lang, String, c::Count)> = vec![];
        loop {
            match self.chan.steal() {
                // What causes these?
                Stolen::Empty | Stolen::Abort => continue,
                Stolen::Data(Work::Quit) => break,
                Stolen::Data(Work::File(path)) => {
                    let lang = c::lang_from_ext(&path);
                    if lang != c::Lang::Unrecognized {
                        let count = c::count(&path);
                        v.push((lang, String::from(path), count));
                    }
                }
            };
        }
        v
    }
}

fn main() {

    let matches = App::new("count")
        .global_settings(&[AppSettings::ColoredHelp])
        .version("0.1")
        .author("Curtis Gagliardi <curtis@curtis.io>")
        .about("counts things quickly hopefully")
        // TODO(cgag): actually implement filtering
        // .arg(Arg::with_name("exclude")
        //     .required(false)
        //     .long("exclude")
        //     .value_name("FILES/DIRS")
        //     .takes_value(true)
        //     .value_delimiter(",")
        //     .help("comma separated list of files/directories to ignore"))
        .arg(Arg::with_name("files")
             .required(false)
             .long("files")
             .takes_value(false)
             .help("Show stats for individual files"))
        .arg(Arg::with_name("sort")
            .required(false)
            .long("sort")
            .value_name("COLUMN")
            .takes_value(true)
            .help("Column to sort by"))
        .arg(Arg::with_name("target")
            .required(true)
            .help("File or directory to count"))
        .get_matches();

    let filepaths = matches.values_of("target").unwrap();
    let sort = matches.value_of("sort").unwrap_or("language");
    let by_file = matches.is_present("files");

    let threads = num_cpus::get();
    let mut workers = vec![];
    let (workq, stealer) = deque::new();
    for _ in 0..threads {
        let worker = Worker { chan: stealer.clone() };
        workers.push(thread::spawn(|| worker.run()));
    }

    for filepath in filepaths {
        for entry in WalkDir::new(filepath) {
            let entry = match entry {
                Ok(e) => e,
                Err(_) => {
                    continue;
                }
            };

            if entry.file_type().is_file() {
                let path = entry.path().to_str().unwrap();
                workq.push(Work::File(String::from(path)));
            }
        }
    }

    for _ in 0..workers.len() {
        workq.push(Work::Quit);
    }

    let mut counts: Vec<(c::Lang, String, c::Count)> = Vec::new();
    for worker in workers {
        counts.extend(worker.join().unwrap().iter().cloned())
    }

    let mut lang_counts_by_file: HashMap<c::Lang, Vec<(String, c::Count)>> = HashMap::new();
    for (lang, filepath, count) in counts {
        match lang_counts_by_file.entry(lang) {
            Entry::Occupied(mut lang_counts_by_file) => {
                lang_counts_by_file.get_mut().push((filepath, count))
            }
            Entry::Vacant(lang_counts_by_file) => {
                lang_counts_by_file.insert(vec![(filepath, count)]);
            }
        };
    }

    let linesep = "---------------------------------------------------------------------------------";

    if by_file {
        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Language",
                 "Files",
                 "Lines",
                 "Blank",
                 "Comment",
                 "Code");
        println!("{}", linesep);

        for (lang, count_vec) in lang_counts_by_file {
            let mut total = c::Count::default();
            for &(_, ref count) in &count_vec {
                total.merge(count);
            }
            println!("{}", linesep);
            println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                     // lang,
                     lang,
                     count_vec.len(),
                     total.lines,
                     total.blank,
                     total.comment,
                     total.code);
            println!("{}", lang);
            println!("{}", linesep);
            for (path, count) in count_vec {
                let mut path_tail = String::from(path);
                if path_tail.len() > 25 {
                    path_tail = path_tail.chars().skip(path_tail.len() - 25).collect::<String>();
                }
                println!("|{0: <25} {1: >12} {2: >12} {3: >12} {4: >12}",
                         path_tail,
                         count.lines,
                         count.blank,
                         count.comment,
                         count.code);
            }
        }
    } else {
        let mut lang_totals: HashMap<&c::Lang, c::LangTotal> = HashMap::new();
        for (lang, count_vec) in &lang_counts_by_file {
            let mut lang_total: c::Count = Default::default();
            for &(_, ref count) in count_vec {
                lang_total.merge(count);
            }
            lang_totals.insert(lang,
                               c::LangTotal {
                                   files: count_vec.len() as u32,
                                   count: lang_total,
                               });
        }

        let mut totals_by_lang = lang_totals.iter().collect::<Vec<(&&c::Lang, &c::LangTotal)>>();
        match sort {
            "language" => totals_by_lang.sort_by(|&(l1, _), &(l2, _)| l1.to_s().cmp(&l2.to_s())),
            "files" => totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.files.cmp(&c1.files)),
            "code" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.code.cmp(&c1.count.code))
            }
            "comment" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.comment.cmp(&c1.count.comment))
            }
            "blank" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.blank.cmp(&c1.count.blank))
            }
            "lines" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.lines.cmp(&c1.count.lines))
            }
            _ => {
                println!("invalid sort option {}, sorting by language", sort);
                totals_by_lang.sort_by(|&(l1, _), &(l2, _)| l1.to_s().cmp(&l2.to_s()))
            }
        }

        let mut totals = c::LangTotal {
            files: 0,
            count: Default::default(),
        };
        for &(_, total) in &totals_by_lang {
            totals.files += total.files;
            totals.count.code += total.count.code;
            totals.count.blank += total.count.blank;
            totals.count.comment += total.count.comment;
            totals.count.lines += total.count.lines;
        }

        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Language",
                 "Files",
                 "Lines",
                 "Blank",
                 "Comment",
                 "Code");
        println!("{}", linesep);

        for &(lang, total) in &totals_by_lang {
            println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                     lang,
                     total.files,
                     total.count.lines,
                     total.count.blank,
                     total.count.comment,
                     total.count.code);
        }

        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Total",
                 totals.files,
                 totals.count.lines,
                 totals.count.blank,
                 totals.count.comment,
                 totals.count.code);
        println!("{}", linesep);
    }
}
<commit_msg>add exluding with rust regexs, a bit hacky<commit_after>extern crate loc;

extern crate clap;
extern crate deque;
extern crate itertools;
extern crate num_cpus;
extern crate walkdir;
extern crate regex;

use clap::{Arg, App, AppSettings};
use walkdir::WalkDir;

use std::collections::HashMap;
use std::collections::hash_map::Entry;
use std::thread;

use deque::{Stealer, Stolen};
use regex::Regex;

use loc as c;

enum Work {
    File(String),
    Quit,
}

struct Worker {
    chan: Stealer<Work>,
}

// TODO(cgag): name this (lang, path, count) tuple concept and make it a struct
impl Worker {
    fn run(self) -> Vec<(c::Lang, String, c::Count)> {
        let mut v: Vec<(c::Lang, String, c::Count)> = vec![];
        loop {
            match self.chan.steal() {
                // What causes these?
                Stolen::Empty | Stolen::Abort => continue,
                Stolen::Data(Work::Quit) => break,
                Stolen::Data(Work::File(path)) => {
                    let lang = c::lang_from_ext(&path);
                    if lang != c::Lang::Unrecognized {
                        let count = c::count(&path);
                        v.push((lang, String::from(path), count));
                    }
                }
            };
        }
        v
    }
}

fn main() {

    let matches = App::new("count")
        .global_settings(&[AppSettings::ColoredHelp])
        .version("0.1")
        .author("Curtis Gagliardi <curtis@curtis.io>")
        .about("counts things quickly hopefully")
        // TODO(cgag): actually implement filtering
        .arg(Arg::with_name("exclude")
            .required(false)
            .long("exclude")
            .value_name("REGEX")
            .takes_value(true)
            .help("comma separated list of files/directories to ignore"))
        .arg(Arg::with_name("files")
             .required(false)
             .long("files")
             .takes_value(false)
             .help("Show stats for individual files"))
        .arg(Arg::with_name("sort")
            .required(false)
            .long("sort")
            .value_name("COLUMN")
            .takes_value(true)
            .help("Column to sort by"))
        .arg(Arg::with_name("target")
            .required(true)
            .help("File or directory to count"))
        .get_matches();

    let filepaths = matches.values_of("target").unwrap();
    let sort = matches.value_of("sort").unwrap_or("language");
    let by_file = matches.is_present("files");
    let exclude_regex = match matches.value_of("exclude") {
        Some(rx_str) => {
            match Regex::new(rx_str) {
                Ok(r) => Some(r),
                Err(e) => {
                    println!("e: {}", e);
                    std::process::exit(1);
                }
            }
        }
        None => None,
    };

    let threads = num_cpus::get();
    let mut workers = vec![];
    let (workq, stealer) = deque::new();
    for _ in 0..threads {
        let worker = Worker { chan: stealer.clone() };
        workers.push(thread::spawn(|| worker.run()));
    }

    for filepath in filepaths {
        if exclude_regex.is_some() {
            let ref r = &exclude_regex.clone().unwrap();
            for entry in WalkDir::new(filepath).into_iter().filter_map(|e| e.ok()) {
                if entry.file_type().is_file() {
                    let path = entry.path().to_str().unwrap();
                    if !r.is_match(path) {
                        workq.push(Work::File(String::from(path)));
                    }
                }
            }
        } else {
            for entry in WalkDir::new(filepath).into_iter().filter_map(|e| e.ok()) {
                if entry.file_type().is_file() {
                    let path = entry.path().to_str().unwrap();
                    workq.push(Work::File(String::from(path)));
                }
            }
        }
    }

    for _ in 0..workers.len() {
        workq.push(Work::Quit);
    }

    let mut counts: Vec<(c::Lang, String, c::Count)> = Vec::new();
    for worker in workers {
        counts.extend(worker.join().unwrap().iter().cloned())
    }

    let mut lang_counts_by_file: HashMap<c::Lang, Vec<(String, c::Count)>> = HashMap::new();
    for (lang, filepath, count) in counts {
        match lang_counts_by_file.entry(lang) {
            Entry::Occupied(mut lang_counts_by_file) => {
                lang_counts_by_file.get_mut().push((filepath, count))
            }
            Entry::Vacant(lang_counts_by_file) => {
                lang_counts_by_file.insert(vec![(filepath, count)]);
            }
        };
    }

    let linesep = "---------------------------------------------------------------------------------";

    if by_file {
        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Language",
                 "Files",
                 "Lines",
                 "Blank",
                 "Comment",
                 "Code");
        println!("{}", linesep);

        for (lang, count_vec) in lang_counts_by_file {
            let mut total = c::Count::default();
            for &(_, ref count) in &count_vec {
                total.merge(count);
            }
            println!("{}", linesep);
            println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                     // lang,
                     lang,
                     count_vec.len(),
                     total.lines,
                     total.blank,
                     total.comment,
                     total.code);
            println!("{}", lang);
            println!("{}", linesep);
            for (path, count) in count_vec {
                let mut path_tail = String::from(path);
                if path_tail.len() > 25 {
                    path_tail = path_tail.chars().skip(path_tail.len() - 25).collect::<String>();
                }
                println!("|{0: <25} {1: >12} {2: >12} {3: >12} {4: >12}",
                         path_tail,
                         count.lines,
                         count.blank,
                         count.comment,
                         count.code);
            }
        }
    } else {
        let mut lang_totals: HashMap<&c::Lang, c::LangTotal> = HashMap::new();
        for (lang, count_vec) in &lang_counts_by_file {
            let mut lang_total: c::Count = Default::default();
            for &(_, ref count) in count_vec {
                lang_total.merge(count);
            }
            lang_totals.insert(lang,
                               c::LangTotal {
                                   files: count_vec.len() as u32,
                                   count: lang_total,
                               });
        }

        let mut totals_by_lang = lang_totals.iter().collect::<Vec<(&&c::Lang, &c::LangTotal)>>();
        match sort {
            "language" => totals_by_lang.sort_by(|&(l1, _), &(l2, _)| l1.to_s().cmp(&l2.to_s())),
            "files" => totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.files.cmp(&c1.files)),
            "code" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.code.cmp(&c1.count.code))
            }
            "comment" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.comment.cmp(&c1.count.comment))
            }
            "blank" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.blank.cmp(&c1.count.blank))
            }
            "lines" => {
                totals_by_lang.sort_by(|&(_, c1), &(_, c2)| c2.count.lines.cmp(&c1.count.lines))
            }
            _ => {
                println!("invalid sort option {}, sorting by language", sort);
                totals_by_lang.sort_by(|&(l1, _), &(l2, _)| l1.to_s().cmp(&l2.to_s()))
            }
        }

        let mut totals = c::LangTotal {
            files: 0,
            count: Default::default(),
        };
        for &(_, total) in &totals_by_lang {
            totals.files += total.files;
            totals.count.code += total.count.code;
            totals.count.blank += total.count.blank;
            totals.count.comment += total.count.comment;
            totals.count.lines += total.count.lines;
        }

        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Language",
                 "Files",
                 "Lines",
                 "Blank",
                 "Comment",
                 "Code");
        println!("{}", linesep);

        for &(lang, total) in &totals_by_lang {
            println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                     lang,
                     total.files,
                     total.count.lines,
                     total.count.blank,
                     total.count.comment,
                     total.count.code);
        }

        println!("{}", linesep);
        println!(" {0: <18} {1: >8} {2: >12} {3: >12} {4: >12} {5: >12}",
                 "Total",
                 totals.files,
                 totals.count.lines,
                 totals.count.blank,
                 totals.count.comment,
                 totals.count.code);
        println!("{}", linesep);
    }
}
<|endoftext|>


<commit_before>extern crate ppbert;
#[macro_use] extern crate clap;

use std::io::{self, Read};
use std::fs;
use std::process::exit;
use std::time::Instant;

use clap::{Arg, App};

use ppbert::bertterm::BertTerm;
use ppbert::error::Result;
use ppbert::parser;

const DEFAULT_INDENT_WIDTH: &str = "2";
const DEFAULT_MAX_TERMS_PER_LINE: &str = "5";
const PROG_NAME: &str = "ppbert";

fn main() {
    let matches = App::new(PROG_NAME)
        .version(crate_version!())
        .author("Vincent Foley")
        .about("Pretty print structure encoded in Erlang's External Term Format")
        .arg(Arg::with_name("input_files")
             .value_name("FILES")
             .multiple(true))
        .arg(Arg::with_name("indent_width")
             .help("Indents with <num> spaces")
             .value_name("num")
             .short("i")
             .long("indent-width")
             .default_value(DEFAULT_INDENT_WIDTH)
             .takes_value(true))
        .arg(Arg::with_name("max_per_line")
             .help("Prints at most <num> basic terms per line")
             .value_name("num")
             .short("m")
             .long("max-terms-per-line")
             .default_value(DEFAULT_MAX_TERMS_PER_LINE)
             .takes_value(true))
        .arg(Arg::with_name("verbose")
             .help("Enables verbose mode")
             .short("v")
             .long("verbose"))
        .arg(Arg::with_name("parse")
             .help("Parses the input, doesn't pretty print it")
             .short("p")
             .long("parse"))
        .arg(Arg::with_name("bert2")
             .help("Parses .bert2 files")
             .conflicts_with("disk_log")
             .short("2")
             .long("bert2"))
        .arg(Arg::with_name("disk_log")
             .help("Parses disk_log files")
             .conflicts_with("bert2")
             .short("d")
             .long("disk-log"))
        .arg(Arg::with_name("json")
             .help("Outputs in JSON")
             .short("j")
             .long("json"))
        .arg(Arg::with_name("transform-proplists")
             .help("Transforms proplists into JSON objects (only valid with --json)")
             .long("transform-proplists"))
        .get_matches();

    let files: Vec<&str> = match matches.values_of("input_files") {
        Some(files) => files.collect(),
        None => vec!["-"]
    };
    let indent_level = value_t!(matches, "indent_width", usize).unwrap();
    let max_per_line = value_t!(matches, "max_per_line", usize).unwrap();
    let verbose = matches.is_present("verbose");
    let parse_only = matches.is_present("parse");
    let transform_proplists = matches.is_present("transform-proplists");

    let parse_fn =
        if matches.is_present("bert2") {
            parse_bert2
        } else if matches.is_present("disk_log") {
            parse_disk_log
        } else {
            parse_bert1
        };
    let output_fn =
        if matches.is_present("json") {
            if transform_proplists {
                pp_json_proplist
            } else {
                pp_json
            }
        } else {
            if transform_proplists {
                eprintln!("{}: warning: --transform-proplists is only valid with the --json flag",
                          PROG_NAME);
            }
            pp_bert
        };

    let mut return_code = 0;
    for file in files {
        let res = handle_file(file, parse_only, verbose,
                              indent_level, max_per_line,
                              parse_fn, output_fn);
        match res {
            Ok(()) => (),
            Err(e) => {
                return_code = 1;
                eprintln!("{}: {}: {}", PROG_NAME, file, e);
            }
        }
    }
    exit(return_code);
}

fn handle_file<T>(
    file: &str,
    parse_only: bool,
    verbose: bool,
    indent: usize,
    terms_per_line: usize,
    parse_fn: fn(Vec<u8>) -> Result<T>,
    pp_fn: fn(T, usize, usize) -> ()
) -> Result<()> {

    // Read file or stdin into buffer
    let now = Instant::now();
    let buf = if file == "-" {
        let stdin = io::stdin();
        let mut stdin = stdin.lock();
        let mut buf: Vec<u8> = Vec::with_capacity(4096);
        stdin.read_to_end(&mut buf)?;
        buf
    } else {
        fs::read(file)?
    };
    let dur = now.elapsed();
    if verbose {
        eprintln!("{}: read time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    // Parse input
    let now = Instant::now();
    let parse_output = parse_fn(buf)?;
    let dur = now.elapsed();

    if verbose {
        eprintln!("{}: parse time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    // Early exit if parse-only
    if parse_only {
        return Ok(());
    }

    // Pretty print
    let now = Instant::now();
    pp_fn(parse_output, indent, terms_per_line);
    let dur = now.elapsed();

    if verbose {
        eprintln!("{}: print time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    return Ok(());
}

fn parse_bert1(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    let term = parser.parse()?;
    return Ok(vec![term]);
}

fn parse_bert2(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    return parser.parse_bert2();
}

fn parse_disk_log(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    return parser.parse_disk_log();
}

/// Outputs a vector of BertTerms to stdout.
fn pp_bert(terms: Vec<BertTerm>, indent_width: usize, terms_per_line: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_erlang(&mut stdout, indent_width, terms_per_line);
        println!(""); // newline
    }
}

/// Outputs a BertTerm as JSON to stdout.
fn pp_json(terms: Vec<BertTerm>, _: usize, _: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_json(&mut stdout, false);
        println!(""); // newline
    }
}

/// Outputs a BertTerm as JSON to stdout;
/// Erlang proplists are converted to JSON objects.
fn pp_json_proplist(terms: Vec<BertTerm>, _: usize, _: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_json(&mut stdout, true);
        println!(""); // newline
    }
}
<commit_msg>Make handling of output_fn clearer<commit_after>extern crate ppbert;
#[macro_use] extern crate clap;

use std::io::{self, Read};
use std::fs;
use std::process::exit;
use std::time::Instant;

use clap::{Arg, App};

use ppbert::bertterm::BertTerm;
use ppbert::error::Result;
use ppbert::parser;

const DEFAULT_INDENT_WIDTH: &str = "2";
const DEFAULT_MAX_TERMS_PER_LINE: &str = "5";
const PROG_NAME: &str = "ppbert";

fn main() {
    let matches = App::new(PROG_NAME)
        .version(crate_version!())
        .author("Vincent Foley")
        .about("Pretty print structure encoded in Erlang's External Term Format")
        .arg(Arg::with_name("input_files")
             .value_name("FILES")
             .multiple(true))
        .arg(Arg::with_name("indent_width")
             .help("Indents with <num> spaces")
             .value_name("num")
             .short("i")
             .long("indent-width")
             .default_value(DEFAULT_INDENT_WIDTH)
             .takes_value(true))
        .arg(Arg::with_name("max_per_line")
             .help("Prints at most <num> basic terms per line")
             .value_name("num")
             .short("m")
             .long("max-terms-per-line")
             .default_value(DEFAULT_MAX_TERMS_PER_LINE)
             .takes_value(true))
        .arg(Arg::with_name("verbose")
             .help("Enables verbose mode")
             .short("v")
             .long("verbose"))
        .arg(Arg::with_name("parse")
             .help("Parses the input, doesn't pretty print it")
             .short("p")
             .long("parse"))
        .arg(Arg::with_name("bert2")
             .help("Parses .bert2 files")
             .conflicts_with("disk_log")
             .short("2")
             .long("bert2"))
        .arg(Arg::with_name("disk_log")
             .help("Parses disk_log files")
             .conflicts_with("bert2")
             .short("d")
             .long("disk-log"))
        .arg(Arg::with_name("json")
             .help("Outputs in JSON")
             .short("j")
             .long("json"))
        .arg(Arg::with_name("transform-proplists")
             .help("Transforms proplists into JSON objects (only valid with --json)")
             .long("transform-proplists"))
        .get_matches();

    let files: Vec<&str> = match matches.values_of("input_files") {
        Some(files) => files.collect(),
        None => vec!["-"]
    };
    let indent_level = value_t!(matches, "indent_width", usize).unwrap();
    let max_per_line = value_t!(matches, "max_per_line", usize).unwrap();
    let verbose = matches.is_present("verbose");
    let parse_only = matches.is_present("parse");
    let json = matches.is_present("json");
    let transform_proplists = matches.is_present("transform-proplists");

    let parse_fn =
        if matches.is_present("bert2") {
            parse_bert2
        } else if matches.is_present("disk_log") {
            parse_disk_log
        } else {
            parse_bert1
        };
    let output_fn = match (json, transform_proplists) {
        (true, false)  => pp_json,
        (true, true)   => pp_json_proplist,
        (false, false) => pp_bert,
        (false, true)  => {
            eprintln!("{}: --transform-proplists is only valid with the --json flag", PROG_NAME);
            pp_bert
        }
    };

    let mut return_code = 0;
    for file in files {
        let res = handle_file(file, parse_only, verbose,
                              indent_level, max_per_line,
                              parse_fn, output_fn);
        match res {
            Ok(()) => (),
            Err(e) => {
                return_code = 1;
                eprintln!("{}: {}: {}", PROG_NAME, file, e);
            }
        }
    }
    exit(return_code);
}

fn handle_file<T>(
    file: &str,
    parse_only: bool,
    verbose: bool,
    indent: usize,
    terms_per_line: usize,
    parse_fn: fn(Vec<u8>) -> Result<T>,
    pp_fn: fn(T, usize, usize) -> ()
) -> Result<()> {

    // Read file or stdin into buffer
    let now = Instant::now();
    let buf = if file == "-" {
        let stdin = io::stdin();
        let mut stdin = stdin.lock();
        let mut buf: Vec<u8> = Vec::with_capacity(4096);
        stdin.read_to_end(&mut buf)?;
        buf
    } else {
        fs::read(file)?
    };
    let dur = now.elapsed();
    if verbose {
        eprintln!("{}: read time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    // Parse input
    let now = Instant::now();
    let parse_output = parse_fn(buf)?;
    let dur = now.elapsed();

    if verbose {
        eprintln!("{}: parse time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    // Early exit if parse-only
    if parse_only {
        return Ok(());
    }

    // Pretty print
    let now = Instant::now();
    pp_fn(parse_output, indent, terms_per_line);
    let dur = now.elapsed();

    if verbose {
        eprintln!("{}: print time: {}.{:09}",
                  PROG_NAME, dur.as_secs(), dur.subsec_nanos());
    }

    return Ok(());
}

fn parse_bert1(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    let term = parser.parse()?;
    return Ok(vec![term]);
}

fn parse_bert2(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    return parser.parse_bert2();
}

fn parse_disk_log(buf: Vec<u8>) -> Result<Vec<BertTerm>> {
    let mut parser = parser::Parser::new(buf);
    return parser.parse_disk_log();
}

/// Outputs a vector of BertTerms to stdout.
fn pp_bert(terms: Vec<BertTerm>, indent_width: usize, terms_per_line: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_erlang(&mut stdout, indent_width, terms_per_line);
        println!(""); // newline
    }
}

/// Outputs a BertTerm as JSON to stdout.
fn pp_json(terms: Vec<BertTerm>, _: usize, _: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_json(&mut stdout, false);
        println!(""); // newline
    }
}

/// Outputs a BertTerm as JSON to stdout;
/// Erlang proplists are converted to JSON objects.
fn pp_json_proplist(terms: Vec<BertTerm>, _: usize, _: usize) {
    let stdout = io::stdout();
    let mut stdout = stdout.lock();
    for t in terms {
        let _ = t.write_as_json(&mut stdout, true);
        println!(""); // newline
    }
}
<|endoftext|>


<commit_before>extern crate actix_web;
extern crate cookie;
extern crate get_if_addrs;
extern crate hyper;
extern crate itertools;
extern crate json;
extern crate log4rs;
#[cfg(not(feature = "lambda"))]
#[macro_use]
extern crate log;
extern crate mustache;
extern crate reqwest_mock;
#[macro_use]
extern crate serde_derive;
extern crate time;
extern crate url;
#[macro_use]
extern crate lazy_static;
#[macro_use]
extern crate serde_json;

#[cfg(test)]
extern crate crossbeam;
#[cfg(test)]
extern crate env_logger;

#[cfg(feature = "lambda")]
#[macro_use]
extern crate lambda_http;
#[cfg(feature = "lambda")]
use lambda_http::RequestExt;

use actix_web::{http::Method, server, App, HttpRequest, HttpResponse};
#[cfg(not(feature = "lambda"))]
use std::env;

mod arrivals;
mod common;
mod favourite;
mod id;
mod nearby;
mod search;

fn root_handler(request: HttpRequest) -> HttpResponse {
    let data = common::mustache_favourites(&request);
    common::render_to_response("resources/templates/root.mustache", &data)
}

fn app() -> App {
    return App::new()
        .route("/", Method::GET, root_handler)
        .route("/search", Method::GET, search::search_handler)
        .route("/id/{id}", Method::GET, id::id_handler)
        .route("/nearby", Method::GET, nearby::nearby_handler)
        .route("/favourites", Method::GET, favourite::list_favourites)
        .route("/favourites", Method::POST, favourite::add_favourite)
        .route("/favourite-remove", Method::POST, favourite::remove_favourite)
        .route("/arrivals/{stopid}", Method::GET, arrivals::arrivals_handler);
}

#[cfg(not(feature = "lambda"))]
fn main() {
    log4rs::init_file("log.yaml", Default::default()).unwrap();
    let port = env::var("PORT")
        .unwrap_or("8000".to_string())
        .parse::<u16>()
        .unwrap();
    let mut server = server::new(|| app().finish());
    for iface in get_if_addrs::get_if_addrs().unwrap() {
        let ip = iface.ip();
        info!("Listening on {}:{} for {}", ip, port, iface.name);
        server = server.bind((ip, port)).unwrap();
    }
    server.run();
}

#[cfg(feature = "lambda")]
fn main() {
    let server = server::new(|| app().finish()).bind("0.0.0.0:0").unwrap();
    let addrs = server.addrs();
    let addr = addrs.first().clone();
    lambda!(|request: lambda_http::Request, _context| {
        println!("Req to inner: {:?}", request);
        Ok(format!(
            "hello {}",
            request
                .query_string_parameters()
                .get("name")
                .unwrap_or_else(|| "stranger")
        ))
    });
}

#[cfg(test)]
mod tests {
    use super::{app, common, main};
    use actix_web::{http, server, test, App, HttpMessage, HttpRequest, HttpResponse, State};
    use crossbeam::channel::unbounded;
    use crossbeam::{Receiver, Sender};
    use std::{env, thread};

    #[derive(Debug, Clone)]
    struct AppState {
        req: Receiver<(i32, serde_json::Value)>,
        res: Sender<String>,
    }

    fn test_app(req: Receiver<(i32, serde_json::Value)>, res: Sender<String>) -> App<AppState> {
        App::with_state(AppState { req, res })
            .resource("/2018-06-01/runtime/invocation/1234/response", |r| {
                r.method(http::Method::POST)
                    .with(|(body, state): (String, State<AppState>)| {
                        println!("Response body: {}", body);
                        state.res.send(body).unwrap();
                        HttpResponse::Ok()
                    })
            })
            .resource("/2018-06-01/runtime/invocation/next", |r| {
                r.method(http::Method::GET).with(|state: State<AppState>| {
                    let (id, body) = match state.req.clone().recv() {
                        Ok(val) => val,
                        Err(err) => {
                            return HttpResponse::InternalServerError().body(format!("{}", err));
                        }
                    };
                    println!("Got req: {}", id);
                    HttpResponse::Ok()
                        .header("Lambda-Runtime-Aws-Request-Id", id.to_string())
                        .header("Lambda-Runtime-Invoked-Function-Arn", "an-arn")
                        .header("Lambda-Runtime-Deadline-Ms", "1000")
                        .json(body)
                })
            })
            .default_resource(|r| {
                r.route().with(|(r, body): (HttpRequest<AppState>, String)| {
                    println!("{:?}", r);
                    println!("Body: {}", body);
                    HttpResponse::NotFound()
                })
            })
    }

    #[cfg(feature = "lambda")]
    #[test]
    fn lambda_test() {
        let (req_send, req_recv) = unbounded();
        let (res_send, res_recv) = unbounded();
        req_send.send((1234, json!({
    "requestContext": {
        "elb": {
            "targetGroupArn": "arn:aws:elasticloadbalancing:region:123456789012:targetgroup/my-target-group/6d0ecf831eec9f09"
        }
    },
    "httpMethod": "GET",
    "path": "/",
    "queryStringParameters": {},
    "headers": {
        "accept": "text/html,application/xhtml+xml",
        "accept-language": "en-US,en;q=0.8",
        "content-type": "text/plain",
        "cookie": "cookies",
        "host": "lambda-846800462-us-east-2.elb.amazonaws.com",
        "user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6)",
        "x-amzn-trace-id": "Root=1-5bdb40ca-556d8b0c50dc66f0511bf520",
        "x-forwarded-for": "72.21.198.66",
        "x-forwarded-port": "443",
        "x-forwarded-proto": "https"
    },
    "isBase64Encoded": false,
    "body": "request_body"
}))).unwrap();
        env_logger::init();
        thread::spawn(move || {
            server::new(move || test_app(req_recv.clone(), res_send.clone()).finish())
                .bind("0.0.0.0:3456")
                .unwrap()
                .run()
        });
        env::set_var("AWS_LAMBDA_FUNCTION_NAME", "foo");
        env::set_var("AWS_LAMBDA_FUNCTION_VERSION", "1");
        env::set_var("AWS_LAMBDA_LOG_STREAM_NAME", "log");
        env::set_var("AWS_LAMBDA_LOG_GROUP_NAME", "lg");
        env::set_var("AWS_LAMBDA_FUNCTION_MEMORY_SIZE", "128");
        env::set_var("AWS_LAMBDA_RUNTIME_API", "127.0.0.1:3456");
        thread::spawn(|| main());
        println!("Response to main: {}", res_recv.recv().unwrap());
    }

    #[test]
    fn simple_search() {
        let mut srv = test::TestServer::with_factory(app);
        common::set_client(common::ClientType::TESTING);
        let request = srv
            .client(http::Method::GET, "/search?query=foo")
            .finish()
            .unwrap();
        let response = srv.execute(request.send()).unwrap();
        let body: String = String::from_utf8(srv.execute(response.body()).unwrap().to_vec()).unwrap();
        assert!(body.find("<title>Search: foo</title>").is_some(), body);
        assert!(response.status().is_success(), response.status());
    }
}
<commit_msg>Shutdown actix after we're done<commit_after>extern crate actix_web;
extern crate cookie;
extern crate get_if_addrs;
extern crate hyper;
extern crate itertools;
extern crate json;
extern crate log4rs;
#[cfg(not(feature = "lambda"))]
#[macro_use]
extern crate log;
extern crate mustache;
extern crate reqwest_mock;
#[macro_use]
extern crate serde_derive;
extern crate time;
extern crate url;
#[macro_use]
extern crate lazy_static;
#[macro_use]
extern crate serde_json;

#[cfg(test)]
extern crate crossbeam;
#[cfg(test)]
extern crate env_logger;

#[cfg(feature = "lambda")]
#[macro_use]
extern crate lambda_http;
#[cfg(feature = "lambda")]
use lambda_http::RequestExt;

use actix_web::{http::Method, server, App, HttpRequest, HttpResponse};
#[cfg(not(feature = "lambda"))]
use std::env;

mod arrivals;
mod common;
mod favourite;
mod id;
mod nearby;
mod search;

fn root_handler(request: HttpRequest) -> HttpResponse {
    let data = common::mustache_favourites(&request);
    common::render_to_response("resources/templates/root.mustache", &data)
}

fn app() -> App {
    return App::new()
        .route("/", Method::GET, root_handler)
        .route("/search", Method::GET, search::search_handler)
        .route("/id/{id}", Method::GET, id::id_handler)
        .route("/nearby", Method::GET, nearby::nearby_handler)
        .route("/favourites", Method::GET, favourite::list_favourites)
        .route("/favourites", Method::POST, favourite::add_favourite)
        .route("/favourite-remove", Method::POST, favourite::remove_favourite)
        .route("/arrivals/{stopid}", Method::GET, arrivals::arrivals_handler);
}

#[cfg(not(feature = "lambda"))]
fn main() {
    log4rs::init_file("log.yaml", Default::default()).unwrap();
    let port = env::var("PORT")
        .unwrap_or("8000".to_string())
        .parse::<u16>()
        .unwrap();
    let mut server = server::new(|| app().finish());
    for iface in get_if_addrs::get_if_addrs().unwrap() {
        let ip = iface.ip();
        info!("Listening on {}:{} for {}", ip, port, iface.name);
        server = server.bind((ip, port)).unwrap();
    }
    server.run();
}

#[cfg(feature = "lambda")]
fn main() {
    let server = server::new(|| app().finish()).bind("0.0.0.0:0").unwrap();
    let addrs = server.addrs();
    let addr = addrs.first().clone();
    lambda!(|request: lambda_http::Request, _context| {
        println!("Req to inner: {:?}", request);
        Ok(format!(
            "hello {}",
            request
                .query_string_parameters()
                .get("name")
                .unwrap_or_else(|| "stranger")
        ))
    });
}

#[cfg(test)]
mod tests {
    use super::{app, common, main};
    use actix_web::actix::System;
    use actix_web::{http, server, test, App, HttpMessage, HttpRequest, HttpResponse, State};
    use crossbeam::channel::unbounded;
    use crossbeam::{Receiver, Sender};
    use std::{env, thread};

    #[derive(Debug, Clone)]
    struct AppState {
        req: Receiver<Result<(i32, serde_json::Value), ()>>,
        res: Sender<String>,
    }

    fn test_app(req: Receiver<Result<(i32, serde_json::Value), ()>>, res: Sender<String>) -> App<AppState> {
        App::with_state(AppState { req, res })
            .resource("/2018-06-01/runtime/invocation/1234/response", |r| {
                r.method(http::Method::POST)
                    .with(|(body, state): (String, State<AppState>)| {
                        println!("Response body: {}", body);
                        state.res.send(body).unwrap();
                        HttpResponse::Ok()
                    })
            })
            .resource("/2018-06-01/runtime/invocation/next", |r| {
                r.method(http::Method::GET).with(|state: State<AppState>| {
                    let (id, body) = match state.req.clone().recv().unwrap() {
                        Ok(val) => val,
                        Err(_) => {
                            System::current().stop();
                            thread::park();
                            unimplemented!();
                        }
                    };
                    println!("Got req: {}", id);
                    HttpResponse::Ok()
                        .header("Lambda-Runtime-Aws-Request-Id", id.to_string())
                        .header("Lambda-Runtime-Invoked-Function-Arn", "an-arn")
                        .header("Lambda-Runtime-Deadline-Ms", "1000")
                        .json(body)
                })
            })
            .default_resource(|r| {
                r.route().with(|(r, body): (HttpRequest<AppState>, String)| {
                    println!("{:?}", r);
                    println!("Body: {}", body);
                    HttpResponse::NotFound()
                })
            })
    }

    #[cfg(feature = "lambda")]
    #[test]
    fn lambda_test() {
        let (req_send, req_recv) = unbounded();
        let (res_send, res_recv) = unbounded();
        req_send.send(Ok((1234, json!({
    "requestContext": {
        "elb": {
            "targetGroupArn": "arn:aws:elasticloadbalancing:region:123456789012:targetgroup/my-target-group/6d0ecf831eec9f09"
        }
    },
    "httpMethod": "GET",
    "path": "/",
    "queryStringParameters": {},
    "headers": {
        "accept": "text/html,application/xhtml+xml",
        "accept-language": "en-US,en;q=0.8",
        "content-type": "text/plain",
        "cookie": "cookies",
        "host": "lambda-846800462-us-east-2.elb.amazonaws.com",
        "user-agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_6)",
        "x-amzn-trace-id": "Root=1-5bdb40ca-556d8b0c50dc66f0511bf520",
        "x-forwarded-for": "72.21.198.66",
        "x-forwarded-port": "443",
        "x-forwarded-proto": "https"
    },
    "isBase64Encoded": false,
    "body": "request_body"
})))).unwrap();
        env_logger::init();
        thread::spawn(move || {
            server::new(move || test_app(req_recv.clone(), res_send.clone()).finish())
                .bind("0.0.0.0:3456")
                .unwrap()
                .run()
        });
        env::set_var("AWS_LAMBDA_FUNCTION_NAME", "foo");
        env::set_var("AWS_LAMBDA_FUNCTION_VERSION", "1");
        env::set_var("AWS_LAMBDA_LOG_STREAM_NAME", "log");
        env::set_var("AWS_LAMBDA_LOG_GROUP_NAME", "lg");
        env::set_var("AWS_LAMBDA_FUNCTION_MEMORY_SIZE", "128");
        env::set_var("AWS_LAMBDA_RUNTIME_API", "127.0.0.1:3456");
        thread::spawn(|| main());
        println!("Response to main: {}", res_recv.recv().unwrap());
        // shutdown
        req_send.send(Err(())).unwrap();
    }

    #[test]
    fn simple_search() {
        let mut srv = test::TestServer::with_factory(app);
        common::set_client(common::ClientType::TESTING);
        let request = srv
            .client(http::Method::GET, "/search?query=foo")
            .finish()
            .unwrap();
        let response = srv.execute(request.send()).unwrap();
        let body: String = String::from_utf8(srv.execute(response.body()).unwrap().to_vec()).unwrap();
        assert!(body.find("<title>Search: foo</title>").is_some(), body);
        assert!(response.status().is_success(), response.status());
    }
}
<|endoftext|>


<commit_before>// Copyright (c) 2013-2015 Sandstorm Development Group, Inc. and contributors
// Licensed under the MIT License:
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.

use {Word, Result};
use private::layout::{StructReader, StructBuilder, StructSize, PointerBuilder, PointerReader};

pub trait FromStructReader<'a> {
    fn new(reader : StructReader<'a>) -> Self;
}

pub trait HasStructSize {
    fn struct_size() -> StructSize;
}

pub trait FromStructBuilder<'a> {
    fn new(structBuilder : StructBuilder<'a>) -> Self;
}

pub trait FromPointerReader<'a> {
    fn get_from_pointer(reader : &PointerReader<'a>) -> Result<Self>;
}

pub trait Owned<'a> {
    type Reader: FromPointerReader<'a>;
    type Builder: FromPointerBuilder<'a>;
    type Pipeline;
}

pub trait OwnedStruct<'a> {
   type Reader: FromStructReader<'a>;
   type Builder: FromStructBuilder<'a> + HasStructSize;
   type Pipeline;
}

pub trait FromPointerReaderRefDefault<'a> {
    fn get_from_pointer(reader : &PointerReader<'a>, default_value : *const Word) -> Self;
}

pub trait FromPointerBuilder<'a> {
    fn init_pointer(PointerBuilder<'a>, u32) -> Self;
    fn get_from_pointer(builder : PointerBuilder<'a>) -> Result<Self>;
}

pub trait FromPointerBuilderRefDefault<'a> {
    fn get_from_pointer(builder : PointerBuilder<'a>, default_value : *const Word) -> Self;
}

pub trait SetPointerBuilder<To> {
    fn set_pointer_builder<'a>(PointerBuilder<'a>, Self) -> Result<()>;
}

pub trait HasTypeId {
    fn type_id() -> u64;
}

pub trait ToU16 {
    fn to_u16(self) -> u16;
}

pub trait FromU16 {
    fn from_u16(value : u16) -> ::std::result::Result<Self, ::NotInSchema>;
}

pub trait IndexMove<I, T> {
    fn index_move(&self, index : I) -> T;
}

pub struct ListIter<T, U> {
    marker : ::std::marker::PhantomData<U>,
    list : T,
    index : u32,
    size : u32,
}

impl <T, U> ListIter<T, U> {
    pub fn new(list : T, size : u32) -> ListIter<T, U> {
        ListIter { list : list, index : 0, size : size, marker : ::std::marker::PhantomData }
    }
}

impl <U, T : IndexMove<u32, U>> ::std::iter::Iterator for ListIter<T, U> {
    type Item = U;
    fn next(&mut self) -> ::std::option::Option<U> {
        if self.index < self.size {
            let result = self.list.index_move(self.index);
            self.index += 1;
            return Some(result);
        } else {
            return None;
        }
    }
}
<commit_msg>Some documentation on Owned.<commit_after>// Copyright (c) 2013-2015 Sandstorm Development Group, Inc. and contributors
// Licensed under the MIT License:
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.

use {Word, Result};
use private::layout::{StructReader, StructBuilder, StructSize, PointerBuilder, PointerReader};

pub trait FromStructReader<'a> {
    fn new(reader : StructReader<'a>) -> Self;
}

pub trait HasStructSize {
    fn struct_size() -> StructSize;
}

pub trait FromStructBuilder<'a> {
    fn new(structBuilder : StructBuilder<'a>) -> Self;
}

pub trait FromPointerReader<'a> {
    fn get_from_pointer(reader : &PointerReader<'a>) -> Result<Self>;
}

/// Associated types hackery that allows us to reason about Cap'n Proto types
/// without needing to give them a lifetime `'a`.
///
/// If `Foo` is a Cap'n Proto struct and `Bar` is a Rust-native struct, then
/// `foo::Reader<'a>` is to `foo::Owned` as `&'a Bar` is to `Bar`, and
/// `foo::Builder<'a>` is to `foo::Owned` as `&'a mut Bar` is to `Bar`.
/// The relationship is formalized by an `impl <'a> capnp::traits::Owned<'a> for foo::Owned`.
/// Because Cap'n Proto struct layout differs from Rust struct layout,
/// `foo::Owned` cannot be an inhabited type; it is useful nonetheless
/// as a type parameter, e.g. for a generic container that owns a Cap'n Proto message
/// of type `T: for<'a> capnp::traits::Owned<'a>`.
pub trait Owned<'a> {
    type Reader: FromPointerReader<'a>;
    type Builder: FromPointerBuilder<'a>;
    type Pipeline;
}

pub trait OwnedStruct<'a> {
   type Reader: FromStructReader<'a>;
   type Builder: FromStructBuilder<'a> + HasStructSize;
   type Pipeline;
}

pub trait FromPointerReaderRefDefault<'a> {
    fn get_from_pointer(reader : &PointerReader<'a>, default_value : *const Word) -> Self;
}

pub trait FromPointerBuilder<'a> {
    fn init_pointer(PointerBuilder<'a>, u32) -> Self;
    fn get_from_pointer(builder : PointerBuilder<'a>) -> Result<Self>;
}

pub trait FromPointerBuilderRefDefault<'a> {
    fn get_from_pointer(builder : PointerBuilder<'a>, default_value : *const Word) -> Self;
}

pub trait SetPointerBuilder<To> {
    fn set_pointer_builder<'a>(PointerBuilder<'a>, Self) -> Result<()>;
}

pub trait HasTypeId {
    fn type_id() -> u64;
}

pub trait ToU16 {
    fn to_u16(self) -> u16;
}

pub trait FromU16 {
    fn from_u16(value : u16) -> ::std::result::Result<Self, ::NotInSchema>;
}

pub trait IndexMove<I, T> {
    fn index_move(&self, index : I) -> T;
}

pub struct ListIter<T, U> {
    marker : ::std::marker::PhantomData<U>,
    list : T,
    index : u32,
    size : u32,
}

impl <T, U> ListIter<T, U> {
    pub fn new(list : T, size : u32) -> ListIter<T, U> {
        ListIter { list : list, index : 0, size : size, marker : ::std::marker::PhantomData }
    }
}

impl <U, T : IndexMove<u32, U>> ::std::iter::Iterator for ListIter<T, U> {
    type Item = U;
    fn next(&mut self) -> ::std::option::Option<U> {
        if self.index < self.size {
            let result = self.list.index_move(self.index);
            self.index += 1;
            return Some(result);
        } else {
            return None;
        }
    }
}
<|endoftext|>


<commit_before>#![feature(plugin)]
#![plugin(clippy)]
// #![deny(clippy_pedantic)]
extern crate termion;
extern crate serde_json;
#[macro_use]
extern crate log;
extern crate log4rs;

mod core;

use termion::{clear, cursor};
use termion::raw::IntoRawMode;
use termion::input::TermRead;
use std::io::{stdout, Write, stdin};
use std::sync::mpsc;
use std::{thread, time};
use core::Core;

struct Screen {
    stdout: termion::raw::RawTerminal<std::io::Stdout>,
    size: (u16, u16),
}

impl Screen {

    fn new() -> Screen {
        let mut stdout = stdout().into_raw_mode().unwrap();
        write!(stdout, "{}", clear::All).unwrap();
        stdout.flush().unwrap();
        Screen {
            size: termion::terminal_size().unwrap(),
            stdout: stdout,
        }
    }

    fn redraw(&mut self, lines: Vec<String>) {
        write!(self.stdout, "{}", termion::clear::All).unwrap();
        write!(self.stdout, "{}", cursor::Up(self.size.1)).unwrap();
        for (_, line) in lines.into_iter().enumerate() {
            self.stdout.write_all(line.as_bytes()).unwrap();
            write!(self.stdout, "{}", cursor::Left(self.size.0)).unwrap();
        }
        self.stdout.flush();
    }

}

fn update_screen(core: &mut Core, screen: &mut Screen) {
    if let Ok(update_msg) = core.update_rx.try_recv() {
        let update = update_msg.as_object().unwrap().get("update").unwrap().as_object().unwrap();
        let lines = update.get("lines").unwrap().as_array().unwrap().into_iter().map(|line| line.as_array().unwrap()[0].as_str().unwrap().to_string()).collect();
        screen.redraw(lines);
    } else {
        thread::sleep_ms(10);
    }
}

pub struct Input {
    tx: mpsc::Sender<termion::event::Event>,
    rx: mpsc::Receiver<termion::event::Event>,
}

impl Input {
    pub fn new() -> Input {
        let (tx, rx) = mpsc::channel();
        Input {
            tx: tx,
            rx: rx,
        }
    }

    pub fn run(&mut self) {
        let tx = self.tx.clone();
        thread::spawn(move || {
            for event_res in stdin().events() {
                match event_res {
                    Ok(event) => {
                        info!("event: {:?}", event);
                        tx.send(event).unwrap();
                    },
                    Err(err) => {
                        error!("{:?}", err);
                    }
                }
            }
        });
    }
}

fn main() {
    log4rs::init_file("log_config.yaml", Default::default()).unwrap();
    let mut core = Core::new("../xi-editor/rust/target/debug/xi-core");
    let mut screen = Screen::new();
    let mut input = Input::new();
    input.run();
    loop {
        if let Ok(event) = input.rx.try_recv() {
            match event {
                termion::event::Event::Key(key) => {
                    match key {
                        termion::event::Key::Char(c) => {
                            core.char(c);
                        },
                        termion::event::Key::Ctrl(c) => {
                            if c == 'c' {
                                info!("received ^C: exiting");
                                return;
                            }
                        },
                        _ => {
                            error!("unsupported key event");
                        }
                    }
                },
                termion::event::Event::Mouse(_) => {
                    error!("mouse events are not supported yet");
                }
                _ => {
                    error!("unsupported event");
                }
            }
        } else {
            update_screen(&mut core, &mut screen);
        }
    }
}
<commit_msg>deserialize updates properly<commit_after>#![feature(plugin)]
#![plugin(clippy)]
// #![deny(clippy_pedantic)]
extern crate termion;
extern crate serde_json;
#[macro_use]
extern crate log;
extern crate log4rs;

mod core;

use termion::{clear, cursor};
use termion::raw::IntoRawMode;
use termion::input::TermRead;
use std::io::{stdout, Write, stdin};
use std::sync::mpsc;
use std::{thread, time};
use core::Core;

struct Screen {
    stdout: termion::raw::RawTerminal<std::io::Stdout>,
    size: (u16, u16),
}

impl Screen {

    fn new() -> Screen {
        let mut stdout = stdout().into_raw_mode().unwrap();
        write!(stdout, "{}", clear::All).unwrap();
        stdout.flush().unwrap();
        Screen {
            size: termion::terminal_size().unwrap(),
            stdout: stdout,
        }
    }

    fn redraw(&mut self, lines: Vec<String>) {
        write!(self.stdout, "{}", termion::clear::All).unwrap();
        write!(self.stdout, "{}", cursor::Up(self.size.1)).unwrap();
        for (_, line) in lines.into_iter().enumerate() {
            self.stdout.write_all(line.as_bytes()).unwrap();
            write!(self.stdout, "{}", cursor::Left(self.size.0)).unwrap();
        }
        self.stdout.flush();
    }

struct Update {
    lines: Vec<Line>,
    height: u64,
    scroll_to: (u64, u64),
    first_line: u64
}

impl Update {
    fn from_value(value: &serde_json::Value) -> Update {
        let object = value.as_object().unwrap();
        let scroll_to = object.get("scrollto").unwrap().as_array().unwrap();
        let mut lines: Vec<Line> = vec![];
        for line in object.get("lines").unwrap().as_array().unwrap().iter() {
            lines.push(Line::from_value(line));
        }
        info!("{:?}", object);
        Update {
            height: object.get("height").unwrap().as_u64().unwrap(),
            first_line: object.get("first_line").unwrap().as_u64().unwrap(),
            lines: lines,
            scroll_to: (scroll_to[0].as_u64().unwrap(), scroll_to[1].as_u64().unwrap()),
        }
    }
}

struct Line {
    text: String,
    selection: Option<(u64, u64)>,
    cursor: Option<u64>,
}

impl Line {
    fn from_value(value: &serde_json::Value) -> Line {
        let line_arr = value.as_array().unwrap();
        let mut line = Line {
            text: line_arr[0].as_str().unwrap().to_string(),
            cursor: None,
            selection: None,
        };
        for annotation in line_arr.iter().skip(1).map(|a| a.as_array().unwrap()) {
            match annotation[0].as_str().unwrap() {
                "cursor" => {
                    line.cursor = Some(annotation[1].as_u64().unwrap());
                },
                "sel" => {
                    line.selection = Some((annotation[1].as_u64().unwrap(), annotation[2].as_u64().unwrap()));
                },
                _ => {
                    error!("unknown annotation");
                }
            }
        }
        line
    }
}

fn update_screen(core: &mut Core, screen: &mut Screen) {
    if let Ok(msg) = core.update_rx.try_recv() {
        let update = Update::from_value(msg.as_object().unwrap().get("update").unwrap());
        screen.redraw(&update);
    } else {
        thread::sleep_ms(10);
    }
}

pub struct Input {
    tx: mpsc::Sender<termion::event::Event>,
    rx: mpsc::Receiver<termion::event::Event>,
}

impl Input {
    pub fn new() -> Input {
        let (tx, rx) = mpsc::channel();
        Input {
            tx: tx,
            rx: rx,
        }
    }

    pub fn run(&mut self) {
        let tx = self.tx.clone();
        thread::spawn(move || {
            for event_res in stdin().events() {
                match event_res {
                    Ok(event) => {
                        info!("event: {:?}", event);
                        tx.send(event).unwrap();
                    },
                    Err(err) => {
                        error!("{:?}", err);
                    }
                }
            }
        });
    }
}

fn main() {
    log4rs::init_file("log_config.yaml", Default::default()).unwrap();
    let mut core = Core::new("../xi-editor/rust/target/debug/xi-core");
    let mut screen = Screen::new();
    let mut input = Input::new();
    input.run();
    loop {
        if let Ok(event) = input.rx.try_recv() {
            match event {
                termion::event::Event::Key(key) => {
                    match key {
                        termion::event::Key::Char(c) => {
                            core.char(c);
                        },
                        termion::event::Key::Ctrl(c) => {
                            if c == 'c' {
                                info!("received ^C: exiting");
                                return;
                            }
                        },
                        _ => {
                            error!("unsupported key event");
                        }
                    }
                },
                termion::event::Event::Mouse(_) => {
                    error!("mouse events are not supported yet");
                }
                _ => {
                    error!("unsupported event");
                }
            }
        } else {
            update_screen(&mut core, &mut screen);
        }
    }
}
<|endoftext|>


<commit_before>fn main() {
    let dow = ["Duinday", "Sitaday", "Wikiday", "Tuxday", "Gnuday", "Commonday"];
    let moy = ["Jabim", "Zodrak", "Trogool", "Yanar", "Shkumbe", "Habniah", "Skarl", "Mikon", "Pertunda", "Kib", "Broket"];
    let yoff: usize = 0;
    let dpm = 33;
    let dpw = dow.len();
    let mpy = moy.len();
    let mut moff = yoff;

    for dd in 0..dpw {
        let mut abbrd = String::from(dow[dd]);
        abbrd.truncate(2);
        print!("{} ", abbrd);
    }

    moff = print_days(moff, dpm, dpw);
}

fn print_days(moff: usize, dpm: usize, dpw: usize) -> usize {
    if moff != 0 {
        println!("");
    }

    for _ in 0 .. moff {
        print!("   ");
    }

    for day in 1 .. dpm + 1 {
        if (day + moff) % dpw == 1 {
            println!("");
        }

        print!("{:2} ", day);
    }

    println!("");
    return if moff == 0 { 3 } else { 0 };
}

<commit_msg>Factor month-printing into entire year<commit_after>fn main() {
    let dow = ["Duinday", "Sitaday", "Wikiday", "Tuxday", "Gnuday", "Commonday"];
    let moy = ["Jabim", "Zodrak", "Trogool", "Yanar", "Shkumbe", "Habniah", "Skarl", "Mikon", "Pertunda", "Kib", "Broket"];
    let yoff: usize = 0;
    let dpm = 33;
    let dpw = dow.len();
    let mpy = moy.len();
    let mut moff = yoff;

    for mm in 0..mpy {
        let spaces = (17 - moy[mm].len()) / 2;
        for _ in 0..spaces {
            print!(" ");
        }
        println!("{}", moy[mm]);

        for dd in 0..dpw {
            let mut abbrd = String::from(dow[dd]);
            abbrd.truncate(2);
            print!("{} ", abbrd);
        }

        moff = print_days(moff, dpm, dpw);
    }
}

fn print_days(moff: usize, dpm: usize, dpw: usize) -> usize {
    if moff != 0 {
        println!("");
    }

    for _ in 0 .. moff {
        print!("   ");
    }

    for day in 1 .. dpm + 1 {
        if (day + moff) % dpw == 1 {
            println!("");
        }

        print!("{:2} ", day);
    }

    println!("");
    return if moff == 0 { 3 } else { 0 };
}

<|endoftext|>


<commit_before>use super::*;

pub struct ExecuteStoredProcedureRequest {
    hyper_client: HyperClient,
    request: RequestBuilder,
    payload: Result<String, serde_json::Error>,
}

impl DocumentRequestExt for ExecuteStoredProcedureRequest {
    fn request(&mut self) -> &mut RequestBuilder {
        &mut self.request
    }
}

impl ExecuteStoredProcedureRequest {
    pub(crate) fn new(
        hyper_client: HyperClient,
        request: RequestBuilder,
        payload: Result<String, serde_json::Error>,
    ) -> ExecuteStoredProcedureRequest {
        ExecuteStoredProcedureRequest {
            hyper_client,
            request,
            payload,
        }
    }

    pub fn execute<R: DeserializeOwned>(self) -> impl Future<Item = ExecuteStoredProcedureResponse<R>, Error = AzureError> {
        trace!("execute_stored_procedure called(request == {:?}", self.request);
        let hc = self.hyper_client;
        let mut req = self.request;
        future::result(self.payload)
            .from_err()
            .and_then(move |payload| future::result(req.body(payload.into())).from_err())
            .and_then(move |r| check_status_extract_headers_and_body(hc.request(r), StatusCode::OK))
            .and_then(move |(headers, v_body)| Self::extract_result(&headers, &v_body))
    }

    fn extract_result<R: DeserializeOwned>(headers: &HeaderMap, v_body: &[u8]) -> Result<ExecuteStoredProcedureResponse<R>, AzureError> {
        let additional_headers = DocumentAdditionalHeaders::derive_from(headers);
        let result = serde_json::from_slice(v_body)?;
        Ok(ExecuteStoredProcedureResponse {
            result,
            additional_headers,
        })
    }
}
<commit_msg>Add partition key header to stored procedure execution as well<commit_after>use super::*;

pub struct ExecuteStoredProcedureRequest {
    hyper_client: HyperClient,
    request: RequestBuilder,
    payload: Result<String, serde_json::Error>,
}

impl DocumentRequestExt for ExecuteStoredProcedureRequest {
    fn request(&mut self) -> &mut RequestBuilder {
        &mut self.request
    }
}

impl ExecuteStoredProcedureRequest {
    pub(crate) fn new(
        hyper_client: HyperClient,
        request: RequestBuilder,
        payload: Result<String, serde_json::Error>,
    ) -> ExecuteStoredProcedureRequest {
        ExecuteStoredProcedureRequest {
            hyper_client,
            request,
            payload,
        }
    }

    request_bytes_ref!(partition_key, str, HEADER_DOCUMENTDB_PARTITIONKEY);

    pub fn execute<R: DeserializeOwned>(self) -> impl Future<Item = ExecuteStoredProcedureResponse<R>, Error = AzureError> {
        trace!("execute_stored_procedure called(request == {:?}", self.request);
        let hc = self.hyper_client;
        let mut req = self.request;
        future::result(self.payload)
            .from_err()
            .and_then(move |payload| future::result(req.body(payload.into())).from_err())
            .and_then(move |r| check_status_extract_headers_and_body(hc.request(r), StatusCode::OK))
            .and_then(move |(headers, v_body)| Self::extract_result(&headers, &v_body))
    }

    fn extract_result<R: DeserializeOwned>(headers: &HeaderMap, v_body: &[u8]) -> Result<ExecuteStoredProcedureResponse<R>, AzureError> {
        let additional_headers = DocumentAdditionalHeaders::derive_from(headers);
        let result = serde_json::from_slice(v_body)?;
        Ok(ExecuteStoredProcedureResponse {
            result,
            additional_headers,
        })
    }
}
<|endoftext|>


<commit_before>//! Conversion of data structures to and from MDB_val
//!
//! Since MDB_val is valid through whole transaction, it is kind of safe
//! to keep plain data, i.e. to keep raw pointers and transmute them back
//! and forward into corresponding data structures to avoid any unnecessary
//! copying.
//!
//! `MdbValue` is a simple wrapper with bounded lifetime which should help
//! keep it sane, i.e. provide compile errors when data retrieved outlives
//! transaction.
//!
//! It would be extremely helpful to create `compile-fail` tests to ensure
//! this, but unfortunately there is no way yet.

use std::{self, mem, slice};

use core::MdbValue;
use ffi::MDB_val;

/// `ToMdbValue` is supposed to convert a value to a memory
/// slice which `lmdb` uses to prevent multiple copying data
/// multiple times. May be unsafe.

pub trait ToMdbValue {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a>;
}

/// `FromMdbValue` is supposed to reconstruct a value from
/// memory slice. It allows to use zero copy where it is
/// required.

pub trait FromMdbValue {
    fn from_mdb_value(value: &MdbValue) -> Self;
}

impl ToMdbValue for Vec<u8> {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            MdbValue::new(std::mem::transmute(self.as_ptr()), self.len())
        }
    }
}

impl ToMdbValue for String {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            let t: &'a str = self;
            MdbValue::new(std::mem::transmute(t.as_ptr()), t.len())
        }
    }
}

impl<'a> ToMdbValue for &'a str {
    fn to_mdb_value<'b, 's>(&'s self) -> MdbValue<'b> {
        unsafe {
            MdbValue::new(mem::transmute(self.as_ptr()),
                          self.len())
        }
    }
}

impl<'a> ToMdbValue for &'a [u8] {
    fn to_mdb_value<'b>(&'b self) -> MdbValue<'b> {
        unsafe {
            MdbValue::new(std::mem::transmute(self.as_ptr()),
                          self.len())
        }
    }
}

impl ToMdbValue for MDB_val {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            MdbValue::from_raw(self)
        }
    }
}

impl<'a> ToMdbValue for MdbValue<'a> {
    fn to_mdb_value<'b>(&'b self) -> MdbValue<'b> {
        *self
    }
}

impl FromMdbValue for String {
    fn from_mdb_value(value: &MdbValue) -> String {
        unsafe {
            let ptr = mem::transmute(value.get_ref());
            let data: Vec<u8> = slice::from_raw_parts(ptr, value.get_size()).to_vec();
            String::from_utf8(data).unwrap()
        }
    }
}

impl FromMdbValue for Vec<u8> {
    fn from_mdb_value(value: &MdbValue) -> Vec<u8> {
        unsafe {
            let ptr = mem::transmute(value.get_ref());
            slice::from_raw_parts(ptr, value.get_size()).to_vec()
        }
    }
}

impl FromMdbValue for () {
    fn from_mdb_value(_: &MdbValue) {
    }
}

impl<'b> FromMdbValue for &'b str {
    fn from_mdb_value(value: &MdbValue) -> &'b str {
        unsafe {
            std::mem::transmute(slice::from_raw_parts(value.get_ref(), value.get_size()))
        }
    }
}

impl<'b> FromMdbValue for &'b [u8] {
    fn from_mdb_value(value: &MdbValue) -> &'b [u8] {
        unsafe {
            std::mem::transmute(slice::from_raw_parts(value.get_ref(), value.get_size()))
        }
    }
}

macro_rules! mdb_for_primitive {
    ($t:ty) => (
        impl ToMdbValue for $t {
            fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
                MdbValue::new_from_sized(self)
            }
        }

        impl FromMdbValue for $t {
            fn from_mdb_value(value: &MdbValue) -> $t {
                unsafe {
                    let t: *mut $t = mem::transmute(value.get_ref());
                    *t
                }
            }
        }

        )
}

mdb_for_primitive!(u8);
mdb_for_primitive!(i8);
mdb_for_primitive!(u16);
mdb_for_primitive!(i16);
mdb_for_primitive!(u32);
mdb_for_primitive!(i32);
mdb_for_primitive!(u64);
mdb_for_primitive!(i64);
mdb_for_primitive!(f32);
mdb_for_primitive!(f64);
mdb_for_primitive!(bool);
<commit_msg>fix incorrect `&self` annotation<commit_after>//! Conversion of data structures to and from MDB_val
//!
//! Since MDB_val is valid through whole transaction, it is kind of safe
//! to keep plain data, i.e. to keep raw pointers and transmute them back
//! and forward into corresponding data structures to avoid any unnecessary
//! copying.
//!
//! `MdbValue` is a simple wrapper with bounded lifetime which should help
//! keep it sane, i.e. provide compile errors when data retrieved outlives
//! transaction.
//!
//! It would be extremely helpful to create `compile-fail` tests to ensure
//! this, but unfortunately there is no way yet.

use std::{self, mem, slice};

use core::MdbValue;
use ffi::MDB_val;

/// `ToMdbValue` is supposed to convert a value to a memory
/// slice which `lmdb` uses to prevent multiple copying data
/// multiple times. May be unsafe.

pub trait ToMdbValue {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a>;
}

/// `FromMdbValue` is supposed to reconstruct a value from
/// memory slice. It allows to use zero copy where it is
/// required.

pub trait FromMdbValue {
    fn from_mdb_value(value: &MdbValue) -> Self;
}

impl ToMdbValue for Vec<u8> {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            MdbValue::new(std::mem::transmute(self.as_ptr()), self.len())
        }
    }
}

impl ToMdbValue for String {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            let t: &'a str = self;
            MdbValue::new(std::mem::transmute(t.as_ptr()), t.len())
        }
    }
}

impl<'a> ToMdbValue for &'a str {
    fn to_mdb_value<'b>(&'b self) -> MdbValue<'b> {
        unsafe {
            MdbValue::new(mem::transmute(self.as_ptr()),
                          self.len())
        }
    }
}

impl<'a> ToMdbValue for &'a [u8] {
    fn to_mdb_value<'b>(&'b self) -> MdbValue<'b> {
        unsafe {
            MdbValue::new(std::mem::transmute(self.as_ptr()),
                          self.len())
        }
    }
}

impl ToMdbValue for MDB_val {
    fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
        unsafe {
            MdbValue::from_raw(self)
        }
    }
}

impl<'a> ToMdbValue for MdbValue<'a> {
    fn to_mdb_value<'b>(&'b self) -> MdbValue<'b> {
        *self
    }
}

impl FromMdbValue for String {
    fn from_mdb_value(value: &MdbValue) -> String {
        unsafe {
            let ptr = mem::transmute(value.get_ref());
            let data: Vec<u8> = slice::from_raw_parts(ptr, value.get_size()).to_vec();
            String::from_utf8(data).unwrap()
        }
    }
}

impl FromMdbValue for Vec<u8> {
    fn from_mdb_value(value: &MdbValue) -> Vec<u8> {
        unsafe {
            let ptr = mem::transmute(value.get_ref());
            slice::from_raw_parts(ptr, value.get_size()).to_vec()
        }
    }
}

impl FromMdbValue for () {
    fn from_mdb_value(_: &MdbValue) {
    }
}

impl<'b> FromMdbValue for &'b str {
    fn from_mdb_value(value: &MdbValue) -> &'b str {
        unsafe {
            std::mem::transmute(slice::from_raw_parts(value.get_ref(), value.get_size()))
        }
    }
}

impl<'b> FromMdbValue for &'b [u8] {
    fn from_mdb_value(value: &MdbValue) -> &'b [u8] {
        unsafe {
            std::mem::transmute(slice::from_raw_parts(value.get_ref(), value.get_size()))
        }
    }
}

macro_rules! mdb_for_primitive {
    ($t:ty) => (
        impl ToMdbValue for $t {
            fn to_mdb_value<'a>(&'a self) -> MdbValue<'a> {
                MdbValue::new_from_sized(self)
            }
        }

        impl FromMdbValue for $t {
            fn from_mdb_value(value: &MdbValue) -> $t {
                unsafe {
                    let t: *mut $t = mem::transmute(value.get_ref());
                    *t
                }
            }
        }

        )
}

mdb_for_primitive!(u8);
mdb_for_primitive!(i8);
mdb_for_primitive!(u16);
mdb_for_primitive!(i16);
mdb_for_primitive!(u32);
mdb_for_primitive!(i32);
mdb_for_primitive!(u64);
mdb_for_primitive!(i64);
mdb_for_primitive!(f32);
mdb_for_primitive!(f64);
mdb_for_primitive!(bool);
<|endoftext|>


<commit_before>#![feature(globs)]
#![feature(unsafe_destructor)]

extern crate piston;
extern crate graphics;
extern crate opengl_graphics;
extern crate sdl2_game_window;
extern crate gl;
extern crate libc;
extern crate cgmath;

use Window = sdl2_game_window::GameWindowSDL2;
use graphics::*;
use piston::{
    AssetStore,
    GameIterator,
    GameIteratorSettings,
    GameWindowSettings,
    Render,
};
use opengl_graphics::{
    Gl,
    Texture,
};

use cam::Camera;

pub mod shader;
pub mod cube;
pub mod quad;
pub mod cam;
pub mod texture;

static TEST_TEXTURE: texture::MinecraftTexture = texture::Grass;

fn main() {
    let mut window = Window::new(
        GameWindowSettings {
            title: "Hematite".to_string(),
            size: [640, 480],
            fullscreen: false,
            exit_on_esc: true,
        }
    );

    let asset_store = AssetStore::from_folder("assets");

    // Load texture.
    let texture = asset_store.path("minecraft-texture.png").unwrap();
    let ref texture = Texture::from_path(&texture).unwrap();
    let game_iter_settings = GameIteratorSettings {
            updates_per_second: 120,
            max_frames_per_second: 60,
        };
    let ref mut gl = Gl::new();

    let shader = shader::Shader::new();

    for e in GameIterator::new(&mut window, &game_iter_settings) {
        match e {
            Render(args) => {
                gl.viewport(0, 0, args.width as i32, args.height as i32);
                let c = Context::abs(args.width as f64, args.height as f64);
                c.rgb(0.0, 0.0, 0.0).draw(gl);

                let tex = TEST_TEXTURE;
                shader.render(gl, |ready_shader| {
                    tex.to_quad(texture).render(ready_shader);
                });
                let (src_x, src_y) = tex.get_src_xy();
                c.image(texture)
                .src_rect(src_x * 16, src_y * 16, 16, 16)
                .draw(gl);
            },
            _ => {}
        }
    }
}
<commit_msg>Added camera to main function<commit_after>#![feature(globs)]
#![feature(unsafe_destructor)]

extern crate piston;
extern crate graphics;
extern crate opengl_graphics;
extern crate sdl2_game_window;
extern crate gl;
extern crate libc;
extern crate cgmath;

use Window = sdl2_game_window::GameWindowSDL2;
use graphics::*;
use piston::{
    AssetStore,
    GameIterator,
    GameIteratorSettings,
    GameWindowSettings,
    Render,
};
use opengl_graphics::{
    Gl,
    Texture,
};

use cam::Camera;

pub mod shader;
pub mod cube;
pub mod quad;
pub mod cam;
pub mod texture;

static TEST_TEXTURE: texture::MinecraftTexture = texture::Grass;

fn main() {
    let mut window = Window::new(
        GameWindowSettings {
            title: "Hematite".to_string(),
            size: [640, 480],
            fullscreen: false,
            exit_on_esc: true,
        }
    );

    let asset_store = AssetStore::from_folder("assets");

    // Load texture.
    let texture = asset_store.path("minecraft-texture.png").unwrap();
    let ref texture = Texture::from_path(&texture).unwrap();
    let game_iter_settings = GameIteratorSettings {
            updates_per_second: 120,
            max_frames_per_second: 60,
        };
    let ref mut gl = Gl::new();

    let shader = shader::Shader::new();

    let camera = Camera {
            position: [0.0, 0.0, -3.0],
            target: [0.0, 0.0, 0.0],
            right: [1.0, 0.0, 0.0],
            up: [0.0, 1.0, 0.0]
        };

    for e in GameIterator::new(&mut window, &game_iter_settings) {
        match e {
            Render(args) => {
                gl.viewport(0, 0, args.width as i32, args.height as i32);
                let c = Context::abs(args.width as f64, args.height as f64);
                c.rgb(0.0, 0.0, 0.0).draw(gl);

                let tex = TEST_TEXTURE;
                shader.render(gl, |ready_shader| {
                    tex.to_quad(texture).render(ready_shader);
                });
                let (src_x, src_y) = tex.get_src_xy();
                c.image(texture)
                .src_rect(src_x * 16, src_y * 16, 16, 16)
                .draw(gl);
            },
            _ => {}
        }
    }
}
<|endoftext|>


<commit_before>//
// zhttpto.rs
//
// Starting code for PS1
// Running on Rust 0.12
//
// Note that this code has serious security risks! You should not run it
// on any system with access to sensitive files.
//
// University of Virginia - cs4414 Spring 2014
// Weilin Xu and David Evans
// Version 0.3

#![feature(globs)]

use std::io::*;
use std::str;

fn main() {

    let addr = "127.0.0.1:4414";
    let mut acceptor = net::tcp::TcpListener::bind(addr).listen();

    println!("Listening on [{}] ...", addr);

    for stream in acceptor.incoming() {
        match stream {
            Err(_) => (),
            // Spawn a task to handle the connection
            Ok(mut stream) => spawn(proc() {
                match stream.peer_name() {
                    Err(_) => (),
                    Ok(pn) => println!("Received connection from: [{}]", pn),
                }

                let mut buf = [0, ..500];
                let _ = stream.read(&mut buf);
                let request_str = str::from_utf8(&buf);
                println!("Received request :\n{}", request_str);

                let response =
                    "HTTP/1.1 200 OK\r\nContent-Type: text/html; charset=UTF-8\r\n\r\n
                     <doctype !html><title>Hello, Rust!</title>

Greetings, Krusty!

                     \r\n";
                let _ = stream.write(response.as_bytes());
                println!("Connection terminates.");
            }),
        }
    }

    drop(acceptor);
}
<commit_msg>So explicit, such error handling<commit_after>//
// zhttpto.rs
//
// Starting code for PS1
// Running on Rust 0.12
//
// Note that this code has serious security risks! You should not run it
// on any system with access to sensitive files.
//
// University of Virginia - cs4414 Spring 2014
// Weilin Xu and David Evans
// Version 0.3

use std::io::TcpListener;
use std::io::{Acceptor, Listener};
use std::str;

fn main() {
    let addr = "127.0.0.1:4414";

    let mut acceptor = TcpListener::bind(addr).unwrap().listen().unwrap();

    println!("Listening on [{}] ...", addr);

    for stream in acceptor.incoming() {
        match stream {
            Err(_) => (),
            // Spawn a task to handle the connection
            Ok(mut stream) => spawn(proc() {
                match stream.peer_name() {
                    Err(_) => (),
                    Ok(pn) => println!("Received connection from: [{}]", pn),
                }

                let mut buf = [0, ..500];
                let _ = stream.read(&mut buf);
                let request_str = str::from_utf8(&buf);
                println!("Received request:\n{}", request_str);

                let response =
                    "HTTP/1.1 200 OK\r\nContent-Type: text/html; charset=UTF-8\r\n\r\n
                     <doctype !html><title>Hello, Rust!</title>

Greetings, Krusty!

                     \r\n";
                let _ = stream.write(response.as_bytes());
                println!("Connection terminates.");
            }),
        }
    }

    drop(acceptor);
}
<|endoftext|>


<commit_before>#[macro_use]
extern crate clap;
extern crate indicatif;
extern crate console;

use clap::{App, SubCommand};
use indicatif::{ProgressBar};
use console::{style, Emoji};
use std::process::Command;
use std::fs::remove_file;

fn main() {
  let matches = App::new("r2")
      .version(crate_version!())
      .author("Olivia Hugger")
      .about("Test")
      .subcommand(SubCommand::with_name("verify").alias("v"))
      .get_matches();

  if let Some(_) = matches.subcommand_matches("verify") {
    compile_only("exercises/ex1.rs");
    compile_only("exercises/ex2.rs");
    compile_only("exercises/ex3.rs");
    compile_only("exercises/ex4.rs");
    compile_only("exercises/ex5.rs");

    compile_only("exercises/variables/variables1.rs");
    compile_only("exercises/variables/variables2.rs");
    compile_only("exercises/variables/variables3.rs");
    compile_only("exercises/variables/variables4.rs");

    compile_only("exercises/functions/functions1.rs");
    compile_only("exercises/functions/functions2.rs");
    compile_only("exercises/functions/functions3.rs");
    compile_only("exercises/functions/functions4.rs");
    compile_only("exercises/functions/functions5.rs");

    compile_only("exercises/primitive_types/primitive_types1.rs");
    compile_only("exercises/primitive_types/primitive_types2.rs");
    compile_only("exercises/primitive_types/primitive_types3.rs");
    compile_only("exercises/primitive_types/primitive_types4.rs");
    compile_only("exercises/primitive_types/primitive_types5.rs");
    compile_only("exercises/primitive_types/primitive_types6.rs");

    test("exercises/tests/tests1.rs");
    test("exercises/tests/tests2.rs");
    test("exercises/tests/tests3.rs");
    test("exercises/tests/tests4.rs");

    test("exercises/if/if1.rs");

    compile_only("exercises/strings/strings1.rs");
    compile_only("exercises/strings/strings2.rs");
    compile_only("exercises/strings/strings3.rs");

    compile_only("exercises/move_semantics/move_semantics1.rs");
    compile_only("exercises/move_semantics/move_semantics2.rs");
    compile_only("exercises/move_semantics/move_semantics3.rs");
    compile_only("exercises/move_semantics/move_semantics4.rs");

    compile_only("exercises/modules/modules1.rs");
    compile_only("exercises/modules/modules2.rs");

    compile_only("exercises/macros/macros1.rs");
    compile_only("exercises/macros/macros2.rs");
    compile_only("exercises/macros/macros3.rs");
    compile_only("exercises/macros/macros4.rs");

    test("exercises/error_handling/errors1.rs");
    test("exercises/error_handling/errors2.rs");
    test("exercises/error_handling/errors3.rs");
    test("exercises/error_handling/errorsn.rs");
    compile_only("exercises/error_handling/option1.rs");
    test("exercises/error_handling/result1.rs");
  }
}

fn compile_only(filename: &str) {
  let bar = ProgressBar::new_spinner();
  bar.set_message(format!("Compiling {}...", filename).as_str());
  bar.enable_steady_tick(100);
  let compilecmd = Command::new("rustc")
                           .args(&[filename, "-o", "temp"])
                           .output()
                           .expect("fail");
  bar.finish_and_clear();
  if compilecmd.status.success() {
    let formatstr = format!("{} Successfully compiled {}!", Emoji("✅", "✓"), filename);
    println!("{}", style(formatstr).green());
    clean().unwrap();
  } else {
    let formatstr = format!("{} Compilation of {} failed! Compiler error message:\n", Emoji("⚠ ", "!"), filename);
    println!("{}", style(formatstr).red());
    println!("{}", String::from_utf8_lossy(&compilecmd.stderr));
    clean().unwrap();
    std::process::exit(1);
  }
}

fn test(filename: &str) {
  let bar = ProgressBar::new_spinner();
  bar.set_message(format!("Testing {}...", filename).as_str());
  bar.enable_steady_tick(100);
  let testcmd = Command::new("rustc")
                        .args(&["--test", filename, "-o", "temp"])
                        .output()
                        .expect("fail");
  bar.finish_and_clear();
  if testcmd.status.success() {
    let formatstr = format!("{} Successfully tested {}!", Emoji("✅", "✓"), filename);
    println!("{}", style(formatstr).green());
    clean().unwrap();
  } else {
    let formatstr = format!("{} Testing of {} failed! Please try again.", Emoji("⚠ ", "!"), filename);
    println!("{}", style(formatstr).red());
    clean().unwrap();
    std::process::exit(1);
  }
}

fn clean() -> Result<(), std::io::Error> {
    remove_file("temp")?;
    Ok(())
}
<commit_msg>add a fancy ascii header<commit_after>#[macro_use]
extern crate clap;
extern crate indicatif;
extern crate console;

use clap::{App, SubCommand};
use indicatif::{ProgressBar};
use console::{style, Emoji};
use std::process::Command;
use std::fs::remove_file;

fn main() {
  let matches = App::new("r2")
      .version(crate_version!())
      .author("Olivia Hugger")
      .about("Test")
      .subcommand(SubCommand::with_name("verify").alias("v"))
      .get_matches();

  println!(r#"                 _   _ _                  "#);
  println!(r#"  _ __ _   _ ___| |_| (_)_ __   __ _ ___  "#);
  println!(r#" | '__| | | / __| __| | | '_ \ / _` / __| "#);
  println!(r#" | |  | |_| \__ \ |_| | | | | | (_| \__ \ "#);
  println!(r#" |_|   \__,_|___/\__|_|_|_| |_|\__, |___/ "#);
  println!(r#"                               |___/      "#);

  if let Some(_) = matches.subcommand_matches("verify") {
    compile_only("exercises/ex1.rs");
    compile_only("exercises/ex2.rs");
    compile_only("exercises/ex3.rs");
    compile_only("exercises/ex4.rs");
    compile_only("exercises/ex5.rs");

    compile_only("exercises/variables/variables1.rs");
    compile_only("exercises/variables/variables2.rs");
    compile_only("exercises/variables/variables3.rs");
    compile_only("exercises/variables/variables4.rs");

    compile_only("exercises/functions/functions1.rs");
    compile_only("exercises/functions/functions2.rs");
    compile_only("exercises/functions/functions3.rs");
    compile_only("exercises/functions/functions4.rs");
    compile_only("exercises/functions/functions5.rs");

    compile_only("exercises/primitive_types/primitive_types1.rs");
    compile_only("exercises/primitive_types/primitive_types2.rs");
    compile_only("exercises/primitive_types/primitive_types3.rs");
    compile_only("exercises/primitive_types/primitive_types4.rs");
    compile_only("exercises/primitive_types/primitive_types5.rs");
    compile_only("exercises/primitive_types/primitive_types6.rs");

    test("exercises/tests/tests1.rs");
    test("exercises/tests/tests2.rs");
    test("exercises/tests/tests3.rs");
    test("exercises/tests/tests4.rs");

    test("exercises/if/if1.rs");

    compile_only("exercises/strings/strings1.rs");
    compile_only("exercises/strings/strings2.rs");
    compile_only("exercises/strings/strings3.rs");

    compile_only("exercises/move_semantics/move_semantics1.rs");
    compile_only("exercises/move_semantics/move_semantics2.rs");
    compile_only("exercises/move_semantics/move_semantics3.rs");
    compile_only("exercises/move_semantics/move_semantics4.rs");

    compile_only("exercises/modules/modules1.rs");
    compile_only("exercises/modules/modules2.rs");

    compile_only("exercises/macros/macros1.rs");
    compile_only("exercises/macros/macros2.rs");
    compile_only("exercises/macros/macros3.rs");
    compile_only("exercises/macros/macros4.rs");

    test("exercises/error_handling/errors1.rs");
    test("exercises/error_handling/errors2.rs");
    test("exercises/error_handling/errors3.rs");
    test("exercises/error_handling/errorsn.rs");
    compile_only("exercises/error_handling/option1.rs");
    test("exercises/error_handling/result1.rs");
  }
}

fn compile_only(filename: &str) {
  let bar = ProgressBar::new_spinner();
  bar.set_message(format!("Compiling {}...", filename).as_str());
  bar.enable_steady_tick(100);
  let compilecmd = Command::new("rustc")
                           .args(&[filename, "-o", "temp"])
                           .output()
                           .expect("fail");
  bar.finish_and_clear();
  if compilecmd.status.success() {
    let formatstr = format!("{} Successfully compiled {}!", Emoji("✅", "✓"), filename);
    println!("{}", style(formatstr).green());
    clean().unwrap();
  } else {
    let formatstr = format!("{} Compilation of {} failed! Compiler error message:\n", Emoji("⚠ ", "!"), filename);
    println!("{}", style(formatstr).red());
    println!("{}", String::from_utf8_lossy(&compilecmd.stderr));
    clean().unwrap();
    std::process::exit(1);
  }
}

fn test(filename: &str) {
  let bar = ProgressBar::new_spinner();
  bar.set_message(format!("Testing {}...", filename).as_str());
  bar.enable_steady_tick(100);
  let testcmd = Command::new("rustc")
                        .args(&["--test", filename, "-o", "temp"])
                        .output()
                        .expect("fail");
  bar.finish_and_clear();
  if testcmd.status.success() {
    let formatstr = format!("{} Successfully tested {}!", Emoji("✅", "✓"), filename);
    println!("{}", style(formatstr).green());
    clean().unwrap();
  } else {
    let formatstr = format!("{} Testing of {} failed! Please try again.", Emoji("⚠ ", "!"), filename);
    println!("{}", style(formatstr).red());
    clean().unwrap();
    std::process::exit(1);
  }
}

fn clean() -> Result<(), std::io::Error> {
    remove_file("temp")?;
    Ok(())
}
<|endoftext|>


<commit_before>extern crate travis_after_all;

use std::process;
use std::error::Error as StdError;
use travis_after_all::{Build, Error};

fn human<T>(val: Result<T, Error>) -> T {
    match val {
        Ok(val) => val,
        Err(e) => {
            println!("travis_after_all failed.");
            println!("");
            println!("Error: {}", e.description());
            process::exit(1);
        }
    }

}

fn main() {
    let config = human(Build::from_env());

    if config.is_leader() {
        println!("I'm the leader.");
        println!("Waiting for others to finish");
        match config.wait_for_others() {
            Ok(()) => println!("Build finished. Now it's my time"),
            Err(Error::NotLeader) => println!("I'm not the leader. Bailing out."),
            Err(Error::FailedBuilds) => println!("Some builds failed. Stopping here."),
            Err(e) => {
                println!("travis_after_all failed.");
                println!("");
                println!("Error: {}", e.description());
                process::exit(1);
            }
        }

        {
            let matrix = config.build_matrix();

            if let Ok(matrix) = matrix {
                for build in matrix.builds() {
                    println!("== Build {}", build.id());
                    println!("Leader: {}", build.is_leader());
                    println!("Finished: {}", build.is_finished());
                    println!("Succeeded: {}", build.is_succeeded());
                    println!("==");
                    println!("");

                }
                println!("Matrix all except master finished: {}", matrix.others_finished());
                println!("Matrix all except master succeeded: {}", matrix.others_succeeded());
            }
        }
    }
}
<commit_msg>Bail out on error<commit_after>extern crate travis_after_all;

use std::process;
use std::error::Error as StdError;
use travis_after_all::{Build, Error};

fn human<T>(val: Result<T, Error>) -> T {
    match val {
        Ok(val) => val,
        Err(e) => {
            println!("travis_after_all failed.");
            println!("");
            println!("Error: {}", e.description());
            process::exit(1);
        }
    }

}

fn main() {
    let config = human(Build::from_env());

    if config.is_leader() {
        println!("I'm the leader.");
        println!("Waiting for others to finish");
        match config.wait_for_others() {
            Ok(()) => println!("Build finished. Now it's my time"),
            Err(Error::NotLeader) => {
                println!("I'm not the leader. Bailing out.");
                process::exit(3);
            },
            Err(Error::FailedBuilds) => {
                println!("Some builds failed. Stopping here.");
                process::exit(2);
            },
            Err(e) => {
                println!("travis_after_all failed.");
                println!("");
                println!("Error: {}", e.description());
                process::exit(1);
            }
        }

        {
            let matrix = config.build_matrix();

            if let Ok(matrix) = matrix {
                for build in matrix.builds() {
                    println!("== Build {}", build.id());
                    println!("Leader: {}", build.is_leader());
                    println!("Finished: {}", build.is_finished());
                    println!("Succeeded: {}", build.is_succeeded());
                    println!("==");
                    println!("");

                }
                println!("Matrix all except master finished: {}", matrix.others_finished());
                println!("Matrix all except master succeeded: {}", matrix.others_succeeded());
            }
        }
    }
}
<|endoftext|>