<commit_before>#![cfg_attr(
    not(any(feature = "vulkan", feature = "dx12", feature = "metal")),
    allow(dead_code, unused_extern_crates, unused_imports)
)]

extern crate env_logger;
extern crate gfx_hal as hal;
#[cfg(feature = "dx12")]
extern crate gfx_backend_dx12 as back;
#[cfg(feature = "vulkan")]
extern crate gfx_backend_vulkan as back;
#[cfg(feature = "metal")]
extern crate gfx_backend_metal as back;

use std::str::FromStr;
use std::ops::Range;

use hal::{Backend, Compute, Gpu, Device, DescriptorPool, Instance, QueueFamily, QueueGroup};
use hal::{queue, pso, memory, buffer, pool, command, device};

#[cfg(any(feature = "vulkan", feature = "dx12", feature = "metal"))]
fn main() {
    env_logger::init().unwrap();

    // For now this just panics if you didn't pass numbers. Could add proper error handling.
    if std::env::args().len() == 1 { panic!("You must pass a list of positive integers!") }
    let numbers: Vec<u32> = std::env::args()
        .skip(1)
        .map(|s| u32::from_str(&s).expect("You must pass a list of positive integers!"))
        .collect();
    let stride = std::mem::size_of::<u32>() as u64;

    #[cfg(any(feature = "vulkan", feature = "dx12", feature = "metal"))]
    let instance = back::Instance::create("gfx-rs compute", 1);

    let mut gpu = instance.enumerate_adapters().into_iter()
        .find(|a| a.queue_families
            .iter()
            .any(|family| family.supports_compute())
        )
        .expect("Failed to find a GPU with compute support!")
        .open_with(|family| {
            if family.supports_compute() {
                Some(1)
            } else {
                None
            }
        });

    let shader = gpu.device.create_shader_module(include_bytes!("shader/collatz.spv")).unwrap();

    let (pipeline_layout, pipeline, set_layout, mut desc_pool) = {
        let set_layout = gpu.device.create_descriptor_set_layout(&[
                pso::DescriptorSetLayoutBinding {
                    binding: 0,
                    ty: pso::DescriptorType::StorageBuffer,
                    count: 1,
                    stage_flags: pso::STAGE_COMPUTE,
                }
            ],
        );

        let pipeline_layout = gpu.device.create_pipeline_layout(&[&set_layout]);
        let entry_point = pso::EntryPoint { entry: "main", module: &shader };
        let pipeline = gpu.device
            .create_compute_pipelines(&[(entry_point, &pipeline_layout)])
            .remove(0)
            .expect("Error creating compute pipeline!");

        let desc_pool = gpu.device.create_descriptor_pool(
            1,
            &[
                pso::DescriptorRangeDesc {
                    ty: pso::DescriptorType::StorageBuffer,
                    count: 1,
                },
            ],
        );
        (pipeline_layout, pipeline, set_layout, desc_pool)
    };

    let (staging_memory, staging_buffer) = create_buffer(
        &mut gpu,
        memory::CPU_VISIBLE | memory::COHERENT,
        buffer::TRANSFER_SRC,
        stride,
        numbers.len() as u64,
    );

    {
        let mut writer = gpu.device.acquire_mapping_writer::<u32>(&staging_buffer, 0..stride * numbers.len() as u64).unwrap();
        writer.copy_from_slice(&numbers);
        gpu.device.release_mapping_writer(writer);
    }

    let (device_memory, device_buffer) = create_buffer(
        &mut gpu,
        memory::DEVICE_LOCAL,
        buffer::TRANSFER_DST,
        stride,
        numbers.len() as u64,
    );

    let desc_set = desc_pool.allocate_sets(&[&set_layout]).remove(0);
    gpu.device.update_descriptor_sets(&[
        pso::DescriptorSetWrite {
            set: &desc_set,
            binding: 0,
            array_offset: 0,
            write: pso::DescriptorWrite::StorageBuffer(vec![(&device_buffer, 0..stride * numbers.len() as u64)])
        }
    ]);

    let mut queue_group = QueueGroup::<_, Compute>::new(gpu.queue_groups.remove(0));
    let mut command_pool = gpu.device.create_command_pool_typed(&queue_group, pool::CommandPoolCreateFlags::empty(), 16);
    let fence = gpu.device.create_fence(false);
    let submission = queue::Submission::new().submit(&[{
        let mut command_buffer = command_pool.acquire_command_buffer();
        command_buffer.copy_buffer(&staging_buffer, &device_buffer, &[command::BufferCopy { src: 0, dst: 0, size: stride * numbers.len() as u64}]);
        command_buffer.pipeline_barrier(
            Range { start: pso::TRANSFER, end: pso::COMPUTE_SHADER },
                &[memory::Barrier::Buffer {
                    states: Range {
                        start: buffer::TRANSFER_WRITE,
                        end: buffer::SHADER_READ | buffer::SHADER_WRITE
                    },
                    target: &device_buffer
                }]);
        command_buffer.bind_compute_pipeline(&pipeline);
        command_buffer.bind_compute_descriptor_sets(&pipeline_layout, 0, &[&desc_set]);
        command_buffer.dispatch(numbers.len() as u32, 1, 1);
        command_buffer.pipeline_barrier(
            Range { start: pso::COMPUTE_SHADER, end: pso::TRANSFER },
                &[memory::Barrier::Buffer {
                    states: Range {
                        start: buffer::SHADER_READ | buffer::SHADER_WRITE,
                        end: buffer::TRANSFER_READ
                    },
                    target: &device_buffer
                }]);
        command_buffer.copy_buffer(&device_buffer, &staging_buffer, &[command::BufferCopy { src: 0, dst: 0, size: stride * numbers.len() as u64}]);
        command_buffer.finish()
    }]);
    queue_group.queues[0].submit(submission, Some(&fence));
    gpu.device.wait_for_fences(&[&fence], device::WaitFor::All, !0);

    {
        let reader = gpu.device.acquire_mapping_reader::<u32>(&staging_buffer, 0..stride * numbers.len() as u64).unwrap();
        println!("Times: {:?}", reader.into_iter().map(|n| *n).collect::<Vec<u32>>());
        gpu.device.release_mapping_reader(reader);
    }

    gpu.device.destroy_descriptor_pool(desc_pool);
    gpu.device.destroy_descriptor_set_layout(set_layout);
    gpu.device.destroy_shader_module(shader);
    gpu.device.destroy_buffer(device_buffer);
    gpu.device.destroy_buffer(staging_buffer);
    gpu.device.destroy_fence(fence);
    gpu.device.destroy_pipeline_layout(pipeline_layout);
    gpu.device.free_memory(device_memory);
    gpu.device.free_memory(staging_memory);
    gpu.device.destroy_compute_pipeline(pipeline);
}

fn create_buffer<B: Backend>(gpu: &mut Gpu<B>, properties: memory::Properties, usage: buffer::Usage, stride: u64, len: u64) -> (B::Memory, B::Buffer) {
    let buffer = gpu.device.create_buffer(stride * len, stride, usage).unwrap();
    let requirements = gpu.device.get_buffer_requirements(&buffer);

    let ty = (&gpu.memory_types).into_iter().find(|memory_type| {
        requirements.type_mask & (1 << memory_type.id) != 0 &&
        memory_type.properties.contains(properties)
    }).unwrap();

    let memory = gpu.device.allocate_memory(&ty, requirements.size).unwrap();
    let buffer = gpu.device.bind_buffer_memory(&memory, 0, buffer).unwrap();

    (memory, buffer)
}

#[cfg(not(any(feature = "vulkan", feature = "dx12", feature = "metal")))]
fn main() {
    println!("You need to enable one of the next-gen API feature (vulkan, dx12, metal) to run this example.");
}
<commit_msg>update the new compute example to use the new bitflags<commit_after>#![cfg_attr(
    not(any(feature = "vulkan", feature = "dx12", feature = "metal")),
    allow(dead_code, unused_extern_crates, unused_imports)
)]

extern crate env_logger;
extern crate gfx_hal as hal;
#[cfg(feature = "dx12")]
extern crate gfx_backend_dx12 as back;
#[cfg(feature = "vulkan")]
extern crate gfx_backend_vulkan as back;
#[cfg(feature = "metal")]
extern crate gfx_backend_metal as back;

use std::str::FromStr;
use std::ops::Range;

use hal::{Backend, Compute, Gpu, Device, DescriptorPool, Instance, QueueFamily, QueueGroup};
use hal::{queue, pso, memory, buffer, pool, command, device};

#[cfg(any(feature = "vulkan", feature = "dx12", feature = "metal"))]
fn main() {
    env_logger::init().unwrap();

    // For now this just panics if you didn't pass numbers. Could add proper error handling.
    if std::env::args().len() == 1 { panic!("You must pass a list of positive integers!") }
    let numbers: Vec<u32> = std::env::args()
        .skip(1)
        .map(|s| u32::from_str(&s).expect("You must pass a list of positive integers!"))
        .collect();
    let stride = std::mem::size_of::<u32>() as u64;

    #[cfg(any(feature = "vulkan", feature = "dx12", feature = "metal"))]
    let instance = back::Instance::create("gfx-rs compute", 1);

    let mut gpu = instance.enumerate_adapters().into_iter()
        .find(|a| a.queue_families
            .iter()
            .any(|family| family.supports_compute())
        )
        .expect("Failed to find a GPU with compute support!")
        .open_with(|family| {
            if family.supports_compute() {
                Some(1)
            } else {
                None
            }
        });

    let shader = gpu.device.create_shader_module(include_bytes!("shader/collatz.spv")).unwrap();

    let (pipeline_layout, pipeline, set_layout, mut desc_pool) = {
        let set_layout = gpu.device.create_descriptor_set_layout(&[
                pso::DescriptorSetLayoutBinding {
                    binding: 0,
                    ty: pso::DescriptorType::StorageBuffer,
                    count: 1,
                    stage_flags: pso::ShaderStageFlags::COMPUTE,
                }
            ],
        );

        let pipeline_layout = gpu.device.create_pipeline_layout(&[&set_layout]);
        let entry_point = pso::EntryPoint { entry: "main", module: &shader };
        let pipeline = gpu.device
            .create_compute_pipelines(&[(entry_point, &pipeline_layout)])
            .remove(0)
            .expect("Error creating compute pipeline!");

        let desc_pool = gpu.device.create_descriptor_pool(
            1,
            &[
                pso::DescriptorRangeDesc {
                    ty: pso::DescriptorType::StorageBuffer,
                    count: 1,
                },
            ],
        );
        (pipeline_layout, pipeline, set_layout, desc_pool)
    };

    let (staging_memory, staging_buffer) = create_buffer(
        &mut gpu,
        memory::Properties::CPU_VISIBLE | memory::Properties::COHERENT,
        buffer::Usage::TRANSFER_SRC,
        stride,
        numbers.len() as u64,
    );

    {
        let mut writer = gpu.device.acquire_mapping_writer::<u32>(&staging_buffer, 0..stride * numbers.len() as u64).unwrap();
        writer.copy_from_slice(&numbers);
        gpu.device.release_mapping_writer(writer);
    }

    let (device_memory, device_buffer) = create_buffer(
        &mut gpu,
        memory::Properties::DEVICE_LOCAL,
        buffer::Usage::TRANSFER_DST,
        stride,
        numbers.len() as u64,
    );

    let desc_set = desc_pool.allocate_sets(&[&set_layout]).remove(0);
    gpu.device.update_descriptor_sets(&[
        pso::DescriptorSetWrite {
            set: &desc_set,
            binding: 0,
            array_offset: 0,
            write: pso::DescriptorWrite::StorageBuffer(vec![(&device_buffer, 0..stride * numbers.len() as u64)])
        }
    ]);

    let mut queue_group = QueueGroup::<_, Compute>::new(gpu.queue_groups.remove(0));
    let mut command_pool = gpu.device.create_command_pool_typed(&queue_group, pool::CommandPoolCreateFlags::empty(), 16);
    let fence = gpu.device.create_fence(false);
    let submission = queue::Submission::new().submit(&[{
        let mut command_buffer = command_pool.acquire_command_buffer();
        command_buffer.copy_buffer(&staging_buffer, &device_buffer, &[command::BufferCopy { src: 0, dst: 0, size: stride * numbers.len() as u64}]);
        command_buffer.pipeline_barrier(
            Range { start: pso::PipelineStage::TRANSFER, end: pso::PipelineStage::COMPUTE_SHADER },
                &[memory::Barrier::Buffer {
                    states: Range {
                        start: buffer::Access::TRANSFER_WRITE,
                        end: buffer::Access::SHADER_READ | buffer::Access::SHADER_WRITE
                    },
                    target: &device_buffer
                }]);
        command_buffer.bind_compute_pipeline(&pipeline);
        command_buffer.bind_compute_descriptor_sets(&pipeline_layout, 0, &[&desc_set]);
        command_buffer.dispatch(numbers.len() as u32, 1, 1);
        command_buffer.pipeline_barrier(
            Range { start: pso::PipelineStage::COMPUTE_SHADER, end: pso::PipelineStage::TRANSFER },
                &[memory::Barrier::Buffer {
                    states: Range {
                        start: buffer::Access::SHADER_READ | buffer::Access::SHADER_WRITE,
                        end: buffer::Access::TRANSFER_READ
                    },
                    target: &device_buffer
                }]);
        command_buffer.copy_buffer(&device_buffer, &staging_buffer, &[command::BufferCopy { src: 0, dst: 0, size: stride * numbers.len() as u64}]);
        command_buffer.finish()
    }]);
    queue_group.queues[0].submit(submission, Some(&fence));
    gpu.device.wait_for_fences(&[&fence], device::WaitFor::All, !0);

    {
        let reader = gpu.device.acquire_mapping_reader::<u32>(&staging_buffer, 0..stride * numbers.len() as u64).unwrap();
        println!("Times: {:?}", reader.into_iter().map(|n| *n).collect::<Vec<u32>>());
        gpu.device.release_mapping_reader(reader);
    }

    gpu.device.destroy_descriptor_pool(desc_pool);
    gpu.device.destroy_descriptor_set_layout(set_layout);
    gpu.device.destroy_shader_module(shader);
    gpu.device.destroy_buffer(device_buffer);
    gpu.device.destroy_buffer(staging_buffer);
    gpu.device.destroy_fence(fence);
    gpu.device.destroy_pipeline_layout(pipeline_layout);
    gpu.device.free_memory(device_memory);
    gpu.device.free_memory(staging_memory);
    gpu.device.destroy_compute_pipeline(pipeline);
}

