<commit_before>use std::ops::{
  Add, AddAssign,
  Sub, SubAssign,
  Mul, MulAssign,
  Div, DivAssign,
  Index, IndexMut,
};

#[derive(Debug, Copy, Clone)]
pub struct Vec3 {
  pub i : f64,
  pub j : f64,
  pub k : f64,
}

impl Vec3 {
  pub fn length(&self) -> f64 {
    (self.i * self.i + self.j * self.j + self.k * self.k).sqrt()
  }
}

impl Add for Vec3 {
  type Output = Vec3;
  fn add(self, other: Vec3) -> Vec3 {
      Vec3 {i: self.i + other.i, j: self.j + other.j, k: self.k + other.k}
  }
}

impl AddAssign for Vec3 {
  fn add_assign(&mut self, other: Vec3) {
    *self = Vec3 {
      i: self.i + other.i,
      j: self.j + other.j,
      k: self.k + other.k,
    };
  }
}

impl Sub for Vec3 {
  type Output = Vec3;
  fn sub(self, other: Vec3) -> Vec3 {
      Vec3 {i: self.i - other.i, j: self.j - other.j, k: self.k - other.k}
  }
}

impl SubAssign for Vec3 {
  fn sub_assign(&mut self, other: Vec3) {
    *self = Vec3 {
      i: self.i - other.i,
      j: self.j - other.j,
      k: self.k - other.k,
    }
  }
}

impl Mul<Vec3> for Vec3 {
  type Output = Vec3;
  fn mul(self, rhs: Vec3) -> Vec3 {
    Vec3 {i: self.i * rhs.i, j: self.j * rhs.j, k: self.k * rhs.k}
  }
}

impl Mul<f64> for Vec3 {
  type Output = Vec3;
  fn mul(self, scalar: f64) -> Vec3 {
    Vec3 {i: self.i * scalar, j: self.j * scalar, k: self.k * scalar}
  }
}

impl MulAssign<Vec3> for Vec3 {
  fn mul_assign(&mut self, rhs: Vec3) {
    *self = Vec3 {
      i: self.i * rhs.i,
      j: self.j * rhs.j,
      k: self.k * rhs.k,
    }
  }
}

impl MulAssign<f64> for Vec3 {
  fn mul_assign(&mut self, scalar: f64) {
    *self = Vec3 {
      i: self.i * scalar,
      j: self.j * scalar,
      k: self.k * scalar,
    }
  }
}

impl Div<Vec3> for Vec3 {
  type Output = Vec3;
  fn div(self, rhs: Vec3) -> Vec3 {
    Vec3 {i: self.i / rhs.i, j: self.j / rhs.j, k: self.k / rhs.k}
  }
}

impl Div<f64> for Vec3 {
  type Output = Vec3;
  fn div(self, scalar: f64) -> Vec3 {
    Vec3 {i: self.i / scalar, j: self.j / scalar, k: self.k / scalar}
  }
}

impl DivAssign<Vec3> for Vec3 {
  fn div_assign(&mut self, rhs: Vec3) {
    *self = Vec3 {
      i: self.i / rhs.i,
      j: self.j / rhs.j,
      k: self.k / rhs.k,
    }
  }
}

impl DivAssign<f64> for Vec3 {
  fn div_assign(&mut self, scalar: f64) {
    *self = Vec3 {
      i: self.i / scalar,
      j: self.j / scalar,
      k: self.k / scalar,
    }
  }
}

impl Index<i32> for Vec3 {
  type Output = f64;
  fn index(&self, idx: i32) -> &f64 {
    match idx {
      0 => &self.i,
      1 => &self.j,
      2 => &self.k,
      _ => panic!("index out of range: {}", idx),
    }
  }
}

impl IndexMut<i32> for Vec3 {
  fn index_mut<'a>(&'a mut self, idx: i32) -> &'a mut f64 {
    match idx {
      0 => &mut self.i,
      1 => &mut self.j,
      2 => &mut self.k,
      _ => panic!("index out of range: {}", idx),
    }
  }
}

#[cfg(test)]
mod should {
  use super::Vec3;
  #[test]
  fn add() {
    let v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let sum = v1 + v2;
    assert_eq!(sum.i, 3.0);
    assert_eq!(sum.j, 3.0);
    assert_eq!(sum.k, 3.0);
  }
  #[test]
  fn add_assign() {
    let mut v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 += v2;
    assert_eq!(v1.i, 3.0);
    assert_eq!(v1.j, 3.0);
    assert_eq!(v1.k, 3.0);
  }
  #[test]
  fn subtract() {
    let v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let diff = v1 - v2;
    assert_eq!(diff.i, -1.0);
    assert_eq!(diff.j, -1.0);
    assert_eq!(diff.k, -1.0);
  }
  #[test]
  fn subtract_assign() {
    let mut v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 -= v2;
    assert_eq!(v1.i, -1.0);
    assert_eq!(v1.j, -1.0);
    assert_eq!(v1.k, -1.0);
  }
  #[test]
  fn multiply_by_vec3_elementwise() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    let product = v1 * v2;
    assert_eq!(product.i, 6.0);
    assert_eq!(product.j, 6.0);
    assert_eq!(product.k, 6.0);
  }
  #[test]
  fn multiply_by_vec3_assign_elementwise() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    v1 *= v2;
    assert_eq!(v1.i, 6.0);
    assert_eq!(v1.j, 6.0);
    assert_eq!(v1.k, 6.0);
  }
  #[test]
  fn multiply_by_f64() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let product = v1 * 3.0;

    assert_eq!(product.i, 6.0);
    assert_eq!(product.j, 6.0);
    assert_eq!(product.k, 6.0);
  }
  #[test]
  fn multiply_by_f64_assign() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 *= 3.0;

    assert_eq!(v1.i, 6.0);
    assert_eq!(v1.j, 6.0);
    assert_eq!(v1.k, 6.0);
  }
  #[test]
  fn divide_by_vec3_elementwise() {
    let v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    let quotient = v1 / v2;
    assert_eq!(quotient.i, 2.0);
    assert_eq!(quotient.j, 2.0);
    assert_eq!(quotient.k, 2.0);
  }
  #[test]
  fn divide_by_vec3_assign_elementwise() {
    let mut v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    v1 /= v2;
    assert_eq!(v1.i, 2.0);
    assert_eq!(v1.j, 2.0);
    assert_eq!(v1.k, 2.0);
  }
  #[test]
  fn divide_by_f64() {
    let v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let quotient = v1 / 3.0;

    assert_eq!(quotient.i, 2.0);
    assert_eq!(quotient.j, 2.0);
    assert_eq!(quotient.k, 2.0);
  }
  #[test]
  fn divide_by_f64_assign() {
    let mut v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    v1 /= 3.0;

    assert_eq!(v1.i, 2.0);
    assert_eq!(v1.j, 2.0);
    assert_eq!(v1.k, 2.0);
  }
  #[test]
  fn allow_index_access() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};

    assert_eq!(v1[0], 2.0);
    assert_eq!(v1[1], 2.0);
    assert_eq!(v1[2], 2.0);
  }
  #[test]
  #[should_panic(expected = "index out of range: 9")]
  fn panic_on_bad_index() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};

    assert_eq!(v1[9], 2.0);
  }
  #[test]
  fn allow_index_mut_access() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1[0] = 9.0;

    assert_eq!(v1[0], 9.0);
    assert_eq!(v1[1], 2.0);
    assert_eq!(v1[2], 2.0);
  }
}<commit_msg>Add test for length<commit_after>use std::ops::{
  Add, AddAssign,
  Sub, SubAssign,
  Mul, MulAssign,
  Div, DivAssign,
  Index, IndexMut,
};

#[derive(Debug, Copy, Clone)]
pub struct Vec3 {
  pub i : f64,
  pub j : f64,
  pub k : f64,
}

impl Vec3 {
  pub fn length(&self) -> f64 {
    (self.i * self.i + self.j * self.j + self.k * self.k).sqrt()
  }
}

impl Add for Vec3 {
  type Output = Vec3;
  fn add(self, other: Vec3) -> Vec3 {
      Vec3 {i: self.i + other.i, j: self.j + other.j, k: self.k + other.k}
  }
}

impl AddAssign for Vec3 {
  fn add_assign(&mut self, other: Vec3) {
    *self = Vec3 {
      i: self.i + other.i,
      j: self.j + other.j,
      k: self.k + other.k,
    };
  }
}

impl Sub for Vec3 {
  type Output = Vec3;
  fn sub(self, other: Vec3) -> Vec3 {
      Vec3 {i: self.i - other.i, j: self.j - other.j, k: self.k - other.k}
  }
}

impl SubAssign for Vec3 {
  fn sub_assign(&mut self, other: Vec3) {
    *self = Vec3 {
      i: self.i - other.i,
      j: self.j - other.j,
      k: self.k - other.k,
    }
  }
}

impl Mul<Vec3> for Vec3 {
  type Output = Vec3;
  fn mul(self, rhs: Vec3) -> Vec3 {
    Vec3 {i: self.i * rhs.i, j: self.j * rhs.j, k: self.k * rhs.k}
  }
}

impl Mul<f64> for Vec3 {
  type Output = Vec3;
  fn mul(self, scalar: f64) -> Vec3 {
    Vec3 {i: self.i * scalar, j: self.j * scalar, k: self.k * scalar}
  }
}

impl MulAssign<Vec3> for Vec3 {
  fn mul_assign(&mut self, rhs: Vec3) {
    *self = Vec3 {
      i: self.i * rhs.i,
      j: self.j * rhs.j,
      k: self.k * rhs.k,
    }
  }
}

impl MulAssign<f64> for Vec3 {
  fn mul_assign(&mut self, scalar: f64) {
    *self = Vec3 {
      i: self.i * scalar,
      j: self.j * scalar,
      k: self.k * scalar,
    }
  }
}

