<commit_before>extern crate reqwest;
extern crate select;
extern crate serenity;

use select::document::Document;
use select::predicate::Class;

use serenity::client::Client;
use serenity::prelude::*;
use serenity::model::*;

// For file reading
use std::io::Read;
use std::fs::File;
use std::io::Write;
use std::fs::OpenOptions;

// For multithreading
use std::thread;
use std::sync::{Arc, Mutex};
use std::ops::DerefMut;

// Allow openssl crosscompiling to work
extern crate openssl_probe;

extern crate time;

#[derive(Debug)]
struct UMassEvent {
    title: String,
    description: String,
    date: String,
    location: Option<String>,
}

impl UMassEvent {
    fn format(&self) -> String {
        match self.location {
            // "Event_Name at Event_location: Long Description"
            Some(ref location) => format!("{} at {}:\n{}", self.title, location, self.description),
            // "Event_Name: Long Description"
            None => format!("{}:\n{}", self.title, self.description),
        }
    }
}

fn get_document(url: &str) -> Result<select::document::Document, reqwest::Error> {
    reqwest::get(url).map(|mut response| {
        // Extract the data from the http request
        let mut content = String::new();
        let _ = response.read_to_string(&mut content);
        Document::from(&*content)
    })
}

fn get_events() -> Vec<UMassEvent> {
    let document = get_document("http://www.umass.edu/events/")
        .expect("Couldn't get the events page");

    // Parse the data into a list of events
    let events = document.find(Class("views-row"))
        .map(|node| {

            // This is really janky and relies on UMass not changing the event page html...

            let title = node.find(Class("views-field-title"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .unwrap()
                .first_child()
                .unwrap()
                .first_child()
                .unwrap()
                .text();
            let description = node.find(Class("views-field-field-short-desc"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .unwrap()
                .first_child()
                .unwrap()
                .text();
            let date = node.find(Class("event-date")).next().unwrap().text();
            let location = node.find(Class("event-location"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .map(|node| node.first_child().unwrap().text());

            // Return the event, which will then be collected into the events vector
            UMassEvent {
                title: title,
                description: description,
                date: date,
                location: location,
            }
        })
        .collect();

    events
}

#[derive(Copy)]
#[derive(Clone)]
#[derive(Debug)]
enum Meal {
    Breakfast,
    Lunch,
    Dinner,
    LateNight,
}

#[derive(Copy)]
#[derive(Clone)]
#[derive(Debug)]
enum DiningCommon {
    Berk,
    Hamp,
    Frank,
    Worcester,
}

fn get_meal_code(meal: Meal, dining_common: DiningCommon) -> String {
    match dining_common {
            DiningCommon::Worcester => {
                match meal {
                    Meal::Breakfast => "0700001",
                    Meal::Lunch => "1130001",
                    Meal::Dinner => "1630001",
                    Meal::LateNight => "2100001",
                }
            }
            DiningCommon::Frank => {
                match meal {
                    Meal::Breakfast => "0700002",
                    Meal::Lunch => "1130002",
                    Meal::Dinner => "1630002",
                    Meal::LateNight => panic!("Frank doesn't have late night"),
                }
            }
            DiningCommon::Hamp => {
                match meal {
                    Meal::Breakfast => "0700003",
                    Meal::Lunch => "1130003",
                    Meal::Dinner => "1630003",
                    Meal::LateNight => panic!("Hamp doesn't have late night"),
                }
            }
            DiningCommon::Berk => {
                match meal {
                    Meal::Breakfast => panic!("Berk doesn't have breakfast"),
                    Meal::Lunch => "1100004",
                    Meal::Dinner => "1630004",
                    Meal::LateNight => "2100004",
                }
            }
        }
        .to_string()

}

fn get_dining_common_code(dining_common: DiningCommon) -> String {
    match dining_common {
            DiningCommon::Worcester => "0",
            DiningCommon::Frank => "1",
            DiningCommon::Hamp => "2",
            DiningCommon::Berk => "3",
        }
        .to_string()
}

fn get_menu_document(dining_common: DiningCommon,
                     meal: Meal)
                     -> Result<select::document::Document, reqwest::Error> {
    let dining_common_id = get_dining_common_code(dining_common.clone());

    let time = time::now();

    let year = time.tm_year + 1900;
    let month = format!("{:02}", time.tm_mon + 1);
    let day = format!("{:02}", time.tm_mday);
    let meal = get_meal_code(meal, dining_common);

    let url: &str = &format!("https://go.umass.\
                              edu/dining/event?feed=dining-halls&id=id_{id}&calendar=dining-halls_id_{id}_event_calendar&startdate={day}-{month}-{year}&event={year}{month}{day}T{meal}%7C{year}{month}{day}T000000&calendarMode=day",
                             id = dining_common_id,
                             year = year,
                             month = month,
                             day = day,
                             meal = meal);

    println!("{}", url);

    get_document(url)

}

fn is_on_menu(dining_common: DiningCommon, meal: Meal, item: &str) -> bool {
    let nodes: Vec<String> = get_menu_document(dining_common, meal)
        .expect("Couldn't get the menu page")
        .find(Class("kgo_web_content"))
        .map(|node| node.text())
        .collect();

    let text: String = nodes.join(" ");

    return text.to_lowercase().as_str().contains(item.to_lowercase().as_str());
}

// Get the token file from memory
fn load_token() -> String {
    let mut token = String::new();
    let _ = File::open("token").expect("No token file").read_to_string(&mut token);
    token
}

// Login to Discord and connect
fn login(listeners: Arc<Mutex<Vec<(ChannelId, String)>>>) -> Client<Handler> {
    Client::new(load_token().trim(), Handler { listeners: listeners })
}

fn check_for(food: String) -> String {
    let mut places: Vec<String> = vec![];

    for dining_common in vec![DiningCommon::Berk,
                              DiningCommon::Hamp,
                              DiningCommon::Frank,
                              DiningCommon::Worcester] {
        let meals = match dining_common.clone() {
            DiningCommon::Berk => vec![Meal::Lunch, Meal::Dinner, Meal::LateNight],
            DiningCommon::Hamp => vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner],
            DiningCommon::Frank => vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner],
            DiningCommon::Worcester => {
                vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner, Meal::LateNight]
            }
        };
        for meal in meals {
            if is_on_menu(dining_common, meal, &food) {
                places.push(format!("{:?} {:?}", dining_common.clone(), meal.clone()).to_string());
            }
        }
    }

    match places.len() {
        0 => format!("{} not found", food).to_string(),
        _ => format!("{}: {}", food, places.join(", ")).to_string(),
    }
}

fn get_guilds() -> Vec<String> {
    let cache = serenity::CACHE.read().unwrap();
    let guilds = cache.all_guilds();
    guilds.into_iter().map(|guild| guild.get().unwrap().name).collect()
}

struct Handler {
    listeners: Arc<Mutex<Vec<(serenity::model::ChannelId, String)>>>,
}

impl EventHandler for Handler {
    fn on_message(&self, _ctx: Context, message: Message) {
        let listeners = self.listeners.clone();

        if !message.content.starts_with("!") {
            // It's not a command, so we don't care about it
            return;
        }

        if message.author.bot {
            // We don't want it to respond to other bots or itself!
            return;
        }

        println!("{}: {} says: {}",
                 message.author.name,
                 message.author.id,
                 message.content);

        let is_owner: bool = message.author.id == 90927967651262464;

        if message.content == "!events" {

            let events = get_events();

            // Intro
            let _ = message.channel_id.say("Today's events are:".to_string());

            let _ = events.iter()
                .map(|event| message.channel_id.say(event.format().to_string()));

        } else if message.content.starts_with("!menu ") {
            let item: String = message.content[6..].to_string();

            let _ = message.channel_id.say(format!("Checking for {}", item).to_string());
            let _ = message.channel_id.say(check_for(item));
        } else if message.content.starts_with("!register ") {
            let item: String = message.content[10..].to_string();
            listeners.lock().unwrap().deref_mut().push((message.channel_id, item.clone()));
            save_listeners(listeners.lock().unwrap().deref_mut());
            let _ = message.channel_id.say(format!("Will check for {}", item).to_string());
        } else if message.content == "!help" {
            let _ = message.channel_id.say("UMass Bot help:");
            let _ = message.channel_id
                .say("```!menu [food name]     | tells you where that food is being served \
                      today```");
            let _ = message.channel_id
                .say("```!register [food name] | schedules it to tell you each day where that \
                      food is being served that day```");
        } else if message.content.starts_with("!guilds") && is_owner {
            let _ = message.channel_id.say(format!("Guilds: {}", get_guilds().join(", ")));
        }
    }
}

fn read_listeners() -> Vec<(serenity::model::ChannelId, String)> {
    let mut listeners_string: String = String::new();
    let _ = OpenOptions::new()
        .read(true)
        .write(true)
        .create(true)
        .open("listeners.txt")
        .expect("No listeners file")
        .read_to_string(&mut listeners_string);

    let mut listeners: Vec<(serenity::model::ChannelId, String)> = vec![];

    for line in listeners_string.split('\n') {
        if line == "" {
            continue;
        }
        let sections: Vec<&str> = line.split(' ').collect();
        let id = serenity::model::ChannelId(sections[0]
            .parse::<u64>()
            .expect("Couldn't parse channel id"));
        let food: String = sections[1..].join(" ").to_string();
        listeners.push((id, food));
    }

    listeners
}

fn save_listeners(vec: &Vec<(serenity::model::ChannelId, String)>) {
    let mut listeners_string: String = String::new();
    vec.into_iter().for_each(|x| {
        let (ref id, ref food) = *x;
        listeners_string = format!("{}\n{} {}", listeners_string, id, food);
    });

    let _ = OpenOptions::new()
        .read(true)
        .write(true)
        .create(true)
        .truncate(true)
        .open("listeners.txt")
        .unwrap()
        .write_all(listeners_string.as_bytes());
}

// Technically gets 5 minutes after midnight... :)
fn get_time_till_midnight() -> std::time::Duration {
    // The server the bot is deployed on is in UTC, so we have to adjust by 5 hours
    let current_time = time::now();
    let mut next_midnight: time::Tm = (time::now() + time::Duration::days(1)).to_local();
    if current_time.tm_hour < 5 || (current_time.tm_hour == 5 && current_time.tm_min < 5) {
        // We want to do it today (in UTC) if it is still yesterday in Eastern Time
        next_midnight = current_time.to_local();
    }
    next_midnight.tm_sec = 0;
    next_midnight.tm_min = 5;
    next_midnight.tm_hour = 5;

    (next_midnight - time::now()).to_std().unwrap()
}

fn main() {
    // Allow openssl crosscompiling to work
    openssl_probe::init_ssl_cert_env_vars();

    let listeners: Arc<Mutex<Vec<(ChannelId, String)>>> = Arc::new(Mutex::new(read_listeners()));
    let mut client = login(listeners.clone());
    println!("Connected to Discord");
    println!("Connected to servers: {}", get_guilds().join(", "));

    // Listeners loop
    let listeners_clone = listeners.clone();
    thread::spawn(move || {
        let listeners = listeners_clone;
        loop {
            println!("Seconds till midnight: {:?}", get_time_till_midnight());
            thread::sleep(get_time_till_midnight());
            println!("Checking for foods now!");
            listeners.lock().unwrap().to_vec().into_iter().for_each(|(channel, food)| {
                println!("Checking on {:?} for {}", channel, food);
                let _ = channel.say(check_for(food));
            });
        }
    });

    let _ = client.start();

}
<commit_msg>Change to run at 6 am instead of midnight<commit_after>extern crate reqwest;
extern crate select;
extern crate serenity;

use select::document::Document;
use select::predicate::Class;

use serenity::client::Client;
use serenity::prelude::*;
use serenity::model::*;

// For file reading
use std::io::Read;
use std::fs::File;
use std::io::Write;
use std::fs::OpenOptions;

// For multithreading
use std::thread;
use std::sync::{Arc, Mutex};
use std::ops::DerefMut;

// Allow openssl crosscompiling to work
extern crate openssl_probe;

extern crate time;

#[derive(Debug)]
struct UMassEvent {
    title: String,
    description: String,
    date: String,
    location: Option<String>,
}

impl UMassEvent {
    fn format(&self) -> String {
        match self.location {
            // "Event_Name at Event_location: Long Description"
            Some(ref location) => format!("{} at {}:\n{}", self.title, location, self.description),
            // "Event_Name: Long Description"
            None => format!("{}:\n{}", self.title, self.description),
        }
    }
}

fn get_document(url: &str) -> Result<select::document::Document, reqwest::Error> {
    reqwest::get(url).map(|mut response| {
        // Extract the data from the http request
        let mut content = String::new();
        let _ = response.read_to_string(&mut content);
        Document::from(&*content)
    })
}

fn get_events() -> Vec<UMassEvent> {
    let document = get_document("http://www.umass.edu/events/")
        .expect("Couldn't get the events page");

    // Parse the data into a list of events
    let events = document.find(Class("views-row"))
        .map(|node| {

            // This is really janky and relies on UMass not changing the event page html...

            let title = node.find(Class("views-field-title"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .unwrap()
                .first_child()
                .unwrap()
                .first_child()
                .unwrap()
                .text();
            let description = node.find(Class("views-field-field-short-desc"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .unwrap()
                .first_child()
                .unwrap()
                .text();
            let date = node.find(Class("event-date")).next().unwrap().text();
            let location = node.find(Class("event-location"))
                .next()
                .unwrap()
                .children()
                .nth(1)
                .map(|node| node.first_child().unwrap().text());

            // Return the event, which will then be collected into the events vector
            UMassEvent {
                title: title,
                description: description,
                date: date,
                location: location,
            }
        })
        .collect();

    events
}

#[derive(Copy)]
#[derive(Clone)]
#[derive(Debug)]
enum Meal {
    Breakfast,
    Lunch,
    Dinner,
    LateNight,
}

#[derive(Copy)]
#[derive(Clone)]
#[derive(Debug)]
enum DiningCommon {
    Berk,
    Hamp,
    Frank,
    Worcester,
}

fn get_meal_code(meal: Meal, dining_common: DiningCommon) -> String {
    match dining_common {
            DiningCommon::Worcester => {
                match meal {
                    Meal::Breakfast => "0700001",
                    Meal::Lunch => "1130001",
                    Meal::Dinner => "1630001",
                    Meal::LateNight => "2100001",
                }
            }
            DiningCommon::Frank => {
                match meal {
                    Meal::Breakfast => "0700002",
                    Meal::Lunch => "1130002",
                    Meal::Dinner => "1630002",
                    Meal::LateNight => panic!("Frank doesn't have late night"),
                }
            }
            DiningCommon::Hamp => {
                match meal {
                    Meal::Breakfast => "0700003",
                    Meal::Lunch => "1130003",
                    Meal::Dinner => "1630003",
                    Meal::LateNight => panic!("Hamp doesn't have late night"),
                }
            }
            DiningCommon::Berk => {
                match meal {
                    Meal::Breakfast => panic!("Berk doesn't have breakfast"),
                    Meal::Lunch => "1100004",
                    Meal::Dinner => "1630004",
                    Meal::LateNight => "2100004",
                }
            }
        }
        .to_string()

}

fn get_dining_common_code(dining_common: DiningCommon) -> String {
    match dining_common {
            DiningCommon::Worcester => "0",
            DiningCommon::Frank => "1",
            DiningCommon::Hamp => "2",
            DiningCommon::Berk => "3",
        }
        .to_string()
}

fn get_menu_document(dining_common: DiningCommon,
                     meal: Meal)
                     -> Result<select::document::Document, reqwest::Error> {
    let dining_common_id = get_dining_common_code(dining_common.clone());

    let time = time::now();

    let year = time.tm_year + 1900;
    let month = format!("{:02}", time.tm_mon + 1);
    let day = format!("{:02}", time.tm_mday);
    let meal = get_meal_code(meal, dining_common);

    let url: &str = &format!("https://go.umass.\
                              edu/dining/event?feed=dining-halls&id=id_{id}&calendar=dining-halls_id_{id}_event_calendar&startdate={day}-{month}-{year}&event={year}{month}{day}T{meal}%7C{year}{month}{day}T000000&calendarMode=day",
                             id = dining_common_id,
                             year = year,
                             month = month,
                             day = day,
                             meal = meal);

    println!("{}", url);

    get_document(url)

}

fn is_on_menu(dining_common: DiningCommon, meal: Meal, item: &str) -> bool {
    let nodes: Vec<String> = get_menu_document(dining_common, meal)
        .expect("Couldn't get the menu page")
        .find(Class("kgo_web_content"))
        .map(|node| node.text())
        .collect();

    let text: String = nodes.join(" ");

    return text.to_lowercase().as_str().contains(item.to_lowercase().as_str());
}

// Get the token file from memory
fn load_token() -> String {
    let mut token = String::new();
    let _ = File::open("token").expect("No token file").read_to_string(&mut token);
    token
}

// Login to Discord and connect
fn login(listeners: Arc<Mutex<Vec<(ChannelId, String)>>>) -> Client<Handler> {
    Client::new(load_token().trim(), Handler { listeners: listeners })
}

fn check_for(food: String) -> String {
    let mut places: Vec<String> = vec![];

    for dining_common in vec![DiningCommon::Berk,
                              DiningCommon::Hamp,
                              DiningCommon::Frank,
                              DiningCommon::Worcester] {
        let meals = match dining_common.clone() {
            DiningCommon::Berk => vec![Meal::Lunch, Meal::Dinner, Meal::LateNight],
            DiningCommon::Hamp => vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner],
            DiningCommon::Frank => vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner],
            DiningCommon::Worcester => {
                vec![Meal::Breakfast, Meal::Lunch, Meal::Dinner, Meal::LateNight]
            }
        };
        for meal in meals {
            if is_on_menu(dining_common, meal, &food) {
                places.push(format!("{:?} {:?}", dining_common.clone(), meal.clone()).to_string());
            }
        }
    }

    match places.len() {
        0 => format!("{} not found", food).to_string(),
        _ => format!("{}: {}", food, places.join(", ")).to_string(),
    }
}

fn get_guilds() -> Vec<String> {
    let cache = serenity::CACHE.read().unwrap();
    let guilds = cache.all_guilds();
    guilds.into_iter().map(|guild| guild.get().unwrap().name).collect()
}

struct Handler {
    listeners: Arc<Mutex<Vec<(serenity::model::ChannelId, String)>>>,
}

impl EventHandler for Handler {
    fn on_message(&self, _ctx: Context, message: Message) {
        let listeners = self.listeners.clone();

        if !message.content.starts_with("!") {
            // It's not a command, so we don't care about it
            return;
        }

        if message.author.bot {
            // We don't want it to respond to other bots or itself!
            return;
        }

        println!("{}: {} says: {}",
                 message.author.name,
                 message.author.id,
                 message.content);

        let is_owner: bool = message.author.id == 90927967651262464;

        if message.content == "!events" {

            let events = get_events();

            // Intro
            let _ = message.channel_id.say("Today's events are:".to_string());

            let _ = events.iter()
                .map(|event| message.channel_id.say(event.format().to_string()));

        } else if message.content.starts_with("!menu ") {
            let item: String = message.content[6..].to_string();

            let _ = message.channel_id.say(format!("Checking for {}", item).to_string());
            let _ = message.channel_id.say(check_for(item));
        } else if message.content.starts_with("!register ") {
            let item: String = message.content[10..].to_string();
            listeners.lock().unwrap().deref_mut().push((message.channel_id, item.clone()));
            save_listeners(listeners.lock().unwrap().deref_mut());
            let _ = message.channel_id.say(format!("Will check for {}", item).to_string());
        } else if message.content == "!help" {
            let _ = message.channel_id.say("UMass Bot help:");
            let _ = message.channel_id
                .say("```!menu [food name]     | tells you where that food is being served \
                      today```");
            let _ = message.channel_id
                .say("```!register [food name] | schedules it to tell you each day where that \
                      food is being served that day```");
        } else if message.content.starts_with("!guilds") && is_owner {
            let _ = message.channel_id.say(format!("Guilds: {}", get_guilds().join(", ")));
        }
    }
}

fn read_listeners() -> Vec<(serenity::model::ChannelId, String)> {
    let mut listeners_string: String = String::new();
    let _ = OpenOptions::new()
        .read(true)
        .write(true)
        .create(true)
        .open("listeners.txt")
        .expect("No listeners file")
        .read_to_string(&mut listeners_string);

    let mut listeners: Vec<(serenity::model::ChannelId, String)> = vec![];

    for line in listeners_string.split('\n') {
        if line == "" {
            continue;
        }
        let sections: Vec<&str> = line.split(' ').collect();
        let id = serenity::model::ChannelId(sections[0]
            .parse::<u64>()
            .expect("Couldn't parse channel id"));
        let food: String = sections[1..].join(" ").to_string();
        listeners.push((id, food));
    }

    listeners
}

fn save_listeners(vec: &Vec<(serenity::model::ChannelId, String)>) {
    let mut listeners_string: String = String::new();
    vec.into_iter().for_each(|x| {
        let (ref id, ref food) = *x;
        listeners_string = format!("{}\n{} {}", listeners_string, id, food);
    });

    let _ = OpenOptions::new()
        .read(true)
        .write(true)
        .create(true)
        .truncate(true)
        .open("listeners.txt")
        .unwrap()
        .write_all(listeners_string.as_bytes());
}

// Runs at 6 AM
fn get_time_till_scheduled() -> std::time::Duration {
    // The server the bot is deployed on is in UTC, so we have to adjust by 5 hours
    let current_time = time::now();
    let mut next_midnight: time::Tm = (time::now() + time::Duration::days(1)).to_local();
    if current_time.tm_hour < 11 || (current_time.tm_hour == 11 && current_time.tm_min < 5) {
        // We want to do it today (in UTC) if it is still yesterday in Eastern Time
        next_midnight = current_time.to_local();
    }
    next_midnight.tm_sec = 0;
    next_midnight.tm_min = 5;
    next_midnight.tm_hour = 11;

    (next_midnight - time::now()).to_std().unwrap()
}

fn main() {
    // Allow openssl crosscompiling to work
    openssl_probe::init_ssl_cert_env_vars();

    let listeners: Arc<Mutex<Vec<(ChannelId, String)>>> = Arc::new(Mutex::new(read_listeners()));
    let mut client = login(listeners.clone());
    println!("Connected to Discord");
    println!("Connected to servers: {}", get_guilds().join(", "));

    // Listeners loop
    let listeners_clone = listeners.clone();
    thread::spawn(move || {
        let listeners = listeners_clone;
        loop {
            println!("Seconds till scheduled: {:?}", get_time_till_scheduled());
            thread::sleep(get_time_till_scheduled());
            println!("Checking for foods now!");
            listeners.lock().unwrap().to_vec().into_iter().for_each(|(channel, food)| {
                println!("Checking on {:?} for {}", channel, food);
                let _ = channel.say(check_for(food));
            });
        }
    });

    let _ = client.start();

}
<|endoftext|>


<commit_before>/// A genetic algorithm in Rust
/// Copyright (C) 2015  Andrew Schwartzmeyer

#[macro_use]
extern crate clap;
extern crate rand;
extern crate time;

use clap::App;
use std::thread;

mod algorithm;
mod individual;
mod problem;

arg_enum!{
    #[derive(Debug, PartialEq, Eq, Copy, Clone)]
    pub enum Problem {
        Ackley,
        Schwefel
    }
}

#[derive(Debug, Copy, Clone)]
pub struct Parameters {
    tolerance: f64,
    dimension: usize,
    population: usize,
    iterations: usize,
    verbosity: usize
}

/// Setup and run algorithm to search for solution
fn main() {
    let matches = App::new("rust-genetic-algorithm")
        .version(&crate_version!()[..])
        .author("Andrew Schwartzmeyer <andrew@schwartzmeyer.com")
        .about("A genetic algorithm in Rust for Schwefel's function.")
        .args_from_usage(
            "[problem]... 'The problem to solve'
             -t --tolerance [0.05] 'Sets the convergence tolerance'
             -d --dimension [30] 'Sets the dimension of the hypercube'
             -p --population [256] 'Sets the size of the population'
             -i --iterations [5000] 'Sets maximum number of generations'
             [verbose]... -v 'Print fitness (1) and solution (2) every 10th generation'")
        .get_matches();
    let problems = value_t!(matches.values_of("problem"), Problem)
        .unwrap_or(vec![Problem::Schwefel, Problem::Ackley]);
    let parameters = Parameters {
        tolerance: value_t!(matches.value_of("t"), f64).unwrap_or(0.05_f64),
        dimension: value_t!(matches.value_of("d"), usize).unwrap_or(30),
        population: value_t!(matches.value_of("p"), usize).unwrap_or(256),
        iterations: value_t!(matches.value_of("i"), usize).unwrap_or(5000),
        verbosity: matches.occurrences_of("verbose") as usize
    };

    let workers = problems.iter().map(|&problem| {
        thread::spawn(move || algorithm::search(problem, parameters))
    });

    for worker in workers {
        if let Ok(results) = worker.join() {
            if let Some(individual) = results.individual {
                println!("{} converged to {} after {} generations in {} seconds.",
                         results.problem, individual.fitness,
                         results.iterations, results.duration);
                println!("{:?}", individual.solution);
            } else {
                println!("{} failed to converge.", results.problem);
            }
        }
    }
}
<commit_msg>Fix CLI by rewriting with builder pattern<commit_after>/// A genetic algorithm in Rust
/// Copyright (C) 2015  Andrew Schwartzmeyer

#[macro_use]
extern crate clap;
extern crate rand;
extern crate time;

use clap::{App, Arg};
use std::thread;

mod algorithm;
mod individual;
mod problem;

arg_enum!{
    #[derive(Debug, PartialEq, Eq, Copy, Clone)]
    pub enum Problem {
        Ackley,
        Schwefel
    }
}

#[derive(Debug, Copy, Clone)]
pub struct Parameters {
    tolerance: f64,
    dimension: usize,
    population: usize,
    iterations: usize,
    verbosity: usize
}

/// Setup and run algorithm to search for solution
fn main() {
    let matches = App::new("rust-genetic-algorithm")
        .version(&crate_version!()[..])
        .author("Andrew Schwartzmeyer <andrew@schwartzmeyer.com")
        .about("A genetic algorithm in Rust for various benchmark problems.")
        .arg(Arg::with_name("tolerance").short("t").long("tol").takes_value(true)
             .help("Sets the convergence tolerance (0.05)"))
        .arg(Arg::with_name("dimension").short("d").long("dim").takes_value(true)
             .help("Sets the dimension of the hypercube (30)"))
        .arg(Arg::with_name("population").short("p").long("pop").takes_value(true)
             .help("Sets the size of the population (256)"))
        .arg(Arg::with_name("iterations").short("i").long("iter").takes_value(true)
             .help("Sets maximum number of generations (5000)"))
        .arg(Arg::with_name("verbose").short("v").long("verbose").multiple(true)
             .help("Print fitness (1) and solution (2) every 10th generation"))
        .arg(Arg::with_name("problem").multiple(true)
             .help("The problems to solve: Schwefel or Ackley"))
        .get_matches();

    let problems = value_t!(matches.values_of("problem"), Problem)
        .unwrap_or(vec![Problem::Schwefel, Problem::Ackley]);

    let parameters = Parameters {
        tolerance: value_t!(matches.value_of("tolerance"), f64).unwrap_or(0.05_f64),
        dimension: value_t!(matches.value_of("dimension"), usize).unwrap_or(30),
        population: value_t!(matches.value_of("population"), usize).unwrap_or(256),
        iterations: value_t!(matches.value_of("iterations"), usize).unwrap_or(5000),
        verbosity: matches.occurrences_of("verbose") as usize
    };

    let workers = problems.iter().map(|&problem| {
        thread::spawn(move || algorithm::search(problem, parameters))
    });

    for worker in workers {
        if let Ok(results) = worker.join() {
            if let Some(individual) = results.individual {
                println!("{} converged to {} after {} generations in {} seconds.",
                         results.problem, individual.fitness,
                         results.iterations, results.duration);
                println!("{:?}", individual.solution);
            } else {
                println!("{} failed to converge.", results.problem);
            }
        }
    }
}
<|endoftext|>


<commit_before>extern crate html5ever;
#[macro_use(qualname,ns,atom)]
extern crate string_cache;
#[macro_use(format_tendril)]
extern crate tendril;

use html5ever::rcdom::NodeEnum::Element;
use html5ever::rcdom::{RcDom, Handle};
use html5ever::serialize::{SerializeOpts, serialize};
use html5ever::tendril::TendrilSink;
use html5ever::tree_builder::{TreeBuilderOpts, TreeSink, NodeOrText};
use html5ever::{ParseOpts, parse_document};
use std::io;

enum Section {
    Package(Handle),
}

fn main() {
    let opts = ParseOpts {
        tree_builder: TreeBuilderOpts { drop_doctype: true, ..Default::default() },
        ..Default::default()
    };

    let stdin = io::stdin();
    let mut dom = parse_document(RcDom::default(), opts)
                      .from_utf8()
                      .read_from(&mut stdin.lock())
                      .unwrap();

    let mut sections = vec![];
    walk(&dom.document, &mut sections);

    for section in sections {
        match section {
            Section::Package(p) => {
                let attr = html5ever::Attribute {
                    name: qualname!("", "name"),
                    value: format_tendril!("xxx"),
                };
                let dash_link = dom.create_element(qualname!(html, "a"), vec![attr]);
                dom.append_before_sibling(p, NodeOrText::AppendNode(dash_link));
            }
        }
    }

    let mut bytes = vec![];
    serialize(&mut bytes, &dom.document, SerializeOpts::default()).unwrap();
    let result = String::from_utf8(bytes).unwrap();
    println!("{}", result);
}

fn walk(h: &Handle, sections: &mut Vec<Section>) {
    let node = h.borrow();
    for e in node.children.iter() {
        walk(e, sections);
        if let Element(ref qualname, _, _) = e.borrow().node {
            if qualname.local == string_cache::Atom::from("script") {
                sections.push(Section::Package(e.clone()));
            }
        }
    }
}
<commit_msg>Implement correct Method matcher<commit_after>extern crate html5ever;
#[macro_use(qualname,ns,atom)]
extern crate string_cache;
#[macro_use(format_tendril)]
extern crate tendril;

use html5ever::rcdom::NodeEnum::Element;
use html5ever::rcdom::{RcDom, Handle};
use html5ever::serialize::{SerializeOpts, serialize};
use html5ever::tendril::TendrilSink;
use html5ever::tree_builder::{TreeBuilderOpts, TreeSink, NodeOrText};
use html5ever::{ParseOpts, parse_document};
use std::io;

enum Section {
    Method(Handle),
}

fn main() {
    let opts = ParseOpts {
        tree_builder: TreeBuilderOpts { drop_doctype: true, ..Default::default() },
        ..Default::default()
    };

    let stdin = io::stdin();
    let mut dom = parse_document(RcDom::default(), opts)
                      .from_utf8()
                      .read_from(&mut stdin.lock())
                      .unwrap();

    let mut sections = vec![];
    walk(&dom.document, &mut sections);

    let class_attr = html5ever::Attribute {
        name: qualname!("", "class"),
        value: format_tendril!("dashAnchor"),
    };

    // https://kapeli.com/docsets#tableofcontents
    // https://kapeli.com/docsets#supportedentrytypes
    for section in sections {
        match section {
            Section::Method(p) => {
                let name_attr = html5ever::Attribute {
                    name: qualname!("", "name"),
                    value: format_tendril!("//apple_ref/cpp/{}/{}", "entrytype", "entryname"),
                };

                let dash_link = dom.create_element(qualname!(html, "a"),
                                                   vec![name_attr, class_attr.clone()]);
                let _ = dom.append_before_sibling(p, NodeOrText::AppendNode(dash_link));
            }
        }
    }

    let mut bytes = vec![];
    serialize(&mut bytes, &dom.document, SerializeOpts::default()).unwrap();
    let result = String::from_utf8(bytes).unwrap();
    println!("{}", result);
}

fn walk(h: &Handle, sections: &mut Vec<Section>) {
    let node = h.borrow();
    for e in node.children.iter() {
        walk(e, sections);
        if let Element(ref qualname, _, ref attrs) = e.borrow().node {
            if qualname.local == string_cache::Atom::from("h4") && attrs.iter().any(|ref x| x.name == qualname!("", "class") && x.value == format_tendril!("method")) {
                sections.push(Section::Method(e.clone()));
            }
        }
    }
}
<|endoftext|>


<commit_before>extern crate iron;
extern crate staticfile;
extern crate mount;
extern crate router;
extern crate logger;
extern crate handlebars_iron as hbs;
extern crate rustc_serialize;

use std::io::prelude::*;
use std::fs::File;
use std::collections::BTreeMap;

use iron::prelude::*;
use iron::mime::Mime;
use iron::status;
use staticfile::Static;
use mount::Mount;
use router::Router;
use logger::Logger;
use hbs::{Template, HandlebarsEngine, DirectorySource};
use rustc_serialize::json::{ToJson, Json};

fn index(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("index", String::new())).set_mut(status::Ok);
    Ok(resp)
}

fn rules(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("rules", String::new())).set_mut(status::Ok);
    Ok(resp)
}

fn games(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("games", String::new())).set_mut(status::Ok);
    Ok(resp)
}

struct User {
    name: String,
    age: u16,
}

impl ToJson for User {
    fn to_json(&self) -> Json {
        let mut map: BTreeMap<String, Json> = BTreeMap::new();

        map.insert("name".to_string(), self.name.to_json());
        map.insert("age".to_string(), self.age.to_json());
        map.to_json()
    }
}

fn test(_: &mut Request) -> IronResult<Response> {
    let data = User {
        name: "Adam".to_string(),
        age: 32u16,
    };

    let mut resp = Response::new();
    resp.set_mut(Template::new("test", data)).set_mut(status::Ok);
    Ok(resp)
}

fn main() {
    let mut bars = HandlebarsEngine::new2();
    bars.add(Box::new(DirectorySource::new("./templates/", ".hbs")));

    if let Err(r) = bars.reload() {
        panic!("{:?}", r);
    }

    let mut router = Router::new();
    router.
        get("/", index).
        get("/rules", rules).
        get("/games", games).
        get("/test", test);

    let mut mount = Mount::new();
    mount.
        mount("/", router).
        mount("/css", Static::new("public/css")).
        mount("/img", Static::new("public/img"));

    let (logger_before, logger_after) = Logger::new(None);
    let mut chain = Chain::new(mount);
    chain.link_before(logger_before);
    chain.link_after(logger_after);
    chain.link_after(bars);

    let url = "localhost:3000";
    match Iron::new(chain).http(url) {
        Ok(_) => println!("Pluto running on http://{}", url),
        Err(e) => println!("Pluto failed to run. Error: {}", e)
    };
}
<commit_msg>Removed unused imports<commit_after>extern crate iron;
extern crate staticfile;
extern crate mount;
extern crate router;
extern crate logger;
extern crate handlebars_iron as hbs;
extern crate rustc_serialize;

use std::collections::BTreeMap;
use iron::prelude::*;
use iron::status;
use staticfile::Static;
use mount::Mount;
use router::Router;
use logger::Logger;
use hbs::{Template, HandlebarsEngine, DirectorySource};
use rustc_serialize::json::{ToJson, Json};

fn index(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("index", String::new())).set_mut(status::Ok);
    Ok(resp)
}

fn rules(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("rules", String::new())).set_mut(status::Ok);
    Ok(resp)
}

fn games(_: &mut Request) -> IronResult<Response> {
    let mut resp = Response::new();
    resp.set_mut(Template::new("games", String::new())).set_mut(status::Ok);
    Ok(resp)
}

struct User {
    name: String,
    age: u16,
}

impl ToJson for User {
    fn to_json(&self) -> Json {
        let mut map: BTreeMap<String, Json> = BTreeMap::new();

        map.insert("name".to_string(), self.name.to_json());
        map.insert("age".to_string(), self.age.to_json());
        map.to_json()
    }
}

fn test(_: &mut Request) -> IronResult<Response> {
    let data = User {
        name: "Adam".to_string(),
        age: 32u16,
    };

    let mut resp = Response::new();
    resp.set_mut(Template::new("test", data)).set_mut(status::Ok);
    Ok(resp)
}

fn main() {
    let mut bars = HandlebarsEngine::new2();
    bars.add(Box::new(DirectorySource::new("./templates/", ".hbs")));

    if let Err(r) = bars.reload() {
        panic!("{:?}", r);
    }

    let mut router = Router::new();
    router.
        get("/", index).
        get("/rules", rules).
        get("/games", games).
        get("/test", test);

    let mut mount = Mount::new();
    mount.
        mount("/", router).
        mount("/css", Static::new("public/css")).
        mount("/img", Static::new("public/img"));

    let (logger_before, logger_after) = Logger::new(None);
    let mut chain = Chain::new(mount);
    chain.link_before(logger_before);
    chain.link_after(logger_after);
    chain.link_after(bars);

    let url = "localhost:3000";
    match Iron::new(chain).http(url) {
        Ok(_) => println!("Pluto running on http://{}", url),
        Err(e) => println!("Pluto failed to run. Error: {}", e)
    };
}
<|endoftext|>


<commit_before>#![feature(convert, collections)]
#![allow(unused_variables)]

use std::collections::HashMap;
use std::hash::{Hash, Hasher};
use std::io;
use std::io::prelude::*;
use std::rc::Rc;
use std::fmt;

type Dictionary = HashMap<String, Rc<Entry>>;
type Statement = Vec<Op>;
type NativeFn = Box<Fn(&mut Vec<Op>, &mut Interpreter)>;

#[derive(Clone, Debug)]
enum Op {
	Number(i32),
	Word(Rc<Entry>),
}

enum Code {
	Native(NativeFn),
	Forth(Statement),
}

#[derive(Clone)]
struct Entry {
	name: String,
	code: Rc<Code>,
}

impl PartialEq for Entry {
	fn eq(&self, other: &Self) -> bool { self.name == other.name }
}

impl Eq for Entry {}

impl Hash for Entry {
	fn hash<H>(&self, state: &mut H) where H: Hasher {
		self.name.hash(state)
	}
}

impl fmt::Debug for Entry {
	fn fmt(&self, fmt: &mut fmt::Formatter) -> Result<(), fmt::Error> {
		self.name.fmt(fmt)
	}
}

impl Entry {
	fn new(name: &str, code: Code) -> Entry {
		Entry {
			name: String::from_str(name),
			code: Rc::new(code),
		}
	}
}

impl Code {
	fn run(&self, stack: &mut Statement, interp: &mut Interpreter) {
		match self {
			&Code::Native(ref f) => {
				f(stack, interp);
			},
			&Code::Forth(ref statement) => {
				for ref op in statement {
					match *op {
						&Op::Number(ref n) => { break; }
						&Op::Word(ref w) => {
							(*w).code.run(stack, interp);
						},
					}
				}
			},
		}
	}
}

trait StatementExt {
	fn pop_number(&mut self, &mut Interpreter) -> i32;
	fn run(&mut self, &mut Interpreter) -> Result<i32, Statement>;
}

impl StatementExt for Statement {
	fn pop_number(&mut self, interp: &mut Interpreter) -> i32 {
		loop {
			match self.pop() {
				Some(Op::Number(n)) => { return n; },
				Some(Op::Word(s)) => s.code.run(self, interp),
				None => panic!("Popped empty statement"),
			}
		}
	}
	fn run(&mut self, interp: &mut Interpreter) -> Result<i32, Statement> {
		while self.len() > 0 {
			match self.pop() {
				Some(Op::Number(n)) => {
					if self.len() == 0 {
						return Ok(n)
					} else {
						self.push(Op::Number(n));
						return Err(self.clone())
					}
				},
				Some(Op::Word(w)) => {
					let code = interp.dictionary[w.name.as_str()].code.clone();
					code.run(self, interp);
				},
				None => unreachable!(),
			};
		}
		Ok(0)
	}
}

trait DictionaryExt {
	fn insert_entry(&mut self, Entry);
}

impl DictionaryExt for Dictionary {
	fn insert_entry(&mut self, entry: Entry) {
		self.insert(entry.name.clone(), Rc::new(entry));
	}
}

struct Interpreter {
    dictionary: Dictionary,
}

macro_rules! binary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let b = stack.pop_number(interp);
					let a = stack.pop_number(interp);
					stack.push(Op::Number($o(a, b)));
				})),
			)
	}
}