fn create_buffer<B: Backend>(gpu: &mut Gpu<B>, properties: memory::Properties, usage: buffer::Usage, stride: u64, len: u64) -> (B::Memory, B::Buffer) {
    let buffer = gpu.device.create_buffer(stride * len, stride, usage).unwrap();
    let requirements = gpu.device.get_buffer_requirements(&buffer);

    let ty = (&gpu.memory_types).into_iter().find(|memory_type| {
        requirements.type_mask & (1 << memory_type.id) != 0 &&
        memory_type.properties.contains(properties)
    }).unwrap();

    let memory = gpu.device.allocate_memory(&ty, requirements.size).unwrap();
    let buffer = gpu.device.bind_buffer_memory(&memory, 0, buffer).unwrap();

    (memory, buffer)
}

#[cfg(not(any(feature = "vulkan", feature = "dx12", feature = "metal")))]
fn main() {
    println!("You need to enable one of the next-gen API feature (vulkan, dx12, metal) to run this example.");
}
<|endoftext|>


<commit_before><commit_msg>perf(App): removed excess clones<commit_after><|endoftext|>


<commit_before>#[macro_use]
extern crate glium;

use glium::Surface;
use glium::glutin;

mod support;

#[derive(Copy, Clone, Debug)]
struct PerInstance {
    pub id: u32,
    pub w_position: (f32, f32, f32),
    pub color: (f32, f32, f32),
}
implement_vertex!(PerInstance, id, w_position, color);