impl Div<Vec3> for Vec3 {
  type Output = Vec3;
  fn div(self, rhs: Vec3) -> Vec3 {
    Vec3 {i: self.i / rhs.i, j: self.j / rhs.j, k: self.k / rhs.k}
  }
}

impl Div<f64> for Vec3 {
  type Output = Vec3;
  fn div(self, scalar: f64) -> Vec3 {
    Vec3 {i: self.i / scalar, j: self.j / scalar, k: self.k / scalar}
  }
}

impl DivAssign<Vec3> for Vec3 {
  fn div_assign(&mut self, rhs: Vec3) {
    *self = Vec3 {
      i: self.i / rhs.i,
      j: self.j / rhs.j,
      k: self.k / rhs.k,
    }
  }
}

impl DivAssign<f64> for Vec3 {
  fn div_assign(&mut self, scalar: f64) {
    *self = Vec3 {
      i: self.i / scalar,
      j: self.j / scalar,
      k: self.k / scalar,
    }
  }
}

impl Index<i32> for Vec3 {
  type Output = f64;
  fn index(&self, idx: i32) -> &f64 {
    match idx {
      0 => &self.i,
      1 => &self.j,
      2 => &self.k,
      _ => panic!("index out of range: {}", idx),
    }
  }
}

impl IndexMut<i32> for Vec3 {
  fn index_mut<'a>(&'a mut self, idx: i32) -> &'a mut f64 {
    match idx {
      0 => &mut self.i,
      1 => &mut self.j,
      2 => &mut self.k,
      _ => panic!("index out of range: {}", idx),
    }
  }
}

#[cfg(test)]
mod should {
  use super::Vec3;
  #[test]
  fn add() {
    let v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let sum = v1 + v2;
    assert_eq!(sum.i, 3.0);
    assert_eq!(sum.j, 3.0);
    assert_eq!(sum.k, 3.0);
  }
  #[test]
  fn add_assign() {
    let mut v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 += v2;
    assert_eq!(v1.i, 3.0);
    assert_eq!(v1.j, 3.0);
    assert_eq!(v1.k, 3.0);
  }
  #[test]
  fn subtract() {
    let v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let diff = v1 - v2;
    assert_eq!(diff.i, -1.0);
    assert_eq!(diff.j, -1.0);
    assert_eq!(diff.k, -1.0);
  }
  #[test]
  fn subtract_assign() {
    let mut v1 = Vec3 { i: 1.0, j: 1.0, k: 1.0};
    let v2 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 -= v2;
    assert_eq!(v1.i, -1.0);
    assert_eq!(v1.j, -1.0);
    assert_eq!(v1.k, -1.0);
  }
  #[test]
  fn multiply_by_vec3_elementwise() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    let product = v1 * v2;
    assert_eq!(product.i, 6.0);
    assert_eq!(product.j, 6.0);
    assert_eq!(product.k, 6.0);
  }
  #[test]
  fn multiply_by_vec3_assign_elementwise() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    v1 *= v2;
    assert_eq!(v1.i, 6.0);
    assert_eq!(v1.j, 6.0);
    assert_eq!(v1.k, 6.0);
  }
  #[test]
  fn multiply_by_f64() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    let product = v1 * 3.0;

    assert_eq!(product.i, 6.0);
    assert_eq!(product.j, 6.0);
    assert_eq!(product.k, 6.0);
  }
  #[test]
  fn multiply_by_f64_assign() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1 *= 3.0;

    assert_eq!(v1.i, 6.0);
    assert_eq!(v1.j, 6.0);
    assert_eq!(v1.k, 6.0);
  }
  #[test]
  fn divide_by_vec3_elementwise() {
    let v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    let quotient = v1 / v2;
    assert_eq!(quotient.i, 2.0);
    assert_eq!(quotient.j, 2.0);
    assert_eq!(quotient.k, 2.0);
  }
  #[test]
  fn divide_by_vec3_assign_elementwise() {
    let mut v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let v2 = Vec3 { i: 3.0, j: 3.0, k: 3.0};
    v1 /= v2;
    assert_eq!(v1.i, 2.0);
    assert_eq!(v1.j, 2.0);
    assert_eq!(v1.k, 2.0);
  }
  #[test]
  fn divide_by_f64() {
    let v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    let quotient = v1 / 3.0;

    assert_eq!(quotient.i, 2.0);
    assert_eq!(quotient.j, 2.0);
    assert_eq!(quotient.k, 2.0);
  }
  #[test]
  fn divide_by_f64_assign() {
    let mut v1 = Vec3 { i: 6.0, j: 6.0, k: 6.0};
    v1 /= 3.0;

    assert_eq!(v1.i, 2.0);
    assert_eq!(v1.j, 2.0);
    assert_eq!(v1.k, 2.0);
  }
  #[test]
  fn allow_index_access() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};

    assert_eq!(v1[0], 2.0);
    assert_eq!(v1[1], 2.0);
    assert_eq!(v1[2], 2.0);
  }
  #[test]
  #[should_panic(expected = "index out of range: 9")]
  fn panic_on_bad_index() {
    let v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};

    assert_eq!(v1[9], 2.0);
  }
  #[test]
  fn allow_index_mut_access() {
    let mut v1 = Vec3 { i: 2.0, j: 2.0, k: 2.0};
    v1[0] = 9.0;

    assert_eq!(v1[0], 9.0);
    assert_eq!(v1[1], 2.0);
    assert_eq!(v1[2], 2.0);
  }

  #[test]
  fn calculate_length() {
    let mut v1 = Vec3 { i: 4.0, j: 4.0, k: 2.0};

    assert_eq!(v1.length(), 6.0);
  }
}<|endoftext|>


<commit_before>use std::ops::Deref;
use std::mem;

/*
* storing in & out edges seperately should cut down on the number of "things" i have to traverse
* if a vertex has 10k edges (5k in and out 5k out) then doing something like*   g(v).outV()
* should be ok
*/
#[derive(Debug)]
pub struct Vertex {
    pub id: i64,
    // pointers on both sides, yay
    pub out_edges: Vec<*mut Edge>,
    pub in_edges:  Vec<*mut Edge>,
}

impl Vertex {
    pub fn new(id: i64) -> Box<Vertex> {
        Box::new(Vertex{id:id,
                        out_edges: Vec::new(),
                        in_edges: Vec::new()})
    }
}

pub struct VertexProxy {
    pub id: i64,
    pub v: *mut Vertex,
}

impl VertexProxy {
    pub fn add_edge(&mut self, to_vertex: &mut VertexProxy) -> EdgeProxy {
        let in_vertex: &mut Vertex;
        let out_vertex: &mut Vertex;

        unsafe {
            in_vertex =  &mut *(self.v);
            out_vertex = &mut *(to_vertex.v);
        }

        // create the edge
        let e = Box::new(Edge{from_vertex: self.v, to_vertex: to_vertex.v});

        let edge: *mut Edge = unsafe { mem::transmute(e) };

        in_vertex.out_edges.push(edge);
        out_vertex.in_edges.push(edge);
        EdgeProxy{edge:edge}
    }

    pub fn query(self) {
    }

}

impl Deref for VertexProxy {
    type Target = Vertex;

    fn deref<'a>(&'a self) -> &'a Vertex {
        unsafe {
            &*(self.v)
        }
    }
}

#[derive(Debug)]
pub struct Edge {
    pub from_vertex: *mut Vertex,
    pub to_vertex: *mut Vertex
}

pub struct EdgeProxy {
    edge: *mut Edge
}

impl Deref for EdgeProxy {
    type Target = Edge;
    fn deref<'a>(&'a self) -> &'a Edge {
        unsafe { &*(self.edge) }
    }
}

enum GraphIterable {
    VertexProxy,
    EdgeProxy
}
<commit_msg>vertex property support<commit_after>use std::ops::Deref;
use std::mem;
use std::collections::HashMap;

#[derive(Debug)]
pub enum GraphProperty {
    i64,
    float,
    String,
}

/*
* storing in & out edges seperately should cut down on the number of "things" i have to traverse
* if a vertex has 10k edges (5k in and out 5k out) then doing something like*   g(v).outV()
* should be ok
*/
#[derive(Debug)]
pub struct Vertex {
    pub id: i64,
    pub properties: HashMap<String, GraphProperty>,
    // pointers on both sides, yay
    pub out_edges: Vec<*mut Edge>,
    pub in_edges:  Vec<*mut Edge>,
}

impl Vertex {
    pub fn new(id: i64) -> Box<Vertex> {
        let mut props  = HashMap::new();
        Box::new(Vertex{id:id,
                        properties: props,
                        out_edges: Vec::new(),
                        in_edges: Vec::new()})
    }
}

pub struct VertexProxy {
    pub id: i64,
    pub v: *mut Vertex,
}

impl VertexProxy {
    pub fn add_edge(&mut self, to_vertex: &mut VertexProxy) -> EdgeProxy {
        let in_vertex: &mut Vertex;
        let out_vertex: &mut Vertex;

        unsafe {
            in_vertex =  &mut *(self.v);
            out_vertex = &mut *(to_vertex.v);
        }

        // create the edge
        let e = Box::new(Edge{from_vertex: self.v, to_vertex: to_vertex.v});

        let edge: *mut Edge = unsafe { mem::transmute(e) };

        in_vertex.out_edges.push(edge);
        out_vertex.in_edges.push(edge);
        EdgeProxy{edge:edge}
    }

    pub fn query(self) {
    }

}

impl Deref for VertexProxy {
    type Target = Vertex;

    fn deref<'a>(&'a self) -> &'a Vertex {
        unsafe {
            &*(self.v)
        }
    }
}

#[derive(Debug)]
pub struct Edge {
    pub from_vertex: *mut Vertex,
    pub to_vertex: *mut Vertex
}

pub struct EdgeProxy {
    edge: *mut Edge
}

impl Deref for EdgeProxy {
    type Target = Edge;
    fn deref<'a>(&'a self) -> &'a Edge {
        unsafe { &*(self.edge) }
    }
}

enum GraphIterable {
    VertexProxy,
    EdgeProxy
}

