<commit_before>extern crate torchrs;
#[macro_use]
extern crate modparse_derive;

use torchrs::autograd::{Variable, BackwardArgs};
use torchrs::tensor::Tensor;
use torchrs::optim;

use torchrs::nn;
use torchrs::nn::{ModuleStruct, ModIntf};
use torchrs::nn::functional::{dropout2d, MaxPool2dArgs, DropoutArgs};
use torchrs::nn::functional as F;
use std::vec;
use std::slice;

type Batch<dT, tT> = (Tensor<dT>, Tensor<tT>);
type Dataset<dT, tT> = Vec<Batch<dT, tT>>;
struct DataLoader<dT, tT> {
    dataset: Dataset<dT, tT>,
}

impl<dT, tT> DataLoader<dT, tT> {
    pub fn new() -> Self {
        DataLoader { dataset: Vec::new() }
    }
    pub fn iter(&self) -> slice::Iter<Batch<dT, tT>> {
        self.dataset.as_slice().iter()
    }
    pub fn iter_mut(&mut self) -> slice::IterMut<Batch<dT, tT>> {
        self.dataset.as_mut_slice().iter_mut()
    }
    pub fn len(&self) -> usize {
        self.dataset.len()
    }
}

#[derive(Default)]
struct NetArgs {
    log_interval: usize,
    cuda: bool,
}

#[derive(ModParse)]
struct Net {
    delegate: nn::Module<f32>,
    conv1: nn::Conv2d<f32>,
    conv2: nn::Conv2d<f32>,
    fc1: nn::Linear<f32>,
    fc2: nn::Linear<f32>,
}

impl Net {
    pub fn new() -> Net {
        let mut t = Net {
            delegate: nn::Module::new(),
            conv1: nn::Conv2d::build(1, 10, 5).done(),
            conv2: nn::Conv2d::build(10, 20, 5).done(),
            fc1: nn::Linear::build(320, 50).done(),
            fc2: nn::Linear::build(50, 10).done(),
        };
        t.init_module();
        t
    }
}
// The forward operations could take on one of two implementations.
// The first supporting a near verbatim version of the python
// implementation, and the second supporting a slightly more
// idiomatic to Rust method chaining.

// a) as a near verbatim implementation of the python version
impl ModIntf<f32> for Net {
    fn forward(&mut self, args: &mut Variable<f32>) -> Variable<f32> {
        let training = self.delegate.training;
        let pool_val = MaxPool2dArgs::default();
        let dropout_val = DropoutArgs::default();
        let mut x = F::relu(&F::max_pool2d(&self.conv1.f(args), (2, 2), &pool_val));
        let mut x = F::relu(&F::max_pool2d(&dropout2d(&self.conv2.f(&mut x), &dropout_val),
                                           (2, 2),
                                           &pool_val));
        let mut x = x.view(&[-1, 320]);
        let x = F::relu(&self.fc1.f(&mut x));
        let mut x = F::dropout(&x, &dropout_val);
        let x = self.fc2.f(&mut x);
        F::log_softmax(&x)
    }
    fn forwardv(&mut self, input: &mut Vec<Variable<f32>>) -> Vec<Variable<f32>> {
        panic!("not valid")
    }

    fn delegate(&mut self) -> &mut nn::Module<f32> {
        &mut self.delegate
    }
}

fn train(model: &mut Net,
         args: &NetArgs,
         train_loader: &DataLoader<f32, i64>,
         epoch: u32,
         optimizer: &mut optim::OptIntf) {
    model.train();
    for (batch_idx, &(ref data, ref target)) in train_loader.iter().enumerate() {
        let (mut data, target) = if args.cuda {
            (Variable::new(data.cuda().clone()), Variable::new(target.cuda().clone()))
        } else {
            (Variable::new(data.clone()), Variable::new(target.clone()))
        };
        optimizer.zero_grad();
        let output = model.f(&mut data);
        let mut loss = F::nll_loss(&output, &target, &F::NLLLossArgs::default());
        loss.backward(&BackwardArgs::default());
        optimizer.step();
        if batch_idx % args.log_interval == 0 {
            println!("Train Epoch: {} [{}/{} ({:.0}%)]\tLoss: {:.6}",
                     epoch,
                     batch_idx * data.data().len(),
                     train_loader.dataset.len(),
                     100. * (batch_idx as f32) / train_loader.len() as f32,
                     loss.data()[0]);
        }
    }
}

fn test(model: &mut Net, args: &NetArgs, test_loader: &DataLoader<f32, i64>, epoch: u32) {
    model.eval();
    let mut test_loss = 0.;
    let mut correct = 0;
    for &(ref data, ref target) in test_loader.iter() {
        let (mut data, mut target) = if args.cuda {
            (Variable::new_volatile(data.cuda().clone()), Variable::new(target.cuda().clone()))
        } else {
            (Variable::new(data.clone()), Variable::new(target.clone()))
        };
        let mut output = model.f(&mut data);
        test_loss += F::nll_loss(&output, &target, &F::NLLLossArgs::default());
        let pred = output.data().reduce_max(1).1;
        correct += pred.tensor_eq(target.data()).cpu().sum();
    }
    test_loss /= test_loader.len() as f32;
    println!("\nTest set: Average loss: {:.4}, Accuracy: {}/{} ({:.0}%)\n",
             test_loss,
             correct,
             test_loader.dataset.len(),
             100. * (correct as f32) / (test_loader.dataset.len() as f32))

}

fn main() {
    let epochs = 10;
    // no data loaders yet so demonstrate with Vec placeholder
    let train_loader: DataLoader<f32, i64> = DataLoader::new();
    let test_loader: DataLoader<f32, i64> = DataLoader::new();
    let args = NetArgs::default();
    let mut optimizer = optim::SGD::new();

    let mut model = Net::new();
    for epoch in 1..epochs + 1 {
        train(&mut model, &args, &train_loader, epoch, &mut optimizer);
        test(&mut model, &args, &test_loader, epoch);
    }
}
<commit_msg>add parse_args, use default values for now<commit_after>extern crate torchrs;
extern crate getopts;
#[macro_use]
extern crate modparse_derive;
#[macro_use]
extern crate derive_builder;

use torchrs::autograd::{Variable, BackwardArgs};
use torchrs::tensor::Tensor;
use torchrs::optim;

use torchrs::nn;
use torchrs::nn::{ModuleStruct, ModIntf};
use torchrs::nn::functional as F;
use std::vec;
use std::slice;

use getopts::Options;
use std::env;

type Batch<dT, tT> = (Tensor<dT>, Tensor<tT>);
type Dataset<dT, tT> = Vec<Batch<dT, tT>>;
struct DataLoader<dT, tT> {
    dataset: Dataset<dT, tT>,
}

impl<dT, tT> DataLoader<dT, tT> {
    pub fn new() -> Self {
        DataLoader { dataset: Vec::new() }
    }
    pub fn iter(&self) -> slice::Iter<Batch<dT, tT>> {
        self.dataset.as_slice().iter()
    }
    pub fn iter_mut(&mut self) -> slice::IterMut<Batch<dT, tT>> {
        self.dataset.as_mut_slice().iter_mut()
    }
    pub fn len(&self) -> usize {
        self.dataset.len()
    }
}

#[derive(ModParse)]
struct Net {
    delegate: nn::Module<f32>,
    conv1: nn::Conv2d<f32>,
    conv2: nn::Conv2d<f32>,
    fc1: nn::Linear<f32>,
    fc2: nn::Linear<f32>,
}

impl Net {
    pub fn new() -> Net {
        let mut t = Net {
            delegate: nn::Module::new(),
            conv1: nn::Conv2d::build(1, 10, 5).done(),
            conv2: nn::Conv2d::build(10, 20, 5).done(),
            fc1: nn::Linear::build(320, 50).done(),
            fc2: nn::Linear::build(50, 10).done(),
        };
        t.init_module();
        t
    }
}
// The forward operations could take on one of two implementations.
// The first supporting a near verbatim version of the python
// implementation, and the second supporting a slightly more
// idiomatic to Rust method chaining.

// a) as a near verbatim implementation of the python version
impl ModIntf<f32> for Net {
    fn forward(&mut self, args: &mut Variable<f32>) -> Variable<f32> {
        let training = self.delegate.training;
        let pool_val = F::MaxPool2dArgs::default();
        let dropout_val = F::DropoutArgs::default();
        let mut x = F::relu(&F::max_pool2d(&self.conv1.f(args), (2, 2), &pool_val));
        let mut x = F::relu(&F::max_pool2d(&F::dropout2d(&self.conv2.f(&mut x), &dropout_val),
                                           (2, 2),
                                           &pool_val));
        let mut x = x.view(&[-1, 320]);
        let x = F::relu(&self.fc1.f(&mut x));
        let mut x = F::dropout(&x, &dropout_val);
        let x = self.fc2.f(&mut x);
        F::log_softmax(&x)
    }
    fn forwardv(&mut self, input: &mut Vec<Variable<f32>>) -> Vec<Variable<f32>> {
        panic!("not valid")
    }

    fn delegate(&mut self) -> &mut nn::Module<f32> {
        &mut self.delegate
    }
}

fn train(model: &mut Net,
         args: &NetArgs,
         train_loader: &DataLoader<f32, i64>,
         epoch: u32,
         optimizer: &mut optim::OptIntf) {
    model.train();
    for (batch_idx, &(ref data, ref target)) in train_loader.iter().enumerate() {
        let (mut data, target) = if args.cuda {
            (Variable::new(data.cuda().clone()), Variable::new(target.cuda().clone()))
        } else {
            (Variable::new(data.clone()), Variable::new(target.clone()))
        };
        optimizer.zero_grad();
        let output = model.f(&mut data);
        let mut loss = F::nll_loss(&output, &target, &F::NLLLossArgs::default());
        loss.backward(&BackwardArgs::default());
        optimizer.step();
        if batch_idx % args.log_interval == 0 {
            println!("Train Epoch: {} [{}/{} ({:.0}%)]\tLoss: {:.6}",
                     epoch,
                     batch_idx * data.data().len(),
                     train_loader.dataset.len(),
                     100. * (batch_idx as f32) / train_loader.len() as f32,
                     loss.data()[0]);
        }
    }
}

fn test(model: &mut Net, args: &NetArgs, test_loader: &DataLoader<f32, i64>, epoch: u32) {
    model.eval();
    let mut test_loss = 0.;
    let mut correct = 0;
    for &(ref data, ref target) in test_loader.iter() {
        let (mut data, mut target) = if args.cuda {
            (Variable::new_volatile(data.cuda().clone()), Variable::new(target.cuda().clone()))
        } else {
            (Variable::new(data.clone()), Variable::new(target.clone()))
        };
        let mut output = model.f(&mut data);
        test_loss += F::nll_loss(&output, &target, &F::NLLLossArgs::default());
        let pred = output.data().reduce_max(1).1;
        correct += pred.tensor_eq(target.data()).cpu().sum();
    }
    test_loss /= test_loader.len() as f32;
    println!("\nTest set: Average loss: {:.4}, Accuracy: {}/{} ({:.0}%)\n",
             test_loss,
             correct,
             test_loader.dataset.len(),
             100. * (correct as f32) / (test_loader.dataset.len() as f32))

}

#[derive(Clone, Builder)]
struct NetArgs {
    #[builder(default="64")]
    batch_size: usize,
    #[builder(default="1000")]
    test_batch_size: usize,
    #[builder(default="10")]
    epochs: u32,
    #[builder(default="0.01")]
    lr: f32,
    #[builder(default="0.5")]
    momentum: f32,
    #[builder(default="true")]
    cuda: bool,
    #[builder(default="1")]
    seed: usize,
    #[builder(default="10")]
    log_interval: usize,
}

impl Default for NetArgs {
    fn default() -> Self {
        NetArgsBuilder::default().build().unwrap()
    }
}

fn parse_args() -> NetArgs {
    let cmd_args: Vec<String> = env::args().collect();
    let mut args = NetArgs::default();
    let mut opts = Options::new();
    /*
    	* XXX do parsey stuff
    	*/
    args
}

