<commit_before>#![crate_name = "xpath"]

extern crate document;

use document::{Any,ToAny};
use document::{Nodeset};
use std::collections::HashMap;

#[deriving(PartialEq,Show,Clone)]
pub enum XPathValue {
    Boolean(bool),
    Number(f64),
    String(String),
    Nodes(Nodeset), // rename as Nodeset
}

impl XPathValue {
    fn boolean(&self) -> bool {
        match *self {
            Boolean(val) => val,
            Number(n) => n != 0.0 && ! n.is_nan(),
            String(ref s) => ! s.is_empty(),
            Nodes(ref nodeset) => nodeset.size() > 0,
        }
    }

    fn number(&self) -> f64 {
        match *self {
            Number(val) => val,
            _ => -42.0
        }
    }

    fn string(&self) -> String {
        match *self {
            String(ref val) => val.clone(),
            _ => "Unimplemented".to_string(),
        }
    }

    fn nodeset(&self) -> Nodeset {
        match *self {
            Nodes(ref ns) => ns.clone(),
            _ => fail!("Did not evaluate to a nodeset!"),
        }
    }
}

pub trait XPathFunction {
    fn evaluate(&self,
                context: &XPathEvaluationContext,
                args: Vec<XPathValue>) -> XPathValue;
}

type BoxFunc = Box<XPathFunction + 'static>;
pub type Functions = HashMap<String, BoxFunc>;
pub type Variables = HashMap<String, XPathValue>;

pub struct XPathEvaluationContext<'a> {
    node: Any,
    functions: & 'a Functions,
    variables: & 'a Variables,
    position: uint,
}

impl<'a> XPathEvaluationContext<'a> {
    pub fn new<A: ToAny>(node: A,
                         functions: &'a Functions,
                         variables: &'a Variables) -> XPathEvaluationContext<'a>
    {
        XPathEvaluationContext {
            node: node.to_any(),
            functions: functions,
            variables: variables,
            position: 0,
        }
    }

    fn node(&self) -> &Any {
        &self.node
    }

    fn new_context_for(& self, size: uint) -> XPathEvaluationContext<'a> {
        XPathEvaluationContext {
            node: self.node.clone(),
            functions: self.functions,
            variables: self.variables,
            position: 0,
        }
    }

    fn next<A: ToAny>(& mut self, node: A) {
        self.position += 1;
    }

    fn position(&self) -> uint {
        self.position
    }

    fn function_for_name(&self, name: &str) -> Option<& 'a BoxFunc> {
        self.functions.find(&name.to_string())
    }

    fn value_of(&self, name: &str) -> Option<&XPathValue> {
        self.variables.find(&name.to_string())
    }
}

pub trait XPathNodeTest {
    fn test(&self, context: &XPathEvaluationContext, result: &mut Nodeset);
}

struct EmptyIterator<T>;

impl<T> Iterator<T> for EmptyIterator<T> {
    fn next(&mut self) -> Option<T> { None }
}

pub mod token;
pub mod tokenizer;
pub mod deabbreviator;
pub mod disambiguator;
pub mod axis;
pub mod expression;
<commit_msg>Fix warnings in xpath<commit_after>#![crate_name = "xpath"]

extern crate document;

use document::{Any,ToAny};
use document::{Nodeset};
use std::collections::HashMap;

#[deriving(PartialEq,Show,Clone)]
pub enum XPathValue {
    Boolean(bool),
    Number(f64),
    String(String),
    Nodes(Nodeset), // rename as Nodeset
}

impl XPathValue {
    fn boolean(&self) -> bool {
        match *self {
            Boolean(val) => val,
            Number(n) => n != 0.0 && ! n.is_nan(),
            String(ref s) => ! s.is_empty(),
            Nodes(ref nodeset) => nodeset.size() > 0,
        }
    }

    fn number(&self) -> f64 {
        match *self {
            Number(val) => val,
            _ => -42.0
        }
    }

    fn string(&self) -> String {
        match *self {
            String(ref val) => val.clone(),
            _ => "Unimplemented".to_string(),
        }
    }

    fn nodeset(&self) -> Nodeset {
        match *self {
            Nodes(ref ns) => ns.clone(),
            _ => fail!("Did not evaluate to a nodeset!"),
        }
    }
}

pub trait XPathFunction {
    fn evaluate(&self,
                context: &XPathEvaluationContext,
                args: Vec<XPathValue>) -> XPathValue;
}

type BoxFunc = Box<XPathFunction + 'static>;
pub type Functions = HashMap<String, BoxFunc>;
pub type Variables = HashMap<String, XPathValue>;

pub struct XPathEvaluationContext<'a> {
    node: Any,
    functions: & 'a Functions,
    variables: & 'a Variables,
    position: uint,
}

impl<'a> XPathEvaluationContext<'a> {
    pub fn new<A: ToAny>(node: A,
                         functions: &'a Functions,
                         variables: &'a Variables) -> XPathEvaluationContext<'a>
    {
        XPathEvaluationContext {
            node: node.to_any(),
            functions: functions,
            variables: variables,
            position: 0,
        }
    }

    fn node(&self) -> &Any {
        &self.node
    }

    fn new_context_for(& self, _size: uint) -> XPathEvaluationContext<'a> {
        XPathEvaluationContext {
            node: self.node.clone(),
            functions: self.functions,
            variables: self.variables,
            position: 0,
        }
    }

    fn next<A: ToAny>(& mut self, _node: A) {
        self.position += 1;
    }

    fn position(&self) -> uint {
        self.position
    }

    fn function_for_name(&self, name: &str) -> Option<& 'a BoxFunc> {
        self.functions.find(&name.to_string())
    }

    fn value_of(&self, name: &str) -> Option<&XPathValue> {
        self.variables.find(&name.to_string())
    }
}

pub trait XPathNodeTest {
    fn test(&self, context: &XPathEvaluationContext, result: &mut Nodeset);
}

pub mod token;
pub mod tokenizer;
pub mod deabbreviator;
pub mod disambiguator;
pub mod axis;
pub mod expression;
<|endoftext|>


<commit_before>//! Defines the render target for tray, where our image will be written too
//! during rendering
//! TODO: Reconstruction filters

use std::vec::Vec;
use std::{iter, cmp, f32};
use std::sync::Mutex;

use film::Colorf;
use film::filter::Filter;
use sampler::Region;

const FILTER_TABLE_SIZE: usize = 16;

/// A struct containing results of an image sample where a ray was fired through
/// continuous pixel coordinates [x, y] and color `color` was computed
pub struct ImageSample {
    pub x: f32,
    pub y: f32,
    pub color: Colorf,
}

impl ImageSample {
    pub fn new(x: f32, y: f32, color: Colorf) -> ImageSample {
        ImageSample { x: x, y: y, color: color }
    }
}

/// RenderTarget is a RGBF render target to write our image too while rendering
pub struct RenderTarget {
    width: usize,
    height: usize,
    pixels: Vec<Colorf>,
    pixels_locked: Vec<Mutex<Vec<Colorf>>>,
    lock_size: (i32, i32),
    filter: Box<Filter + Send + Sync>,
    filter_table: Vec<f32>,
    filter_pixel_width: (i32, i32),
}