struct GraphPath {
    path: GraphIterable
}

<|endoftext|>


<commit_before>// Copyright 2016 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.

use LinkerFlavor;
use target::{Target, TargetOptions, TargetResult};

pub fn target() -> TargetResult {
    let base = super::linux_base::opts();
    Ok(Target {
        llvm_target: "armv5te-unknown-linux-gnueabi".to_string(),
        target_endian: "little".to_string(),
        target_pointer_width: "32".to_string(),
        target_c_int_width: "32".to_string(),
        data_layout: "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64".to_string(),
        arch: "arm".to_string(),
        target_os: "linux".to_string(),
        target_env: "gnu".to_string(),
        target_vendor: "unknown".to_string(),
        linker_flavor: LinkerFlavor::Gcc,

        options: TargetOptions {
            features: "+soft-float,+strict-align".to_string(),
            // No atomic instructions on ARMv5
            max_atomic_width: Some(0),
            abi_blacklist: super::arm_base::abi_blacklist(),
            .. base
        }
    })
}
<commit_msg>Allow atomic operations up to 32 bits<commit_after>// Copyright 2016 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.

use LinkerFlavor;
use target::{Target, TargetOptions, TargetResult};

pub fn target() -> TargetResult {
    let base = super::linux_base::opts();
    Ok(Target {
        llvm_target: "armv5te-unknown-linux-gnueabi".to_string(),
        target_endian: "little".to_string(),
        target_pointer_width: "32".to_string(),
        target_c_int_width: "32".to_string(),
        data_layout: "e-m:e-p:32:32-i64:64-v128:64:128-a:0:32-n32-S64".to_string(),
        arch: "arm".to_string(),
        target_os: "linux".to_string(),
        target_env: "gnu".to_string(),
        target_vendor: "unknown".to_string(),
        linker_flavor: LinkerFlavor::Gcc,

        options: TargetOptions {
            features: "+soft-float,+strict-align".to_string(),

            // Atomic operations provided when linked with libgcc.
            // FIXME: If the following PR is merged, the atomic operations would be
            // provided by compiler-builtins instead with no change of behavior:
            // https://github.com/rust-lang-nursery/compiler-builtins/pull/115/files
            max_atomic_width: Some(32),
            abi_blacklist: super::arm_base::abi_blacklist(),
            .. base
        }
    })
}
<|endoftext|>


<commit_before>// Copyright 2016 Joe Wilm, The Alacritty Project 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.
use std::convert::From;
use std::fmt::{self, Display};
use std::ops::Deref;

use gl;
use glutin::{self, ContextBuilder, ControlFlow, CursorState, Event, EventsLoop,
             MouseCursor as GlutinMouseCursor, WindowBuilder};
use glutin::GlContext;

use MouseCursor;

use config::WindowConfig;

/// Window errors
#[derive(Debug)]
pub enum Error {
    /// Error creating the window
    ContextCreation(glutin::CreationError),

    /// Error manipulating the rendering context
    Context(glutin::ContextError),
}

/// Result of fallible operations concerning a Window.
type Result<T> = ::std::result::Result<T, Error>;

/// A window which can be used for displaying the terminal
///
/// Wraps the underlying windowing library to provide a stable API in Alacritty
pub struct Window {
    event_loop: EventsLoop,
    window: glutin::GlWindow,
    cursor_visible: bool,

    /// Whether or not the window is the focused window.
    pub is_focused: bool,
}

/// Threadsafe APIs for the window
pub struct Proxy {
    inner: glutin::EventsLoopProxy,
}

/// Information about where the window is being displayed
///
/// Useful for subsystems like the font rasterized which depend on DPI and scale
/// factor.
pub struct DeviceProperties {
    /// Scale factor for pixels <-> points.
    ///
    /// This will be 1. on standard displays and may have a different value on
    /// hidpi displays.
    pub scale_factor: f32,
}

/// Size of the window
#[derive(Debug, Copy, Clone)]
pub struct Size<T> {
    pub width: T,
    pub height: T,
}

/// Strongly typed Pixels unit
#[derive(Debug, Copy, Clone)]
pub struct Pixels<T>(pub T);

/// Strongly typed Points unit
///
/// Points are like pixels but adjusted for DPI.
#[derive(Debug, Copy, Clone)]
pub struct Points<T>(pub T);

pub trait ToPoints {
    fn to_points(&self, scale: f32) -> Size<Points<u32>>;
}

impl ToPoints for Size<Points<u32>> {
    #[inline]
    fn to_points(&self, _scale: f32) -> Size<Points<u32>> {
        *self
    }
}

impl ToPoints for Size<Pixels<u32>> {
    fn to_points(&self, scale: f32) -> Size<Points<u32>> {
        let width_pts = (*self.width as f32 / scale) as u32;
        let height_pts = (*self.height as f32 / scale) as u32;

        Size {
            width: Points(width_pts),
            height: Points(height_pts)
        }
    }
}

impl<T: Display> Display for Size<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{} × {}", self.width, self.height)
    }
}

macro_rules! deref_newtype {
    ($($src:ty),+) => {
        $(
        impl<T> Deref for $src {
            type Target = T;

            #[inline]
            fn deref(&self) -> &Self::Target {
                &self.0
            }
        }
        )+
    }
}

deref_newtype! { Points<T>, Pixels<T> }

impl<T: Display> Display for Pixels<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}px", self.0)
    }
}

impl<T: Display> Display for Points<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}pts", self.0)
    }
}

impl ::std::error::Error for Error {
    fn cause(&self) -> Option<&::std::error::Error> {
        match *self {
            Error::ContextCreation(ref err) => Some(err),
            Error::Context(ref err) => Some(err),
        }
    }

    fn description(&self) -> &str {
        match *self {
            Error::ContextCreation(ref _err) => "Error creating gl context",
            Error::Context(ref _err) => "Error operating on render context",
        }
    }
}

impl Display for Error {
    fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result {
        match *self {
            Error::ContextCreation(ref err) => {
                write!(f, "Error creating GL context; {}", err)
            },
            Error::Context(ref err) => {
                write!(f, "Error operating on render context; {}", err)
            },
        }
    }
}

impl From<glutin::CreationError> for Error {
    fn from(val: glutin::CreationError) -> Error {
        Error::ContextCreation(val)
    }
}

impl From<glutin::ContextError> for Error {
    fn from(val: glutin::ContextError) -> Error {
        Error::Context(val)
    }
}

impl Window {
    /// Create a new window
    ///
    /// This creates a window and fully initializes a window.
    pub fn new(
        title: &str,
        window_config: &WindowConfig,
    ) -> Result<Window> {
        let event_loop = EventsLoop::new();

        Window::platform_window_init();
        let window = WindowBuilder::new()
            .with_title(title)
            .with_transparency(true)
            .with_decorations(window_config.decorations());
        let context = ContextBuilder::new()
            .with_vsync(true);
        let window = ::glutin::GlWindow::new(window, context, &event_loop)?;

        // Text cursor
        window.set_cursor(GlutinMouseCursor::Text);

        // Set OpenGL symbol loader
        gl::load_with(|symbol| window.get_proc_address(symbol) as *const _);

        // Make the context current so OpenGL operations can run
        unsafe {
            window.make_current()?;
        }

        let window = Window {
            event_loop: event_loop,
            window: window,
            cursor_visible: true,
            is_focused: true,
        };

        window.run_os_extensions();

        Ok(window)
    }

    /// Get some properties about the device
    ///
    /// Some window properties are provided since subsystems like font
    /// rasterization depend on DPI and scale factor.
    pub fn device_properties(&self) -> DeviceProperties {
        DeviceProperties {
            scale_factor: self.window.hidpi_factor(),
        }
    }

    pub fn inner_size_pixels(&self) -> Option<Size<Pixels<u32>>> {
        self.window
            .get_inner_size()
            .map(|(w, h)| Size { width: Pixels(w), height: Pixels(h) })
    }

    #[inline]
    pub fn hidpi_factor(&self) -> f32 {
        self.window.hidpi_factor()
    }

    #[inline]
    pub fn create_window_proxy(&self) -> Proxy {
        Proxy {
            inner: self.event_loop.create_proxy(),
        }
    }

    #[inline]
    pub fn swap_buffers(&self) -> Result<()> {
        self.window
            .swap_buffers()
            .map_err(From::from)
    }

    /// Poll for any available events
    #[inline]
    pub fn poll_events<F>(&mut self, func: F)
        where F: FnMut(Event)
    {
        self.event_loop.poll_events(func);
    }

    #[inline]
    pub fn resize(&self, width: u32, height: u32) {
        self.window.resize(width, height);
    }

    /// Block waiting for events
    #[inline]
    pub fn wait_events<F>(&mut self, func: F)
        where F: FnMut(Event) -> ControlFlow
    {
        self.event_loop.run_forever(func);
    }

    /// Set the window title
    #[inline]
    pub fn set_title(&self, title: &str) {
        self.window.set_title(title);
    }

    #[inline]
    pub fn set_mouse_cursor(&self, cursor: MouseCursor) {
        self.window.set_cursor(match cursor {
            MouseCursor::Arrow => GlutinMouseCursor::Arrow,
            MouseCursor::Text => GlutinMouseCursor::Text,
        });
    }