fn main() {
    // no data loaders yet so demonstrate with Vec placeholder
    let train_loader: DataLoader<f32, i64> = DataLoader::new();
    let test_loader: DataLoader<f32, i64> = DataLoader::new();
    let args = parse_args();
    let mut optimizer = optim::SGD::new();

    let mut model = Net::new();
    for epoch in 1..args.epochs + 1 {
        train(&mut model, &args, &train_loader, epoch, &mut optimizer);
        test(&mut model, &args, &test_loader, epoch);
    }
}
<|endoftext|>


<commit_before>extern crate winit;
use std::time::{Duration, Instant};
use winit::window::WindowBuilder;
use winit::event::{Event, WindowEvent, StartCause};
use winit::event_loop::{EventLoop, ControlFlow};

fn main() {
    let event_loop = EventLoop::new();

    let _window = WindowBuilder::new()
        .with_title("A fantastic window!")
        .build(&event_loop)
        .unwrap();

    event_loop.run(move |event, _, control_flow| {
        println!("{:?}", event);

        match event {
            Event::NewEvents(StartCause::Init) =>
                *control_flow = ControlFlow::WaitUntil(Instant::now() + Duration::new(1, 0)),
            Event::NewEvents(StartCause::ResumeTimeReached{..}) => {
                *control_flow = ControlFlow::WaitUntil(Instant::now() + Duration::new(1, 0));
                println!("\nTimer\n");
                _window.set_inner_size(winit::dpi::LogicalSize::new(300.0, 300.0));
            },
            Event::WindowEvent {
                event: WindowEvent::CloseRequested,
                ..
            } => *control_flow = ControlFlow::Exit,
            _ => ()
        }
    });
}
<commit_msg>Remove window resize call in timer example (#938)<commit_after>extern crate winit;
use std::time::{Duration, Instant};
use winit::window::WindowBuilder;
use winit::event::{Event, WindowEvent, StartCause};
use winit::event_loop::{EventLoop, ControlFlow};

fn main() {
    let event_loop = EventLoop::new();

    let _window = WindowBuilder::new()
        .with_title("A fantastic window!")
        .build(&event_loop)
        .unwrap();

    let timer_length = Duration::new(1, 0);

    event_loop.run(move |event, _, control_flow| {
        println!("{:?}", event);

        match event {
            Event::NewEvents(StartCause::Init) =>
                *control_flow = ControlFlow::WaitUntil(Instant::now() + timer_length),
            Event::NewEvents(StartCause::ResumeTimeReached{..}) => {
                *control_flow = ControlFlow::WaitUntil(Instant::now() + timer_length);
                println!("\nTimer\n");
            },
            Event::WindowEvent {
                event: WindowEvent::CloseRequested,
                ..
            } => *control_flow = ControlFlow::Exit,
            _ => ()
        }
    });
}
<|endoftext|>


<commit_before>use std::hash::Hash;
use std::collections::HashMap;
use std::ops::DerefMut;

use Data;
use dataflow::channels::pact::Pipeline;
use dataflow::channels::Content;
use dataflow::{Stream, Scope};
use dataflow::operators::unary::Unary;

pub trait Delay<G: Scope, D: Data> {
    fn delay<F: Fn(&D, &G::Timestamp)->G::Timestamp+'static>(&self, F) -> Self;
    fn delay_batch<F: Fn(&G::Timestamp)->G::Timestamp+'static>(&self, F) -> Self;
}

impl<G: Scope, D: Data> Delay<G, D> for Stream<G, D>
where G::Timestamp: Hash {
    fn delay<F: Fn(&D, &G::Timestamp)->G::Timestamp+'static>(&self, func: F) -> Stream<G, D> {
        let mut elements = HashMap::new();
        self.unary_notify(Pipeline, "Delay", vec![], move |input, output, notificator| {
            while let Some((time, data)) = input.next() {
                for datum in data.drain(..) {
                    let new_time = func(&datum, &time);
                    assert!(new_time >= time.time());
                    elements.entry(new_time)
                            .or_insert_with(|| { notificator.notify_at(time.delayed(&new_time)); Vec::new() })
                            .push(datum);
                }
            }
            // for each available notification, send corresponding set
            for (time, _count) in notificator {
                if let Some(mut data) = elements.remove(&time) {
                    output.session(&time).give_iterator(data.drain(..));
                }
            }
        })
    }

    fn delay_batch<F: Fn(&G::Timestamp)->G::Timestamp+'static>(&self, func: F) -> Stream<G, D> {
        let mut stash = Vec::new();
        let mut elements = HashMap::new();
        self.unary_notify(Pipeline, "Delay", vec![], move |input, output, notificator| {
            while let Some((time, data)) = input.next() {
                let new_time = func(&time);
                assert!(new_time >= time.time());
                let spare = stash.pop().unwrap_or_else(Vec::new);
                let data = ::std::mem::replace(data.deref_mut(), spare);

                elements.entry(new_time)
                        .or_insert_with(|| { notificator.notify_at(time.delayed(&new_time)); Vec::new() })
                        .push(data);
            }

            // for each available notification, send corresponding set
            for (time, _count) in notificator {
                if let Some(mut datas) = elements.remove(&time) {
                    for mut data in datas.drain(..) {
                        let mut message = Content::from_typed(&mut data);
                        output.session(&time).give_content(&mut message);
                        let buffer = message.into_typed();
                        if buffer.capacity() == Content::<D>::default_length() { stash.push(buffer); }
                    }
                }
            }
        })
    }
}
<commit_msg>updated documentation and tests for delay<commit_after>//! Operators acting on timestamps to logically delay records

use std::hash::Hash;
use std::collections::HashMap;
use std::ops::DerefMut;

use Data;
use dataflow::channels::pact::Pipeline;
use dataflow::channels::Content;
use dataflow::{Stream, Scope};
use dataflow::operators::unary::Unary;

/// Methods to advance the timestamps of records or batches of records.
pub trait Delay<G: Scope, D: Data> {
    /// Advances the timestamp of records using a supplied function.
    ///
    /// The function *must* advance the timestamp; the operator will test that the
    /// new timestamp is greater or equal to the old timestamp, and will assert if
    /// it is not.
    ///
    /// #Examples
    ///
    /// The following example takes the sequence `0..10` at time `RootTimestamp(0)`
    /// and delays each element `i` to time `RootTimestamp(i)`.
    ///
    /// ```
    /// use timely::dataflow::operators::{ToStream, Delay, Unary};
    /// use timely::dataflow::channels::pact::Pipeline;
    /// use timely::progress::timestamp::RootTimestamp;
    ///
    /// timely::example(|scope| {
    ///     (0..10).to_stream(scope)
    ///            .delay(|data, time| RootTimestamp::new(*data))
    ///            .unary_stream(Pipeline, "example", |input, output| {
    ///                while let Some((time, data)) = input.next() {
    ///                    println!("data at time: {:?}", time);
    ///                    output.session(&time).give_content(data);
    ///                }
    ///            });
    /// });
    /// ```
    fn delay<F: Fn(&D, &G::Timestamp)->G::Timestamp+'static>(&self, F) -> Self;
    /// Advances the timestamp of batches of records using a supplied function.
    ///
    /// The function *must* advance the timestamp; the operator will test that the
    /// new timestamp is greater or equal to the old timestamp, and will assert if
    /// it is not. The batch version does not consult the data, and may only view
    /// the timestamp itself.
    ///
    /// #Examples
    ///
    /// The following example takes the sequence `0..10` at time `RootTimestamp(0)`
    /// and delays each batch (there is just one) to time `RootTimestamp(1)`.
    ///
    /// ```
    /// use timely::dataflow::operators::{ToStream, Delay, Unary};
    /// use timely::dataflow::channels::pact::Pipeline;
    /// use timely::progress::timestamp::RootTimestamp;
    ///
    /// timely::example(|scope| {
    ///     (0..10).to_stream(scope)
    ///            .delay_batch(|time| RootTimestamp::new(time.inner + 1))
    ///            .unary_stream(Pipeline, "example", |input, output| {
    ///                while let Some((time, data)) = input.next() {
    ///                    println!("data at time: {:?}", time);
    ///                    output.session(&time).give_content(data);
    ///                }
    ///            });
    /// });
    /// ```
    fn delay_batch<F: Fn(&G::Timestamp)->G::Timestamp+'static>(&self, F) -> Self;
}

impl<G: Scope, D: Data> Delay<G, D> for Stream<G, D>
where G::Timestamp: Hash {
    fn delay<F: Fn(&D, &G::Timestamp)->G::Timestamp+'static>(&self, func: F) -> Stream<G, D> {
        let mut elements = HashMap::new();
        self.unary_notify(Pipeline, "Delay", vec![], move |input, output, notificator| {
            while let Some((time, data)) = input.next() {
                for datum in data.drain(..) {
                    let new_time = func(&datum, &time);
                    assert!(new_time >= time.time());
                    elements.entry(new_time)
                            .or_insert_with(|| { notificator.notify_at(time.delayed(&new_time)); Vec::new() })
                            .push(datum);
                }
            }
            // for each available notification, send corresponding set
            for (time, _count) in notificator {
                if let Some(mut data) = elements.remove(&time) {
                    output.session(&time).give_iterator(data.drain(..));
                }
            }
        })
    }

    fn delay_batch<F: Fn(&G::Timestamp)->G::Timestamp+'static>(&self, func: F) -> Stream<G, D> {
        let mut stash = Vec::new();
        let mut elements = HashMap::new();
        self.unary_notify(Pipeline, "Delay", vec![], move |input, output, notificator| {
            while let Some((time, data)) = input.next() {
                let new_time = func(&time);
                assert!(new_time >= time.time());
                let spare = stash.pop().unwrap_or_else(Vec::new);
                let data = ::std::mem::replace(data.deref_mut(), spare);

                elements.entry(new_time)
                        .or_insert_with(|| { notificator.notify_at(time.delayed(&new_time)); Vec::new() })
                        .push(data);
            }

            // for each available notification, send corresponding set
            for (time, _count) in notificator {
                if let Some(mut datas) = elements.remove(&time) {
                    for mut data in datas.drain(..) {
                        let mut message = Content::from_typed(&mut data);
                        output.session(&time).give_content(&mut message);
                        let buffer = message.into_typed();
                        if buffer.capacity() == Content::<D>::default_length() { stash.push(buffer); }
                    }
                }
            }
        })
    }
}
<|endoftext|>


<commit_before>//! Caches run-time feature detection so that it only needs to be computed
//! once.

#![allow(dead_code)] // not used on all platforms

use crate::sync::atomic::Ordering;

#[cfg(target_pointer_width = "64")]
use crate::sync::atomic::AtomicU64;

#[cfg(target_pointer_width = "32")]
use crate::sync::atomic::AtomicU32;

/// Sets the `bit` of `x`.
#[inline]
const fn set_bit(x: u64, bit: u32) -> u64 {
    x | 1 << bit
}

/// Tests the `bit` of `x`.
#[inline]
const fn test_bit(x: u64, bit: u32) -> bool {
    x & (1 << bit) != 0
}

/// Unset the `bit of `x`.
#[inline]
const fn unset_bit(x: u64, bit: u32) -> u64 {
    x & !(1 << bit)
}

/// Maximum number of features that can be cached.
const CACHE_CAPACITY: u32 = 63;

/// This type is used to initialize the cache
#[derive(Copy, Clone)]
pub(crate) struct Initializer(u64);

#[allow(clippy::use_self)]
impl Default for Initializer {
    fn default() -> Self {
        Initializer(0)
    }
}

impl Initializer {
    /// Tests the `bit` of the cache.
    #[allow(dead_code)]
    #[inline]
    pub(crate) fn test(self, bit: u32) -> bool {
        // FIXME: this way of making sure that the cache is large enough is
        // brittle.
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        test_bit(self.0, bit)
    }

    /// Sets the `bit` of the cache.
    #[inline]
    pub(crate) fn set(&mut self, bit: u32) {
        // FIXME: this way of making sure that the cache is large enough is
        // brittle.
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        let v = self.0;
        self.0 = set_bit(v, bit);
    }