macro_rules! unary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let b = stack.pop_number(interp);
					stack.push(Op::Number($o(a)));
				})),
			)
	}
}

macro_rules! nonary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					Op::Number($o);
				})),
			)
	}
}

impl Interpreter {
	fn new() -> Interpreter {
		let mut dict = Dictionary::new();

		dict.insert_entry(binary_entry!("/", ::std::ops::Div::div));
		dict.insert_entry(binary_entry!("*", ::std::ops::Mul::mul));
		dict.insert_entry(binary_entry!("+", ::std::ops::Add::add));
		dict.insert_entry(binary_entry!("-", ::std::ops::Sub::sub));
		dict.insert_entry(binary_entry!("MOD", ::std::ops::Rem::rem));
		dict.insert_entry(binary_entry!("AND", ::std::ops::BitAnd::bitand));
		dict.insert_entry(binary_entry!("OR", ::std::ops::BitOr::bitor));

		dict.insert_entry(nonary_entry!("QUIT", ::std::process::exit(0)));
		dict.insert_entry(nonary_entry!("bye", ::std::process::exit(0)));

		dict.insert_entry(Entry::new("DUP",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop().unwrap();
					stack.push(x.clone());
					stack.push(x);
				})),
			));

		dict.insert_entry(Entry::new("OVER",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop().unwrap();
					let y = stack.pop().unwrap();
					stack.push(x.clone());
					stack.push(y);
					stack.push(x);
				})),
			));

		dict.insert_entry(Entry::new("ROT",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop().unwrap();
					let y = stack.pop().unwrap();
					let z = stack.pop().unwrap();
					stack.push(y);
					stack.push(x);
					stack.push(z);
				})),
			));

		Interpreter {
			dictionary: dict,
		}
	}

	fn lex(&mut self, statement: &str) -> Statement {
		let words = statement.split(' ');
		let mut ret = Statement::new();
		for word in words {
			if let Some(n) = i32::from_str_radix(word, 10).ok() {
				ret.push(Op::Number(n));
			} else {
				ret.push(Op::Word(self.dictionary[word].clone()));
			}
		};
		ret
	}

	fn exec(&mut self, statement: &str) -> Result<i32, Statement> {
		let mut statement = self.lex(statement);
		return statement.run(self);
	}
}