    /// Set cursor visible
    pub fn set_cursor_visible(&mut self, visible: bool) {
        if visible != self.cursor_visible {
            self.cursor_visible = visible;
            if let Err(err) = self.window.set_cursor_state(if visible {
                CursorState::Normal
            } else {
                CursorState::Hide
            }) {
                warn!("Failed to set cursor visibility: {}", err);
            }
        }
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn platform_window_init() {
        /// Set up env to make XIM work correctly
        use x11_dl::xlib;
        use libc::{setlocale, LC_CTYPE};
        let xlib = xlib::Xlib::open().expect("get xlib");
        unsafe {
            // Use empty c string to fallback to LC_CTYPE in environment variables
            setlocale(LC_CTYPE, b"\0".as_ptr() as *const _);
            // Use empty c string for implementation dependent behavior,
            // which might be the XMODIFIERS set in env
            (xlib.XSetLocaleModifiers)(b"\0".as_ptr() as *const _);
        }
    }

    /// TODO: change this directive when adding functions for other platforms
    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn platform_window_init() {
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn set_urgent(&self, is_urgent: bool) {
        use glutin::os::unix::WindowExt;
        use std::os::raw;
        use x11_dl::xlib::{self, XUrgencyHint};

        let xlib_display = self.window.get_xlib_display();
        let xlib_window = self.window.get_xlib_window();

        if let (Some(xlib_window), Some(xlib_display)) = (xlib_window, xlib_display) {
            let xlib = xlib::Xlib::open().expect("get xlib");

            unsafe {
                let mut hints = (xlib.XGetWMHints)(xlib_display as _, xlib_window as _);

                if hints.is_null() {
                    hints = (xlib.XAllocWMHints)();
                }

                if is_urgent {
                    (*hints).flags |= XUrgencyHint;
                } else {
                    (*hints).flags &= !XUrgencyHint;
                 }

                (xlib.XSetWMHints)(xlib_display as _, xlib_window as _, hints);

                (xlib.XFree)(hints as *mut raw::c_void);
            }
        }

    }

    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn set_urgent(&self, _: bool) {
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn send_xim_spot(&self, x: i16, y: i16) {
        use glutin::os::unix::WindowExt;
        self.window.send_xim_spot(x, y);
    }

    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn send_xim_spot(&self, _x: i16, _y: i16) {
    }

    #[cfg(not(target_os = "macos"))]
    pub fn get_window_id(&self) -> Option<usize> {
        use glutin::os::unix::WindowExt;

        match self.window.get_xlib_window() {
            Some(xlib_window) => Some(xlib_window as usize),
            None => None
        }
    }

    #[cfg(target_os = "macos")]
    pub fn get_window_id(&self) -> Option<usize> {
        None
    }
}

pub trait OsExtensions {
    fn run_os_extensions(&self) {}
}

#[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os="dragonfly", target_os="openbsd")))]
impl OsExtensions for Window { }

#[cfg(any(target_os = "linux", target_os = "freebsd", target_os="dragonfly", target_os="openbsd"))]
impl OsExtensions for Window {
    fn run_os_extensions(&self) {
        use glutin::os::unix::WindowExt;
        use x11_dl::xlib::{self, XA_CARDINAL, PropModeReplace};
        use std::ffi::{CStr};
        use std::ptr;
        use libc::getpid;

        let xlib_display = self.window.get_xlib_display();
        let xlib_window = self.window.get_xlib_window();

        if let (Some(xlib_window), Some(xlib_display)) = (xlib_window, xlib_display) {
            let xlib = xlib::Xlib::open().expect("get xlib");

            // Set _NET_WM_PID to process pid
            unsafe {
                let _net_wm_pid = CStr::from_ptr(b"_NET_WM_PID\0".as_ptr() as *const _);
                let atom = (xlib.XInternAtom)(xlib_display as *mut _, _net_wm_pid.as_ptr(), 0);
                let pid = getpid();

                (xlib.XChangeProperty)(xlib_display as _, xlib_window as _, atom,
                    XA_CARDINAL, 32, PropModeReplace, &pid as *const i32 as *const u8, 1);

            }
            // Although this call doesn't actually pass any data, it does cause
            // WM_CLIENT_MACHINE to be set. WM_CLIENT_MACHINE MUST be set if _NET_WM_PID is set
            // (which we do above).
            unsafe {
                (xlib.XSetWMProperties)(xlib_display as _, xlib_window as _, ptr::null_mut(),
                    ptr::null_mut(), ptr::null_mut(), 0, ptr::null_mut(), ptr::null_mut(),
                    ptr::null_mut());
            }
        }
    }
}

impl Proxy {
    /// Wakes up the event loop of the window
    ///
    /// This is useful for triggering a draw when the renderer would otherwise
    /// be waiting on user input.
    pub fn wakeup_event_loop(&self) {
        self.inner.wakeup().unwrap();
    }
}

pub trait SetInnerSize<T> {
    fn set_inner_size<S: ToPoints>(&mut self, size: &S);
}

impl SetInnerSize<Pixels<u32>> for Window {
    fn set_inner_size<T: ToPoints>(&mut self, size: &T) {
        let size = size.to_points(self.hidpi_factor());
        self.window.set_inner_size(*size.width as _, *size.height as _);
    }
}
<commit_msg>Spawn alacritty window as invisible<commit_after>// Copyright 2016 Joe Wilm, The Alacritty Project 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.
use std::convert::From;
use std::fmt::{self, Display};
use std::ops::Deref;

use gl;
use glutin::{self, ContextBuilder, ControlFlow, CursorState, Event, EventsLoop,
             MouseCursor as GlutinMouseCursor, WindowBuilder};
use glutin::GlContext;

use MouseCursor;

use config::WindowConfig;

/// Window errors
#[derive(Debug)]
pub enum Error {
    /// Error creating the window
    ContextCreation(glutin::CreationError),

    /// Error manipulating the rendering context
    Context(glutin::ContextError),
}

/// Result of fallible operations concerning a Window.
type Result<T> = ::std::result::Result<T, Error>;

/// A window which can be used for displaying the terminal
///
/// Wraps the underlying windowing library to provide a stable API in Alacritty
pub struct Window {
    event_loop: EventsLoop,
    window: glutin::GlWindow,
    cursor_visible: bool,

    /// Whether or not the window is the focused window.
    pub is_focused: bool,
}

/// Threadsafe APIs for the window
pub struct Proxy {
    inner: glutin::EventsLoopProxy,
}

/// Information about where the window is being displayed
///
/// Useful for subsystems like the font rasterized which depend on DPI and scale
/// factor.
pub struct DeviceProperties {
    /// Scale factor for pixels <-> points.
    ///
    /// This will be 1. on standard displays and may have a different value on
    /// hidpi displays.
    pub scale_factor: f32,
}

/// Size of the window
#[derive(Debug, Copy, Clone)]
pub struct Size<T> {
    pub width: T,
    pub height: T,
}

/// Strongly typed Pixels unit
#[derive(Debug, Copy, Clone)]
pub struct Pixels<T>(pub T);

/// Strongly typed Points unit
///
/// Points are like pixels but adjusted for DPI.
#[derive(Debug, Copy, Clone)]
pub struct Points<T>(pub T);

pub trait ToPoints {
    fn to_points(&self, scale: f32) -> Size<Points<u32>>;
}

impl ToPoints for Size<Points<u32>> {
    #[inline]
    fn to_points(&self, _scale: f32) -> Size<Points<u32>> {
        *self
    }
}

impl ToPoints for Size<Pixels<u32>> {
    fn to_points(&self, scale: f32) -> Size<Points<u32>> {
        let width_pts = (*self.width as f32 / scale) as u32;
        let height_pts = (*self.height as f32 / scale) as u32;

        Size {
            width: Points(width_pts),
            height: Points(height_pts)
        }
    }
}

impl<T: Display> Display for Size<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{} × {}", self.width, self.height)
    }
}

macro_rules! deref_newtype {
    ($($src:ty),+) => {
        $(
        impl<T> Deref for $src {
            type Target = T;

            #[inline]
            fn deref(&self) -> &Self::Target {
                &self.0
            }
        }
        )+
    }
}

deref_newtype! { Points<T>, Pixels<T> }

impl<T: Display> Display for Pixels<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}px", self.0)
    }
}

impl<T: Display> Display for Points<T> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "{}pts", self.0)
    }
}

impl ::std::error::Error for Error {
    fn cause(&self) -> Option<&::std::error::Error> {
        match *self {
            Error::ContextCreation(ref err) => Some(err),
            Error::Context(ref err) => Some(err),
        }
    }

    fn description(&self) -> &str {
        match *self {
            Error::ContextCreation(ref _err) => "Error creating gl context",
            Error::Context(ref _err) => "Error operating on render context",
        }
    }
}

impl Display for Error {
    fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result {
        match *self {
            Error::ContextCreation(ref err) => {
                write!(f, "Error creating GL context; {}", err)
            },
            Error::Context(ref err) => {
                write!(f, "Error operating on render context; {}", err)
            },
        }
    }
}

impl From<glutin::CreationError> for Error {
    fn from(val: glutin::CreationError) -> Error {
        Error::ContextCreation(val)
    }
}

impl From<glutin::ContextError> for Error {
    fn from(val: glutin::ContextError) -> Error {
        Error::Context(val)
    }
}

impl Window {
    /// Create a new window
    ///
    /// This creates a window and fully initializes a window.
    pub fn new(
        title: &str,
        window_config: &WindowConfig,
    ) -> Result<Window> {
        let event_loop = EventsLoop::new();

        Window::platform_window_init();
        let window = WindowBuilder::new()
            .with_title(title)
            .with_visibility(false)
            .with_transparency(true)
            .with_decorations(window_config.decorations());
        let context = ContextBuilder::new()
            .with_vsync(true);
        let window = ::glutin::GlWindow::new(window, context, &event_loop)?;
        window.show();

        // Text cursor
        window.set_cursor(GlutinMouseCursor::Text);

        // Set OpenGL symbol loader
        gl::load_with(|symbol| window.get_proc_address(symbol) as *const _);

        // Make the context current so OpenGL operations can run
        unsafe {
            window.make_current()?;
        }

        let window = Window {
            event_loop: event_loop,
            window: window,
            cursor_visible: true,
            is_focused: true,
        };

        window.run_os_extensions();

        Ok(window)
    }

    /// Get some properties about the device
    ///
    /// Some window properties are provided since subsystems like font
    /// rasterization depend on DPI and scale factor.
    pub fn device_properties(&self) -> DeviceProperties {
        DeviceProperties {
            scale_factor: self.window.hidpi_factor(),
        }
    }