    /// Unsets the `bit` of the cache.
    #[inline]
    pub(crate) fn unset(&mut self, bit: u32) {
        // FIXME: this way of making sure that the cache is large enough is
        // brittle.
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        let v = self.0;
        self.0 = unset_bit(v, bit);
    }
}

/// This global variable is a cache of the features supported by the CPU.
static CACHE: Cache = Cache::uninitialized();

/// Feature cache with capacity for `CACHE_CAPACITY` features.
///
/// Note: the last feature bit is used to represent an
/// uninitialized cache.
#[cfg(target_pointer_width = "64")]
struct Cache(AtomicU64);

#[cfg(target_pointer_width = "64")]
#[allow(clippy::use_self)]
impl Cache {
    /// Creates an uninitialized cache.
    #[allow(clippy::declare_interior_mutable_const)]
    const fn uninitialized() -> Self {
        Cache(AtomicU64::new(u64::max_value()))
    }
    /// Is the cache uninitialized?
    #[inline]
    pub(crate) fn is_uninitialized(&self) -> bool {
        self.0.load(Ordering::Relaxed) == u64::max_value()
    }

    /// Is the `bit` in the cache set?
    #[inline]
    pub(crate) fn test(&self, bit: u32) -> bool {
        test_bit(CACHE.0.load(Ordering::Relaxed), bit)
    }

    /// Initializes the cache.
    #[inline]
    pub(crate) fn initialize(&self, value: Initializer) {
        self.0.store(value.0, Ordering::Relaxed);
    }
}

/// Feature cache with capacity for `CACHE_CAPACITY` features.
///
/// Note: the last feature bit is used to represent an
/// uninitialized cache.
#[cfg(target_pointer_width = "32")]
struct Cache(AtomicU32, AtomicU32);

#[cfg(target_pointer_width = "32")]
impl Cache {
    /// Creates an uninitialized cache.
    const fn uninitialized() -> Self {
        Cache(
            AtomicU32::new(u32::max_value()),
            AtomicU32::new(u32::max_value()),
        )
    }
    /// Is the cache uninitialized?
    #[inline]
    pub(crate) fn is_uninitialized(&self) -> bool {
        self.1.load(Ordering::Relaxed) == u32::max_value()
    }

    /// Is the `bit` in the cache set?
    #[inline]
    pub(crate) fn test(&self, bit: u32) -> bool {
        if bit < 32 {
            test_bit(CACHE.0.load(Ordering::Relaxed) as u64, bit)
        } else {
            test_bit(CACHE.1.load(Ordering::Relaxed) as u64, bit - 32)
        }
    }

    /// Initializes the cache.
    #[inline]
    pub(crate) fn initialize(&self, value: Initializer) {
        let lo: u32 = value.0 as u32;
        let hi: u32 = (value.0 >> 32) as u32;
        self.0.store(lo, Ordering::Relaxed);
        self.1.store(hi, Ordering::Relaxed);
    }
}
cfg_if! {
    if #[cfg(feature = "std_detect_env_override")] {
        fn env_override(mut value: Initializer) -> Initializer {
            if let Ok(disable) = crate::env::var("RUST_STD_DETECT_UNSTABLE") {
                for v in disable.split(" ") {
                    let _ = super::Feature::from_str(v).map(|v| value.unset(v as u32));
                }
                value
            } else {
                value
            }
        }
    } else {
        #[inline]
        fn env_override(value: Initializer) -> Initializer {
            value
        }
    }
}

/// Tests the `bit` of the storage. If the storage has not been initialized,
/// initializes it with the result of `f()`.
///
/// On its first invocation, it detects the CPU features and caches them in the
/// `CACHE` global variable as an `AtomicU64`.
///
/// It uses the `Feature` variant to index into this variable as a bitset. If
/// the bit is set, the feature is enabled, and otherwise it is disabled.
///
/// If the feature `std_detect_env_override` is enabled looks for the env
/// variable `RUST_STD_DETECT_UNSTABLE` and uses its its content to disable
/// Features that would had been otherwise detected.
#[inline]
pub(crate) fn test<F>(bit: u32, f: F) -> bool
where
    F: FnOnce() -> Initializer,
{
    if CACHE.is_uninitialized() {
        CACHE.initialize(env_override(f()));
    }
    CACHE.test(bit)
}
<commit_msg>Remove the FIXME about the cache size checks<commit_after>//! Caches run-time feature detection so that it only needs to be computed
//! once.

#![allow(dead_code)] // not used on all platforms

use crate::sync::atomic::Ordering;

#[cfg(target_pointer_width = "64")]
use crate::sync::atomic::AtomicU64;

#[cfg(target_pointer_width = "32")]
use crate::sync::atomic::AtomicU32;

/// Sets the `bit` of `x`.
#[inline]
const fn set_bit(x: u64, bit: u32) -> u64 {
    x | 1 << bit
}

/// Tests the `bit` of `x`.
#[inline]
const fn test_bit(x: u64, bit: u32) -> bool {
    x & (1 << bit) != 0
}

/// Unset the `bit of `x`.
#[inline]
const fn unset_bit(x: u64, bit: u32) -> u64 {
    x & !(1 << bit)
}

/// Maximum number of features that can be cached.
const CACHE_CAPACITY: u32 = 63;

/// This type is used to initialize the cache
#[derive(Copy, Clone)]
pub(crate) struct Initializer(u64);

#[allow(clippy::use_self)]
impl Default for Initializer {
    fn default() -> Self {
        Initializer(0)
    }
}

// NOTE: the `debug_assert!` would catch that we do not add more Features than
// the one fitting our cache.
impl Initializer {
    /// Tests the `bit` of the cache.
    #[allow(dead_code)]
    #[inline]
    pub(crate) fn test(self, bit: u32) -> bool {
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        test_bit(self.0, bit)
    }

    /// Sets the `bit` of the cache.
    #[inline]
    pub(crate) fn set(&mut self, bit: u32) {
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        let v = self.0;
        self.0 = set_bit(v, bit);
    }

    /// Unsets the `bit` of the cache.
    #[inline]
    pub(crate) fn unset(&mut self, bit: u32) {
        debug_assert!(
            bit < CACHE_CAPACITY,
            "too many features, time to increase the cache size!"
        );
        let v = self.0;
        self.0 = unset_bit(v, bit);
    }
}

/// This global variable is a cache of the features supported by the CPU.
static CACHE: Cache = Cache::uninitialized();

/// Feature cache with capacity for `CACHE_CAPACITY` features.
///
/// Note: the last feature bit is used to represent an
/// uninitialized cache.
#[cfg(target_pointer_width = "64")]
struct Cache(AtomicU64);

#[cfg(target_pointer_width = "64")]
#[allow(clippy::use_self)]
impl Cache {
    /// Creates an uninitialized cache.
    #[allow(clippy::declare_interior_mutable_const)]
    const fn uninitialized() -> Self {
        Cache(AtomicU64::new(u64::max_value()))
    }
    /// Is the cache uninitialized?
    #[inline]
    pub(crate) fn is_uninitialized(&self) -> bool {
        self.0.load(Ordering::Relaxed) == u64::max_value()
    }

    /// Is the `bit` in the cache set?
    #[inline]
    pub(crate) fn test(&self, bit: u32) -> bool {
        test_bit(CACHE.0.load(Ordering::Relaxed), bit)
    }

    /// Initializes the cache.
    #[inline]
    pub(crate) fn initialize(&self, value: Initializer) {
        self.0.store(value.0, Ordering::Relaxed);
    }
}

/// Feature cache with capacity for `CACHE_CAPACITY` features.
///
/// Note: the last feature bit is used to represent an
/// uninitialized cache.
#[cfg(target_pointer_width = "32")]
struct Cache(AtomicU32, AtomicU32);

#[cfg(target_pointer_width = "32")]
impl Cache {
    /// Creates an uninitialized cache.
    const fn uninitialized() -> Self {
        Cache(
            AtomicU32::new(u32::max_value()),
            AtomicU32::new(u32::max_value()),
        )
    }
    /// Is the cache uninitialized?
    #[inline]
    pub(crate) fn is_uninitialized(&self) -> bool {
        self.1.load(Ordering::Relaxed) == u32::max_value()
    }

    /// Is the `bit` in the cache set?
    #[inline]
    pub(crate) fn test(&self, bit: u32) -> bool {
        if bit < 32 {
            test_bit(CACHE.0.load(Ordering::Relaxed) as u64, bit)
        } else {
            test_bit(CACHE.1.load(Ordering::Relaxed) as u64, bit - 32)
        }
    }

    /// Initializes the cache.
    #[inline]
    pub(crate) fn initialize(&self, value: Initializer) {
        let lo: u32 = value.0 as u32;
        let hi: u32 = (value.0 >> 32) as u32;
        self.0.store(lo, Ordering::Relaxed);
        self.1.store(hi, Ordering::Relaxed);
    }
}
cfg_if! {
    if #[cfg(feature = "std_detect_env_override")] {
        fn env_override(mut value: Initializer) -> Initializer {
            if let Ok(disable) = crate::env::var("RUST_STD_DETECT_UNSTABLE") {
                for v in disable.split(" ") {
                    let _ = super::Feature::from_str(v).map(|v| value.unset(v as u32));
                }
                value
            } else {
                value
            }
        }
    } else {
        #[inline]
        fn env_override(value: Initializer) -> Initializer {
            value
        }
    }
}

/// Tests the `bit` of the storage. If the storage has not been initialized,
/// initializes it with the result of `f()`.
///
/// On its first invocation, it detects the CPU features and caches them in the
/// `CACHE` global variable as an `AtomicU64`.
///
/// It uses the `Feature` variant to index into this variable as a bitset. If
/// the bit is set, the feature is enabled, and otherwise it is disabled.
///
/// If the feature `std_detect_env_override` is enabled looks for the env
/// variable `RUST_STD_DETECT_UNSTABLE` and uses its its content to disable
/// Features that would had been otherwise detected.
#[inline]
pub(crate) fn test<F>(bit: u32, f: F) -> bool
where
    F: FnOnce() -> Initializer,
{
    if CACHE.is_uninitialized() {
        CACHE.initialize(env_override(f()));
    }
    CACHE.test(bit)
}
<|endoftext|>


<commit_before>use std::ffi::CString;
use std::ptr;

use class::TypeParams;
use ctxt::{Fct, FctId, FctParent, FctSrc, SemContext};
use ty::{BuiltinType, MachineMode};

use dora_parser::ast::*;

use llvm;
use llvm::core::*;
// use llvm::execution_engine::*;
// use llvm::target::*;

pub fn generate<'ast>(
    ctxt: &SemContext<'ast>,
    id: FctId,
    cls_type_params: &TypeParams,
    fct_type_params: &TypeParams,
) -> Result<*const u8, ()> {
    let fct = ctxt.fcts[id].borrow();
    let src = fct.src();
    let mut src = src.borrow_mut();

    generate_fct(ctxt, &fct, &mut src, cls_type_params, fct_type_params)
}

pub fn generate_fct<'ast>(
    ctxt: &SemContext<'ast>,
    fct: &Fct<'ast>,
    src: &mut FctSrc,
    cls_type_params: &TypeParams,
    fct_type_params: &TypeParams,
) -> Result<*const u8, ()> {
    let name = fct.full_name(ctxt);

    let mut cg = CodeGen {
        ctxt: ctxt,
        fct: fct,
        ast: fct.ast,
        src: src,
        cls_type_params,
        fct_type_params,

        fct_name: CString::new(name).unwrap(),

        context: ptr::null_mut(),
        module: ptr::null_mut(),
        builder: ptr::null_mut(),
        function: ptr::null_mut(),
    };

    cg.generate()
}

struct CodeGen<'a, 'ast: 'a> {
    ctxt: &'a SemContext<'ast>,
    fct: &'a Fct<'ast>,
    ast: &'ast Function,
    src: &'a mut FctSrc,
    cls_type_params: &'a TypeParams,
    fct_type_params: &'a TypeParams,

    fct_name: CString,

    context: *mut llvm::LLVMContext,
    module: *mut llvm::LLVMModule,
    builder: *mut llvm::LLVMBuilder,
    function: *mut llvm::LLVMValue,
}