fn main() {
	println!("forth-rs version 0.1.0");
	println!("Type 'bye' to exit");
    let mut interp = Interpreter::new();
    let mut stdin = io::stdin();
    loop {
    	print!("> ");
    	io::stdout().flush().ok().expect("Could not flush stdout");
    	let mut line = String::new();
    	stdin.read_line(&mut line).ok().expect("Unable to read from stdin");
    	match interp.exec(line.trim_right()) {
    		Err(s) => {
    			println!("{:?}", s);
    		},
    		Ok(n) => {
    			println!("{}", n);
    		},
    	}
    }
}
<commit_msg>Added a bunch of builtins. Fix builtins popping a word rather than executing it.<commit_after>#![feature(convert, collections)]
#![allow(unused_variables)]

use std::collections::HashMap;
use std::hash::{Hash, Hasher};
use std::io;
use std::io::prelude::*;
use std::rc::Rc;
use std::fmt;

type Dictionary = HashMap<String, Rc<Entry>>;
type Statement = Vec<Op>;
type NativeFn = Box<Fn(&mut Vec<Op>, &mut Interpreter)>;

#[derive(Clone, Debug)]
enum Op {
	Number(i32),
	Word(Rc<Entry>),
}

enum Code {
	Native(NativeFn),
	Forth(Statement),
}