    pub fn inner_size_pixels(&self) -> Option<Size<Pixels<u32>>> {
        self.window
            .get_inner_size()
            .map(|(w, h)| Size { width: Pixels(w), height: Pixels(h) })
    }

    #[inline]
    pub fn hidpi_factor(&self) -> f32 {
        self.window.hidpi_factor()
    }

    #[inline]
    pub fn create_window_proxy(&self) -> Proxy {
        Proxy {
            inner: self.event_loop.create_proxy(),
        }
    }

    #[inline]
    pub fn swap_buffers(&self) -> Result<()> {
        self.window
            .swap_buffers()
            .map_err(From::from)
    }

    /// Poll for any available events
    #[inline]
    pub fn poll_events<F>(&mut self, func: F)
        where F: FnMut(Event)
    {
        self.event_loop.poll_events(func);
    }

    #[inline]
    pub fn resize(&self, width: u32, height: u32) {
        self.window.resize(width, height);
    }

    /// Block waiting for events
    #[inline]
    pub fn wait_events<F>(&mut self, func: F)
        where F: FnMut(Event) -> ControlFlow
    {
        self.event_loop.run_forever(func);
    }

    /// Set the window title
    #[inline]
    pub fn set_title(&self, title: &str) {
        self.window.set_title(title);
    }

    #[inline]
    pub fn set_mouse_cursor(&self, cursor: MouseCursor) {
        self.window.set_cursor(match cursor {
            MouseCursor::Arrow => GlutinMouseCursor::Arrow,
            MouseCursor::Text => GlutinMouseCursor::Text,
        });
    }