impl<'a, 'ast> CodeGen<'a, 'ast>
where
    'ast: 'a,
{
    fn generate(&mut self) -> Result<*const u8, ()> {
        self.init();
        self.create_function()?;

        Err(())
    }

    fn init(&mut self) {
        unsafe {
            self.context = LLVMContextCreate();
            self.module = LLVMModuleCreateWithNameInContext(
                self.fct_name.as_ptr(),
                self.context,
            );
            self.builder = LLVMCreateBuilderInContext(self.context);
        }
    }

    fn create_function(&mut self) -> Result<(), ()> {
        let mut params = Vec::with_capacity(self.ast.params.len());

        for param in &self.ast.params {
            let ty = self.ty(param.id);
            params.push(self.llvm_ty(ty));
        }

        let return_type = self.specialize_type(self.fct.return_type);
        let llvm_return_type = self.llvm_ty(return_type);

        unsafe {
            let function_type = LLVMFunctionType(
                llvm_return_type,
                params.as_mut_ptr(),
                params.len() as u32,
                0);

            self.function = LLVMAddFunction(self.module, self.fct_name.as_ptr(), function_type);
        }

        Err(())
    }

    fn ty(&self, id: NodeId) -> BuiltinType {
        let ty = self.src.ty(id);
        self.specialize_type(ty)
    }

    fn specialize_type(&self, ty: BuiltinType) -> BuiltinType {
        match ty {
            BuiltinType::ClassTypeParam(cls_id, id) => {
                assert!(self.fct.parent == FctParent::Class(cls_id));
                self.cls_type_params[id.idx()]
            }

            BuiltinType::FctTypeParam(fct_id, id) => {
                assert!(self.fct.id == fct_id);
                self.fct_type_params[id.idx()]
            }

            BuiltinType::Class(cls_id, list_id) => {
                let params = self.ctxt.lists.borrow().get(list_id);

                let params: Vec<_> = params.iter().map(|t| self.specialize_type(t)).collect();

                let list_id = self.ctxt.lists.borrow_mut().insert(params.into());

                BuiltinType::Class(cls_id, list_id)
            }

            BuiltinType::Lambda(_) => unimplemented!(),

            _ => ty,
        }
    }

    fn llvm_ty(&self, ty: BuiltinType) -> *mut llvm::LLVMType {
        let mode = ty.mode();

        unsafe {
            match mode {
                MachineMode::Int64 => LLVMInt64TypeInContext(self.context),
                MachineMode::Int32 => LLVMInt32TypeInContext(self.context),
                MachineMode::Int8 => LLVMInt8TypeInContext(self.context),
                MachineMode::Float32 => LLVMFloatTypeInContext(self.context),
                MachineMode::Float64 => LLVMDoubleTypeInContext(self.context),
                MachineMode::Ptr => {
                    let int8 = LLVMInt8TypeInContext(self.context);
                    LLVMPointerType(int8, 1)
                }
            }
        }
    }
}
<commit_msg>opt: emit return stmt<commit_after>use std::ffi::CString;
use std::ptr;

use class::TypeParams;
use ctxt::{Fct, FctId, FctParent, FctSrc, SemContext};
use ty::{BuiltinType, MachineMode};

use dora_parser::ast::*;
use dora_parser::ast::Expr::*;
use dora_parser::ast::Stmt::*;

use llvm;
use llvm::core::*;
// use llvm::execution_engine::*;
// use llvm::target::*;

pub fn generate<'ast>(
    ctxt: &SemContext<'ast>,
    id: FctId,
    cls_type_params: &TypeParams,
    fct_type_params: &TypeParams,
) -> Result<*const u8, ()> {
    let fct = ctxt.fcts[id].borrow();
    let src = fct.src();
    let mut src = src.borrow_mut();

    generate_fct(ctxt, &fct, &mut src, cls_type_params, fct_type_params)
}

pub fn generate_fct<'ast>(
    ctxt: &SemContext<'ast>,
    fct: &Fct<'ast>,
    src: &mut FctSrc,
    cls_type_params: &TypeParams,
    fct_type_params: &TypeParams,
) -> Result<*const u8, ()> {
    let name = fct.full_name(ctxt);

    let mut cg = CodeGen {
        ctxt: ctxt,
        fct: fct,
        ast: fct.ast,
        src: src,
        cls_type_params,
        fct_type_params,

        fct_name: CString::new(name).unwrap(),

        context: ptr::null_mut(),
        module: ptr::null_mut(),
        builder: ptr::null_mut(),
        function: ptr::null_mut(),
    };

    cg.generate()
}

type EmitResult<T> = Result<T, ()>;

fn fail<T>() -> EmitResult<T> {
    Err(())
}

fn ok<T>(value: T) -> EmitResult<T> {
    Ok(value)
}

struct CodeGen<'a, 'ast: 'a> {
    ctxt: &'a SemContext<'ast>,
    fct: &'a Fct<'ast>,
    ast: &'ast Function,
    src: &'a mut FctSrc,
    cls_type_params: &'a TypeParams,
    fct_type_params: &'a TypeParams,

    fct_name: CString,

    context: *mut llvm::LLVMContext,
    module: *mut llvm::LLVMModule,
    builder: *mut llvm::LLVMBuilder,
    function: *mut llvm::LLVMValue,
}

impl<'a, 'ast> CodeGen<'a, 'ast>
where
    'ast: 'a,
{
    fn generate(&mut self) -> Result<*const u8, ()> {
        self.init();
        self.create_function()?;

        let block = self.ast.block.as_ref().unwrap();
        self.emit_stmt(block)?;

        Err(())
    }

    fn init(&mut self) {
        unsafe {
            self.context = LLVMContextCreate();
            self.module = LLVMModuleCreateWithNameInContext(
                self.fct_name.as_ptr(),
                self.context,
            );
            self.builder = LLVMCreateBuilderInContext(self.context);
        }
    }

    fn create_function(&mut self) -> Result<(), ()> {
        let mut params = Vec::with_capacity(self.ast.params.len());

        for param in &self.ast.params {
            let ty = self.ty(param.id);
            params.push(self.llvm_ty(ty));
        }

        let return_type = self.specialize_type(self.fct.return_type);
        let llvm_return_type = self.llvm_ty(return_type);

        unsafe {
            let function_type = LLVMFunctionType(
                llvm_return_type,
                params.as_mut_ptr(),
                params.len() as u32,
                0);

            self.function = LLVMAddFunction(self.module, self.fct_name.as_ptr(), function_type);
        }

        Err(())
    }

    fn emit_stmt(&mut self, s: &'ast Stmt) -> EmitResult<()> {
        match *s {
            StmtExpr(ref stmt) => {
                self.emit_expr(&stmt.expr)?;

                Ok(())
            }

            StmtIf(_) => fail(),
            StmtLoop(_) => fail(),
            StmtWhile(_) => fail(),
            StmtFor(_) => fail(),
            StmtReturn(ref stmt) => self.emit_return(stmt),
            StmtBreak(_) => fail(),
            StmtContinue(_) => fail(),
            StmtBlock(_) => fail(),
            StmtVar(_) => fail(),
            StmtThrow(_) => fail(),
            StmtDefer(_) => fail(),
            StmtDo(_) => fail(),
            StmtSpawn(_) => fail(),
        }
    }

    fn emit_expr(&mut self, e: &'ast Expr) -> EmitResult<*mut llvm::LLVMValue> {
        match *e {
            ExprLitChar(_) => fail(),
            ExprLitInt(_) => fail(),
            ExprLitFloat(_) => fail(),
            ExprLitBool(_) => fail(),
            ExprLitStr(_) => fail(),
            ExprLitStruct(_) => fail(),
            ExprUn(_) => fail(),
            ExprIdent(_) => fail(),
            ExprAssign(_) => fail(),
            ExprBin(_) => fail(),
            ExprCall(_) => fail(),
            ExprDelegation(_) => fail(),
            ExprField(_) => fail(),
            ExprSelf(_) => fail(),
            ExprSuper(_) => fail(),
            ExprNil(_) => fail(),
            ExprArray(_) => fail(),
            ExprConv(_) => fail(),
            ExprTry(_) => fail(),
            ExprLambda(_) => fail(),
        }
    }

    fn emit_return(&mut self, s: &'ast StmtReturnType) -> EmitResult<()> {
        if let Some(ref expr) = s.expr {
            let value = self.emit_expr(expr)?;

            unsafe {
                LLVMBuildRet(self.builder, value);
            }

        } else {
            unsafe {
                LLVMBuildRetVoid(self.builder);
            }
        }

        ok(())
    }

    fn ty(&self, id: NodeId) -> BuiltinType {
        let ty = self.src.ty(id);
        self.specialize_type(ty)
    }

    fn specialize_type(&self, ty: BuiltinType) -> BuiltinType {
        match ty {
            BuiltinType::ClassTypeParam(cls_id, id) => {
                assert!(self.fct.parent == FctParent::Class(cls_id));
                self.cls_type_params[id.idx()]
            }

            BuiltinType::FctTypeParam(fct_id, id) => {
                assert!(self.fct.id == fct_id);
                self.fct_type_params[id.idx()]
            }

            BuiltinType::Class(cls_id, list_id) => {
                let params = self.ctxt.lists.borrow().get(list_id);

                let params: Vec<_> = params.iter().map(|t| self.specialize_type(t)).collect();

                let list_id = self.ctxt.lists.borrow_mut().insert(params.into());

                BuiltinType::Class(cls_id, list_id)
            }

            BuiltinType::Lambda(_) => unimplemented!(),

            _ => ty,
        }
    }

    fn llvm_ty(&self, ty: BuiltinType) -> *mut llvm::LLVMType {
        let mode = ty.mode();

        unsafe {
            match mode {
                MachineMode::Int64 => LLVMInt64TypeInContext(self.context),
                MachineMode::Int32 => LLVMInt32TypeInContext(self.context),
                MachineMode::Int8 => LLVMInt8TypeInContext(self.context),
                MachineMode::Float32 => LLVMFloatTypeInContext(self.context),
                MachineMode::Float64 => LLVMDoubleTypeInContext(self.context),
                MachineMode::Ptr => {
                    let int8 = LLVMInt8TypeInContext(self.context);
                    LLVMPointerType(int8, 1)
                }
            }
        }
    }
}
<|endoftext|>


<commit_before>const VERSION: &'static str = env!("CARGO_PKG_VERSION");

use std::env;
use std::fs;
use std::path::{Path, PathBuf};
use clap::{App, AppSettings, Arg, ArgMatches};

pub fn get_options() -> Options {
    let matches = build_cli_parser().get_matches();
    Options::from_matches(matches)
}

