<commit_before>use routing;
use rpc;

use hash::Hash;
use bincode::serde;
use std::{net, io, thread, time};
use std::sync::{ Weak, Arc};

pub const SOCKET_BUFFER_SIZE_BYTES : usize = 65536;
pub const SOCKET_TIMEOUT_S         : u64   = 5;

/// Subotai node.
///
/// On construction, a detached thread for packet reception is
/// launched.
 pub struct Node {
   pub id     : Hash,
   table      : routing::Table,
   outbound   : net::UdpSocket,
   inbound    : net::UdpSocket,
}

impl Node {
   pub fn new(inbound_port: u16, outbound_port: u16) -> io::Result<Arc<Node>> {
      let id = Hash::random();

      let node = Arc::new(Node {
         id         : id.clone(),
         table      : routing::Table::new(id),
         inbound    : try!(net::UdpSocket::bind(("0.0.0.0", inbound_port))),
         outbound   : try!(net::UdpSocket::bind(("0.0.0.0", outbound_port))),
      });

      try!(node.inbound.set_read_timeout(Some(time::Duration::new(SOCKET_TIMEOUT_S,0))));

      let reception_node = Arc::downgrade(&node);
      thread::spawn(move || { Node::reception_loop(reception_node) });

      Ok(node)
   }

   /// Sends an RPC to a destination node. If the node address is known, the RPC will
   /// be sent directly. Otherwise, a node lookup will be performed first.
   pub fn send_rpc(&self, rpc: &rpc::Rpc, destination: &routing::NodeInfo)-> io::Result<()> {
      if let Some(address) = destination.address {
         let payload = rpc.serialize();
         try!(self.outbound.send_to(&payload, address));
      }
      else {
         // Perform lookup.
         unimplemented!();
      }
      Ok(())
   }

   /// Receives and processes data as long as the table is alive. Will gracefully exit, at most,
   /// `SOCKET_TIMEOUT_S` seconds after the table is dropped.
   fn reception_loop(node: Weak<Node>) {
      let mut buffer = [0u8; SOCKET_BUFFER_SIZE_BYTES];

      while let Some(node) = node.upgrade() {
         if let Ok((_, source)) = node.inbound.recv_from(&mut buffer) {
            node.table.process_incoming_rpc(&buffer, source);
         }
      }
   }
}

impl routing::Table {
   fn process_incoming_rpc(&self, buffer: &[u8], mut source: net::SocketAddr) -> serde::DeserializeResult<()> {
      let rpc = try!(rpc::Rpc::deserialize(buffer));

      source.set_port(rpc.reply_port);
      let sender_node = routing::NodeInfo {
         node_id : rpc.sender_id,
         address : Some(source),
      };

      match rpc.kind {
         rpc::Kind::Ping => self.insert_node(sender_node),
         _ => (),
      }
      Ok(())
   }
}

#[cfg(test)]
mod tests {
   use node;
   use rpc;
   use std::thread;
   use std::time;
   use routing;
   use std::net;
   use std::str::FromStr;
   pub const POLL_FREQUENCY_MS: u64 = 50;
   pub const TRIES: u8 = 5;

   #[test]
   fn node_ping() {
      let alpha = node::Node::new(50000, 50001).unwrap();
      let beta  = node::Node::new(50002, 50003).unwrap();

      let ip = net::IpAddr::from_str("127.0.0.1").unwrap();
      let address_beta = net::SocketAddr::new(ip, 50002);

      let info_beta = routing::NodeInfo {
         node_id : beta.id.clone(),
         address : Some(address_beta),
      };
      let ping = rpc::Rpc::ping(alpha.id.clone(), 50000);

      // Before sending the ping, beta does not know about alpha.
      assert!(beta.table.specific_node(&alpha.id).is_none());

      // Alpha pings beta.
      alpha.send_rpc(&ping, &info_beta);

      // Eventually, beta knows of alpha.
      let mut found = beta.table.specific_node(&alpha.id);
      for _ in 0..TRIES {
         if found.is_some() {
            break;
         }
         found = beta.table.specific_node(&alpha.id);
         thread::sleep(time::Duration::from_millis(POLL_FREQUENCY_MS));
      }

      assert!(found.is_some());
   }
}
<commit_msg>Chain of weak pointers<commit_after>use routing;
use rpc;

use hash::Hash;
use bincode::serde;
use std::{net, io, thread, time};
use std::sync::{ Weak, Arc};

pub const SOCKET_BUFFER_SIZE_BYTES : usize = 65536;
pub const SOCKET_TIMEOUT_S         : u64   = 5;

/// Subotai node.
///
/// On construction, a detached thread for packet reception is
/// launched.
 pub struct Node {
   pub id     : Hash,
   table      : routing::Table,
   outbound   : net::UdpSocket,
   inbound    : net::UdpSocket,
}

impl Node {
   pub fn new(inbound_port: u16, outbound_port: u16) -> io::Result<Arc<Node>> {
      let id = Hash::random();

      let node = Arc::new(Node {
         id         : id.clone(),
         table      : routing::Table::new(id),
         inbound    : try!(net::UdpSocket::bind(("0.0.0.0", inbound_port))),
         outbound   : try!(net::UdpSocket::bind(("0.0.0.0", outbound_port))),
      });

      try!(node.inbound.set_read_timeout(Some(time::Duration::new(SOCKET_TIMEOUT_S,0))));

      let reception_node = Arc::downgrade(&node);
      thread::spawn(move || { Node::reception_loop(reception_node) });

      Ok(node)
   }

   /// Sends an RPC to a destination node. If the node address is known, the RPC will
   /// be sent directly. Otherwise, a node lookup will be performed first.
   pub fn send_rpc(&self, rpc: &rpc::Rpc, destination: &routing::NodeInfo)-> io::Result<()> {
      if let Some(address) = destination.address {
         let payload = rpc.serialize();
         try!(self.outbound.send_to(&payload, address));
      }
      else {
         // Perform lookup.
         unimplemented!();
      }
      Ok(())
   }

   /// Receives and processes data as long as the table is alive. Will gracefully exit, at most,
   /// `SOCKET_TIMEOUT_S` seconds after the table is dropped.
   fn reception_loop(weak: Weak<Node>) {
      let mut buffer = [0u8; SOCKET_BUFFER_SIZE_BYTES];

      while let Some(strong) = weak.upgrade() {
         if let Ok((_, source)) = strong.inbound.recv_from(&mut buffer) {
            Node::process_incoming_rpc(weak.clone(), &buffer, source);
         }
      }
   }

   fn process_incoming_rpc(weak: Weak<Node>, buffer: &[u8], mut source: net::SocketAddr) -> serde::DeserializeResult<()> {
      let rpc = try!(rpc::Rpc::deserialize(buffer));

      source.set_port(rpc.reply_port);
      let sender = routing::NodeInfo {
         node_id : rpc.sender_id.clone(),
         address : Some(source),
      };

      if let Some(strong) = weak.upgrade() {
         match rpc.kind {
            rpc::Kind::Ping => Node::handle_ping(weak, rpc, sender),
            _ => (),
         }
      }
      Ok(())
   }

   fn handle_ping(weak: Weak<Node>, ping: rpc::Rpc, sender: routing::NodeInfo){
      if let Some(strong) = weak.upgrade() {
         strong.table.insert_node(sender);
         // TODO send ping response
      }
   }
}

#[cfg(test)]
mod tests {
   use node;
   use rpc;
   use std::thread;
   use std::time;
   use routing;
   use std::net;
   use std::str::FromStr;
   pub const POLL_FREQUENCY_MS: u64 = 50;
   pub const TRIES: u8 = 5;

   #[test]
   fn node_ping() {
      let alpha = node::Node::new(50000, 50001).unwrap();
      let beta  = node::Node::new(50002, 50003).unwrap();

      let ip = net::IpAddr::from_str("127.0.0.1").unwrap();
      let address_beta = net::SocketAddr::new(ip, 50002);

      let info_beta = routing::NodeInfo {
         node_id : beta.id.clone(),
         address : Some(address_beta),
      };
      let ping = rpc::Rpc::ping(alpha.id.clone(), 50000);

      // Before sending the ping, beta does not know about alpha.
      assert!(beta.table.specific_node(&alpha.id).is_none());

      // Alpha pings beta.
      alpha.send_rpc(&ping, &info_beta);

      // Eventually, beta knows of alpha.
      let mut found = beta.table.specific_node(&alpha.id);
      for _ in 0..TRIES {
         if found.is_some() {
            break;
         }
         found = beta.table.specific_node(&alpha.id);
         thread::sleep(time::Duration::from_millis(POLL_FREQUENCY_MS));
      }

      assert!(found.is_some());
   }
}
<|endoftext|>


<commit_before>#![feature(phase)]
#![feature(globs)]
#![crate_name = "cube"]

extern crate gfx;
extern crate piston;
// extern crate glfw_game_window;
extern crate sdl2_game_window;
#[phase(plugin)]
extern crate gfx_macros;
extern crate native;
extern crate time;

// use glfw_game_window::WindowGLFW;
use sdl2_game_window::WindowSDL2;
use gfx::{Device, DeviceHelper};
use piston::{cam, Window};
//----------------------------------------
// Cube associated data

#[vertex_format]
struct Vertex {
    #[as_float]
    a_pos: [i8, ..3],
    #[as_float]
    a_tex_coord: [u8, ..2],
}

impl Vertex {
    fn new(pos: [i8, ..3], tc: [u8, ..2]) -> Vertex {
        Vertex {
            a_pos: pos,
            a_tex_coord: tc,
        }
    }
}

#[shader_param(CubeBatch)]
struct Params {
    u_model_view_proj: [[f32, ..4], ..4],
    t_color: gfx::shade::TextureParam,
}

static VERTEX_SRC: gfx::ShaderSource = shaders! {
GLSL_120: b"
    #version 120
    attribute vec3 a_pos;
    attribute vec2 a_tex_coord;
    varying vec2 v_TexCoord;
    uniform mat4 u_model_view_proj;
    void main() {
        v_TexCoord = a_tex_coord;
        gl_Position = u_model_view_proj * vec4(a_pos, 1.0);
    }
"
GLSL_150: b"
    #version 150 core
    in vec3 a_pos;
    in vec2 a_tex_coord;
    out vec2 v_TexCoord;
    uniform mat4 u_model_view_proj;
    void main() {
        v_TexCoord = a_tex_coord;
        gl_Position = u_model_view_proj * vec4(a_pos, 1.0);
    }
"
};