    /// Set cursor visible
    pub fn set_cursor_visible(&mut self, visible: bool) {
        if visible != self.cursor_visible {
            self.cursor_visible = visible;
            if let Err(err) = self.window.set_cursor_state(if visible {
                CursorState::Normal
            } else {
                CursorState::Hide
            }) {
                warn!("Failed to set cursor visibility: {}", err);
            }
        }
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn platform_window_init() {
        /// Set up env to make XIM work correctly
        use x11_dl::xlib;
        use libc::{setlocale, LC_CTYPE};
        let xlib = xlib::Xlib::open().expect("get xlib");
        unsafe {
            // Use empty c string to fallback to LC_CTYPE in environment variables
            setlocale(LC_CTYPE, b"\0".as_ptr() as *const _);
            // Use empty c string for implementation dependent behavior,
            // which might be the XMODIFIERS set in env
            (xlib.XSetLocaleModifiers)(b"\0".as_ptr() as *const _);
        }
    }

    /// TODO: change this directive when adding functions for other platforms
    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn platform_window_init() {
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn set_urgent(&self, is_urgent: bool) {
        use glutin::os::unix::WindowExt;
        use std::os::raw;
        use x11_dl::xlib::{self, XUrgencyHint};

        let xlib_display = self.window.get_xlib_display();
        let xlib_window = self.window.get_xlib_window();

        if let (Some(xlib_window), Some(xlib_display)) = (xlib_window, xlib_display) {
            let xlib = xlib::Xlib::open().expect("get xlib");

            unsafe {
                let mut hints = (xlib.XGetWMHints)(xlib_display as _, xlib_window as _);

                if hints.is_null() {
                    hints = (xlib.XAllocWMHints)();
                }

                if is_urgent {
                    (*hints).flags |= XUrgencyHint;
                } else {
                    (*hints).flags &= !XUrgencyHint;
                 }

                (xlib.XSetWMHints)(xlib_display as _, xlib_window as _, hints);

                (xlib.XFree)(hints as *mut raw::c_void);
            }
        }

    }

    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn set_urgent(&self, _: bool) {
    }

    #[cfg(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd"))]
    pub fn send_xim_spot(&self, x: i16, y: i16) {
        use glutin::os::unix::WindowExt;
        self.window.send_xim_spot(x, y);
    }

    #[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os = "dragonfly", target_os = "openbsd")))]
    pub fn send_xim_spot(&self, _x: i16, _y: i16) {
    }

    #[cfg(not(target_os = "macos"))]
    pub fn get_window_id(&self) -> Option<usize> {
        use glutin::os::unix::WindowExt;

        match self.window.get_xlib_window() {
            Some(xlib_window) => Some(xlib_window as usize),
            None => None
        }
    }

    #[cfg(target_os = "macos")]
    pub fn get_window_id(&self) -> Option<usize> {
        None
    }
}

pub trait OsExtensions {
    fn run_os_extensions(&self) {}
}

#[cfg(not(any(target_os = "linux", target_os = "freebsd", target_os="dragonfly", target_os="openbsd")))]
impl OsExtensions for Window { }

#[cfg(any(target_os = "linux", target_os = "freebsd", target_os="dragonfly", target_os="openbsd"))]
impl OsExtensions for Window {
    fn run_os_extensions(&self) {
        use glutin::os::unix::WindowExt;
        use x11_dl::xlib::{self, XA_CARDINAL, PropModeReplace};
        use std::ffi::{CStr};
        use std::ptr;
        use libc::getpid;

        let xlib_display = self.window.get_xlib_display();
        let xlib_window = self.window.get_xlib_window();

        if let (Some(xlib_window), Some(xlib_display)) = (xlib_window, xlib_display) {
            let xlib = xlib::Xlib::open().expect("get xlib");

            // Set _NET_WM_PID to process pid
            unsafe {
                let _net_wm_pid = CStr::from_ptr(b"_NET_WM_PID\0".as_ptr() as *const _);
                let atom = (xlib.XInternAtom)(xlib_display as *mut _, _net_wm_pid.as_ptr(), 0);
                let pid = getpid();

                (xlib.XChangeProperty)(xlib_display as _, xlib_window as _, atom,
                    XA_CARDINAL, 32, PropModeReplace, &pid as *const i32 as *const u8, 1);

            }
            // Although this call doesn't actually pass any data, it does cause
            // WM_CLIENT_MACHINE to be set. WM_CLIENT_MACHINE MUST be set if _NET_WM_PID is set
            // (which we do above).
            unsafe {
                (xlib.XSetWMProperties)(xlib_display as _, xlib_window as _, ptr::null_mut(),
                    ptr::null_mut(), ptr::null_mut(), 0, ptr::null_mut(), ptr::null_mut(),
                    ptr::null_mut());
            }
        }
    }
}

impl Proxy {
    /// Wakes up the event loop of the window
    ///
    /// This is useful for triggering a draw when the renderer would otherwise
    /// be waiting on user input.
    pub fn wakeup_event_loop(&self) {
        self.inner.wakeup().unwrap();
    }
}

pub trait SetInnerSize<T> {
    fn set_inner_size<S: ToPoints>(&mut self, size: &S);
}

impl SetInnerSize<Pixels<u32>> for Window {
    fn set_inner_size<T: ToPoints>(&mut self, size: &T) {
        let size = size.to_points(self.hidpi_factor());
        self.window.set_inner_size(*size.width as _, *size.height as _);
    }
}
<|endoftext|>


<commit_before>use Parameter;
use fa::{VFunction, Projection};
use agents::PredictionAgent;
use geometry::Space;
use std::marker::PhantomData;

pub struct GTD2<S: Space, V: VFunction<S> + Projection<S>>
{
    v_func: V,
    a_func: V,

    alpha: Parameter,
    beta: Parameter,
    gamma: Parameter,

    phantom: PhantomData<S>,
}

impl<S: Space, V> GTD2<S, V>
    where V: VFunction<S> + Projection<S>
{
    pub fn new<T1, T2, T3>(v_func: V, a_func: V,
                           alpha: T1, beta: T2, gamma: T3) -> Self
        where T1: Into<Parameter>,
              T2: Into<Parameter>,
              T3: Into<Parameter>
    {
        if !v_func.equivalent(&a_func) {
            panic!("v_func and a_func must be equivalent function approximators.")
        }

        GTD2 {
            v_func: v_func,
            a_func: a_func,

            alpha: alpha.into(),
            beta: beta.into(),
            gamma: gamma.into(),

            phantom: PhantomData,
        }
    }
}

impl<S: Space, V> PredictionAgent<S> for GTD2<S, V>
    where V: VFunction<S> + Projection<S>
{
    fn handle_transition(&mut self, s: &S::Repr, ns: &S::Repr, r: f64) -> Option<f64> {
        let phi_s = self.v_func.project(s);
        let phi_ns = self.v_func.project(ns);

        let td_error = r + self.gamma*self.v_func.evaluate_phi(&phi_ns) -
            self.v_func.evaluate_phi(&phi_s);
        let td_estimate = self.a_func.evaluate_phi(&phi_s);

        self.v_func.update_phi(&(&phi_s - &(self.gamma.value()*&phi_ns)), self.alpha*td_estimate);
        self.a_func.update_phi(&phi_s, self.beta*(td_error - td_estimate));

        Some(td_error)
    }

    fn handle_terminal(&mut self, _: &S::Repr) {
        self.alpha = self.alpha.step();
        self.beta = self.alpha.step();
        self.gamma = self.gamma.step();
    }
}

pub struct TDC<S: Space, V: VFunction<S> + Projection<S>>
{
    v_func: V,
    a_func: V,

    alpha: Parameter,
    beta: Parameter,
    gamma: Parameter,

    phantom: PhantomData<S>,
}

impl<S: Space, V> TDC<S, V>
    where V: VFunction<S> + Projection<S>
{
    pub fn new<T1, T2, T3>(v_func: V, a_func: V,
                           alpha: T1, beta: T2, gamma: T3) -> Self
        where T1: Into<Parameter>,
              T2: Into<Parameter>,
              T3: Into<Parameter>
    {
        if !v_func.equivalent(&a_func) {
            panic!("v_func and a_func must be equivalent function approximators.")
        }

        TDC {
            v_func: v_func,
            a_func: a_func,

            alpha: alpha.into(),
            beta: beta.into(),
            gamma: gamma.into(),

            phantom: PhantomData,
        }
    }
}

impl<S: Space, V> PredictionAgent<S> for TDC<S, V>
    where V: VFunction<S> + Projection<S>
{
    fn handle_transition(&mut self, s: &S::Repr, ns: &S::Repr, r: f64) -> Option<f64> {
        let phi_s = self.v_func.project(s);
        let phi_ns = self.v_func.project(ns);

        let td_error = r + self.gamma*self.v_func.evaluate_phi(&phi_ns) -
            self.v_func.evaluate_phi(&phi_s);
        let td_estimate = self.a_func.evaluate_phi(&phi_s);

        self.v_func.update_phi(&(&(td_error*&phi_s) - &(self.gamma.value()*td_estimate*&phi_ns)), self.alpha.value());
        self.a_func.update_phi(&phi_s, self.beta*(td_error - td_estimate));

        Some(td_error)
    }

    fn handle_terminal(&mut self, _: &S::Repr) {
        self.alpha = self.alpha.step();
        self.beta = self.alpha.step();
        self.gamma = self.gamma.step();
    }
}

<commit_msg>Replace type parameters in prediction/gtd.rs<commit_after>use Parameter;
use fa::{VFunction, Projection, Linear};
use agents::PredictionAgent;
use geometry::Space;

pub struct GTD2<S: Space, P: Projection<S>>
{
    v_func: Linear<S, P>,
    a_func: Linear<S, P>,

    alpha: Parameter,
    beta: Parameter,
    gamma: Parameter,
}

impl<S: Space, P: Projection<S>> GTD2<S, P> {
    pub fn new<T1, T2, T3>(v_func: Linear<S, P>, a_func: Linear<S, P>,
                           alpha: T1, beta: T2, gamma: T3) -> Self
        where T1: Into<Parameter>,
              T2: Into<Parameter>,
              T3: Into<Parameter>
    {
        if !v_func.equivalent(&a_func) {
            panic!("v_func and a_func must be equivalent function approximators.")
        }

        GTD2 {
            v_func: v_func,
            a_func: a_func,

            alpha: alpha.into(),
            beta: beta.into(),
            gamma: gamma.into(),
        }
    }
}

impl<S: Space, V> PredictionAgent<S> for GTD2<S, V>
    where V: VFunction<S> + Projection<S>
{
    fn handle_transition(&mut self, s: &S::Repr, ns: &S::Repr, r: f64) -> Option<f64> {
        let phi_s = self.v_func.project(s);
        let phi_ns = self.v_func.project(ns);

        let td_error = r + self.gamma*self.v_func.evaluate_phi(&phi_ns) -
            self.v_func.evaluate_phi(&phi_s);
        let td_estimate = self.a_func.evaluate_phi(&phi_s);

        self.v_func.update_phi(&(&phi_s - &(self.gamma.value()*&phi_ns)), self.alpha*td_estimate);
        self.a_func.update_phi(&phi_s, self.beta*(td_error - td_estimate));

        Some(td_error)
    }

    fn handle_terminal(&mut self, _: &S::Repr) {
        self.alpha = self.alpha.step();
        self.beta = self.alpha.step();
        self.gamma = self.gamma.step();
    }
}

pub struct TDC<S: Space, P: Projection<S>>
{
    v_func: Linear<S, P>,
    a_func: Linear<S, P>,

    alpha: Parameter,
    beta: Parameter,
    gamma: Parameter,
}

impl<S: Space, P: Projection<S>> TDC<S, P> {
    pub fn new<T1, T2, T3>(v_func: Linear<S, P>, a_func: Linear<S, P>,
                           alpha: T1, beta: T2, gamma: T3) -> Self
        where T1: Into<Parameter>,
              T2: Into<Parameter>,
              T3: Into<Parameter>
    {
        if !v_func.equivalent(&a_func) {
            panic!("v_func and a_func must be equivalent function approximators.")
        }

        TDC {
            v_func: v_func,
            a_func: a_func,

            alpha: alpha.into(),
            beta: beta.into(),
            gamma: gamma.into(),
        }
    }
}

impl<S: Space, V> PredictionAgent<S> for TDC<S, V>
    where V: VFunction<S> + Projection<S>
{
    fn handle_transition(&mut self, s: &S::Repr, ns: &S::Repr, r: f64) -> Option<f64> {
        let phi_s = self.v_func.project(s);
        let phi_ns = self.v_func.project(ns);

        let td_error = r + self.gamma*self.v_func.evaluate_phi(&phi_ns) -
            self.v_func.evaluate_phi(&phi_s);
        let td_estimate = self.a_func.evaluate_phi(&phi_s);

        self.v_func.update_phi(&(&(td_error*&phi_s) - &(self.gamma.value()*td_estimate*&phi_ns)), self.alpha.value());
        self.a_func.update_phi(&phi_s, self.beta*(td_error - td_estimate));

        Some(td_error)
    }

    fn handle_terminal(&mut self, _: &S::Repr) {
        self.alpha = self.alpha.step();
        self.beta = self.alpha.step();
        self.gamma = self.gamma.step();
    }
}

<|endoftext|>


<commit_before>use std::ops::{Add};

fn main() {
    let search_term = "picture";
    let quote = "Every face, every shop, bedroom window, public-house, and
    dark square is a picture feverishly turned--in search of what?
    It is the same with books. What do we seek through millions of pages?";

    for (idx, line) in quote.lines().enumerate() {
        if line.contains(search_term) {
            let line_num = idx + 1;
            println!("{}: {}", line_num, line);
        }
    }
    println!("");

    let (a, b) = (1.2, 3.4);
    let (x, y) = (10, 20);

    let c = add(a,b);
    let z = add(x, y);

    println!("{} + {} = {}", a, b, c);
    println!("{} + {} = {}", x, y, z);
    println!("");

    let haystack = [1, 1, 2, 5, 14, 42, 132, 429, 1430, 4862];

    for reference in haystack.iter() {
        let item = *reference;

        let result = match item {
            42 | 132 => "hit!",
            _ => "miss",
        };

        if result == "hit!" {
            println!("{}: {}", item, result);
        }
    }
    println!("");

    let three = 0b11;
    let thirty = 0o36;
    let three_hundred = 0x12C;

    println!("{} {} {}", three, thirty, three_hundred);
    println!("{:b} {:b} {:b}", three, thirty, three_hundred);
    println!("{:o} {:o} {:o}", three, thirty, three_hundred);
    println!("{:x} {:x} {:x}", three, thirty, three_hundred);
    println!("");

    let twenty = 20;
    let twenty_one: i32 = twenty + 1;
    let floats_okay = 21.0;
    let one_million = 1_000_000;

    println!("{}; {}; {}; {}", twenty, twenty_one, floats_okay, one_million);
    println!("");

    let a = 10;
    let b: i32 = 20;

    let c = add(a, b);
    println!("a + b = {}", c);
}

fn add<T: Add<Output = T>>(i: T, j: T) -> T {
    i + j
}
<commit_msg>arrays<commit_after>use std::ops::{Add};

fn main() {
    println!();

    // ARRAYS
    let one             = [1,2,3];
    let two: [u8; 3]    = [1,2,3];
    let blank1          = [0; 3];
    let blank2: [u8; 3] = [0; 3];

    let arrays = [one, two, blank1, blank2];

    for a in &arrays {
        print!("{:?}: ", a);
        for n in a.iter() {
            print!("\t{} + 10 = {}", n, n+10);
        }

        let mut sum = 0;
        for i in 0..a.len() {
            sum += a[i];
        }
        print!("\t(Σ{:?} = {})", a, sum);
        println!();
    }
    println!();

    // GREP-LITE
    let search_term = "picture";
    let quote = "Every face, every shop, bedroom window, public-house, and
    dark square is a picture feverishly turned--in search of what?
    It is the same with books. What do we seek through millions of pages?";

    for (idx, line) in quote.lines().enumerate() {
        if line.contains(search_term) {
            let line_num = idx + 1;
            println!("{}: {}", line_num, line);
        }
    }
    println!();

    // NUMBERS AND GENERIC FUNCTION
    let (a, b) = (1.2, 3.4);
    let (x, y) = (10, 20);

    let c = add(a,b);
    let z = add(x, y);

    println!("{} + {} = {}", a, b, c);
    println!("{} + {} = {}", x, y, z);
    println!();

    // SIMPLE FINDER
    let haystack = [1, 1, 2, 5, 14, 42, 132, 429, 1430, 4862];

    for reference in haystack.iter() {
        let item = *reference;

        let result = match item {
            42 | 132 => "hit!",
            _ => "miss",
        };

        if result == "hit!" {
            println!("{}: {}", item, result);
        }
    }
    println!();

    // NUMBERS AND BASE SYSTEMS
    let three = 0b11;
    let thirty = 0o36;
    let three_hundred = 0x12C;

    println!("{} {} {}", three, thirty, three_hundred);
    println!("{:b} {:b} {:b}", three, thirty, three_hundred);
    println!("{:o} {:o} {:o}", three, thirty, three_hundred);
    println!("{:x} {:x} {:x}", three, thirty, three_hundred);
    println!();

    // NUMBERS AND TYPES
    let twenty = 20;
    let twenty_one: i32 = twenty + 1;
    let floats_okay = 21.0;
    let one_million = 1_000_000;

    println!("{}; {}; {}; {}", twenty, twenty_one, floats_okay, one_million);
    println!();

    let a = 10;
    let b: i32 = 20;

    let c = add(a, b);
    println!("a + b = {}", c);
}

//GENERIC FUNCTION
fn add<T: Add<Output = T>>(i: T, j: T) -> T {
    i + j
}
<|endoftext|>


<commit_before>//! Randomized tests to try to catch crlf seam errors.

extern crate rand;
extern crate ropey;

use rand::Rng;
use ropey::Rope;

#[test]
fn crlf_inserts() {
    let mut rng = rand::thread_rng();
    let mut tree = Rope::new();

    // Do a bunch of random incoherent inserts of CRLF
    // pairs.
    for _ in 0..(1 << 11) {
        let len = tree.len_chars().max(1);
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");

        // Make sure the tree is sound
        tree.assert_integrity();
        tree.assert_invariants();
    }
}

#[test]
fn crlf_removals() {
    let mut rng = rand::thread_rng();
    let mut tree = Rope::new();

    // Build tree.
    for _ in 0..(1 << 11) {
        let len = tree.len_chars().max(1);
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r");
    }

    // Do a bunch of random incoherent removals
    for _ in 0..(1 << 10) {
        let start = rng.gen::<usize>() % tree.len_chars().max(1);
        let end = (start + 5).min(tree.len_chars());
        tree.remove(start..end);

        let start = rng.gen::<usize>() % tree.len_chars().max(1);
        let end = (start + 6).min(tree.len_chars());
        tree.remove(start..end);

        // Make sure the tree is sound
        tree.assert_integrity();
        tree.assert_invariants();
    }
}
<commit_msg>Improved the CRLF tests a bit.<commit_after>//! Randomized tests to try to catch crlf seam errors.

extern crate rand;
extern crate ropey;

use rand::Rng;
use ropey::Rope;

#[test]
fn crlf_inserts() {
    let mut rng = rand::thread_rng();
    let mut tree = Rope::new();

    // Do a bunch of random incoherent inserts of CRLF
    // pairs.
    for _ in 0..(1 << 12) {
        let len = tree.len_chars().max(1);
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n");
        tree.insert(rng.gen::<usize>() % len, "\n\r\n\r");

        // Make sure the tree is sound
        tree.assert_invariants();
    }
}

#[test]
fn crlf_removals() {
    let mut rng = rand::thread_rng();
    let mut tree = Rope::new();

    // Build tree.
    for _ in 0..(1 << 9) {
        let len = tree.len_chars().max(1);
        tree.insert(rng.gen::<usize>() % len, "\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r");
    }

    // Do a bunch of random incoherent removals
    for _ in 0..(1 << 11) {
        let start = rng.gen::<usize>() % tree.len_chars().max(1);
        let end = (start + 5).min(tree.len_chars());
        tree.remove(start..end);

        let start = rng.gen::<usize>() % tree.len_chars().max(1);
        let end = (start + 6).min(tree.len_chars());
        tree.remove(start..end);

        // Make sure the tree is sound
        tree.assert_invariants();
    }
}
<|endoftext|>


<commit_before>#[test]
fn method_experiments() {
    let s4 = S(4);
    let mut s5 = S(5);
    assert_eq!(200, S(2).f());
    assert_eq!(300, S(3).f_mut());
    assert_eq!(400, s4.f_ref(&S(400)));
    assert_eq!(4,   s4.0);
    assert_eq!(500, s5.f_ref_mut(&mut S(500)));
    assert_eq!(5,   s5.0);
}

struct S(u32);

use std::mem;

impl <'a> S {
    fn f(self) -> u32 {
        unsafe {
            let moved_self = mem::replace(&mut*(&self as *const Self as *mut Self), mem::uninitialized());
            let new_self = moved_self.s();
            *(&self as *const Self as *mut Self) = new_self;
//            *(&self as *const Self as *mut Self) =
//                mem::replace(&mut*(&self as *const Self as *mut Self), mem::uninitialized())
//                    .s();
        }
        self.0
    }

    fn f_mut(mut self) -> u32 {
        unsafe {
            let moved_self = mem::replace(&mut*(&self as *const Self as *mut Self), mem::uninitialized());
            let new_self = moved_self.s();
            *(&self as *const Self as *mut Self) = new_self;
//            *(&self as *const Self as *mut Self) =
//                mem::replace(&mut*(&self as *const Self as *mut Self), mem::uninitialized())
//                    .s();
        }
        self.0
    }

    fn f_ref(&'a self, other: &'a Self) -> u32 {
        unsafe {
            let moved_self = mem::replace(&mut*(&self as *const &Self as *mut &Self), mem::uninitialized());
            let new_self = moved_self.t(other);
            *(&self as *const &Self as *mut &Self) = new_self;
//            *(&self as *const &Self as *mut &Self) =
//                mem::replace(&mut*(&self as *const &Self as *mut &Self), mem::uninitialized())
//                    .t(other);
        }
        self.0
    }

    fn f_ref_mut(&'a mut self, other: &'a mut Self) -> u32 {
        unsafe { // 'unsafe' IF SELF
            //A
            let new_self = Self::u(mem::replace(&mut*(&self as *const &mut Self as *mut &mut Self), mem::uninitialized()), other);
            *(&self as *const &mut Self as *mut &mut Self) = new_self; // IF SELF
            //B
//            let moved_self = mem::replace(&mut*(&self as *const &mut Self as *mut &mut Self), mem::uninitialized());
//            let new_self = moved_self.u(other);
//            *(&self as *const &mut Self as *mut &mut Self) = new_self;
            //C
//            *(&self as *const &mut Self as *mut &mut Self) =
//                mem::replace(&mut*(&self as *const &mut Self as *mut &mut Self), mem::uninitialized())
//                    .u(other);
        }
        self.0
    }

    fn s(self) -> Self {
        S(self.0 * 100)
    }

    fn t(&'a self, other: &'a Self) -> &'a Self {
        other
    }