#[derive(Clone)]
struct Entry {
	name: String,
	code: Rc<Code>,
}

impl PartialEq for Entry {
	fn eq(&self, other: &Self) -> bool { self.name == other.name }
}

impl Eq for Entry {}

impl Hash for Entry {
	fn hash<H>(&self, state: &mut H) where H: Hasher {
		self.name.hash(state)
	}
}

impl fmt::Debug for Entry {
	fn fmt(&self, fmt: &mut fmt::Formatter) -> Result<(), fmt::Error> {
		self.name.fmt(fmt)
	}
}

impl Entry {
	fn new(name: &str, code: Code) -> Entry {
		Entry {
			name: String::from_str(name),
			code: Rc::new(code),
		}
	}
}

impl Code {
	fn run(&self, stack: &mut Statement, interp: &mut Interpreter) {
		match self {
			&Code::Native(ref f) => {
				f(stack, interp);
			},
			&Code::Forth(ref statement) => {
				for ref op in statement {
					match *op {
						&Op::Number(ref n) => { break; }
						&Op::Word(ref w) => {
							(*w).code.run(stack, interp);
						},
					}
				}
			},
		}
	}
}

trait StatementExt {
	fn pop_number(&mut self, &mut Interpreter) -> i32;
	fn push_number(&mut self, i32);
	fn run(&mut self, &mut Interpreter) -> Result<i32, Statement>;
}

impl StatementExt for Statement {
	fn pop_number(&mut self, interp: &mut Interpreter) -> i32 {
		loop {
			match self.pop() {
				Some(Op::Number(n)) => { return n; },
				Some(Op::Word(s)) => s.code.run(self, interp),
				None => panic!("Popped empty statement"),
			}
		}
	}

	fn push_number(&mut self, number: i32) {
		self.push(Op::Number(number));
	}

	fn run(&mut self, interp: &mut Interpreter) -> Result<i32, Statement> {
		while self.len() > 0 {
			match self.pop() {
				Some(Op::Number(n)) => {
					if self.len() == 0 {
						return Ok(n)
					} else {
						self.push(Op::Number(n));
						return Err(self.clone())
					}
				},
				Some(Op::Word(w)) => {
					let code = interp.dictionary[w.name.as_str()].code.clone();
					code.run(self, interp);
				},
				None => unreachable!(),
			};
		}
		Ok(0)
	}
}

trait DictionaryExt {
	fn insert_entry(&mut self, Entry);
}

impl DictionaryExt for Dictionary {
	fn insert_entry(&mut self, entry: Entry) {
		self.insert(entry.name.clone(), Rc::new(entry));
	}
}

struct Interpreter {
    dictionary: Dictionary,
}

macro_rules! binary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let b = stack.pop_number(interp);
					let a = stack.pop_number(interp);
					stack.push_number($o(a, b));
				})),
			)
	}
}