impl RenderTarget {
    /// Create a render target with `width * height` pixels
    pub fn new(image_dim: (usize, usize), lock_size: (usize, usize), filter: Box<Filter + Send + Sync>) -> RenderTarget {
        if image_dim.0 % lock_size.0 != 0 || image_dim.1 % lock_size.1 != 0 {
            panic!("Image with dimension {:?} not evenly divided by blocks of {:?}", image_dim, lock_size);
        }
        let width = image_dim.0;
        let height = image_dim.1;
        let filter_pixel_width = (f32::floor(filter.width() / 0.5) as i32, f32::floor(filter.height() / 0.5) as i32);
        let mut filter_table: Vec<f32> = iter::repeat(0.0).take(FILTER_TABLE_SIZE * FILTER_TABLE_SIZE)
            .collect();
        for y in 0..FILTER_TABLE_SIZE {
            let fy = (y as f32 + 0.5) * filter.height() / FILTER_TABLE_SIZE as f32;
            for x in 0..FILTER_TABLE_SIZE {
                let fx = (x as f32 + 0.5) * filter.width() / FILTER_TABLE_SIZE as f32;
                filter_table[y * FILTER_TABLE_SIZE + x] = filter.weight(fx, fy);
            }
        }

        let x_blocks = width / lock_size.0;
        let y_blocks = height / lock_size.1;
        let mut pixels_locked = Vec::with_capacity(x_blocks * y_blocks);
        for _ in 0..x_blocks * y_blocks {
            pixels_locked.push(Mutex::new(iter::repeat(Colorf::broadcast(0.0)).take(lock_size.0 * lock_size.1).collect()));
        }

        RenderTarget { width: width, height: height,
            pixels: iter::repeat(Colorf::broadcast(0.0)).take(width * height).collect(),
            pixels_locked: pixels_locked,
            lock_size: (lock_size.0 as i32, lock_size.1 as i32),
            filter: filter,
            filter_table: filter_table,
            filter_pixel_width: filter_pixel_width,
        }
    }
    /// Write all the image samples to the render target
    pub fn write(&self, samples: &Vec<ImageSample>, region: &Region) {
        // Determine which blocks we touch with our set of samples
        let x_range = (cmp::max(region.start.0 as i32 - self.filter_pixel_width.0, 0),
                       cmp::min(region.end.0 as i32 + self.filter_pixel_width.0, self.width as i32 - 1));
        let y_range = (cmp::max(region.start.1 as i32 - self.filter_pixel_width.1, 0),
                       cmp::min(region.end.1 as i32 + self.filter_pixel_width.1, self.height as i32 - 1));

        if x_range.1 - x_range.0 < 0 || y_range.1 - y_range.0 < 0 {
                return;
        }
        let block_x_range = (x_range.0 / self.lock_size.0, x_range.1 / self.lock_size.0);
        let block_y_range = (y_range.0 / self.lock_size.1, y_range.1 / self.lock_size.1);
        // Temporary storage for filtered samples so we can compute the filtered results for
        // the block we're writing too without having to get the lock
        let mut filtered_samples: Vec<_> = iter::repeat(Colorf::broadcast(0.0))
            .take((self.lock_size.0 * self.lock_size.1) as usize).collect();

        let blocks_per_row = self.width as i32 / self.lock_size.0;
        for y in block_y_range.0..block_y_range.1 + 1 {
            for x in block_x_range.0..block_x_range.1 + 1 {
                let block_x_start = x * self.lock_size.0;
                let block_y_start = y * self.lock_size.1;

                let x_write_range = (cmp::max(x_range.0, block_x_start),
                                     cmp::min(x_range.1 + 1, block_x_start + self.lock_size.0));
                let y_write_range = (cmp::max(y_range.0, block_y_start),
                                     cmp::min(y_range.1 + 1, block_y_start + self.lock_size.1));

                let block_samples = samples.iter().filter(|s| {
                    s.x >= (x_write_range.0 - self.filter_pixel_width.0) as f32
                        && s.x < (x_write_range.1 + self.filter_pixel_width.0) as f32
                        && s.y >= (y_write_range.0 - self.filter_pixel_width.1) as f32
                        && s.y < (y_write_range.1 + self.filter_pixel_width.1) as f32
                });

                for c in &mut filtered_samples {
                    *c = Colorf::broadcast(0.0);
                }

                // Compute the filtered samples for the block
                for c in block_samples {
                    let img_x = c.x - 0.5;
                    let img_y = c.y - 0.5;
                    for iy in y_write_range.0..y_write_range.1 {
                        let fy = f32::abs(iy as f32 - img_y) * self.filter.inv_height() * FILTER_TABLE_SIZE as f32;
                        let fy_idx = cmp::min(fy as usize, FILTER_TABLE_SIZE - 1);
                        for ix in x_write_range.0..x_write_range.1 {
                            let fx = f32::abs(ix as f32 - img_x) * self.filter.inv_width() * FILTER_TABLE_SIZE as f32;
                            let fx_idx = cmp::min(fx as usize, FILTER_TABLE_SIZE - 1);
                            let weight = self.filter_table[fy_idx * FILTER_TABLE_SIZE + fx_idx];
                            let px = ((iy - block_y_start) * self.lock_size.0 + ix - block_x_start) as usize;
                            // TODO: Can't currently overload the += operator
                            // Coming soon though, see RFC #953 https://github.com/rust-lang/rfcs/pull/953
                            filtered_samples[px].r += weight * c.color.r;
                            filtered_samples[px].g += weight * c.color.g;
                            filtered_samples[px].b += weight * c.color.b;
                            // TODO: Remove this it's just for debugging adaptive sampler
                            filtered_samples[px].a += weight;
                        }
                    }
                }

                // Acquire lock for the block and write the filtered samples
                let block_idx = (y * blocks_per_row + x) as usize;
                let mut pixels = self.pixels_locked[block_idx].lock().unwrap();
                for iy in y_write_range.0..y_write_range.1 {
                    for ix in x_write_range.0..x_write_range.1 {
                        let px = ((iy - block_y_start) * self.lock_size.0 + ix - block_x_start) as usize;
                        let c = &filtered_samples[px];
                        pixels[px].r += c.r;
                        pixels[px].g += c.g;
                        pixels[px].b += c.b;
                        pixels[px].a += c.a;
                    }
                }
            }
        }
    }
    /// Clear the render target to black
    pub fn clear(&mut self) {
        for p in self.pixels.iter_mut() {
            *p = Colorf::broadcast(0.0);
        }
    }
    /// Get the dimensions of the render target
    pub fn dimensions(&self) -> (usize, usize) {
        (self.width, self.height)
    }
    /// Convert the floating point color buffer to 24bpp sRGB for output to an image
    pub fn get_render(&self) -> Vec<u8> {
        let mut render: Vec<u8> = iter::repeat(0u8).take(self.width * self.height * 3).collect();
        let x_blocks = self.width / self.lock_size.0 as usize;
        let y_blocks = self.height / self.lock_size.1 as usize;
        for by in 0..y_blocks {
            for bx in 0..x_blocks {
                let block_x_start = bx * self.lock_size.0 as usize;
                let block_y_start = by * self.lock_size.1 as usize;
                let block_idx = (by * x_blocks + bx) as usize;
                let pixels = self.pixels_locked[block_idx].lock().unwrap();
                for y in 0..self.lock_size.1 as usize {
                    for x in 0..self.lock_size.0 as usize {
                        let c = &pixels[y * self.lock_size.0 as usize + x];
                        if c.a > 0.0 {
                            let cn = (*c / c.a).clamp().to_srgb();
                            let px = (y + block_y_start) * self.width * 3 + (x + block_x_start) * 3;
                            for i in 0..3 {
                                render[px + i] = (cn[i] * 255.0) as u8;
                            }
                        }
                    }
                }
            }
        }
        render
    }
}

<commit_msg>Clear the new blocked render target<commit_after>//! Defines the render target for tray, where our image will be written too
//! during rendering
//! TODO: Reconstruction filters

use std::vec::Vec;
use std::{iter, cmp, f32};
use std::sync::Mutex;

use film::Colorf;
use film::filter::Filter;
use sampler::Region;

const FILTER_TABLE_SIZE: usize = 16;

/// A struct containing results of an image sample where a ray was fired through
/// continuous pixel coordinates [x, y] and color `color` was computed
pub struct ImageSample {
    pub x: f32,
    pub y: f32,
    pub color: Colorf,
}

impl ImageSample {
    pub fn new(x: f32, y: f32, color: Colorf) -> ImageSample {
        ImageSample { x: x, y: y, color: color }
    }
}

/// RenderTarget is a RGBF render target to write our image too while rendering
pub struct RenderTarget {
    width: usize,
    height: usize,
    pixels_locked: Vec<Mutex<Vec<Colorf>>>,
    lock_size: (i32, i32),
    filter: Box<Filter + Send + Sync>,
    filter_table: Vec<f32>,
    filter_pixel_width: (i32, i32),
}

impl RenderTarget {
    /// Create a render target with `width * height` pixels
    pub fn new(image_dim: (usize, usize), lock_size: (usize, usize), filter: Box<Filter + Send + Sync>) -> RenderTarget {
        if image_dim.0 % lock_size.0 != 0 || image_dim.1 % lock_size.1 != 0 {
            panic!("Image with dimension {:?} not evenly divided by blocks of {:?}", image_dim, lock_size);
        }
        let width = image_dim.0;
        let height = image_dim.1;
        let filter_pixel_width = (f32::floor(filter.width() / 0.5) as i32, f32::floor(filter.height() / 0.5) as i32);
        let mut filter_table: Vec<f32> = iter::repeat(0.0).take(FILTER_TABLE_SIZE * FILTER_TABLE_SIZE)
            .collect();
        for y in 0..FILTER_TABLE_SIZE {
            let fy = (y as f32 + 0.5) * filter.height() / FILTER_TABLE_SIZE as f32;
            for x in 0..FILTER_TABLE_SIZE {
                let fx = (x as f32 + 0.5) * filter.width() / FILTER_TABLE_SIZE as f32;
                filter_table[y * FILTER_TABLE_SIZE + x] = filter.weight(fx, fy);
            }
        }

        let x_blocks = width / lock_size.0;
        let y_blocks = height / lock_size.1;
        let mut pixels_locked = Vec::with_capacity(x_blocks * y_blocks);
        for _ in 0..x_blocks * y_blocks {
            pixels_locked.push(Mutex::new(iter::repeat(Colorf::broadcast(0.0)).take(lock_size.0 * lock_size.1).collect()));
        }

        RenderTarget { width: width, height: height,
            pixels_locked: pixels_locked,
            lock_size: (lock_size.0 as i32, lock_size.1 as i32),
            filter: filter,
            filter_table: filter_table,
            filter_pixel_width: filter_pixel_width,
        }
    }
    /// Write all the image samples to the render target
    pub fn write(&self, samples: &Vec<ImageSample>, region: &Region) {
        // Determine which blocks we touch with our set of samples
        let x_range = (cmp::max(region.start.0 as i32 - self.filter_pixel_width.0, 0),
                       cmp::min(region.end.0 as i32 + self.filter_pixel_width.0, self.width as i32 - 1));
        let y_range = (cmp::max(region.start.1 as i32 - self.filter_pixel_width.1, 0),
                       cmp::min(region.end.1 as i32 + self.filter_pixel_width.1, self.height as i32 - 1));

        if x_range.1 - x_range.0 < 0 || y_range.1 - y_range.0 < 0 {
                return;
        }
        let block_x_range = (x_range.0 / self.lock_size.0, x_range.1 / self.lock_size.0);
        let block_y_range = (y_range.0 / self.lock_size.1, y_range.1 / self.lock_size.1);
        // Temporary storage for filtered samples so we can compute the filtered results for
        // the block we're writing too without having to get the lock
        let mut filtered_samples: Vec<_> = iter::repeat(Colorf::broadcast(0.0))
            .take((self.lock_size.0 * self.lock_size.1) as usize).collect();

        let blocks_per_row = self.width as i32 / self.lock_size.0;
        for y in block_y_range.0..block_y_range.1 + 1 {
            for x in block_x_range.0..block_x_range.1 + 1 {
                let block_x_start = x * self.lock_size.0;
                let block_y_start = y * self.lock_size.1;

                let x_write_range = (cmp::max(x_range.0, block_x_start),
                                     cmp::min(x_range.1 + 1, block_x_start + self.lock_size.0));
                let y_write_range = (cmp::max(y_range.0, block_y_start),
                                     cmp::min(y_range.1 + 1, block_y_start + self.lock_size.1));

                let block_samples = samples.iter().filter(|s| {
                    s.x >= (x_write_range.0 - self.filter_pixel_width.0) as f32
                        && s.x < (x_write_range.1 + self.filter_pixel_width.0) as f32
                        && s.y >= (y_write_range.0 - self.filter_pixel_width.1) as f32
                        && s.y < (y_write_range.1 + self.filter_pixel_width.1) as f32
                });

                for c in &mut filtered_samples {
                    *c = Colorf::broadcast(0.0);
                }

                // Compute the filtered samples for the block
                for c in block_samples {
                    let img_x = c.x - 0.5;
                    let img_y = c.y - 0.5;
                    for iy in y_write_range.0..y_write_range.1 {
                        let fy = f32::abs(iy as f32 - img_y) * self.filter.inv_height() * FILTER_TABLE_SIZE as f32;
                        let fy_idx = cmp::min(fy as usize, FILTER_TABLE_SIZE - 1);
                        for ix in x_write_range.0..x_write_range.1 {
                            let fx = f32::abs(ix as f32 - img_x) * self.filter.inv_width() * FILTER_TABLE_SIZE as f32;
                            let fx_idx = cmp::min(fx as usize, FILTER_TABLE_SIZE - 1);
                            let weight = self.filter_table[fy_idx * FILTER_TABLE_SIZE + fx_idx];
                            let px = ((iy - block_y_start) * self.lock_size.0 + ix - block_x_start) as usize;
                            // TODO: Can't currently overload the += operator
                            // Coming soon though, see RFC #953 https://github.com/rust-lang/rfcs/pull/953
                            filtered_samples[px].r += weight * c.color.r;
                            filtered_samples[px].g += weight * c.color.g;
                            filtered_samples[px].b += weight * c.color.b;
                            // TODO: Remove this it's just for debugging adaptive sampler
                            filtered_samples[px].a += weight;
                        }
                    }
                }

                // Acquire lock for the block and write the filtered samples
                let block_idx = (y * blocks_per_row + x) as usize;
                let mut pixels = self.pixels_locked[block_idx].lock().unwrap();
                for iy in y_write_range.0..y_write_range.1 {
                    for ix in x_write_range.0..x_write_range.1 {
                        let px = ((iy - block_y_start) * self.lock_size.0 + ix - block_x_start) as usize;
                        let c = &filtered_samples[px];
                        pixels[px].r += c.r;
                        pixels[px].g += c.g;
                        pixels[px].b += c.b;
                        pixels[px].a += c.a;
                    }
                }
            }
        }
    }
    /// Clear the render target to black
    pub fn clear(&mut self) {
        let x_blocks = self.width / self.lock_size.0 as usize;
        let y_blocks = self.height / self.lock_size.1 as usize;
        for by in 0..y_blocks {
            for bx in 0..x_blocks {
                let block_idx = (by * x_blocks + bx) as usize;
                let mut pixels = self.pixels_locked[block_idx].lock().unwrap();
                for p in pixels.iter_mut() {
                    *p = Colorf::broadcast(0.0);
                }
            }
        }
    }
    /// Get the dimensions of the render target
    pub fn dimensions(&self) -> (usize, usize) {
        (self.width, self.height)
    }
    /// Convert the floating point color buffer to 24bpp sRGB for output to an image
    pub fn get_render(&self) -> Vec<u8> {
        let mut render: Vec<u8> = iter::repeat(0u8).take(self.width * self.height * 3).collect();
        let x_blocks = self.width / self.lock_size.0 as usize;
        let y_blocks = self.height / self.lock_size.1 as usize;
        for by in 0..y_blocks {
            for bx in 0..x_blocks {
                let block_x_start = bx * self.lock_size.0 as usize;
                let block_y_start = by * self.lock_size.1 as usize;
                let block_idx = (by * x_blocks + bx) as usize;
                let pixels = self.pixels_locked[block_idx].lock().unwrap();
                for y in 0..self.lock_size.1 as usize {
                    for x in 0..self.lock_size.0 as usize {
                        let c = &pixels[y * self.lock_size.0 as usize + x];
                        if c.a > 0.0 {
                            let cn = (*c / c.a).clamp().to_srgb();
                            let px = (y + block_y_start) * self.width * 3 + (x + block_x_start) * 3;
                            for i in 0..3 {
                                render[px + i] = (cn[i] * 255.0) as u8;
                            }
                        }
                    }
                }
            }
        }
        render
    }
}