static FRAGMENT_SRC: gfx::ShaderSource = shaders! {
GLSL_120: b"
    #version 120
    varying vec2 v_TexCoord;
    uniform sampler2D t_color;
    void main() {
        vec4 tex = texture2D(t_color, v_TexCoord);
        float blend = dot(v_TexCoord-vec2(0.5,0.5), v_TexCoord-vec2(0.5,0.5));
        gl_FragColor = mix(tex, vec4(0.0,0.0,0.0,0.0), blend*1.0);
    }
"
GLSL_150: b"
    #version 150 core
    in vec2 v_TexCoord;
    out vec4 o_Color;
    uniform sampler2D t_color;
    void main() {
        vec4 tex = texture(t_color, v_TexCoord);
        float blend = dot(v_TexCoord-vec2(0.5,0.5), v_TexCoord-vec2(0.5,0.5));
        o_Color = mix(tex, vec4(0.0,0.0,0.0,0.0), blend*1.0);
    }
"
};

//----------------------------------------

// We need to run on the main thread, so ensure we are using the `native` runtime. This is
// technically not needed, since this is the default, but it's not guaranteed.
#[start]
fn start(argc: int, argv: *const *const u8) -> int {
     native::start(argc, argv, main)
}

fn main() {
    let (win_width, win_height) = (640, 480);
    let mut window = WindowSDL2::new(
        piston::shader_version::opengl::OpenGL_3_2,
        piston::WindowSettings {
            title: "cube".to_string(),
            size: [win_width, win_height],
            fullscreen: false,
            exit_on_esc: true,
            samples: 4,
        }
    );

    window.capture_cursor(true);

    let (mut device, frame) = window.gfx();
    let state = gfx::DrawState::new().depth(gfx::state::LessEqual, true);

    let vertex_data = vec![
        //top (0, 0, 1)
        Vertex::new([-1, -1,  1], [0, 0]),
        Vertex::new([ 1, -1,  1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([-1,  1,  1], [0, 1]),
        //bottom (0, 0, -1)
        Vertex::new([ 1,  1, -1], [0, 0]),
        Vertex::new([-1,  1, -1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([ 1, -1, -1], [0, 1]),
        //right (1, 0, 0)
        Vertex::new([ 1, -1, -1], [0, 0]),
        Vertex::new([ 1,  1, -1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([ 1, -1,  1], [0, 1]),
        //left (-1, 0, 0)
        Vertex::new([-1,  1,  1], [0, 0]),
        Vertex::new([-1, -1,  1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([-1,  1, -1], [0, 1]),
        //front (0, 1, 0)
        Vertex::new([-1,  1, -1], [0, 0]),
        Vertex::new([ 1,  1, -1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([-1,  1,  1], [0, 1]),
        //back (0, -1, 0)
        Vertex::new([ 1, -1,  1], [0, 0]),
        Vertex::new([-1, -1,  1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([ 1, -1, -1], [0, 1]),
    ];

    let mesh = device.create_mesh(vertex_data);

    let slice = {
        let index_data = vec![
            0u8, 1, 2, 2, 3, 0,    //top
            4, 5, 6, 6, 7, 4,       //bottom
            8, 9, 10, 10, 11, 8,    //right
            12, 13, 14, 14, 16, 12, //left
            16, 17, 18, 18, 19, 16, //front
            20, 21, 22, 22, 23, 20, //back
        ];

        let buf = device.create_buffer_static(&index_data);
        gfx::IndexSlice8(gfx::TriangleList, buf, 0, 36)
    };

    let tinfo = gfx::tex::TextureInfo {
        width: 1,
        height: 1,
        depth: 1,
        levels: 1,
        kind: gfx::tex::Texture2D,
        format: gfx::tex::RGBA8,
    };
    let img_info = tinfo.to_image_info();
    let texture = device.create_texture(tinfo).unwrap();
    device.update_texture(
            &texture,
            &img_info,
            &vec![0x20u8, 0xA0u8, 0xC0u8, 0x00u8].as_slice()
        ).unwrap();

    let sampler = device.create_sampler(
        gfx::tex::SamplerInfo::new(
            gfx::tex::Bilinear,
            gfx::tex::Clamp
        )
    );

    let program = device.link_program(
            VERTEX_SRC.clone(),
            FRAGMENT_SRC.clone()
        ).unwrap();

    let mut graphics = gfx::Graphics::new(device);
    let batch: CubeBatch = graphics.make_batch(&program, &mesh, slice, &state).unwrap();

    let mut data = Params {
        u_model_view_proj: piston::vecmath::mat4_id(),
        t_color: (texture, Some(sampler)),
    };

    let model = piston::vecmath::mat4_id();
    let projection = cam::CameraPerspective {
            fov: 90.0f32,
            near_clip: 0.1,
            far_clip: 1000.0,
            aspect_ratio: (win_width as f32) / (win_height as f32)
        }.projection();
    let mut first_person = cam::FirstPerson::new(
        [0.5f32, 0.5, 4.0],
        cam::FirstPersonSettings::keyboard_wasd()
    );

    let mut game_iter = piston::EventIterator::new(
        &mut window,
        &piston::EventSettings {
            updates_per_second: 120,
            max_frames_per_second: 60
        }
    );

    for e in game_iter {
        match e {
            piston::Render(args) => {
                graphics.clear(
                    gfx::ClearData {
                        color: [0.3, 0.3, 0.3, 1.0],
                        depth: 1.0,
                        stencil: 0,
                    },
                    gfx::Color | gfx::Depth,
                    &frame
                );
                data.u_model_view_proj = cam::model_view_projection(
                        model,
                        first_person.camera(args.ext_dt).orthogonal(),
                        projection
                    );
                graphics.draw(&batch, &data, &frame);
                graphics.end_frame();
            },
            piston::Update(args) => first_person.update(args.dt),
            piston::Input(e) => first_person.input(&e),
        }
    }
}

<commit_msg>Update now that sdl2_game_window doesn't depend on gfx<commit_after>#![feature(phase)]
#![feature(globs)]
#![crate_name = "cube"]

extern crate gfx;
extern crate piston;
// extern crate glfw_game_window;
extern crate sdl2;
extern crate sdl2_game_window;
#[phase(plugin)]
extern crate gfx_macros;
extern crate native;
extern crate time;

// use glfw_game_window::WindowGLFW;
use sdl2_game_window::WindowSDL2;
use gfx::{Device, DeviceHelper};
use piston::{cam, Window};
//----------------------------------------
// Cube associated data

#[vertex_format]
struct Vertex {
    #[as_float]
    a_pos: [i8, ..3],
    #[as_float]
    a_tex_coord: [u8, ..2],
}

impl Vertex {
    fn new(pos: [i8, ..3], tc: [u8, ..2]) -> Vertex {
        Vertex {
            a_pos: pos,
            a_tex_coord: tc,
        }
    }
}

#[shader_param(CubeBatch)]
struct Params {
    u_model_view_proj: [[f32, ..4], ..4],
    t_color: gfx::shade::TextureParam,
}

static VERTEX_SRC: gfx::ShaderSource = shaders! {
GLSL_120: b"
    #version 120
    attribute vec3 a_pos;
    attribute vec2 a_tex_coord;
    varying vec2 v_TexCoord;
    uniform mat4 u_model_view_proj;
    void main() {
        v_TexCoord = a_tex_coord;
        gl_Position = u_model_view_proj * vec4(a_pos, 1.0);
    }
"
GLSL_150: b"
    #version 150 core
    in vec3 a_pos;
    in vec2 a_tex_coord;
    out vec2 v_TexCoord;
    uniform mat4 u_model_view_proj;
    void main() {
        v_TexCoord = a_tex_coord;
        gl_Position = u_model_view_proj * vec4(a_pos, 1.0);
    }
"
};

static FRAGMENT_SRC: gfx::ShaderSource = shaders! {
GLSL_120: b"
    #version 120
    varying vec2 v_TexCoord;
    uniform sampler2D t_color;
    void main() {
        vec4 tex = texture2D(t_color, v_TexCoord);
        float blend = dot(v_TexCoord-vec2(0.5,0.5), v_TexCoord-vec2(0.5,0.5));
        gl_FragColor = mix(tex, vec4(0.0,0.0,0.0,0.0), blend*1.0);
    }
"
GLSL_150: b"
    #version 150 core
    in vec2 v_TexCoord;
    out vec4 o_Color;
    uniform sampler2D t_color;
    void main() {
        vec4 tex = texture(t_color, v_TexCoord);
        float blend = dot(v_TexCoord-vec2(0.5,0.5), v_TexCoord-vec2(0.5,0.5));
        o_Color = mix(tex, vec4(0.0,0.0,0.0,0.0), blend*1.0);
    }
"
};

//----------------------------------------

// We need to run on the main thread, so ensure we are using the `native` runtime. This is
// technically not needed, since this is the default, but it's not guaranteed.
#[start]
fn start(argc: int, argv: *const *const u8) -> int {
     native::start(argc, argv, main)
}

fn main() {
    let (win_width, win_height) = (640, 480);
    let mut window = WindowSDL2::new(
        piston::shader_version::opengl::OpenGL_3_2,
        piston::WindowSettings {
            title: "cube".to_string(),
            size: [win_width, win_height],
            fullscreen: false,
            exit_on_esc: true,
            samples: 4,
        }
    );

    window.capture_cursor(true);

    let mut device = gfx::GlDevice::new(|s| unsafe {
        std::mem::transmute(sdl2::video::gl_get_proc_address(s))
    });
    let frame = gfx::Frame::new(win_width as u16, win_height as u16);
    //let (mut device, frame) = window.gfx();
    let state = gfx::DrawState::new().depth(gfx::state::LessEqual, true);

    let vertex_data = vec![
        //top (0, 0, 1)
        Vertex::new([-1, -1,  1], [0, 0]),
        Vertex::new([ 1, -1,  1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([-1,  1,  1], [0, 1]),
        //bottom (0, 0, -1)
        Vertex::new([ 1,  1, -1], [0, 0]),
        Vertex::new([-1,  1, -1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([ 1, -1, -1], [0, 1]),
        //right (1, 0, 0)
        Vertex::new([ 1, -1, -1], [0, 0]),
        Vertex::new([ 1,  1, -1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([ 1, -1,  1], [0, 1]),
        //left (-1, 0, 0)
        Vertex::new([-1,  1,  1], [0, 0]),
        Vertex::new([-1, -1,  1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([-1,  1, -1], [0, 1]),
        //front (0, 1, 0)
        Vertex::new([-1,  1, -1], [0, 0]),
        Vertex::new([ 1,  1, -1], [1, 0]),
        Vertex::new([ 1,  1,  1], [1, 1]),
        Vertex::new([-1,  1,  1], [0, 1]),
        //back (0, -1, 0)
        Vertex::new([ 1, -1,  1], [0, 0]),
        Vertex::new([-1, -1,  1], [1, 0]),
        Vertex::new([-1, -1, -1], [1, 1]),
        Vertex::new([ 1, -1, -1], [0, 1]),
    ];

    let mesh = device.create_mesh(vertex_data.as_slice());

    let slice = {
        let index_data = vec![
            0u8, 1, 2, 2, 3, 0,    //top
            4, 5, 6, 6, 7, 4,       //bottom
            8, 9, 10, 10, 11, 8,    //right
            12, 13, 14, 14, 16, 12, //left
            16, 17, 18, 18, 19, 16, //front
            20, 21, 22, 22, 23, 20, //back
        ];

        let buf = device.create_buffer_static(index_data.as_slice());
        gfx::IndexSlice8(gfx::TriangleList, buf, 0, 36)
    };

    let tinfo = gfx::tex::TextureInfo {
        width: 1,
        height: 1,
        depth: 1,
        levels: 1,
        kind: gfx::tex::Texture2D,
        format: gfx::tex::RGBA8,
    };
    let img_info = tinfo.to_image_info();
    let texture = device.create_texture(tinfo).unwrap();
    device.update_texture(
            &texture,
            &img_info,
            vec![0x20u8, 0xA0u8, 0xC0u8, 0x00u8].as_slice()
        ).unwrap();

    let sampler = device.create_sampler(
        gfx::tex::SamplerInfo::new(
            gfx::tex::Bilinear,
            gfx::tex::Clamp
        )
    );

    let program = device.link_program(
            VERTEX_SRC.clone(),
            FRAGMENT_SRC.clone()
        ).unwrap();

    let mut graphics = gfx::Graphics::new(device);
    let batch: CubeBatch = graphics.make_batch(&program, &mesh, slice, &state).unwrap();

    let mut data = Params {
        u_model_view_proj: piston::vecmath::mat4_id(),
        t_color: (texture, Some(sampler)),
    };

    let model = piston::vecmath::mat4_id();
    let projection = cam::CameraPerspective {
            fov: 90.0f32,
            near_clip: 0.1,
            far_clip: 1000.0,
            aspect_ratio: (win_width as f32) / (win_height as f32)
        }.projection();
    let mut first_person = cam::FirstPerson::new(
        [0.5f32, 0.5, 4.0],
        cam::FirstPersonSettings::keyboard_wasd()
    );

    let mut game_iter = piston::EventIterator::new(
        &mut window,
        &piston::EventSettings {
            updates_per_second: 120,
            max_frames_per_second: 60
        }
    );

    for e in game_iter {
        match e {
            piston::Render(args) => {
                graphics.clear(
                    gfx::ClearData {
                        color: [0.3, 0.3, 0.3, 1.0],
                        depth: 1.0,
                        stencil: 0,
                    },
                    gfx::Color | gfx::Depth,
                    &frame
                );
                data.u_model_view_proj = cam::model_view_projection(
                        model,
                        first_person.camera(args.ext_dt).orthogonal(),
                        projection
                    );
                graphics.draw(&batch, &data, &frame);
                graphics.end_frame();
            },
            piston::Update(args) => first_person.update(args.dt),
            piston::Input(e) => first_person.input(&e),
        }
    }
}

<|endoftext|>


<commit_before>#![no_std]
#![no_main]
#![feature(custom_test_frameworks)]
#![test_runner(daedalos::test_runner)]
#![reexport_test_harness_main = "test_main"]

use daedalos::{println, serial_print, serial_println};

#[no_mangle]
pub extern "C" fn _start() -> ! {
    test_main();

    loop {}
}

#[panic_handler]
fn panic(info: &core::panic::PanicInfo) -> ! {
    daedalos::test_panic_handler(info)
}

#[test_case]
fn test_println() {
    serial_print!("test_println... ");
    println!("test_println output");
    serial_println!("[ok]");
}
<commit_msg>tests/basic_boot: organize<commit_after>#![feature(custom_test_frameworks)]
#![no_main]
#![no_std]
#![reexport_test_harness_main = "test_main"]
#![test_runner(daedalos::test_runner)]

use daedalos::{println, serial_print, serial_println};

#[panic_handler]
fn panic(info: &core::panic::PanicInfo) -> ! {
    daedalos::test_panic_handler(info)
}

#[no_mangle]
pub extern "C" fn _start() -> ! {
    test_main();

    loop {}
}

#[test_case]
fn test_println() {
    serial_print!("test_println... ");
    println!("test_println output");
    serial_println!("[ok]");
}
<|endoftext|>


<commit_before>include!("header.rs");

macro_rules! impl_test {
    ($modname:ident, $random:path) => {
mod $modname {
    use ndarray::prelude::*;
    use ndarray_linalg::prelude::*;
    use ndarray_rand::RandomExt;
    use rand_extra::*;
    #[test]
    fn solve_upper() {
        let r_dist = RealNormal::new(0.0, 1.0);
        let a = drop_lower($random((3, 3), r_dist));
        println!("a = \n{:?}", &a);
        let b = $random(3, r_dist);
        println!("b = \n{:?}", &b);
        let x = a.solve_upper(b.clone()).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }

    #[test]
    fn solve_upper_t() {
        let r_dist = RealNormal::new(0., 1.);
        let a = drop_lower($random((3, 3), r_dist).reversed_axes());
        println!("a = \n{:?}", &a);
        let b = $random(3, r_dist);
        println!("b = \n{:?}", &b);
        let x = a.solve_upper(b.clone()).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }

    #[test]
    fn solve_lower() {
        let r_dist = RealNormal::new(0., 1.);
        let a = drop_upper($random((3, 3), r_dist));
        println!("a = \n{:?}", &a);
        let b = $random(3, r_dist);
        println!("b = \n{:?}", &b);
        let x = a.solve_lower(b.clone()).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }

    #[test]
    fn solve_lower_t() {
        let r_dist = RealNormal::new(0., 1.);
        let a = drop_upper($random((3, 3), r_dist).reversed_axes());
        println!("a = \n{:?}", &a);
        let b = $random(3, r_dist);
        println!("b = \n{:?}", &b);
        let x = a.solve_lower(b.clone()).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }
}
}} // impl_test_opnorm

impl_test!(owned, Array<f64, _>::random);
impl_test!(shared, RcArray<f64, _>::random);

macro_rules! impl_test_2d {
    ($modname:ident, $drop:path, $solve:ident) => {
mod $modname {
    use super::random_owned;
    use ndarray_linalg::prelude::*;
    #[test]
    fn solve_tt() {
        let a = $drop(random_owned(3, 3, true));
        println!("a = \n{:?}", &a);
        let b = random_owned(3, 2, true);
        println!("b = \n{:?}", &b);
        let x = a.$solve(&b).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }
    #[test]
    fn solve_tf() {
        let a = $drop(random_owned(3, 3, true));
        println!("a = \n{:?}", &a);
        let b = random_owned(3, 2, false);
        println!("b = \n{:?}", &b);
        let x = a.$solve(&b).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }
    #[test]
    fn solve_ft() {
        let a = $drop(random_owned(3, 3, false));
        println!("a = \n{:?}", &a);
        let b = random_owned(3, 2, true);
        println!("b = \n{:?}", &b);
        let x = a.$solve(&b).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }
    #[test]
    fn solve_ff() {
        let a = $drop(random_owned(3, 3, false));
        println!("a = \n{:?}", &a);
        let b = random_owned(3, 2, false);
        println!("b = \n{:?}", &b);
        let x = a.$solve(&b).unwrap();
        println!("x = \n{:?}", &x);
        println!("Ax = \n{:?}", a.dot(&x));
        assert_close_l2!(&a.dot(&x), &b, 1e-7);
    }
}
}} // impl_test_2d

impl_test_2d!(lower2d, drop_upper, solve_lower);
impl_test_2d!(upper2d, drop_lower, solve_upper);
<commit_msg>Remove old test<commit_after>
extern crate ndarray;
#[macro_use]
extern crate ndarray_linalg;

use ndarray::*;
use ndarray_linalg::prelude::*;

fn test1d<A, Sa, Sb, Tol>(uplo: UPLO, a: ArrayBase<Sa, Ix2>, b: ArrayBase<Sb, Ix1>, tol: Tol)
    where A: Field + Absolute<Output = Tol>,
          Sa: Data<Elem = A>,
          Sb: DataMut<Elem = A> + DataClone,
          Tol: RealField
{
    println!("a = {:?}", &a);
    println!("b = {:?}", &b);
    let ans = b.clone();
    let x = a.solve_triangular(uplo, Diag::NonUnit, b).unwrap();
    let b_ = a.dot(&x);
    assert_close_l2!(&b_, &ans, tol);
}
<|endoftext|>


<commit_before>#![allow(non_upper_case_globals)]

use crate::gen_ir::*;
use crate::*;

lazy_static! {
    static ref USED: Mutex<Vec<bool>> = Mutex::new(Vec::new());
    static ref REG_MAP: Mutex<Vec<i32>> = Mutex::new(Vec::new());
}

pub const regs: [&'static str; 8] = ["rbp", "r10", "r11", "rbx", "r12", "r13", "r14", "r15"];
pub const regs8: [&'static str; 8] = ["rbl", "r10b", "r11b", "bl", "r12b", "r13b", "r14b", "r15b"];

// Code generator

fn alloc(ir_reg: i32) -> i32 {
    let mut reg_map = REG_MAP.lock().unwrap();
    if reg_map[ir_reg as usize] != -1 {
        let r = reg_map[ir_reg as usize];
        assert!(USED.lock().unwrap()[r as usize], "");
        return r;
    }

    let mut used = USED.lock().unwrap();
    for i in 0..regs.len() {
        if used[i] {
            continue;
        }
        reg_map[ir_reg as usize] = i as i32;
        used[i] = true;
        return i as i32;
    }
    panic!("register exhausted");
}

fn kill(i: i32) {
    let mut used = USED.lock().unwrap();
    let r = i as usize;
    assert!(used[r]);
    used[r] = false;
}

fn visit(irv: &mut Vec<IR>) {
    // r0 is a reserved register that is always mapped to rbp.

    match (REG_MAP.lock(), USED.lock()) {
        (Ok(mut reg_map), Ok(mut used)) => {
            reg_map[0] = 0;
            used[0] = true;
        }
        _ => {
            panic!();
        }
    }

    let irinfo = IRINFO.lock().unwrap();
    for i in 0..irv.len() {
        let mut ir = &mut irv[i];

        match irinfo.get(&ir.op).unwrap().ty {
            IRInfoType::REG | IRInfoType::REG_IMM | IRInfoType::REG_LABEL => {
                ir.lhs = alloc(ir.lhs);
            }
            IRInfoType::REG_REG => {
                ir.lhs = alloc(ir.lhs);
                ir.rhs = alloc(ir.rhs);
            }
            IRInfoType::CALL => {
                ir.lhs = alloc(ir.lhs);
                for i in 0..ir.nargs {
                    ir.args[i] = alloc(ir.args[i]);
                }
            }
            _ => {}
        }

        if ir.op == IRType::KILL {
            kill(ir.lhs);
            ir.op = IRType::NOP;
        }
    }
}

pub fn alloc_regs(fns: &mut Vec<IR>) {

    for i in 0..fns.len() {
        let mut fun = &mut fns[i];
        match (REG_MAP.lock(), USED.lock()) {
            (Ok(mut reg_map), Ok(mut used)) => {
                *reg_map = Vec::new();
                for _i in 0..fun.ir.len() {
                    reg_map.push(-1);
                }

                *used = Vec::new();
                for _i in 0..regs.len() {
                    used.push(false);
                }
            }
            _ => {
                panic!();
            }
        }

        visit(&mut fun.ir);
    }
}
<commit_msg>Inline a small function.<commit_after>#![allow(non_upper_case_globals)]

use crate::gen_ir::*;
use crate::*;

lazy_static! {
    static ref USED: Mutex<Vec<bool>> = Mutex::new(Vec::new());
    static ref REG_MAP: Mutex<Vec<i32>> = Mutex::new(Vec::new());
}

pub const regs: [&'static str; 8] = ["rbp", "r10", "r11", "rbx", "r12", "r13", "r14", "r15"];
pub const regs8: [&'static str; 8] = ["rbl", "r10b", "r11b", "bl", "r12b", "r13b", "r14b", "r15b"];

// Code generator

fn alloc(ir_reg: i32) -> i32 {
    let mut reg_map = REG_MAP.lock().unwrap();
    if reg_map[ir_reg as usize] != -1 {
        let r = reg_map[ir_reg as usize];
        assert!(USED.lock().unwrap()[r as usize], "");
        return r;
    }

    let mut used = USED.lock().unwrap();
    for i in 0..regs.len() {
        if used[i] {
            continue;
        }
        reg_map[ir_reg as usize] = i as i32;
        used[i] = true;
        return i as i32;
    }
    panic!("register exhausted");
}

fn visit(irv: &mut Vec<IR>) {
    // r0 is a reserved register that is always mapped to rbp.

    match (REG_MAP.lock(), USED.lock()) {
        (Ok(mut reg_map), Ok(mut used)) => {
            reg_map[0] = 0;
            used[0] = true;
        }
        _ => {
            panic!();
        }
    }

    let irinfo = IRINFO.lock().unwrap();
    for i in 0..irv.len() {
        let mut ir = &mut irv[i];

        match irinfo.get(&ir.op).unwrap().ty {
            IRInfoType::REG | IRInfoType::REG_IMM | IRInfoType::REG_LABEL => {
                ir.lhs = alloc(ir.lhs);
            }
            IRInfoType::REG_REG => {
                ir.lhs = alloc(ir.lhs);
                ir.rhs = alloc(ir.rhs);
            }
            IRInfoType::CALL => {
                ir.lhs = alloc(ir.lhs);
                for i in 0..ir.nargs {
                    ir.args[i] = alloc(ir.args[i]);
                }
            }
            _ => {}
        }

        if ir.op == IRType::KILL {
            let mut used = USED.lock().unwrap();
            assert!(used[ir.lhs as usize]);
            used[ir.lhs as usize] = false;
            ir.op = IRType::NOP;
        }
    }
}

pub fn alloc_regs(fns: &mut Vec<IR>) {

    for i in 0..fns.len() {
        let mut fun = &mut fns[i];
        match (REG_MAP.lock(), USED.lock()) {
            (Ok(mut reg_map), Ok(mut used)) => {
                *reg_map = Vec::new();
                for _i in 0..fun.ir.len() {
                    reg_map.push(-1);
                }

                *used = Vec::new();
                for _i in 0..regs.len() {
                    used.push(false);
                }
            }
            _ => {
                panic!();
            }
        }

        visit(&mut fun.ir);
    }
}
<|endoftext|>


<commit_before>use rustc_serialize::json::{self, Json, ToJson};

use common::{Nullable, Date};
use cookie;
use time;

#[derive(Debug)]
pub enum WebDriverResponse {
    CloseWindow(CloseWindowResponse),
    Cookie(CookieResponse),
    DeleteSession,
    ElementRect(ElementRectResponse),
    Generic(ValueResponse),
    NewSession(NewSessionResponse),
    Timeouts(TimeoutsResponse),
    Void,
    WindowPosition(WindowPositionResponse),
    WindowSize(WindowSizeResponse),
}

impl WebDriverResponse {
    pub fn to_json_string(self) -> String {
        let obj = match self {
            WebDriverResponse::CloseWindow(ref x) => json::encode(&x.to_json()),
            WebDriverResponse::Cookie(ref x) => json::encode(x),
            WebDriverResponse::DeleteSession => Ok("{}".to_string()),
            WebDriverResponse::ElementRect(ref x) => json::encode(x),
            WebDriverResponse::Generic(ref x) => json::encode(x),
            WebDriverResponse::NewSession(ref x) => json::encode(x),
            WebDriverResponse::Timeouts(ref x) => json::encode(x),
            WebDriverResponse::Void => Ok("{}".to_string()),
            WebDriverResponse::WindowPosition(ref x) => json::encode(x),
            WebDriverResponse::WindowSize(ref x) => json::encode(x),
        }.unwrap();

        match self {
            WebDriverResponse::Generic(_) |
            WebDriverResponse::Cookie(_) => obj,
            _ => {
                let mut data = String::with_capacity(11 + obj.len());
                data.push_str("{\"value\": ");
                data.push_str(&*obj);
                data.push_str("}");
                data
            }
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct CloseWindowResponse {
    pub window_handles: Vec<String>,
}

impl CloseWindowResponse {
    pub fn new(handles: Vec<String>) -> CloseWindowResponse {
        CloseWindowResponse { window_handles: handles }
    }
}

impl ToJson for CloseWindowResponse {
    fn to_json(&self) -> Json {
        Json::Array(self.window_handles
                    .iter()
                    .map(|x| Json::String(x.clone()))
                    .collect::<Vec<Json>>())
    }
}

#[derive(RustcEncodable, Debug)]
pub struct NewSessionResponse {
    pub sessionId: String,
    pub capabilities: json::Json
}

impl NewSessionResponse {
    pub fn new(session_id: String, capabilities: json::Json) -> NewSessionResponse {
        NewSessionResponse {
            capabilities: capabilities,
            sessionId: session_id
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct TimeoutsResponse {
    pub script: u64,
    pub pageLoad: u64,
    pub implicit: u64,
}

impl TimeoutsResponse {
    pub fn new(script: u64, page_load: u64, implicit: u64) -> TimeoutsResponse {
        TimeoutsResponse {
            script: script,
            pageLoad: page_load,
            implicit: implicit,
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct ValueResponse {
    pub value: json::Json
}

impl ValueResponse {
    pub fn new(value: json::Json) -> ValueResponse {
        ValueResponse {
            value: value
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct WindowSizeResponse {
    pub width: u64,
    pub height: u64
}

impl WindowSizeResponse {
    pub fn new(width: u64, height: u64) -> WindowSizeResponse {
        WindowSizeResponse {
            width: width,
            height: height
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct WindowPositionResponse {
    pub x: i64,
    pub y: i64,
}

impl WindowPositionResponse {
    pub fn new(x: i64, y: i64) -> WindowPositionResponse {
        WindowPositionResponse { x: x, y: y }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct ElementRectResponse {
    pub x: f64,
    pub y: f64,
    pub width: f64,
    pub height: f64
}

impl ElementRectResponse {
    pub fn new(x: f64, y: f64, width: f64, height: f64) -> ElementRectResponse {
        ElementRectResponse {
            x: x,
            y: y,
            width: width,
            height: height
        }
    }
}

//TODO: some of these fields are probably supposed to be optional
#[derive(RustcEncodable, PartialEq, Debug, Clone)]
pub struct Cookie {
    pub name: String,
    pub value: String,
    pub path: Nullable<String>,
    pub domain: Nullable<String>,
    pub expiry: Nullable<Date>,
    pub secure: bool,
    pub httpOnly: bool
}

impl Cookie {
    pub fn new(name: String, value: String, path: Nullable<String>, domain: Nullable<String>,
               expiry: Nullable<Date>, secure: bool, http_only: bool) -> Cookie {
        Cookie {
            name: name,
            value: value,
            path: path,
            domain: domain,
            expiry: expiry,
            secure: secure,
            httpOnly: http_only
        }
    }
}

impl Into<cookie::Cookie<'static>> for Cookie {
    fn into(self) -> cookie::Cookie<'static> {
        let cookie = cookie::Cookie::build(self.name, self.value)
            .secure(self.secure)
            .http_only(self.httpOnly);
        let cookie = match self.domain {
            Nullable::Value(domain) => cookie.domain(domain),
            Nullable::Null => cookie,
        };
        let cookie = match self.path {
            Nullable::Value(path) => cookie.path(path),
            Nullable::Null => cookie,
        };
        let cookie = match self.expiry {
            Nullable::Value(Date(expiry)) => {
                cookie.expires(time::at(time::Timespec::new(expiry as i64, 0)))
            },
            Nullable::Null => cookie,
        };
        cookie.finish()
    }
}

#[derive(RustcEncodable, Debug)]
pub struct CookieResponse {
    pub value: Vec<Cookie>
}

impl CookieResponse {
    pub fn new(value: Vec<Cookie>) -> CookieResponse {
        CookieResponse {
            value: value
        }
    }
}

#[cfg(test)]
mod tests {
    use std::collections::BTreeMap;
    use rustc_serialize::json::Json;
    use super::{WebDriverResponse,
                CloseWindowResponse,
                CookieResponse,
                ElementRectResponse,
                NewSessionResponse,
                ValueResponse,
                TimeoutsResponse,
                WindowPositionResponse,
                WindowSizeResponse,
                Cookie,
                Nullable};

    fn test(resp: WebDriverResponse, expected_str: &str) {
        let data = resp.to_json_string();
        let actual = Json::from_str(&*data).unwrap();
        let expected = Json::from_str(expected_str).unwrap();
        assert_eq!(actual, expected);
    }

    #[test]
    fn test_close_window() {
        let resp = WebDriverResponse::CloseWindow(
            CloseWindowResponse::new(vec!["test".into()]));
        let expected = r#"{"value": ["test"]}"#;
        test(resp, expected);
    }

    #[test]
    fn test_cookie() {
        let resp = WebDriverResponse::Cookie(CookieResponse::new(
            vec![
                Cookie::new("test".into(),
                            "test_value".into(),
                            Nullable::Value("/".into()),
                            Nullable::Null,
                            Nullable::Null,
                            true,
                            false)
            ]));
        let expected = r#"{"value": [{"name": "test", "value": "test_value", "path": "/",
"domain": null, "expiry": null, "secure": true, "httpOnly": false}]}"#;
        test(resp, expected);
    }

    #[test]
    fn test_element_rect() {
        let resp = WebDriverResponse::ElementRect(ElementRectResponse::new(
            0f64, 1f64, 2f64, 3f64));
        let expected = r#"{"value": {"x": 0.0, "y": 1.0, "width": 2.0, "height": 3.0}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_new_session() {
        let resp = WebDriverResponse::NewSession(
            NewSessionResponse::new("test".into(),
                                    Json::Object(BTreeMap::new())));
        let expected = r#"{"value": {"sessionId": "test", "capabilities": {}}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_timeouts() {
         let resp = WebDriverResponse::Timeouts(TimeoutsResponse::new(
            1, 2, 3));
        let expected = r#"{"value": {"script": 1, "pageLoad": 2, "implicit": 3}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_value() {
        let mut value = BTreeMap::new();
        value.insert("example".into(), Json::Array(vec![Json::String("test".into())]));
        let resp = WebDriverResponse::Generic(ValueResponse::new(
            Json::Object(value)));
        let expected = r#"{"value": {"example": ["test"]}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_window_position() {
         let resp = WebDriverResponse::WindowPosition(WindowPositionResponse::new(
            1, 2));
        let expected = r#"{"value": {"x": 1, "y": 2}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_window_size() {
         let resp = WebDriverResponse::WindowSize(WindowSizeResponse::new(
            1, 2));
        let expected = r#"{"value": {"width": 1, "height": 2}}"#;
        test(resp, expected);
    }
}
<commit_msg>response: add WindowRectResponse and remove WindowPosition/WindowSize<commit_after>use rustc_serialize::json::{self, Json, ToJson};

use common::{Nullable, Date};
use cookie;
use time;

#[derive(Debug)]
pub enum WebDriverResponse {
    CloseWindow(CloseWindowResponse),
    Cookie(CookieResponse),
    DeleteSession,
    ElementRect(ElementRectResponse),
    Generic(ValueResponse),
    NewSession(NewSessionResponse),
    Timeouts(TimeoutsResponse),
    Void,
    WindowRect(WindowRectResponse),
}

impl WebDriverResponse {
    pub fn to_json_string(self) -> String {
        let obj = match self {
            WebDriverResponse::CloseWindow(ref x) => json::encode(&x.to_json()),
            WebDriverResponse::Cookie(ref x) => json::encode(x),
            WebDriverResponse::DeleteSession => Ok("{}".to_string()),
            WebDriverResponse::ElementRect(ref x) => json::encode(x),
            WebDriverResponse::Generic(ref x) => json::encode(x),
            WebDriverResponse::NewSession(ref x) => json::encode(x),
            WebDriverResponse::Timeouts(ref x) => json::encode(x),
            WebDriverResponse::Void => Ok("{}".to_string()),
            WebDriverResponse::WindowRect(ref x) => json::encode(x),
        }.unwrap();

        match self {
            WebDriverResponse::Generic(_) |
            WebDriverResponse::Cookie(_) => obj,
            _ => {
                let mut data = String::with_capacity(11 + obj.len());
                data.push_str("{\"value\": ");
                data.push_str(&*obj);
                data.push_str("}");
                data
            }
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct CloseWindowResponse {
    pub window_handles: Vec<String>,
}

impl CloseWindowResponse {
    pub fn new(handles: Vec<String>) -> CloseWindowResponse {
        CloseWindowResponse { window_handles: handles }
    }
}

impl ToJson for CloseWindowResponse {
    fn to_json(&self) -> Json {
        Json::Array(self.window_handles
                    .iter()
                    .map(|x| Json::String(x.clone()))
                    .collect::<Vec<Json>>())
    }
}

#[derive(RustcEncodable, Debug)]
pub struct NewSessionResponse {
    pub sessionId: String,
    pub capabilities: json::Json
}

impl NewSessionResponse {
    pub fn new(session_id: String, capabilities: json::Json) -> NewSessionResponse {
        NewSessionResponse {
            capabilities: capabilities,
            sessionId: session_id
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct TimeoutsResponse {
    pub script: u64,
    pub pageLoad: u64,
    pub implicit: u64,
}

impl TimeoutsResponse {
    pub fn new(script: u64, page_load: u64, implicit: u64) -> TimeoutsResponse {
        TimeoutsResponse {
            script: script,
            pageLoad: page_load,
            implicit: implicit,
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct ValueResponse {
    pub value: json::Json
}

impl ValueResponse {
    pub fn new(value: json::Json) -> ValueResponse {
        ValueResponse {
            value: value
        }
    }
}

#[derive(RustcEncodable, Debug)]
pub struct WindowRectResponse {
    pub x: i64,
    pub y: i64,
    pub width: u64,
    pub height: u64,
}

#[derive(RustcEncodable, Debug)]
pub struct ElementRectResponse {
    pub x: f64,
    pub y: f64,
    pub width: f64,
    pub height: f64
}

impl ElementRectResponse {
    pub fn new(x: f64, y: f64, width: f64, height: f64) -> ElementRectResponse {
        ElementRectResponse {
            x: x,
            y: y,
            width: width,
            height: height
        }
    }
}

//TODO: some of these fields are probably supposed to be optional
#[derive(RustcEncodable, PartialEq, Debug, Clone)]
pub struct Cookie {
    pub name: String,
    pub value: String,
    pub path: Nullable<String>,
    pub domain: Nullable<String>,
    pub expiry: Nullable<Date>,
    pub secure: bool,
    pub httpOnly: bool
}

impl Cookie {
    pub fn new(name: String, value: String, path: Nullable<String>, domain: Nullable<String>,
               expiry: Nullable<Date>, secure: bool, http_only: bool) -> Cookie {
        Cookie {
            name: name,
            value: value,
            path: path,
            domain: domain,
            expiry: expiry,
            secure: secure,
            httpOnly: http_only
        }
    }
}

impl Into<cookie::Cookie<'static>> for Cookie {
    fn into(self) -> cookie::Cookie<'static> {
        let cookie = cookie::Cookie::build(self.name, self.value)
            .secure(self.secure)
            .http_only(self.httpOnly);
        let cookie = match self.domain {
            Nullable::Value(domain) => cookie.domain(domain),
            Nullable::Null => cookie,
        };
        let cookie = match self.path {
            Nullable::Value(path) => cookie.path(path),
            Nullable::Null => cookie,
        };
        let cookie = match self.expiry {
            Nullable::Value(Date(expiry)) => {
                cookie.expires(time::at(time::Timespec::new(expiry as i64, 0)))
            },
            Nullable::Null => cookie,
        };
        cookie.finish()
    }
}

#[derive(RustcEncodable, Debug)]
pub struct CookieResponse {
    pub value: Vec<Cookie>
}

impl CookieResponse {
    pub fn new(value: Vec<Cookie>) -> CookieResponse {
        CookieResponse {
            value: value
        }
    }
}

#[cfg(test)]
mod tests {
    use std::collections::BTreeMap;
    use rustc_serialize::json::Json;
    use super::{WebDriverResponse,
                CloseWindowResponse,
                CookieResponse,
                ElementRectResponse,
                NewSessionResponse,
                ValueResponse,
                TimeoutsResponse,
                WindowRectResponse,
                Cookie,
                Nullable};

    fn test(resp: WebDriverResponse, expected_str: &str) {
        let data = resp.to_json_string();
        let actual = Json::from_str(&*data).unwrap();
        let expected = Json::from_str(expected_str).unwrap();
        assert_eq!(actual, expected);
    }

    #[test]
    fn test_close_window() {
        let resp = WebDriverResponse::CloseWindow(
            CloseWindowResponse::new(vec!["test".into()]));
        let expected = r#"{"value": ["test"]}"#;
        test(resp, expected);
    }

    #[test]
    fn test_cookie() {
        let resp = WebDriverResponse::Cookie(CookieResponse::new(
            vec![
                Cookie::new("test".into(),
                            "test_value".into(),
                            Nullable::Value("/".into()),
                            Nullable::Null,
                            Nullable::Null,
                            true,
                            false)
            ]));
        let expected = r#"{"value": [{"name": "test", "value": "test_value", "path": "/",
"domain": null, "expiry": null, "secure": true, "httpOnly": false}]}"#;
        test(resp, expected);
    }

    #[test]
    fn test_element_rect() {
        let resp = WebDriverResponse::ElementRect(ElementRectResponse::new(
            0f64, 1f64, 2f64, 3f64));
        let expected = r#"{"value": {"x": 0.0, "y": 1.0, "width": 2.0, "height": 3.0}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_window_rect() {
        let resp = WebDriverResponse::WindowRect(WindowRectResponse {
            x: 0i64,
            y: 1i64,
            width: 2u64,
            height: 3u64,
        });
        let expected = r#"{"value": {"x": 0, "y": 1, "width": 2, "height": 3}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_new_session() {
        let resp = WebDriverResponse::NewSession(
            NewSessionResponse::new("test".into(),
                                    Json::Object(BTreeMap::new())));
        let expected = r#"{"value": {"sessionId": "test", "capabilities": {}}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_timeouts() {
         let resp = WebDriverResponse::Timeouts(TimeoutsResponse::new(
            1, 2, 3));
        let expected = r#"{"value": {"script": 1, "pageLoad": 2, "implicit": 3}}"#;
        test(resp, expected);
    }

    #[test]
    fn test_value() {
        let mut value = BTreeMap::new();
        value.insert("example".into(), Json::Array(vec![Json::String("test".into())]));
        let resp = WebDriverResponse::Generic(ValueResponse::new(
            Json::Object(value)));
        let expected = r#"{"value": {"example": ["test"]}}"#;
        test(resp, expected);
    }
}
<|endoftext|>


<commit_before>//! Diagnostic reporting support for the codespan crate

use codespan::ByteSpan;

use Severity;

/// A style for the label
#[derive(Copy, Clone, PartialEq, Debug)]
pub enum LabelStyle {
    /// The main focus of the diagnostic
    Primary,
    /// Supporting labels that may help to isolate the cause of the diagnostic
    Secondary,
}

/// A label describing an underlined region of code associated with a diagnostic
#[derive(Clone, Debug)]
pub struct Label {
    /// The span we are going to include in the final snippet.
    pub span: ByteSpan,
    /// A message to provide some additional information for the underlined code.
    pub message: Option<String>,
    /// The style to use for the label.
    pub style: LabelStyle,
}

/// Represents a diagnostic message and associated child messages.
#[derive(Clone, Debug)]
pub struct Diagnostic {
    /// The overall severity of the diagnostic
    pub severity: Severity,
    /// The main message associated with this diagnostic
    pub message: String,
    /// The labelled spans marking the regions of code that cause this
    /// diagnostic to be raised
    pub labels: Vec<Label>,
}
<commit_msg>Add some builder methods to diagnostic structs<commit_after>//! Diagnostic reporting support for the codespan crate

use codespan::ByteSpan;

use Severity;

/// A style for the label
#[derive(Copy, Clone, PartialEq, Debug)]
pub enum LabelStyle {
    /// The main focus of the diagnostic
    Primary,
    /// Supporting labels that may help to isolate the cause of the diagnostic
    Secondary,
}

/// A label describing an underlined region of code associated with a diagnostic
#[derive(Clone, Debug)]
pub struct Label {
    /// The span we are going to include in the final snippet.
    pub span: ByteSpan,
    /// A message to provide some additional information for the underlined code.
    pub message: Option<String>,
    /// The style to use for the label.
    pub style: LabelStyle,
}

impl Label {
    pub fn new_primary<S: Into<String>>(span: ByteSpan, message: S) -> Label {
        Label {
            span,
            message: Some(message.into()),
            style: LabelStyle::Primary,
        }
    }

    pub fn new_secondary<S: Into<String>>(span: ByteSpan, message: S) -> Label {
        Label {
            span,
            message: Some(message.into()),
            style: LabelStyle::Primary,
        }
    }
}

/// Represents a diagnostic message and associated child messages.
#[derive(Clone, Debug)]
pub struct Diagnostic {
    /// The overall severity of the diagnostic
    pub severity: Severity,
    /// The main message associated with this diagnostic
    pub message: String,
    /// The labelled spans marking the regions of code that cause this
    /// diagnostic to be raised
    pub labels: Vec<Label>,
}

impl Diagnostic {
    pub fn new<S: Into<String>>(severity: Severity, message: S) -> Diagnostic {
        Diagnostic {
            severity,
            message: message.into(),
            labels: Vec::new(),
        }
    }

    pub fn new_bug<S: Into<String>>(message: S) -> Diagnostic {
        Diagnostic::new(Severity::Bug, message)
    }

    pub fn new_error<S: Into<String>>(message: S) -> Diagnostic {
        Diagnostic::new(Severity::Error, message)
    }

    pub fn new_warning<S: Into<String>>(message: S) -> Diagnostic {
        Diagnostic::new(Severity::Warning, message)
    }

    pub fn new_note<S: Into<String>>(message: S) -> Diagnostic {
        Diagnostic::new(Severity::Note, message)
    }

    pub fn new_help<S: Into<String>>(message: S) -> Diagnostic {
        Diagnostic::new(Severity::Help, message)
    }

    pub fn with_label(mut self, label: Label) -> Diagnostic {
        self.labels.push(label);
        self
    }

    pub fn with_primary_label<S: Into<String>>(self, span: ByteSpan, message: S) -> Diagnostic {
        self.with_label(Label::new_primary(span, message))
    }

    pub fn with_secondary_label<S: Into<String>>(self, span: ByteSpan, message: S) -> Diagnostic {
        self.with_label(Label::new_secondary(span, message))
    }
}
<|endoftext|>


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

pub mod key {
    use std::fs::File;
    use std::io::{BufRead, BufReader};
    use std::path::Path;

    use error::{Error, Result};
    use hcore;

    // shared between origin::key::upload and origin::key::upload_latest
    fn get_name_with_rev(keyfile: &Path, expected_vsn: &str) -> Result<String> {
        let f = try!(File::open(&keyfile));
        let f = BufReader::new(f);
        let mut lines = f.lines();
        let _ = match lines.next() {
            Some(val) => {
                let val = try!(val);
                if &val != expected_vsn {
                    let msg = format!("Unsupported version: {}", &val);
                    return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
                }
                ()
            }
            None => {
                let msg = "Corrupt key file, can't read file version".to_string();
                return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
            }
        };
        let name_with_rev = match lines.next() {
            Some(val) => try!(val),
            None => {
                let msg = "Corrupt key file, can't read name with rev".to_string();
                return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
            }
        };
        Ok(name_with_rev)
    }

    pub mod download {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use hcore::crypto::SigKeyPair;

        use {PRODUCT, VERSION};
        use error::{Error, Result};

        use retry::retry;

        pub fn start(ui: &mut UI,
                     depot: &str,
                     origin: &str,
                     revision: Option<&str>,
                     cache: &Path)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            match revision {
                Some(revision) => {
                    let nwr = format!("{}-{}", origin, revision);
                    try!(ui.begin(format!("Downloading public origin key {}", &nwr)));
                    match download_key(ui, &depot_client, &nwr, origin, revision, cache) {
                        Ok(()) => {
                            let msg = format!("Download of {} public origin key completed.", nwr);
                            try!(ui.end(msg));
                            Ok(())
                        }
                        Err(e) => Err(e),
                    }
                }
                None => {
                    try!(ui.begin(format!("Downloading public origin keys for {}", origin)));
                    match depot_client.show_origin_keys(origin) {
                        Ok(ref keys) if keys.len() == 0 => {
                            try!(ui.end(format!("No public keys for {}.", origin)));
                            Ok(())
                        }
                        Ok(keys) => {
                            for key in keys {
                                let nwr = format!("{}-{}", key.get_origin(), key.get_revision());
                                try!(download_key(ui,
                                                  &depot_client,
                                                  &nwr,
                                                  key.get_origin(),
                                                  key.get_revision(),
                                                  cache));
                            }
                            try!(ui.end(format!("Download of {} public origin keys completed.",
                                                &origin)));
                            Ok(())
                        }
                        Err(e) => Err(Error::from(e)),
                    }
                }
            }
        }

        fn download_key(ui: &mut UI,
                        depot_client: &Client,
                        nwr: &str,
                        name: &str,
                        rev: &str,
                        cache: &Path)
                        -> Result<()> {
            match SigKeyPair::get_public_key_path(&nwr, &cache) {
                Ok(_) => try!(ui.status(Status::Using, &nwr)),
                Err(_) => {
                    let download_fn = || -> Result<()> {
                        try!(ui.status(Status::Downloading, &nwr));
                        try!(depot_client.fetch_origin_key(name, rev, cache, ui.progress()));
                        try!(ui.status(Status::Cached, &nwr));
                        Ok(())
                    };

                    if retry(5, 3000, download_fn, |res| res.is_ok()).is_err() {
                        return Err(Error::from(depot_client::Error::DownloadFailed(format!("We tried 5 times but could not download {}/{} origin key. Giving up.", &name, &rev))));
                    }
                }
            }
            Ok(())
        }
    }

    pub mod export {
        use std::io;
        use std::fs::File;
        use std::path::Path;

        use hcore::crypto::SigKeyPair;
        use hcore::crypto::keys::PairType;

        use error::Result;

        pub fn start(origin: &str, pair_type: PairType, cache: &Path) -> Result<()> {
            let latest = try!(SigKeyPair::get_latest_pair_for(origin, cache));
            let path = match pair_type {
                PairType::Public => {
                    try!(SigKeyPair::get_public_key_path(&latest.name_with_rev(), cache))
                }
                PairType::Secret => {
                    try!(SigKeyPair::get_secret_key_path(&latest.name_with_rev(), cache))
                }
            };
            let mut file = try!(File::open(&path));
            debug!("Streaming file contents of {} {} to standard out",
                   &pair_type,
                   &path.display());
            try!(io::copy(&mut file, &mut io::stdout()));
            Ok(())
        }
    }

    pub mod generate {
        use std::path::Path;

        use common::ui::UI;
        use hcore::crypto::SigKeyPair;

        use error::Result;

        pub fn start(ui: &mut UI, origin: &str, cache: &Path) -> Result<()> {
            try!(ui.begin(format!("Generating origin key for {}", &origin)));
            let pair = try!(SigKeyPair::generate_pair_for_origin(origin, cache));
            try!(ui.end(format!("Generated origin key pair {}.", &pair.name_with_rev())));
            Ok(())
        }
    }

    pub mod import {
        use std::path::Path;

        use common::ui::UI;
        use hcore::crypto::SigKeyPair;

        use error::Result;

        pub fn start(ui: &mut UI, content: &str, cache: &Path) -> Result<()> {
            try!(ui.begin("Importing origin key from standard input"));
            let (pair, pair_type) = try!(SigKeyPair::write_file_from_str(content, cache));
            try!(ui.end(format!("Imported {} origin key {}.",
                                &pair_type,
                                &pair.name_with_rev())));
            Ok(())
        }
    }

    pub mod upload {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use hcore::crypto::keys::parse_name_with_rev;
        use hcore::crypto::{PUBLIC_SIG_KEY_VERSION, SECRET_SIG_KEY_VERSION};
        use hyper::status::StatusCode;

        use super::get_name_with_rev;
        use {PRODUCT, VERSION};
        use error::{Error, Result};

        pub fn start(ui: &mut UI,
                     depot: &str,
                     token: &str,
                     public_keyfile: &Path,
                     secret_keyfile: Option<&Path>)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            try!(ui.begin(format!("Uploading public origin key {}", public_keyfile.display())));

            let name_with_rev = try!(get_name_with_rev(&public_keyfile, PUBLIC_SIG_KEY_VERSION));
            let (name, rev) = try!(parse_name_with_rev(&name_with_rev));
            try!(ui.status(Status::Uploading, public_keyfile.display()));

            match depot_client.put_origin_key(&name, &rev, public_keyfile, token, ui.progress()) {
                Ok(()) => try!(ui.status(Status::Uploaded, &name_with_rev)),
                Err(depot_client::Error::APIError(StatusCode::Conflict, _)) => {
                    try!(ui.status(Status::Using,
                                   format!("public key revision {} which already \
                                           exists in the depot",
                                           &name_with_rev)));
                }
                Err(err) => return Err(Error::from(err)),
            }
            try!(ui.end(format!("Upload of public origin key {} complete.", &name_with_rev)));

            if let Some(secret_keyfile) = secret_keyfile {
                let name_with_rev = try!(get_name_with_rev(&secret_keyfile,
                                                           SECRET_SIG_KEY_VERSION));
                let (name, rev) = try!(parse_name_with_rev(&name_with_rev));
                try!(ui.status(Status::Uploading, secret_keyfile.display()));
                match depot_client.put_origin_secret_key(&name,
                                                         &rev,
                                                         secret_keyfile,
                                                         token,
                                                         ui.progress()) {
                    Ok(()) => {
                        try!(ui.status(Status::Uploaded, &name_with_rev));
                        try!(ui.end(format!("Upload of secret origin key {} complete.",
                                            &name_with_rev)));
                    }
                    Err(e) => {
                        return Err(Error::DepotClient(e));
                    }
                }
            }

            Ok(())
        }
    }

    pub mod upload_latest {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use error::{Error, Result};
        use hcore::crypto::keys::parse_name_with_rev;
        use hcore::crypto::{PUBLIC_SIG_KEY_VERSION, SECRET_SIG_KEY_VERSION, SigKeyPair};
        use hyper::status::StatusCode;

        use super::get_name_with_rev;
        use {PRODUCT, VERSION};

        pub fn start(ui: &mut UI,
                     depot: &str,
                     token: &str,
                     origin: &str,
                     with_secret: bool,
                     cache: &Path)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            try!(ui.begin(format!("Uploading latest public origin key {}", &origin)));
            let latest = try!(SigKeyPair::get_latest_pair_for(origin, cache));
            let public_keyfile = try!(SigKeyPair::get_public_key_path(&latest.name_with_rev(),
                                                                      cache));
            let name_with_rev = try!(get_name_with_rev(&public_keyfile, PUBLIC_SIG_KEY_VERSION));
            let (name, rev) = try!(parse_name_with_rev(&name_with_rev));
            try!(ui.status(Status::Uploading, public_keyfile.display()));

            match depot_client.put_origin_key(&name, &rev, &public_keyfile, token, ui.progress()) {
                Ok(()) => try!(ui.status(Status::Uploaded, &name_with_rev)),
                Err(depot_client::Error::APIError(StatusCode::Conflict, _)) => {
                    try!(ui.status(Status::Using,
                                   format!("public key revision {} which already \
                                           exists in the depot",
                                           &name_with_rev)));
                }
                Err(err) => return Err(Error::from(err)),
            }
            try!(ui.end(format!("Upload of public origin key {} complete.", &name_with_rev)));

            if with_secret {
                let secret_keyfile = try!(SigKeyPair::get_secret_key_path(&latest.name_with_rev(),
                                                                          cache));

                // we already have this value, but get_name_with_rev will also
                // check the SECRET_SIG_KEY_VERSION
                let name_with_rev = try!(get_name_with_rev(&secret_keyfile,
                                                           SECRET_SIG_KEY_VERSION));
                try!(ui.status(Status::Uploading, secret_keyfile.display()));
                match depot_client.put_origin_secret_key(&name,
                                                         &rev,
                                                         &secret_keyfile,
                                                         token,
                                                         ui.progress()) {
                    Ok(()) => {
                        try!(ui.status(Status::Uploaded, &name_with_rev));
                        try!(ui.end(format!("Upload of secret origin key {} complete.",
                                            &name_with_rev)));
                    }
                    Err(e) => {
                        return Err(Error::DepotClient(e));
                    }
                }
            }
            Ok(())
        }
    }
}
<commit_msg>Retry origin key uploads<commit_after>// Copyright (c) 2016 Chef Software Inc. and/or applicable contributors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

pub mod key {
    use std::fs::File;
    use std::io::{BufRead, BufReader};
    use std::path::Path;

    use error::{Error, Result};
    use hcore;

    // shared between origin::key::upload and origin::key::upload_latest
    fn get_name_with_rev(keyfile: &Path, expected_vsn: &str) -> Result<String> {
        let f = try!(File::open(&keyfile));
        let f = BufReader::new(f);
        let mut lines = f.lines();
        let _ = match lines.next() {
            Some(val) => {
                let val = try!(val);
                if &val != expected_vsn {
                    let msg = format!("Unsupported version: {}", &val);
                    return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
                }
                ()
            }
            None => {
                let msg = "Corrupt key file, can't read file version".to_string();
                return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
            }
        };
        let name_with_rev = match lines.next() {
            Some(val) => try!(val),
            None => {
                let msg = "Corrupt key file, can't read name with rev".to_string();
                return Err(Error::HabitatCore(hcore::Error::CryptoError(msg)));
            }
        };
        Ok(name_with_rev)
    }

    pub mod download {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use hcore::crypto::SigKeyPair;

        use {PRODUCT, VERSION};
        use error::{Error, Result};

        use retry::retry;

        pub fn start(ui: &mut UI,
                     depot: &str,
                     origin: &str,
                     revision: Option<&str>,
                     cache: &Path)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            match revision {
                Some(revision) => {
                    let nwr = format!("{}-{}", origin, revision);
                    try!(ui.begin(format!("Downloading public origin key {}", &nwr)));
                    match download_key(ui, &depot_client, &nwr, origin, revision, cache) {
                        Ok(()) => {
                            let msg = format!("Download of {} public origin key completed.", nwr);
                            try!(ui.end(msg));
                            Ok(())
                        }
                        Err(e) => Err(e),
                    }
                }
                None => {
                    try!(ui.begin(format!("Downloading public origin keys for {}", origin)));
                    match depot_client.show_origin_keys(origin) {
                        Ok(ref keys) if keys.len() == 0 => {
                            try!(ui.end(format!("No public keys for {}.", origin)));
                            Ok(())
                        }
                        Ok(keys) => {
                            for key in keys {
                                let nwr = format!("{}-{}", key.get_origin(), key.get_revision());
                                try!(download_key(ui,
                                                  &depot_client,
                                                  &nwr,
                                                  key.get_origin(),
                                                  key.get_revision(),
                                                  cache));
                            }
                            try!(ui.end(format!("Download of {} public origin keys completed.",
                                                &origin)));
                            Ok(())
                        }
                        Err(e) => Err(Error::from(e)),
                    }
                }
            }
        }

        fn download_key(ui: &mut UI,
                        depot_client: &Client,
                        nwr: &str,
                        name: &str,
                        rev: &str,
                        cache: &Path)
                        -> Result<()> {
            match SigKeyPair::get_public_key_path(&nwr, &cache) {
                Ok(_) => try!(ui.status(Status::Using, &nwr)),
                Err(_) => {
                    let download_fn = || -> Result<()> {
                        try!(ui.status(Status::Downloading, &nwr));
                        try!(depot_client.fetch_origin_key(name, rev, cache, ui.progress()));
                        try!(ui.status(Status::Cached, &nwr));
                        Ok(())
                    };

                    if retry(5, 3000, download_fn, |res| res.is_ok()).is_err() {
                        return Err(Error::from(depot_client::Error::DownloadFailed(format!(
                                        "We tried 5 times but could not \
                                         download {}/{} origin key. Giving up.",
                                        &name, &rev))));
                    }
                }
            }
            Ok(())
        }
    }

    pub mod export {
        use std::io;
        use std::fs::File;
        use std::path::Path;

        use hcore::crypto::SigKeyPair;
        use hcore::crypto::keys::PairType;

        use error::Result;

        pub fn start(origin: &str, pair_type: PairType, cache: &Path) -> Result<()> {
            let latest = try!(SigKeyPair::get_latest_pair_for(origin, cache));
            let path = match pair_type {
                PairType::Public => {
                    try!(SigKeyPair::get_public_key_path(&latest.name_with_rev(), cache))
                }
                PairType::Secret => {
                    try!(SigKeyPair::get_secret_key_path(&latest.name_with_rev(), cache))
                }
            };
            let mut file = try!(File::open(&path));
            debug!("Streaming file contents of {} {} to standard out",
                   &pair_type,
                   &path.display());
            try!(io::copy(&mut file, &mut io::stdout()));
            Ok(())
        }
    }

    pub mod generate {
        use std::path::Path;

        use common::ui::UI;
        use hcore::crypto::SigKeyPair;

        use error::Result;

        pub fn start(ui: &mut UI, origin: &str, cache: &Path) -> Result<()> {
            try!(ui.begin(format!("Generating origin key for {}", &origin)));
            let pair = try!(SigKeyPair::generate_pair_for_origin(origin, cache));
            try!(ui.end(format!("Generated origin key pair {}.", &pair.name_with_rev())));
            Ok(())
        }
    }

    pub mod import {
        use std::path::Path;

        use common::ui::UI;
        use hcore::crypto::SigKeyPair;

        use error::Result;

        pub fn start(ui: &mut UI, content: &str, cache: &Path) -> Result<()> {
            try!(ui.begin("Importing origin key from standard input"));
            let (pair, pair_type) = try!(SigKeyPair::write_file_from_str(content, cache));
            try!(ui.end(format!("Imported {} origin key {}.",
                                &pair_type,
                                &pair.name_with_rev())));
            Ok(())
        }
    }

    pub mod upload {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use hcore::crypto::keys::parse_name_with_rev;
        use hcore::crypto::{PUBLIC_SIG_KEY_VERSION, SECRET_SIG_KEY_VERSION};
        use hyper::status::StatusCode;
        use retry::retry;

        use super::get_name_with_rev;
        use {PRODUCT, VERSION};
        use error::{Error, Result};

        pub fn start(ui: &mut UI,
                     depot: &str,
                     token: &str,
                     public_keyfile: &Path,
                     secret_keyfile: Option<&Path>)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            try!(ui.begin(format!("Uploading public origin key {}", public_keyfile.display())));

            let name_with_rev = try!(get_name_with_rev(&public_keyfile, PUBLIC_SIG_KEY_VERSION));
            let (name, rev) = try!(parse_name_with_rev(&name_with_rev));

            {
                let upload_fn = || -> Result<()> {
                    try!(ui.status(Status::Uploading, public_keyfile.display()));
                    match depot_client.put_origin_key(
                        &name, &rev, public_keyfile, token, ui.progress()) {
                        Ok(()) => try!(ui.status(Status::Uploaded, &name_with_rev)),
                        Err(depot_client::Error::APIError(StatusCode::Conflict, _)) => {
                            try!(ui.status(Status::Using,
                                        format!("public key revision {} which already \
                                                    exists in the depot",
                                                &name_with_rev)));
                        }
                        Err(err) => return Err(Error::from(err)),
                    }
                    Ok(())
                };

                if retry(5, 3000, upload_fn, |res| res.is_ok()).is_err() {
                    return Err(Error::from(depot_client::Error::UploadFailed(format!("We tried \
                                                                                5 times \
                                                                                but could \
                                                                                not upload \
                                                                                {}/{} public \
                                                                                origin key. \
                                                                                Giving up.\
                                                                                ",
                                                                                &name,
                                                                                &rev))));
                }
            }

            try!(ui.end(format!("Upload of public origin key {} complete.", &name_with_rev)));

            if let Some(secret_keyfile) = secret_keyfile {
                let name_with_rev = try!(get_name_with_rev(&secret_keyfile,
                                                           SECRET_SIG_KEY_VERSION));
                let (name, rev) = try!(parse_name_with_rev(&name_with_rev));

                let upload_fn = || -> Result<()> {
                    try!(ui.status(Status::Uploading, secret_keyfile.display()));
                    match depot_client.put_origin_secret_key(&name,
                                                             &rev,
                                                             secret_keyfile,
                                                             token,
                                                             ui.progress()) {
                        Ok(()) => {
                            try!(ui.status(Status::Uploaded, &name_with_rev));
                            try!(ui.end(format!("Upload of secret origin key {} complete.",
                                                &name_with_rev)));
                            Ok(())
                        }
                        Err(e) => {
                            return Err(Error::DepotClient(e));
                        }
                    }
                };

                if retry(5, 3000, upload_fn, |res| res.is_ok()).is_err() {
                    return Err(Error::from(depot_client::Error::UploadFailed(format!("We tried \
                                                                                5 times \
                                                                                but could \
                                                                                not upload \
                                                                                {}/{} secret \
                                                                                origin key. \
                                                                                Giving up.\
                                                                                ",
                                                                                &name,
                                                                                &rev))));
                }
            }

            Ok(())
        }
    }

    pub mod upload_latest {
        use std::path::Path;

        use common::ui::{Status, UI};
        use depot_client::{self, Client};
        use error::{Error, Result};
        use hcore::crypto::keys::parse_name_with_rev;
        use hcore::crypto::{PUBLIC_SIG_KEY_VERSION, SECRET_SIG_KEY_VERSION, SigKeyPair};
        use hyper::status::StatusCode;

        use super::get_name_with_rev;
        use {PRODUCT, VERSION};

        pub fn start(ui: &mut UI,
                     depot: &str,
                     token: &str,
                     origin: &str,
                     with_secret: bool,
                     cache: &Path)
                     -> Result<()> {
            let depot_client = try!(Client::new(depot, PRODUCT, VERSION, None));
            try!(ui.begin(format!("Uploading latest public origin key {}", &origin)));
            let latest = try!(SigKeyPair::get_latest_pair_for(origin, cache));
            let public_keyfile = try!(SigKeyPair::get_public_key_path(&latest.name_with_rev(),
                                                                      cache));
            let name_with_rev = try!(get_name_with_rev(&public_keyfile, PUBLIC_SIG_KEY_VERSION));
            let (name, rev) = try!(parse_name_with_rev(&name_with_rev));
            try!(ui.status(Status::Uploading, public_keyfile.display()));

            match depot_client.put_origin_key(&name, &rev, &public_keyfile, token, ui.progress()) {
                Ok(()) => try!(ui.status(Status::Uploaded, &name_with_rev)),
                Err(depot_client::Error::APIError(StatusCode::Conflict, _)) => {
                    try!(ui.status(Status::Using,
                                   format!("public key revision {} which already \
                                           exists in the depot",
                                           &name_with_rev)));
                }
                Err(err) => return Err(Error::from(err)),
            }
            try!(ui.end(format!("Upload of public origin key {} complete.", &name_with_rev)));

            if with_secret {
                let secret_keyfile = try!(SigKeyPair::get_secret_key_path(&latest.name_with_rev(),
                                                                          cache));

                // we already have this value, but get_name_with_rev will also
                // check the SECRET_SIG_KEY_VERSION
                let name_with_rev = try!(get_name_with_rev(&secret_keyfile,
                                                           SECRET_SIG_KEY_VERSION));
                try!(ui.status(Status::Uploading, secret_keyfile.display()));
                match depot_client.put_origin_secret_key(&name,
                                                         &rev,
                                                         &secret_keyfile,
                                                         token,
                                                         ui.progress()) {
                    Ok(()) => {
                        try!(ui.status(Status::Uploaded, &name_with_rev));
                        try!(ui.end(format!("Upload of secret origin key {} complete.",
                                            &name_with_rev)));
                    }
                    Err(e) => {
                        return Err(Error::DepotClient(e));
                    }
                }
            }
            Ok(())
        }
    }
}
<|endoftext|>


<commit_before>// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

// error-pattern:index out of bounds

fn main() {

    // This should cause a bounds-check failure, but may not if we do our
    // bounds checking by comparing the scaled index to the vector's
    // address-bounds, since we've scaled the index to wrap around to the
    // address of the 0th cell in the array (even though the index is
    // huge).

    let x = ~[1u,2u,3u];
    do vec::as_imm_buf(x) |p, _len| {
        let base = p as uint;                     // base = 0x1230 say
        let idx = base / sys::size_of::<uint>();  // idx  = 0x0246 say
        error!("ov1 base = 0x%x", base);
        error!("ov1 idx = 0x%x", idx);
        error!("ov1 sizeof::<uint>() = 0x%x", sys::size_of::<uint>());
        error!("ov1 idx * sizeof::<uint>() = 0x%x",
               idx * sys::size_of::<uint>());

        // This should fail.
        error!("ov1 0x%x",  x[idx]);
    }
}
<commit_msg>test: Fix comments in pretty-printed test. rs=burningtree<commit_after>// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

// error-pattern:index out of bounds

fn main() {

    // This should cause a bounds-check failure, but may not if we do our
    // bounds checking by comparing the scaled index to the vector's
    // address-bounds, since we've scaled the index to wrap around to the
    // address of the 0th cell in the array (even though the index is
    // huge).

    let x = ~[1u,2u,3u];
    do vec::as_imm_buf(x) |p, _len| {
        let base = p as uint;
        let idx = base / sys::size_of::<uint>();
        error!("ov1 base = 0x%x", base);
        error!("ov1 idx = 0x%x", idx);
        error!("ov1 sizeof::<uint>() = 0x%x", sys::size_of::<uint>());
        error!("ov1 idx * sizeof::<uint>() = 0x%x",
               idx * sys::size_of::<uint>());

        // This should fail.
        error!("ov1 0x%x",  x[idx]);
    }
}
<|endoftext|>


<commit_before>#![cfg(test)]

use std::collections::HashMap;
use rustc_serialize::json;
use rustc_serialize::json::{decode, Json, Object};
use rustc_serialize::{Decoder, Decodable};
use std::io::prelude::*;
use std::fs::File;
use token::{Token, ReservedWord};

pub struct ExpectPass {
    source: String,
    expected: Json,
    options: Option<Json>
}

pub struct ExpectFail {
    source: String,
    error: String,
    options: Option<Json>
}

pub enum TestCase {
    Pass(ExpectPass),
    Fail(ExpectFail)
}

trait JsonExt {
    fn into_array(self) -> json::Array;
    fn into_string(self) -> String;
    fn into_string_opt(self) -> Option<String>;
}

impl JsonExt for Json {
    fn into_array(self) -> json::Array {
        match self {
            Json::Array(array) => array,
            _ => panic!("expected array")
        }
    }
    fn into_string(self) -> String {
        match self {
            Json::String(string) => string,
            _ => panic!("expected string")
        }
    }
    fn into_string_opt(self) -> Option<String> {
        match self {
            Json::Null => None,
            Json::String(string) => Some(string),
            _ => panic!("expected string or null")
        }
    }
}

fn parse_expect_fail(test: &mut Object) -> ExpectFail {
    ExpectFail {
        source: test.remove("source").unwrap().into_string(),
        error: test.remove("error").unwrap().into_string(),
        options: None
    }
}

fn parse_expect_pass(test: &mut Object) -> ExpectPass {
    ExpectPass {
        source: test.remove("source").unwrap().into_string(),
        expected: test.remove("expected").unwrap(),
        options: None
    }
}

fn deserialize_token(mut data: Json) -> Token {
    let mut obj = data.as_object_mut().unwrap();
    let ty = obj.remove("type").unwrap().into_string();

    let mut matchers: HashMap<&str, Box<Fn(&mut Object) -> Option<Token>>> = HashMap::new();
    matchers.insert("LBrace", Box::new(|_:&mut Object| -> Option<Token> { Some(Token::LBrace) }));
    matchers.insert("DecimalInt", Box::new(|data:&mut Object| -> Option<Token> {
        match data.remove("value") {
            None => None,
            Some(str) => Some(Token::DecimalInt(str.into_string()))
        }
    }));
    let f = matchers.get("DecimalInt").unwrap();
    let mut data = Json::from_str("{\"type\":\"DecimalInt\",\"value\":\"11.3\"}").unwrap();
    let obj = data.as_object_mut().unwrap();
    f(obj).unwrap()
}

fn parse_test(mut test: Json) -> TestCase {
    let obj = test.as_object_mut().unwrap();
    if obj.contains_key("error") {
        TestCase::Fail(parse_expect_fail(obj))
    } else {
        TestCase::Pass(parse_expect_pass(obj))
    }
}

pub fn read_tests(path: &str) -> Vec<TestCase> {
    let mut f: File = File::open(path).unwrap();
    let mut s = String::new();
    f.read_to_string(&mut s);
    parse_tests(&s)
}

pub fn parse_tests(src: &str) -> Vec<TestCase> {
    let data: Json = src.parse().unwrap();
    data.into_array()
        .into_iter()
        .map(parse_test)
        .collect()
}
<commit_msg>eliminate unnecessary closure arg type annotation<commit_after>#![cfg(test)]

use std::collections::HashMap;
use rustc_serialize::json;
use rustc_serialize::json::{decode, Json, Object};
use rustc_serialize::{Decoder, Decodable};
use std::io::prelude::*;
use std::fs::File;
use token::{Token, ReservedWord};

pub struct ExpectPass {
    source: String,
    expected: Json,
    options: Option<Json>
}

pub struct ExpectFail {
    source: String,
    error: String,
    options: Option<Json>
}

pub enum TestCase {
    Pass(ExpectPass),
    Fail(ExpectFail)
}

trait JsonExt {
    fn into_array(self) -> json::Array;
    fn into_string(self) -> String;
    fn into_string_opt(self) -> Option<String>;
}

impl JsonExt for Json {
    fn into_array(self) -> json::Array {
        match self {
            Json::Array(array) => array,
            _ => panic!("expected array")
        }
    }
    fn into_string(self) -> String {
        match self {
            Json::String(string) => string,
            _ => panic!("expected string")
        }
    }
    fn into_string_opt(self) -> Option<String> {
        match self {
            Json::Null => None,
            Json::String(string) => Some(string),
            _ => panic!("expected string or null")
        }
    }
}

fn parse_expect_fail(test: &mut Object) -> ExpectFail {
    ExpectFail {
        source: test.remove("source").unwrap().into_string(),
        error: test.remove("error").unwrap().into_string(),
        options: None
    }
}

fn parse_expect_pass(test: &mut Object) -> ExpectPass {
    ExpectPass {
        source: test.remove("source").unwrap().into_string(),
        expected: test.remove("expected").unwrap(),
        options: None
    }
}

fn deserialize_token(mut data: Json) -> Token {
    let mut obj = data.as_object_mut().unwrap();
    let ty = obj.remove("type").unwrap().into_string();

    let mut matchers: HashMap<&str, Box<Fn(&mut Object) -> Option<Token>>> = HashMap::new();
    matchers.insert("LBrace", Box::new(|_| -> Option<Token> { Some(Token::LBrace) }));
    matchers.insert("DecimalInt", Box::new(|data| -> Option<Token> {
        match data.remove("value") {
            None => None,
            Some(str) => Some(Token::DecimalInt(str.into_string()))
        }
    }));
    let f = matchers.get("DecimalInt").unwrap();
    let mut data = Json::from_str("{\"type\":\"DecimalInt\",\"value\":\"11.3\"}").unwrap();
    let obj = data.as_object_mut().unwrap();
    f(obj).unwrap()
}

fn parse_test(mut test: Json) -> TestCase {
    let obj = test.as_object_mut().unwrap();
    if obj.contains_key("error") {
        TestCase::Fail(parse_expect_fail(obj))
    } else {
        TestCase::Pass(parse_expect_pass(obj))
    }
}

pub fn read_tests(path: &str) -> Vec<TestCase> {
    let mut f: File = File::open(path).unwrap();
    let mut s = String::new();
    f.read_to_string(&mut s);
    parse_tests(&s)
}

pub fn parse_tests(src: &str) -> Vec<TestCase> {
    let data: Json = src.parse().unwrap();
    data.into_array()
        .into_iter()
        .map(parse_test)
        .collect()
}
<|endoftext|>