macro_rules! unary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let a = stack.pop_number(interp);
					stack.push_number($o(a));
				})),
			)
	}
}

macro_rules! nonary_entry {
	($name:expr, $o:expr) => {
		Entry::new($name,
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					Op::Number($o);
				})),
			)
	}
}

impl Interpreter {
	fn new() -> Interpreter {
		let mut dict = Dictionary::new();

		dict.insert_entry(binary_entry!("/", ::std::ops::Div::div));
		dict.insert_entry(binary_entry!("*", ::std::ops::Mul::mul));
		dict.insert_entry(binary_entry!("+", ::std::ops::Add::add));
		dict.insert_entry(binary_entry!("-", ::std::ops::Sub::sub));
		dict.insert_entry(binary_entry!("MOD", ::std::ops::Rem::rem));
		dict.insert_entry(binary_entry!("AND", ::std::ops::BitAnd::bitand));
		dict.insert_entry(binary_entry!("OR", ::std::ops::BitOr::bitor));
		dict.insert_entry(binary_entry!("XOR", ::std::ops::BitXor::bitxor));
		dict.insert_entry(binary_entry!("RSHIFT", ::std::ops::Shr::shr));
		dict.insert_entry(binary_entry!("LSHIFT", ::std::ops::Shl::shl));

		dict.insert_entry(unary_entry!("NEGATE", ::std::ops::Neg::neg));
		dict.insert_entry(unary_entry!("NOT", ::std::ops::Not::not));

		dict.insert_entry(nonary_entry!("bye", ::std::process::exit(0)));

		dict.insert_entry(Entry::new("<",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let y = stack.pop_number(interp);
					let x = stack.pop_number(interp);
					stack.push(if x < y { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new(">",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let y = stack.pop_number(interp);
					let x = stack.pop_number(interp);
					stack.push(if x > y { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new("=",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let y = stack.pop_number(interp);
					let x = stack.pop_number(interp);
					stack.push(if x == y { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new("0<",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push(if x < 0 { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new("0=",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push(if x == 0 { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new("0>",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push(if x > 0 { Op::Number(1) } else { Op::Number(0) });
				})),
			));

		dict.insert_entry(Entry::new("1+",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x + 1);
				})),
			));

		dict.insert_entry(Entry::new("1-",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x - 1);
				})),
			));

		dict.insert_entry(Entry::new("2+",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x + 2);
				})),
			));

		dict.insert_entry(Entry::new("2-",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x - 2);
				})),
			));

		dict.insert_entry(Entry::new("2/",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x >> 1); // Per fst83 standard
				})),
			));

		dict.insert_entry(Entry::new("DUP",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					stack.push_number(x.clone());
					stack.push_number(x);
				})),
			));

		dict.insert_entry(Entry::new("?DUP",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					if x != 0 {
						stack.push_number(x.clone());
						stack.push_number(x);
					} else {
						stack.push_number(x);
					}
				})),
			));

		dict.insert_entry(Entry::new("OVER",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					let y = stack.pop_number(interp);
					stack.push_number(x.clone());
					stack.push_number(y);
					stack.push_number(x);
				})),
			));

		dict.insert_entry(Entry::new("ROT",
				Code::Native(Box::new(|stack: &mut Statement, interp: &mut Interpreter| {
					let x = stack.pop_number(interp);
					let y = stack.pop_number(interp);
					let z = stack.pop_number(interp);
					stack.push_number(y);
					stack.push_number(x);
					stack.push_number(z);
				})),
			));

		Interpreter {
			dictionary: dict,
		}
	}

	fn lex(&mut self, statement: &str) -> Statement {
		let words = statement.split(' ');
		let mut ret = Statement::new();
		for word in words {
			if let Some(n) = i32::from_str_radix(word, 10).ok() {
				ret.push(Op::Number(n));
			} else {
				ret.push(Op::Word(self.dictionary[word].clone()));
			}
		};
		ret
	}

	fn exec(&mut self, statement: &str) -> Result<i32, Statement> {
		let mut statement = self.lex(statement);
		return statement.run(self);
	}
}

fn main() {
	println!("forth-rs version 0.1.0");
	println!("Type 'bye' to exit");
    let mut interp = Interpreter::new();
    let mut stdin = io::stdin();
    loop {
    	print!("> ");
    	io::stdout().flush().ok().expect("Could not flush stdout");
    	let mut line = String::new();
    	stdin.read_line(&mut line).ok().expect("Unable to read from stdin");
    	match interp.exec(line.trim_right()) {
    		Err(s) => {
    			println!("{:?}", s);
    		},
    		Ok(n) => {
    			println!("{}", n);
    		},
    	}
    }
}
<|endoftext|>


<commit_before>//! Implementation of a simple uTP client and server.
#[macro_use]
extern crate log;
extern crate env_logger;
extern crate getopts;
extern crate daemonize;
extern crate udt;
extern crate crypto;
extern crate byteorder;
extern crate rand;
extern crate sodiumoxide;
extern crate rustc_serialize;

use daemonize::{Daemonize};
use std::process::Command;
use std::net::{UdpSocket, SocketAddr, SocketAddrV4, Ipv4Addr};
use std::str;
use std::env;
use std::fs::File;
use std::str::FromStr;
use std::path::Path;
use std::ffi::OsStr;
use std::io::{Cursor, Error, Seek, SeekFrom, ErrorKind, stderr, Read, Write};
use getopts::Options;
use udt::*;
use byteorder::{ReadBytesExt, WriteBytesExt, LittleEndian};
use sodiumoxide::crypto::secretbox;
use sodiumoxide::crypto::secretbox::xsalsa20poly1305::Key;
use rustc_serialize::hex::{FromHex, ToHex};

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

fn send_file(stream: UdtSocket, filename: &str) -> Result<(), Error> {
    let mut f = File::open(filename).unwrap();

    let mut filesize = 0u64;
    let mut buf = vec![0; 1024 * 1024];
    loop {
        match try!(f.read(&mut buf)) {
            0    => { break },
            read => { filesize += read as u64 },
        }
    }

    let mut wtr = vec![];
    wtr.write_u64::<LittleEndian>(filesize).unwrap();
    match stream.sendmsg(&wtr[..]) {
        Ok(0) => {
            return Err(Error::new(ErrorKind::WriteZero, "failed to write filesize header before timeout"))
        },
        Err(e) => {
            return Err(Error::new(ErrorKind::Other, format!("{:?}", e)))
        }
        _ => {
            // println!("wrote filesize of {:.2}kb.", filesize as f64 / 1024f64);
        }
    }
    // let mut total = 0;
    let mut payload = vec![0; 1300];
    f.seek(SeekFrom::Start(0)).unwrap();
    loop {
        match f.read(&mut payload) {
            Ok(0) => {
                // println!("\nEOF.");
                stream.sendmsg(&vec![0;0]).unwrap();
                break;
            }
            Ok(read) => {
                match stream.sendmsg(&payload[0..read]) {
                    Ok(_) =>  { }
                    Err(e) => {
                        stream.close().expect("Error closing stream");
                        panic!("{:?}", e);
                    }
                }
            },
            Err(e) => {
                stream.close().expect("Error closing stream");
                panic!("{:?}", e);
            }
        }
    }

    stream.close().expect("Error closing stream.");
    // println!("all done!");
    Ok(())
}

fn get_open_port(start: u16, end: u16) -> Result<u16, ()> {
    assert!(end >= start);
    let mut p = start;
    loop {
        match UdpSocket::bind(&format!("0.0.0.0:{}", p)[..]) {
            Ok(_) => {
                return Ok(p);
            }
            Err(_) => {
                p += 1;
                if p > end {
                    return Err(());
                }
            }
        }
    }
}

fn recv_file(sock: UdtSocket, filesize: u64, filename: &str) -> Result<(), Error> {
    let mut f = File::create(filename).unwrap();
    let mut total = 0u64;
    loop {
        let buf = try!(sock.recvmsg(1300).map_err(|e| Error::new(ErrorKind::Other, format!("{:?}", e))));
        total += buf.len() as u64;
        f.write_all(&buf[..]).unwrap();
        print!("\rreceived {}kb / {}kb ({:.1}%)", total/1024, filesize/1024, (total as f64/1024f64) / (filesize as f64/1024f64) * 100f64);
        if total >= filesize {
            println!("\nEOF");
            break;
        }
    }
    let _ = sock.close();
    Ok(())
}

fn main() {
    enum Mode {Server, Client}
    env_logger::init().expect("Error starting logger");

    let args: Vec<String> = env::args().collect();
    let program = args[0].clone();
    let mut opts = Options::new();
    // opts.optopt("o", "output", "set output file name", "NAME");
    opts.optflag("s", "server", "server mode");
    opts.optflag("p", "port-range", "server listening port range");
    opts.optflag("h", "help", "print this help menu");

    let matches = match opts.parse(&args[1..]) {
        Ok(m) => { m }
        Err(f) => { panic!(f.to_string()) }
    };

    if matches.opt_present("h") {
        print_usage(&program, opts);
        return;
    }

    let input = if !matches.free.is_empty() {
        matches.free[0].clone()
    } else {
        print_usage(&program, opts);
        return;
    };

    // Parse the mode argument
    let mode: Mode = match matches.opt_present("s") {
        true => Mode::Server,
        false => Mode::Client
    };

    match mode {
        Mode::Server => {
            let ip = env::var("SSH_CONNECTION").unwrap_or(String::from("0.0.0.0"));
            let port = get_open_port(55000, 55100).unwrap();
            let key = secretbox::gen_key();
            match key {
                Key(keybytes) => { println!("shoop 0 {} {} {}", ip, port, keybytes.to_hex()) }
            }

            let daemonize = Daemonize::new();
            match daemonize.start() {
                Ok(_) => { let _ = writeln!(&mut stderr(), "daemonized"); }
                Err(_) => { let _ = writeln!(&mut stderr(), "RWRWARWARARRR"); }
            }

            udt::init();
            let sock = UdtSocket::new(SocketFamily::AFInet, SocketType::Datagram).unwrap();
            sock.setsockopt(UdtOpts::UDP_RCVBUF, 5590000i32).unwrap();
            sock.setsockopt(UdtOpts::UDP_SNDBUF, 5590000i32).unwrap();
            sock.bind(SocketAddr::V4(SocketAddrV4::from_str(&format!("{}:{}", ip, port)[..]).unwrap())).unwrap();

            sock.listen(1).unwrap();

            let (stream, _) = sock.accept().unwrap();
            // dbg(format!("Received new connection from peer {:?}", peer));

            if let Ok(version) = stream.recvmsg(1) {
                // dbg(format!("frand using protocol version {}.", version[0]));
                if version[0] == 0x00 {
                    send_file(stream, &input).unwrap();
                } else {
                    panic!("Unrecognized version.");
                }
            } else {
                panic!("Failed to receive version byte from client.");
            }
        }
        Mode::Client => {
            let sections: Vec<&str> = input.split(":").collect();
            let addr: String = sections[0].to_owned();
            let path: String = sections[1].to_owned();
            let cmd = format!("~/bin/shoop -s {}", path);
            println!("addr: {}, path: {}, cmd: {}", addr, path, cmd);

            let output = Command::new("ssh")
                                 .arg(addr.to_owned())
                                 .arg(cmd)
                                 .output()
                                 .unwrap_or_else(|e| {
                                     panic!("failed to execute process: {}", e);
                                 });
            let infostring = String::from_utf8_lossy(&output.stdout).to_owned().trim().to_owned();
            let info: Vec<&str> = infostring.split(" ").collect();
            if info.len() != 5 {
                panic!("unexpected response format from server");
            }

            let (magic, version, ip, port, keyhex) = (info[0], info[1], info[2], info[3], info[4]);
            if magic != "shoop" || version != "0" {
                panic!("response from server.. i don't know what it means. what does it mean? help me i am so confused.");
            }

            let mut keybytes = [0u8; 32];
            keybytes.copy_from_slice(&keyhex.from_hex().unwrap()[..]);
            let key = Key(keybytes);
            println!("got key {}", keyhex);

            udt::init();
            let sock = UdtSocket::new(SocketFamily::AFInet, SocketType::Datagram).unwrap();
            sock.setsockopt(UdtOpts::UDP_RCVBUF, 5590000i32).unwrap();
            sock.setsockopt(UdtOpts::UDP_SNDBUF, 5590000i32).unwrap();
            let addr: SocketAddr = SocketAddr::V4(SocketAddrV4::from_str(&format!("{}:{}", ip, port)[..]).unwrap());
            // let addr: SocketAddr = SocketAddr::V4(SocketAddrV4::new(Ipv4Addr::from_str(&addr).unwrap(), 55000));
            match sock.connect(addr) {
               Ok(()) => {
                   println!("connected!");
               },
               Err(e) => {
                   panic!("errrrrrrr {:?}", e);
               }
            }

            sock.sendmsg(&[0u8; 1]).unwrap();
            println!("checking if server is frand");

            match sock.recvmsg(8) {
               Ok(msg) => {
                   if msg.len() == 0 {
                       panic!("failed to get filesize from server, probable timeout.");
                   }
                   let mut rdr = Cursor::new(msg);
                   let filesize = rdr.read_u64::<LittleEndian>().unwrap();
                   println!("got reported filesize of {}", filesize);
                   let filename = Path::new(&path).file_name().unwrap_or(OsStr::new("outfile")).to_str().unwrap_or("outfile");
                   println!("writing to {}", filename);
                   recv_file(sock, filesize, filename).unwrap();
               }
               Err(e) => {
                   panic!("{:?}", e);
               }
            }
        }
    }
}