<|endoftext|>


<commit_before>
//! All entities of a gerrit instance
//!
//! The entities are documented on gerrit site on
//! <https://gerrit-documentation.storage.googleapis.com/Documentation/2.12.3/rest-api-changes.html#json-entities>.
//!
//! **NOTICE**: Only current needed entities are here reflected.

use std::collections::HashMap;
use std::fmt;
use std::fmt::Display;

#[derive(RustcDecodable, Debug)]
pub struct AccountInfo {
    pub _account_id: u64,
    pub name: Option<String>,
    pub email: Option<String>,
    pub secondary_emails: Option<Vec<String>>,
    pub username: Option<String>,
    pub _more_accounts: Option<String>,
}

impl Display for AccountInfo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        if let Some(x) = self.name.clone() {
            let _ = write!(f, "{}", x);
        } else {
            let _ = write!(f, "uid:{}", self._account_id);
        };

        if let Some(x) = self.email.clone() {
            let _ = write!(f, "{}", x);
        };

        Ok(())
    }
}

#[derive(RustcDecodable, Debug)]
pub struct ActionInfo {
    pub method: Option<String>,
    pub label: Option<String>,
    pub title: Option<String>,
    pub enabled: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub enum ChangeStatus {
    NEW,
    MERGED,
    ABANDONED,
    DRAFT,
}

impl Display for ChangeStatus {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        let s = match *self {
            ChangeStatus::NEW => "NEW",
            ChangeStatus::MERGED => "MERGED",
            ChangeStatus::ABANDONED => "ABANDONED",
            ChangeStatus::DRAFT => "DRAFT",
        };
        write!(f, "{}", s)
    }
}

#[derive(RustcDecodable, Debug)]
pub struct LabelInfo {
    pub optional: Option<bool>,
}

#[derive(RustcDecodable, Debug)]
pub struct ChangeMessageInfo {
    pub id: String,
    pub author: Option<AccountInfo>,
    pub date: String,
    pub message: String,
    pub tag: Option<String>,
    pub _revision_number: Option<u16>,
}

#[allow(non_camel_case_types)]
#[derive(RustcDecodable, Debug)]
pub enum RevisionInfoKind {
    REWORK,
    TRIVIAL_REBASE,
    MERGE_FIRST_PARENT_UPDATE,
    NO_CODE_CHANGE,
    NO_CHANGE,
}

#[derive(RustcDecodable, Debug)]
pub struct FetchInfo {
    pub url: String,
    pub reference: String,
    pub commands: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub struct RevisionInfo {
    pub draft: bool,
    pub kind: RevisionInfoKind,
    pub _number: u16,
    pub created: String,
    pub uploader: AccountInfo,
    pub reference: String,
    pub fetch: HashMap<String, FetchInfo>,
    /* TODO: Some fileds ommited */
}

#[derive(RustcDecodable, Debug)]
pub struct ProblemInfo {
    pub message: String,
    pub status: Option<String>,
    pub outcome: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub struct ChangeInfo {
    pub id: String,
    pub project: String,
    pub branch: String,
    pub topic: Option<String>,
    pub change_id: String,
    pub subject: String,
    pub status: ChangeStatus,
    pub created: String,
    pub updated: String,
    pub submitted: Option<String>,
    pub starred: Option<bool>,
    pub stars: Option<Vec<String>>,
    pub reviewed: Option<bool>,
    pub submit_type: Option<String>,
    pub mergeable: Option<bool>,
    pub insertions: u16,
    pub deletions: u16,
    pub _number: u16,
    pub owner: AccountInfo,
    pub action: Option<Vec<ActionInfo>>,
    pub labels: Option<HashMap<String, LabelInfo>>,
    pub permitted_labels: Option<HashMap<String, LabelInfo>>,
    pub removeable_reviewers: Option<Vec<AccountInfo>>,
    pub reviewers: Option<String>,
    pub messages: Option<HashMap<String, ChangeMessageInfo>>,
    pub current_revision: Option<HashMap<String, RevisionInfo>>,
    pub revision: Option<HashMap<String, RevisionInfo>>,
    pub _more_changes: Option<bool>,
    pub problems: Option<Vec<ProblemInfo>>,
}

/// **TODO**: This is subject to change! Its to unflexible.
impl Display for ChangeInfo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        let _ = writeln!(f, "* {project:.<41.41} {branch:.<20.20} {subject:.>30.30}", project=self.project, branch=self.branch, subject=self.subject);
        let _ = writeln!(f, "| {changeid:41.41} {number:<31.10} {created:>19.19}", changeid=self.change_id, number=self._number, created=self.created);
        let _ = writeln!(f, "| {topic:73.41} {updated:19.19}", topic=self.topic.clone().unwrap_or("N/A".to_string()), updated=self.updated);
        write!(f, "` {status}, {owner}", owner=self.owner, status=self.status)
    }
}

#[derive(RustcDecodable, Debug)]
pub enum ProjectState {
    ACTIVE,
    READONLY,
    HIDDEN,
}

#[derive(RustcDecodable, Debug, Clone)]
pub enum ProjectTypes {
    ALL,
    CODE,
    PERMISSIONS,
}

#[derive(RustcDecodable, Debug)]
pub struct WebLinkInfo {
    pub name: String,
    pub url: String,
    pub image_url: String,
}

#[derive(RustcDecodable, Debug)]
pub struct ProjectInfo {
    pub name: Option<String>,
    pub id: String,
    pub parent: Option<String>,
    pub description: Option<String>,
    pub state: Option<ProjectState>,
    pub branches: Option<HashMap<String, String>>,
    pub web_links: Option<Vec<WebLinkInfo>>,
}
<commit_msg>entities: use try! instead of let _ =<commit_after>
//! All entities of a gerrit instance
//!
//! The entities are documented on gerrit site on
//! <https://gerrit-documentation.storage.googleapis.com/Documentation/2.12.3/rest-api-changes.html#json-entities>.
//!
//! **NOTICE**: Only current needed entities are here reflected.

use std::collections::HashMap;
use std::fmt;
use std::fmt::Display;

#[derive(RustcDecodable, Debug)]
pub struct AccountInfo {
    pub _account_id: u64,
    pub name: Option<String>,
    pub email: Option<String>,
    pub secondary_emails: Option<Vec<String>>,
    pub username: Option<String>,
    pub _more_accounts: Option<String>,
}

impl Display for AccountInfo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        if let Some(x) = self.name.clone() {
            try!(write!(f, "{}", x));
        } else {
            try!(write!(f, "uid:{}", self._account_id));
        };

        if let Some(x) = self.email.clone() {
            try!(write!(f, "{}", x));
        };

        Ok(())
    }
}

#[derive(RustcDecodable, Debug)]
pub struct ActionInfo {
    pub method: Option<String>,
    pub label: Option<String>,
    pub title: Option<String>,
    pub enabled: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub enum ChangeStatus {
    NEW,
    MERGED,
    ABANDONED,
    DRAFT,
}

impl Display for ChangeStatus {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        let s = match *self {
            ChangeStatus::NEW => "NEW",
            ChangeStatus::MERGED => "MERGED",
            ChangeStatus::ABANDONED => "ABANDONED",
            ChangeStatus::DRAFT => "DRAFT",
        };
        write!(f, "{}", s)
    }
}

#[derive(RustcDecodable, Debug)]
pub struct LabelInfo {
    pub optional: Option<bool>,
}

#[derive(RustcDecodable, Debug)]
pub struct ChangeMessageInfo {
    pub id: String,
    pub author: Option<AccountInfo>,
    pub date: String,
    pub message: String,
    pub tag: Option<String>,
    pub _revision_number: Option<u16>,
}

#[allow(non_camel_case_types)]
#[derive(RustcDecodable, Debug)]
pub enum RevisionInfoKind {
    REWORK,
    TRIVIAL_REBASE,
    MERGE_FIRST_PARENT_UPDATE,
    NO_CODE_CHANGE,
    NO_CHANGE,
}

