<commit_before>use resolution::solver::Solver;
use integration::integrator::Integrator;
use detection::detector::Detector;

pub struct World<N, O, C> {
    objects:     ~[@mut O],
    integrators: ~[@mut Integrator<N, O>],
    detectors:   ~[@mut Detector<N, O, C>],
    solvers:     ~[@mut Solver<N, C>]
}

impl<N, O, C> World<N, O, C> {
    pub fn new() -> World<N, O, C> {
        World {
            objects:     ~[],
            integrators: ~[],
            detectors:   ~[],
            solvers:     ~[]
        }
    }
}

impl<N: Clone, O, C> World<N, O, C> {
    pub fn step(&mut self, dt: N) {
        //
        // Integration
        //
        for i in self.integrators.mut_iter() {
            i.update(dt.clone())
        }

        //
        // Interference detection
        //
        let mut interferences = ~[];

        for d in self.detectors.mut_iter() {
            d.update();
            d.interferences(&mut interferences);
        }

        //
        // Resolution
        //
        for s in self.solvers.mut_iter() {
            s.solve(dt.clone(), interferences)
        }
    }

    pub fn add_detector<D: 'static + Detector<N, O, C>>(&mut self, d: @mut D) {
        self.detectors.push(d as @mut Detector<N, O, C>);

        for o in self.objects.iter() {
            d.add(o.clone())
        }
    }

    pub fn add_integrator<I: 'static + Integrator<N, O>>(&mut self, i: @mut I) {
        self.integrators.push(i as @mut Integrator<N, O>);

        for o in self.objects.mut_iter() {
            i.add(o.clone())
        }
    }

    pub fn add_solver<S: 'static + Solver<N, C>>(&mut self, s: @mut S) {
        self.solvers.push(s as @mut Solver<N, C>);
    }

    pub fn add_object(&mut self, rb: @mut O) {
        self.objects.push(rb);

        let rb = self.objects.last();

        for d in self.integrators.mut_iter() {
            d.add(rb.clone())
        }

        for d in self.detectors.mut_iter() {
            d.add(rb.clone())
        }
    }
}
<commit_msg>Add acces to the world attributes.<commit_after>use resolution::solver::Solver;
use integration::integrator::Integrator;
use detection::detector::Detector;

pub struct World<N, O, C> {
    objects:     ~[@mut O],
    integrators: ~[@mut Integrator<N, O>],
    detectors:   ~[@mut Detector<N, O, C>],
    solvers:     ~[@mut Solver<N, C>]
}

impl<N, O, C> World<N, O, C> {
    pub fn new() -> World<N, O, C> {
        World {
            objects:     ~[],
            integrators: ~[],
            detectors:   ~[],
            solvers:     ~[]
        }
    }
}

impl<N: Clone, O, C> World<N, O, C> {
    pub fn step(&mut self, dt: N) {
        //
        // Integration
        //
        for i in self.integrators.mut_iter() {
            i.update(dt.clone())
        }

        //
        // Interference detection
        //
        let mut interferences = ~[];

        for d in self.detectors.mut_iter() {
            d.update();
            d.interferences(&mut interferences);
        }

        //
        // Resolution
        //
        for s in self.solvers.mut_iter() {
            s.solve(dt.clone(), interferences)
        }
    }

    pub fn add_detector<D: 'static + Detector<N, O, C>>(&mut self, d: @mut D) {
        self.detectors.push(d as @mut Detector<N, O, C>);

        for o in self.objects.iter() {
            d.add(o.clone())
        }
    }

    pub fn add_integrator<I: 'static + Integrator<N, O>>(&mut self, i: @mut I) {
        self.integrators.push(i as @mut Integrator<N, O>);

        for o in self.objects.mut_iter() {
            i.add(o.clone())
        }
    }

    pub fn add_solver<S: 'static + Solver<N, C>>(&mut self, s: @mut S) {
        self.solvers.push(s as @mut Solver<N, C>);
    }

    pub fn add_object(&mut self, rb: @mut O) {
        self.objects.push(rb);

        let rb = self.objects.last();

        for d in self.integrators.mut_iter() {
            d.add(rb.clone())
        }

        for d in self.detectors.mut_iter() {
            d.add(rb.clone())
        }
    }

    pub fn objects<'r>(&'r self) -> &'r [@mut O] {
        let res: &'r [@mut O] = self.objects;

        res
    }

    pub fn integrators<'r>(&'r self) -> &'r [@mut Integrator<N, O>] {
        let res: &'r [@mut Integrator<N, O>] = self.integrators;

        res
    }

    pub fn detectors<'r>(&'r self) -> &'r [@mut Detector<N, O, C>] {
        let res: &'r [@mut Detector<N, O, C>] = self.detectors;

        res
    }

    pub fn solvers<'r>(&'r self) -> &'r [@mut Solver<N, C>] {
        let res: &'r [@mut Solver<N, C>] = self.solvers;

        res
    }
}
<|endoftext|>