<commit_msg>parse SSH_CONNECTION envvar proplerly-ish<commit_after>//! Implementation of a simple uTP client and server.
#[macro_use]
extern crate log;
extern crate env_logger;
extern crate getopts;
extern crate daemonize;
extern crate udt;
extern crate crypto;
extern crate byteorder;
extern crate rand;
extern crate sodiumoxide;
extern crate rustc_serialize;

use daemonize::{Daemonize};
use std::process::Command;
use std::net::{UdpSocket, SocketAddr, SocketAddrV4, Ipv4Addr};
use std::str;
use std::env;
use std::fs::File;
use std::str::FromStr;
use std::path::Path;
use std::ffi::OsStr;
use std::io::{Cursor, Error, Seek, SeekFrom, ErrorKind, stderr, Read, Write};
use getopts::Options;
use udt::*;
use byteorder::{ReadBytesExt, WriteBytesExt, LittleEndian};
use sodiumoxide::crypto::secretbox;
use sodiumoxide::crypto::secretbox::xsalsa20poly1305::Key;
use rustc_serialize::hex::{FromHex, ToHex};

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

fn send_file(stream: UdtSocket, filename: &str) -> Result<(), Error> {
    let mut f = File::open(filename).unwrap();

    let mut filesize = 0u64;
    let mut buf = vec![0; 1024 * 1024];
    loop {
        match try!(f.read(&mut buf)) {
            0    => { break },
            read => { filesize += read as u64 },
        }
    }

    let mut wtr = vec![];
    wtr.write_u64::<LittleEndian>(filesize).unwrap();
    match stream.sendmsg(&wtr[..]) {
        Ok(0) => {
            return Err(Error::new(ErrorKind::WriteZero, "failed to write filesize header before timeout"))
        },
        Err(e) => {
            return Err(Error::new(ErrorKind::Other, format!("{:?}", e)))
        }
        _ => {
            // println!("wrote filesize of {:.2}kb.", filesize as f64 / 1024f64);
        }
    }
    // let mut total = 0;
    let mut payload = vec![0; 1300];
    f.seek(SeekFrom::Start(0)).unwrap();
    loop {
        match f.read(&mut payload) {
            Ok(0) => {
                // println!("\nEOF.");
                stream.sendmsg(&vec![0;0]).unwrap();
                break;
            }
            Ok(read) => {
                match stream.sendmsg(&payload[0..read]) {
                    Ok(_) =>  { }
                    Err(e) => {
                        stream.close().expect("Error closing stream");
                        panic!("{:?}", e);
                    }
                }
            },
            Err(e) => {
                stream.close().expect("Error closing stream");
                panic!("{:?}", e);
            }
        }
    }

    stream.close().expect("Error closing stream.");
    // println!("all done!");
    Ok(())
}

fn get_open_port(start: u16, end: u16) -> Result<u16, ()> {
    assert!(end >= start);
    let mut p = start;
    loop {
        match UdpSocket::bind(&format!("0.0.0.0:{}", p)[..]) {
            Ok(_) => {
                return Ok(p);
            }
            Err(_) => {
                p += 1;
                if p > end {
                    return Err(());
                }
            }
        }
    }
}

fn recv_file(sock: UdtSocket, filesize: u64, filename: &str) -> Result<(), Error> {
    let mut f = File::create(filename).unwrap();
    let mut total = 0u64;
    loop {
        let buf = try!(sock.recvmsg(1300).map_err(|e| Error::new(ErrorKind::Other, format!("{:?}", e))));
        total += buf.len() as u64;
        f.write_all(&buf[..]).unwrap();
        print!("\rreceived {}kb / {}kb ({:.1}%)", total/1024, filesize/1024, (total as f64/1024f64) / (filesize as f64/1024f64) * 100f64);
        if total >= filesize {
            println!("\nEOF");
            break;
        }
    }
    let _ = sock.close();
    Ok(())
}

fn main() {
    enum Mode {Server, Client}
    env_logger::init().expect("Error starting logger");

    let args: Vec<String> = env::args().collect();
    let program = args[0].clone();
    let mut opts = Options::new();
    // opts.optopt("o", "output", "set output file name", "NAME");
    opts.optflag("s", "server", "server mode");
    opts.optflag("p", "port-range", "server listening port range");
    opts.optflag("h", "help", "print this help menu");

    let matches = match opts.parse(&args[1..]) {
        Ok(m) => { m }
        Err(f) => { panic!(f.to_string()) }
    };

    if matches.opt_present("h") {
        print_usage(&program, opts);
        return;
    }

    let input = if !matches.free.is_empty() {
        matches.free[0].clone()
    } else {
        print_usage(&program, opts);
        return;
    };

    // Parse the mode argument
    let mode: Mode = match matches.opt_present("s") {
        true => Mode::Server,
        false => Mode::Client
    };

    match mode {
        Mode::Server => {
            let sshconnstr = env::var("SSH_CONNECTION").unwrap_or(String::from("0.0.0.0 0 0.0.0.0 22")).trim().to_owned();
            let sshconn: Vec<&str> = sshconnstr.split(" ").collect();
            let ip = sshconn[2];
            let port = get_open_port(55000, 55100).unwrap();
            let key = secretbox::gen_key();
            match key {
                Key(keybytes) => { println!("shoop 0 {} {} {}", ip, port, keybytes.to_hex()) }
            }

            let daemonize = Daemonize::new();
            match daemonize.start() {
                Ok(_) => { let _ = writeln!(&mut stderr(), "daemonized"); }
                Err(_) => { let _ = writeln!(&mut stderr(), "RWRWARWARARRR"); }
            }

            udt::init();
            let sock = UdtSocket::new(SocketFamily::AFInet, SocketType::Datagram).unwrap();
            sock.setsockopt(UdtOpts::UDP_RCVBUF, 5590000i32).unwrap();
            sock.setsockopt(UdtOpts::UDP_SNDBUF, 5590000i32).unwrap();
            sock.bind(SocketAddr::V4(SocketAddrV4::from_str(&format!("{}:{}", ip, port)[..]).unwrap())).unwrap();

            sock.listen(1).unwrap();

            let (stream, _) = sock.accept().unwrap();
            // dbg(format!("Received new connection from peer {:?}", peer));

            if let Ok(version) = stream.recvmsg(1) {
                // dbg(format!("frand using protocol version {}.", version[0]));
                if version[0] == 0x00 {
                    send_file(stream, &input).unwrap();
                } else {
                    panic!("Unrecognized version.");
                }
            } else {
                panic!("Failed to receive version byte from client.");
            }
        }
        Mode::Client => {
            let sections: Vec<&str> = input.split(":").collect();
            let addr: String = sections[0].to_owned();
            let path: String = sections[1].to_owned();
            let cmd = format!("~/bin/shoop -s {}", path);
            println!("addr: {}, path: {}, cmd: {}", addr, path, cmd);

            let output = Command::new("ssh")
                                 .arg(addr.to_owned())
                                 .arg(cmd)
                                 .output()
                                 .unwrap_or_else(|e| {
                                     panic!("failed to execute process: {}", e);
                                 });
            let infostring = String::from_utf8_lossy(&output.stdout).to_owned().trim().to_owned();
            let info: Vec<&str> = infostring.split(" ").collect();
            if info.len() != 5 {
                panic!("unexpected response format from server");
            }

            let (magic, version, ip, port, keyhex) = (info[0], info[1], info[2], info[3], info[4]);
            if magic != "shoop" || version != "0" {
                panic!("response from server.. i don't know what it means. what does it mean? help me i am so confused.");
            }

            let mut keybytes = [0u8; 32];
            keybytes.copy_from_slice(&keyhex.from_hex().unwrap()[..]);
            let key = Key(keybytes);
            println!("got key {}", keyhex);

            udt::init();
            let sock = UdtSocket::new(SocketFamily::AFInet, SocketType::Datagram).unwrap();
            sock.setsockopt(UdtOpts::UDP_RCVBUF, 5590000i32).unwrap();
            sock.setsockopt(UdtOpts::UDP_SNDBUF, 5590000i32).unwrap();
            let addr: SocketAddr = SocketAddr::V4(SocketAddrV4::from_str(&format!("{}:{}", ip, port)[..]).unwrap());
            // let addr: SocketAddr = SocketAddr::V4(SocketAddrV4::new(Ipv4Addr::from_str(&addr).unwrap(), 55000));
            match sock.connect(addr) {
               Ok(()) => {
                   println!("connected!");
               },
               Err(e) => {
                   panic!("errrrrrrr {:?}", e);
               }
            }

            sock.sendmsg(&[0u8; 1]).unwrap();
            println!("checking if server is frand");

            match sock.recvmsg(8) {
               Ok(msg) => {
                   if msg.len() == 0 {
                       panic!("failed to get filesize from server, probable timeout.");
                   }
                   let mut rdr = Cursor::new(msg);
                   let filesize = rdr.read_u64::<LittleEndian>().unwrap();
                   println!("got reported filesize of {}", filesize);
                   let filename = Path::new(&path).file_name().unwrap_or(OsStr::new("outfile")).to_str().unwrap_or("outfile");
                   println!("writing to {}", filename);
                   recv_file(sock, filesize, filename).unwrap();
               }
               Err(e) => {
                   panic!("{:?}", e);
               }
            }
        }
    }
}

<|endoftext|>


<commit_before>//! Muxed. A tmux project manager with no runtime dependencies.
extern crate getopts;
extern crate libc;
extern crate yaml_rust;

use std::env;

mod tmux;
mod project;

/// The main execution method.
/// Verify all the arguments and options passed are valid for the application.
fn main() {
    let args: Vec<String> = env::args().collect();
    let program = args[0].clone();
    let input = args[1].clone();

    project::open(input.clone());
}
<commit_msg>Run muxed<commit_after>//! Muxed. A tmux project manager with no runtime dependencies.
extern crate getopts;
extern crate libc;
extern crate yaml_rust;

use std::env;

mod tmux;
mod project;

use project::processor;

/// The main execution method.
/// Verify all the arguments and options passed are valid for the application.
fn main() {
    let args: Vec<String> = env::args().collect();
    let program = args[0].clone();
    let input = args[1].clone();

    let commands = project::open(input.clone());
    processor::main(&commands);
}
<|endoftext|>