#[derive(RustcDecodable, Debug)]
pub struct FetchInfo {
    pub url: String,
    pub reference: String,
    pub commands: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub struct RevisionInfo {
    pub draft: bool,
    pub kind: RevisionInfoKind,
    pub _number: u16,
    pub created: String,
    pub uploader: AccountInfo,
    pub reference: String,
    pub fetch: HashMap<String, FetchInfo>,
    /* TODO: Some fileds ommited */
}

#[derive(RustcDecodable, Debug)]
pub struct ProblemInfo {
    pub message: String,
    pub status: Option<String>,
    pub outcome: Option<String>,
}

#[derive(RustcDecodable, Debug)]
pub struct ChangeInfo {
    pub id: String,
    pub project: String,
    pub branch: String,
    pub topic: Option<String>,
    pub change_id: String,
    pub subject: String,
    pub status: ChangeStatus,
    pub created: String,
    pub updated: String,
    pub submitted: Option<String>,
    pub starred: Option<bool>,
    pub stars: Option<Vec<String>>,
    pub reviewed: Option<bool>,
    pub submit_type: Option<String>,
    pub mergeable: Option<bool>,
    pub insertions: u16,
    pub deletions: u16,
    pub _number: u16,
    pub owner: AccountInfo,
    pub action: Option<Vec<ActionInfo>>,
    pub labels: Option<HashMap<String, LabelInfo>>,
    pub permitted_labels: Option<HashMap<String, LabelInfo>>,
    pub removeable_reviewers: Option<Vec<AccountInfo>>,
    pub reviewers: Option<String>,
    pub messages: Option<HashMap<String, ChangeMessageInfo>>,
    pub current_revision: Option<HashMap<String, RevisionInfo>>,
    pub revision: Option<HashMap<String, RevisionInfo>>,
    pub _more_changes: Option<bool>,
    pub problems: Option<Vec<ProblemInfo>>,
}

/// **TODO**: This is subject to change! Its to unflexible.
impl Display for ChangeInfo {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        try!(writeln!(f, "* {project:.<41.41} {branch:.<20.20} {subject:.>30.30}", project=self.project, branch=self.branch, subject=self.subject));
        try!(writeln!(f, "| {changeid:41.41} {number:<31.10} {created:>19.19}", changeid=self.change_id, number=self._number, created=self.created));
        try!(writeln!(f, "| {topic:73.41} {updated:19.19}", topic=self.topic.clone().unwrap_or("N/A".to_string()), updated=self.updated));
        write!(f, "` {status}, {owner}", owner=self.owner, status=self.status)
    }
}

#[derive(RustcDecodable, Debug)]
pub enum ProjectState {
    ACTIVE,
    READONLY,
    HIDDEN,
}

#[derive(RustcDecodable, Debug, Clone)]
pub enum ProjectTypes {
    ALL,
    CODE,
    PERMISSIONS,
}

#[derive(RustcDecodable, Debug)]
pub struct WebLinkInfo {
    pub name: String,
    pub url: String,
    pub image_url: String,
}

#[derive(RustcDecodable, Debug)]
pub struct ProjectInfo {
    pub name: Option<String>,
    pub id: String,
    pub parent: Option<String>,
    pub description: Option<String>,
    pub state: Option<ProjectState>,
    pub branches: Option<HashMap<String, String>>,
    pub web_links: Option<Vec<WebLinkInfo>>,
}
<|endoftext|>


<commit_before>use super::Peripheral;
use std::fmt;

#[derive(RustcEncodable, RustcDecodable)]
pub struct Memory {
    rom: u8,
    ram_0x4000_0x7fff: usize,
    ram_0x8000_0xbfff: usize,
    ram_0xc000_0xffff: usize,

    rom0: Box<[u8]>,
    rom1: Box<[u8]>,
    bank: [Box<[u8]>; 8],

    writable_rom: bool,
}

impl Memory {
    pub fn read_word(&self, addr: u16) -> u8 {
        match addr {
            0x0000...0x3FFF => {
                match self.rom {
                    0 => self.rom0[addr as usize],
                    1 => self.rom1[addr as usize],
                    _ => unreachable!(),
                }
            }
            0x4000...0x7FFF => self.bank[self.ram_0x4000_0x7fff][(addr - 0x4000) as usize],
            0x8000...0xBFFF => self.bank[self.ram_0x8000_0xbfff][(addr - 0x8000) as usize],
            0xC000...0xFFFF => self.bank[self.ram_0xc000_0xffff][(addr - 0xC000) as usize],
            _ => unreachable!(),
        }
    }

    pub fn write_word(&mut self, addr: u16, val: u8) {
        if addr >= 0xC000 {
            self.bank[self.ram_0xc000_0xffff][(addr - 0xC000) as usize] = val;
        } else if addr >= 0x8000 && addr <= 0xBFFF {
            self.bank[self.ram_0x8000_0xbfff][(addr - 0x8000) as usize] = val;
        } else if addr >= 0x4000 && addr <= 0x7FFF {
            self.bank[self.ram_0x4000_0x7fff][(addr - 0x4000) as usize] = val;
        } else {
            if self.writable_rom {
                match self.rom {
                    0 => {
                        self.rom0[addr as usize] = val;
                    }
                    1 => {
                        self.rom1[addr as usize] = val;
                    }
                    _ => unreachable!(),
                }
            } else {
                panic!("Trying to write to unrecognized address: {:#x}", addr);
            }
        }
    }

    fn change_bank(&mut self, val: u8) {
        self.ram_0xc000_0xffff = val as usize;
    }

    fn change_rom_bank(&mut self, val: u8) {
        self.rom = val;
    }

    pub fn clear(&mut self) {
        if self.writable_rom {
            for x in self.rom0.iter_mut() {
                *x = 0;
            }
            for x in self.rom1.iter_mut() {
                *x = 0;
            }
        }
        for bank in self.bank.iter_mut() {
            for x in bank.iter_mut() {
                *x = 0;
            }
        }
    }

    pub fn get_0000_bank(&self) -> u8 {
        self.rom
    }
    pub fn get_4000_bank(&self) -> u8 {
        self.ram_0x4000_0x7fff as u8
    }
    pub fn get_8000_bank(&self) -> u8 {
        self.ram_0x8000_0xbfff as u8
    }
    pub fn get_c000_bank(&self) -> u8 {
        self.ram_0xc000_0xffff as u8
    }
}

impl Peripheral for Memory {
    fn read_port(&self, _: u16) -> u8 {
        0
    }

    fn write_port(&mut self, _: u16, val: u8) {
        self.change_bank(val & 0b00000111);
        self.change_rom_bank((val & 0b00010000) >> 4);
    }
}

impl fmt::Debug for Memory {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        writeln!(f,
                 "ram_0xc000_0xffff: {}
                  ram_0x8000_0xbfff: {}
                  ram_0x4000_0x7fff: {}
                  rom: {} ",
                 self.ram_0xc000_0xffff,
                 self.ram_0x8000_0xbfff,
                 self.ram_0x4000_0x7fff,
                 self.rom)
    }
}

pub struct MemoryBuilder {
    rom: u8,
    ram_0x4000_0x7fff: usize,
    ram_0x8000_0xbfff: usize,
    ram_0xc000_0xffff: usize,

    rom0: Box<[u8]>,
    rom1: Box<[u8]>,
    bank: [Box<[u8]>; 8],

    writable_rom: bool,
}

impl MemoryBuilder {
    pub fn new() -> Self {
        MemoryBuilder {
            rom: 0,
            ram_0x4000_0x7fff: 5,
            ram_0x8000_0xbfff: 2,
            ram_0xc000_0xffff: 0,

            rom0: vec![0; 16 * 1024].into_boxed_slice(),
            rom1: vec![0; 16 * 1024].into_boxed_slice(),

            bank: [vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice()],

            writable_rom: false,
        }
    }

    pub fn rom0(mut self, mem: Box<[u8]>) -> MemoryBuilder {
        self.rom0 = mem;
        self
    }

    pub fn rom1(mut self, mem: Box<[u8]>) -> MemoryBuilder {
        self.rom1 = mem;
        self
    }

    pub fn writable_rom(mut self, val: bool) -> MemoryBuilder {
        self.writable_rom = val;
        self
    }

    pub fn finalize(self) -> Memory {
        Memory {
            rom: self.rom,
            ram_0x4000_0x7fff: self.ram_0x4000_0x7fff,
            ram_0x8000_0xbfff: self.ram_0x8000_0xbfff,
            ram_0xc000_0xffff: self.ram_0xc000_0xffff,

            rom0: self.rom0,
            rom1: self.rom1,
            bank: self.bank,

            writable_rom: self.writable_rom,
        }
    }
}
<commit_msg>Ignore writes to ROM bank<commit_after>use super::Peripheral;
use std::fmt;

#[derive(RustcEncodable, RustcDecodable)]
pub struct Memory {
    rom: u8,
    ram_0x4000_0x7fff: usize,
    ram_0x8000_0xbfff: usize,
    ram_0xc000_0xffff: usize,

    rom0: Box<[u8]>,
    rom1: Box<[u8]>,
    bank: [Box<[u8]>; 8],

    writable_rom: bool,
}

impl Memory {
    pub fn read_word(&self, addr: u16) -> u8 {
        match addr {
            0x0000...0x3FFF => {
                match self.rom {
                    0 => self.rom0[addr as usize],
                    1 => self.rom1[addr as usize],
                    _ => unreachable!(),
                }
            }
            0x4000...0x7FFF => self.bank[self.ram_0x4000_0x7fff][(addr - 0x4000) as usize],
            0x8000...0xBFFF => self.bank[self.ram_0x8000_0xbfff][(addr - 0x8000) as usize],
            0xC000...0xFFFF => self.bank[self.ram_0xc000_0xffff][(addr - 0xC000) as usize],
            _ => unreachable!(),
        }
    }

    pub fn write_word(&mut self, addr: u16, val: u8) {
        if addr >= 0xC000 {
            self.bank[self.ram_0xc000_0xffff][(addr - 0xC000) as usize] = val;
        } else if addr >= 0x8000 && addr <= 0xBFFF {
            self.bank[self.ram_0x8000_0xbfff][(addr - 0x8000) as usize] = val;
        } else if addr >= 0x4000 && addr <= 0x7FFF {
            self.bank[self.ram_0x4000_0x7fff][(addr - 0x4000) as usize] = val;
        } else {
            if self.writable_rom {
                match self.rom {
                    0 => {
                        self.rom0[addr as usize] = val;
                    }
                    1 => {
                        self.rom1[addr as usize] = val;
                    }
                    _ => unreachable!(),
                }
            }
        }
    }