<commit_before>/*
Copyright (c) 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::collections::HashMap;
use std::io::Write;

#[macro_use]
extern crate serde_derive;
extern crate serde_json;

/// Legal values for the direction of a port on a module
#[derive(Copy, Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
pub enum PortDirection {
    #[serde(rename = "input")]
    Input,
    #[serde(rename = "output")]
    Output,
    #[serde(rename = "inout")]
    InOut,
}

/// Special constant bit values
#[derive(Copy, Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
pub enum SpecialBit {
    /// Constant 0
    #[serde(rename = "0")]
    _0,
    /// Constant 1
    #[serde(rename = "1")]
    _1,
    /// Constant X (invalid)
    #[serde(rename = "x")]
    X,
    /// Constant Z (tri-state)
    #[serde(rename = "z")]
    Z,
}

/// A number representing a single bit of a wire
#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
#[serde(untagged)]
pub enum BitVal {
    /// An actual signal number
    N(usize),
    /// A special constant value
    S(SpecialBit)
}

/// The value of an attribute/parameter
#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
#[serde(untagged)]
pub enum AttributeVal {
    /// Numeric attribute value
    N(usize),
    /// String attribute value
    S(String),
}

/// Represents an entire .json file used by Yosys
#[derive(Serialize, Deserialize, Debug, Default)]
pub struct Netlist {
    /// The program that created this file.
    #[serde(default)]
    pub creator: String,
    /// A map from module names to module objects contained in this .json file
    #[serde(default)]
    pub modules: HashMap<String, Module>,
}

/// Represents one module in the Yosys hierarchy
#[derive(Serialize, Deserialize, Debug, Default)]
pub struct Module {
    /// Module attributes
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
    /// Module ports (interfaces to other modules)
    #[serde(default)]
    pub ports: HashMap<String, Port>,
    /// Module cells (objects inside this module)
    #[serde(default)]
    pub cells: HashMap<String, Cell>,
    /// Module netnames (names of wires in this module)
    #[serde(default)]
    pub netnames: HashMap<String, Netname>,
}

/// Represents a port on a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Port {
    /// Port direction
    pub direction: PortDirection,
    /// Bit value(s) representing the wire(s) connected to this port
    pub bits: Vec<BitVal>,
}

/// Represents a cell in a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Cell {
    /// Indicates an internal/auto-generated name that starts with `$`
    #[serde(default)]
    pub hide_name: usize,
    /// Name of the type of this cell
    #[serde(rename="type")]
    pub cell_type: String,
    /// Parameters specified on this cell
    #[serde(default)]
    pub parameters: HashMap<String, AttributeVal>,
    /// Attributes specified on this cell
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
    /// The direction of the ports on this cell
    #[serde(default)]
    pub port_directions: HashMap<String, String>,
    /// Bit value(s) representing the wire(s) connected to the inputs/outputs of this cell
    pub connections: HashMap<String, Vec<BitVal>>,
}

/// Represents the name of a net in a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Netname {
    /// Indicates an internal/auto-generated name that starts with `$`
    #[serde(default)]
    pub hide_name: usize,
    /// Bit value(s) that should be given this name
    pub bits: Vec<BitVal>,
    /// Attributes for this netname
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
}

impl Netlist {
    /// Read netlist data from a slice containing the bytes from a Yosys .json file
    pub fn from_slice(input: &[u8]) -> Result<Netlist, serde_json::Error> {
        serde_json::from_slice(input)
    }

    /// Serialize to a String
    pub fn to_string(&self) -> Result<String, serde_json::Error> {
        serde_json::to_string(self)
    }

    /// Serialize to a writer
    pub fn to_writer(&self, writer: &mut Write) -> Result<(), serde_json::Error> {
        serde_json::to_writer(writer, self)
    }
}

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

    #[test]
    fn super_empty_json() {
        let result = Netlist::from_slice(br#"
            {}"#).unwrap();
        assert_eq!(result.creator, "");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn empty_json() {
        let result = Netlist::from_slice(br#"
            {
              "creator": "this is a test",
              "modules": {
              }
            }"#).unwrap();
        assert_eq!(result.creator, "this is a test");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn empty_json_2() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
              }
            }"#).unwrap();
        assert_eq!(result.creator, "");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn bit_values_test() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "connections": {
                        "IN": [ "x", 0, "z", 234, "1", "0" ]
                      }
                    }
                  }
                }
              }
            }"#).unwrap();
        assert_eq!(result.modules.get("mymodule").unwrap().cells.get("mycell").unwrap().connections.get("IN").unwrap(),
            &vec![BitVal::S(SpecialBit::X), BitVal::N(0), BitVal::S(SpecialBit::Z), BitVal::N(234),
                BitVal::S(SpecialBit::_1), BitVal::S(SpecialBit::_0)]);
    }

    #[test]
    #[should_panic]
    fn invalid_bit_value_test() {
        Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "connections": {
                        "IN": [ "w" ]
                      }
                    }
                  }
                }
              }
            }"#).unwrap();
    }

    #[test]
    fn attribute_value_test() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "parameters": {
                        "testparam": 123
                      },
                      "connections": {}
                    }
                  }
                }
              }
            }"#).unwrap();
        assert_eq!(result.modules.get("mymodule").unwrap().cells.get("mycell").unwrap()
            .parameters.get("testparam").unwrap(), &AttributeVal::N(123));
    }

    #[test]
    #[should_panic]
    fn invalid_attribute_value_test() {
        Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "parameters": {
                        "testparam": [123]
                      },
                      "connections": {}
                    }
                  }
                }
              }
            }"#).unwrap();
    }
}
<commit_msg>yosys-netlist-json: Fix port_directions on cells<commit_after>/*
Copyright (c) 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::collections::HashMap;
use std::io::Write;

#[macro_use]
extern crate serde_derive;
extern crate serde_json;

/// Legal values for the direction of a port on a module
#[derive(Copy, Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
pub enum PortDirection {
    #[serde(rename = "input")]
    Input,
    #[serde(rename = "output")]
    Output,
    #[serde(rename = "inout")]
    InOut,
}

/// Special constant bit values
#[derive(Copy, Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
pub enum SpecialBit {
    /// Constant 0
    #[serde(rename = "0")]
    _0,
    /// Constant 1
    #[serde(rename = "1")]
    _1,
    /// Constant X (invalid)
    #[serde(rename = "x")]
    X,
    /// Constant Z (tri-state)
    #[serde(rename = "z")]
    Z,
}

/// A number representing a single bit of a wire
#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
#[serde(untagged)]
pub enum BitVal {
    /// An actual signal number
    N(usize),
    /// A special constant value
    S(SpecialBit)
}

/// The value of an attribute/parameter
#[derive(Clone, Serialize, Deserialize, Debug, Eq, PartialEq, Hash)]
#[serde(untagged)]
pub enum AttributeVal {
    /// Numeric attribute value
    N(usize),
    /// String attribute value
    S(String),
}

/// Represents an entire .json file used by Yosys
#[derive(Serialize, Deserialize, Debug, Default)]
pub struct Netlist {
    /// The program that created this file.
    #[serde(default)]
    pub creator: String,
    /// A map from module names to module objects contained in this .json file
    #[serde(default)]
    pub modules: HashMap<String, Module>,
}

/// Represents one module in the Yosys hierarchy
#[derive(Serialize, Deserialize, Debug, Default)]
pub struct Module {
    /// Module attributes
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
    /// Module ports (interfaces to other modules)
    #[serde(default)]
    pub ports: HashMap<String, Port>,
    /// Module cells (objects inside this module)
    #[serde(default)]
    pub cells: HashMap<String, Cell>,
    /// Module netnames (names of wires in this module)
    #[serde(default)]
    pub netnames: HashMap<String, Netname>,
}

/// Represents a port on a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Port {
    /// Port direction
    pub direction: PortDirection,
    /// Bit value(s) representing the wire(s) connected to this port
    pub bits: Vec<BitVal>,
}

/// Represents a cell in a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Cell {
    /// Indicates an internal/auto-generated name that starts with `$`
    #[serde(default)]
    pub hide_name: usize,
    /// Name of the type of this cell
    #[serde(rename="type")]
    pub cell_type: String,
    /// Parameters specified on this cell
    #[serde(default)]
    pub parameters: HashMap<String, AttributeVal>,
    /// Attributes specified on this cell
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
    /// The direction of the ports on this cell
    #[serde(default)]
    pub port_directions: HashMap<String, PortDirection>,
    /// Bit value(s) representing the wire(s) connected to the inputs/outputs of this cell
    pub connections: HashMap<String, Vec<BitVal>>,
}

/// Represents the name of a net in a module
#[derive(Serialize, Deserialize, Debug)]
pub struct Netname {
    /// Indicates an internal/auto-generated name that starts with `$`
    #[serde(default)]
    pub hide_name: usize,
    /// Bit value(s) that should be given this name
    pub bits: Vec<BitVal>,
    /// Attributes for this netname
    #[serde(default)]
    pub attributes: HashMap<String, AttributeVal>,
}

impl Netlist {
    /// Read netlist data from a slice containing the bytes from a Yosys .json file
    pub fn from_slice(input: &[u8]) -> Result<Netlist, serde_json::Error> {
        serde_json::from_slice(input)
    }

    /// Serialize to a String
    pub fn to_string(&self) -> Result<String, serde_json::Error> {
        serde_json::to_string(self)
    }

    /// Serialize to a writer
    pub fn to_writer(&self, writer: &mut Write) -> Result<(), serde_json::Error> {
        serde_json::to_writer(writer, self)
    }
}

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

    #[test]
    fn super_empty_json() {
        let result = Netlist::from_slice(br#"
            {}"#).unwrap();
        assert_eq!(result.creator, "");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn empty_json() {
        let result = Netlist::from_slice(br#"
            {
              "creator": "this is a test",
              "modules": {
              }
            }"#).unwrap();
        assert_eq!(result.creator, "this is a test");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn empty_json_2() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
              }
            }"#).unwrap();
        assert_eq!(result.creator, "");
        assert_eq!(result.modules.len(), 0);
    }

    #[test]
    fn bit_values_test() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "connections": {
                        "IN": [ "x", 0, "z", 234, "1", "0" ]
                      }
                    }
                  }
                }
              }
            }"#).unwrap();
        assert_eq!(result.modules.get("mymodule").unwrap().cells.get("mycell").unwrap().connections.get("IN").unwrap(),
            &vec![BitVal::S(SpecialBit::X), BitVal::N(0), BitVal::S(SpecialBit::Z), BitVal::N(234),
                BitVal::S(SpecialBit::_1), BitVal::S(SpecialBit::_0)]);
    }

    #[test]
    #[should_panic]
    fn invalid_bit_value_test() {
        Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "connections": {
                        "IN": [ "w" ]
                      }
                    }
                  }
                }
              }
            }"#).unwrap();
    }

    #[test]
    fn attribute_value_test() {
        let result = Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "parameters": {
                        "testparam": 123
                      },
                      "connections": {}
                    }
                  }
                }
              }
            }"#).unwrap();
        assert_eq!(result.modules.get("mymodule").unwrap().cells.get("mycell").unwrap()
            .parameters.get("testparam").unwrap(), &AttributeVal::N(123));
    }

    #[test]
    #[should_panic]
    fn invalid_attribute_value_test() {
        Netlist::from_slice(br#"
            {
              "modules": {
                "mymodule": {
                  "cells": {
                    "mycell": {
                      "type": "celltype",
                      "parameters": {
                        "testparam": [123]
                      },
                      "connections": {}
                    }
                  }
                }
              }
            }"#).unwrap();
    }
}
<|endoftext|>


<commit_before>use std::fs::File;
use std::io::Read;
use std::path::Path;
use std::process::Command;

static PROGNAME: &'static str = "./sort";

#[test]
fn numeric1() {
    numeric_helper(1);
}

#[test]
fn numeric2() {
    numeric_helper(2);
}

#[test]
fn numeric3() {
    numeric_helper(3);
}

#[test]
fn numeric4() {
    numeric_helper(4);
}

#[test]
fn numeric5() {
    numeric_helper(5);
}

fn numeric_helper(test_num: isize) {
    let mut cmd = Command::new(PROGNAME);
    cmd.arg("-n");
    let po = match cmd.arg(format!("{}{}{}", "numeric", test_num, ".txt")).output() {
        Ok(p) => p,
        Err(err) => panic!("{}", err),
    };

    let filename = format!("{}{}{}", "numeric", test_num, ".ans");
    let mut f = File::open(Path::new(&filename)).unwrap_or_else(|err| {
        panic!("{}", err)
    });
    let mut answer = vec!();
    let _ = f.read_to_end(&mut answer);
    assert_eq!(String::from_utf8(po.stdout).unwrap(), String::from_utf8(answer).unwrap());
}
<commit_msg>Check return value of read().<commit_after>use std::fs::File;
use std::io::Read;
use std::path::Path;
use std::process::Command;

static PROGNAME: &'static str = "./sort";

#[test]
fn numeric1() {
    numeric_helper(1);
}

#[test]
fn numeric2() {
    numeric_helper(2);
}

#[test]
fn numeric3() {
    numeric_helper(3);
}

#[test]
fn numeric4() {
    numeric_helper(4);
}

#[test]
fn numeric5() {
    numeric_helper(5);
}

fn numeric_helper(test_num: isize) {
    let mut cmd = Command::new(PROGNAME);
    cmd.arg("-n");
    let po = match cmd.arg(format!("{}{}{}", "numeric", test_num, ".txt")).output() {
        Ok(p) => p,
        Err(err) => panic!("{}", err)
    };

    let filename = format!("{}{}{}", "numeric", test_num, ".ans");
    let mut f = File::open(Path::new(&filename)).unwrap_or_else(|err| {
        panic!("{}", err)
    });
    let mut answer = vec!();
    match f.read_to_end(&mut answer) {
        Ok(_) => {},
        Err(err) => panic!("{}", err)
    }
    assert_eq!(String::from_utf8(po.stdout).unwrap(), String::from_utf8(answer).unwrap());
}
<|endoftext|>


<commit_before>//! Helper functions to gather information for each of the non-function sections of a
//! WebAssembly module.
//!
//! The code of theses helper function is straightforward since it is only about reading metadata
//! about linear memories, tables, globals, etc. and storing them for later use.
//!
//! The special case of the initialize expressions for table elements offsets or global variables
//! is handled, according to the semantics of WebAssembly, to only specific expressions that are
//! interpreted on the fly.
use translation_utils::{type_to_type, Import, TableIndex, FunctionIndex, GlobalIndex,
                        SignatureIndex, MemoryIndex, Global, GlobalInit, Table, TableElementType,
                        Memory};
use cretonne::ir::{Signature, ArgumentType, CallConv};
use cretonne;
use wasmparser::{Parser, ParserState, FuncType, ImportSectionEntryType, ExternalKind, WasmDecoder,
                 MemoryType, Operator};
use wasmparser;
use std::collections::HashMap;
use std::str::from_utf8;
use runtime::WasmRuntime;

pub enum SectionParsingError {
    WrongSectionContent(String),
}

/// Reads the Type Section of the wasm module and returns the corresponding function signatures.
pub fn parse_function_signatures(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Signature>, SectionParsingError> {
    let mut signatures: Vec<Signature> = Vec::new();
    loop {
        match *parser.read() {
            ParserState::EndSection => break,
            ParserState::TypeSectionEntry(FuncType {
                                              form: wasmparser::Type::Func,
                                              ref params,
                                              ref returns,
                                          }) => {
                let mut sig = Signature::new(CallConv::Native);
                sig.argument_types.extend(params.iter().map(|ty| {
                    let cret_arg: cretonne::ir::Type = match type_to_type(ty) {
                        Ok(ty) => ty,
                        Err(()) => panic!("only numeric types are supported in\
                                      function signatures"),
                    };
                    ArgumentType::new(cret_arg)
                }));
                sig.return_types.extend(returns.iter().map(|ty| {
                    let cret_arg: cretonne::ir::Type = match type_to_type(ty) {
                        Ok(ty) => ty,
                        Err(()) => panic!("only numeric types are supported in\
                                  function signatures"),
                    };
                    ArgumentType::new(cret_arg)
                }));
                runtime.declare_signature(&sig);
                signatures.push(sig);
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
    }
    Ok(signatures)
}

/// Retrieves the imports from the imports section of the binary.
pub fn parse_import_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Import>, SectionParsingError> {
    let mut imports = Vec::new();
    loop {
        match *parser.read() {
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Function(sig),
                module,
                field,
            } => {
                runtime.declare_func_import(sig as SignatureIndex, module, field);
                imports.push(Import::Function { sig_index: sig });
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Memory(MemoryType { limits: ref memlimits }), ..
            } => {
                imports.push(Import::Memory(Memory {
                    pages_count: memlimits.initial as usize,
                    maximum: memlimits.maximum.map(|x| x as usize),
                }))
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Global(ref ty), ..
            } => {
                imports.push(Import::Global(Global {
                    ty: type_to_type(&ty.content_type).unwrap(),
                    mutability: ty.mutability != 0,
                    initializer: GlobalInit::Import(),
                }));
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Table(ref tab), ..
            } => {
                imports.push(Import::Table(Table {
                    ty: match type_to_type(&tab.element_type) {
                        Ok(t) => TableElementType::Val(t),
                        Err(()) => TableElementType::Func(),
                    },
                    size: tab.limits.initial as usize,
                    maximum: tab.limits.maximum.map(|x| x as usize),
                }));
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(imports)
}

/// Retrieves the correspondances between functions and signatures from the function section
pub fn parse_function_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<SignatureIndex>, SectionParsingError> {
    let mut funcs = Vec::new();
    loop {
        match *parser.read() {
            ParserState::FunctionSectionEntry(sigindex) => {
                runtime.declare_func_type(sigindex as SignatureIndex);
                funcs.push(sigindex as SignatureIndex);
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(funcs)
}

/// Retrieves the names of the functions from the export section
pub fn parse_export_section(
    parser: &mut Parser,
) -> Result<HashMap<FunctionIndex, String>, SectionParsingError> {
    let mut exports: HashMap<FunctionIndex, String> = HashMap::new();
    loop {
        match *parser.read() {
            ParserState::ExportSectionEntry {
                field,
                ref kind,
                index,
            } => {
                match *kind {
                    ExternalKind::Function => {
                        exports.insert(
                            index as FunctionIndex,
                            String::from(from_utf8(field).unwrap()),
                        );
                    }
                    _ => (),//TODO: deal with other kind of exports
                }
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(exports)
}

/// Retrieves the size and maximum fields of memories from the memory section
pub fn parse_memory_section(parser: &mut Parser) -> Result<Vec<Memory>, SectionParsingError> {
    let mut memories: Vec<Memory> = Vec::new();
    loop {
        match *parser.read() {
            ParserState::MemorySectionEntry(ref ty) => {
                memories.push(Memory {
                    pages_count: ty.limits.initial as usize,
                    maximum: ty.limits.maximum.map(|x| x as usize),
                })
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(memories)
}

/// Retrieves the size and maximum fields of memories from the memory section
pub fn parse_global_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Global>, SectionParsingError> {
    let mut globals = Vec::new();
    loop {
        let (content_type, mutability) = match *parser.read() {
            ParserState::BeginGlobalSectionEntry(ref ty) => (ty.content_type, ty.mutability),
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
        let initializer = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                GlobalInit::I32Const(value)
            }
            ParserState::InitExpressionOperator(Operator::I64Const { value }) => {
                GlobalInit::I64Const(value)
            }
            ParserState::InitExpressionOperator(Operator::F32Const { value }) => {
                GlobalInit::F32Const(value.bits())
            }
            ParserState::InitExpressionOperator(Operator::F64Const { value }) => {
                GlobalInit::F64Const(value.bits())
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                GlobalInit::GlobalRef(global_index as GlobalIndex)
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),

        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
        let global = Global {
            ty: type_to_type(&content_type).unwrap(),
            mutability: mutability != 0,
            initializer: initializer,
        };
        runtime.declare_global(global);
        globals.push(global);
        match *parser.read() {
            ParserState::EndGlobalSectionEntry => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
    }
    Ok(globals)
}

pub fn parse_data_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
    globals: &[Global],
) -> Result<(), SectionParsingError> {
    loop {
        let memory_index = match *parser.read() {
            ParserState::BeginDataSectionEntry(memory_index) => memory_index,
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        let mut offset = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                if value < 0 {
                    return Err(SectionParsingError::WrongSectionContent(String::from(
                        "negative \
                    offset value",
                    )));
                } else {
                    value as usize
                }
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                match globals[global_index as usize].initializer {
                    GlobalInit::I32Const(value) => {
                        if value < 0 {
                            return Err(SectionParsingError::WrongSectionContent(String::from(
                                "\
                            negative offset value",
                            )));
                        } else {
                            value as usize
                        }
                    }
                    GlobalInit::Import() => {
                        return Err(SectionParsingError::WrongSectionContent(String::from(
                            "\
                        imported globals not supported",
                        )))
                    } // TODO: add runtime support
                    _ => panic!("should not happen"),
                }
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginDataSectionEntryBody(_) => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        loop {
            let data = match *parser.read() {
                ParserState::DataSectionEntryBodyChunk(data) => data,
                ParserState::EndDataSectionEntry => break,
                ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
            };
            match runtime.declare_data_initialization(memory_index as MemoryIndex, offset, data) {
                Ok(()) => (),
                Err(s) => return Err(SectionParsingError::WrongSectionContent(s)),
            };
            offset += data.len();
        }
    }
    Ok(())
}

/// Retrieves the tables from the table section
pub fn parse_table_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<(), SectionParsingError> {
    loop {
        match *parser.read() {
            ParserState::TableSectionEntry(ref table) => {
                runtime.declare_table(Table {
                    ty: match type_to_type(&table.element_type) {
                        Ok(t) => TableElementType::Val(t),
                        Err(()) => TableElementType::Func(),
                    },
                    size: table.limits.initial as usize,
                    maximum: table.limits.maximum.map(|x| x as usize),
                })
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(())
}

/// Retrieves the tables from the table section
pub fn parse_elements_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
    globals: &[Global],
) -> Result<(), SectionParsingError> {
    loop {
        let table_index = match *parser.read() {
            ParserState::BeginElementSectionEntry(ref table_index) => *table_index as TableIndex,
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        let offset = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                if value < 0 {
                    return Err(SectionParsingError::WrongSectionContent(String::from(
                        "negative \
                    offset value",
                    )));
                } else {
                    value as usize
                }
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                match globals[global_index as usize].initializer {
                    GlobalInit::I32Const(value) => {
                        if value < 0 {
                            return Err(SectionParsingError::WrongSectionContent(String::from(
                                "\
                            negative offset value",
                            )));
                        } else {
                            value as usize
                        }
                    }
                    GlobalInit::Import() => 0, // TODO: add runtime support
                    _ => panic!("should not happen"),
                }
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::ElementSectionEntryBody(ref elements) => {
                let elems: Vec<FunctionIndex> =
                    elements.iter().map(|&x| x as FunctionIndex).collect();
                runtime.declare_table_elements(table_index, offset, &elems)
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndElementSectionEntry => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(())
}
<commit_msg>Fix a confusion between EndDataSectionEntry and EndDataSectionEntryBody.<commit_after>//! Helper functions to gather information for each of the non-function sections of a
//! WebAssembly module.
//!
//! The code of theses helper function is straightforward since it is only about reading metadata
//! about linear memories, tables, globals, etc. and storing them for later use.
//!
//! The special case of the initialize expressions for table elements offsets or global variables
//! is handled, according to the semantics of WebAssembly, to only specific expressions that are
//! interpreted on the fly.
use translation_utils::{type_to_type, Import, TableIndex, FunctionIndex, GlobalIndex,
                        SignatureIndex, MemoryIndex, Global, GlobalInit, Table, TableElementType,
                        Memory};
use cretonne::ir::{Signature, ArgumentType, CallConv};
use cretonne;
use wasmparser::{Parser, ParserState, FuncType, ImportSectionEntryType, ExternalKind, WasmDecoder,
                 MemoryType, Operator};
use wasmparser;
use std::collections::HashMap;
use std::str::from_utf8;
use runtime::WasmRuntime;

pub enum SectionParsingError {
    WrongSectionContent(String),
}

/// Reads the Type Section of the wasm module and returns the corresponding function signatures.
pub fn parse_function_signatures(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Signature>, SectionParsingError> {
    let mut signatures: Vec<Signature> = Vec::new();
    loop {
        match *parser.read() {
            ParserState::EndSection => break,
            ParserState::TypeSectionEntry(FuncType {
                                              form: wasmparser::Type::Func,
                                              ref params,
                                              ref returns,
                                          }) => {
                let mut sig = Signature::new(CallConv::Native);
                sig.argument_types.extend(params.iter().map(|ty| {
                    let cret_arg: cretonne::ir::Type = match type_to_type(ty) {
                        Ok(ty) => ty,
                        Err(()) => panic!("only numeric types are supported in\
                                      function signatures"),
                    };
                    ArgumentType::new(cret_arg)
                }));
                sig.return_types.extend(returns.iter().map(|ty| {
                    let cret_arg: cretonne::ir::Type = match type_to_type(ty) {
                        Ok(ty) => ty,
                        Err(()) => panic!("only numeric types are supported in\
                                  function signatures"),
                    };
                    ArgumentType::new(cret_arg)
                }));
                runtime.declare_signature(&sig);
                signatures.push(sig);
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
    }
    Ok(signatures)
}

/// Retrieves the imports from the imports section of the binary.
pub fn parse_import_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Import>, SectionParsingError> {
    let mut imports = Vec::new();
    loop {
        match *parser.read() {
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Function(sig),
                module,
                field,
            } => {
                runtime.declare_func_import(sig as SignatureIndex, module, field);
                imports.push(Import::Function { sig_index: sig });
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Memory(MemoryType { limits: ref memlimits }), ..
            } => {
                imports.push(Import::Memory(Memory {
                    pages_count: memlimits.initial as usize,
                    maximum: memlimits.maximum.map(|x| x as usize),
                }))
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Global(ref ty), ..
            } => {
                imports.push(Import::Global(Global {
                    ty: type_to_type(&ty.content_type).unwrap(),
                    mutability: ty.mutability != 0,
                    initializer: GlobalInit::Import(),
                }));
            }
            ParserState::ImportSectionEntry {
                ty: ImportSectionEntryType::Table(ref tab), ..
            } => {
                imports.push(Import::Table(Table {
                    ty: match type_to_type(&tab.element_type) {
                        Ok(t) => TableElementType::Val(t),
                        Err(()) => TableElementType::Func(),
                    },
                    size: tab.limits.initial as usize,
                    maximum: tab.limits.maximum.map(|x| x as usize),
                }));
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(imports)
}

/// Retrieves the correspondances between functions and signatures from the function section
pub fn parse_function_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<SignatureIndex>, SectionParsingError> {
    let mut funcs = Vec::new();
    loop {
        match *parser.read() {
            ParserState::FunctionSectionEntry(sigindex) => {
                runtime.declare_func_type(sigindex as SignatureIndex);
                funcs.push(sigindex as SignatureIndex);
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(funcs)
}

/// Retrieves the names of the functions from the export section
pub fn parse_export_section(
    parser: &mut Parser,
) -> Result<HashMap<FunctionIndex, String>, SectionParsingError> {
    let mut exports: HashMap<FunctionIndex, String> = HashMap::new();
    loop {
        match *parser.read() {
            ParserState::ExportSectionEntry {
                field,
                ref kind,
                index,
            } => {
                match *kind {
                    ExternalKind::Function => {
                        exports.insert(
                            index as FunctionIndex,
                            String::from(from_utf8(field).unwrap()),
                        );
                    }
                    _ => (),//TODO: deal with other kind of exports
                }
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(exports)
}

/// Retrieves the size and maximum fields of memories from the memory section
pub fn parse_memory_section(parser: &mut Parser) -> Result<Vec<Memory>, SectionParsingError> {
    let mut memories: Vec<Memory> = Vec::new();
    loop {
        match *parser.read() {
            ParserState::MemorySectionEntry(ref ty) => {
                memories.push(Memory {
                    pages_count: ty.limits.initial as usize,
                    maximum: ty.limits.maximum.map(|x| x as usize),
                })
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(memories)
}

/// Retrieves the size and maximum fields of memories from the memory section
pub fn parse_global_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<Vec<Global>, SectionParsingError> {
    let mut globals = Vec::new();
    loop {
        let (content_type, mutability) = match *parser.read() {
            ParserState::BeginGlobalSectionEntry(ref ty) => (ty.content_type, ty.mutability),
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
        let initializer = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                GlobalInit::I32Const(value)
            }
            ParserState::InitExpressionOperator(Operator::I64Const { value }) => {
                GlobalInit::I64Const(value)
            }
            ParserState::InitExpressionOperator(Operator::F32Const { value }) => {
                GlobalInit::F32Const(value.bits())
            }
            ParserState::InitExpressionOperator(Operator::F64Const { value }) => {
                GlobalInit::F64Const(value.bits())
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                GlobalInit::GlobalRef(global_index as GlobalIndex)
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),

        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
        let global = Global {
            ty: type_to_type(&content_type).unwrap(),
            mutability: mutability != 0,
            initializer: initializer,
        };
        runtime.declare_global(global);
        globals.push(global);
        match *parser.read() {
            ParserState::EndGlobalSectionEntry => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        }
    }
    Ok(globals)
}

pub fn parse_data_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
    globals: &[Global],
) -> Result<(), SectionParsingError> {
    loop {
        let memory_index = match *parser.read() {
            ParserState::BeginDataSectionEntry(memory_index) => memory_index,
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        let mut offset = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                if value < 0 {
                    return Err(SectionParsingError::WrongSectionContent(String::from(
                        "negative \
                    offset value",
                    )));
                } else {
                    value as usize
                }
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                match globals[global_index as usize].initializer {
                    GlobalInit::I32Const(value) => {
                        if value < 0 {
                            return Err(SectionParsingError::WrongSectionContent(String::from(
                                "\
                            negative offset value",
                            )));
                        } else {
                            value as usize
                        }
                    }
                    GlobalInit::Import() => {
                        return Err(SectionParsingError::WrongSectionContent(String::from(
                            "\
                        imported globals not supported",
                        )))
                    } // TODO: add runtime support
                    _ => panic!("should not happen"),
                }
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginDataSectionEntryBody(_) => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        loop {
            let data = match *parser.read() {
                ParserState::DataSectionEntryBodyChunk(data) => data,
                ParserState::EndDataSectionEntryBody => break,
                ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
            };
            match runtime.declare_data_initialization(memory_index as MemoryIndex, offset, data) {
                Ok(()) => (),
                Err(s) => return Err(SectionParsingError::WrongSectionContent(s)),
            };
            offset += data.len();
        }
        match *parser.read() {
            ParserState::EndDataSectionEntry => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(())
}

/// Retrieves the tables from the table section
pub fn parse_table_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
) -> Result<(), SectionParsingError> {
    loop {
        match *parser.read() {
            ParserState::TableSectionEntry(ref table) => {
                runtime.declare_table(Table {
                    ty: match type_to_type(&table.element_type) {
                        Ok(t) => TableElementType::Val(t),
                        Err(()) => TableElementType::Func(),
                    },
                    size: table.limits.initial as usize,
                    maximum: table.limits.maximum.map(|x| x as usize),
                })
            }
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(())
}

/// Retrieves the tables from the table section
pub fn parse_elements_section(
    parser: &mut Parser,
    runtime: &mut WasmRuntime,
    globals: &[Global],
) -> Result<(), SectionParsingError> {
    loop {
        let table_index = match *parser.read() {
            ParserState::BeginElementSectionEntry(ref table_index) => *table_index as TableIndex,
            ParserState::EndSection => break,
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::BeginInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        let offset = match *parser.read() {
            ParserState::InitExpressionOperator(Operator::I32Const { value }) => {
                if value < 0 {
                    return Err(SectionParsingError::WrongSectionContent(String::from(
                        "negative \
                    offset value",
                    )));
                } else {
                    value as usize
                }
            }
            ParserState::InitExpressionOperator(Operator::GetGlobal { global_index }) => {
                match globals[global_index as usize].initializer {
                    GlobalInit::I32Const(value) => {
                        if value < 0 {
                            return Err(SectionParsingError::WrongSectionContent(String::from(
                                "\
                            negative offset value",
                            )));
                        } else {
                            value as usize
                        }
                    }
                    GlobalInit::Import() => 0, // TODO: add runtime support
                    _ => panic!("should not happen"),
                }
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndInitExpressionBody => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::ElementSectionEntryBody(ref elements) => {
                let elems: Vec<FunctionIndex> =
                    elements.iter().map(|&x| x as FunctionIndex).collect();
                runtime.declare_table_elements(table_index, offset, &elems)
            }
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
        match *parser.read() {
            ParserState::EndElementSectionEntry => (),
            ref s => return Err(SectionParsingError::WrongSectionContent(format!("{:?}", s))),
        };
    }
    Ok(())
}
<|endoftext|>


<commit_before>extern crate clap;

use std::env;
use std::ffi::OsStr;

use clap::{App, Arg};

#[test]
fn env() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn env_os() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env_os(OsStr::new("CLP_TEST_ENV")))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn no_env() {
    // All the other tests use the presence of the Environment variable...
    // we need another variable just in case one of the others is running at the same time...
    env::remove_var("CLP_TEST_ENV_NONE");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV_NONE"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(!m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg"), None);
}

#[test]
fn with_default() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .default_value("default"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn opt_user_override() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("--arg [FILE] 'some arg'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec!["", "--arg", "opt"]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 1);
    assert_eq!(m.value_of("arg").unwrap(), "opt");
}

#[test]
fn positionals() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn positionals_user_override() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec!["", "opt"]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 1);
    assert_eq!(m.value_of("arg").unwrap(), "opt");
}

#[test]
fn multiple_one() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .use_delimiter(true)
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.values_of("arg").unwrap().collect::<Vec<_>>(), vec!["env"]);
}

#[test]
fn multiple_three() {
    env::set_var("CLP_TEST_ENV_MULTI1", "env1,env2,env3");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV_MULTI1")
                .use_delimiter(true)
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(
        m.values_of("arg").unwrap().collect::<Vec<_>>(),
        vec!["env1", "env2", "env3"]
    );
}

#[test]
fn multiple_no_delimiter() {
    env::set_var("CLP_TEST_ENV_MULTI2", "env1 env2 env3");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV_MULTI2")
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(
        m.values_of("arg").unwrap().collect::<Vec<_>>(),
        vec!["env1 env2 env3"]
    );
}

#[test]
fn possible_value() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .possible_value("env"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn not_possible_value() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .possible_value("never"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_err());
}

#[test]
fn validator() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .validator(|s| {
                    if s == "env" {
                        Ok(())
                    } else {
                        Err("not equal".to_string())
                    }
                }),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn validator_invalid() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .validator(|s| {
                    if s != "env" {
                        Ok(())
                    } else {
                        Err("is equal".to_string())
                    }
                }),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_err());
}
<commit_msg>test validator with custom return type<commit_after>extern crate clap;

use std::env;
use std::ffi::OsStr;

use clap::{App, Arg};

#[test]
fn env() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn env_os() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env_os(OsStr::new("CLP_TEST_ENV")))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn no_env() {
    // All the other tests use the presence of the Environment variable...
    // we need another variable just in case one of the others is running at the same time...
    env::remove_var("CLP_TEST_ENV_NONE");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV_NONE"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(!m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg"), None);
}

#[test]
fn with_default() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .default_value("default"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn opt_user_override() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("--arg [FILE] 'some arg'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec!["", "--arg", "opt"]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 1);
    assert_eq!(m.value_of("arg").unwrap(), "opt");
}

#[test]
fn positionals() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn positionals_user_override() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(Arg::from_usage("[arg] 'some opt'").env("CLP_TEST_ENV"))
        .get_matches_from_safe(vec!["", "opt"]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 1);
    assert_eq!(m.value_of("arg").unwrap(), "opt");
}

#[test]
fn multiple_one() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .use_delimiter(true)
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.values_of("arg").unwrap().collect::<Vec<_>>(), vec!["env"]);
}

#[test]
fn multiple_three() {
    env::set_var("CLP_TEST_ENV_MULTI1", "env1,env2,env3");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV_MULTI1")
                .use_delimiter(true)
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(
        m.values_of("arg").unwrap().collect::<Vec<_>>(),
        vec!["env1", "env2", "env3"]
    );
}

#[test]
fn multiple_no_delimiter() {
    env::set_var("CLP_TEST_ENV_MULTI2", "env1 env2 env3");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV_MULTI2")
                .multiple(true),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(
        m.values_of("arg").unwrap().collect::<Vec<_>>(),
        vec!["env1 env2 env3"]
    );
}

#[test]
fn possible_value() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .possible_value("env"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn not_possible_value() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .possible_value("never"),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_err());
}

#[test]
fn validator() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .validator(|s| {
                    if s == "env" {
                        Ok(())
                    } else {
                        Err("not equal".to_string())
                    }
                }),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_ok());
    let m = r.unwrap();
    assert!(m.is_present("arg"));
    assert_eq!(m.occurrences_of("arg"), 0);
    assert_eq!(m.value_of("arg").unwrap(), "env");
}

#[test]
fn validator_output() {
    env::set_var("CLP_TEST_ENV", "42");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .validator(|s| s.parse::<i32>())
        )
        .get_matches_from_safe(vec![""]);

    assert_eq!(r.unwrap().value_of("arg").unwrap().parse(), Ok(42));
}

#[test]
fn validator_invalid() {
    env::set_var("CLP_TEST_ENV", "env");

    let r = App::new("df")
        .arg(
            Arg::from_usage("[arg] 'some opt'")
                .env("CLP_TEST_ENV")
                .validator(|s| {
                    if s != "env" {
                        Ok(())
                    } else {
                        Err("is equal".to_string())
                    }
                }),
        )
        .get_matches_from_safe(vec![""]);

    assert!(r.is_err());
}
<|endoftext|>


<commit_before>#![feature(test)]
extern crate test;
extern crate warc_parser;
mod tests{
    use std::error::Error;
    use std::fs::File;
    use std::io::prelude::*;
    use std::path::Path;

    fn read_sample_file(sample_name: &str) -> Vec<u8> {
        let full_path = "sample/".to_string()+sample_name;
        let mut f = File::open(full_path).unwrap();
        let mut s = Vec::new();
        f.read_to_end(&mut s).unwrap();
        s
    }
    use warc_parser;
    #[test]
    fn it_parses_a_plethora(){
        let examples = read_sample_file("plethora.warc");
        let parsed = warc_parser::records(&examples);
        println!("{:?}",parsed);
        assert!(parsed.is_done());
    }

    #[test]
    fn it_parses_single(){
        let bbc = read_sample_file("bbc.warc");
        let parsed = warc_parser::record(&bbc);
        assert!(parsed.is_done());
    }
}
<commit_msg>Fix warnings<commit_after>#![feature(test)]
extern crate test;
extern crate warc_parser;
mod tests{
    use std::fs::File;
    use std::io::prelude::*;

    fn read_sample_file(sample_name: &str) -> Vec<u8> {
        let full_path = "sample/".to_string()+sample_name;
        let mut f = File::open(full_path).unwrap();
        let mut s = Vec::new();
        f.read_to_end(&mut s).unwrap();
        s
    }
    use warc_parser;
    #[test]
    fn it_parses_a_plethora(){
        let examples = read_sample_file("plethora.warc");
        let parsed = warc_parser::records(&examples);
        println!("{:?}",parsed);
        assert!(parsed.is_done());
    }

    #[test]
    fn it_parses_single(){
        let bbc = read_sample_file("bbc.warc");
        let parsed = warc_parser::record(&bbc);
        assert!(parsed.is_done());
    }
}
<|endoftext|>


<commit_before>extern crate sorting;

use std::fmt::Debug;

/// Verify order of input vector as sorted by indices.
///
/// # Details
///
/// This function takes as arguments a vector of data and a vector representing the indices of the
/// first vector making it sorted.
///
/// The elements of the sorted vector are compared to the next ones to make sure they are less
/// or equal.
///
/// # Panics
///
/// The sorting of the data vector is enforced using `assert!()`.
///
/// # Examples
///
/// ```
/// let data: Vec<i32> = vec![4, 2, 3, 1];
/// let sorted_indices: Vec<usize> = vec![3, 1, 2, 0];
/// verify_sorting(&data, &sorted_indices);
/// ```
///
fn verify_sorting<T: Debug + PartialOrd>(array: &Vec<T>, sorted_indices: &Vec<usize>) {
    let n = array.len();
    assert_eq!(n , sorted_indices.len());

    for i in 0..n-1 {
        println!("array[sorted_indices[i={:?}]]={:?}   array[sorted_indices[i+1={:?}]]={:?}",
            i, array[sorted_indices[i]], i+1, array[sorted_indices[i+1]]);
        assert!(array[sorted_indices[i]] <= array[sorted_indices[i+1]]);
    }
}

#[test]
fn simple_insertion_multiple_sizes_f64() {
    let to_sort: Vec<f64> = vec![6.0,   5.0,  3.0,  1.0,  2.4, 4.0, 10.0, 7.0,
                                 3.42, 32.2, 44.2, 56.3, 67.9, 3.2, 44.2, 2.0];

    let sorted_indices = sorting::simplesorts::insertion::sort(&to_sort);

    verify_sorting(&to_sort, &sorted_indices);
}
<commit_msg>New test; Empty vectors<commit_after>extern crate sorting;

use std::fmt::Debug;

/// Verify order of input vector as sorted by indices.
///
/// # Details
///
/// This function takes as arguments a vector of data and a vector representing the indices of the
/// first vector making it sorted.
///
/// The elements of the sorted vector are compared to the next ones to make sure they are less
/// or equal.
///
/// # Panics
///
/// The sorting of the data vector is enforced using `assert!()`.
///
/// # Examples
///
/// ```
/// let data: Vec<i32> = vec![4, 2, 3, 1];
/// let sorted_indices: Vec<usize> = vec![3, 1, 2, 0];
/// verify_sorting(&data, &sorted_indices);
/// ```
///
fn verify_sorting<T: Debug + PartialOrd>(array: &Vec<T>, sorted_indices: &Vec<usize>) {
    let n = array.len();
    assert_eq!(n , sorted_indices.len());

    if !array.is_empty() {
        for i in 0..n-1 {
            println!("array[sorted_indices[i={:?}]]={:?}   array[sorted_indices[i+1={:?}]]={:?}",
                i, array[sorted_indices[i]], i+1, array[sorted_indices[i+1]]);
            assert!(array[sorted_indices[i]] <= array[sorted_indices[i+1]]);
        }
    }
}

#[test]
fn simple_insertion_empty() {
    let to_sort: Vec<i32> = vec![];

    let sorted_indices = sorting::simplesorts::insertion::sort(&to_sort);

    assert_eq!(sorted_indices, vec![]);
    verify_sorting(&to_sort, &sorted_indices);
}

#[test]
fn simple_insertion_multiple_sizes_f64() {
    let to_sort: Vec<f64> = vec![6.0,   5.0,  3.0,  1.0,  2.4, 4.0, 10.0, 7.0,
                                 3.42, 32.2, 44.2, 56.3, 67.9, 3.2, 44.2, 2.0];

    let sorted_indices = sorting::simplesorts::insertion::sort(&to_sort);

    verify_sorting(&to_sort, &sorted_indices);
}
<|endoftext|>


<commit_before>/// extern test-lib for zwreec
/// to test the whole zwreec library
/// for the future: real twee and z-code test-data

extern crate zwreec;

#[test]
fn file_test() {
    assert_eq!("hello from file", zwreec::utils::file::temp_hello());
}

#[test]
fn frontend_test() {
}

#[test]
fn backend_test() {
    assert_eq!("hello from backend", zwreec::backend::temp_hello());
}
<commit_msg>Removed useless Test(lines)<commit_after>/// extern test-lib for zwreec
/// to test the whole zwreec library
/// for the future: real twee and z-code test-data

extern crate zwreec;

//TODO!

#[test]
fn frontend_test() {
}

#[test]
fn backend_test() {
}
<|endoftext|>


<commit_before>extern crate human_name;
extern crate unicode_normalization;

use std::io::prelude::*;
use std::io::BufReader;
use std::fs::File;
use std::hash::{Hash,Hasher,SipHasher};
use unicode_normalization::UnicodeNormalization;

fn none_if_empty(s: &str) -> Option<&str> {
    if s.is_empty() {
        None
    } else {
        Some(s)
    }
}

fn stderr_newline() {
    writeln!(&mut std::io::stderr(), "").ok().unwrap();
}

fn hash<T: Hash>(t: &T) -> u64 {
    let mut s = SipHasher::new();
    t.hash(&mut s);
    s.finish()
}

#[test]
fn parsing() {
    let f = File::open("tests/parseable-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line: String = line.ok().unwrap().nfkd().collect();

        if line.starts_with("#") || !line.contains("|") {
            continue;
        }

        let parts: Vec<&str> = line.split("|").collect();
        let input = parts[0];
        let surname = parts[1];
        let given_name = parts[2];
        let middle_names = parts[3];
        let first_initial = parts[4].chars().nth(0).unwrap();
        let middle_initials = parts[5];
        let suffix = parts[6];

        let name = human_name::Name::parse(input);
        assert!(!name.is_none(), "[{}] Could not parse!", input);

        let given_name = none_if_empty(&given_name);
        let middle_names = none_if_empty(&middle_names);
        let middle_initials = none_if_empty(&middle_initials);
        let suffix = none_if_empty(&suffix);

        let name = name.unwrap();
        assert!(name.surname() == surname,
                "[{}] Expected surname {}, got {}",
                input,
                surname,
                name.surname());
        assert!(name.first_initial() == first_initial,
                "[{}] Expected first initial {}, got {}",
                input,
                first_initial,
                name.first_initial());
        assert!(name.given_name() == given_name,
                "[{}] Expected given_name {:?}, got {:?}",
                input,
                given_name,
                name.given_name());
        assert!(name.middle_name().map(|w|w.to_string()) == middle_names.map(|w|w.to_string()),
                "[{}] Expected middle names {:?}, got {:?}",
                input,
                middle_names,
                name.middle_name());
        assert!(name.middle_initials() == middle_initials,
                "[{}] Expected middle initials {:?}, got {:?}",
                input,
                middle_initials,
                name.middle_initials());
        assert!(name.suffix() == suffix,
                "[{}] Expected suffix {:?}, got {:?}",
                input,
                suffix,
                name.suffix());

        writeln!(&mut std::io::stderr(),
                 "Parsed '{}' as '{}', {:?} {:?} ({:?}), {:?}",
                 input,
                 surname,
                 given_name,
                 middle_names,
                 middle_initials,
                 suffix)
            .ok()
            .unwrap();
    }

    stderr_newline();
}

#[test]
fn unparseable() {
    let f = File::open("tests/unparseable-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line = line.ok().unwrap();

        if line.starts_with("#") {
            continue;
        }

        let result = human_name::Name::parse(&line);
        assert!(result.is_none(),
                "'Parsed' junk name: '{}' as '{}'",
                line,
                result.unwrap().display_short());

        writeln!(&mut std::io::stderr(), "Correctly discarded '{}'", line).ok().unwrap();
    }

    stderr_newline();
}

#[test]
fn equality() {
    let f = File::open("tests/equal-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line = line.ok().unwrap();

        if line.starts_with("#") {
            continue;
        }

        let parts: Vec<&str> = line.split('|').collect();
        let a = parts[0];
        let b = parts[1];
        let expect = parts[2];

        let parsed_a = human_name::Name::parse(&a);
        let parsed_b = human_name::Name::parse(&b);

        if expect == "==" {
            assert!(parsed_a == parsed_b,
                    "{} should be equal to {} but was not!",
                    a,
                    b);
            assert!(parsed_b == parsed_a,
                    "{} should be equal to {} but was not!",
                    b,
                    a);
            assert!(hash(&parsed_a) == hash(&parsed_b),
                    "{} should have the same hash as {} but did not!",
                    a,
                    b);
        } else {
            assert!(parsed_a != parsed_b,
                    "{} should not be equal to {} but was!",
                    a,
                    b);
            assert!(parsed_b != parsed_a,
                    "{} should not be equal to {} but was!",
                    b,
                    a);
        }

        writeln!(&mut std::io::stderr(), "{} {} {}", a, expect, b).ok().unwrap();
    }

    stderr_newline();
}
<commit_msg>rustfmt tests/lib<commit_after>extern crate human_name;
extern crate unicode_normalization;

use std::io::prelude::*;
use std::io::BufReader;
use std::fs::File;
use std::hash::{Hash, Hasher, SipHasher};
use unicode_normalization::UnicodeNormalization;

fn none_if_empty(s: &str) -> Option<&str> {
    if s.is_empty() {
        None
    } else {
        Some(s)
    }
}

fn stderr_newline() {
    writeln!(&mut std::io::stderr(), "").ok().unwrap();
}

fn hash<T: Hash>(t: &T) -> u64 {
    let mut s = SipHasher::new();
    t.hash(&mut s);
    s.finish()
}

#[test]
fn parsing() {
    let f = File::open("tests/parseable-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line: String = line.ok().unwrap().nfkd().collect();

        if line.starts_with("#") || !line.contains("|") {
            continue;
        }

        let parts: Vec<&str> = line.split("|").collect();
        let input = parts[0];
        let surname = parts[1];
        let given_name = parts[2];
        let middle_names = parts[3];
        let first_initial = parts[4].chars().nth(0).unwrap();
        let middle_initials = parts[5];
        let suffix = parts[6];

        let name = human_name::Name::parse(input);
        assert!(!name.is_none(), "[{}] Could not parse!", input);

        let given_name = none_if_empty(&given_name);
        let middle_names = none_if_empty(&middle_names);
        let middle_initials = none_if_empty(&middle_initials);
        let suffix = none_if_empty(&suffix);

        let name = name.unwrap();
        assert!(name.surname() == surname,
                "[{}] Expected surname {}, got {}",
                input,
                surname,
                name.surname());
        assert!(name.first_initial() == first_initial,
                "[{}] Expected first initial {}, got {}",
                input,
                first_initial,
                name.first_initial());
        assert!(name.given_name() == given_name,
                "[{}] Expected given_name {:?}, got {:?}",
                input,
                given_name,
                name.given_name());
        assert!(name.middle_name().map(|w| w.to_string()) == middle_names.map(|w| w.to_string()),
                "[{}] Expected middle names {:?}, got {:?}",
                input,
                middle_names,
                name.middle_name());
        assert!(name.middle_initials() == middle_initials,
                "[{}] Expected middle initials {:?}, got {:?}",
                input,
                middle_initials,
                name.middle_initials());
        assert!(name.suffix() == suffix,
                "[{}] Expected suffix {:?}, got {:?}",
                input,
                suffix,
                name.suffix());

        writeln!(&mut std::io::stderr(),
                 "Parsed '{}' as '{}', {:?} {:?} ({:?}), {:?}",
                 input,
                 surname,
                 given_name,
                 middle_names,
                 middle_initials,
                 suffix)
            .ok()
            .unwrap();
    }

    stderr_newline();
}

#[test]
fn unparseable() {
    let f = File::open("tests/unparseable-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line = line.ok().unwrap();

        if line.starts_with("#") {
            continue;
        }

        let result = human_name::Name::parse(&line);
        assert!(result.is_none(),
                "'Parsed' junk name: '{}' as '{}'",
                line,
                result.unwrap().display_short());

        writeln!(&mut std::io::stderr(), "Correctly discarded '{}'", line).ok().unwrap();
    }

    stderr_newline();
}

#[test]
fn equality() {
    let f = File::open("tests/equal-names.txt").ok().unwrap();
    let reader = BufReader::new(f);

    stderr_newline();

    for line in reader.lines() {
        let line = line.ok().unwrap();

        if line.starts_with("#") {
            continue;
        }

        let parts: Vec<&str> = line.split('|').collect();
        let a = parts[0];
        let b = parts[1];
        let expect = parts[2];

        let parsed_a = human_name::Name::parse(&a);
        let parsed_b = human_name::Name::parse(&b);

        if expect == "==" {
            assert!(parsed_a == parsed_b,
                    "{} should be equal to {} but was not!",
                    a,
                    b);
            assert!(parsed_b == parsed_a,
                    "{} should be equal to {} but was not!",
                    b,
                    a);
            assert!(hash(&parsed_a) == hash(&parsed_b),
                    "{} should have the same hash as {} but did not!",
                    a,
                    b);
        } else {
            assert!(parsed_a != parsed_b,
                    "{} should not be equal to {} but was!",
                    a,
                    b);
            assert!(parsed_b != parsed_a,
                    "{} should not be equal to {} but was!",
                    b,
                    a);
        }

        writeln!(&mut std::io::stderr(), "{} {} {}", a, expect, b).ok().unwrap();
    }

    stderr_newline();
}
<|endoftext|>