fn main() {
    use glium::DisplayBuild;

    // building the display, ie. the main object
    let display = glutin::WindowBuilder::new()
        .with_depth_buffer(24)
        .build_glium()
        .unwrap();

    // building the vertex and index buffers
    let vertex_buffer = support::load_wavefront(&display, include_bytes!("support/teapot.obj"));

    // the program
    let program = program!(&display,
        140 => {
            vertex: "
                #version 140

                uniform mat4 persp_matrix;
                uniform mat4 view_matrix;

                in uint id;
                in vec3 w_position;
                in vec3 color;
                in vec3 position;
                in vec3 normal;
                out vec3 v_normal;
                out vec3 v_color;

                void main() {
                    v_normal = normal;
                    v_color = color;
                    gl_Position = persp_matrix * view_matrix * vec4(position * 0.005 + w_position, 1.0);
                }
            ",

            fragment: "
                #version 140

                in vec3 v_normal;
                in vec3 v_color;
                out vec4 f_color;

                const vec3 LIGHT = vec3(-0.2, 0.8, 0.1);

                void main() {
                    float lum = max(dot(normalize(v_normal), normalize(LIGHT)), 0.0);
                    vec3 color = (0.3 + 0.7 * lum) * v_color;
                    f_color = vec4(color, 1.0);
                }
            ",
        },
    ).unwrap();

    // the picking program
    let picking_program = program!(&display,
        140 => {
            vertex: "
                #version 140

                uniform mat4 persp_matrix;
                uniform mat4 view_matrix;

                in uint id;
                in vec3 w_position;
                in vec3 color;
                in vec3 position;
                in vec3 normal;
                flat out uint v_id;

                void main() {
                    v_id = id;
                    gl_Position = persp_matrix * view_matrix * vec4(position * 0.005 + w_position, 1.0);
                }
            ",

            fragment: "
                #version 140

                flat in uint v_id;
                out uint f_id;

                void main() {
                    f_id = v_id;
                }
            ",
        },
    ).unwrap();

    let mut camera = support::camera::CameraState::new();
    camera.set_position((0.0, 0.0, 1.5));
    camera.set_direction((0.0, 0.0, 1.0));

    //id's must be unique and != 0
    let mut per_instance = vec![
        PerInstance { id: 1, w_position: (-1.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
        PerInstance { id: 2, w_position: ( 0.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
        PerInstance { id: 3, w_position: ( 1.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
    ];
    per_instance.sort_by(|a, b| a.id.cmp(&b.id));
    let original = per_instance.clone();

    let mut picking_attachments: Option<(glium::texture::UnsignedTexture2d, glium::framebuffer::DepthRenderBuffer)> = None;
    let picking_pbo: glium::texture::pixel_buffer::PixelBuffer<u32>
        = glium::texture::pixel_buffer::PixelBuffer::new_empty(&display, 1);

    let mut cursor_position: Option<(i32, i32)> = None;

    // the main loop
    support::start_loop(|| {
        camera.update();

        // determing which object has been picked at the previous frame
        let picked_object = {
            let data = picking_pbo.read().map(|d| d[0]).unwrap_or(0);
            if data != 0 {
                per_instance.binary_search_by(|x| x.id.cmp(&data)).ok()
            } else {
                None
            }
        };

        per_instance = original.clone();
        if let Some(index) = picked_object {
            per_instance[index as usize] = PerInstance {
                id: per_instance[index as usize].id,
                w_position: per_instance[index as usize].w_position,
                color: (0.0, 1.0, 0.0)
            };
        }

        // building the uniforms
        let uniforms = uniform! {
            persp_matrix: camera.get_perspective(),
            view_matrix: camera.get_view(),
        };

        // draw parameters
        let params = glium::DrawParameters {
            depth: glium::Depth {
                test: glium::DepthTest::IfLess,
                write: true,
                .. Default::default()
            },
            .. Default::default()
        };

        let per_instance_buffer = glium::vertex::VertexBuffer::new(&display, &per_instance).unwrap();

        // drawing a frame
        let mut target = display.draw();
        target.clear_color_and_depth((0.0, 0.0, 0.0, 0.0), 1.0);

        //update picking texture
        if picking_attachments.is_none() || (
            picking_attachments.as_ref().unwrap().0.get_width(),
            picking_attachments.as_ref().unwrap().0.get_height().unwrap()
        ) != target.get_dimensions() {
            let (width, height) = target.get_dimensions();
            picking_attachments = Some((
                glium::texture::UnsignedTexture2d::empty_with_format(
                    &display,
                    glium::texture::UncompressedUintFormat::U32,
                    glium::texture::MipmapsOption::NoMipmap,
                    width, height,
                ).unwrap(),
                glium::framebuffer::DepthRenderBuffer::new(
                    &display,
                    glium::texture::DepthFormat::F32,
                    width, height,
                ).unwrap()
            ))
        }

        // drawing the models and pass the picking texture
        if let Some((ref picking_texture, ref depth_buffer)) = picking_attachments {
            //clearing the picking texture
            picking_texture.main_level().first_layer().into_image(None).unwrap().raw_clear_buffer([0u32, 0, 0, 0]);

            let mut picking_target = glium::framebuffer::SimpleFrameBuffer::with_depth_buffer(&display, picking_texture, depth_buffer).unwrap();
            picking_target.clear_depth(1.0);
            picking_target.draw((&vertex_buffer, per_instance_buffer.per_instance().unwrap()),
                        &glium::index::NoIndices(glium::index::PrimitiveType::TrianglesList),
                        &picking_program, &uniforms, &params).unwrap();
        }
        target.draw((&vertex_buffer, per_instance_buffer.per_instance().unwrap()),
                    &glium::index::NoIndices(glium::index::PrimitiveType::TrianglesList),
                    &program, &uniforms, &params).unwrap();
        target.finish().unwrap();

        // committing into the picking pbo
        if let (Some(cursor), Some(&(ref picking_texture, _))) = (cursor_position, picking_attachments.as_ref()) {
            let read_target = glium::Rect {
                left: (cursor.0 - 1) as u32,
                bottom: picking_texture.get_height().unwrap() - std::cmp::max(cursor.1 - 1, 0) as u32,
                width: 1,
                height: 1,
            };

            if read_target.left < picking_texture.get_width()
            && read_target.bottom < picking_texture.get_height().unwrap() {
                picking_texture.main_level()
                    .first_layer()
                    .into_image(None).unwrap()
                    .raw_read_to_pixel_buffer(&read_target, &picking_pbo);
            } else {
                picking_pbo.write(&[0]);
            }
        } else {
            picking_pbo.write(&[0]);
        }

        // polling and handling the events received by the window
        for event in display.poll_events() {
            match event {
                glutin::Event::Closed => return support::Action::Stop,
                glutin::Event::MouseMoved(m) => cursor_position = Some(m),
                ev => camera.process_input(&ev),
            }
        }

        support::Action::Continue
    });
}
<commit_msg>examples/picking: trivial fix for MouseMoved API<commit_after>#[macro_use]
extern crate glium;

use glium::Surface;
use glium::glutin;

mod support;

#[derive(Copy, Clone, Debug)]
struct PerInstance {
    pub id: u32,
    pub w_position: (f32, f32, f32),
    pub color: (f32, f32, f32),
}
implement_vertex!(PerInstance, id, w_position, color);

fn main() {
    use glium::DisplayBuild;

    // building the display, ie. the main object
    let display = glutin::WindowBuilder::new()
        .with_depth_buffer(24)
        .build_glium()
        .unwrap();

    // building the vertex and index buffers
    let vertex_buffer = support::load_wavefront(&display, include_bytes!("support/teapot.obj"));

    // the program
    let program = program!(&display,
        140 => {
            vertex: "
                #version 140

                uniform mat4 persp_matrix;
                uniform mat4 view_matrix;

                in uint id;
                in vec3 w_position;
                in vec3 color;
                in vec3 position;
                in vec3 normal;
                out vec3 v_normal;
                out vec3 v_color;

                void main() {
                    v_normal = normal;
                    v_color = color;
                    gl_Position = persp_matrix * view_matrix * vec4(position * 0.005 + w_position, 1.0);
                }
            ",

            fragment: "
                #version 140

                in vec3 v_normal;
                in vec3 v_color;
                out vec4 f_color;

                const vec3 LIGHT = vec3(-0.2, 0.8, 0.1);

                void main() {
                    float lum = max(dot(normalize(v_normal), normalize(LIGHT)), 0.0);
                    vec3 color = (0.3 + 0.7 * lum) * v_color;
                    f_color = vec4(color, 1.0);
                }
            ",
        },
    ).unwrap();

    // the picking program
    let picking_program = program!(&display,
        140 => {
            vertex: "
                #version 140

                uniform mat4 persp_matrix;
                uniform mat4 view_matrix;

                in uint id;
                in vec3 w_position;
                in vec3 color;
                in vec3 position;
                in vec3 normal;
                flat out uint v_id;

                void main() {
                    v_id = id;
                    gl_Position = persp_matrix * view_matrix * vec4(position * 0.005 + w_position, 1.0);
                }
            ",

            fragment: "
                #version 140

                flat in uint v_id;
                out uint f_id;

                void main() {
                    f_id = v_id;
                }
            ",
        },
    ).unwrap();

    let mut camera = support::camera::CameraState::new();
    camera.set_position((0.0, 0.0, 1.5));
    camera.set_direction((0.0, 0.0, 1.0));

    //id's must be unique and != 0
    let mut per_instance = vec![
        PerInstance { id: 1, w_position: (-1.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
        PerInstance { id: 2, w_position: ( 0.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
        PerInstance { id: 3, w_position: ( 1.0, 0.0, 0.0), color: (1.0, 0.0, 0.0)},
    ];
    per_instance.sort_by(|a, b| a.id.cmp(&b.id));
    let original = per_instance.clone();

    let mut picking_attachments: Option<(glium::texture::UnsignedTexture2d, glium::framebuffer::DepthRenderBuffer)> = None;
    let picking_pbo: glium::texture::pixel_buffer::PixelBuffer<u32>
        = glium::texture::pixel_buffer::PixelBuffer::new_empty(&display, 1);

    let mut cursor_position: Option<(i32, i32)> = None;

    // the main loop
    support::start_loop(|| {
        camera.update();

        // determing which object has been picked at the previous frame
        let picked_object = {
            let data = picking_pbo.read().map(|d| d[0]).unwrap_or(0);
            if data != 0 {
                per_instance.binary_search_by(|x| x.id.cmp(&data)).ok()
            } else {
                None
            }
        };

        per_instance = original.clone();
        if let Some(index) = picked_object {
            per_instance[index as usize] = PerInstance {
                id: per_instance[index as usize].id,
                w_position: per_instance[index as usize].w_position,
                color: (0.0, 1.0, 0.0)
            };
        }

        // building the uniforms
        let uniforms = uniform! {
            persp_matrix: camera.get_perspective(),
            view_matrix: camera.get_view(),
        };

        // draw parameters
        let params = glium::DrawParameters {
            depth: glium::Depth {
                test: glium::DepthTest::IfLess,
                write: true,
                .. Default::default()
            },
            .. Default::default()
        };

        let per_instance_buffer = glium::vertex::VertexBuffer::new(&display, &per_instance).unwrap();

        // drawing a frame
        let mut target = display.draw();
        target.clear_color_and_depth((0.0, 0.0, 0.0, 0.0), 1.0);

        //update picking texture
        if picking_attachments.is_none() || (
            picking_attachments.as_ref().unwrap().0.get_width(),
            picking_attachments.as_ref().unwrap().0.get_height().unwrap()
        ) != target.get_dimensions() {
            let (width, height) = target.get_dimensions();
            picking_attachments = Some((
                glium::texture::UnsignedTexture2d::empty_with_format(
                    &display,
                    glium::texture::UncompressedUintFormat::U32,
                    glium::texture::MipmapsOption::NoMipmap,
                    width, height,
                ).unwrap(),
                glium::framebuffer::DepthRenderBuffer::new(
                    &display,
                    glium::texture::DepthFormat::F32,
                    width, height,
                ).unwrap()
            ))
        }

        // drawing the models and pass the picking texture
        if let Some((ref picking_texture, ref depth_buffer)) = picking_attachments {
            //clearing the picking texture
            picking_texture.main_level().first_layer().into_image(None).unwrap().raw_clear_buffer([0u32, 0, 0, 0]);

            let mut picking_target = glium::framebuffer::SimpleFrameBuffer::with_depth_buffer(&display, picking_texture, depth_buffer).unwrap();
            picking_target.clear_depth(1.0);
            picking_target.draw((&vertex_buffer, per_instance_buffer.per_instance().unwrap()),
                        &glium::index::NoIndices(glium::index::PrimitiveType::TrianglesList),
                        &picking_program, &uniforms, &params).unwrap();
        }
        target.draw((&vertex_buffer, per_instance_buffer.per_instance().unwrap()),
                    &glium::index::NoIndices(glium::index::PrimitiveType::TrianglesList),
                    &program, &uniforms, &params).unwrap();
        target.finish().unwrap();

        // committing into the picking pbo
        if let (Some(cursor), Some(&(ref picking_texture, _))) = (cursor_position, picking_attachments.as_ref()) {
            let read_target = glium::Rect {
                left: (cursor.0 - 1) as u32,
                bottom: picking_texture.get_height().unwrap() - std::cmp::max(cursor.1 - 1, 0) as u32,
                width: 1,
                height: 1,
            };

            if read_target.left < picking_texture.get_width()
            && read_target.bottom < picking_texture.get_height().unwrap() {
                picking_texture.main_level()
                    .first_layer()
                    .into_image(None).unwrap()
                    .raw_read_to_pixel_buffer(&read_target, &picking_pbo);
            } else {
                picking_pbo.write(&[0]);
            }
        } else {
            picking_pbo.write(&[0]);
        }

        // polling and handling the events received by the window
        for event in display.poll_events() {
            match event {
                glutin::Event::Closed => return support::Action::Stop,
                glutin::Event::MouseMoved(x,y) => cursor_position = Some((x,y)),
                ev => camera.process_input(&ev),
            }
        }

        support::Action::Continue
    });
}
<|endoftext|>


<commit_before><commit_msg>Remove some warnings<commit_after><|endoftext|>


<commit_before><commit_msg>Move documentation to appropriate place<commit_after><|endoftext|>


<commit_before><commit_msg>Simplify store debug print<commit_after><|endoftext|>


<commit_before><commit_msg>Remove GlobStoreIdIterator helper iterator type<commit_after><|endoftext|>


<commit_before><commit_msg>moving the closure<commit_after><|endoftext|>


<commit_before>// Copyright 2015 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 {Intrinsic, i, f, v};
use rustc::middle::ty;

macro_rules! p {
    ($name: expr, ($($inputs: tt),*) -> $output: tt) => {
        plain!(concat!("llvm.aarch64.neon.", $name), ($($inputs),*) -> $output)
    }
}
pub fn find<'tcx>(_tcx: &ty::ctxt<'tcx>, name: &str) -> Option<Intrinsic> {
    Some(match name {
        "vmaxvq_u8" => p!("umaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_u16" => p!("umaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_u32" => p!("umaxv.i32.v4i32", (i32x4) -> i32),

        "vmaxvq_s8" => p!("smaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_s16" => p!("smaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_s32" => p!("smaxv.i32.v4i32", (i32x4) -> i32),

        "vminvq_u8" => p!("uminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_u16" => p!("uminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_u32" => p!("uminv.i32.v4i32", (i32x4) -> i32),
        "vminvq_s8" => p!("sminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_s16" => p!("sminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_s32" => p!("sminv.i32.v4i32", (i32x4) -> i32),

        "vsqrtq_f32" => plain!("llvm.sqrt.v4f32", (f32x4) -> f32x4),
        "vsqrtq_f64" => plain!("llvm.sqrt.v2f64", (f64x2) -> f64x2),

        "vrsqrteq_f32" => p!("vrsqrte.v4f32", (f32x4) -> f32x4),
        "vrsqrteq_f64" => p!("vrsqrte.v2f64", (f64x2) -> f64x2),
        "vrecpeq_f32" => p!("vrecpe.v4f32", (f32x4) -> f32x4),
        "vrecpeq_f64" => p!("vrecpe.v2f64", (f64x2) -> f64x2),

        "vmaxq_f32" => p!("fmax.v4f32", (f32x4, f32x4) -> f32x4),
        "vmaxq_f64" => p!("fmax.v2f64", (f64x2, f64x2) -> f64x2),

        "vminq_f32" => p!("fmin.v4f32", (f32x4, f32x4) -> f32x4),
        "vminq_f64" => p!("fmin.v2f64", (f64x2, f64x2) -> f64x2),
        _ => return None,
    })
}
<commit_msg>Tweak aarch64 SIMD intrinsics.<commit_after>// Copyright 2015 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 {Intrinsic, i, f, v};
use rustc::middle::ty;

macro_rules! p {
    ($name: expr, ($($inputs: tt),*) -> $output: tt) => {
        plain!(concat!("llvm.aarch64.neon.", $name), ($($inputs),*) -> $output)
    }
}
pub fn find<'tcx>(_tcx: &ty::ctxt<'tcx>, name: &str) -> Option<Intrinsic> {
    Some(match name {
        "vmaxvq_u8" => p!("umaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_u16" => p!("umaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_u32" => p!("umaxv.i32.v4i32", (i32x4) -> i32),

        "vmaxvq_s8" => p!("smaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_s16" => p!("smaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_s32" => p!("smaxv.i32.v4i32", (i32x4) -> i32),

        "vminvq_u8" => p!("uminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_u16" => p!("uminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_u32" => p!("uminv.i32.v4i32", (i32x4) -> i32),
        "vminvq_s8" => p!("sminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_s16" => p!("sminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_s32" => p!("sminv.i32.v4i32", (i32x4) -> i32),

        "vsqrtq_f32" => plain!("llvm.sqrt.v4f32", (f32x4) -> f32x4),
        "vsqrtq_f64" => plain!("llvm.sqrt.v2f64", (f64x2) -> f64x2),

        "vrsqrteq_f32" => p!("frsqrte.v4f32", (f32x4) -> f32x4),
        "vrsqrteq_f64" => p!("frsqrte.v2f64", (f64x2) -> f64x2),
        "vrecpeq_f32" => p!("frecpe.v4f32", (f32x4) -> f32x4),
        "vrecpeq_f64" => p!("frecpe.v2f64", (f64x2) -> f64x2),

        "vmaxq_f32" => p!("fmax.v4f32", (f32x4, f32x4) -> f32x4),
        "vmaxq_f64" => p!("fmax.v2f64", (f64x2, f64x2) -> f64x2),

        "vminq_f32" => p!("fmin.v4f32", (f32x4, f32x4) -> f32x4),
        "vminq_f64" => p!("fmin.v2f64", (f64x2, f64x2) -> f64x2),

        "vqtbl1q_u8" => p!("tbl1.v16i8", (i8x16, i8x16) -> i8x16),
        "vqtbl1q_s8" => p!("tbl1.v16i8", (i8x16, i8x16) -> i8x16),
        _ => return None,
    })
}
<|endoftext|>


<commit_before>/// The representation of the installed toolchain and its components.
/// `Components` and `DirectoryPackage` are the two sides of the
/// installation / uninstallation process.

use rustup_utils::utils;
use prefix::InstallPrefix;
use errors::*;

use component::transaction::Transaction;
use component::package::{INSTALLER_VERSION, VERSION_FILE};

use std::path::{Path, PathBuf};
use std::fs::File;

const COMPONENTS_FILE: &'static str = "components";

#[derive(Clone, Debug)]
pub struct Components {
    prefix: InstallPrefix,
}

impl Components {
    pub fn open(prefix: InstallPrefix) -> Result<Self> {
        let c = Components { prefix: prefix };

        // Validate that the metadata uses a format we know
        if let Some(v) = try!(c.read_version()) {
            if v != INSTALLER_VERSION {
                return Err(ErrorKind::BadInstalledMetadataVersion(v).into());
            }
        }

        Ok(c)
    }
    fn rel_components_file(&self) -> PathBuf {
        self.prefix.rel_manifest_file(COMPONENTS_FILE)
    }
    fn rel_component_manifest(&self, name: &str) -> PathBuf {
        self.prefix.rel_manifest_file(&format!("manifest-{}", name))
    }
    fn read_version(&self) -> Result<Option<String>> {
        let p = self.prefix.manifest_file(VERSION_FILE);
        if utils::is_file(&p) {
            Ok(Some(try!(utils::read_file(VERSION_FILE, &p)).trim().to_string()))
        } else {
            Ok(None)
        }
    }
    fn write_version(&self, tx: &mut Transaction) -> Result<()> {
        try!(tx.modify_file(self.prefix.rel_manifest_file(VERSION_FILE)));
        try!(utils::write_file(VERSION_FILE,
                               &self.prefix.manifest_file(VERSION_FILE),
                               INSTALLER_VERSION));

        Ok(())
    }
    pub fn list(&self) -> Result<Vec<Component>> {
        let path = self.prefix.abs_path(self.rel_components_file());
        if !utils::is_file(&path) {
            return Ok(Vec::new());
        }
        let content = try!(utils::read_file("components", &path));
        Ok(content.lines()
                  .map(|s| {
                      Component {
                          components: self.clone(),
                          name: s.to_owned(),
                      }
                  })
                  .collect())
    }
    pub fn add<'a>(&self, name: &str, tx: Transaction<'a>) -> ComponentBuilder<'a> {
        ComponentBuilder {
            components: self.clone(),
            name: name.to_owned(),
            parts: Vec::new(),
            tx: tx,
        }
    }
    pub fn find(&self, name: &str) -> Result<Option<Component>> {
        let result = try!(self.list());
        Ok(result.into_iter().filter(|c| (c.name() == name)).next())
    }
    pub fn prefix(&self) -> InstallPrefix {
        self.prefix.clone()
    }
}

pub struct ComponentBuilder<'a> {
    components: Components,
    name: String,
    parts: Vec<ComponentPart>,
    tx: Transaction<'a>
}

impl<'a> ComponentBuilder<'a> {
    pub fn add_file(&mut self, path: PathBuf) -> Result<File> {
        self.parts.push(ComponentPart("file".to_owned(), path.clone()));
        self.tx.add_file(&self.name, path)
    }
    pub fn copy_file(&mut self, path: PathBuf, src: &Path) -> Result<()> {
        self.parts.push(ComponentPart("file".to_owned(), path.clone()));
        self.tx.copy_file(&self.name, path, src)
    }
    pub fn copy_dir(&mut self, path: PathBuf, src: &Path) -> Result<()> {
        self.parts.push(ComponentPart("dir".to_owned(), path.clone()));
        self.tx.copy_dir(&self.name, path, src)
    }

    pub fn finish(mut self) -> Result<Transaction<'a>> {
        // Write component manifest
        let path = self.components.rel_component_manifest(&self.name);
        let abs_path = self.components.prefix.abs_path(&path);
        let mut file = try!(self.tx.add_file(&self.name, path));
        for part in self.parts {
            // FIXME: This writes relative paths to the component manifest,
            // but rust-installer writes absolute paths.
            try!(utils::write_line("component", &mut file, &abs_path, &part.encode()));
        }

        // Add component to components file
        let path = self.components.rel_components_file();
        let abs_path = self.components.prefix.abs_path(&path);
        try!(self.tx.modify_file(path));
        try!(utils::append_file("components", &abs_path, &self.name));

        // Drop in the version file for future use
        try!(self.components.write_version(&mut self.tx));

        Ok(self.tx)
    }
}

#[derive(Debug)]
pub struct ComponentPart(pub String, pub PathBuf);

impl ComponentPart {
    pub fn encode(&self) -> String {
        format!("{}:{}", &self.0, &self.1.to_string_lossy())
    }
    pub fn decode(line: &str) -> Option<Self> {
        line.find(":")
            .map(|pos| ComponentPart(line[0..pos].to_owned(),
                                     PathBuf::from(&line[(pos + 1)..])))
    }
}

#[derive(Clone, Debug)]
pub struct Component {
    components: Components,
    name: String,
}

impl Component {
    pub fn manifest_name(&self) -> String {
        format!("manifest-{}", &self.name)
    }
    pub fn manifest_file(&self) -> PathBuf {
        self.components.prefix.manifest_file(&self.manifest_name())
    }
    pub fn rel_manifest_file(&self) -> PathBuf {
        self.components.prefix.rel_manifest_file(&self.manifest_name())
    }
    pub fn name(&self) -> &str {
        &self.name
    }
    pub fn parts(&self) -> Result<Vec<ComponentPart>> {
        let mut result = Vec::new();
        for line in try!(utils::read_file("component", &self.manifest_file())).lines() {
            result.push(try!(ComponentPart::decode(line)
                                 .ok_or_else(|| ErrorKind::CorruptComponent(self.name.clone()))));
        }
        Ok(result)
    }
    pub fn uninstall<'a>(&self, mut tx: Transaction<'a>) -> Result<Transaction<'a>> {
        // Update components file
        let path = self.components.rel_components_file();
        let abs_path = self.components.prefix.abs_path(&path);
        let temp = try!(tx.temp().new_file());
        try!(utils::filter_file("components", &abs_path, &temp, |l| (l != self.name)));
        try!(tx.modify_file(path));
        try!(utils::rename_file("components", &temp, &abs_path));

        // TODO: If this is the last component remove the components file
        // and the version file.

        // Remove parts
        for part in try!(self.parts()).into_iter().rev() {
            match &*part.0 {
                "file" => try!(tx.remove_file(&self.name, part.1)),
                "dir" => try!(tx.remove_dir(&self.name, part.1)),
                _ => return Err(ErrorKind::CorruptComponent(self.name.clone()).into()),
            }
        }

        // Remove component manifest
        try!(tx.remove_file(&self.name, self.rel_manifest_file()));

        Ok(tx)
    }
}
<commit_msg>Remove empty dirs after component uninstall<commit_after>/// The representation of the installed toolchain and its components.
/// `Components` and `DirectoryPackage` are the two sides of the
/// installation / uninstallation process.

use rustup_utils::utils;
use prefix::InstallPrefix;
use errors::*;

use component::transaction::Transaction;
use component::package::{INSTALLER_VERSION, VERSION_FILE};

use std::path::{Path, PathBuf};
use std::fs::File;

const COMPONENTS_FILE: &'static str = "components";

#[derive(Clone, Debug)]
pub struct Components {
    prefix: InstallPrefix,
}

impl Components {
    pub fn open(prefix: InstallPrefix) -> Result<Self> {
        let c = Components { prefix: prefix };

        // Validate that the metadata uses a format we know
        if let Some(v) = try!(c.read_version()) {
            if v != INSTALLER_VERSION {
                return Err(ErrorKind::BadInstalledMetadataVersion(v).into());
            }
        }

        Ok(c)
    }
    fn rel_components_file(&self) -> PathBuf {
        self.prefix.rel_manifest_file(COMPONENTS_FILE)
    }
    fn rel_component_manifest(&self, name: &str) -> PathBuf {
        self.prefix.rel_manifest_file(&format!("manifest-{}", name))
    }
    fn read_version(&self) -> Result<Option<String>> {
        let p = self.prefix.manifest_file(VERSION_FILE);
        if utils::is_file(&p) {
            Ok(Some(try!(utils::read_file(VERSION_FILE, &p)).trim().to_string()))
        } else {
            Ok(None)
        }
    }
    fn write_version(&self, tx: &mut Transaction) -> Result<()> {
        try!(tx.modify_file(self.prefix.rel_manifest_file(VERSION_FILE)));
        try!(utils::write_file(VERSION_FILE,
                               &self.prefix.manifest_file(VERSION_FILE),
                               INSTALLER_VERSION));

        Ok(())
    }
    pub fn list(&self) -> Result<Vec<Component>> {
        let path = self.prefix.abs_path(self.rel_components_file());
        if !utils::is_file(&path) {
            return Ok(Vec::new());
        }
        let content = try!(utils::read_file("components", &path));
        Ok(content.lines()
                  .map(|s| {
                      Component {
                          components: self.clone(),
                          name: s.to_owned(),
                      }
                  })
                  .collect())
    }
    pub fn add<'a>(&self, name: &str, tx: Transaction<'a>) -> ComponentBuilder<'a> {
        ComponentBuilder {
            components: self.clone(),
            name: name.to_owned(),
            parts: Vec::new(),
            tx: tx,
        }
    }
    pub fn find(&self, name: &str) -> Result<Option<Component>> {
        let result = try!(self.list());
        Ok(result.into_iter().filter(|c| (c.name() == name)).next())
    }
    pub fn prefix(&self) -> InstallPrefix {
        self.prefix.clone()
    }
}

pub struct ComponentBuilder<'a> {
    components: Components,
    name: String,
    parts: Vec<ComponentPart>,
    tx: Transaction<'a>
}

impl<'a> ComponentBuilder<'a> {
    pub fn add_file(&mut self, path: PathBuf) -> Result<File> {
        self.parts.push(ComponentPart("file".to_owned(), path.clone()));
        self.tx.add_file(&self.name, path)
    }
    pub fn copy_file(&mut self, path: PathBuf, src: &Path) -> Result<()> {
        self.parts.push(ComponentPart("file".to_owned(), path.clone()));
        self.tx.copy_file(&self.name, path, src)
    }
    pub fn copy_dir(&mut self, path: PathBuf, src: &Path) -> Result<()> {
        self.parts.push(ComponentPart("dir".to_owned(), path.clone()));
        self.tx.copy_dir(&self.name, path, src)
    }

    pub fn finish(mut self) -> Result<Transaction<'a>> {
        // Write component manifest
        let path = self.components.rel_component_manifest(&self.name);
        let abs_path = self.components.prefix.abs_path(&path);
        let mut file = try!(self.tx.add_file(&self.name, path));
        for part in self.parts {
            // FIXME: This writes relative paths to the component manifest,
            // but rust-installer writes absolute paths.
            try!(utils::write_line("component", &mut file, &abs_path, &part.encode()));
        }

        // Add component to components file
        let path = self.components.rel_components_file();
        let abs_path = self.components.prefix.abs_path(&path);
        try!(self.tx.modify_file(path));
        try!(utils::append_file("components", &abs_path, &self.name));

        // Drop in the version file for future use
        try!(self.components.write_version(&mut self.tx));

        Ok(self.tx)
    }
}

#[derive(Debug)]
pub struct ComponentPart(pub String, pub PathBuf);

impl ComponentPart {
    pub fn encode(&self) -> String {
        format!("{}:{}", &self.0, &self.1.to_string_lossy())
    }
    pub fn decode(line: &str) -> Option<Self> {
        line.find(":")
            .map(|pos| ComponentPart(line[0..pos].to_owned(),
                                     PathBuf::from(&line[(pos + 1)..])))
    }
}

#[derive(Clone, Debug)]
pub struct Component {
    components: Components,
    name: String,
}

impl Component {
    pub fn manifest_name(&self) -> String {
        format!("manifest-{}", &self.name)
    }
    pub fn manifest_file(&self) -> PathBuf {
        self.components.prefix.manifest_file(&self.manifest_name())
    }
    pub fn rel_manifest_file(&self) -> PathBuf {
        self.components.prefix.rel_manifest_file(&self.manifest_name())
    }
    pub fn name(&self) -> &str {
        &self.name
    }
    pub fn parts(&self) -> Result<Vec<ComponentPart>> {
        let mut result = Vec::new();
        for line in try!(utils::read_file("component", &self.manifest_file())).lines() {
            result.push(try!(ComponentPart::decode(line)
                                 .ok_or_else(|| ErrorKind::CorruptComponent(self.name.clone()))));
        }
        Ok(result)
    }
    pub fn uninstall<'a>(&self, mut tx: Transaction<'a>) -> Result<Transaction<'a>> {
        // Update components file
        let path = self.components.rel_components_file();
        let abs_path = self.components.prefix.abs_path(&path);
        let temp = try!(tx.temp().new_file());
        try!(utils::filter_file("components", &abs_path, &temp, |l| (l != self.name)));
        try!(tx.modify_file(path));
        try!(utils::rename_file("components", &temp, &abs_path));

        // TODO: If this is the last component remove the components file
        // and the version file.

        // Track visited directories
        use std::collections::HashSet;
        use std::collections::hash_set::IntoIter;
        use std::fs::read_dir;

        // dirs will contain the set of longest disjoint directory paths seen
        // ancestors help in filtering seen paths and constructing dirs
        // All seen paths must be relative to avoid surprises
        struct PruneSet {
            dirs: HashSet<PathBuf>,
            ancestors: HashSet<PathBuf>,
            prefix: PathBuf,
        }

        impl PruneSet {
            fn seen(&mut self, mut path: PathBuf) {
                if !path.is_relative() || !path.pop() {
                    return;
                }
                if self.dirs.contains(&path) || self.ancestors.contains(&path) {
                    return;
                }
                self.dirs.insert(path.clone());
                while path.pop() {
                    if path.file_name().is_none() {
			break;
		    }
		    if self.dirs.contains(&path) {
			self.dirs.remove(&path);
		    }
		    if self.ancestors.contains(&path) {
			break;
		    }
		    self.ancestors.insert(path.clone());
                }
            }
        }

        struct PruneIter {
            iter: IntoIter<PathBuf>,
            path_buf: Option<PathBuf>,
            prefix: PathBuf,
        }

        impl IntoIterator for PruneSet {
            type Item = PathBuf;
            type IntoIter = PruneIter;

            fn into_iter(self) -> Self::IntoIter {
                PruneIter {
                    iter: self.dirs.into_iter(),
                    path_buf: None,
                    prefix: self.prefix,
                }
            }
        }

        // Returns only empty directories
        impl Iterator for PruneIter {
            type Item = PathBuf;

            fn next(&mut self) -> Option<Self::Item> {
                self.path_buf = match self.path_buf {
                    None => self.iter.next(),
                    Some(_) => {
                        let mut path_buf = self.path_buf.take().unwrap();
                        match path_buf.file_name() {
                            Some(_) => if path_buf.pop() { Some(path_buf) } else { None },
                            None => self.iter.next(),
                        }
                    },
                };
                if self.path_buf.is_none() {
                    return None;
                }
                let full_path = self.prefix.join(self.path_buf.as_ref().unwrap());
                let empty = match read_dir(full_path) {
                    Ok(dir) => dir.count() == 0,
                    Err(_) => false,
                };
                if empty {
                    self.path_buf.clone()
                } else {
                    self.next()
                }
            }
        }

        // Remove parts
        let mut pset = PruneSet {
            dirs: HashSet::new(),
            ancestors: HashSet::new(),
            prefix: self.components.prefix.abs_path(""),
        };
        for part in try!(self.parts()).into_iter().rev() {
            match &*part.0 {
                "file" => {
                    try!(tx.remove_file(&self.name, part.1.clone()));
                    pset.seen(part.1);
                },
                "dir" => {
                    try!(tx.remove_dir(&self.name, part.1.clone()));
                    pset.seen(part.1);
                },
                _ => return Err(ErrorKind::CorruptComponent(self.name.clone()).into()),
            }
        }
        for empty_dir in pset {
            try!(tx.remove_dir(&self.name, empty_dir));
        }

        // Remove component manifest
        try!(tx.remove_file(&self.name, self.rel_manifest_file()));

        Ok(tx)
    }
}
<|endoftext|>


<commit_before><commit_msg>rustc: Add a test case for previous commit<commit_after>tag opt[T] {
    none;
}

fn main() {
    auto x = none[int];
    alt (x) {
        case (none[int]) { log "hello world"; }
    }
}

<|endoftext|>


<commit_before><commit_msg>Add Breadth-First Search using The Rust Programming Language<commit_after>use std::io::stdin;
use std::collections::VecDeque;

// DFS receives a graph and the start point
fn bfs(graph: &mut Vec<Vec<usize>>, start: usize) {
    let mut visited: Vec<bool> = Vec::new();
    visited.resize(graph.len(), false);

    let mut queue = VecDeque::new();
    visited[start] = true;
    queue.push_back(start);

    while !queue.is_empty() {
        let node = queue.pop_front().unwrap();
        println!("{}", node);

        let adj_list = &graph[node];
        for neighbor in adj_list {
            if !visited[*neighbor] {
                visited[*neighbor] = true;
                queue.push_back(*neighbor);
            }
        }
    }
}

fn add_edge(graph: &mut Vec<Vec<usize>>, u: usize, v: usize) {
    graph[u].push(v);
}

fn main() {
    let mut edges: usize;
    let mut graph: Vec<Vec<usize>> = Vec::new();
    graph.resize(100, vec![]);

    // Read number of edges from user
    let mut input: String = String::new();
    stdin().read_line(&mut input).unwrap();
    edges = input.trim().parse::<u32>().unwrap() as usize;

    while edges > 0 {
        let u: usize;
        let v: usize;

        // Read u and v by splitting input into words and reading the first words found
        let mut input: String = String::new();
        stdin().read_line(&mut input).unwrap();
        let mut words = input.split_whitespace();
        u = words.next().unwrap().parse::<u32>().unwrap() as usize;
        v = words.next().unwrap().parse::<u32>().unwrap() as usize;

        add_edge(&mut graph, u, v);

        edges = edges - 1;
    }

    let start: usize;
    let mut input: String = String::new();
    stdin().read_line(&mut input).unwrap();
    start = input.trim().parse::<u32>().unwrap() as usize;

    bfs(&mut graph, start);
}

#[test]
fn test_bfs_with_graph() {
    let mut graph: Vec<Vec<usize>> = Vec::new();
    graph.resize(4, vec![]);

    add_edge(&mut graph, 0, 1);
    add_edge(&mut graph, 0, 2);
    add_edge(&mut graph, 1, 2);
    add_edge(&mut graph, 2, 0);
    add_edge(&mut graph, 2, 3);
    add_edge(&mut graph, 3, 3);

    println!("BFS Starting from vertex 2");

    bfs(&mut graph, 2);
}
<|endoftext|>


<commit_before><commit_msg>Default impl on Packed<commit_after><|endoftext|>


<commit_before>// Copyright 2012-2013 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 ast;
use codemap;
use codemap::{Pos, Span};
use codemap::{ExpnInfo, NameAndSpan};
use ext::base::*;
use ext::base;
use ext::build::AstBuilder;
use parse;
use parse::token::{get_ident_interner};
use print::pprust;

use std::io;
use std::io::File;
use std::str;

// These macros all relate to the file system; they either return
// the column/row/filename of the expression, or they include
// a given file into the current one.

/* line!(): expands to the current line number */
pub fn expand_line(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "line!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);

    base::MRExpr(cx.expr_uint(topmost.call_site, loc.line))
}

/* col!(): expands to the current column number */
pub fn expand_col(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "col!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);
    base::MRExpr(cx.expr_uint(topmost.call_site, loc.col.to_uint()))
}

/* file!(): expands to the current filename */
/* The filemap (`loc.file`) contains a bunch more information we could spit
 * out if we wanted. */
pub fn expand_file(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "file!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);
    let filename = loc.file.name;
    base::MRExpr(cx.expr_str(topmost.call_site, filename))
}

pub fn expand_stringify(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let s = pprust::tts_to_str(tts, get_ident_interner());
    base::MRExpr(cx.expr_str(sp, s.to_managed()))
}

pub fn expand_mod(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "module_path!");
    base::MRExpr(cx.expr_str(sp,
                             cx.mod_path().map(|x| cx.str_of(*x)).connect("::").to_managed()))
}

// include! : parse the given file as an expr
// This is generally a bad idea because it's going to behave
// unhygienically.
pub fn expand_include(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let file = get_single_str_from_tts(cx, sp, tts, "include!");
    let p = parse::new_sub_parser_from_file(
        cx.parse_sess(), cx.cfg(),
        &res_rel_file(cx, sp, &Path::new(file)), sp);
    base::MRExpr(p.parse_expr())
}

// include_str! : read the given file, insert it as a literal string expr
pub fn expand_include_str(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let file = get_single_str_from_tts(cx, sp, tts, "include_str!");
    let file = res_rel_file(cx, sp, &Path::new(file));
    let bytes = match io::result(|| File::open(&file).read_to_end()) {
        Err(e) => {
            cx.span_fatal(sp, format!("couldn't read {}: {}",
                                      file.display(), e.desc));
        }
        Ok(bytes) => bytes,
    };
    match str::from_utf8_owned_opt(bytes) {
        Some(s) => base::MRExpr(cx.expr_str(sp, s.to_managed())),
        None => {
            cx.span_fatal(sp, format!("{} wasn't a utf-8 file", file.display()));
        }
    }
}

pub fn expand_include_bin(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
        -> base::MacResult
{
    use std::at_vec;

    let file = get_single_str_from_tts(cx, sp, tts, "include_bin!");
    let file = res_rel_file(cx, sp, &Path::new(file));
    match io::result(|| File::open(&file).read_to_end()) {
        Err(e) => {
            cx.span_fatal(sp, format!("couldn't read {}: {}",
                                      file.display(), e.desc));
        }
        Ok(bytes) => {
            let bytes = at_vec::to_managed_move(bytes);
            base::MRExpr(cx.expr_lit(sp, ast::lit_binary(bytes)))
        }
    }
}

// recur along an ExpnInfo chain to find the original expression
fn topmost_expn_info(expn_info: @codemap::ExpnInfo) -> @codemap::ExpnInfo {
    match *expn_info {
        ExpnInfo { call_site: ref call_site, .. } => {
            match call_site.expn_info {
                Some(next_expn_info) => {
                    match *next_expn_info {
                        ExpnInfo {
                            callee: NameAndSpan { name: ref name, .. },
                            ..
                        } => {
                            // Don't recurse into file using "include!"
                            if "include" == *name  {
                                expn_info
                            } else {
                                topmost_expn_info(next_expn_info)
                            }
                        }
                    }
                },
                None => expn_info
            }
        }
    }
}

// resolve a file-system path to an absolute file-system path (if it
// isn't already)
fn res_rel_file(cx: @ExtCtxt, sp: codemap::Span, arg: &Path) -> Path {
    // NB: relative paths are resolved relative to the compilation unit
    if !arg.is_absolute() {
        let mut cu = Path::new(cx.codemap().span_to_filename(sp));
        cu.pop();
        cu.push(arg);
        cu
    } else {
        arg.clone()
    }
}
<commit_msg>Fix missing code map entry for uses of `include_str!`.<commit_after>// Copyright 2012-2013 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 ast;
use codemap;
use codemap::{Pos, Span};
use codemap::{ExpnInfo, NameAndSpan};
use ext::base::*;
use ext::base;
use ext::build::AstBuilder;
use parse;
use parse::token::{get_ident_interner};
use print::pprust;

use std::io;
use std::io::File;
use std::str;

// These macros all relate to the file system; they either return
// the column/row/filename of the expression, or they include
// a given file into the current one.

/* line!(): expands to the current line number */
pub fn expand_line(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "line!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);

    base::MRExpr(cx.expr_uint(topmost.call_site, loc.line))
}

/* col!(): expands to the current column number */
pub fn expand_col(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "col!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);
    base::MRExpr(cx.expr_uint(topmost.call_site, loc.col.to_uint()))
}

/* file!(): expands to the current filename */
/* The filemap (`loc.file`) contains a bunch more information we could spit
 * out if we wanted. */
pub fn expand_file(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "file!");

    let topmost = topmost_expn_info(cx.backtrace().unwrap());
    let loc = cx.codemap().lookup_char_pos(topmost.call_site.lo);
    let filename = loc.file.name;
    base::MRExpr(cx.expr_str(topmost.call_site, filename))
}

pub fn expand_stringify(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let s = pprust::tts_to_str(tts, get_ident_interner());
    base::MRExpr(cx.expr_str(sp, s.to_managed()))
}

pub fn expand_mod(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    base::check_zero_tts(cx, sp, tts, "module_path!");
    base::MRExpr(cx.expr_str(sp,
                             cx.mod_path().map(|x| cx.str_of(*x)).connect("::").to_managed()))
}

// include! : parse the given file as an expr
// This is generally a bad idea because it's going to behave
// unhygienically.
pub fn expand_include(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let file = get_single_str_from_tts(cx, sp, tts, "include!");
    // The file will be added to the code map by the parser
    let p = parse::new_sub_parser_from_file(
        cx.parse_sess(), cx.cfg(),
        &res_rel_file(cx, sp, &Path::new(file)), sp);
    base::MRExpr(p.parse_expr())
}

// include_str! : read the given file, insert it as a literal string expr
pub fn expand_include_str(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
    -> base::MacResult {
    let file = get_single_str_from_tts(cx, sp, tts, "include_str!");
    let file = res_rel_file(cx, sp, &Path::new(file));
    let bytes = match io::result(|| File::open(&file).read_to_end()) {
        Err(e) => {
            cx.span_fatal(sp, format!("couldn't read {}: {}",
                                      file.display(), e.desc));
        }
        Ok(bytes) => bytes,
    };
    match str::from_utf8_owned_opt(bytes) {
        Some(s) => {
            let s = s.to_managed();
            // Add this input file to the code map to make it available as
            // dependency information
            cx.parse_sess.cm.files.push(@codemap::FileMap {
                name: file.display().to_str().to_managed(),
                substr: codemap::FssNone,
                src: s,
                start_pos: codemap::BytePos(0),
                lines: @mut ~[],
                multibyte_chars: @mut ~[],
            });
            base::MRExpr(cx.expr_str(sp, s))
        }
        None => {
            cx.span_fatal(sp, format!("{} wasn't a utf-8 file", file.display()));
        }
    }
}

pub fn expand_include_bin(cx: @ExtCtxt, sp: Span, tts: &[ast::token_tree])
        -> base::MacResult
{
    use std::at_vec;

    let file = get_single_str_from_tts(cx, sp, tts, "include_bin!");
    let file = res_rel_file(cx, sp, &Path::new(file));
    match io::result(|| File::open(&file).read_to_end()) {
        Err(e) => {
            cx.span_fatal(sp, format!("couldn't read {}: {}",
                                      file.display(), e.desc));
        }
        Ok(bytes) => {
            let bytes = at_vec::to_managed_move(bytes);
            base::MRExpr(cx.expr_lit(sp, ast::lit_binary(bytes)))
        }
    }
}

// recur along an ExpnInfo chain to find the original expression
fn topmost_expn_info(expn_info: @codemap::ExpnInfo) -> @codemap::ExpnInfo {
    match *expn_info {
        ExpnInfo { call_site: ref call_site, .. } => {
            match call_site.expn_info {
                Some(next_expn_info) => {
                    match *next_expn_info {
                        ExpnInfo {
                            callee: NameAndSpan { name: ref name, .. },
                            ..
                        } => {
                            // Don't recurse into file using "include!"
                            if "include" == *name  {
                                expn_info
                            } else {
                                topmost_expn_info(next_expn_info)
                            }
                        }
                    }
                },
                None => expn_info
            }
        }
    }
}

// resolve a file-system path to an absolute file-system path (if it
// isn't already)
fn res_rel_file(cx: @ExtCtxt, sp: codemap::Span, arg: &Path) -> Path {
    // NB: relative paths are resolved relative to the compilation unit
    if !arg.is_absolute() {
        let mut cu = Path::new(cx.codemap().span_to_filename(sp));
        cu.pop();
        cu.push(arg);
        cu
    } else {
        arg.clone()
    }
}
<|endoftext|>


<commit_before><commit_msg>Reading body correctly<commit_after><|endoftext|>


<commit_before>// Copyright 2015 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 {Intrinsic, i, f, v};
use rustc::middle::ty;

macro_rules! p {
    ($name: expr, ($($inputs: tt),*) -> $output: tt) => {
        plain!(concat!("llvm.aarch64.neon.", $name), ($($inputs),*) -> $output)
    }
}
pub fn find<'tcx>(_tcx: &ty::ctxt<'tcx>, name: &str) -> Option<Intrinsic> {
    Some(match name {
        "vmaxvq_u8" => p!("umaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_u16" => p!("umaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_u32" => p!("umaxv.i32.v4i32", (i32x4) -> i32),

        "vmaxvq_s8" => p!("smaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_s16" => p!("smaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_s32" => p!("smaxv.i32.v4i32", (i32x4) -> i32),

        "vminvq_u8" => p!("uminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_u16" => p!("uminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_u32" => p!("uminv.i32.v4i32", (i32x4) -> i32),
        "vminvq_s8" => p!("sminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_s16" => p!("sminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_s32" => p!("sminv.i32.v4i32", (i32x4) -> i32),

        "vsqrtq_f32" => plain!("llvm.sqrt.v4f32", (f32x4) -> f32x4),
        "vsqrtq_f64" => plain!("llvm.sqrt.v2f64", (f64x2) -> f64x2),

        "vrsqrteq_f32" => p!("vrsqrte.v4f32", (f32x4) -> f32x4),
        "vrsqrteq_f64" => p!("vrsqrte.v2f64", (f64x2) -> f64x2),
        "vrecpeq_f32" => p!("vrecpe.v4f32", (f32x4) -> f32x4),
        "vrecpeq_f64" => p!("vrecpe.v2f64", (f64x2) -> f64x2),

        "vmaxq_f32" => p!("fmax.v4f32", (f32x4, f32x4) -> f32x4),
        "vmaxq_f64" => p!("fmax.v2f64", (f64x2, f64x2) -> f64x2),

        "vminq_f32" => p!("fmin.v4f32", (f32x4, f32x4) -> f32x4),
        "vminq_f64" => p!("fmin.v2f64", (f64x2, f64x2) -> f64x2),
        _ => return None,
    })
}
<commit_msg>Auto merge of #27907 - huonw:simd, r=alexcrichton<commit_after>// Copyright 2015 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 {Intrinsic, i, f, v};
use rustc::middle::ty;

macro_rules! p {
    ($name: expr, ($($inputs: tt),*) -> $output: tt) => {
        plain!(concat!("llvm.aarch64.neon.", $name), ($($inputs),*) -> $output)
    }
}
pub fn find<'tcx>(_tcx: &ty::ctxt<'tcx>, name: &str) -> Option<Intrinsic> {
    Some(match name {
        "vmaxvq_u8" => p!("umaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_u16" => p!("umaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_u32" => p!("umaxv.i32.v4i32", (i32x4) -> i32),

        "vmaxvq_s8" => p!("smaxv.i8.v16i8", (i8x16) -> i8),
        "vmaxvq_s16" => p!("smaxv.i16.v8i16", (i16x8) -> i16),
        "vmaxvq_s32" => p!("smaxv.i32.v4i32", (i32x4) -> i32),

        "vminvq_u8" => p!("uminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_u16" => p!("uminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_u32" => p!("uminv.i32.v4i32", (i32x4) -> i32),
        "vminvq_s8" => p!("sminv.i8.v16i8", (i8x16) -> i8),
        "vminvq_s16" => p!("sminv.i16.v8i16", (i16x8) -> i16),
        "vminvq_s32" => p!("sminv.i32.v4i32", (i32x4) -> i32),

        "vsqrtq_f32" => plain!("llvm.sqrt.v4f32", (f32x4) -> f32x4),
        "vsqrtq_f64" => plain!("llvm.sqrt.v2f64", (f64x2) -> f64x2),

        "vrsqrteq_f32" => p!("frsqrte.v4f32", (f32x4) -> f32x4),
        "vrsqrteq_f64" => p!("frsqrte.v2f64", (f64x2) -> f64x2),
        "vrecpeq_f32" => p!("frecpe.v4f32", (f32x4) -> f32x4),
        "vrecpeq_f64" => p!("frecpe.v2f64", (f64x2) -> f64x2),

        "vmaxq_f32" => p!("fmax.v4f32", (f32x4, f32x4) -> f32x4),
        "vmaxq_f64" => p!("fmax.v2f64", (f64x2, f64x2) -> f64x2),

        "vminq_f32" => p!("fmin.v4f32", (f32x4, f32x4) -> f32x4),
        "vminq_f64" => p!("fmin.v2f64", (f64x2, f64x2) -> f64x2),

        "vqtbl1q_u8" => p!("tbl1.v16i8", (i8x16, i8x16) -> i8x16),
        "vqtbl1q_s8" => p!("tbl1.v16i8", (i8x16, i8x16) -> i8x16),
        _ => return None,
    })
}
<|endoftext|>


<commit_before><commit_msg>Added Rule 110 example<commit_after>/*

Rule 110 is a simple cellular automaton that is universal.

The problem is to find the reverse history from a final state,
up to a limited number of iterations.

*/

extern crate quickbacktrack;

use quickbacktrack::{BackTrackSolver, Puzzle, SolveSettings};

#[derive(Clone)]
pub struct Rule110 {
	pub cells: Vec<Vec<u8>>,
}

impl Rule110 {
    pub fn next(&mut self) -> Vec<u8> {
        let last = self.cells.last().unwrap();
        let n = last.len();
        let mut new_row = vec![0; n];
        for i in 0..n {
            let input = (
                if i > 0 { last[(i + n - 1)%n] } else { 1 },
                last[i],
                if i + 1 < n { last[i + 1] } else { 1 }
            );
            new_row[i] = rule(input);
        }
        new_row
    }

    /// Returns `false` when a contradition is found.
    /// This is checked by checking all affected cells in next step.
    pub fn is_satisfied(&self, pos: [usize; 2], val: u8) -> bool {
        let row = pos[0];
        let col = pos[1] as isize;

        if row + 1 < self.cells.len() {
            // Replace with new value if looking up cell at the location.
            let f = |ind: isize| {
                if ind < 0 { return 1; }
                if ind >= self.cells[row].len() as isize { 1 }
                else if ind == col { val }
                else { self.cells[row][ind as usize] }
            };
            for i in -1..2 {
                // Skip output cells at the edges.
                if col + i <= 0 ||
                   col + i >= self.cells[row].len() as isize {
                    continue;
                }

                let input = (
                    f(col + i - 1),
                    f(col + i),
                    f(col + i + 1),
                );

                let new_value = rule(input);
                let old_value = self.cells[row + 1][(col + i) as usize];
                match (new_value, old_value) {
                    (_, 0) => {}
                    (0, _) => {}
                    (a, b) if a == b => {}
                    (_, _) => return false,
                }
            }
        }

        // Check that previous row yields value.
        if row > 0 {
            let f = |ind: isize| {
                if ind < 0 { return 1; }
                if ind >= self.cells[row - 1].len() as isize { 1 }
                else { self.cells[row - 1][ind as usize] }
            };
            let input = (
                f(col - 1),
                f(col),
                f(col + 1),
            );
            match (rule(input), val) {
                (_, 0) => {}
                (0, _) => {}
                (a, b) if a == b => {}
                (_, _) => return false,
            }
        }

        true
    }

    pub fn possible(&self, pos: [usize; 2]) -> Vec<u8> {
        let mut res = vec![];
        for v in 1..3 {
            if self.is_satisfied(pos, v) {
                res.push(v);
            }
        }
        res
    }

    pub fn find_min_empty(&self) -> Option<[usize; 2]> {
        let mut min = None;
        let mut min_pos = None;
        for i in 0..self.cells.len() {
            for j in 0..self.cells[i].len() {
                if self.cells[i][j] == 0 {
                    let possible = self.possible([i, j]);
                    if min.is_none() || min.unwrap() >= possible.len() {
                        min = Some(possible.len());
                        min_pos = Some([i, j]);
                    }
                }
            }
        }
        return min_pos;
    }
}

/// Rule 110 extended with unknown inputs.
fn rule(state: (u8, u8, u8)) -> u8 {
    match state {
        (2, 2, 2) => 1,
        (2, 2, 1) => 2,
        (2, 1, 2) => 2,
        (2, 1, 1) => 1,
        (1, 2, 2) => 2,
        (1, 2, 1) => 2,
        (1, 1, 2) => 2,
        (1, 1, 1) => 1,

        // 1 unknown.
        (2, 2, 0) => 0,
        (2, 0, 2) => 0,
        (0, 2, 2) => 0,
        (2, 0, 1) => 0,
        (0, 2, 1) => 2,
        (2, 1, 0) => 0,
        (0, 1, 2) => 2,
        (0, 1, 1) => 1,
        (1, 2, 0) => 2,
        (1, 0, 2) => 2,
        (1, 0, 1) => 0,
        (1, 1, 0) => 0,

        // All with 2 unknowns or more has unknown result.
        (_, _, _) => 0,
    }
}

impl Puzzle for Rule110 {
    type Pos = [usize; 2];
    type Val = u8;

    fn solve_simple(&mut self) {}

    fn set(&mut self, pos: [usize; 2], val: u8) {
        self.cells[pos[0]][pos[1]] = val;
    }

    fn is_solved(&self) -> bool {
        for row in &self.cells {
            for col in row {
                if *col == 0 { return false; }
            }
        }
        true
    }

    fn remove(&mut self, other: &Rule110) {
        for i in 0..self.cells.len() {
            for j in 0..self.cells[i].len() {
                if other.cells[i][j] != 0 {
                    self.cells[i][j] = 0;
                }
            }
        }
    }

    fn print(&self) {
        println!("");
        for row in &self.cells {
            for cell in row {
                if *cell == 2 { print!("x"); }
                else if *cell == 1 { print!("_"); }
                else { print!(" "); }
            }
            println!("")
        }
        println!("");
    }
}

fn main() {
    /*
    let mut r = Rule110 {
        cells: vec![
            // _xx__xxxx_xx__x
            vec![1, 2, 2, 1, 1, 2, 2, 2, 2, 1, 2, 2, 1, 1, 2]
        ]
    };
    let next = r.next();
    r.cells.push(next);
    r.print();
    return;
    */

    let x = Rule110 {
        cells: vec![
            vec![0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            vec![0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            vec![0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
            vec![2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2],
        ]
    };
    // println!("{}", x.is_satisfied([0, 1], 2));

    let settings = SolveSettings::new()
		.solve_simple(false)
		.debug(false)
		.difference(false)
		.sleep_ms(50)
	;
    let solver = BackTrackSolver::new(x, settings);
    let difference = solver.solve(|s| s.find_min_empty(), |s, p| s.possible(p))
		.expect("Expected solution").puzzle;
	println!("Solution:");
	difference.print();
    println!("{}\n{:?}", difference.cells.len(),
        difference.cells[2]);
}

pub fn example1() -> Rule110 {
    Rule110 {
        cells: vec![
            vec![1, 1, 1, 2, 1],
            vec![1, 0, 0, 0, 1],
            vec![1, 0, 0, 0, 1],
            vec![2, 2, 1, 2, 1],
        ]
    }
}

pub fn example2() -> Rule110 {
    Rule110 {
        cells: vec![
            vec![1, 1, 0, 0, 0],
            vec![0, 0, 0, 0, 0],
            vec![0, 0, 0, 0, 0],
            vec![2, 2, 1, 2, 1],
        ]
    }
}
<|endoftext|>


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

// compile-flags:-Z extra-debug-info
// debugger:rbreak zzz
// debugger:run
// debugger:finish
// debugger:whatis unit
// check:type = ()
// debugger:whatis b
// check:type = bool
// debugger:whatis i
// check:type = int
// debugger:whatis c
// check:type = char
// debugger:whatis i8
// check:type = i8
// debugger:whatis i16
// check:type = i16
// debugger:whatis i32
// check:type = i32
// debugger:whatis i64
// check:type = i64
// debugger:whatis u
// check:type = uint
// debugger:whatis u8
// check:type = u8
// debugger:whatis u16
// check:type = u16
// debugger:whatis u32
// check:type = u32
// debugger:whatis u64
// check:type = u64
// debugger:whatis f32
// check:type = f32
// debugger:whatis f64
// check:type = f64
// debugger:info functions _yyy
// check:[...]
// check:! basic-types-metadata::_yyy()();
// debugger:detach
// debugger:quit

#[allow(unused_variable)];

fn main() {
    let unit: () = ();
    let b: bool = false;
    let i: int = -1;
    let c: char = 'a';
    let i8: i8 = 68;
    let i16: i16 = -16;
    let i32: i32 = -32;
    let i64: i64 = -64;
    let u: uint = 1;
    let u8: u8 = 100;
    let u16: u16 = 16;
    let u32: u32 = 32;
    let u64: u64 = 64;
    let f32: f32 = 2.5;
    let f64: f64 = 3.5;
    _zzz();
}

fn _zzz() {()}
fn _yyy() -> ! {fail!()}
<commit_msg>Relax the constraints on a debuginfo test<commit_after>// Copyright 2013 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.

// compile-flags:-Z extra-debug-info
// debugger:rbreak zzz
// debugger:run
// debugger:finish
// debugger:whatis unit
// check:type = ()
// debugger:whatis b
// check:type = bool
// debugger:whatis i
// check:type = int
// debugger:whatis c
// check:type = char
// debugger:whatis i8
// check:type = i8
// debugger:whatis i16
// check:type = i16
// debugger:whatis i32
// check:type = i32
// debugger:whatis i64
// check:type = i64
// debugger:whatis u
// check:type = uint
// debugger:whatis u8
// check:type = u8
// debugger:whatis u16
// check:type = u16
// debugger:whatis u32
// check:type = u32
// debugger:whatis u64
// check:type = u64
// debugger:whatis f32
// check:type = f32
// debugger:whatis f64
// check:type = f64
// debugger:info functions _yyy
// check:[...]
// check:![...]_yyy()();
// debugger:detach
// debugger:quit

#[allow(unused_variable)];

fn main() {
    let unit: () = ();
    let b: bool = false;
    let i: int = -1;
    let c: char = 'a';
    let i8: i8 = 68;
    let i16: i16 = -16;
    let i32: i32 = -32;
    let i64: i64 = -64;
    let u: uint = 1;
    let u8: u8 = 100;
    let u16: u16 = 16;
    let u32: u32 = 32;
    let u64: u64 = 64;
    let f32: f32 = 2.5;
    let f64: f64 = 3.5;
    _zzz();
}

fn _zzz() {()}
fn _yyy() -> ! {fail!()}
<|endoftext|>


<commit_before><commit_msg>Add more context in error messages<commit_after><|endoftext|>


<commit_before><commit_msg>firecracker: added jailer stub<commit_after>#[macro_use(crate_version, crate_authors)]
extern crate clap;

use clap::{App, Arg};

fn main() {
    // Initially, the uid and gid params had default values, but it turns out that it's quite
    // easy to shoot yourself in the foot by not setting proper permissions when preparing the
    // contents of the jail, so I think their values should be provided explicitly.
    let cmd_arguments = App::new("firejailer")
        .version(crate_version!())
        .author(crate_authors!())
        .about("Jail a microVM.")
        .arg(
            Arg::with_name("id")
                .long("id")
                .help("Jail ID")
                .required(true)
                .takes_value(true),
        )
        .arg(
            Arg::with_name("exec_file")
                .long("exec-file")
                .help("File path to exec into")
                .required(true)
                .takes_value(true),
        )
        .arg(
            Arg::with_name("uid")
                .long("uid")
                .help("Chroot uid")
                .required(true)
                .takes_value(true),
        )
        .arg(
            Arg::with_name("gid")
                .long("gid")
                .help("Chroot gid")
                .required(true)
                .takes_value(true),
        )
        .get_matches();
}
<|endoftext|>


<commit_before>use num;

pub trait Color: Clone + PartialEq {
    type Tag;
    type ChannelsTuple;

    fn num_channels() -> u32;
    fn from_tuple(values: Self::ChannelsTuple) -> Self;
    fn to_tuple(self) -> Self::ChannelsTuple;
}

pub trait PolarColor: Color {
    type Angular;
    type Cartesian;
}

pub trait Flatten: Color {
    type ScalarFormat;
    fn from_slice(values: &[Self::ScalarFormat]) -> Self;
    fn as_slice(&self) -> &[Self::ScalarFormat];
}

pub trait HomogeneousColor: Color {
    type ChannelFormat;

    fn broadcast(value: Self::ChannelFormat) -> Self;
    fn clamp(self, min: Self::ChannelFormat, max: Self::ChannelFormat) -> Self;
}

pub trait Color3: Color {}
pub trait Color4: Color {}

pub trait Lerp {
    type Position: num::Float;
    fn lerp(&self, right: &Self, pos: Self::Position) -> Self;
}

pub trait Invert {
    fn invert(self) -> Self;
}

pub trait Bounded {
    fn normalize(self) -> Self;
    fn is_normalized(&self) -> bool;
}

pub trait ColorCast: Color {
    fn color_cast<To>(&self) -> To where To: Color<Tag = Self::Tag>;
}
<commit_msg>Remove ColorCast trait for now<commit_after>use num;

pub trait Color: Clone + PartialEq {
    type Tag;
    type ChannelsTuple;

    fn num_channels() -> u32;
    fn from_tuple(values: Self::ChannelsTuple) -> Self;
    fn to_tuple(self) -> Self::ChannelsTuple;
}

pub trait PolarColor: Color {
    type Angular;
    type Cartesian;
}

pub trait Flatten: Color {
    type ScalarFormat;
    fn from_slice(values: &[Self::ScalarFormat]) -> Self;
    fn as_slice(&self) -> &[Self::ScalarFormat];
}

pub trait HomogeneousColor: Color {
    type ChannelFormat;

    fn broadcast(value: Self::ChannelFormat) -> Self;
    fn clamp(self, min: Self::ChannelFormat, max: Self::ChannelFormat) -> Self;
}

pub trait Color3: Color {}
pub trait Color4: Color {}

pub trait Lerp {
    type Position: num::Float;
    fn lerp(&self, right: &Self, pos: Self::Position) -> Self;
}

pub trait Invert {
    fn invert(self) -> Self;
}

pub trait Bounded {
    fn normalize(self) -> Self;
    fn is_normalized(&self) -> bool;
}

<|endoftext|>


<commit_before>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

use eutil::slice_to_str;
use libc::{c_int};
use std::collections::TreeMap;
use std::mem;
use std::string::String;
use string::{cef_string_userfree_utf8_alloc,cef_string_userfree_utf8_free,cef_string_utf8_set};
use types::{cef_string_multimap_t,cef_string_t};

fn string_multimap_to_treemap(smm: *mut cef_string_multimap_t) -> *mut TreeMap<String, Vec<*mut cef_string_t>> {
    smm as *mut TreeMap<String, Vec<*mut cef_string_t>>
}

//cef_string_multimap

#[no_mangle]
pub extern "C" fn cef_string_multimap_alloc() -> *mut cef_string_multimap_t {
    unsafe {
         let smm: Box<TreeMap<String, Vec<*mut cef_string_t>>> = box TreeMap::new();
         mem::transmute(smm)
    }
}

#[no_mangle]
pub extern "C" fn cef_string_multimap_size(smm: *mut cef_string_multimap_t) -> c_int {
    unsafe {
        if smm.is_null() { return 0; }
        let mut c: c_int = 0;
        let v = string_multimap_to_treemap(smm);
        for (_, val) in (*v).iter() {
            c = c + (*val).len() as c_int;
        }
        c
    }
}

#[no_mangle]
pub extern "C" fn cef_string_multimap_find_count(smm: *mut cef_string_multimap_t, key: *const cef_string_t) -> c_int {
    unsafe {
        if smm.is_null() { return 0; }
        let v = string_multimap_to_treemap(smm);
        slice_to_str((*key).str as *const u8, (*key).length as uint, |result| {
            match (*v).find(&String::from_str(result)) {
                Some(s) => {
                    s.len() as c_int
                }
                None => 0
            }
        })
    }
}
<commit_msg>embedding: cef_string_multimap_append()<commit_after>/* This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */

use eutil::slice_to_str;
use libc::{c_int};
use std::collections::TreeMap;
use std::mem;
use std::string::String;
use string::{cef_string_userfree_utf8_alloc,cef_string_userfree_utf8_free,cef_string_utf8_set};
use types::{cef_string_multimap_t,cef_string_t};

fn string_multimap_to_treemap(smm: *mut cef_string_multimap_t) -> *mut TreeMap<String, Vec<*mut cef_string_t>> {
    smm as *mut TreeMap<String, Vec<*mut cef_string_t>>
}

//cef_string_multimap

#[no_mangle]
pub extern "C" fn cef_string_multimap_alloc() -> *mut cef_string_multimap_t {
    unsafe {
         let smm: Box<TreeMap<String, Vec<*mut cef_string_t>>> = box TreeMap::new();
         mem::transmute(smm)
    }
}

#[no_mangle]
pub extern "C" fn cef_string_multimap_size(smm: *mut cef_string_multimap_t) -> c_int {
    unsafe {
        if smm.is_null() { return 0; }
        let mut c: c_int = 0;
        let v = string_multimap_to_treemap(smm);
        for (_, val) in (*v).iter() {
            c = c + (*val).len() as c_int;
        }
        c
    }
}

#[no_mangle]
pub extern "C" fn cef_string_multimap_find_count(smm: *mut cef_string_multimap_t, key: *const cef_string_t) -> c_int {
    unsafe {
        if smm.is_null() { return 0; }
        let v = string_multimap_to_treemap(smm);
        slice_to_str((*key).str as *const u8, (*key).length as uint, |result| {
            match (*v).find(&String::from_str(result)) {
                Some(s) => {
                    s.len() as c_int
                }
                None => 0
            }
        })
    }
}

#[no_mangle]
pub extern "C" fn cef_string_multimap_append(smm: *mut cef_string_multimap_t, key: *const cef_string_t, value: *const cef_string_t) -> c_int {
    unsafe {
        if smm.is_null() { return 0; }
        let v = string_multimap_to_treemap(smm);
        slice_to_str((*key).str as *const u8, (*key).length as uint, |result| {
            let s = String::from_str(result);
            let csv = cef_string_userfree_utf8_alloc();
            cef_string_utf8_set((*value).str as *const u8, (*value).length, csv, 1);
            match (*v).find_mut(&s) {
                Some(vc) => {
                    (*vc).push(csv);
                    1
                }
                None => {
                    let vc = vec!(csv);
                    (*v).insert(s, vc);
                    1
                }
            }
        })
    }
}
<|endoftext|>


<commit_before><commit_msg>debug: add debug mod<commit_after>
use std::fmt;
use std::slice;
use std::mem;
use std::ops;
use std::iter;
use std::marker::PhantomData;

use rocks_sys as ll;

use to_raw::{ToRaw, FromRaw};
use types::SequenceNumber;

// Value types encoded as the last component of internal keys.
#[repr(C)]
#[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
pub enum ValueType {
    Deletion = 0x0,
    Value = 0x1,
    Merge = 0x2,
    LogData = 0x3, // WAL only.
    ColumnFamilyDeletion = 0x4, // WAL only.
    ColumnFamilyValue = 0x5, // WAL only.
    ColumnFamilyMerge = 0x6, // WAL only.
    SingleDeletion = 0x7,
    ColumnFamilySingleDeletion = 0x8, // WAL only.
    BeginPrepareXID = 0x9, // WAL only.
    EndPrepareXID = 0xA, // WAL only.
    CommitXID = 0xB, // WAL only.
    RollbackXID = 0xC, // WAL only.
    Noop = 0xD, // WAL only.
    ColumnFamilyRangeDeletion = 0xE, // WAL only.
    RangeDeletion = 0xF, // meta block
}

// Data associated with a particular version of a key. A database may internally
// store multiple versions of a same user key due to snapshots, compaction not
// happening yet, etc.
pub struct KeyVersion {
    raw: ll::rocks_key_version_t,
}

impl fmt::Debug for KeyVersion {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        f.debug_struct("KeyVersion")
            .field("user_key", &self.user_key())
            .field("sequence", &self.sequence())
            .field("type", &self.value_type())
            .finish()
    }
}

impl ToRaw<ll::rocks_key_version_t> for KeyVersion {
    fn raw(&self) -> *mut ll::rocks_key_version_t {
        unsafe { mem::transmute(self) }
    }
}

impl<'a> FromRaw<ll::rocks_key_version_t> for &'a KeyVersion {
    unsafe fn from_ll(raw: *mut ll::rocks_key_version_t) -> Self {
        &*(raw as *mut KeyVersion)
    }
}

impl KeyVersion {
    pub fn user_key(&self) -> &[u8] {
        unsafe {
            let mut keylen = 0;
            let key_ptr = ll::rocks_key_version_user_key(self.raw(), &mut keylen);
            slice::from_raw_parts(key_ptr as *const u8, keylen)
        }
    }

    pub fn value(&self) -> &[u8] {
        unsafe {
            let mut vallen = 0;
            let val_ptr = ll::rocks_key_version_value(self.raw(), &mut vallen);
            slice::from_raw_parts(val_ptr as *const u8, vallen)
        }
    }

    pub fn sequence(&self) -> SequenceNumber {
        unsafe { ll::rocks_key_version_sequence_numer(self.raw()).into() }
    }

    pub fn value_type(&self) -> ValueType {
        unsafe { mem::transmute(ll::rocks_key_version_type(self.raw())) }
    }
}

pub struct KeyVersionVec<'a> {
    raw: *mut ll::rocks_key_version_collection_t,
    _marker: PhantomData<&'a ()>,
}

impl<'a> fmt::Debug for KeyVersionVec<'a> {
    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
        write!(f, "KeyVersionVec {{ size: {} }}", self.len())
    }
}

impl<'a> Drop for KeyVersionVec<'a> {
    fn drop(&mut self) {
        unsafe {
            ll::rocks_key_version_collection_destroy(self.raw);
        }
    }
}

impl<'a> FromRaw<ll::rocks_key_version_collection_t> for KeyVersionVec<'a> {
    unsafe fn from_ll(raw: *mut ll::rocks_key_version_collection_t) -> Self {
        KeyVersionVec {
            raw: raw,
            _marker: PhantomData,
        }
    }
}

impl<'a> KeyVersionVec<'a> {
    pub fn len(&self) -> usize {
        unsafe { ll::rocks_key_version_collection_size(self.raw) }
    }

    pub fn is_empty(&self) -> bool {
        self.len() == 0
    }

    pub fn iter<'b>(&'b self) -> KeyVersionVecIter<'b> {
        KeyVersionVecIter {
            vec: self,
            idx: 0,
        }
    }
}

impl<'a> iter::IntoIterator for &'a KeyVersionVec<'a> {
    type Item = &'a KeyVersion;
    type IntoIter = KeyVersionVecIter<'a>;
    fn into_iter(self) -> Self::IntoIter {
        self.iter()
    }
}

impl<'a> ops::Index<usize> for KeyVersionVec<'a> {
    type Output = KeyVersion;

    fn index(&self, index: usize) -> &Self::Output {
        assert!(index < self.len());
        unsafe { FromRaw::from_ll(ll::rocks_key_version_collection_nth(self.raw, index)) }
    }
}

pub struct KeyVersionVecIter<'a> {
    vec: &'a KeyVersionVec<'a>,
    idx: usize,
}

impl<'a> iter::Iterator for KeyVersionVecIter<'a> {
    type Item = &'a KeyVersion;

    fn next(&mut self) -> Option<Self::Item> {
        if self.idx >= self.vec.len() {
            None
        } else {
            unsafe {
                let p = ll::rocks_key_version_collection_nth(self.vec.raw, self.idx);
                self.idx += 1;
                Some(FromRaw::from_ll(p))
            }
        }
    }
}

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

    #[test]
    fn key_version() {
        let tmp_dir = ::tempdir::TempDir::new_in("", "rocks").unwrap();
        let db = DB::open(
            Options::default()
                .map_db_options(|db| db.create_if_missing(true))
                .map_cf_options(|cf| cf.disable_auto_compactions(true)),
            &tmp_dir,
        ).unwrap();

        for i in 0..100 {
            let key = format!("k{}", i % 20);
            let val = format!("v{}", i * i);
            let value: String = iter::repeat(val).take(i * i).collect::<Vec<_>>().concat();

            db.put(WriteOptions::default_instance(), key.as_bytes(), value.as_bytes())
                .unwrap();

            if i % 13 == 0 {
                db.delete(WriteOptions::default_instance(), key.as_bytes())
                    .unwrap();
            }
        }

        let vers = db.get_all_key_versions(b"\x00", b"\xff");
        assert!(vers.is_ok());
        let vers = vers.unwrap();
        // assert_eq!(vers.len(), 100);
        for i in 0..99 {
            assert!(vers[i].user_key().len() > 0);
        }

        for v in &vers {
            assert!(true, "iterator works");
            return;
        }
        assert!(false);
    }
}
<|endoftext|>


<commit_before><commit_msg>add `Sized` bound to `Trig` trait<commit_after><|endoftext|>


<commit_before><commit_msg>add KMS integration tests<commit_after>#![cfg(feature = "kms")]

extern crate rusoto;

use rusoto::kms::{KmsClient, ListKeysRequest};
use rusoto::{DefaultCredentialsProvider, Region};

#[test]
fn should_list_keys() {
    let credentials = DefaultCredentialsProvider::new().unwrap();
    let client = KmsClient::new(credentials, Region::UsEast1);

    let request = ListKeysRequest::default();

    match client.list_keys(&request) {
        Ok(response) => {
            println!("{:#?}", response);
            assert!(true)
        },
        Err(err) => panic!("Expected OK response, got {:#?}", err)
    };
}
<|endoftext|>