    fn change_bank(&mut self, val: u8) {
        self.ram_0xc000_0xffff = val as usize;
    }

    fn change_rom_bank(&mut self, val: u8) {
        self.rom = val;
    }

    pub fn clear(&mut self) {
        if self.writable_rom {
            for x in self.rom0.iter_mut() {
                *x = 0;
            }
            for x in self.rom1.iter_mut() {
                *x = 0;
            }
        }
        for bank in self.bank.iter_mut() {
            for x in bank.iter_mut() {
                *x = 0;
            }
        }
    }

    pub fn get_0000_bank(&self) -> u8 {
        self.rom
    }
    pub fn get_4000_bank(&self) -> u8 {
        self.ram_0x4000_0x7fff as u8
    }
    pub fn get_8000_bank(&self) -> u8 {
        self.ram_0x8000_0xbfff as u8
    }
    pub fn get_c000_bank(&self) -> u8 {
        self.ram_0xc000_0xffff as u8
    }
}

impl Peripheral for Memory {
    fn read_port(&self, _: u16) -> u8 {
        0
    }

    fn write_port(&mut self, _: u16, val: u8) {
        self.change_bank(val & 0b00000111);
        self.change_rom_bank((val & 0b00010000) >> 4);
    }
}

impl fmt::Debug for Memory {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        writeln!(f,
                 "ram_0xc000_0xffff: {}
                  ram_0x8000_0xbfff: {}
                  ram_0x4000_0x7fff: {}
                  rom: {} ",
                 self.ram_0xc000_0xffff,
                 self.ram_0x8000_0xbfff,
                 self.ram_0x4000_0x7fff,
                 self.rom)
    }
}

pub struct MemoryBuilder {
    rom: u8,
    ram_0x4000_0x7fff: usize,
    ram_0x8000_0xbfff: usize,
    ram_0xc000_0xffff: usize,

    rom0: Box<[u8]>,
    rom1: Box<[u8]>,
    bank: [Box<[u8]>; 8],

    writable_rom: bool,
}

impl MemoryBuilder {
    pub fn new() -> Self {
        MemoryBuilder {
            rom: 0,
            ram_0x4000_0x7fff: 5,
            ram_0x8000_0xbfff: 2,
            ram_0xc000_0xffff: 0,

            rom0: vec![0; 16 * 1024].into_boxed_slice(),
            rom1: vec![0; 16 * 1024].into_boxed_slice(),

            bank: [vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice(),
                   vec![0; 16 * 1024].into_boxed_slice()],

            writable_rom: false,
        }
    }

    pub fn rom0(mut self, mem: Box<[u8]>) -> MemoryBuilder {
        self.rom0 = mem;
        self
    }

    pub fn rom1(mut self, mem: Box<[u8]>) -> MemoryBuilder {
        self.rom1 = mem;
        self
    }

    pub fn writable_rom(mut self, val: bool) -> MemoryBuilder {
        self.writable_rom = val;
        self
    }

    pub fn finalize(self) -> Memory {
        Memory {
            rom: self.rom,
            ram_0x4000_0x7fff: self.ram_0x4000_0x7fff,
            ram_0x8000_0xbfff: self.ram_0x8000_0xbfff,
            ram_0xc000_0xffff: self.ram_0xc000_0xffff,

            rom0: self.rom0,
            rom1: self.rom1,
            bank: self.bank,

            writable_rom: self.writable_rom,
        }
    }
}
<|endoftext|>


<commit_before>
use super::Population;
use super::super::individual::Individual;

#[derive(Clone, Copy, PartialEq, Eq, Debug)]
pub enum Error {
    IndexOutOfRange { index: usize, total: usize },
}

impl<T> Population for Vec<T> where T: Individual {
    type I = T;
    type E = Error;

    fn size(&self) -> usize {
        self.len()
    }

    fn get(&self, index: usize) -> Result<&Self::I, Self::E> {
        let slice: &[T] = self;
        slice.get(index).ok_or(Error::IndexOutOfRange { index: index, total: self.len(), })
    }

    fn add(&mut self, indiv: Self::I) -> Result<(), Self::E> {
        self.push(indiv);
        Ok(())
    }

    fn del(&mut self, index: usize) -> Result<Self::I, Self::E> {
        if index < self.len() {
            Ok(self.swap_remove(index))
        } else {
            Err(Error::IndexOutOfRange { index: index, total: self.len(), })
        }
    }
}

#[cfg(test)]
mod tests {
    use super::Error;
    use super::super::Population;
    use super::super::super::individual;

    #[derive(PartialEq, Eq, Debug)]
    struct TestC(u8);

    impl individual::chromosome::Chromosome for TestC {
        type E = ();
    }

    #[derive(PartialEq, Eq, Debug)]
    struct TestI(TestC);

    impl individual::Individual for TestI {
        type C = TestC;
        type E = ();

        fn get_chromosome(&self) -> &Self::C {
            &self.0
        }
    }

    fn run_basic<P>(mut pop: P) where P: Population<I = TestI, E = Error> {
        assert_eq!(pop.size(), 0);
        assert_eq!(pop.add(TestI(TestC(0))), Ok(()));
        assert_eq!(pop.size(), 1);
        assert_eq!(pop.add(TestI(TestC(1))), Ok(()));
        assert_eq!(pop.size(), 2);
        assert_eq!(pop.get(0), Ok(&TestI(TestC(0))));
        assert_eq!(pop.get(1), Ok(&TestI(TestC(1))));
        assert_eq!(pop.get(2), Err(Error::IndexOutOfRange { index: 2, total: 2, }));
    }

    #[test]
    fn basic() {
        run_basic(Vec::new());
    }
}
<commit_msg>some more tests<commit_after>
use super::Population;
use super::super::individual::Individual;

#[derive(Clone, Copy, PartialEq, Eq, Debug)]
pub enum Error {
    IndexOutOfRange { index: usize, total: usize },
}

impl<T> Population for Vec<T> where T: Individual {
    type I = T;
    type E = Error;

    fn size(&self) -> usize {
        self.len()
    }

    fn get(&self, index: usize) -> Result<&Self::I, Self::E> {
        let slice: &[T] = self;
        slice.get(index).ok_or(Error::IndexOutOfRange { index: index, total: self.len(), })
    }

    fn add(&mut self, indiv: Self::I) -> Result<(), Self::E> {
        self.push(indiv);
        Ok(())
    }

    fn del(&mut self, index: usize) -> Result<Self::I, Self::E> {
        if index < self.len() {
            Ok(self.swap_remove(index))
        } else {
            Err(Error::IndexOutOfRange { index: index, total: self.len(), })
        }
    }
}

#[cfg(test)]
mod tests {
    use super::Error;
    use super::super::Population;
    use super::super::super::individual;

    #[derive(PartialEq, Eq, Debug)]
    struct TestC(u8);

    impl individual::chromosome::Chromosome for TestC {
        type E = ();
    }

    #[derive(PartialEq, Eq, Debug)]
    struct TestI(TestC);

    impl individual::Individual for TestI {
        type C = TestC;
        type E = ();

        fn get_chromosome(&self) -> &Self::C {
            &self.0
        }
    }

    fn run_basic<P>(mut pop: P) where P: Population<I = TestI, E = Error> {
        assert_eq!(pop.size(), 0);
        assert_eq!(pop.add(TestI(TestC(0))), Ok(()));
        assert_eq!(pop.size(), 1);
        assert_eq!(pop.add(TestI(TestC(1))), Ok(()));
        assert_eq!(pop.size(), 2);
        assert_eq!(pop.get(0), Ok(&TestI(TestC(0))));
        assert_eq!(pop.get(1), Ok(&TestI(TestC(1))));
        assert_eq!(pop.get(2), Err(Error::IndexOutOfRange { index: 2, total: 2, }));
        assert_eq!(pop.del(0), Ok(TestI(TestC(0))));
        assert_eq!(pop.size(), 1);
        assert_eq!(pop.get(0), Ok(&TestI(TestC(1))));
    }

    #[test]
    fn basic() {
        run_basic(Vec::new());
    }
}
<|endoftext|>


<commit_before>extern crate nom;

use std::str;
use nom::{
    is_hex_digit,
    digit,
    alpha,
    alphanumeric,
};

fn is_ws(c: char) -> bool {
    let u = c as u32;
    u == 0x20 || u == 0x9 || u == 0xD || u == 0xA
}

fn is_anon(c: char) -> bool {
    c == '[' || c == ']' || is_ws(c)
}

#[derive(PartialEq, Debug)]
pub struct Langtag<'a> {
    language: &'a str,
    subtags:  Vec<&'a str>,
}
/* [144s] LANGTAG */
named!(pub langtag<&str, Langtag>, do_parse!(
    tag!("@") >>
    language: alpha >>
    tag!("-") >>
    subtags:  separated_list_complete!(
        tag!("-"),
        alphanumeric
    ) >>
    (Langtag{
        language: language,
        subtags:  subtags,
    })
));

#[derive(PartialEq, Debug)]
pub struct Integer<'a> {
    sign:          Option<&'a str>,
    integer_part:  &'a str,
}
/* [19] INTEGER */
named!(pub integer<&str, Integer>, do_parse!(
    sign:         opt!(alt!(tag!("+") | tag!("-"))) >>
    integer_part: digit                             >>
    (Integer{
        sign:          sign,
        integer_part:  integer_part,
    })
));

#[derive(PartialEq, Debug)]
pub struct Decimal<'a> {
    sign:          Option<&'a str>,
    integer_part:  Option<&'a str>,
    decimal_point: &'a str,
    decimal_part:  &'a str,
}
/* [20] DECIMAL */
named!(pub decimal<&str, Decimal>, do_parse!(
    sign:          opt!(alt!(tag!("+") | tag!("-"))) >>
    integer_part:  opt!(digit)                       >>
    decimal_point: tag!(".")                         >>
    decimal_part:  digit                             >>
    (Decimal{
        sign:          sign,
        integer_part:  integer_part,
        decimal_point: decimal_point,
        decimal_part:  decimal_part,
    })
));