// Has crazy lifetimes due to how clap works. The app return value is never
// exposed outside of this module, so I'm not very concerned.
fn build_cli_parser<'a>() -> App<'a, 'a, 'a, 'a, 'a, 'a> {
    App::new("cargo-bump")
        .version(VERSION)
        .author("Wraithan McCarroll <xwraithanx@gmail.com>")
        .usage("cargo bump [FLAGS] [<version> | major | minor | patch]")
        .about("Increments the version number in Cargo.toml as specified.")
        .setting(AppSettings::ArgRequiredElseHelp)
        .version_short("v")
        .arg(Arg::with_name("bump")
             .possible_value("bump")
             .index(1)
             .required(true)
             .hidden(true))
        .arg(Arg::with_name("no_git")
             .long("no-git-tag-version")
             .help("Disables the git iteractions"))
        .arg(Arg::with_name("message")
             .short("m")
             .long("message")
             .takes_value(true)
             .help("Commit message, %s will be replaced with new version number"))
        .arg(Arg::with_name("version")
             .index(2)
             .help("Version should be a semver (https://semver.org/) string or the
               position of the current version to increment: major, minor or patch."))
}

fn search_up_for(root: &Path, target: &str) -> Option<PathBuf> {
    let mut current = root;

    loop {
        let potential = current.join(target);

        if fs::metadata(&potential).is_ok() {
            return Some(potential)
        }

        match current.parent() {
            Some(parent) => current = parent,
            None => return None
        }
    }
}

fn has_git_on_path() -> bool {
    if let Some(paths) = env::var_os("PATH") {
        for path in env::split_paths(&paths) {
            let potential = path.join("git");
            if fs::metadata(&potential).is_ok() {
                return true
            }
        }
    }
    false
}

#[derive(Debug, PartialEq)]
pub struct Options {
    version: NewVersion,
    git_tag: bool,
    message: String,
    root: PathBuf,
    manifest: PathBuf
}

impl Options {
    fn from_matches(matches: ArgMatches) -> Options {
        let cwd = env::current_dir().unwrap();
        let manifest = search_up_for(&cwd, "Cargo.toml").unwrap_or_else(|| panic!("couldn't find Cargo.toml"));
        let mut root = manifest.clone();
        root.pop();
        let has_git = has_git_on_path();
        let has_git_dir = has_git && search_up_for(&root, ".git").is_some();
        Options{
            version: NewVersion::from_str(matches.value_of("version").unwrap_or("patch")),
            git_tag: has_git_dir && !matches.is_present("no_git"),
            message: matches.value_of("message").unwrap_or("v%s").to_owned(),
            root: root,
            manifest: manifest
        }
    }
}

#[derive(Debug, PartialEq)]
pub enum NewVersion {
    String(String),
    Major,
    Minor,
    Patch
}

impl NewVersion {
    fn from_str(input: &str) -> NewVersion {
        match input {
            "major" => NewVersion::Major,
            "minor" => NewVersion::Minor,
            "patch" => NewVersion::Patch,
            _ => NewVersion::String(input.to_owned())

        }
    }
}

#[cfg(test)]
mod tests {
    use super::{NewVersion, Options, build_cli_parser};
    use std::env;

    fn test_options(input: Vec<&str>, version: NewVersion, git_tag: bool, message: &str) {
        let parser = build_cli_parser();
        let root = env::current_dir().unwrap();
        let mut manifest = root.clone();
        manifest.push("Cargo.toml");
        let matches = parser.get_matches_from_safe(input).unwrap();
        let options = Options::from_matches(matches);
        assert_eq!(options.version, version);
        assert_eq!(options.git_tag, git_tag);
        assert_eq!(&options.message, message);
        assert_eq!(options.root, root);
        assert_eq!(options.manifest, manifest);
    }

    #[test]
    fn bump_arg_only() {
        let input = vec!["cargo-bump", "bump"];
        test_options(input, NewVersion::Patch, true, "v%s")
    }

    #[test]
    fn version_arg_minor() {
        let input = vec!["cargo-bump", "bump", "minor"];
        test_options(input, NewVersion::Minor, true, "v%s")
    }

    #[test]
    fn git_tag_version_set() {
        let input = vec!["cargo-bump", "bump", "--no-git-tag-version"];
        test_options(input, NewVersion::Patch, false, "v%s")
    }

    #[test]
    fn commit_message_set() {
        let input = vec!["cargo-bump", "bump", "-m", "releasing version %s"];
        test_options(input, NewVersion::Patch, true, "releasing version %s")
    }
}
<commit_msg>clean up forgotten rename<commit_after><|endoftext|>


<commit_before>extern crate reql;
#[macro_use]
extern crate slog;
extern crate slog_term;

use reql::{r, Run};
use slog::{Logger, DrainExt};
//use reql::types;
/*
use ql2::commands::ReadMode::Outdated;
use ql2::commands::IdentifierFormat::Uuid;
*/
#[test]
fn db_works() {
    let log = Logger::root(slog_term::streamer().build().fuse(), o!("test" => "driver"));
    reql::set_logger(&log);
    r.connection().connect().unwrap();
    /*
    let query = r.table("heroes").map(|hero: Arg| {
            //(row as Command<types::Object, ()>).get_field::<_, types::Object>("villain")
            hero.get_field::<_, types::Object>("villain")
        })
        ;
        */
    /*
    let query = r.table("heroes").map(|hero: Arg| {
            //(row as Command<types::Object, ()>).get_field::<_, types::Object>("villain")
            hero.get_field::<_, types::Object>("villain")
        })
        ;
    */

    /*
    let query = r.map("John Doe", |seq| {
        //seq.info()
    });
    */
    let query = r.table("heroes").run::<()>().unwrap();
    for row in query {
        debug!(log, "{:?}", row);
    }
}
<commit_msg>Propagate errors<commit_after>extern crate reql;
#[macro_use]
extern crate slog;
extern crate slog_term;

use reql::{r, Run};
use slog::{Logger, DrainExt};
//use reql::types;
/*
use ql2::commands::ReadMode::Outdated;
use ql2::commands::IdentifierFormat::Uuid;
*/
#[test]
fn db_works() {
    let log = Logger::root(slog_term::streamer().build().fuse(), o!("test" => "driver"));
    reql::set_logger(&log);
    r.connection().connect().unwrap();
    /*
    let query = r.table("heroes").map(|hero: Arg| {
            //(row as Command<types::Object, ()>).get_field::<_, types::Object>("villain")
            hero.get_field::<_, types::Object>("villain")
        })
        ;
        */
    /*
    let query = r.table("heroes").map(|hero: Arg| {
            //(row as Command<types::Object, ()>).get_field::<_, types::Object>("villain")
            hero.get_field::<_, types::Object>("villain")
        })
        ;
    */

    /*
    let query = r.map("John Doe", |seq| {
        //seq.info()
    });
    */
    r.table_create("heroes").run::<()>().unwrap().into_iter().next();
    let query = r.table("heroes").changes().run::<()>().unwrap();
    for row in query {
        debug!(log, "{:?}", row);
    }
}
<|endoftext|>


<commit_before>use syntax::{
    ast::{self, AstNode},
    match_ast,
};

use crate::{AssistContext, AssistId, AssistKind, Assists};

// Assist: extract_type_alias
//
// Extracts the selected type as a type alias.
//
// ```
// struct S {
//     field: $0(u8, u8, u8)$0,
// }
// ```
// ->
// ```
// type $0Type = (u8, u8, u8);
//
// struct S {
//     field: Type,
// }
// ```
pub(crate) fn extract_type_alias(acc: &mut Assists, ctx: &AssistContext) -> Option<()> {
    if ctx.frange.range.is_empty() {
        return None;
    }

    let node = ctx.find_node_at_range::<ast::Type>()?;
    let item = ctx.find_node_at_offset::<ast::Item>()?;
    let insert = match_ast! {
        match (item.syntax().parent()?) {
            ast::AssocItemList(it) => it.syntax().parent()?.text_range().start(),
            _ => item.syntax().text_range().start(),
        }
    };
    let target = node.syntax().text_range();

    acc.add(
        AssistId("extract_type_alias", AssistKind::RefactorExtract),
        "Extract type as type alias",
        target,
        |builder| {
            builder.edit_file(ctx.frange.file_id);
            builder.replace(target, "Type");
            match ctx.config.snippet_cap {
                Some(cap) => {
                    builder.insert_snippet(cap, insert, format!("type $0Type = {};\n\n", node));
                }
                None => {
                    builder.insert(insert, format!("type Type = {};\n\n", node));
                }
            }
        },
    )
}

#[cfg(test)]
mod tests {
    use crate::tests::{check_assist, check_assist_not_applicable};

    use super::*;

    #[test]
    fn test_not_applicable_without_selection() {
        check_assist_not_applicable(
            extract_type_alias,
            r"
struct S {
    field: $0(u8, u8, u8),
}
            ",
        );
    }

    #[test]
    fn test_simple_types() {
        check_assist(
            extract_type_alias,
            r"
struct S {
    field: $0u8$0,
}
            ",
            r#"
type $0Type = u8;

struct S {
    field: Type,
}
            "#,
        );
    }

    #[test]
    fn test_generic_type_arg() {
        check_assist(
            extract_type_alias,
            r"
fn generic<T>() {}

fn f() {
    generic::<$0()$0>();
}
            ",
            r#"
fn generic<T>() {}

type $0Type = ();

fn f() {
    generic::<Type>();
}
            "#,
        );
    }

    #[test]
    fn test_inner_type_arg() {
        check_assist(
            extract_type_alias,
            r"
struct Vec<T> {}
struct S {
    v: Vec<Vec<$0Vec<u8>$0>>,
}
            ",
            r#"
struct Vec<T> {}
type $0Type = Vec<u8>;

struct S {
    v: Vec<Vec<Type>>,
}
            "#,
        );
    }

    #[test]
    fn test_extract_inner_type() {
        check_assist(
            extract_type_alias,
            r"
struct S {
    field: ($0u8$0,),
}
            ",
            r#"
type $0Type = u8;

struct S {
    field: (Type,),
}
            "#,
        );
    }

    #[test]
    fn extract_from_impl_or_trait() {
        // When invoked in an impl/trait, extracted type alias should be placed next to the
        // impl/trait, not inside.
        check_assist(
            extract_type_alias,
            r#"
impl S {
    fn f() -> $0(u8, u8)$0 {}
}
            "#,
            r#"
type $0Type = (u8, u8);

impl S {
    fn f() -> Type {}
}
            "#,
        );
        check_assist(
            extract_type_alias,
            r#"
trait Tr {
    fn f() -> $0(u8, u8)$0 {}
}
            "#,
            r#"
type $0Type = (u8, u8);

trait Tr {
    fn f() -> Type {}
}
            "#,
        );
    }
}
<commit_msg>Preserve indentation<commit_after>use syntax::{
    ast::{self, edit::IndentLevel, AstNode},
    match_ast,
};

use crate::{AssistContext, AssistId, AssistKind, Assists};

// Assist: extract_type_alias
//
// Extracts the selected type as a type alias.
//
// ```
// struct S {
//     field: $0(u8, u8, u8)$0,
// }
// ```
// ->
// ```
// type $0Type = (u8, u8, u8);
//
// struct S {
//     field: Type,
// }
// ```
pub(crate) fn extract_type_alias(acc: &mut Assists, ctx: &AssistContext) -> Option<()> {
    if ctx.frange.range.is_empty() {
        return None;
    }

    let node = ctx.find_node_at_range::<ast::Type>()?;
    let item = ctx.find_node_at_offset::<ast::Item>()?;
    let insert = match_ast! {
        match (item.syntax().parent()?) {
            ast::AssocItemList(it) => it.syntax().parent()?.clone(),
            _ => item.syntax().clone(),
        }
    };
    let indent = IndentLevel::from_node(&insert);
    let insert = insert.text_range().start();
    let target = node.syntax().text_range();

    acc.add(
        AssistId("extract_type_alias", AssistKind::RefactorExtract),
        "Extract type as type alias",
        target,
        |builder| {
            builder.edit_file(ctx.frange.file_id);
            builder.replace(target, "Type");
            match ctx.config.snippet_cap {
                Some(cap) => {
                    builder.insert_snippet(
                        cap,
                        insert,
                        format!("type $0Type = {};\n\n{}", node, indent),
                    );
                }
                None => {
                    builder.insert(insert, format!("type Type = {};\n\n{}", node, indent));
                }
            }
        },
    )
}

#[cfg(test)]
mod tests {
    use crate::tests::{check_assist, check_assist_not_applicable};

    use super::*;

    #[test]
    fn test_not_applicable_without_selection() {
        check_assist_not_applicable(
            extract_type_alias,
            r"
struct S {
    field: $0(u8, u8, u8),
}
            ",
        );
    }

    #[test]
    fn test_simple_types() {
        check_assist(
            extract_type_alias,
            r"
struct S {
    field: $0u8$0,
}
            ",
            r#"
type $0Type = u8;

struct S {
    field: Type,
}
            "#,
        );
    }

    #[test]
    fn test_generic_type_arg() {
        check_assist(
            extract_type_alias,
            r"
fn generic<T>() {}

fn f() {
    generic::<$0()$0>();
}
            ",
            r#"
fn generic<T>() {}

type $0Type = ();

fn f() {
    generic::<Type>();
}
            "#,
        );
    }

    #[test]
    fn test_inner_type_arg() {
        check_assist(
            extract_type_alias,
            r"
struct Vec<T> {}
struct S {
    v: Vec<Vec<$0Vec<u8>$0>>,
}
            ",
            r#"
struct Vec<T> {}
type $0Type = Vec<u8>;

struct S {
    v: Vec<Vec<Type>>,
}
            "#,
        );
    }

    #[test]
    fn test_extract_inner_type() {
        check_assist(
            extract_type_alias,
            r"
struct S {
    field: ($0u8$0,),
}
            ",
            r#"
type $0Type = u8;

struct S {
    field: (Type,),
}
            "#,
        );
    }

    #[test]
    fn extract_from_impl_or_trait() {
        // When invoked in an impl/trait, extracted type alias should be placed next to the
        // impl/trait, not inside.
        check_assist(
            extract_type_alias,
            r#"
impl S {
    fn f() -> $0(u8, u8)$0 {}
}
            "#,
            r#"
type $0Type = (u8, u8);

impl S {
    fn f() -> Type {}
}
            "#,
        );
        check_assist(
            extract_type_alias,
            r#"
trait Tr {
    fn f() -> $0(u8, u8)$0 {}
}
            "#,
            r#"
type $0Type = (u8, u8);

trait Tr {
    fn f() -> Type {}
}
            "#,
        );
    }

    #[test]
    fn indentation() {
        check_assist(
            extract_type_alias,
            r#"
mod m {
    fn f() -> $0u8$0 {}
}
            "#,
            r#"
mod m {
    type $0Type = u8;

    fn f() -> Type {}
}
            "#,
        );
    }
}
<|endoftext|>


<commit_before>use std::fmt;

use protocol::command::*;
use protocol::message::{IrcMessage, RawMessage, ParseMessageError, ParseMessageErrorKind};

#[derive(Debug, Clone, Eq, PartialEq)]
pub struct JoinCommand<'a> {
    channels: &'a str,
    keys: Option<&'a str>,
}