<commit_before>extern crate libc;

use std::io;
use std::thread;
use std::time::Duration;
use std::fs::OpenOptions;
use std::os::unix::fs::OpenOptionsExt;
use std::os::unix::io::AsRawFd;
use std::ptr::{ self, read_volatile, write_volatile };

const GPIO_ADDR : libc::off_t      = 0x3F200000; // BCM2836 and BCM2837 GPIO address
const MEM_BLK_SIZE : libc::size_t  = 4096;       // page size(4KB)

const GPFSEL2_OFFSET_ADDR : isize  = 0x02;       // 0x08 / 4
const GPSET0_OFFSET_ADDR : isize   = 0x07;       // 0x1C / 4
const GPCLR0_OFFSET_ADDR : isize   = 0x0A;       // 0x28 / 4
const GPLEV0_OFFSET_ADDR : isize   = 0x0D;       // 0x34 / 4

const FSEL27_BIT : isize    = 21;
const SET27_BIT : isize     = 27;
const CLR27_BIT : isize     = 27;
const LEV27_BIT : isize     = 27;

const GPFSEL_INPUT : u32    = 0;
const GPFSEL_OUTPUT : u32   = 1;
const FSEL27_MASK : u32     = 0xFF1FFFFF;

const GPLEV_HIGH : u32      = 1;
const ON : u32              = 1;

const SLEEP_DELAY : u64     = 1;

fn main() {
    let mut blink_cnt : i32 = 0;

    let gpio_ptr : *mut u32 = map_gpio().expect( "failed to gpio mapping" );
    let fsel2_reg : *mut u32 = gpio_ptr.wrapping_offset( GPFSEL2_OFFSET_ADDR );
    let clr0_reg : *mut u32 = gpio_ptr.wrapping_offset( GPCLR0_OFFSET_ADDR );

    unsafe {
        write_volatile( fsel2_reg, ( *fsel2_reg & FSEL27_MASK ) | ( GPFSEL_OUTPUT << FSEL27_BIT ) );
    }

    while blink_cnt < 10 {
        blink_led( gpio_ptr );
        thread::sleep( Duration::from_secs( SLEEP_DELAY ) );
        blink_cnt = blink_cnt + 1;
    }

    unsafe {
        write_volatile( clr0_reg, *clr0_reg | ( ( ON << CLR27_BIT ) ) );
        write_volatile( fsel2_reg, ( *fsel2_reg & FSEL27_MASK ) | ( GPFSEL_INPUT << FSEL27_BIT ) );
    }
}

fn map_gpio() -> io::Result<*mut u32>  {
    let mem_file = OpenOptions::new()
                .read( true )
                .write( true )
                .custom_flags( libc::O_SYNC )
                .open( "/dev/gpiomem" )
                .expect( "can't open /dev/gpiomem" );

    unsafe {
        let gpio_ptr = libc::mmap( ptr::null_mut(),
                                   MEM_BLK_SIZE,
                                   libc::PROT_READ | libc::PROT_WRITE,
                                   libc::MAP_SHARED,
                                   mem_file.as_raw_fd(),
                                   GPIO_ADDR );

        if gpio_ptr == libc::MAP_FAILED {
             Err( io::Error::last_os_error() )
        }
        else
        {
            Ok( gpio_ptr as *mut u32 )
        }
    }
}

fn blink_led( gpio_ptr : *mut u32 ) {
    let set0_reg : *mut u32 = gpio_ptr.wrapping_offset( GPSET0_OFFSET_ADDR );
    let clr0_reg : *mut u32 = gpio_ptr.wrapping_offset( GPCLR0_OFFSET_ADDR );
    let lev0_reg : *mut u32 = gpio_ptr.wrapping_offset( GPLEV0_OFFSET_ADDR );
    let level : u32;

    unsafe {
       level = ( read_volatile( lev0_reg ) >> LEV27_BIT ) & 0x00000001;
    }

    if level == GPLEV_HIGH {
        unsafe {
            write_volatile( clr0_reg, *clr0_reg | ( ON << CLR27_BIT ) );
        }
    }
    else
    {
        unsafe {
            write_volatile( set0_reg, *set0_reg | ( ON << SET27_BIT ) );
        }
    }
}
<commit_msg>Unused pointer.wrapping_offset<commit_after>extern crate libc;

use std::io;
use std::thread;
use std::time::Duration;
use std::fs::OpenOptions;
use std::os::unix::fs::OpenOptionsExt;
use std::os::unix::io::AsRawFd;
use std::ptr::{ self, read_volatile, write_volatile };

const GPIO_ADDR : libc::off_t      = 0x3F200000; // BCM2836 and BCM2837 GPIO address
const MEM_BLK_SIZE : libc::size_t  = 4096;       // page size(4KB)

const GPFSEL2_OFFSET_ADDR : isize  = 0x02;       // 0x08 / 4
const GPSET0_OFFSET_ADDR : isize   = 0x07;       // 0x1C / 4
const GPCLR0_OFFSET_ADDR : isize   = 0x0A;       // 0x28 / 4
const GPLEV0_OFFSET_ADDR : isize   = 0x0D;       // 0x34 / 4

const FSEL27_BIT : isize    = 21;
const SET27_BIT : isize     = 27;
const CLR27_BIT : isize     = 27;
const LEV27_BIT : isize     = 27;

const GPFSEL_INPUT : u32    = 0;
const GPFSEL_OUTPUT : u32   = 1;
const FSEL27_MASK : u32     = 0xFF1FFFFF;

const GPLEV_HIGH : u32      = 1;
const ON : u32              = 1;

const SLEEP_DELAY : u64     = 1;

fn main() {
    let mut blink_cnt : i32 = 0;
    let gpio_ptr : *mut u32 = map_gpio().expect( "failed to gpio mapping" );
    let fsel2_reg : *mut u32 = unsafe { gpio_ptr.offset( GPFSEL2_OFFSET_ADDR ) };
    let clr0_reg : *mut u32 = unsafe { gpio_ptr.offset( GPCLR0_OFFSET_ADDR ) };

    unsafe {
        write_volatile( fsel2_reg, ( *fsel2_reg & FSEL27_MASK ) | ( GPFSEL_OUTPUT << FSEL27_BIT ) );
    }

    while blink_cnt < 10 {
        blink_led( gpio_ptr );
        thread::sleep( Duration::from_secs( SLEEP_DELAY ) );
        blink_cnt = blink_cnt + 1;
    }

    unsafe {
        write_volatile( clr0_reg, *clr0_reg | ( ( ON << CLR27_BIT ) ) );
        write_volatile( fsel2_reg, ( *fsel2_reg & FSEL27_MASK ) | ( GPFSEL_INPUT << FSEL27_BIT ) );
    }
}

fn map_gpio() -> io::Result<*mut u32>  {
    let mem_file = OpenOptions::new()
                .read( true )
                .write( true )
                .custom_flags( libc::O_SYNC )
                .open( "/dev/gpiomem" )
                .expect( "can't open /dev/gpiomem" );

    unsafe {
        let gpio_ptr = libc::mmap( ptr::null_mut(),
                                   MEM_BLK_SIZE,
                                   libc::PROT_READ | libc::PROT_WRITE,
                                   libc::MAP_SHARED,
                                   mem_file.as_raw_fd(),
                                   GPIO_ADDR );

        if gpio_ptr == libc::MAP_FAILED {
            Err( io::Error::last_os_error() )
        }
        else
        {
            Ok( gpio_ptr as *mut u32 )
        }
    }
}

fn blink_led( gpio_ptr : *mut u32 ) {
    let set0_reg : *mut u32 = unsafe { gpio_ptr.offset( GPSET0_OFFSET_ADDR ) };
    let clr0_reg : *mut u32 = unsafe { gpio_ptr.offset( GPCLR0_OFFSET_ADDR ) };
    let lev0_reg : *mut u32 = unsafe { gpio_ptr.offset( GPLEV0_OFFSET_ADDR ) };
    let level : u32;

    unsafe {
        level = ( read_volatile( lev0_reg ) >> LEV27_BIT ) & 0x00000001;
    }

    if level == GPLEV_HIGH {
        unsafe {
            write_volatile( clr0_reg, *clr0_reg | ( ON << CLR27_BIT ) );
        }
    }
    else
    {
        unsafe {
            write_volatile( set0_reg, *set0_reg | ( ON << SET27_BIT ) );
        }
    }
}
<|endoftext|>


<commit_before>#![cfg_attr(feature = "clippy", feature(plugin))]
#![cfg_attr(feature = "clippy", plugin(clippy))]

extern crate sdl2;

mod jeebie;

use jeebie::core::cpu::CPU;

use std::env;
use std::thread;
use std::time::Duration;
use std::error::Error;

use sdl2::render::{Canvas, Texture};
use sdl2::pixels::PixelFormatEnum;
use sdl2::event::Event;
use sdl2::keyboard::Keycode;

fn main() {
    let args: Vec<String> = env::args().collect();
    run_emulator(&args[1]).expect("An error occurred when running the emulator");
}

pub fn run_emulator(path: &str) -> Result<(), Box<dyn Error>> {
    let mut emulator = CPU::new_with_path(path)?;
    let sdl_context = sdl2::init()?;
    let video_subsystem = sdl_context.video()?;
    let (width, height) = (160, 144);

    let window = video_subsystem.window("Jeebie", width * 3, height * 3)
        .position_centered()
        .resizable()
        .opengl()
        .build()?;

    let mut event_pump = sdl_context.event_pump()?;
    let mut canvas = window.into_canvas()
                    .present_vsync()
                    .accelerated()
                    .build()?;

    let tc = canvas.texture_creator();
    let mut texture = tc.create_texture_streaming(PixelFormatEnum::RGB24, width, height)?;

    'running: loop {
        // Handle inputs
        for event in event_pump.poll_iter() {
            match event {
                Event::Quit {..} | Event::KeyDown { keycode: Some(Keycode::Escape), .. } => break 'running,
                _ => {},
            };
        }

        // Execute
        let fb = emulator.exec_one_frame();

        // Draw
        draw_step(&mut canvas, &mut texture, &fb)?;

        thread::sleep(Duration::from_millis(16));
    }

    Ok(())
}

fn draw_step(canvas: &mut Canvas<sdl2::video::Window>, texture: &mut Texture, framebuffer: &[(u8, u8, u8)]) -> Result<(), Box<dyn Error>> {
    canvas.clear();

    let (width, height) = (160, 144);

    texture.with_lock(None, |buffer: &mut [u8], pitch: usize| {

        for y in 0..height {
            for x in 0..width {
                let offset = x * 3 + pitch * y;
                let fb_index = x + (y * height);
                let (r, g, b) = framebuffer[fb_index];

                buffer[offset] = r;
                buffer[offset + 1] = g;
                buffer[offset + 2] = b;
            }
        }
    })?;

    canvas.copy(&texture, None, None)?;
    canvas.present();

    Ok(())
}<commit_msg>remove clippy attributes<commit_after>extern crate sdl2;

mod jeebie;

use jeebie::core::cpu::CPU;

use std::env;
use std::thread;
use std::time::Duration;
use std::error::Error;

use sdl2::render::{Canvas, Texture};
use sdl2::pixels::PixelFormatEnum;
use sdl2::event::Event;
use sdl2::keyboard::Keycode;

fn main() {
    let args: Vec<String> = env::args().collect();
    run_emulator(&args[1]).expect("An error occurred when running the emulator");
}