    fn u(&'a mut self, other: &'a mut Self) -> &'a mut Self {
        other
    }
}
<commit_msg>Add trait mocking experiments<commit_after>extern crate mocktopus;

use mocktopus::*;
use std::fmt::Debug;

trait Trait {
    fn f(x: u32) -> u32;
    fn g(x: u32) -> u32 {
        let x = match mocktopus::Mockable::call_mock(&<Self as Trait>::g, (x,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        x * 2
    }
}

//TODO TEST TRAIT DEFAULT LEAKAGE
//TODO TEST REGULAR AND TRAIT METHODS LEAKAGE

struct StructG<T>(T);

struct StructG2<T>(T);

impl <T> Into<StructG2<T>> for StructG<T> {
    fn into(mut self) -> StructG2<T> {
        self = match mocktopus::Mockable::call_mock(&Self::into, (self,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        StructG2(self.0)
    }
}

struct Struct();

impl Struct {
    fn into(self) -> u32 {
        match mocktopus::Mockable::call_mock(&Self::into, (self,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        42
    }
}

impl Into<u32> for Struct {
    fn into(self) -> u32 {
        match mocktopus::Mockable::call_mock(&<Self as Into<u32>>::into, (self,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        42
    }
}

impl Into<f64> for Struct {
    fn into(self) -> f64 {
        match mocktopus::Mockable::call_mock(&<Self as Into<f64>>::into, (self,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        42.
    }
}

impl Trait for Struct {
    fn f(x: u32) -> u32 {
        let x = match mocktopus::Mockable::call_mock(&Self::f, (x,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        x * 2
    }
}
struct Struct2();

impl Trait for Struct2 {
    fn f(x: u32) -> u32 {
        let x = match mocktopus::Mockable::call_mock(&<Self as Trait>::f, (x,)) {
            mocktopus::MockResult::Continue((xx,)) => xx,
            mocktopus::MockResult::Return(xx) => return xx,
        };
        x * 2
    }
}

#[test]
fn trait_experiments() {
    <Struct as Trait>::f.mock_raw(|_| MockResult::Return(123));
    assert_eq!(123, Struct::f(3));
    <Struct as Trait>::f.mock_raw(|x| MockResult::Continue((x+1,)));
    assert_eq!(8, Struct::f(3));

    <Struct as Trait>::g.mock_raw(|_| MockResult::Return(123));
    assert_eq!(123, Struct::g(3));
    <Struct as Trait>::g.mock_raw(|x| MockResult::Continue((x+1,)));
    assert_eq!(8, Struct::g(3));
    assert_eq!(6, Struct2::g(3));
}
<|endoftext|>


<commit_before>// Copyright (c) 2016 The vulkano developers
// 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. All files in the project carrying such
// notice may not be copied, modified, or distributed except
// according to those terms.

extern crate tempdir;

use std::fs::File;
use std::io::Write;
use std::process::Command;

pub type SpirvOutput = File;

pub fn compile(code: &str, ty: ShaderType) -> Result<SpirvOutput, String> {
    compile_inner(Some((code, ty)))
}

// Eventually the API will look like this, with an iterator for multiple shader stages.
// However for the moment GLSLang doesn't like that, so we only pass one shader at a time.
fn compile_inner<'a, I>(shaders: I) -> Result<SpirvOutput, String>
    where I: IntoIterator<Item = (&'a str, ShaderType)>
{
    let temp_dir = tempdir::TempDir::new("glslang-compile").unwrap();
    let output_file = temp_dir.path().join("compilation_output.spv");

    let mut command = Command::new(concat!(env!("OUT_DIR"), "/glslang_validator"));
    command.arg("-V");
    command.arg("-l");
    command.arg("-o").arg(&output_file);

    for (num, (source, ty)) in shaders.into_iter().enumerate() {
        let extension = match ty {
            ShaderType::Vertex => ".vert",
            ShaderType::Fragment => ".frag",
            ShaderType::Geometry => ".geom",
            ShaderType::TessellationControl => ".tesc",
            ShaderType::TessellationEvaluation => ".tese",
            ShaderType::Compute => ".comp",
        };

        let file_path = temp_dir.path().join(format!("{}{}", num, extension));
        File::create(&file_path).unwrap().write_all(source.as_bytes()).unwrap();
        command.arg(file_path);
    }

    let output = command.output().expect("Failed to execute glslangValidator");

    if output.status.success() {
        let spirv_output = File::open(output_file).expect("failed to open SPIR-V output file");
        return Ok(spirv_output);
    }

    let error1 = String::from_utf8(output.stdout).expect("output of glsl compiler is not UTF-8");
    let error2 = String::from_utf8(output.stderr).expect("output of glsl compiler is not UTF-8");
    return Err(error1 + &error2);
}

/// Type of shader.
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum ShaderType {
    Vertex,
    Fragment,
    Geometry,
    TessellationControl,
    TessellationEvaluation,
    Compute,
}
<commit_msg>Try harder to propagate shader compilation error messages<commit_after>// Copyright (c) 2016 The vulkano developers
// 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. All files in the project carrying such
// notice may not be copied, modified, or distributed except
// according to those terms.

extern crate tempdir;

use std::fs::File;
use std::io::Write;
use std::process::Command;

pub type SpirvOutput = File;

pub fn compile(code: &str, ty: ShaderType) -> Result<SpirvOutput, String> {
    compile_inner(Some((code, ty)))
}

// Eventually the API will look like this, with an iterator for multiple shader stages.
// However for the moment GLSLang doesn't like that, so we only pass one shader at a time.
fn compile_inner<'a, I>(shaders: I) -> Result<SpirvOutput, String>
    where I: IntoIterator<Item = (&'a str, ShaderType)>
{
    let temp_dir = tempdir::TempDir::new("glslang-compile").unwrap();
    let output_file = temp_dir.path().join("compilation_output.spv");

    let mut command = Command::new(concat!(env!("OUT_DIR"), "/glslang_validator"));
    command.arg("-V");
    command.arg("-l");
    command.arg("-o").arg(&output_file);

    for (num, (source, ty)) in shaders.into_iter().enumerate() {
        let extension = match ty {
            ShaderType::Vertex => ".vert",
            ShaderType::Fragment => ".frag",
            ShaderType::Geometry => ".geom",
            ShaderType::TessellationControl => ".tesc",
            ShaderType::TessellationEvaluation => ".tese",
            ShaderType::Compute => ".comp",
        };

        let file_path = temp_dir.path().join(format!("{}{}", num, extension));
        File::create(&file_path).unwrap().write_all(source.as_bytes()).unwrap();
        command.arg(file_path);
    }

    let output = command.output().expect("Failed to execute glslangValidator");

    if output.status.success() {
        let spirv_output = File::open(output_file).expect("failed to open SPIR-V output file");
        return Ok(spirv_output);
    }

    let error1 = String::from_utf8_lossy(&output.stdout);
    let error2 = String::from_utf8_lossy(&output.stderr);
    return Err(error1.into_owned() + &error2);
}

/// Type of shader.
#[derive(Debug, Clone, PartialEq, Eq)]
pub enum ShaderType {
    Vertex,
    Fragment,
    Geometry,
    TessellationControl,
    TessellationEvaluation,
    Compute,
}
<|endoftext|>


<commit_before>use super::{MissingExtensionError, X11Error};

/// The extension macro.
///
/// This macro generates a struct which checks for the presence of some X11 extensions and stores
/// the version supplied by the X server.
///
/// ```rust
/// extensions! {
///     // The extension to check for. This should correspond to the name of the extension inside x11rb's `x11rb::protocol::xproto::<name>` module path.
///     xfixes {
///         // The function used to query the available version of the extension. This will be inside the module path as explained above
///         xfixes_query_version,
///         // The minimum version of the extension that will be accepted.
///         minimum: (4, 0),
///         // The version of the extension to request.
///         request: (4, 0),
///     },
/// }
///
/// // The extensions may be checked then using the generated `Extensions` struct using the `check_extensions` function.
/// ```
macro_rules! extensions {
    (
        $(
            $extension:ident { // Extension name for path lookup
                $extension_fn:ident, // Function used to look up the version of the extension
                required: $required:expr,
                minimum: ($min_major:expr, $min_minor:expr),
                request: ($req_major:expr, $req_minor:expr),
            },
        )*
    ) => {
        #[derive(Debug, Copy, Clone)]
        pub struct Extensions {
            $(
                #[doc = concat!(" The version of the `", stringify!($extension), "` extension.")]
                pub $extension: Option<(u32, u32)>,
            )*
        }

        impl Extensions {
            pub fn check_extensions<C: x11rb::connection::Connection>(connection: &C, logger: &slog::Logger) -> Result<Extensions, X11Error> {
                $(
                    let $extension = {
                        use x11rb::protocol::$extension::{ConnectionExt as _, X11_EXTENSION_NAME};

                        if connection.extension_information(X11_EXTENSION_NAME)?.is_some() {
                            let version = connection.$extension_fn($req_major, $req_minor)?.reply()?;

                            #[allow(unused_comparisons)] // Macro comparisons
                            if version.major_version >= $req_major
                                || (version.major_version == $req_major && version.minor_version >= $req_minor)
                            {
                                slog::info!(
                                    logger,
                                    "Loaded extension {} version {}.{}",
                                    X11_EXTENSION_NAME,
                                    version.major_version,
                                    version.minor_version,
                                );

                                Some((version.major_version, version.minor_version))
                            } else {
                                if $required {
                                    slog::error!(
                                        logger,
                                        "required extension {} version is too low (have {}.{}, expected {}.{})",
                                        X11_EXTENSION_NAME,
                                        version.major_version,
                                        version.minor_version,
                                        $req_major,
                                        $req_minor,
                                    );

                                    return Err(MissingExtensionError::WrongVersion {
                                        name: X11_EXTENSION_NAME,
                                        required_major: $req_major,
                                        required_minor: $req_minor,
                                        available_major: version.major_version,
                                        available_minor: version.minor_version,
                                    }.into());
                                } else {
                                    None
                                }
                            }
                        } else {
                            if $required {
                                slog::error!(logger, "required extension {} not found", X11_EXTENSION_NAME);

                                return Err(MissingExtensionError::NotFound {
                                    name: X11_EXTENSION_NAME,
                                    major: $min_major,
                                    minor: $min_minor,
                                }
                                .into());
                            } else {
                                None
                            }
                        }
                    };
                )*

                Ok(Extensions {
                    $(
                        $extension,
                    )*
                })
            }
        }
    };
}

extensions! {
    present {
        present_query_version,
        required: true,
        minimum: (1, 0),
        request: (1, 0),
    },

    xfixes {
        xfixes_query_version,
        required: true,
        minimum: (4, 0),
        request: (4, 0),
    },

    dri3 {
        dri3_query_version,
        required: true,
        minimum: (1, 0),
        request: (1, 2),
    },
}
<commit_msg>disable internal x11 doctest<commit_after>use super::{MissingExtensionError, X11Error};

/// The extension macro.
///
/// This macro generates a struct which checks for the presence of some X11 extensions and stores
/// the version supplied by the X server.
///
/// ```ignore(cannot-test-this-because-non-exported-macro)
/// extensions! {
///     // The extension to check for. This should correspond to the name of the extension inside x11rb's `x11rb::protocol::xproto::<name>` module path.
///     xfixes {
///         // The function used to query the available version of the extension. This will be inside the module path as explained above
///         xfixes_query_version,
///         // The minimum version of the extension that will be accepted.
///         minimum: (4, 0),
///         // The version of the extension to request.
///         request: (4, 0),
///     },
/// }
///
/// // The extensions may be checked then using the generated `Extensions` struct using the `check_extensions` function.
/// ```
macro_rules! extensions {
    (
        $(
            $extension:ident { // Extension name for path lookup
                $extension_fn:ident, // Function used to look up the version of the extension
                required: $required:expr,
                minimum: ($min_major:expr, $min_minor:expr),
                request: ($req_major:expr, $req_minor:expr),
            },
        )*
    ) => {
        #[derive(Debug, Copy, Clone)]
        pub struct Extensions {
            $(
                #[doc = concat!(" The version of the `", stringify!($extension), "` extension.")]
                pub $extension: Option<(u32, u32)>,
            )*
        }

        impl Extensions {
            pub fn check_extensions<C: x11rb::connection::Connection>(connection: &C, logger: &slog::Logger) -> Result<Extensions, X11Error> {
                $(
                    let $extension = {
                        use x11rb::protocol::$extension::{ConnectionExt as _, X11_EXTENSION_NAME};

                        if connection.extension_information(X11_EXTENSION_NAME)?.is_some() {
                            let version = connection.$extension_fn($req_major, $req_minor)?.reply()?;

                            #[allow(unused_comparisons)] // Macro comparisons
                            if version.major_version >= $req_major
                                || (version.major_version == $req_major && version.minor_version >= $req_minor)
                            {
                                slog::info!(
                                    logger,
                                    "Loaded extension {} version {}.{}",
                                    X11_EXTENSION_NAME,
                                    version.major_version,
                                    version.minor_version,
                                );

                                Some((version.major_version, version.minor_version))
                            } else {
                                if $required {
                                    slog::error!(
                                        logger,
                                        "required extension {} version is too low (have {}.{}, expected {}.{})",
                                        X11_EXTENSION_NAME,
                                        version.major_version,
                                        version.minor_version,
                                        $req_major,
                                        $req_minor,
                                    );

                                    return Err(MissingExtensionError::WrongVersion {
                                        name: X11_EXTENSION_NAME,
                                        required_major: $req_major,
                                        required_minor: $req_minor,
                                        available_major: version.major_version,
                                        available_minor: version.minor_version,
                                    }.into());
                                } else {
                                    None
                                }
                            }
                        } else {
                            if $required {
                                slog::error!(logger, "required extension {} not found", X11_EXTENSION_NAME);

                                return Err(MissingExtensionError::NotFound {
                                    name: X11_EXTENSION_NAME,
                                    major: $min_major,
                                    minor: $min_minor,
                                }
                                .into());
                            } else {
                                None
                            }
                        }
                    };
                )*

                Ok(Extensions {
                    $(
                        $extension,
                    )*
                })
            }
        }
    };
}

extensions! {
    present {
        present_query_version,
        required: true,
        minimum: (1, 0),
        request: (1, 0),
    },

    xfixes {
        xfixes_query_version,
        required: true,
        minimum: (4, 0),
        request: (4, 0),
    },

    dri3 {
        dri3_query_version,
        required: true,
        minimum: (1, 0),
        request: (1, 2),
    },
}
<|endoftext|>