#[derive(PartialEq, Debug)]
pub enum Mantissa<'a> {
    IntegerDecimal {
        integer_part:  &'a str,
        decimal_point: &'a str,
        decimal_part:  Option<&'a str>,
    },
    Decimal {
        decimal_point: &'a str,
        decimal_part:  &'a str,
    },
    Integer {
        integer_part: &'a str,
    },
}
#[derive(PartialEq, Debug)]
pub struct Double<'a> {
    sign:     Option<&'a str>,
    mantissa: Mantissa<'a>,
    exponent: Exponent<'a>,
}
/* [21] DOUBLE */
named!(pub double<&str, Double>, do_parse!(
    sign:     opt!(alt!(tag!("+") | tag!("-"))) >>
    mantissa: alt!(
        do_parse!(
            integer_part:  digit       >>
            decimal_point: tag!(".")   >>
            decimal_part:  opt!(digit) >>
            (Mantissa::IntegerDecimal{
                integer_part:  integer_part,
                decimal_point: decimal_point,
                decimal_part:  decimal_part,
            })
        ) |
        do_parse!(
            decimal_point: tag!(".") >>
            decimal_part:  digit     >>
            (Mantissa::Decimal{
                decimal_point: decimal_point,
                decimal_part:  decimal_part,
            })
        ) |
        do_parse!(
            integer_part: digit >>
            (Mantissa::Integer{
                integer_part: integer_part,
            })
        )
    ) >>
    exponent: exponent >>
    (Double{
        sign:     sign,
        mantissa: mantissa,
        exponent: exponent,
    })
));

#[derive(PartialEq, Debug)]
pub struct Exponent<'a> {
    exponent_symbol: &'a str,
    sign:            Option<&'a str>,
    exponent_number: &'a str,
}

/* [154s] EXPONENT */
named!(pub exponent<&str, Exponent>, do_parse!(
    exponent_symbol: alt!(tag!("e") | tag!("E"))       >>
    sign:            opt!(alt!(tag!("+") | tag!("-"))) >>
    exponent_number: digit                             >>
    (Exponent{
        exponent_symbol: exponent_symbol,
        sign:            sign,
        exponent_number: exponent_number,
    })
));

/* [161s] WS */
named!(pub ws<&str, &str>, take_while_s!(is_ws));

/* [162s] ANON */
named!(pub anon<&str, &str>, verify!(
    take_while_s!(is_anon),
    |val:&str| {
        let len = val.char_indices().count();
        val.char_indices().all(|(idx, c)| {
            if idx == 0 {
                c == '['
            } else if idx == len - 1 {
                c == ']'
            } else {
                is_ws(c)
            }
        })
    }
));

/* [170s] PERCENT */
named!(pub percent<&str, &str>, verify!(
    take_s!(3),
    |val:&str| {
        let bytes = val.as_bytes();
        bytes[0] == 0x25 && is_hex_digit(bytes[1]) && is_hex_digit(bytes[2])
    }
));

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

    #[test]
    fn langtag_normal_test() {
        let input    = "@en-a-bbb-a-ccc,rest";
        let expected = IResult::Done(",rest", Langtag{
            language: "en",
            subtags:  vec!["a", "bbb", "a", "ccc"]
        });
        assert_eq!(langtag(input), expected);
    }

    #[test]
    fn langtag_abnormal_test() {
        let input    = "@en01-a-bbb-a-ccc,rest";
        let expected = IResult::Error(ErrorKind::Tag);
        assert_eq!(langtag(input), expected);
    }

    #[test]
    fn integer_normal_test() {
        let input    = "-1234rest";
        let expected = IResult::Done("rest", Integer{
            sign:          Some("-"),
            integer_part:  "1234",
        });
        assert_eq!(integer(input), expected);
    }

    #[test]
    fn decimal_normal_test() {
        let input    = "-1234.5678rest";
        let expected = IResult::Done("rest", Decimal{
            sign:          Some("-"),
            integer_part:  Some("1234"),
            decimal_point: ".",
            decimal_part:  "5678",
        });
        assert_eq!(decimal(input), expected);
    }

    #[test]
    fn double_normal_test() {
        let input    = "-1234.5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("-"),
            mantissa: Mantissa::IntegerDecimal {
                integer_part:  "1234",
                decimal_point: ".",
                decimal_part:  Some("5678"),
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);

        let input    = "-.5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("-"),
            mantissa: Mantissa::Decimal {
                decimal_point: ".",
                decimal_part:  "5678",
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);

        let input    = "+5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("+"),
            mantissa: Mantissa::Integer {
                integer_part: "5678",
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);
    }

    #[test]
    fn exponent_normal_test() {
        let input    = "e-0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "e",
            sign:            Some("-"),
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);

        let input    = "E+0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "E",
            sign:            Some("+"),
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);

        let input    = "e0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "e",
            sign:            None,
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);
    }

    #[test]
    fn ws_test() {
        assert_eq!(ws("   a"), IResult::Done("a", "   "));
    }

    #[test]
    fn anon_test() {
        assert_eq!(anon("[ ]a"), IResult::Done("a", "[ ]"));
    }

    #[test]
    fn percent_test() {
        assert_eq!(percent("%2Abc"), IResult::Done("bc", "%2A"));
    }
}
<commit_msg>Fix ws_test<commit_after>extern crate nom;

use std::str;
use nom::{
    is_hex_digit,
    digit,
    alpha,
    alphanumeric,
};

fn is_ws(c: char) -> bool {
    let u = c as u32;
    u == 0x20 || u == 0x9 || u == 0xD || u == 0xA
}

fn is_anon(c: char) -> bool {
    c == '[' || c == ']' || is_ws(c)
}

#[derive(PartialEq, Debug)]
pub struct Langtag<'a> {
    language: &'a str,
    subtags:  Vec<&'a str>,
}
/* [144s] LANGTAG */
named!(pub langtag<&str, Langtag>, do_parse!(
    tag!("@") >>
    language: alpha >>
    tag!("-") >>
    subtags:  separated_list_complete!(
        tag!("-"),
        alphanumeric
    ) >>
    (Langtag{
        language: language,
        subtags:  subtags,
    })
));

#[derive(PartialEq, Debug)]
pub struct Integer<'a> {
    sign:          Option<&'a str>,
    integer_part:  &'a str,
}
/* [19] INTEGER */
named!(pub integer<&str, Integer>, do_parse!(
    sign:         opt!(alt!(tag!("+") | tag!("-"))) >>
    integer_part: digit                             >>
    (Integer{
        sign:          sign,
        integer_part:  integer_part,
    })
));

#[derive(PartialEq, Debug)]
pub struct Decimal<'a> {
    sign:          Option<&'a str>,
    integer_part:  Option<&'a str>,
    decimal_point: &'a str,
    decimal_part:  &'a str,
}
/* [20] DECIMAL */
named!(pub decimal<&str, Decimal>, do_parse!(
    sign:          opt!(alt!(tag!("+") | tag!("-"))) >>
    integer_part:  opt!(digit)                       >>
    decimal_point: tag!(".")                         >>
    decimal_part:  digit                             >>
    (Decimal{
        sign:          sign,
        integer_part:  integer_part,
        decimal_point: decimal_point,
        decimal_part:  decimal_part,
    })
));

#[derive(PartialEq, Debug)]
pub enum Mantissa<'a> {
    IntegerDecimal {
        integer_part:  &'a str,
        decimal_point: &'a str,
        decimal_part:  Option<&'a str>,
    },
    Decimal {
        decimal_point: &'a str,
        decimal_part:  &'a str,
    },
    Integer {
        integer_part: &'a str,
    },
}
#[derive(PartialEq, Debug)]
pub struct Double<'a> {
    sign:     Option<&'a str>,
    mantissa: Mantissa<'a>,
    exponent: Exponent<'a>,
}
/* [21] DOUBLE */
named!(pub double<&str, Double>, do_parse!(
    sign:     opt!(alt!(tag!("+") | tag!("-"))) >>
    mantissa: alt!(
        do_parse!(
            integer_part:  digit       >>
            decimal_point: tag!(".")   >>
            decimal_part:  opt!(digit) >>
            (Mantissa::IntegerDecimal{
                integer_part:  integer_part,
                decimal_point: decimal_point,
                decimal_part:  decimal_part,
            })
        ) |
        do_parse!(
            decimal_point: tag!(".") >>
            decimal_part:  digit     >>
            (Mantissa::Decimal{
                decimal_point: decimal_point,
                decimal_part:  decimal_part,
            })
        ) |
        do_parse!(
            integer_part: digit >>
            (Mantissa::Integer{
                integer_part: integer_part,
            })
        )
    ) >>
    exponent: exponent >>
    (Double{
        sign:     sign,
        mantissa: mantissa,
        exponent: exponent,
    })
));

#[derive(PartialEq, Debug)]
pub struct Exponent<'a> {
    exponent_symbol: &'a str,
    sign:            Option<&'a str>,
    exponent_number: &'a str,
}

/* [154s] EXPONENT */
named!(pub exponent<&str, Exponent>, do_parse!(
    exponent_symbol: alt!(tag!("e") | tag!("E"))       >>
    sign:            opt!(alt!(tag!("+") | tag!("-"))) >>
    exponent_number: digit                             >>
    (Exponent{
        exponent_symbol: exponent_symbol,
        sign:            sign,
        exponent_number: exponent_number,
    })
));

/* [161s] WS */
named!(pub ws<&str, &str>, take_while_s!(is_ws));

/* [162s] ANON */
named!(pub anon<&str, &str>, verify!(
    take_while_s!(is_anon),
    |val:&str| {
        let len = val.char_indices().count();
        val.char_indices().all(|(idx, c)| {
            if idx == 0 {
                c == '['
            } else if idx == len - 1 {
                c == ']'
            } else {
                is_ws(c)
            }
        })
    }
));