pub fn run_emulator(path: &str) -> Result<(), Box<dyn Error>> {
    let mut emulator = CPU::new_with_path(path)?;
    let sdl_context = sdl2::init()?;
    let video_subsystem = sdl_context.video()?;
    let (width, height) = (160, 144);

    let window = video_subsystem.window("Jeebie", width * 3, height * 3)
        .position_centered()
        .resizable()
        .opengl()
        .build()?;

    let mut event_pump = sdl_context.event_pump()?;
    let mut canvas = window.into_canvas()
                    .present_vsync()
                    .accelerated()
                    .build()?;

    let tc = canvas.texture_creator();
    let mut texture = tc.create_texture_streaming(PixelFormatEnum::RGB24, width, height)?;

    'running: loop {
        // Handle inputs
        for event in event_pump.poll_iter() {
            match event {
                Event::Quit {..} | Event::KeyDown { keycode: Some(Keycode::Escape), .. } => break 'running,
                _ => {},
            };
        }

        // Execute
        let fb = emulator.exec_one_frame();

        // Draw
        draw_step(&mut canvas, &mut texture, &fb)?;

        thread::sleep(Duration::from_millis(16));
    }

    Ok(())
}

fn draw_step(canvas: &mut Canvas<sdl2::video::Window>, texture: &mut Texture, framebuffer: &[(u8, u8, u8)]) -> Result<(), Box<dyn Error>> {
    canvas.clear();

    let (width, height) = (160, 144);

    texture.with_lock(None, |buffer: &mut [u8], pitch: usize| {

        for y in 0..height {
            for x in 0..width {
                let offset = x * 3 + pitch * y;
                let fb_index = x + (y * height);
                let (r, g, b) = framebuffer[fb_index];

                buffer[offset] = r;
                buffer[offset + 1] = g;
                buffer[offset + 2] = b;
            }
        }
    })?;

    canvas.copy(&texture, None, None)?;
    canvas.present();

    Ok(())
}<|endoftext|>


<commit_before>extern crate bismuth;
extern crate glutin;
extern crate nalgebra;

use bismuth::cube::{Cursor, Geometry, LogWidth, Root, Spatial};
use bismuth::event::{ElementState, Event, MouseButton, VirtualKeyCode};
use bismuth::math::{FPoint3, FScalar, IntoSpace, Matrix4Ext, UPoint2, UPoint3, UScalar, UVector3};
use bismuth::render::{AspectRatio, Camera, Context, Projection, ToMeshBuffer, Transform};
use glutin::WindowBuilder;

fn new_root(width: LogWidth) -> Root {
    let cursor = Cursor::at_point_with_span(&UPoint3::origin(), width - 3, &UVector3::new(7, 1, 7));
    let mut root = Root::new(width);
    root.to_cube_mut().subdivide_to_cursor(&cursor);
    root
}

fn new_camera<W, C>(window: &W, cube: &C) -> Camera
    where W: AspectRatio,
          C: Spatial
{
    let midpoint: FPoint3 = cube.partition().midpoint().into_space();
    let projection = {
        let mut projection = Projection::default();
        projection.far = cube.partition().width().exp() as FScalar * 2.0;
        projection
    };
    let mut camera = Camera::new(window, &projection);
    camera.look_at(&FPoint3::new(midpoint.x * 0.25, -midpoint.y, midpoint.z * 3.0),
                   &midpoint);
    camera
}

fn main() {
    let mut context = Context::from_glutin_window(WindowBuilder::new()
        .with_title("Bismuth")
        .with_dimensions(1024, 576)
        .with_vsync()
        .build()
        .unwrap());
    let width = LogWidth::new(8);
    let mut root = new_root(width);
    let mut mesh = root.to_cube().to_mesh_buffer();
    let camera = new_camera(&context.window, &root);
    let mut pointer = UPoint2::origin();
    let mut transform = Transform::default();
    'main: loop {
        transform.camera = camera.transform().to_array();
        for event in context.window.poll_events() {
            match event {
                Event::KeyboardInput(_, _, Some(VirtualKeyCode::Escape)) |
                Event::Closed => {
                    break 'main;
                }
                Event::MouseInput(ElementState::Pressed, MouseButton::Left) => {
                    let ray = camera.cast_ray(&context.window, &pointer);
                    let mut edited = false;
                    if let Some((_, mut cube)) = root.to_cube_mut()
                        .at_ray_mut(&ray, LogWidth::min_value()) {
                        if let Some(leaf) = cube.as_leaf_mut() {
                            leaf.geometry = Geometry::empty();
                            edited = true;
                        }
                    }
                    if edited {
                        mesh = root.to_cube().to_mesh_buffer();
                    }
                }
                Event::MouseMoved(x, y) => {
                    pointer = UPoint2::new(x as UScalar, y as UScalar);
                }
                _ => {}
            }
        }
        context.clear();
        context.set_transform(&transform).unwrap();
        context.draw_mesh_buffer(&mesh);
        context.flush().unwrap();
    }
}
<commit_msg>Refactor `main` to use `framework` module.<commit_after>extern crate bismuth;
extern crate glutin;
extern crate nalgebra;

use bismuth::cube::{Cursor, Geometry, LogWidth, Root, Spatial};
use bismuth::event::{ElementState, Event, MouseButton, Reactor};
use bismuth::framework::{Application, Harness};
use bismuth::input::Mouse;
use bismuth::math::{FMatrix4, FPoint3, FScalar, IntoSpace, UPoint3, UVector3};
use bismuth::render::{AspectRatio, Camera, Context, MeshBuffer, MetaContext, Projection,
                      ToMeshBuffer, Transform};
use glutin::WindowBuilder;

struct Bismuth {
    root: Root,
    mesh: MeshBuffer,
    camera: Camera,
    mouse: Mouse,
}

impl<C> Application<C> for Bismuth
    where C: MetaContext
{
    fn start(context: &mut Context<C>) -> Self {
        let root = new_root(LogWidth::new(8));
        let mesh = root.to_cube().to_mesh_buffer();
        let camera = new_camera(&context.window, &root);
        Bismuth {
            root: root,
            mesh: mesh,
            camera: camera,
            mouse: Mouse::new(),
        }
    }

    fn update(&mut self, context: &mut Context<C>) {
        let mut dirty = false;
        match self.mouse.button(MouseButton::Left) {
            ElementState::Pressed => {
                let ray = self.camera.cast_ray(&context.window, self.mouse.position());
                let mut cube = self.root.to_cube_mut();
                if let Some((_, mut cube)) = cube.at_ray_mut(&ray, LogWidth::min_value()) {
                    if let Some(leaf) = cube.as_leaf_mut() {
                        leaf.geometry = Geometry::empty();
                        dirty = true;
                    }
                }
            }
            _ => {}
        }
        if dirty {
            self.mesh = self.root.to_cube().to_mesh_buffer();
        }
    }

    fn draw(&mut self, context: &mut Context<C>) {
        context.set_transform(&Transform::new(&self.camera.transform(),
                                              &FMatrix4::identity())).unwrap();
        context.draw_mesh_buffer(&self.mesh);
    }

    fn stop(self) {}
}

impl Reactor for Bismuth {
    fn react(&mut self, event: &Event) {
        self.camera.react(event);
        self.mouse.react(event);
    }
}

fn new_root(width: LogWidth) -> Root {
    let cursor = Cursor::at_point_with_span(&UPoint3::origin(), width - 3, &UVector3::new(7, 1, 7));
    let mut root = Root::new(width);
    root.to_cube_mut().subdivide_to_cursor(&cursor);
    root
}

fn new_camera<W, C>(window: &W, cube: &C) -> Camera
    where W: AspectRatio,
          C: Spatial
{
    let midpoint: FPoint3 = cube.partition().midpoint().into_space();
    let projection = {
        let mut projection = Projection::default();
        projection.far = cube.partition().width().exp() as FScalar * 2.0;
        projection
    };
    let mut camera = Camera::new(window, &projection);
    camera.look_at(&FPoint3::new(midpoint.x * 0.25, -midpoint.y, midpoint.z * 3.0),
                   &midpoint);
    camera
}

fn main() {
    let mut harness = Harness::from_glutin_window(WindowBuilder::new()
        .with_title("Bismuth")
        .with_dimensions(1024, 576)
        .with_vsync()
        .build()
        .unwrap());
    harness.start::<Bismuth>();
}
<|endoftext|>


<commit_before>extern crate curl;
extern crate iron;
#[macro_use] extern crate lazy_static;
extern crate plugin;
extern crate queryst;
extern crate regex;
extern crate router;
extern crate rustc_serialize;

mod cmd;
mod error;

use std::error::Error;

use curl::http;

use iron::status;
use iron::prelude::*;

use router::Router;

use rustc_serialize::json::{self, Json};

use cmd::SlashCommand;

#[derive(RustcDecodable)]
struct Config {
    incoming_webhook: String,
    token: String
}

lazy_static! {
    static ref CONFIG: Config = json::decode(include_str!("../assets/config.json")).unwrap();
}

fn veto(req: &mut Request) -> IronResult<Response> {
    let cmd = try!(req.get::<SlashCommand>());
    if &cmd.token != &CONFIG.token[..] {
        return Err(IronError::new(error::AuthError::from("invalid token"), status::Unauthorized));
    }
    let request_json = Json::Object(vec![("text".to_owned(), Json::String(format!("User {:?} has been vetoed", cmd.text)))].into_iter().collect());
    let request_body = json::encode(&request_json).unwrap();
    try!(http::handle().post(&CONFIG.incoming_webhook[..], &request_body).exec().map_err(|e| IronError::new(error::WebhookError::from(e.description()), status::InternalServerError)));
    Ok(Response::with(status::Ok))
}

fn main() {
    // route
    let mut router = Router::new();
    router.post("/veto", veto);
    // serve
    Iron::new(router).http("0.0.0.0:18802").unwrap();
}
<commit_msg>Check status code returned by the incoming webhook request<commit_after>extern crate curl;
extern crate iron;
#[macro_use] extern crate lazy_static;
extern crate plugin;
extern crate queryst;
extern crate regex;
extern crate router;
extern crate rustc_serialize;

mod cmd;
mod error;

use std::error::Error;

use curl::http;

use iron::status;
use iron::prelude::*;

use router::Router;

use rustc_serialize::json::{self, Json};

use cmd::SlashCommand;

#[derive(RustcDecodable)]
struct Config {
    incoming_webhook: String,
    token: String
}

lazy_static! {
    static ref CONFIG: Config = json::decode(include_str!("../assets/config.json")).unwrap();
}

fn veto(req: &mut Request) -> IronResult<Response> {
    let cmd = try!(req.get::<SlashCommand>());
    if &cmd.token != &CONFIG.token[..] {
        return Err(IronError::new(error::AuthError::from("invalid token"), status::Unauthorized));
    }
    let request_json = Json::Object(vec![("text".to_owned(), Json::String(format!("User {:?} has been vetoed", cmd.text)))].into_iter().collect());
    let request_body = json::encode(&request_json).unwrap();
    let response = try!(http::handle().post(&CONFIG.incoming_webhook[..], &request_body).exec().map_err(|e| IronError::new(error::WebhookError::from(e.description()), status::InternalServerError)));
    match response.get_code() {
        404 => {
            let err_msg = match std::str::from_utf8(response.get_body()) {
                Ok(body) => format!("incoming webhook responded {}: {}", response.get_code(), body),
                Err(_) => format!("incoming webhook responded {}", response.get_code())
            };
            Err(IronError::new(error::WebhookError::from(err_msg), status::BadRequest))
        }
        //200 => Ok(Response::with(status::Ok)),
        _ => {
            let err_msg = match std::str::from_utf8(response.get_body()) {
                Ok(body) => format!("incoming webhook responded {}: {}", response.get_code(), body),
                Err(_) => format!("incoming webhook responded {}", response.get_code())
            };
            Err(IronError::new(error::WebhookError::from(err_msg), status::InternalServerError))
        }
    }
}

fn main() {
    // route
    let mut router = Router::new();
    router.post("/veto", veto);
    // serve
    Iron::new(router).http("0.0.0.0:18802").unwrap();
}
<|endoftext|>