impl<'a> JoinCommand<'a> {
    pub fn new(c: &'a str, keys: Option<&'a str>) -> JoinCommand<'a> {
        JoinCommand {
            channels: c,
            keys: keys,
        }
    }

    pub fn channels(&self) -> ChannelIter<'a> {
        ChannelIter::wrap(self.channels)
    }

    pub fn keys(&self) -> Option<&'a str> {
        self.keys
    }
}

impl<'a> fmt::Display for JoinCommand<'a> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        try!(write!(f, "{} {}", CMD_JOIN, self.channels));

        match self.keys {
            Some(k) => write!(f, "{}", k),
            None => Ok(()),
        }
    }
}

impl<'a> IrcMessage<'a> for JoinCommand<'a> {
    fn from_raw(raw: &RawMessage<'a>) -> Result<JoinCommand<'a>, ParseMessageError> {
        let mut params = raw.parameters();

        let channels = match params.next() {
            None => {
                return Err(ParseMessageError::new(ParseMessageErrorKind::NeedMoreParams,
                                                  "JOIN requires channels"));
            },
            Some(n) => n
        };

        let keys = params.next();

        Ok(JoinCommand::new(channels, keys))
    }
}
<commit_msg>updated join struct<commit_after>use std::fmt;

use protocol::command::*;
use protocol::message::{IrcMessage, RawMessage, ParseMessageError, ParseMessageErrorKind};

pub struct ChannelKeyIter<'a> {
    channels: &'a str,
    keys: Option<&'a str>,
}

impl<'a> Iterator for ChannelKeyIter<'a> {
    type Item = (&'a str, Option<&'a str>);

    fn next(&mut self) -> Option<(&'a str, Option<&'a str>)> {
        if self.channels.is_empty() {
            None
        } else {
            let chan = match self.channels.find(',') {
                None => {
                    let chan = self.channels;
                    self.channels = &self.channels[self.channels.len()..];
                    chan
                },
                Some(idx) => {
                    let chan = &self.channels[..idx];
                    self.channels = &self.channels[idx+1..];
                    chan
                }
            };

            let key = match self.keys.as_mut() {
                None | Some(&mut "") => None,
                Some(k) => {
                    match k.find(',') {
                        None => {
                            let key = *k;
                            *k = &k[k.len()..];
                            Some(key)
                        },
                        Some(idx) => {
                            let key = &k[..idx];
                            *k = &k[idx+1..];
                            Some(key)
                        }
                    }
                }
            };

            Some((chan, key))
        }
    }
}

#[derive(Debug, Clone, Eq, PartialEq)]
pub struct JoinCommand<'a> {
    channels: &'a str,
    keys: Option<&'a str>,
}

impl<'a> JoinCommand<'a> {
    pub fn new(c: &'a str, keys: Option<&'a str>) -> JoinCommand<'a> {
        JoinCommand {
            channels: c,
            keys: keys,
        }
    }

    pub fn channel_with_keys(&self) -> ChannelKeyIter<'a> {
        ChannelKeyIter {
            channels: self.channels,
            keys: self.keys,
        }
    }
}

impl<'a> fmt::Display for JoinCommand<'a> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        try!(write!(f, "{} {}", CMD_JOIN, self.channels));

        match self.keys {
            Some(k) => write!(f, "{}", k),
            None => Ok(()),
        }
    }
}

impl<'a> IrcMessage<'a> for JoinCommand<'a> {
    fn from_raw(raw: &RawMessage<'a>) -> Result<JoinCommand<'a>, ParseMessageError> {
        let mut params = raw.parameters();

        let channels = match params.next() {
            None => {
                return Err(ParseMessageError::new(ParseMessageErrorKind::NeedMoreParams,
                                                  "JOIN requires channels"));
            },
            Some(n) => n
        };

        let keys = params.next();

        Ok(JoinCommand::new(channels, keys))
    }
}

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

    use protocol::message::IrcMessage;

    #[test]
    fn test_join_command_basic() {
        let data = "JOIN #foo,#bar fubar,foobar";

        let cmd = JoinCommand::from_str(data).unwrap();

        let expected_chan = [
            ("#foo", Some("fubar")),
            ("#bar", Some("foobar")),
        ];

        let actual: Vec<(&str, Option<&str>)> = cmd.channel_with_keys().collect();

        assert_eq!(&expected_chan[..], &actual[..]);
    }

    #[test]
    fn test_join_command_basic2() {
        let data = "JOIN #foo,#bar fubar";

        let cmd = JoinCommand::from_str(data).unwrap();

        let expected_chan = [
            ("#foo", Some("fubar")),
            ("#bar", None),
        ];

        let actual: Vec<(&str, Option<&str>)> = cmd.channel_with_keys().collect();

        assert_eq!(&expected_chan[..], &actual[..]);
    }

    #[test]
    fn test_join_command_basic3() {
        let data = "JOIN #foo,#bar";

        let cmd = JoinCommand::from_str(data).unwrap();

        let expected_chan = [
            ("#foo", None),
            ("#bar", None),
        ];

        let actual: Vec<(&str, Option<&str>)> = cmd.channel_with_keys().collect();

        assert_eq!(&expected_chan[..], &actual[..]);
    }
}
<|endoftext|>


<commit_before>// Copyright 2015 The Gfx-rs Developers.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

//! Various helper macros.

mod pso;
mod structure;

#[macro_export]
macro_rules! gfx_format {
    ($name:ident : $surface:ident = $container:ident<$channel:ident>) => {
        impl $crate::format::Formatted for $name {
            type Surface = $crate::format::$surface;
            type Channel = $crate::format::$channel;
            type View = $crate::format::$container<
                <$crate::format::$channel as $crate::format::ChannelTyped>::ShaderType
                >;
        }
    }
}