/* [170s] PERCENT */
named!(pub percent<&str, &str>, verify!(
    take_s!(3),
    |val:&str| {
        let bytes = val.as_bytes();
        bytes[0] == 0x25 && is_hex_digit(bytes[1]) && is_hex_digit(bytes[2])
    }
));

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

    #[test]
    fn langtag_normal_test() {
        let input    = "@en-a-bbb-a-ccc,rest";
        let expected = IResult::Done(",rest", Langtag{
            language: "en",
            subtags:  vec!["a", "bbb", "a", "ccc"]
        });
        assert_eq!(langtag(input), expected);
    }

    #[test]
    fn langtag_abnormal_test() {
        let input    = "@en01-a-bbb-a-ccc,rest";
        let expected = IResult::Error(ErrorKind::Tag);
        assert_eq!(langtag(input), expected);
    }

    #[test]
    fn integer_normal_test() {
        let input    = "-1234rest";
        let expected = IResult::Done("rest", Integer{
            sign:          Some("-"),
            integer_part:  "1234",
        });
        assert_eq!(integer(input), expected);
    }

    #[test]
    fn decimal_normal_test() {
        let input    = "-1234.5678rest";
        let expected = IResult::Done("rest", Decimal{
            sign:          Some("-"),
            integer_part:  Some("1234"),
            decimal_point: ".",
            decimal_part:  "5678",
        });
        assert_eq!(decimal(input), expected);
    }

    #[test]
    fn double_normal_test() {
        let input    = "-1234.5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("-"),
            mantissa: Mantissa::IntegerDecimal {
                integer_part:  "1234",
                decimal_point: ".",
                decimal_part:  Some("5678"),
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);

        let input    = "-.5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("-"),
            mantissa: Mantissa::Decimal {
                decimal_point: ".",
                decimal_part:  "5678",
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);

        let input    = "+5678e-0123456789rest";
        let expected = IResult::Done("rest", Double{
            sign:     Some("+"),
            mantissa: Mantissa::Integer {
                integer_part: "5678",
            },
            exponent: exponent("e-0123456789").unwrap().1,
        });
        assert_eq!(double(input), expected);
    }

    #[test]
    fn exponent_normal_test() {
        let input    = "e-0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "e",
            sign:            Some("-"),
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);

        let input    = "E+0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "E",
            sign:            Some("+"),
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);

        let input    = "e0123456789rest";
        let expected = IResult::Done("rest", Exponent{
            exponent_symbol: "e",
            sign:            None,
            exponent_number: "0123456789",
        });
        assert_eq!(exponent(input), expected);
    }

    #[test]
    fn ws_test() {
        assert_eq!(ws(" 	\r\nrest"), IResult::Done("rest", " 	\r\n"));
    }

    #[test]
    fn anon_test() {
        assert_eq!(anon("[ ]a"), IResult::Done("a", "[ ]"));
    }

    #[test]
    fn percent_test() {
        assert_eq!(percent("%2Abc"), IResult::Done("bc", "%2A"));
    }
}
<|endoftext|>


<commit_before>use webcore::value::{Value, Reference};
use webcore::try_from::TryInto;
use webapi::blob::IBlob;
use webapi::event_target::{IEventTarget, EventTarget};
use webapi::array_buffer::ArrayBuffer;
use private::TODO;

/// The FileReader object lets web applications asynchronously read the contents of files
/// (or raw data buffers) stored on the user's computer, using [File](struct.File.html)
/// or [Blob](struct.Blob.html) objects to specify the file or data to read.
///
/// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader)
// https://w3c.github.io/FileAPI/#dfn-filereader
#[derive(Clone, Debug, PartialEq, Eq, ReferenceType)]
#[reference(instance_of = "FileReader")]
#[reference(subclass_of(EventTarget))]
pub struct FileReader( Reference );

impl IEventTarget for FileReader {}

/// The [result](struct.FileReader.html#method.result) of a read operation performed with a [FileReader](struct.File.html).
#[derive(Clone, Debug)]
pub enum FileReaderResult {
    /// A string; a result of calling [FileReader::read_as_text](struct.FileReader.html#method.read_as_text).
    String( String ),

    /// An [ArrayBuffer](struct.ArrayBuffer.html); a result of calling [FileReader::read_as_text](struct.FileReader.html#method.read_as_array_buffer).
    ArrayBuffer( ArrayBuffer )
}

/// A number indicating the state of the `FileReader`.
///
/// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readyState)
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
pub enum FileReaderReadyState {
    Empty,
    Loading,
    Done
}

impl FileReader {
    /// Returns a newly constructed `FileReader`.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/FileReader)
    // https://w3c.github.io/FileAPI/#dom-filereader-filereader
    pub fn new() -> FileReader {
        js!( return new FileReader(); ).try_into().unwrap()
    }

    /// Starts reading the contents of the specified blob. Once finished
    /// the `result` attribute will contain the contents of the file as a text string.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readAsText)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readAsText
    pub fn read_as_text< T: IBlob >( &self, blob: &T ) -> Result< (), TODO > {
        js!( @{self}.readAsText( @{blob.as_ref()} ); );
        Ok(())
    }

    /// Starts reading the contents of the specified blob. Once finished
    /// the `result` attribute will contain the contents of the file as an [TypedArray](struct.ArrayBuffer.html).
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readAsArrayBuffer)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readAsArrayBuffer
    pub fn read_as_array_buffer< T: IBlob >( &self, blob: &T ) -> Result< (), TODO > {
        js!( @{self}.readAsArrayBuffer( @{blob.as_ref()} ); );
        Ok(())
    }

    /// Aborts the read operation. Upon return, the `ready_state` will be `Done`.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/abort)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-abort%E2%91%A0
    pub fn abort( &self ) {
        js!( return @{self}.abort(); );
    }

    /// Returns the current state of the reader.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readyState)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readyState
    pub fn ready_state( &self ) -> FileReaderReadyState {
        let state: i32 = js!( return @{self}.readyState; ).try_into().unwrap();
        match state {
            0 => FileReaderReadyState::Empty,
            1 => FileReaderReadyState::Loading,
            2 => FileReaderReadyState::Done,
            _ => unreachable!( "Unexpected value of FileReader::readyState: {}", state )
        }
    }

    /// The file's contents. This method will only return a value after the read operation
    /// is complete, and the format of the data depends on which of the methods was used
    /// to initiate the read operation.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/result)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-result
    pub fn result( &self ) -> Option< FileReaderResult > {
        let result = js!( return @{self}.result; );
        match result {
            Value::Undefined | Value::Null => None,
            Value::String( text ) => Some( FileReaderResult::String( text ) ),
            Value::Reference( reference ) => Some( FileReaderResult::ArrayBuffer( reference.try_into().unwrap() ) ),
            _ => unreachable!( "Unexpected result of a FileReader: {:?}", result )
        }
    }
}
<commit_msg>Fixing file_reader.rs documentation<commit_after>use webcore::value::{Value, Reference};
use webcore::try_from::TryInto;
use webapi::blob::IBlob;
use webapi::event_target::{IEventTarget, EventTarget};
use webapi::array_buffer::ArrayBuffer;
use private::TODO;

/// The FileReader object lets web applications asynchronously read the contents of files
/// (or raw data buffers) stored on the user's computer, using [File](struct.File.html)
/// or [Blob](struct.Blob.html) objects to specify the file or data to read.
///
/// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader)
// https://w3c.github.io/FileAPI/#dfn-filereader
#[derive(Clone, Debug, PartialEq, Eq, ReferenceType)]
#[reference(instance_of = "FileReader")]
#[reference(subclass_of(EventTarget))]
pub struct FileReader( Reference );

impl IEventTarget for FileReader {}

/// The [result](struct.FileReader.html#method.result) of a read operation performed with a [FileReader](struct.File.html).
#[derive(Clone, Debug)]
pub enum FileReaderResult {
    /// A string; a result of calling [FileReader::read_as_text](struct.FileReader.html#method.read_as_text).
    String( String ),

    /// An [ArrayBuffer](struct.ArrayBuffer.html); a result of calling [FileReader::read_as_array_buffer](struct.FileReader.html#method.read_as_array_buffer).
    ArrayBuffer( ArrayBuffer )
}

/// A number indicating the state of the `FileReader`.
///
/// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readyState)
#[derive(Copy, Clone, PartialEq, Eq, Debug)]
pub enum FileReaderReadyState {
    Empty,
    Loading,
    Done
}

impl FileReader {
    /// Returns a newly constructed `FileReader`.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/FileReader)
    // https://w3c.github.io/FileAPI/#dom-filereader-filereader
    pub fn new() -> FileReader {
        js!( return new FileReader(); ).try_into().unwrap()
    }

    /// Starts reading the contents of the specified blob. Once finished
    /// the `result` attribute will contain the contents of the file as a text string.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readAsText)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readAsText
    pub fn read_as_text< T: IBlob >( &self, blob: &T ) -> Result< (), TODO > {
        js!( @{self}.readAsText( @{blob.as_ref()} ); );
        Ok(())
    }

    /// Starts reading the contents of the specified blob. Once finished
    /// the `result` attribute will contain the contents of the file as an [TypedArray](struct.ArrayBuffer.html).
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readAsArrayBuffer)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readAsArrayBuffer
    pub fn read_as_array_buffer< T: IBlob >( &self, blob: &T ) -> Result< (), TODO > {
        js!( @{self}.readAsArrayBuffer( @{blob.as_ref()} ); );
        Ok(())
    }

    /// Aborts the read operation. Upon return, the `ready_state` will be `Done`.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/abort)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-abort%E2%91%A0
    pub fn abort( &self ) {
        js!( return @{self}.abort(); );
    }

    /// Returns the current state of the reader.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/readyState)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-readyState
    pub fn ready_state( &self ) -> FileReaderReadyState {
        let state: i32 = js!( return @{self}.readyState; ).try_into().unwrap();
        match state {
            0 => FileReaderReadyState::Empty,
            1 => FileReaderReadyState::Loading,
            2 => FileReaderReadyState::Done,
            _ => unreachable!( "Unexpected value of FileReader::readyState: {}", state )
        }
    }

    /// The file's contents. This method will only return a value after the read operation
    /// is complete, and the format of the data depends on which of the methods was used
    /// to initiate the read operation.
    ///
    /// [(JavaScript docs)](https://developer.mozilla.org/en-US/docs/Web/API/FileReader/result)
    // https://w3c.github.io/FileAPI/#ref-for-dfn-result
    pub fn result( &self ) -> Option< FileReaderResult > {
        let result = js!( return @{self}.result; );
        match result {
            Value::Undefined | Value::Null => None,
            Value::String( text ) => Some( FileReaderResult::String( text ) ),
            Value::Reference( reference ) => Some( FileReaderResult::ArrayBuffer( reference.try_into().unwrap() ) ),
            _ => unreachable!( "Unexpected result of a FileReader: {:?}", result )
        }
    }
}
<|endoftext|>