/// Defines vertex, constant and pipeline formats in one block.
///
/// # Example
///
/// ```{.rust}
/// #[macro_use]
/// extern crate gfx;
///
/// gfx_defines! {
///     vertex Vertex {
///         pos: [f32; 4] = "a_Pos",
///         tex_coord: [f32; 2] = "a_TexCoord",
///     }
///
///     constant Locals {
///         transform: [[f32; 4]; 4] = "u_Transform",
///     }
///
///     pipeline pipe {
///         vbuf: gfx::VertexBuffer<Vertex> = (),
///         // Global buffers are added for compatibility when
///         // constant buffers are not supported.
///         transform: gfx::Global<[[f32; 4]; 4]> = "u_Transform",
///         locals: gfx::ConstantBuffer<Locals> = "Locals",
///         color: gfx::TextureSampler<[f32; 4]> = "t_Color",
///         out_color: gfx::RenderTarget<gfx::format::Rgba8> = "Target0",
///         out_depth: gfx::DepthTarget<gfx::format::DepthStencil> =
///             gfx::preset::depth::LESS_EQUAL_WRITE,
///     }
/// }
///
/// impl Vertex {
///     fn new(p: [i8; 3], tex: [i8; 2]) -> Vertex {
///         Vertex {
///             pos: [p[0] as f32, p[1] as f32, p[2] as f32, 1.0f32],
///             tex_coord: [tex[0] as f32, tex[1] as f32],
///         }
///     }
/// }
///
/// fn main() {
///     let vertex_data = [
///         Vertex::new([-1, -1, 1], [0, 0]),
///         Vertex::new([ 1, -1, 1], [1, 0]),
///         // Add more vertices..
///     ];
/// }
/// ```
/// `vertex` and `constant` structures defined with `gfx_defines!`
/// can be extended with attributes:
///
/// ```{.rust}
/// #[macro_use]
/// extern crate gfx;
///
/// gfx_defines! {
///     #[derive(Default)]
///     vertex Vertex {
///         pos: [f32; 4] = "a_Pos",
///         tex_coord: [f32; 2] = "a_TexCoord",
///     }
/// }
///
/// fn main() {
///     let vertex = Vertex::default();
///     assert_eq!(vertex.pos[0], 0f32);
///     assert_eq!(vertex.tex_coord[0], 0f32);
/// }
/// ```
///
/// # `pipe`
///
/// The `pipeline state object` or `pso` can consist of the following
/// `pso` components:
///
/// - A single [vertex buffer](pso/buffer/type.VertexBuffer.html) component to hold the vertices.
/// - A single [instance buffer](pso/buffer/type.InstanceBuffer.html) component.
/// - Single or multiple [constant buffer](pso/buffer/struct.ConstantBuffer.html) components. (DX11 and OpenGL3)
/// - Single or multiple [global buffer](pos/buffer/struct.Global.html) components.
/// - Single or multiple [samplers](pos/resource/struct.Sampler.html)
///   such as [texture samplers](pso/resource/struct.TextureSampler.html].
/// - [Render](pso/target/struct.RenderTarget.html), [blend](pso/target/struct.BlendTarget.html),
///   [depth](pso/target/struct.DepthTarget.html) and [stencil](pso/target/struct.StencilTarget.html) targets
/// - A [shader resource view](pso/resource/struct.ShaderResource.html) (SRV, DX11)
/// - A [unordered access view](pso/resource/struct.UnorderedAccess.html) (UAV, DX11, not yet implemented in the OpenGL backend)
/// - A [scissor](pso/target/struct.Scissor.html) rectangle value (DX11)
///
/// Structure of a `pipeline state object` can be defined
/// freely but should at the very least consist of one vertex buffer object.
///
/// # `vertex`
///
/// Defines a vertex format to be passed onto a vertex buffer. Similar
/// to `pipeline state objects` multiple vertex formats can be set.
///
/// # `constant`
///
/// Defines a structure for shader constant data. This constant data
/// is then appended into a constant buffer in the `pso`. Constant buffers
/// are only supported by DirectX 11 and OpenGL backend uses it's own
/// Uniform Buffer Object which requires OpenGL 3.1.
#[macro_export]
macro_rules! gfx_defines {
    ($(#[$attr:meta])* vertex $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_vertex_struct_meta!($(#[$attr])* vertex_struct_meta $name {$($field:$ty = $e,)+});
    };

    ($(#[$attr:meta])* constant $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_constant_struct_meta!($(#[$attr])* constant_struct_meta $name {$($field:$ty = $e,)+});
    };

    (pipeline $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_pipeline!($name {$($field:$ty = $e,)+});
    };

    // The recursive case for vertex structs
    ($(#[$attr:meta])* vertex $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $(#[$attr])*
            vertex $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };

    // The recursive case for constant structs
    ($(#[$attr:meta])* constant $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $(#[$attr])*
            constant $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };

    // The recursive case for the other keywords
    ($keyword:ident $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $keyword $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };
}
<commit_msg>Fixed incorrect information<commit_after>// Copyright 2015 The Gfx-rs Developers.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

//! Various helper macros.

mod pso;
mod structure;

#[macro_export]
macro_rules! gfx_format {
    ($name:ident : $surface:ident = $container:ident<$channel:ident>) => {
        impl $crate::format::Formatted for $name {
            type Surface = $crate::format::$surface;
            type Channel = $crate::format::$channel;
            type View = $crate::format::$container<
                <$crate::format::$channel as $crate::format::ChannelTyped>::ShaderType
                >;
        }
    }
}

/// Defines vertex, constant and pipeline formats in one block.
///
/// # Example
///
/// ```{.rust}
/// #[macro_use]
/// extern crate gfx;
///
/// gfx_defines! {
///     vertex Vertex {
///         pos: [f32; 4] = "a_Pos",
///         tex_coord: [f32; 2] = "a_TexCoord",
///     }
///
///     constant Locals {
///         transform: [[f32; 4]; 4] = "u_Transform",
///     }
///
///     pipeline pipe {
///         vbuf: gfx::VertexBuffer<Vertex> = (),
///         // Global buffers are added for compatibility when
///         // constant buffers are not supported.
///         transform: gfx::Global<[[f32; 4]; 4]> = "u_Transform",
///         locals: gfx::ConstantBuffer<Locals> = "Locals",
///         color: gfx::TextureSampler<[f32; 4]> = "t_Color",
///         out_color: gfx::RenderTarget<gfx::format::Rgba8> = "Target0",
///         out_depth: gfx::DepthTarget<gfx::format::DepthStencil> =
///             gfx::preset::depth::LESS_EQUAL_WRITE,
///     }
/// }
///
/// impl Vertex {
///     fn new(p: [i8; 3], tex: [i8; 2]) -> Vertex {
///         Vertex {
///             pos: [p[0] as f32, p[1] as f32, p[2] as f32, 1.0f32],
///             tex_coord: [tex[0] as f32, tex[1] as f32],
///         }
///     }
/// }
///
/// fn main() {
///     let vertex_data = [
///         Vertex::new([-1, -1, 1], [0, 0]),
///         Vertex::new([ 1, -1, 1], [1, 0]),
///         // Add more vertices..
///     ];
/// }
/// ```
/// `vertex` and `constant` structures defined with `gfx_defines!`
/// can be extended with attributes:
///
/// ```{.rust}
/// #[macro_use]
/// extern crate gfx;
///
/// gfx_defines! {
///     #[derive(Default)]
///     vertex Vertex {
///         pos: [f32; 4] = "a_Pos",
///         tex_coord: [f32; 2] = "a_TexCoord",
///     }
/// }
///
/// fn main() {
///     let vertex = Vertex::default();
///     assert_eq!(vertex.pos[0], 0f32);
///     assert_eq!(vertex.tex_coord[0], 0f32);
/// }
/// ```
///
/// # `pipe`
///
/// The `pipeline state object` or `pso` can consist of the following
/// `pso` components:
///
/// - A [vertex buffer](pso/buffer/type.VertexBuffer.html) component to hold the vertices.
/// - An [instance buffer](pso/buffer/type.InstanceBuffer.html) component.
/// - Single or multiple [constant buffer](pso/buffer/struct.ConstantBuffer.html) components. (DX11 and OpenGL3)
/// - Single or multiple [global buffer](pso/buffer/struct.Global.html) components.
/// - Single or multiple [samplers](pso/resource/struct.Sampler.html).
/// - [Render](pso/target/struct.RenderTarget.html), [blend](pso/target/struct.BlendTarget.html),
///   [depth](pso/target/struct.DepthTarget.html), [stencil](pso/target/struct.StencilTarget.html) targets.
/// - A [shader resource view](pso/resource/struct.ShaderResource.html) (SRV, DX11)
/// - An [unordered access view](pso/resource/struct.UnorderedAccess.html) (UAV, DX11, not yet implemented in the OpenGL backend)
/// - A [scissor](pso/target/struct.Scissor.html) rectangle value (DX11)
///
/// Structure of a `pipeline state object` can be defined freely.
///
/// It should be noted however, that you can have multiple objects of everything but
/// depth/stencil and scissor objects in a `pipeline state object`, which is the only
/// restriction in the freedom of defining a `pipeline state object`.
///
/// # `vertex`
///
/// Defines a vertex format to be passed onto a vertex buffer. Similar
/// to `pipeline state objects` multiple vertex formats can be set.
///
/// # `constant`
///
/// Defines a structure for shader constant data. This constant data
/// is then appended into a constant buffer in the `pso`. Constant buffers
/// are supported by DirectX 11 and OpenGL3 backend, but in OpenGL they
/// are called `Uniform Buffer Object`s or `UBO`s.
#[macro_export]
macro_rules! gfx_defines {
    ($(#[$attr:meta])* vertex $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_vertex_struct_meta!($(#[$attr])* vertex_struct_meta $name {$($field:$ty = $e,)+});
    };

    ($(#[$attr:meta])* constant $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_constant_struct_meta!($(#[$attr])* constant_struct_meta $name {$($field:$ty = $e,)+});
    };

    (pipeline $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    }) => {
        gfx_pipeline!($name {$($field:$ty = $e,)+});
    };

    // The recursive case for vertex structs
    ($(#[$attr:meta])* vertex $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $(#[$attr])*
            vertex $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };

    // The recursive case for constant structs
    ($(#[$attr:meta])* constant $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $(#[$attr])*
            constant $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };

    // The recursive case for the other keywords
    ($keyword:ident $name:ident {
            $( $field:ident : $ty:ty = $e:expr, )+
    } $($tail:tt)+) => {
        gfx_defines! {
            $keyword $name { $($field : $ty = $e,)+ }
        }
        gfx_defines!($($tail)+);
    };
}
<|endoftext|>


<commit_before><commit_msg>discover: do not panic on MAC mismatch. (Fixes #289)<commit_after><|endoftext|>


<commit_before>#![cfg_attr(feature="nightly", feature(alloc_system))]
#[cfg(feature="nightly")]
extern crate alloc_system;
extern crate libc;
extern crate tensorflow_sys as ffi;

use libc::{c_int, int64_t, size_t};
use std::ffi::{CStr, CString};
use std::path::Path;

macro_rules! nonnull(
    ($pointer:expr) => ({
        let pointer = $pointer;
        assert!(!pointer.is_null());
        pointer
    });
);

macro_rules! ok(
    ($status:expr) => ({
        if ffi::TF_GetCode($status) != ffi::TF_OK {
            panic!(CStr::from_ptr(ffi::TF_Message($status)).to_string_lossy().into_owned());
        }
    });
);

fn main() {
    use std::mem::size_of;
    use std::ptr::{null, null_mut};
    use std::slice::from_raw_parts;

    unsafe {
        let options = nonnull!(ffi::TF_NewSessionOptions());
        let status = nonnull!(ffi::TF_NewStatus());
        let session = nonnull!(ffi::TF_NewDeprecatedSession(options, status));

        let graph = read("examples/assets/multiplication.pb"); // c = a * b
        ffi::TF_ExtendGraph(session,
                            graph.as_ptr() as *const _,
                            graph.len() as size_t,
                            status);
        ok!(status);

        let mut input_names = vec![];
        let mut inputs = vec![];

        let name = CString::new("a").unwrap();
        let mut data = vec![1f32, 2.0, 3.0];
        let dims = vec![data.len() as int64_t];
        let tensor = nonnull!(ffi::TF_NewTensor(ffi::TF_FLOAT,
                                                dims.as_ptr(),
                                                dims.len() as c_int,
                                                data.as_mut_ptr() as *mut _,
                                                data.len() as size_t,
                                                Some(noop),
                                                null_mut()));

        input_names.push(name.as_ptr());
        inputs.push(tensor);

        let name = CString::new("b").unwrap();
        let mut data = vec![4f32, 5.0, 6.0];
        let dims = vec![data.len() as int64_t];
        let tensor = nonnull!(ffi::TF_NewTensor(ffi::TF_FLOAT,
                                                dims.as_ptr(),
                                                dims.len() as c_int,
                                                data.as_mut_ptr() as *mut _,
                                                data.len() as size_t,
                                                Some(noop),
                                                null_mut()));

        input_names.push(name.as_ptr());
        inputs.push(tensor);

        let mut output_names = vec![];
        let mut outputs = vec![];

        let name = CString::new("c").unwrap();

        output_names.push(name.as_ptr());
        outputs.push(null_mut());

        let mut target_names = vec![];

        ffi::TF_Run(session,
                    null(),
                    input_names.as_mut_ptr(),
                    inputs.as_mut_ptr(),
                    input_names.len() as c_int,
                    output_names.as_mut_ptr(),
                    outputs.as_mut_ptr(),
                    output_names.len() as c_int,
                    target_names.as_mut_ptr(),
                    target_names.len() as c_int,
                    null_mut(),
                    status);
        ok!(status);

        let tensor = nonnull!(outputs[0]);
        let data = nonnull!(ffi::TF_TensorData(tensor)) as *const f32;
        let data = from_raw_parts(data, ffi::TF_TensorByteSize(tensor) / size_of::<f32>());

        assert_eq!(data, &[1.0 * 4.0, 2.0 * 5.0, 3.0 * 6.0]);

        ffi::TF_CloseDeprecatedSession(session, status);

        ffi::TF_DeleteTensor(tensor);
        ffi::TF_DeleteDeprecatedSession(session, status);
        ffi::TF_DeleteStatus(status);
        ffi::TF_DeleteSessionOptions(options);
    }

    unsafe extern "C" fn noop(_: *mut std::os::raw::c_void, _: size_t, _: *mut std::os::raw::c_void) {}
}

fn read<T: AsRef<Path>>(path: T) -> Vec<u8> {
    use std::fs::File;
    use std::io::Read;

    let mut buffer = vec![];
    let mut file = File::open(path).unwrap();
    file.read_to_end(&mut buffer).unwrap();
    buffer
}
<commit_msg>Upgrade tensorflow-sys multiplication example to non-deprecated API<commit_after>#![cfg_attr(feature="nightly", feature(alloc_system))]
#[cfg(feature="nightly")]
extern crate alloc_system;
extern crate libc;
extern crate tensorflow_sys as ffi;

use libc::{c_int, int64_t, size_t};
use std::ffi::{CStr, CString};
use std::mem;
use std::path::Path;
use std::os::raw::c_void;

macro_rules! nonnull(
    ($pointer:expr) => ({
        let pointer = $pointer;
        assert!(!pointer.is_null());
        pointer
    });
);

macro_rules! ok(
    ($status:expr) => ({
        if ffi::TF_GetCode($status) != ffi::TF_OK {
            panic!(CStr::from_ptr(ffi::TF_Message($status)).to_string_lossy().into_owned());
        }
    });
);

fn main() {
    use std::mem::size_of;
    use std::ptr::{null, null_mut};
    use std::slice::from_raw_parts;

    unsafe {
        let options = nonnull!(ffi::TF_NewSessionOptions());
        let status = nonnull!(ffi::TF_NewStatus());
        let graph = nonnull!(ffi::TF_NewGraph());

        let graph_def = read("examples/assets/multiplication.pb"); // c = a * b
        let opts = nonnull!(ffi::TF_NewImportGraphDefOptions());
        let graph_def_buf = ffi::TF_Buffer{
            data: graph_def.as_ptr() as *const c_void,
            length: graph_def.len(),
            data_deallocator: None,
        };
        ffi::TF_GraphImportGraphDef(graph,
                                    &graph_def_buf,
                                    opts,
                                    status);
        ffi::TF_DeleteImportGraphDefOptions(opts);
        ok!(status);

        let session = nonnull!(ffi::TF_NewSession(graph, options, status));
        let mut inputs = vec![];
        let mut input_tensors: Vec<*const ffi::TF_Tensor> = vec![];

        let name = CString::new("a").unwrap();
        let mut data = vec![1f32, 2.0, 3.0];
        let dims = vec![data.len() as int64_t];
        let tensor = nonnull!(ffi::TF_NewTensor(ffi::TF_FLOAT,
                                                dims.as_ptr(),
                                                dims.len() as c_int,
                                                data.as_mut_ptr() as *mut _,
                                                data.len() as size_t * mem::size_of::<f32>(),
                                                Some(noop),
                                                null_mut()));

        let input_op = nonnull!(ffi::TF_GraphOperationByName(graph, name.as_ptr()));
        inputs.push(ffi::TF_Output{
            oper: input_op,
            index: 0,
        });
        input_tensors.push(tensor);

        let name = CString::new("b").unwrap();
        let mut data = vec![4f32, 5.0, 6.0];
        let dims = vec![data.len() as int64_t];
        let tensor = nonnull!(ffi::TF_NewTensor(ffi::TF_FLOAT,
                                                dims.as_ptr(),
                                                dims.len() as c_int,
                                                data.as_mut_ptr() as *mut _,
                                                data.len() as size_t as size_t * mem::size_of::<f32>(),
                                                Some(noop),
                                                null_mut()));

        let input_op = nonnull!(ffi::TF_GraphOperationByName(graph, name.as_ptr()));
        inputs.push(ffi::TF_Output{
            oper: input_op,
            index: 0,
        });
        input_tensors.push(tensor);

        let mut outputs = vec![];
        let mut output_tensors = vec![];

        let name = CString::new("c").unwrap();

        let output_op = nonnull!(ffi::TF_GraphOperationByName(graph, name.as_ptr()));
        outputs.push(ffi::TF_Output{
            oper: output_op,
            index: 0,
        });
        output_tensors.push(null_mut());

        let mut target_names = vec![];

        ffi::TF_SessionRun(session,
                    null(),
                    inputs.as_mut_ptr(),
                    input_tensors.as_ptr(),
                    inputs.len() as c_int,
                    outputs.as_mut_ptr(),
                    output_tensors.as_mut_ptr(),
                    outputs.len() as c_int,
                    target_names.as_mut_ptr(),
                    target_names.len() as c_int,
                    null_mut(),
                    status);
        ok!(status);

        let tensor = nonnull!(output_tensors[0]);
        let data = nonnull!(ffi::TF_TensorData(tensor)) as *const f32;
        let data = from_raw_parts(data, ffi::TF_TensorByteSize(tensor) / size_of::<f32>());

        assert_eq!(data, &[1.0 * 4.0, 2.0 * 5.0, 3.0 * 6.0]);

        ffi::TF_CloseSession(session, status);

        ffi::TF_DeleteSession(session, status);
        ffi::TF_DeleteGraph(graph);
        ffi::TF_DeleteTensor(tensor);
        ffi::TF_DeleteStatus(status);
        ffi::TF_DeleteSessionOptions(options);
    }

    unsafe extern "C" fn noop(_: *mut std::os::raw::c_void, _: size_t, _: *mut std::os::raw::c_void) {}
}

fn read<T: AsRef<Path>>(path: T) -> Vec<u8> {
    use std::fs::File;
    use std::io::Read;

    let mut buffer = vec![];
    let mut file = File::open(path).unwrap();
    file.read_to_end(&mut buffer).unwrap();
    buffer
}
<|endoftext|>


<commit_before>extern crate chrono;
#[macro_use(crate_version)]
extern crate clap;
#[cfg(test)]
#[macro_use(expect)]
extern crate expectest;
extern crate mprovision;

use mprovision as mp;
use cli::Command;
use std::env;
use std::path::PathBuf;
use chrono::*;

mod cli;

fn main() {
    let result = cli::parse(env::args()).and_then(|command| match command {
        Command::List(cli::ListParams {
            filter,
            expire_in_days,
            directory,
        }) => list(filter, expire_in_days, directory),
        Command::ShowUuid(uuid, directory) => show_uuid(uuid, directory),
        Command::ShowFile(path) => show_file(path),
        Command::Remove(uuids, directory) => remove(uuids, directory),
        Command::Clean(directory) => clean(directory),
    });
    if let Err(e) = result {
        e.exit();
    }
}

fn list(
    filter: Option<String>,
    expires_in_days: Option<i64>,
    directory: Option<PathBuf>,
) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|dir| mp::entries(&dir).map(|entries| entries.collect::<Vec<_>>()))
        .map_err(|err| err.into())
        .map(|entries| {
            let total = entries.len();
            let date = expires_in_days.map(|days| Utc::now() + Duration::days(days));
            let filter_string = filter.as_ref();
            let mut profiles = mp::filter(entries, |profile| match (date, filter_string) {
                (Some(date), Some(string)) => {
                    profile.expiration_date <= date && profile.contains(string)
                }
                (Some(date), _) => profile.expiration_date <= date,
                (_, Some(string)) => profile.contains(string),
                (_, _) => true,
            });
            profiles.sort_by(|a, b| a.creation_date.cmp(&b.creation_date));
            (total, profiles)
        })
        .and_then(|(total, profiles)| {
            if profiles.is_empty() {
                Ok(println!("Nothing found"))
            } else {
                for profile in &profiles {
                    println!("\n{}", profile.description());
                }
                Ok(println!("\nFound {} of {}", profiles.len(), total))
            }
        })
}

fn show_uuid(uuid: String, directory: Option<PathBuf>) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|directory| {
            mp::find_by_uuid(&directory, &uuid)
                .and_then(|profile| mp::show(&profile.path).map(|xml| println!("{}", xml)))
        })
        .map_err(|err| err.into())
}

fn show_file(path: PathBuf) -> Result<(), cli::Error> {
    mp::show(&path)
        .map(|xml| println!("{}", xml))
        .map_err(|err| err.into())
}

fn remove(uuids: Vec<String>, directory: Option<PathBuf>) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|directory| {
            mp::find_by_uuids(&directory, uuids).and_then(|profiles| {
                for profile in profiles {
                    match mp::remove(&profile.path) {
                        Ok(_) => println!("'{}' was removed", profile.uuid),
                        Err(_) => println!("Error while removing '{}'", profile.uuid),
                    }
                }
                Ok(())
            })
        })
        .map_err(|err| err.into())
}

fn clean(directory: Option<PathBuf>) -> Result<(), cli::Error> {
    fn concat(mut s1: String, s2: String) -> String {
        s1.push_str(&s2);
        s1
    }

    mp::with_directory(directory)
        .and_then(|dir| mp::entries(&dir).map(|entries| entries.collect::<Vec<_>>()))
        .map_err(|err| err.into())
        .map(|entries| {
            let date = Utc::now();
            mp::filter(entries, |profile| profile.expiration_date <= date)
        })
        .and_then(|profiles| {
            if profiles.is_empty() {
                Ok(println!("All provisioning profiles are valid"))
            } else {
                profiles
                    .iter()
                    .map(|profile| {
                        std::fs::remove_file(&profile.path)
                            .map(|_| format!("'{}' was removed\n", profile.uuid))
                            .map_err(|err| format!("'{}' {}\n", profile.uuid, err))
                    })
                    .fold(Ok(String::new()), |acc, s| match (acc, s) {
                        (Ok(acc), Ok(s)) => Ok(concat(acc, s)),
                        (Ok(acc), Err(s)) | (Err(acc), Ok(s)) | (Err(acc), Err(s)) => {
                            Err(concat(acc, s))
                        }
                    })
                    .map(|s| println!("{}", s))
                    .map_err(cli::Error::Custom)
            }
        })
}
<commit_msg>Refactor matching on Command into separate function<commit_after>extern crate chrono;
#[macro_use(crate_version)]
extern crate clap;
#[cfg(test)]
#[macro_use(expect)]
extern crate expectest;
extern crate mprovision;

use mprovision as mp;
use cli::Command;
use std::env;
use std::path::PathBuf;
use chrono::*;

mod cli;

fn main() {
    if let Err(e) = cli::parse(env::args()).and_then(run) {
        e.exit();
    }
}

fn run(command: cli::Command) -> Result<(), cli::Error> {
    match command {
        Command::List(cli::ListParams {
            filter,
            expire_in_days,
            directory,
        }) => list(filter, expire_in_days, directory),
        Command::ShowUuid(uuid, directory) => show_uuid(uuid, directory),
        Command::ShowFile(path) => show_file(path),
        Command::Remove(uuids, directory) => remove(uuids, directory),
        Command::Clean(directory) => clean(directory),
    }
}

fn list(
    filter: Option<String>,
    expires_in_days: Option<i64>,
    directory: Option<PathBuf>,
) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|dir| mp::entries(&dir).map(|entries| entries.collect::<Vec<_>>()))
        .map_err(|err| err.into())
        .map(|entries| {
            let total = entries.len();
            let date = expires_in_days.map(|days| Utc::now() + Duration::days(days));
            let filter_string = filter.as_ref();
            let mut profiles = mp::filter(entries, |profile| match (date, filter_string) {
                (Some(date), Some(string)) => {
                    profile.expiration_date <= date && profile.contains(string)
                }
                (Some(date), _) => profile.expiration_date <= date,
                (_, Some(string)) => profile.contains(string),
                (_, _) => true,
            });
            profiles.sort_by(|a, b| a.creation_date.cmp(&b.creation_date));
            (total, profiles)
        })
        .and_then(|(total, profiles)| {
            if profiles.is_empty() {
                Ok(println!("Nothing found"))
            } else {
                for profile in &profiles {
                    println!("\n{}", profile.description());
                }
                Ok(println!("\nFound {} of {}", profiles.len(), total))
            }
        })
}

fn show_uuid(uuid: String, directory: Option<PathBuf>) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|directory| {
            mp::find_by_uuid(&directory, &uuid)
                .and_then(|profile| mp::show(&profile.path).map(|xml| println!("{}", xml)))
        })
        .map_err(|err| err.into())
}

fn show_file(path: PathBuf) -> Result<(), cli::Error> {
    mp::show(&path)
        .map(|xml| println!("{}", xml))
        .map_err(|err| err.into())
}

fn remove(uuids: Vec<String>, directory: Option<PathBuf>) -> Result<(), cli::Error> {
    mp::with_directory(directory)
        .and_then(|directory| {
            mp::find_by_uuids(&directory, uuids).and_then(|profiles| {
                for profile in profiles {
                    match mp::remove(&profile.path) {
                        Ok(_) => println!("'{}' was removed", profile.uuid),
                        Err(_) => println!("Error while removing '{}'", profile.uuid),
                    }
                }
                Ok(())
            })
        })
        .map_err(|err| err.into())
}

fn clean(directory: Option<PathBuf>) -> Result<(), cli::Error> {
    fn concat(mut s1: String, s2: String) -> String {
        s1.push_str(&s2);
        s1
    }

    mp::with_directory(directory)
        .and_then(|dir| mp::entries(&dir).map(|entries| entries.collect::<Vec<_>>()))
        .map_err(|err| err.into())
        .map(|entries| {
            let date = Utc::now();
            mp::filter(entries, |profile| profile.expiration_date <= date)
        })
        .and_then(|profiles| {
            if profiles.is_empty() {
                Ok(println!("All provisioning profiles are valid"))
            } else {
                profiles
                    .iter()
                    .map(|profile| {
                        std::fs::remove_file(&profile.path)
                            .map(|_| format!("'{}' was removed\n", profile.uuid))
                            .map_err(|err| format!("'{}' {}\n", profile.uuid, err))
                    })
                    .fold(Ok(String::new()), |acc, s| match (acc, s) {
                        (Ok(acc), Ok(s)) => Ok(concat(acc, s)),
                        (Ok(acc), Err(s)) | (Err(acc), Ok(s)) | (Err(acc), Err(s)) => {
                            Err(concat(acc, s))
                        }
                    })
                    .map(|s| println!("{}", s))
                    .map_err(cli::Error::Custom)
            }
        })
}
<|endoftext|>