<commit_before>/*
Copyright (c) 2016-2017, Robert Ou <rqou@robertou.com> and contributors
All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:

1. Redistributions of source code must retain the above copyright notice,
   this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice,
   this list of conditions and the following disclaimer in the documentation
   and/or other materials provided with the distribution.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

use std::hash::{Hash, Hasher};
use std::marker::PhantomData;
use std::slice;

#[derive(Debug)]
pub struct ObjPoolIndex<T> {
    i: usize,
    type_marker: PhantomData<T>
}

impl<T> Copy for ObjPoolIndex<T> { }

impl<T> Clone for ObjPoolIndex<T> {
    fn clone(&self) -> ObjPoolIndex<T> {
        *self
    }
}

impl<T> PartialEq for ObjPoolIndex<T> {
    fn eq(&self, other: &ObjPoolIndex<T>) -> bool {
        self.i == other.i
    }
}

impl<T> Eq for ObjPoolIndex<T> { }

impl<T> Hash for ObjPoolIndex<T> {
    fn hash<H: Hasher>(&self, state: &mut H) {
        self.i.hash(state);
    }
}

#[derive(Debug)]
pub struct ObjPool<T> {
    storage: Vec<T>
}

impl<T> ObjPool<T> {
    pub fn new() -> ObjPool<T> {
        ObjPool {storage: Vec::new()}
    }

    pub fn insert(&mut self, item: T) -> ObjPoolIndex<T> {
        let i = self.storage.len();

        self.storage.push(item);

        ObjPoolIndex::<T> {i: i, type_marker: PhantomData}
    }

    pub fn get(&self, i: ObjPoolIndex<T>) -> &T {
        &self.storage[i.i]
    }

    pub fn get_mut(&mut self, i: ObjPoolIndex<T>) -> &mut T {
        &mut self.storage[i.i]
    }

    pub fn iter(&self) -> ObjPoolIterator<T> {
        ObjPoolIterator {
            pool: self,
            current_idx: 0,
        }
    }
}

impl<T: Default> ObjPool<T> {
    pub fn alloc(&mut self) -> ObjPoolIndex<T> {
        let i = self.storage.len();
        let o = T::default();

        self.storage.push(o);

        ObjPoolIndex::<T> {i: i, type_marker: PhantomData}
    }
}

pub struct ObjPoolIterator<'a, T: 'a> {
    pool: &'a ObjPool<T>,
    current_idx: usize,
}

impl<'a, T: 'a> Iterator for ObjPoolIterator<'a, T> {
    type Item = ObjPoolIndex<T>;

    fn next(&mut self) -> Option<ObjPoolIndex<T>> {
        if self.current_idx == self.pool.storage.len() {
            None
        } else {
            let ret = ObjPoolIndex::<T> {i: self.current_idx, type_marker: PhantomData};
            self.current_idx += 1;
            Some(ret)
        }
    }
}

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

    #[derive(Default)]
    struct ObjPoolTestObject {
        foo: u32
    }

    #[test]
    fn objpool_basic_works() {
        let mut pool = ObjPool::<ObjPoolTestObject>::new();
        let x = pool.alloc();
        let y = pool.alloc();
        {
            let o = pool.get_mut(x);
            o.foo = 123;
        }
        {
            let o = pool.get_mut(y);
            o.foo = 456;
        }
        let ox = pool.get(x);
        let oy = pool.get(y);
        assert_eq!(ox.foo, 123);
        assert_eq!(oy.foo, 456);
    }
}
<commit_msg>xc2par: Expose some info about raw indices in objpool<commit_after>/*
Copyright (c) 2016-2017, Robert Ou <rqou@robertou.com> and contributors
All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:

1. Redistributions of source code must retain the above copyright notice,
   this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice,
   this list of conditions and the following disclaimer in the documentation
   and/or other materials provided with the distribution.

THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/

use std::hash::{Hash, Hasher};
use std::marker::PhantomData;

#[derive(Debug)]
pub struct ObjPoolIndex<T> {
    i: usize,
    type_marker: PhantomData<T>
}

impl<T> Copy for ObjPoolIndex<T> { }

impl<T> Clone for ObjPoolIndex<T> {
    fn clone(&self) -> ObjPoolIndex<T> {
        *self
    }
}

impl<T> PartialEq for ObjPoolIndex<T> {
    fn eq(&self, other: &ObjPoolIndex<T>) -> bool {
        self.i == other.i
    }
}

impl<T> Eq for ObjPoolIndex<T> { }

impl<T> Hash for ObjPoolIndex<T> {
    fn hash<H: Hasher>(&self, state: &mut H) {
        self.i.hash(state);
    }
}

impl<T> ObjPoolIndex<T> {
    pub fn get_raw_i(&self) -> usize {
        self.i
    }
}

#[derive(Debug)]
pub struct ObjPool<T> {
    storage: Vec<T>
}

impl<T> ObjPool<T> {
    pub fn new() -> ObjPool<T> {
        ObjPool {storage: Vec::new()}
    }

    pub fn insert(&mut self, item: T) -> ObjPoolIndex<T> {
        let i = self.storage.len();

        self.storage.push(item);

        ObjPoolIndex::<T> {i: i, type_marker: PhantomData}
    }

    pub fn get(&self, i: ObjPoolIndex<T>) -> &T {
        &self.storage[i.i]
    }

    pub fn get_mut(&mut self, i: ObjPoolIndex<T>) -> &mut T {
        &mut self.storage[i.i]
    }

    pub fn iter(&self) -> ObjPoolIterator<T> {
        ObjPoolIterator {
            pool: self,
            current_idx: 0,
        }
    }

    pub fn len(&self) -> usize {
        self.storage.len()
    }
}

impl<T: Default> ObjPool<T> {
    pub fn alloc(&mut self) -> ObjPoolIndex<T> {
        let i = self.storage.len();
        let o = T::default();

        self.storage.push(o);

        ObjPoolIndex::<T> {i: i, type_marker: PhantomData}
    }
}

pub struct ObjPoolIterator<'a, T: 'a> {
    pool: &'a ObjPool<T>,
    current_idx: usize,
}

impl<'a, T: 'a> Iterator for ObjPoolIterator<'a, T> {
    type Item = ObjPoolIndex<T>;

    fn next(&mut self) -> Option<ObjPoolIndex<T>> {
        if self.current_idx == self.pool.storage.len() {
            None
        } else {
            let ret = ObjPoolIndex::<T> {i: self.current_idx, type_marker: PhantomData};
            self.current_idx += 1;
            Some(ret)
        }
    }
}

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

    #[derive(Default)]
    struct ObjPoolTestObject {
        foo: u32
    }

    #[test]
    fn objpool_basic_works() {
        let mut pool = ObjPool::<ObjPoolTestObject>::new();
        let x = pool.alloc();
        let y = pool.alloc();
        {
            let o = pool.get_mut(x);
            o.foo = 123;
        }
        {
            let o = pool.get_mut(y);
            o.foo = 456;
        }
        let ox = pool.get(x);
        let oy = pool.get(y);
        assert_eq!(ox.foo, 123);
        assert_eq!(oy.foo, 456);
    }
}
<|endoftext|>


<commit_before>use expression::Expression;
use query_builder::AsQuery;
use query_source::QuerySource;

/// Sets the order clause of a query. If there was already a order clause, it
/// will be overridden. The expression passed to `order` must actually be valid
/// for the query. See also:
/// [`.desc()`](../expression/expression_methods/global_expression_methods/trait.ExpressionMethods.html#method.desc)
/// and [`.asc()`](../expression/expression_methods/global_expression_methods/trait.ExpressionMethods.html#method.asc)
///
/// Ordering by multiple columns can be achieved by passing a tuple of those
/// columns.
///
/// This is automatically implemented for the various query builder types.
///
/// # Examples
///
/// ```rust
/// # #[macro_use] extern crate diesel;
/// # include!("src/doctest_setup.rs");
/// #
/// # table! {
/// #     users {
/// #         id -> Integer,
/// #         name -> VarChar,
/// #     }
/// # }
/// #
/// # fn main() {
/// let connection = establish_connection();
/// #     connection.execute("DELETE FROM users").unwrap();
/// connection.execute("INSERT INTO users (name) VALUES ('Saul'), ('Steve'), ('Stan')").unwrap();
/// use self::users::dsl::{users, id, name};
/// // load all users' names, ordered by their name descending
/// let ordered_names = users.select(name).order(name.desc()).load(&connection).unwrap();
/// assert_eq!(Ok(vec![String::from("Steve"), String::from("Stan"), String::from("Saul")]), ordered_names);
/// # }
/// ```
pub trait OrderDsl<Expr: Expression>: AsQuery {
    type Output: AsQuery<SqlType=Self::SqlType>;

    fn order(self, expr: Expr) -> Self::Output;
}

impl<T, Expr, ST> OrderDsl<Expr> for T where
    Expr: Expression,
    T: QuerySource + AsQuery<SqlType=ST>,
    T::Query: OrderDsl<Expr, SqlType=ST>,
{
    type Output = <T::Query as OrderDsl<Expr>>::Output;

    fn order(self, expr: Expr) -> Self::Output {
        self.as_query().order(expr)
    }
}
<commit_msg>Removed Ok() unbox call and added another example showing multiple ordering<commit_after>use expression::Expression;
use query_builder::AsQuery;
use query_source::QuerySource;

/// Sets the order clause of a query. If there was already a order clause, it
/// will be overridden. The expression passed to `order` must actually be valid
/// for the query. See also:
/// [`.desc()`](../expression/expression_methods/global_expression_methods/trait.ExpressionMethods.html#method.desc)
/// and [`.asc()`](../expression/expression_methods/global_expression_methods/trait.ExpressionMethods.html#method.asc)
///
/// Ordering by multiple columns can be achieved by passing a tuple of those
/// columns.
///
/// This is automatically implemented for the various query builder types.
///
/// # Examples
///
/// ```rust
/// # #[macro_use] extern crate diesel;
/// # include!("src/doctest_setup.rs");
/// #
/// # table! {
/// #     users {
/// #         id -> Integer,
/// #         name -> VarChar,
/// #     }
/// # }
/// #
/// # fn main() {
/// let connection = establish_connection();
/// #     connection.execute("DELETE FROM users").unwrap();
/// connection.execute("INSERT INTO users (name) VALUES ('Saul'), ('Steve'), ('Stan')").unwrap();
/// use self::users::dsl::{users, id, name};
/// // load all users' names, ordered by their name descending
/// let ordered_names = users.select(name).order(name.desc()).load(&connection).unwrap();
/// assert_eq!(vec![String::from("Steve"), String::from("Stan"), String::from("Saul")], ordered_names);
///
/// connection.execute("INSERT INTO users (name) VALUES ('Stan')").unwrap();
/// let ordered_name_id_pairs = users.filter(name.eq("Stan")).select((name, id)).order((name.asc(), id.desc())).load(&connection).unwrap();
/// assert_eq!(vec![(String::from("Saul"), 1), (String::from("Stan"), 2), (String::from("Stan"), 1), (String::from("Steve"), 1)], ordered_name_id_pairs);
/// # }
/// ```
pub trait OrderDsl<Expr: Expression>: AsQuery {
    type Output: AsQuery<SqlType=Self::SqlType>;

    fn order(self, expr: Expr) -> Self::Output;
}

impl<T, Expr, ST> OrderDsl<Expr> for T where
    Expr: Expression,
    T: QuerySource + AsQuery<SqlType=ST>,
    T::Query: OrderDsl<Expr, SqlType=ST>,
{
    type Output = <T::Query as OrderDsl<Expr>>::Output;

    fn order(self, expr: Expr) -> Self::Output {
        self.as_query().order(expr)
    }
}
<|endoftext|>