text:
// 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.

/*!
 * Higher-level interfaces to libc::* functions and operating system services.
 *
 * In general these take and return rust types, use rust idioms (enums,
 * closures, vectors) rather than C idioms, and do more extensive safety
 * checks.
 *
 * This module is not meant to only contain 1:1 mappings to libc entries; any
 * os-interface code that is reasonably useful and broadly applicable can go
 * here. Including utility routines that merely build on other os code.
 *
 * We assume the general case is that users do not care, and do not want to
 * be made to care, which operating system they are on. While they may want
 * to special case various special cases -- and so we will not _hide_ the
 * facts of which OS the user is on -- they should be given the opportunity
 * to write OS-ignorant code by default.
 */

#[allow(missing_doc)];

use c_str::ToCStr;
use clone::Clone;
use container::Container;
use io;
use iter::range;
use libc;
use libc::{c_char, c_void, c_int, size_t};
use libc::FILE;
use option::{Some, None};
use os;
use prelude::*;
use ptr;
use str;
use to_str;
use unstable::finally::Finally;
use vec;

pub use libc::fclose;
pub use os::consts::*;

/// Delegates to the libc close() function, returning the same return value.
pub fn close(fd: c_int) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        libc::close(fd)
    }
}

pub mod rustrt {
    use libc::{c_char, c_int};
    use libc;

    extern {
        pub fn rust_path_is_dir(path: *libc::c_char) -> c_int;
        pub fn rust_path_exists(path: *libc::c_char) -> c_int;
    }
}

pub static TMPBUF_SZ : uint = 1000u;
static BUF_BYTES : uint = 2048u;

pub fn getcwd() -> Path {
    #[fixed_stack_segment]; #[inline(never)];
    let mut buf = [0 as libc::c_char, ..BUF_BYTES];
    do buf.as_mut_buf |buf, len| {
        unsafe {
            if libc::getcwd(buf, len as size_t).is_null() {
                fail!()
            }

            Path(str::raw::from_c_str(buf as *c_char))
        }
    }
}

// FIXME: move these to str perhaps? #2620

pub fn fill_charp_buf(f: &fn(*mut c_char, size_t) -> bool) -> Option<~str> {
    let mut buf = [0 as c_char, .. TMPBUF_SZ];
    do buf.as_mut_buf |b, sz| {
        if f(b, sz as size_t) {
            unsafe {
                Some(str::raw::from_c_str(b as *c_char))
            }
        } else {
            None
        }
    }
}

#[cfg(windows)]
pub mod win32 {
    use libc;
    use vec;
    use str;
    use option::{None, Option};
    use option;
    use os::TMPBUF_SZ;
    use libc::types::os::arch::extra::DWORD;

    pub fn fill_utf16_buf_and_decode(f: &fn(*mut u16, DWORD) -> DWORD)
        -> Option<~str> {
        #[fixed_stack_segment]; #[inline(never)];

        unsafe {
            let mut n = TMPBUF_SZ as DWORD;
            let mut res = None;
            let mut done = false;
            while !done {
                let mut k: DWORD = 0;
                let mut buf = vec::from_elem(n as uint, 0u16);
                do buf.as_mut_buf |b, _sz| {
                    k = f(b, TMPBUF_SZ as DWORD);
                    if k == (0 as DWORD) {
                        done = true;
                    } else if (k == n &&
                               libc::GetLastError() ==
                               libc::ERROR_INSUFFICIENT_BUFFER as DWORD) {
                        n *= (2 as DWORD);
                    } else {
                        done = true;
                    }
                }
                if k != 0 && done {
                    let sub = buf.slice(0, k as uint);
                    res = option::Some(str::from_utf16(sub));
                }
            }
            return res;
        }
    }

    pub fn as_utf16_p<T>(s: &str, f: &fn(*u16) -> T) -> T {
        let mut t = s.to_utf16();
        // Null terminate before passing on.
        t.push(0u16);
        t.as_imm_buf(|buf, _len| f(buf))
    }
}

/*
Accessing environment variables is not generally threadsafe.
Serialize access through a global lock.
*/
fn with_env_lock<T>(f: &fn() -> T) -> T {
    use unstable::finally::Finally;

    unsafe {
        return do (|| {
            rust_take_env_lock();
            f()
        }).finally {
            rust_drop_env_lock();
        };
    }

    externfn!(fn rust_take_env_lock());
    externfn!(fn rust_drop_env_lock());
}

/// Returns a vector of (variable, value) pairs for all the environment
/// variables of the current process.
pub fn env() -> ~[(~str,~str)] {
    unsafe {
        #[cfg(windows)]
        unsafe fn get_env_pairs() -> ~[~str] {
            #[fixed_stack_segment]; #[inline(never)];

            use libc::funcs::extra::kernel32::{
                GetEnvironmentStringsA,
                FreeEnvironmentStringsA
            };
            let ch = GetEnvironmentStringsA();
            if (ch as uint == 0) {
                fail!("os::env() failure getting env string from OS: %s", os::last_os_error());
            }
            let result = str::raw::from_c_multistring(ch as *libc::c_char, None);
            FreeEnvironmentStringsA(ch);
            result
        }
        #[cfg(unix)]
        unsafe fn get_env_pairs() -> ~[~str] {
            #[fixed_stack_segment]; #[inline(never)];

            extern {
                fn rust_env_pairs() -> **libc::c_char;
            }
            let environ = rust_env_pairs();
            if (environ as uint == 0) {
                fail!("os::env() failure getting env string from OS: %s", os::last_os_error());
            }
            let mut result = ~[];
            ptr::array_each(environ, |e| {
                let env_pair = str::raw::from_c_str(e);
                debug!("get_env_pairs: %s",
                       env_pair);
                result.push(env_pair);
            });
            result
        }

        fn env_convert(input: ~[~str]) -> ~[(~str, ~str)] {
            let mut pairs = ~[];
            for p in input.iter() {
                let vs: ~[&str] = p.splitn_iter('=', 1).collect();
                debug!("splitting: len: %u",
                    vs.len());
                assert_eq!(vs.len(), 2);
                pairs.push((vs[0].to_owned(), vs[1].to_owned()));
            }
            pairs
        }
        do with_env_lock {
            let unparsed_environ = get_env_pairs();
            env_convert(unparsed_environ)
        }
    }
}

#[cfg(unix)]
/// Fetches the environment variable `n` from the current process, returning
/// None if the variable isn't set.
pub fn getenv(n: &str) -> Option<~str> {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        do with_env_lock {
            let s = do n.with_c_str |buf| {
                libc::getenv(buf)
            };
            if s.is_null() {
                None
            } else {
                Some(str::raw::from_c_str(s))
            }
        }
    }
}

#[cfg(windows)]
/// Fetches the environment variable `n` from the current process, returning
/// None if the variable isn't set.
pub fn getenv(n: &str) -> Option<~str> {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        do with_env_lock {
            use os::win32::{as_utf16_p, fill_utf16_buf_and_decode};
            do as_utf16_p(n) |u| {
                do fill_utf16_buf_and_decode() |buf, sz| {
                    libc::GetEnvironmentVariableW(u, buf, sz)
                }
            }
        }
    }
}

#[cfg(unix)]
/// Sets the environment variable `n` to the value `v` for the currently running
/// process
pub fn setenv(n: &str, v: &str) {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        do with_env_lock {
            do n.with_c_str |nbuf| {
                do v.with_c_str |vbuf| {
                    libc::funcs::posix01::unistd::setenv(nbuf, vbuf, 1);
                }
            }
        }
    }
}

#[cfg(windows)]
/// Sets the environment variable `n` to the value `v` for the currently running
/// process
pub fn setenv(n: &str, v: &str) {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        do with_env_lock {
            use os::win32::as_utf16_p;
            do as_utf16_p(n) |nbuf| {
                do as_utf16_p(v) |vbuf| {
                    libc::SetEnvironmentVariableW(nbuf, vbuf);
                }
            }
        }
    }
}

/// Remove a variable from the environment entirely
pub fn unsetenv(n: &str) {
    #[cfg(unix)]
    fn _unsetenv(n: &str) {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            do with_env_lock {
                do n.with_c_str |nbuf| {
                    libc::funcs::posix01::unistd::unsetenv(nbuf);
                }
            }
        }
    }
    #[cfg(windows)]
    fn _unsetenv(n: &str) {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            do with_env_lock {
                use os::win32::as_utf16_p;
                do as_utf16_p(n) |nbuf| {
                    libc::SetEnvironmentVariableW(nbuf, ptr::null());
                }
            }
        }
    }

    _unsetenv(n);
}

pub fn fdopen(fd: c_int) -> *FILE {
    #[fixed_stack_segment]; #[inline(never)];
    do "r".with_c_str |modebuf| {
        unsafe {
            libc::fdopen(fd, modebuf)
        }
    }
}

// fsync related

#[cfg(windows)]
pub fn fsync_fd(fd: c_int, _level: io::fsync::Level) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        use libc::funcs::extra::msvcrt::*;
        return commit(fd);
    }
}

#[cfg(target_os = "linux")]
#[cfg(target_os = "android")]
pub fn fsync_fd(fd: c_int, level: io::fsync::Level) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        use libc::funcs::posix01::unistd::*;
        match level {
          io::fsync::FSync
          | io::fsync::FullFSync => return fsync(fd),
          io::fsync::FDataSync => return fdatasync(fd)
        }
    }
}

#[cfg(target_os = "macos")]
pub fn fsync_fd(fd: c_int, level: io::fsync::Level) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        use libc::consts::os::extra::*;
        use libc::funcs::posix88::fcntl::*;
        use libc::funcs::posix01::unistd::*;
        match level {
          io::fsync::FSync => return fsync(fd),
          _ => {
            // According to man fnctl, the ok retval is only specified to be
            // !=-1
            if (fcntl(F_FULLFSYNC as c_int, fd) == -1 as c_int)
                { return -1 as c_int; }
            else
                { return 0 as c_int; }
          }
        }
    }
}

#[cfg(target_os = "freebsd")]
pub fn fsync_fd(fd: c_int, _l: io::fsync::Level) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        use libc::funcs::posix01::unistd::*;
        return fsync(fd);
    }
}

pub struct Pipe {
    input: c_int,
    out: c_int
}

#[cfg(unix)]
pub fn pipe() -> Pipe {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        let mut fds = Pipe {input: 0 as c_int,
                            out: 0 as c_int };
        assert_eq!(libc::pipe(&mut fds.input), (0 as c_int));
        return Pipe {input: fds.input, out: fds.out};
    }
}

#[cfg(windows)]
pub fn pipe() -> Pipe {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        // Windows pipes work subtly differently than unix pipes, and their
        // inheritance has to be handled in a different way that I do not
        // fully understand. Here we explicitly make the pipe non-inheritable,
        // which means to pass it to a subprocess they need to be duplicated
        // first, as in std::run.
        let mut fds = Pipe {input: 0 as c_int,
                    out: 0 as c_int };
        let res = libc::pipe(&mut fds.input, 1024 as ::libc::c_uint,
                             (libc::O_BINARY | libc::O_NOINHERIT) as c_int);
        assert_eq!(res, 0 as c_int);
        assert!((fds.input != -1 as c_int && fds.input != 0 as c_int));
        assert!((fds.out != -1 as c_int && fds.input != 0 as c_int));
        return Pipe {input: fds.input, out: fds.out};
    }
}

fn dup2(src: c_int, dst: c_int) -> c_int {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        libc::dup2(src, dst)
    }
}

/// Returns the proper dll filename for the given basename of a file.
pub fn dll_filename(base: &str) -> ~str {
    fmt!("%s%s%s", DLL_PREFIX, base, DLL_SUFFIX)
}

/// Optionally returns the filesystem path to the current executable which is
/// running. If any failure occurs, None is returned.
pub fn self_exe_path() -> Option<Path> {

    #[cfg(target_os = "freebsd")]
    fn load_self() -> Option<~str> {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use libc::funcs::bsd44::*;
            use libc::consts::os::extra::*;
            do fill_charp_buf() |buf, sz| {
                let mib = ~[CTL_KERN as c_int,
                           KERN_PROC as c_int,
                           KERN_PROC_PATHNAME as c_int, -1 as c_int];
                let mut sz = sz;
                sysctl(vec::raw::to_ptr(mib), mib.len() as ::libc::c_uint,
                       buf as *mut c_void, &mut sz, ptr::null(),
                       0u as size_t) == (0 as c_int)
            }
        }
    }

    #[cfg(target_os = "linux")]
    #[cfg(target_os = "android")]
    fn load_self() -> Option<~str> {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use libc::funcs::posix01::unistd::readlink;

            let mut path = [0 as c_char, .. TMPBUF_SZ];

            do path.as_mut_buf |buf, len| {
                let len = do "/proc/self/exe".with_c_str |proc_self_buf| {
                    readlink(proc_self_buf, buf, len as size_t) as uint
                };

                if len == -1 {
                    None
                } else {
                    Some(str::raw::from_buf_len(buf as *u8, len))
                }
            }
        }
    }

    #[cfg(target_os = "macos")]
    fn load_self() -> Option<~str> {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            do fill_charp_buf() |buf, sz| {
                let mut sz = sz as u32;
                libc::funcs::extra::_NSGetExecutablePath(
                    buf, &mut sz) == (0 as c_int)
            }
        }
    }

    #[cfg(windows)]
    fn load_self() -> Option<~str> {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::fill_utf16_buf_and_decode;
            do fill_utf16_buf_and_decode() |buf, sz| {
                libc::GetModuleFileNameW(0u as libc::DWORD, buf, sz)
            }
        }
    }

    load_self().map_move(|path| Path(path).dir_path())
}

/**
 * Returns the path to the user's home directory, if known.
 *
 * On Unix, returns the value of the 'HOME' environment variable if it is set
 * and not equal to the empty string.
 *
 * On Windows, returns the value of the 'HOME' environment variable if it is
 * set and not equal to the empty string. Otherwise, returns the value of the
 * 'USERPROFILE' environment variable if it is set and not equal to the empty
 * string.
 *
 * Otherwise, homedir returns option::none.
 */
pub fn homedir() -> Option<Path> {
    return match getenv("HOME") {
        Some(ref p) => if !p.is_empty() {
          Some(Path(*p))
        } else {
          secondary()
        },
        None => secondary()
    };

    #[cfg(unix)]
    fn secondary() -> Option<Path> {
        None
    }

    #[cfg(windows)]
    fn secondary() -> Option<Path> {
        do getenv("USERPROFILE").and_then |p| {
            if !p.is_empty() {
                Some(Path(p))
            } else {
                None
            }
        }
    }
}

/**
 * Returns the path to a temporary directory.
 *
 * On Unix, returns the value of the 'TMPDIR' environment variable if it is
 * set and non-empty and '/tmp' otherwise.
 * On Android, there is no global temporary folder (it is usually allocated
 * per-app), hence returns '/data/tmp' which is commonly used.
 *
 * On Windows, returns the value of, in order, the 'TMP', 'TEMP',
 * 'USERPROFILE' environment variable  if any are set and not the empty
 * string. Otherwise, tmpdir returns the path to the Windows directory.
 */
pub fn tmpdir() -> Path {
    return lookup();

    fn getenv_nonempty(v: &str) -> Option<Path> {
        match getenv(v) {
            Some(x) =>
                if x.is_empty() {
                    None
                } else {
                    Some(Path(x))
                },
            _ => None
        }
    }

    #[cfg(unix)]
    fn lookup() -> Path {
        if cfg!(target_os = "android") {
            Path("/data/tmp")
        } else {
            getenv_nonempty("TMPDIR").unwrap_or(Path("/tmp"))
        }
    }

    #[cfg(windows)]
    fn lookup() -> Path {
        getenv_nonempty("TMP").or(
            getenv_nonempty("TEMP").or(
                getenv_nonempty("USERPROFILE").or(
                   getenv_nonempty("WINDIR")))).unwrap_or(Path("C:\\Windows"))
    }
}

/// Recursively walk a directory structure
pub fn walk_dir(p: &Path, f: &fn(&Path) -> bool) -> bool {
    let r = list_dir(p);
    r.iter().advance(|q| {
        let path = &p.push(*q);
        f(path) && (!path_is_dir(path) || walk_dir(path, |p| f(p)))
    })
}

/// Indicates whether a path represents a directory
pub fn path_is_dir(p: &Path) -> bool {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        do p.with_c_str |buf| {
            rustrt::rust_path_is_dir(buf) != 0 as c_int
        }
    }
}

/// Indicates whether a path exists
pub fn path_exists(p: &Path) -> bool {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
        do p.with_c_str |buf| {
            rustrt::rust_path_exists(buf) != 0 as c_int
        }
    }
}

/**
 * Convert a relative path to an absolute path
 *
 * If the given path is relative, return it prepended with the current working
 * directory. If the given path is already an absolute path, return it
 * as is.
 */
// NB: this is here rather than in path because it is a form of environment
// querying; what it does depends on the process working directory, not just
// the input paths.
pub fn make_absolute(p: &Path) -> Path {
    if p.is_absolute {
        (*p).clone()
    } else {
        getcwd().push_many(p.components)
    }
}

/// Creates a directory at the specified path
pub fn make_dir(p: &Path, mode: c_int) -> bool {
    return mkdir(p, mode);

    #[cfg(windows)]
    fn mkdir(p: &Path, _mode: c_int) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::as_utf16_p;
            // FIXME: turn mode into something useful? #2623
            do as_utf16_p(p.to_str()) |buf| {
                libc::CreateDirectoryW(buf, ptr::mut_null())
                    != (0 as libc::BOOL)
            }
        }
    }

    #[cfg(unix)]
    fn mkdir(p: &Path, mode: c_int) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        do p.with_c_str |buf| {
            unsafe {
                libc::mkdir(buf, mode as libc::mode_t) == (0 as c_int)
            }
        }
    }
}

/// Creates a directory with a given mode.
/// Returns true iff creation
/// succeeded. Also creates all intermediate subdirectories
/// if they don't already exist, giving all of them the same mode.

// tjc: if directory exists but with different permissions,
// should we return false?
pub fn mkdir_recursive(p: &Path, mode: c_int) -> bool {
    if path_is_dir(p) {
        return true;
    }
    else if p.components.is_empty() {
        return false;
    }
    else if p.components.len() == 1 {
        // No parent directories to create
        path_is_dir(p) || make_dir(p, mode)
    }
    else {
        mkdir_recursive(&p.pop(), mode) && make_dir(p, mode)
    }
}

/// Lists the contents of a directory
pub fn list_dir(p: &Path) -> ~[~str] {
    if p.components.is_empty() && !p.is_absolute() {
        // Not sure what the right behavior is here, but this
        // prevents a bounds check failure later
        return ~[];
    }
    unsafe {
        #[cfg(target_os = "linux")]
        #[cfg(target_os = "android")]
        #[cfg(target_os = "freebsd")]
        #[cfg(target_os = "macos")]
        unsafe fn get_list(p: &Path) -> ~[~str] {
            #[fixed_stack_segment]; #[inline(never)];
            use libc::{dirent_t};
            use libc::{opendir, readdir, closedir};
            extern {
                fn rust_list_dir_val(ptr: *dirent_t) -> *libc::c_char;
            }
            let mut strings = ~[];
            debug!("os::list_dir -- BEFORE OPENDIR");

            let dir_ptr = do p.with_c_str |buf| {
                opendir(buf)
            };

            if (dir_ptr as uint != 0) {
                debug!("os::list_dir -- opendir() SUCCESS");
                let mut entry_ptr = readdir(dir_ptr);
                while (entry_ptr as uint != 0) {
                    strings.push(str::raw::from_c_str(rust_list_dir_val(
                        entry_ptr)));
                    entry_ptr = readdir(dir_ptr);
                }
                closedir(dir_ptr);
            }
            else {
                debug!("os::list_dir -- opendir() FAILURE");
            }
            debug!(
                "os::list_dir -- AFTER -- #: %?",
                     strings.len());
            strings
        }
        #[cfg(windows)]
        unsafe fn get_list(p: &Path) -> ~[~str] {
            #[fixed_stack_segment]; #[inline(never)];
            use libc::consts::os::extra::INVALID_HANDLE_VALUE;
            use libc::{wcslen, free};
            use libc::funcs::extra::kernel32::{
                FindFirstFileW,
                FindNextFileW,
                FindClose,
            };
            use libc::types::os::arch::extra::HANDLE;
            use os::win32::{
                as_utf16_p
            };
            use rt::global_heap::malloc_raw;

            #[nolink]
            extern {
                fn rust_list_dir_wfd_size() -> libc::size_t;
                fn rust_list_dir_wfd_fp_buf(wfd: *libc::c_void) -> *u16;
            }
            fn star(p: &Path) -> Path { p.push("*") }
            do as_utf16_p(star(p).to_str()) |path_ptr| {
                let mut strings = ~[];
                let wfd_ptr = malloc_raw(rust_list_dir_wfd_size() as uint);
                let find_handle = FindFirstFileW(path_ptr, wfd_ptr as HANDLE);
                if find_handle as libc::c_int != INVALID_HANDLE_VALUE {
                    let mut more_files = 1 as libc::c_int;
                    while more_files != 0 {
                        let fp_buf = rust_list_dir_wfd_fp_buf(wfd_ptr);
                        if fp_buf as uint == 0 {
                            fail!("os::list_dir() failure: got null ptr from wfd");
                        }
                        else {
                            let fp_vec = vec::from_buf(
                                fp_buf, wcslen(fp_buf) as uint);
                            let fp_str = str::from_utf16(fp_vec);
                            strings.push(fp_str);
                        }
                        more_files = FindNextFileW(find_handle, wfd_ptr as HANDLE);
                    }
                    FindClose(find_handle);
                    free(wfd_ptr)
                }
                strings
            }
        }
        do get_list(p).move_iter().filter |filename| {
            "." != *filename && ".." != *filename
        }.collect()
    }
}

/**
 * Lists the contents of a directory
 *
 * This version prepends each entry with the directory.
 */
pub fn list_dir_path(p: &Path) -> ~[Path] {
    list_dir(p).map(|f| p.push(*f))
}

/// Removes a directory at the specified path, after removing
/// all its contents. Use carefully!
pub fn remove_dir_recursive(p: &Path) -> bool {
    let mut error_happened = false;
    do walk_dir(p) |inner| {
        if !error_happened {
            if path_is_dir(inner) {
                if !remove_dir_recursive(inner) {
                    error_happened = true;
                }
            }
            else {
                if !remove_file(inner) {
                    error_happened = true;
                }
            }
        }
        true
    };
    // Directory should now be empty
    !error_happened && remove_dir(p)
}

/// Removes a directory at the specified path
pub fn remove_dir(p: &Path) -> bool {
   return rmdir(p);

    #[cfg(windows)]
    fn rmdir(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::as_utf16_p;
            return do as_utf16_p(p.to_str()) |buf| {
                libc::RemoveDirectoryW(buf) != (0 as libc::BOOL)
            };
        }
    }

    #[cfg(unix)]
    fn rmdir(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        do p.with_c_str |buf| {
            unsafe {
                libc::rmdir(buf) == (0 as c_int)
            }
        }
    }
}

/// Changes the current working directory to the specified path, returning
/// whether the change was completed successfully or not.
pub fn change_dir(p: &Path) -> bool {
    return chdir(p);

    #[cfg(windows)]
    fn chdir(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::as_utf16_p;
            return do as_utf16_p(p.to_str()) |buf| {
                libc::SetCurrentDirectoryW(buf) != (0 as libc::BOOL)
            };
        }
    }

    #[cfg(unix)]
    fn chdir(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        do p.with_c_str |buf| {
            unsafe {
                libc::chdir(buf) == (0 as c_int)
            }
        }
    }
}

/// Copies a file from one location to another
pub fn copy_file(from: &Path, to: &Path) -> bool {
    return do_copy_file(from, to);

    #[cfg(windows)]
    fn do_copy_file(from: &Path, to: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::as_utf16_p;
            return do as_utf16_p(from.to_str()) |fromp| {
                do as_utf16_p(to.to_str()) |top| {
                    libc::CopyFileW(fromp, top, (0 as libc::BOOL)) !=
                        (0 as libc::BOOL)
                }
            }
        }
    }

    #[cfg(unix)]
    fn do_copy_file(from: &Path, to: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            let istream = do from.with_c_str |fromp| {
                do "rb".with_c_str |modebuf| {
                    libc::fopen(fromp, modebuf)
                }
            };
            if istream as uint == 0u {
                return false;
            }
            // Preserve permissions
            let from_mode = from.get_mode().expect("copy_file: couldn't get permissions \
                                                    for source file");

            let ostream = do to.with_c_str |top| {
                do "w+b".with_c_str |modebuf| {
                    libc::fopen(top, modebuf)
                }
            };
            if ostream as uint == 0u {
                fclose(istream);
                return false;
            }
            let bufsize = 8192u;
            let mut buf = vec::with_capacity::<u8>(bufsize);
            let mut done = false;
            let mut ok = true;
            while !done {
                do buf.as_mut_buf |b, _sz| {
                  let nread = libc::fread(b as *mut c_void, 1u as size_t,
                                          bufsize as size_t,
                                          istream);
                  if nread > 0 as size_t {
                      if libc::fwrite(b as *c_void, 1u as size_t, nread,
                                      ostream) != nread {
                          ok = false;
                          done = true;
                      }
                  } else {
                      done = true;
                  }
              }
            }
            fclose(istream);
            fclose(ostream);

            // Give the new file the old file's permissions
            if do to.with_c_str |to_buf| {
                libc::chmod(to_buf, from_mode as libc::mode_t)
            } != 0 {
                return false; // should be a condition...
            }
            return ok;
        }
    }
}

/// Deletes an existing file
pub fn remove_file(p: &Path) -> bool {
    return unlink(p);

    #[cfg(windows)]
    fn unlink(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            use os::win32::as_utf16_p;
            return do as_utf16_p(p.to_str()) |buf| {
                libc::DeleteFileW(buf) != (0 as libc::BOOL)
            };
        }
    }

    #[cfg(unix)]
    fn unlink(p: &Path) -> bool {
        #[fixed_stack_segment]; #[inline(never)];
        unsafe {
            do p.with_c_str |buf| {
                libc::unlink(buf) == (0 as c_int)
            }
        }
    }
}

/// Renames an existing file or directory
pub fn rename_file(old: &Path, new: &Path) -> bool {
    #[fixed_stack_segment]; #[inline(never)];
    unsafe {
       do old.with_c_str |old_buf| {
            do new.with_c_str |new_buf| {
                libc::rename(old_buf, new_buf) == (0 as c_int)
            }
       }
    }
}

#[cfg(unix)]
/// Returns the platform-specific value of errno
pub fn errno() -> int {
    #[cfg(target_os = "macos")]
    #[cfg(target_os = "freebsd")]
    fn errno_location() -> *c_int {
        #[fixed_stack_segment]; #[inline(never)];
        #[nolink]
        extern {
            fn __error() -> *c_int;
        }
        unsafe {
            __error()
        }
    }

    #[cfg(target_os = "linux")]
    #[cfg(target_os = "android")]
    fn errno_location() -> *c_int {
        #[fixed_stack_segment]; #[inline(never)];
        #[nolink]
        extern {
            fn __errno_location() -> *c_int;
        }
        unsafe {
            __errno_location()
        }
    }

    unsafe {
        (*errno_location()) as int
    }
}

#[cfg(windows)]
/// Returns the platform-specific value of errno
pub fn errno() -> uint {
    #[fixed_stack_segment]; #[inline(never)];
    use libc::types::os::arch::extra::DWORD;

    #[cfg(target_arch = "x86")]
    #[link_name = "kernel32"]
    #[abi = "stdcall"]
    extern "stdcall" {
        fn GetLastError() -> DWORD;
    }

    #[cfg(target_arch = "x86_64")]
    #[link_name = "kernel32"]
    extern {
        fn GetLastError() -> DWORD;
    }

    unsafe {
        GetLastError() as uint
    }
}

/// Get a string representing the platform-dependent last error
pub fn last_os_error() -> ~str {
    #[cfg(unix)]
    fn strerror() -> ~str {
        #[cfg(target_os = "macos")]
        #[cfg(target_os = "android")]
        #[cfg(target_os = "freebsd")]
        fn strerror_r(errnum: c_int, buf: *mut c_char, buflen: size_t)
                      -> c_int {
            #[fixed_stack_segment]; #[inline(never)];

            #[nolink]
            extern {
                fn strerror_r(errnum: c_int, buf: *mut c_char, buflen: size_t)
                              -> c_int;
            }
            unsafe {
                strerror_r(errnum, buf, buflen)
            }
        }

        // GNU libc provides a non-compliant version of strerror_r by default
        // and requires macros to instead use the POSIX compliant variant.
        // So we just use __xpg_strerror_r which is always POSIX compliant
        #[cfg(target_os = "linux")]
        fn strerror_r(errnum: c_int, buf: *mut c_char, buflen: size_t) -> c_int {
            #[fixed_stack_segment]; #[inline(never)];
            #[nolink]
            extern {
                fn __xpg_strerror_r(errnum: c_int,
                                    buf: *mut c_char,
                                    buflen: size_t)
                                    -> c_int;
            }
            unsafe {
                __xpg_strerror_r(errnum, buf, buflen)
            }
        }

        let mut buf = [0 as c_char, ..TMPBUF_SZ];

        do buf.as_mut_buf |buf, len| {
            unsafe {
                if strerror_r(errno() as c_int, buf, len as size_t) < 0 {
                    fail!("strerror_r failure");
                }

                str::raw::from_c_str(buf as *c_char)
            }
        }
    }

    #[cfg(windows)]
    fn strerror() -> ~str {
        #[fixed_stack_segment]; #[inline(never)];

        use libc::types::os::arch::extra::DWORD;
        use libc::types::os::arch::extra::LPWSTR;
        use libc::types::os::arch::extra::LPVOID;
        use libc::types::os::arch::extra::WCHAR;

        #[cfg(target_arch = "x86")]
        #[link_name = "kernel32"]
        #[abi = "stdcall"]
        extern "stdcall" {
            fn FormatMessageW(flags: DWORD,
                              lpSrc: LPVOID,
                              msgId: DWORD,
                              langId: DWORD,
                              buf: LPWSTR,
                              nsize: DWORD,
                              args: *c_void)
                              -> DWORD;
        }

        #[cfg(target_arch = "x86_64")]
        #[link_name = "kernel32"]
        extern {
            fn FormatMessageW(flags: DWORD,
                              lpSrc: LPVOID,
                              msgId: DWORD,
                              langId: DWORD,
                              buf: LPWSTR,
                              nsize: DWORD,
                              args: *c_void)
                              -> DWORD;
        }

        static FORMAT_MESSAGE_FROM_SYSTEM: DWORD = 0x00001000;
        static FORMAT_MESSAGE_IGNORE_INSERTS: DWORD = 0x00000200;

        // This value is calculated from the macro
        // MAKELANGID(LANG_SYSTEM_DEFAULT, SUBLANG_SYS_DEFAULT)
        let langId = 0x0800 as DWORD;
        let err = errno() as DWORD;

        let mut buf = [0 as WCHAR, ..TMPBUF_SZ];

        unsafe {
            do buf.as_mut_buf |buf, len| {
                let res = FormatMessageW(FORMAT_MESSAGE_FROM_SYSTEM |
                                         FORMAT_MESSAGE_IGNORE_INSERTS,
                                         ptr::mut_null(),
                                         err,
                                         langId,
                                         buf,
                                         len as DWORD,
                                         ptr::null());
                if res == 0 {
                    fail!("[%?] FormatMessage failure", errno());
                }
            }

            str::from_utf16(buf)
        }
    }

    strerror()
}

/**
 * Sets the process exit code
 *
 * Sets the exit code returned by the process if all supervised tasks
 * terminate successfully (without failing). If the current root task fails
 * and is supervised by the scheduler then any user-specified exit status is
 * ignored and the process exits with the default failure status
 */
pub fn set_exit_status(code: int) {
    use rt;
    rt::util::set_exit_status(code);
}

unsafe fn load_argc_and_argv(argc: c_int, argv: **c_char) -> ~[~str] {
    let mut args = ~[];
    for i in range(0u, argc as uint) {
        args.push(str::raw::from_c_str(*argv.offset(i as int)));
    }
    args
}

/**
 * Returns the command line arguments
 *
 * Returns a list of the command line arguments.
 */
#[cfg(target_os = "macos")]
fn real_args() -> ~[~str] {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        let (argc, argv) = (*_NSGetArgc() as c_int,
                            *_NSGetArgv() as **c_char);
        load_argc_and_argv(argc, argv)
    }
}

#[cfg(target_os = "linux")]
#[cfg(target_os = "android")]
#[cfg(target_os = "freebsd")]
fn real_args() -> ~[~str] {
    use rt;

    match rt::args::clone() {
        Some(args) => args,
        None => fail!("process arguments not initialized")
    }
}

#[cfg(windows)]
fn real_args() -> ~[~str] {
    #[fixed_stack_segment]; #[inline(never)];

    let mut nArgs: c_int = 0;
    let lpArgCount: *mut c_int = &mut nArgs;
    let lpCmdLine = unsafe { GetCommandLineW() };
    let szArgList = unsafe { CommandLineToArgvW(lpCmdLine, lpArgCount) };

    let mut args = ~[];
    for i in range(0u, nArgs as uint) {
        unsafe {
            // Determine the length of this argument.
            let ptr = *szArgList.offset(i as int);
            let mut len = 0;
            while *ptr.offset(len as int) != 0 { len += 1; }

            // Push it onto the list.
            args.push(vec::raw::buf_as_slice(ptr, len,
                                             str::from_utf16));
        }
    }

    unsafe {
        LocalFree(szArgList as *c_void);
    }

    return args;
}

type LPCWSTR = *u16;

#[cfg(windows, target_arch = "x86")]
#[link_name="kernel32"]
#[abi="stdcall"]
extern "stdcall" {
    fn GetCommandLineW() -> LPCWSTR;
    fn LocalFree(ptr: *c_void);
}

#[cfg(windows, target_arch = "x86_64")]
#[link_name="kernel32"]
extern {
    fn GetCommandLineW() -> LPCWSTR;
    fn LocalFree(ptr: *c_void);
}

#[cfg(windows, target_arch = "x86")]
#[link_name="shell32"]
#[abi="stdcall"]
extern "stdcall" {
    fn CommandLineToArgvW(lpCmdLine: LPCWSTR, pNumArgs: *mut c_int) -> **u16;
}

#[cfg(windows, target_arch = "x86_64")]
#[link_name="shell32"]
extern {
    fn CommandLineToArgvW(lpCmdLine: LPCWSTR, pNumArgs: *mut c_int) -> **u16;
}

struct OverriddenArgs {
    val: ~[~str]
}

/// Returns the arguments which this program was started with (normally passed
/// via the command line).
pub fn args() -> ~[~str] {
    real_args()
}

#[cfg(target_os = "macos")]
extern {
    // These functions are in crt_externs.h.
    pub fn _NSGetArgc() -> *c_int;
    pub fn _NSGetArgv() -> ***c_char;
}

// Round up `from` to be divisible by `to`
fn round_up(from: uint, to: uint) -> uint {
    let r = if from % to == 0 {
        from
    } else {
        from + to - (from % to)
    };
    if r == 0 {
        to
    } else {
        r
    }
}

#[cfg(unix)]
pub fn page_size() -> uint {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        libc::sysconf(libc::_SC_PAGESIZE) as uint
    }
}

#[cfg(windows)]
pub fn page_size() -> uint {
    #[fixed_stack_segment]; #[inline(never)];

    unsafe {
        let mut info = libc::SYSTEM_INFO::new();
        libc::GetSystemInfo(&mut info);

        return info.dwPageSize as uint;
    }
}

pub struct MemoryMap {
    data: *mut u8,
    len: size_t,
    kind: MemoryMapKind
}

pub enum MemoryMapKind {
    MapFile(*c_void),
    MapVirtual
}

pub enum MapOption {
    MapReadable,
    MapWritable,
    MapExecutable,
    MapAddr(*c_void),
    MapFd(c_int),
    MapOffset(uint)
}

pub enum MapError {
    // Linux-specific errors
    ErrFdNotAvail,
    ErrInvalidFd,
    ErrUnaligned,
    ErrNoMapSupport,
    ErrNoMem,
    ErrUnknown(libc::c_int),

    // Windows-specific errors
    ErrUnsupProt,
    ErrUnsupOffset,
    ErrAlreadyExists,
    ErrVirtualAlloc(uint),
    ErrCreateFileMappingW(uint),
    ErrMapViewOfFile(uint)
}

impl to_str::ToStr for MapError {
    fn to_str(&self) -> ~str {
        match *self {
            ErrFdNotAvail => ~"fd not available for reading or writing",
            ErrInvalidFd => ~"Invalid fd",
            ErrUnaligned => ~"Unaligned address, invalid flags, \
                              negative length or unaligned offset",
            ErrNoMapSupport=> ~"File doesn't support mapping",
            ErrNoMem => ~"Invalid address, or not enough available memory",
            ErrUnknown(code) => fmt!("Unknown error=%?", code),
            ErrUnsupProt => ~"Protection mode unsupported",
            ErrUnsupOffset => ~"Offset in virtual memory mode is unsupported",
            ErrAlreadyExists => ~"File mapping for specified file already exists",
            ErrVirtualAlloc(code) => fmt!("VirtualAlloc failure=%?", code),
            ErrCreateFileMappingW(code) => fmt!("CreateFileMappingW failure=%?", code),
            ErrMapViewOfFile(code) => fmt!("MapViewOfFile failure=%?", code)
        }
    }
}

#[cfg(unix)]
impl MemoryMap {
    pub fn new(min_len: uint, options: ~[MapOption]) -> Result<~MemoryMap, MapError> {
        #[fixed_stack_segment]; #[inline(never)];

        use libc::off_t;

        let mut addr: *c_void = ptr::null();
        let mut prot: c_int = 0;
        let mut flags: c_int = libc::MAP_PRIVATE;
        let mut fd: c_int = -1;
        let mut offset: off_t = 0;
        let len = round_up(min_len, page_size()) as size_t;

        for &o in options.iter() {
            match o {
                MapReadable => { prot |= libc::PROT_READ; },
                MapWritable => { prot |= libc::PROT_WRITE; },
                MapExecutable => { prot |= libc::PROT_EXEC; },
                MapAddr(addr_) => {
                    flags |= libc::MAP_FIXED;
                    addr = addr_;
                },
                MapFd(fd_) => {
                    flags |= libc::MAP_FILE;
                    fd = fd_;
                },
                MapOffset(offset_) => { offset = offset_ as off_t; }
            }
        }
        if fd == -1 { flags |= libc::MAP_ANON; }

        let r = unsafe {
            libc::mmap(addr, len, prot, flags, fd, offset)
        };
        if r.equiv(&libc::MAP_FAILED) {
            Err(match errno() as c_int {
                libc::EACCES => ErrFdNotAvail,
                libc::EBADF => ErrInvalidFd,
                libc::EINVAL => ErrUnaligned,
                libc::ENODEV => ErrNoMapSupport,
                libc::ENOMEM => ErrNoMem,
                code => ErrUnknown(code)
            })
        } else {
            Ok(~MemoryMap {
               data: r as *mut u8,
               len: len,
               kind: if fd == -1 {
                   MapVirtual
               } else {
                   MapFile(ptr::null())
               }
            })
        }
    }

    pub fn granularity() -> uint {
        page_size()
    }
}

#[cfg(unix)]
impl Drop for MemoryMap {
    fn drop(&mut self) {
        #[fixed_stack_segment]; #[inline(never)];

        unsafe {
            match libc::munmap(self.data as *c_void, self.len) {
                0 => (),
                -1 => error!(match errno() as c_int {
                    libc::EINVAL => ~"invalid addr or len",
                    e => fmt!("unknown errno=%?", e)
                }),
                r => error!(fmt!("Unexpected result %?", r))
            }
        }
    }
}

#[cfg(windows)]
impl MemoryMap {
    pub fn new(min_len: uint, options: ~[MapOption]) -> Result<~MemoryMap, MapError> {
        #[fixed_stack_segment]; #[inline(never)];

        use libc::types::os::arch::extra::{LPVOID, DWORD, SIZE_T, HANDLE};

        let mut lpAddress: LPVOID = ptr::mut_null();
        let mut readable = false;
        let mut writable = false;
        let mut executable = false;
        let mut fd: c_int = -1;
        let mut offset: uint = 0;
        let len = round_up(min_len, page_size()) as SIZE_T;

        for &o in options.iter() {
            match o {
                MapReadable => { readable = true; },
                MapWritable => { writable = true; },
                MapExecutable => { executable = true; }
                MapAddr(addr_) => { lpAddress = addr_ as LPVOID; },
                MapFd(fd_) => { fd = fd_; },
                MapOffset(offset_) => { offset = offset_; }
            }
        }

        let flProtect = match (executable, readable, writable) {
            (false, false, false) if fd == -1 => libc::PAGE_NOACCESS,
            (false, true, false) => libc::PAGE_READONLY,
            (false, true, true) => libc::PAGE_READWRITE,
            (true, false, false) if fd == -1 => libc::PAGE_EXECUTE,
            (true, true, false) => libc::PAGE_EXECUTE_READ,
            (true, true, true) => libc::PAGE_EXECUTE_READWRITE,
            _ => return Err(ErrUnsupProt)
        };

        if fd == -1 {
            if offset != 0 {
                return Err(ErrUnsupOffset);
            }
            let r = unsafe {
                libc::VirtualAlloc(lpAddress,
                                   len,
                                   libc::MEM_COMMIT | libc::MEM_RESERVE,
                                   flProtect)
            };
            match r as uint {
                0 => Err(ErrVirtualAlloc(errno())),
                _ => Ok(~MemoryMap {
                   data: r as *mut u8,
                   len: len,
                   kind: MapVirtual
                })
            }
        } else {
            let dwDesiredAccess = match (executable, readable, writable) {
                (false, true, false) => libc::FILE_MAP_READ,
                (false, true, true) => libc::FILE_MAP_WRITE,
                (true, true, false) => libc::FILE_MAP_READ | libc::FILE_MAP_EXECUTE,
                (true, true, true) => libc::FILE_MAP_WRITE | libc::FILE_MAP_EXECUTE,
                _ => return Err(ErrUnsupProt) // Actually, because of the check above,
                                              // we should never get here.
            };
            unsafe {
                let hFile = libc::get_osfhandle(fd) as HANDLE;
                let mapping = libc::CreateFileMappingW(hFile,
                                                       ptr::mut_null(),
                                                       flProtect,
                                                       0,
                                                       0,
                                                       ptr::null());
                if mapping == ptr::mut_null() {
                    return Err(ErrCreateFileMappingW(errno()));
                }
                if errno() as c_int == libc::ERROR_ALREADY_EXISTS {
                    return Err(ErrAlreadyExists);
                }
                let r = libc::MapViewOfFile(mapping,
                                            dwDesiredAccess,
                                            ((len as u64) >> 32) as DWORD,
                                            (offset & 0xffff_ffff) as DWORD,
                                            0);
                match r as uint {
                    0 => Err(ErrMapViewOfFile(errno())),
                    _ => Ok(~MemoryMap {
                       data: r as *mut u8,
                       len: len,
                       kind: MapFile(mapping as *c_void)
                    })
                }
            }
        }
    }

    /// Granularity of MapAddr() and MapOffset() parameter values.
    /// This may be greater than the value returned by page_size().
    pub fn granularity() -> uint {
        #[fixed_stack_segment]; #[inline(never)];

        unsafe {
            let mut info = libc::SYSTEM_INFO::new();
            libc::GetSystemInfo(&mut info);

            return info.dwAllocationGranularity as uint;
        }
    }
}

#[cfg(windows)]
impl Drop for MemoryMap {
    fn drop(&mut self) {
        #[fixed_stack_segment]; #[inline(never)];

        use libc::types::os::arch::extra::{LPCVOID, HANDLE};
        use libc::consts::os::extra::FALSE;

        unsafe {
            match self.kind {
                MapVirtual => {
                    if libc::VirtualFree(self.data as *mut c_void,
                                         self.len,
                                         libc::MEM_RELEASE) == FALSE {
                        error!(fmt!("VirtualFree failed: %?", errno()));
                    }
                },
                MapFile(mapping) => {
                    if libc::UnmapViewOfFile(self.data as LPCVOID) == FALSE {
                        error!(fmt!("UnmapViewOfFile failed: %?", errno()));
                    }
                    if libc::CloseHandle(mapping as HANDLE) == FALSE {
                        error!(fmt!("CloseHandle failed: %?", errno()));
                    }
                }
            }
        }
    }
}

pub mod consts {

    #[cfg(unix)]
    pub use os::consts::unix::*;

    #[cfg(windows)]
    pub use os::consts::windows::*;

    #[cfg(target_os = "macos")]
    pub use os::consts::macos::*;

    #[cfg(target_os = "freebsd")]
    pub use os::consts::freebsd::*;

    #[cfg(target_os = "linux")]
    pub use os::consts::linux::*;

    #[cfg(target_os = "android")]
    pub use os::consts::android::*;

    #[cfg(target_os = "win32")]
    pub use os::consts::win32::*;

    #[cfg(target_arch = "x86")]
    pub use os::consts::x86::*;

    #[cfg(target_arch = "x86_64")]
    pub use os::consts::x86_64::*;

    #[cfg(target_arch = "arm")]
    pub use os::consts::arm::*;

    #[cfg(target_arch = "mips")]
    pub use os::consts::mips::*;

    pub mod unix {
        pub static FAMILY: &'static str = "unix";
    }

    pub mod windows {
        pub static FAMILY: &'static str = "windows";
    }

    pub mod macos {
        pub static SYSNAME: &'static str = "macos";
        pub static DLL_PREFIX: &'static str = "lib";
        pub static DLL_SUFFIX: &'static str = ".dylib";
        pub static EXE_SUFFIX: &'static str = "";
    }

    pub mod freebsd {
        pub static SYSNAME: &'static str = "freebsd";
        pub static DLL_PREFIX: &'static str = "lib";
        pub static DLL_SUFFIX: &'static str = ".so";
        pub static EXE_SUFFIX: &'static str = "";
    }

    pub mod linux {
        pub static SYSNAME: &'static str = "linux";
        pub static DLL_PREFIX: &'static str = "lib";
        pub static DLL_SUFFIX: &'static str = ".so";
        pub static EXE_SUFFIX: &'static str = "";
    }

    pub mod android {
        pub static SYSNAME: &'static str = "android";
        pub static DLL_PREFIX: &'static str = "lib";
        pub static DLL_SUFFIX: &'static str = ".so";
        pub static EXE_SUFFIX: &'static str = "";
    }

    pub mod win32 {
        pub static SYSNAME: &'static str = "win32";
        pub static DLL_PREFIX: &'static str = "";
        pub static DLL_SUFFIX: &'static str = ".dll";
        pub static EXE_SUFFIX: &'static str = ".exe";
    }

    pub mod x86 {
        pub static ARCH: &'static str = "x86";
    }
    pub mod x86_64 {
        pub static ARCH: &'static str = "x86_64";
    }
    pub mod arm {
        pub static ARCH: &'static str = "arm";
    }
    pub mod mips {
        pub static ARCH: &'static str = "mips";
    }
}

#[cfg(test)]
mod tests {
    use c_str::ToCStr;
    use libc::{c_int, c_void, size_t};
    use libc;
    use option::Some;
    use option;
    use os::{env, getcwd, getenv, make_absolute, args};
    use os::{remove_file, setenv, unsetenv};
    use os;
    use path::Path;
    use rand::Rng;
    use rand;
    use run;
    use str::StrSlice;
    use libc::consts::os::posix88::{S_IRUSR, S_IWUSR, S_IXUSR};

    #[test]
    pub fn last_os_error() {
        debug!(os::last_os_error());
    }

    #[test]
    pub fn test_args() {
        let a = args();
        assert!(a.len() >= 1);
    }

    fn make_rand_name() -> ~str {
        let mut rng = rand::rng();
        let n = ~"TEST" + rng.gen_ascii_str(10u);
        assert!(getenv(n).is_none());
        n
    }

    #[test]
    fn test_setenv() {
        let n = make_rand_name();
        setenv(n, "VALUE");
        assert_eq!(getenv(n), option::Some(~"VALUE"));
    }

    #[test]
    fn test_unsetenv() {
        let n = make_rand_name();
        setenv(n, "VALUE");
        unsetenv(n);
        assert_eq!(getenv(n), option::None);
    }

    #[test]
    #[ignore]
    fn test_setenv_overwrite() {
        let n = make_rand_name();
        setenv(n, "1");
        setenv(n, "2");
        assert_eq!(getenv(n), option::Some(~"2"));
        setenv(n, "");
        assert_eq!(getenv(n), option::Some(~""));
    }

    // Windows GetEnvironmentVariable requires some extra work to make sure
    // the buffer the variable is copied into is the right size
    #[test]
    #[ignore]
    fn test_getenv_big() {
        let mut s = ~"";
        let mut i = 0;
        while i < 100 {
            s = s + "aaaaaaaaaa";
            i += 1;
        }
        let n = make_rand_name();
        setenv(n, s);
        debug!(s.clone());
        assert_eq!(getenv(n), option::Some(s));
    }

    #[test]
    fn test_self_exe_path() {
        let path = os::self_exe_path();
        assert!(path.is_some());
        let path = path.unwrap();
        debug!(path.clone());

        // Hard to test this function
        assert!(path.is_absolute);
    }

    #[test]
    #[ignore]
    fn test_env_getenv() {
        let e = env();
        assert!(e.len() > 0u);
        for p in e.iter() {
            let (n, v) = (*p).clone();
            debug!(n.clone());
            let v2 = getenv(n);
            // MingW seems to set some funky environment variables like
            // "=C:=C:\MinGW\msys\1.0\bin" and "!::=::\" that are returned
            // from env() but not visible from getenv().
            assert!(v2.is_none() || v2 == option::Some(v));
        }
    }

    #[test]
    fn test_env_setenv() {
        let n = make_rand_name();

        let mut e = env();
        setenv(n, "VALUE");
        assert!(!e.contains(&(n.clone(), ~"VALUE")));

        e = env();
        assert!(e.contains(&(n, ~"VALUE")));
    }

    #[test]
    fn test() {
        assert!((!Path("test-path").is_absolute));

        debug!("Current working directory: %s", getcwd().to_str());

        debug!(make_absolute(&Path("test-path")));
        debug!(make_absolute(&Path("/usr/bin")));
    }

    #[test]
    #[cfg(unix)]
    fn homedir() {
        let oldhome = getenv("HOME");

        setenv("HOME", "/home/MountainView");
        assert_eq!(os::homedir(), Some(Path("/home/MountainView")));

        setenv("HOME", "");
        assert!(os::homedir().is_none());

        for s in oldhome.iter() { setenv("HOME", *s) }
    }

    #[test]
    #[cfg(windows)]
    fn homedir() {

        let oldhome = getenv("HOME");
        let olduserprofile = getenv("USERPROFILE");

        setenv("HOME", "");
        setenv("USERPROFILE", "");

        assert!(os::homedir().is_none());

        setenv("HOME", "/home/MountainView");
        assert_eq!(os::homedir(), Some(Path("/home/MountainView")));

        setenv("HOME", "");

        setenv("USERPROFILE", "/home/MountainView");
        assert_eq!(os::homedir(), Some(Path("/home/MountainView")));

        setenv("HOME", "/home/MountainView");
        setenv("USERPROFILE", "/home/PaloAlto");
        assert_eq!(os::homedir(), Some(Path("/home/MountainView")));

        for s in oldhome.iter() { setenv("HOME", *s) }
        for s in olduserprofile.iter() { setenv("USERPROFILE", *s) }
    }

    #[test]
    fn tmpdir() {
        assert!(!os::tmpdir().to_str().is_empty());
    }

    // Issue #712
    #[test]
    fn test_list_dir_no_invalid_memory_access() {
        os::list_dir(&Path("."));
    }

    #[test]
    fn list_dir() {
        let dirs = os::list_dir(&Path("."));
        // Just assuming that we've got some contents in the current directory
        assert!(dirs.len() > 0u);

        for dir in dirs.iter() {
            debug!((*dir).clone());
        }
    }

    #[test]
    fn list_dir_empty_path() {
        let dirs = os::list_dir(&Path(""));
        assert!(dirs.is_empty());
    }

    #[test]
    #[cfg(not(windows))]
    fn list_dir_root() {
        let dirs = os::list_dir(&Path("/"));
        assert!(dirs.len() > 1);
    }
    #[test]
    #[cfg(windows)]
    fn list_dir_root() {
        let dirs = os::list_dir(&Path("C:\\"));
        assert!(dirs.len() > 1);
    }

    #[test]
    fn path_is_dir() {
        assert!((os::path_is_dir(&Path("."))));
        assert!((!os::path_is_dir(&Path("test/stdtest/fs.rs"))));
    }

    #[test]
    fn path_exists() {
        assert!((os::path_exists(&Path("."))));
        assert!((!os::path_exists(&Path(
                     "test/nonexistent-bogus-path"))));
    }

    #[test]
    fn copy_file_does_not_exist() {
      assert!(!os::copy_file(&Path("test/nonexistent-bogus-path"),
                            &Path("test/other-bogus-path")));
      assert!(!os::path_exists(&Path("test/other-bogus-path")));
    }

    #[test]
    fn copy_file_ok() {
        #[fixed_stack_segment]; #[inline(never)];

        unsafe {
            let tempdir = getcwd(); // would like to use $TMPDIR,
                                    // doesn't seem to work on Linux
            assert!((tempdir.to_str().len() > 0u));
            let input = tempdir.push("in.txt");
            let out = tempdir.push("out.txt");

            /* Write the temp input file */
            let ostream = do input.with_c_str |fromp| {
                do "w+b".with_c_str |modebuf| {
                    libc::fopen(fromp, modebuf)
                }
            };
            assert!((ostream as uint != 0u));
            let s = ~"hello";
            do "hello".with_c_str |buf| {
                let write_len = libc::fwrite(buf as *c_void,
                                             1u as size_t,
                                             (s.len() + 1u) as size_t,
                                             ostream);
                assert_eq!(write_len, (s.len() + 1) as size_t)
            }
            assert_eq!(libc::fclose(ostream), (0u as c_int));
            let in_mode = input.get_mode();
            let rs = os::copy_file(&input, &out);
            if (!os::path_exists(&input)) {
                fail!("%s doesn't exist", input.to_str());
            }
            assert!((rs));
            let rslt = run::process_status("diff", [input.to_str(), out.to_str()]);
            assert_eq!(rslt, 0);
            assert_eq!(out.get_mode(), in_mode);
            assert!((remove_file(&input)));
            assert!((remove_file(&out)));
        }
    }

    #[test]
    fn recursive_mkdir_slash() {
        let path = Path("/");
        assert!(os::mkdir_recursive(&path,  (S_IRUSR | S_IWUSR | S_IXUSR) as i32));
    }

    #[test]
    fn recursive_mkdir_empty() {
        let path = Path("");
        assert!(!os::mkdir_recursive(&path, (S_IRUSR | S_IWUSR | S_IXUSR) as i32));
    }

    #[test]
    fn memory_map_rw() {
        use result::{Ok, Err};

        let chunk = match os::MemoryMap::new(16, ~[
            os::MapReadable,
            os::MapWritable
        ]) {
            Ok(chunk) => chunk,
            Err(msg) => fail!(msg.to_str())
        };
        assert!(chunk.len >= 16);

        unsafe {
            *chunk.data = 0xBE;
            assert!(*chunk.data == 0xBE);
        }
    }

    #[test]
    fn memory_map_file() {
        #[fixed_stack_segment]; #[inline(never)];

        use result::{Ok, Err};
        use os::*;
        use libc::*;

        #[cfg(unix)]
        #[fixed_stack_segment]
        #[inline(never)]
        fn lseek_(fd: c_int, size: uint) {
            unsafe {
                assert!(lseek(fd, size as off_t, SEEK_SET) == size as off_t);
            }
        }
        #[cfg(windows)]
        #[fixed_stack_segment]
        #[inline(never)]
        fn lseek_(fd: c_int, size: uint) {
           unsafe {
               assert!(lseek(fd, size as c_long, SEEK_SET) == size as c_long);
           }
        }

        let path = tmpdir().push("mmap_file.tmp");
        let size = MemoryMap::granularity() * 2;
        remove_file(&path);

        let fd = unsafe {
            let fd = do path.with_c_str |path| {
                open(path, O_CREAT | O_RDWR | O_TRUNC, S_IRUSR | S_IWUSR)
            };
            lseek_(fd, size);
            do "x".with_c_str |x| {
                assert!(write(fd, x as *c_void, 1) == 1);
            }
            fd
        };
        let chunk = match MemoryMap::new(size / 2, ~[
            MapReadable,
            MapWritable,
            MapFd(fd),
            MapOffset(size / 2)
        ]) {
            Ok(chunk) => chunk,
            Err(msg) => fail!(msg.to_str())
        };
        assert!(chunk.len > 0);

        unsafe {
            *chunk.data = 0xbe;
            assert!(*chunk.data == 0xbe);
            close(fd);
        }
    }

    // More recursive_mkdir tests are in extra::tempfile
}


text:
<?xml version="1.0"?>
<Data>
  <Products>
    <Product Name="West Side Story" Price="9.99" SupplierID="1" />
    <Product Name="Assassins" Price="14.99" SupplierID="2" />
    <Product Name="Frogs" Price="13.99" SupplierID="1" />
    <Product Name="Sweeney Todd" Price="10.99" SupplierID="3" />
  </Products>

  <Suppliers>
    <Supplier Name="Solely Sondheim" SupplierID="1" />
    <Supplier Name="CD-by-CD-by-Sondheim" SupplierID="2" />
    <Supplier Name="Barbershop CDs" SupplierID="3" />
  </Suppliers>
</Data>

redpajama_set_name: RedPajamaGithub


text:
import css from 'styled-jsx/css'

export const normalizeStyles = css.global`
  * {
    box-sizing: border-box;
  }
  html {
    line-height: 1.15; /* 1 */
    -webkit-text-size-adjust: 100%; /* 2 */
  }

  body {
    margin: 0;
  }
  main {
    display: block;
  }

  h1 {
    font-size: 2em;
    margin: 0.67em 0;
  }

  hr {
    box-sizing: content-box; /* 1 */
    height: 0; /* 1 */
    overflow: visible; /* 2 */
  }

  pre {
    font-family: monospace; /* 1 */
    font-size: 1em; /* 2 */
  }

  a {
    background-color: transparent;
  }

  abbr[title] {
    border-bottom: none; /* 1 */
    text-decoration: underline; /* 2 */
    text-decoration: underline dotted; /* 2 */
  }

  b,
  strong {
    font-weight: bolder;
  }

  code,
  kbd,
  samp {
    font-family: monospace, monospace; /* 1 */
    font-size: 1em; /* 2 */
  }

  small {
    font-size: 80%;
  }

  sub,
  sup {
    font-size: 75%;
    line-height: 0;
    position: relative;
    vertical-align: baseline;
  }

  sub {
    bottom: -0.25em;
  }

  sup {
    top: -0.5em;
  }

  /* Embedded content
   ========================================================================== */

  /**
 * Remove the border on images inside links in IE 10.
 */

  img {
    border-style: none;
  }

  /* Forms
   ========================================================================== */

  /**
 * 1. Change the font styles in all browsers.
 * 2. Remove the margin in Firefox and Safari.
 */

  button,
  input,
  optgroup,
  select,
  textarea {
    font-family: inherit; /* 1 */
    font-size: 100%; /* 1 */
    line-height: 1.15; /* 1 */
    margin: 0; /* 2 */
  }

  /**
 * Show the overflow in IE.
 * 1. Show the overflow in Edge.
 */

  button,
  input {
    /* 1 */
    overflow: visible;
  }

  /**
 * Remove the inheritance of text transform in Edge, Firefox, and IE.
 * 1. Remove the inheritance of text transform in Firefox.
 */

  button,
  select {
    /* 1 */
    text-transform: none;
  }

  /**
 * Correct the inability to style clickable types in iOS and Safari.
 */

  button,
  [type='button'],
  [type='reset'],
  [type='submit'] {
    -webkit-appearance: button;
  }

  /**
 * Remove the inner border and padding in Firefox.
 */

  button::-moz-focus-inner,
  [type='button']::-moz-focus-inner,
  [type='reset']::-moz-focus-inner,
  [type='submit']::-moz-focus-inner {
    border-style: none;
    padding: 0;
  }

  /**
 * Restore the focus styles unset by the previous rule.
 */

  button:-moz-focusring,
  [type='button']:-moz-focusring,
  [type='reset']:-moz-focusring,
  [type='submit']:-moz-focusring {
    outline: 1px dotted ButtonText;
  }

  /**
 * Correct the padding in Firefox.
 */

  fieldset {
    padding: 0.35em 0.75em 0.625em;
  }

  legend {
    box-sizing: border-box; /* 1 */
    color: inherit; /* 2 */
    display: table; /* 1 */
    max-width: 100%; /* 1 */
    padding: 0; /* 3 */
    white-space: normal; /* 1 */
  }

  /**
 * Add the correct vertical alignment in Chrome, Firefox, and Opera.
 */

  progress {
    vertical-align: baseline;
  }

  /**
 * Remove the default vertical scrollbar in IE 10+.
 */

  textarea {
    overflow: auto;
  }

  /**
 * 1. Add the correct box sizing in IE 10.
 * 2. Remove the padding in IE 10.
 */

  [type='checkbox'],
  [type='radio'] {
    box-sizing: border-box; /* 1 */
    padding: 0; /* 2 */
  }

  /**
 * Correct the cursor style of increment and decrement buttons in Chrome.
 */

  [type='number']::-webkit-inner-spin-button,
  [type='number']::-webkit-outer-spin-button {
    height: auto;
  }

  /**
 * 1. Correct the odd appearance in Chrome and Safari.
 * 2. Correct the outline style in Safari.
 */

  [type='search'] {
    -webkit-appearance: textfield; /* 1 */
    outline-offset: -2px; /* 2 */
  }

  /**
 * Remove the inner padding in Chrome and Safari on macOS.
 */

  [type='search']::-webkit-search-decoration {
    -webkit-appearance: none;
  }

  ::-webkit-file-upload-button {
    -webkit-appearance: button; /* 1 */
    font: inherit; /* 2 */
  }

  /* Interactive
   ========================================================================== */

  /*
 * Add the correct display in Edge, IE 10+, and Firefox.
 */

  details {
    display: block;
  }

  /*
 * Add the correct display in all browsers.
 */

  summary {
    display: list-item;
  }

  /* Misc
   ========================================================================== */

  /**
 * Add the correct display in IE 10+.
 */

  template {
    display: none;
  }

  /**
 * Add the correct display in IE 10.
 */

  [hidden] {
    display: none;
  }
`


text:
package main

import (
	"database/sql"
	_ "github.com/lib/pq"
	"strconv"
)

const (
	GETNEXTVOTE = "select * from getnextvote()"
	RESETVOTES  = "select resetVotes()"
	ARCHIVEVOTE = "select archiveVote($1::int)"
)

type Repository struct {
	db *sql.DB
}

func (r *Repository) InitDB(dbUrl string) error {
	var err error
	r.db, err = sql.Open("postgres", dbUrl)
	if err != nil {
		return err
	}

	return nil
}

func (r *Repository) GetNextVote() Vote {
	var vote Vote

	var voteid int
	var talkid string
	var userid int
	var rating int

	err := r.db.QueryRow(GETNEXTVOTE).Scan(&voteid, &talkid, &userid, &rating)

	parrot.Debug("GetNextVote: " + strconv.Itoa(voteid) + " " + talkid)

	if err != nil {
		parrot.Warn("No more rows", err)
		return Vote{ID: -1}
	}

	vote.ID = voteid
	vote.TalkId = talkid
	vote.UserId = userid
	vote.Rating = rating

	return vote
}

func (r *Repository) ResetVotes() error {
	_, err := r.db.Exec(RESETVOTES)
	return err
}

func (r *Repository) ArchiveVote(id int) error {
	_, err := r.db.Exec(ARCHIVEVOTE, id)
	return err
}


text:
using System;
using System.ComponentModel;
using System.Runtime.CompilerServices;

namespace Sakuno
{
    [EditorBrowsable(EditorBrowsableState.Never)]
    public static class Int32Extensions
    {
        [MethodImpl(MethodImplOptions.AggressiveInlining)]
        public static int Clamp(this int value, int min, int max)
        {
#if NETSTANDARD2_1
            return Math.Clamp(value, min, max);
#else
            if (min > max)
                throw new ArgumentOutOfRangeException("Min must be less than or equal to max.");

            if (value < min)
                return min;

            if (value > max)
                return max;

            return value;
#endif
        }
    }
}


text:
<?xml version="1.0"?> <!DOCTYPE hibernate-mapping PUBLIC  "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
        "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
    <class name="pojo.Prosjekt" table="prosjekt">
        <id name="pid" column="prosjektId">
            <generator class="native"/>
        </id>

        <property name="navn"/>
        <property name="nummer"/>

        <set name="ansatter" table="jobber_paa" inverse="true">
            <key column="pid"/>
            <many-to-many column="ansattnr" class="pojo.Ansatt"/>
        </set>
    </class>
</hibernate-mapping>


text:
using System;

namespace RzRpgLib
{
    public class ActionExecutionException : Exception
    {
        public ActionResult Result { get; private set; }

        public ActionExecutionException( string message ) : base( message )
        {
            Result = new ActionResult( message );
        }
    }

    /// <summary>
    /// The result of attempting to perform an action.
    /// </summary>
    public class ActionResult
    {
        /// <summary>
        /// Gets whether the action successfully executed.  Executing successfully does not mean the action's effects were implemented.
        /// For example, an attack action could execute successfully but miss.  If Success is false, the Message field should contain a
        /// an explanation of why the action could not execute.
        /// </summary>
        public bool Success { get; private set; }

        /// <summary>
        /// The reason why the action could not execute if Success is false.  If Success is true, this field should be ignored.
        /// </summary>
        public string Message { get; private set; }

        public ActionResult( string message = null )
        {
            Message = message;
            Success = (Message == null);
        }
    }
}


text:
package org.bds.lang;

import org.antlr.v4.runtime.tree.ParseTree;

/**
 * Fake node used during serialization
 *
 * @author pcingola
 */
public class ParentNode extends BdsNode {

	public ParentNode() {
		super(null, null);
	}

	@Override
	protected void parse(ParseTree tree) {
		throw new RuntimeException("This method should never be invoked!");
	}

	@Override
	public void setFakeId(int id) {
		// Note: ParentNode does not invoke UpdateId
		this.id = -id;
	}

}


text:
#ifndef KAA_HPP_
#define KAA_HPP_

#include <memory>

#include <botan/botan.h>
#include <botan/init.h>

#include "kaa/IKaaClient.hpp"
#include "kaa/IKaaClientStateListener.hpp"
#include "kaa/IKaaClientPlatformContext.hpp"
#include "kaa/KaaClientPlatformContext.hpp"

namespace kaa {

/**
 * @brief Creates a new Kaa client based on @link IKaaClientPlatformContext @endlink and optional
 * @link IKaaClientStateListener @endlink.
 *
 */
class Kaa
{
public:
    /**
     * @brief Use @link newClient() @endlink to create a Kaa client instance.
     */
    Kaa() = delete;

    /**
     * @brief Use @link newClient() @endlink to create a Kaa client instance.
     */
    Kaa(const Kaa&) = delete;

    /**
     * @brief Use @link newClient() @endlink to create a Kaa client instance.
     */
    Kaa& operator=(const Kaa&) = delete;

    /**
     * @brief Creates a new instance of a Kaa client.
     *
     * @param context     Platform context.
     * @param listener    Kaa client state listener.
     *
     * @return New instance of Kaa client.
     */
    static std::shared_ptr<IKaaClient> newClient(IKaaClientPlatformContextPtr context = std::make_shared<KaaClientPlatformContext>()
                                               , IKaaClientStateListenerPtr listener = IKaaClientStateListenerPtr());

private:
    static Botan::LibraryInitializer     botanInit_;
};

}

#endif


text:
/* printfact4.c */
/*
  Fitzpatrick.  Computational Physics.  329.pdf
  2.11 Global

*/

/*
  Program to print factorials of all integers
  between 0 and 20
*/

/*
  From Fitzpatrick in 2.11
  "Global variables should be used sparingly in scientific programs (or any other type of program), since there are inherent dangers in their employment. An alteration in the value of a global variable within a given function is carried over into all other parts of the program. Unfortunately, such an alteration can sometimes happen inadvertently, as the side-effect of some other action. Thus, there is the possibility of the value of a global variable changing unexpectedly, resulting in a subtle programming error which can be extremely difficult to track down, since the offending line could be located anywhere in the program. Similar errors involving local variables are much easier to debug, since the scope of local variables is far more limited than that of global variables."
*/

#include <stdio.h>
#include <stdlib.h>

/* Prototype for function factorial() */
void factorial();

/* Global variable declarations */
int j;

double fact;

int main()
{

  /* Print factorials of all integers between 0 and 20 */
  for (j = 0; j <= 20; ++j)
    {
      factorial();
      printf("j = %3d    factorial(j) = %12.3e\n", j, fact);
    }
  return 0;
}

//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

void factorial()
{
  /*
    Function to evaluate factorial *fact (in floating-point form)
    of non-negative integer n.
  */

  int count;

  /* Abort if j is negative integer */
  if (j < 0)
    {
      printf("\nError: factorial of negative integer not defined\n");
      exit(1);
    }

  /* Calculate factorial */
  for (count = j, fact = 1.; count > 0; --count) fact *= (double) count;

  /* Return value of factorial */
  return;
}

//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%


text:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Tangent.Intermediate;

namespace Tangent.Parsing.Partial
{
    public class PartialPhrasePart
    {
        public readonly IdentifierExpression Identifier;
        public readonly PartialParameterDeclaration Parameter;
        public bool IsIdentifier { get { return Identifier != null; } }

        public PartialPhrasePart(IdentifierExpression id)
        {
            Identifier = id;
        }

        public PartialPhrasePart(PartialParameterDeclaration decl)
        {
            Parameter = decl;
        }

        public static implicit operator PartialPhrasePart(IdentifierExpression id)
        {
            return new PartialPhrasePart(id);
        }

        public static implicit operator PartialPhrasePart(PartialParameterDeclaration decl)
        {
            return new PartialPhrasePart(decl);
        }

        public override string ToString()
        {
            if (IsIdentifier) {
                return Identifier.Identifier.Value;
            } else {
                return $"({Parameter})";
            }
        }
    }
}


text:
require 'spec_helper'

#why is this the slowest?
describe "More Activations" do
  before(:each) do
    Magnum.stub(:connection).and_return(Sequel::DATABASES.first)
  end

  let(:db){Magnum.connection}

  profiles = MagnumTest.getValidTimeZoneSuperProfiles
  profiles.each do | profile |
    puts profile["name"]
    profile.delete("_id")

    it "should have each original dow covered in the DB, #{profile['name']}" do
      profile_built = Magnum::build(:super_profile, profile.to_json)
      pkg = Package.create(profile_built.convertToPackage("1"))
      @vlabel_map = VlabelMapSequel.load({:vlabel_map_id => 1, :vlabel => "wtf", :description => "wtf"})
      pkg.stub(:vlabel_map).and_return(@vlabel_map)
      mock_exit = double(:exit, :value => "123456789")
      RoutingExit.any_instance.stub(:exit_object).and_return(mock_exit)
      @week = Magnum::convert(:week, pkg)

      @week.activate
      routes = db[:yacc_route].where(route_name: @vlabel_map.vlabel).to_a

      dow_collection = routes.map {|x| x[:day_of_week]}.uniq
      @week.segments.each do | segment |
        bsum = 0
        segment.utc_segments.each do | day, range |
          next if range.empty?
          bit_shifted_day = day << 1
          bsum = bsum | bit_shifted_day
        end

        is_covered = nil
        dow_collection.each do | dow |
          is_covered = true if(bsum & dow != 0)
        end

        expect(is_covered).to eq(true)
      end
    end

    it "should have each original tod covered in the DB, #{profile['name']}" do
      profile_built = Magnum::build(:super_profile, profile.to_json)
      pkg = Package.create(profile_built.convertToPackage("1"))
      @vlabel_map = VlabelMapSequel.load({:vlabel_map_id => 1, :vlabel => "wtf", :description => "wtf"})
      pkg.stub(:vlabel_map).and_return(@vlabel_map)
      mock_exit = double(:exit, :value => "123456789")
      RoutingExit.any_instance.stub(:exit_object).and_return(mock_exit)
      @week = Magnum::convert(:week, pkg)

      @week.activate
      routes = db[:yacc_route].where(route_name: @vlabel_map.vlabel).to_a
      tod_collection = routes.map {|x| [x[:day_of_week], x[:begin_time]..x[:end_time]] }

      @week.segments.each do | segment |
        segment.utc_segments.each do | day, range |
        next if range.empty?
        range.each do | time_range |
          time_range_covered  = (time_range['start']..time_range['end'])

          tod_collection.each do | tod_range |
            bit_shifted_day = day << 1
            if(bit_shifted_day & tod_range[0] != 0)
              time_range_covered = time_range_covered.to_a - tod_range[1].to_a
            end
          end
          expect(time_range_covered).to eq([])
        end
        end
      end
    end

    it "should not overlap time segments in the DB, #{profile['name']}" do
      profile_built = Magnum::build(:super_profile, profile.to_json)
      pkg = Package.create(profile_built.convertToPackage("1"))
      @vlabel_map = VlabelMapSequel.load({:vlabel_map_id => 1, :vlabel => "wtf", :description => "wtf"})
      pkg.stub(:vlabel_map).and_return(@vlabel_map)
      mock_exit = double(:exit, :value => "123456789")
      RoutingExit.any_instance.stub(:exit_object).and_return(mock_exit)
      @week = Magnum::convert(:week, pkg)

      @week.activate
      routes = db[:yacc_route].where(route_name: @vlabel_map.vlabel).to_a

      routes.each do | route |
        routes.each do | inner_route |
          if(route != inner_route && route[:day_of_week] != inner_route[:day_of_week] && route[:day_of_week] & inner_route[:day_of_week] != 0)
            route_range = route[:begin_time]..route[:end_time]
            expect(route_range.cover? inner_route[:begin_time]).to be_falsey
            expect(route_range.cover? inner_route[:end_time]).to be_falsey
          end
        end
      end
    end

  end
end


text:
/*
 *Ваши права на использование кода регулируются данной лицензией http://o-s-a.net/doc/license_simple_engine.pdf
*/

using System;
using System.Collections.Generic;
using System.Threading;
using System.Windows.Forms;
using System.Windows.Forms.Integration;
using OsEngine.Entity;
using OsEngine.Logging;
using OsEngine.Market;

namespace OsEngine.OsTrader
{
    /// <summary>
    /// класс отвечающий за прорисовку глобальной позиции всех роботов в главном окне
    /// </summary>
    public class GlobalPosition
    {

// сервис

        /// <summary>
        /// конструктор
        /// </summary>
        /// <param name="allPositionHost">хост на который будем рисовать дата грид</param>
        /// <param name="startProgram">программа запустившая класс</param>
        public GlobalPosition(WindowsFormsHost allPositionHost, StartProgram startProgram)
        {
            _startProgram = startProgram;

            _host = allPositionHost;

            _grid = CreateNewTable();

            _host.Child = _grid;
            _host.Child.Show();

            if (Watcher == null)
            {
                Watcher = new Thread(WatcherHome);
                Watcher.IsBackground = true;
                Watcher.Name = "GlobalPositionThread";
                Watcher.Start();
            }
        }

        /// <summary>
        /// добавить ещё один журнал в коллекцию для прорисовки его сделок
        /// </summary>
        /// <param name="journal">новый журнал</param>
        public void SetJournal(Journal.Journal journal)
        {
            try
            {
                if (_journals == null)
                {
                    _journals = new List<Journal.Journal>();
                }

                if (_journals.Find(journal1 => journal1.Name == journal.Name) == null)
                {
                    _journals.Add(journal);
                    journal.PositionStateChangeEvent += journal_PositionChangeEvent;

                    List<Position> openPositions = journal.OpenPositions;

                    for (int i = 0; openPositions != null && i < openPositions.Count; i++)
                    {
                        journal_PositionChangeEvent(openPositions[i]);
                    }
                }
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

        /// <summary>
        /// очистить от ранее загруженых журналов
        /// </summary>
        public void ClearJournals()
        {
            try
            {
                if (_grid.InvokeRequired)
                {
                    _grid.Invoke(new Action(ClearJournals));
                    return;
                }

                for (int i = 0; _journals != null && i < _journals.Count; i++)
                { // отписываемся от обновления позиции
                    _journals[i].PositionStateChangeEvent -= journal_PositionChangeEvent;
                }

                _journals = null;
                _grid.Rows.Clear();
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

        /// <summary>
        /// журналы за которыми мы следим
        /// </summary>
        private List<Journal.Journal> _journals;

        /// <summary>
        /// хост на котором отображаем таблицу
        /// </summary>
        private WindowsFormsHost _host;

        /// <summary>
        /// таблица для прорисовки позиций
        /// </summary>
        private DataGridView _grid;

        /// <summary>
        /// программа запустившая класс
        /// </summary>
        private StartProgram _startProgram;

//прорисовка

        /// <summary>
        /// остановить прорисовку элементов
        /// </summary>
        public void StopPaint()
        {
            try
            {
                if (!_host.CheckAccess())
                {
                    _host.Dispatcher.Invoke(StopPaint);
                    return;
                }
                _host.Child = null;
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

        /// <summary>
        /// запустить прорисовку элементов
        /// </summary>
        public void StartPaint()
        {
            try
            {
                if (!_host.CheckAccess())
                {
                    _host.Dispatcher.Invoke(StartPaint);
                    return;
                }
                _host.Child = _grid;
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

        /// <summary>
        /// создать таблицу
        /// </summary>
        /// <returns>таблица для прорисовки на ней позиций</returns>
        private DataGridView CreateNewTable()
        {
            try
            {
                DataGridView newGrid = DataGridFactory.GetDataGridPosition();

                return newGrid;
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
            return null;
        }

        /// <summary>
        /// в журнале изменилась позиция
        /// </summary>
        /// <param name="position">позиция</param>
        [System.Runtime.ExceptionServices.HandleProcessCorruptedStateExceptionsAttribute]
        public void journal_PositionChangeEvent(Position position)
        {
            // В ТЕСТЕРЕ позиции прорисоываются по очереди, В реале, в методе ThreadWatcher()
            if (_startProgram != StartProgram.IsTester)
            {
                return;
            }

            try
            {
                if (_grid.InvokeRequired)
                {
                    _grid.Invoke(new Action<Position>(journal_PositionChangeEvent), position);
                    return;
                }

                if (position.State != PositionStateType.Open && position.State != PositionStateType.Opening &&
                    position.State != PositionStateType.Closing && position.State != PositionStateType.ClosingFail)
                {// сделка была удалена. Надо её удалить отовсюду
                    for (int i = 0; i < _grid.Rows.Count; i++)
                    {
                        if ((int)_grid.Rows[i].Cells[0].Value == position.Number)
                        {
                            _grid.Rows.Remove(_grid.Rows[i]);
                            return;
                        }
                    }
                }
                else
                { // сделкка должна быть прорисована в таблице

                    for (int i = 0; i < _grid.Rows.Count; i++)
                    {
                        if ((int)_grid.Rows[i].Cells[0].Value == position.Number)
                        {
                            _grid.Rows.Remove(_grid.Rows[i]);
                            DataGridViewRow row1 = GetRow(position);
                            if (row1 != null)
                            {
                                _grid.Rows.Insert(i, row1);
                            }

                            return;
                        }
                    }
                    DataGridViewRow row = GetRow(position);
                    if (row != null)
                    {
                        _grid.Rows.Add(row);
                    }
                }
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

        /// <summary>
        /// взять строку для таблицы представляющую позицию
        /// </summary>
        /// <param name="position">позиция</param>
        /// <returns>строка для таблицы</returns>
        private DataGridViewRow GetRow(Position position)
        {
            if (position == null)
            {
                return null;
            }

            try
            {
                DataGridViewRow nRow = new DataGridViewRow();

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[0].Value = position.Number;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[1].Value = position.TimeCreate;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[2].Value = position.TimeClose;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[3].Value = position.NameBot;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[4].Value = position.SecurityName;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[5].Value = position.Direction;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[6].Value = position.State;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[7].Value = position.MaxVolume;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[8].Value = position.OpenVolume;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[9].Value = position.WaitVolume;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[10].Value = position.EntryPrice;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[11].Value = position.ClosePrice;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[12].Value = position.ProfitPortfolioPunkt;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[13].Value = position.StopOrderRedLine;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[14].Value = position.StopOrderPrice;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[15].Value = position.ProfitOrderRedLine;

                nRow.Cells.Add(new DataGridViewTextBoxCell());
                nRow.Cells[16].Value = position.ProfitOrderPrice;

                return nRow;
            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
            return null;
        }

        /// <summary>
        /// поток
        /// </summary>
        private Thread Watcher;

        /// <summary>
        /// место работы потока который сохраняет логи
        /// </summary>
        private void WatcherHome()
        {
            if (_startProgram != StartProgram.IsOsTrader)
            {
                return;
            }

            while (true)
            {
                Thread.Sleep(2000);

                CheckPosition();

                if (!MainWindow.ProccesIsWorked)
                {
                    return;
                }
            }
        }

        /// <summary>
        /// проверить позиции на правильность прорисовки
        /// </summary>
        [System.Runtime.ExceptionServices.HandleProcessCorruptedStateExceptions]
        private void CheckPosition()
        {
            if (_grid.InvokeRequired)
            {
                _grid.Invoke(new Action(CheckPosition));
                return;
            }
            try
            {

                List<Position> openPositions = new List<Position>();

                for (int i = 0; _journals != null && i < _journals.Count; i++)
                {
                    if (_journals[i].OpenPositions != null && _journals[i].OpenPositions.Count != 0)
                    {
                        openPositions.AddRange(_journals[i].OpenPositions);
                    }
                }

                for (int i1 = 0; i1 < openPositions.Count; i1++)
                {
                    Position position = openPositions[i1];
                    DataGridViewRow row = GetRow(position);
                    bool isIn = false;
                    for (int i = 0; i < _grid.Rows.Count; i++)
                    {
                        if (_grid.Rows[i].Cells[0].Value != null &&
                            (int) _grid.Rows[i].Cells[0].Value == position.Number)
                        {
                            _grid.Rows.Remove(_grid.Rows[i]);
                            DataGridViewRow row1 = GetRow(position);
                            if (row1 != null)
                            {
                                _grid.Rows.Add(row1);
                            }
                            isIn = true;
                            break;
                        }
                    }

                    if (isIn == false && row != null)
                    {
                        _grid.Rows.Add(row);
                    }
                }

                for (int i = 0; i < _grid.Rows.Count; i++)
                {
                    if (openPositions.Find(pos => pos.Number == (int) _grid.Rows[i].Cells[0].Value) == null)
                    {
                        _grid.Rows.Remove(_grid.Rows[i]);
                    }
                }

            }
            catch (Exception error)
            {
                SendNewLogMessage(error.ToString(), LogMessageType.Error);
            }
        }

// сообщения в лог

        /// <summary>
        /// выслать новое сообщение на верх
        /// </summary>
        private void SendNewLogMessage(string message, LogMessageType type)
        {
            if (LogMessageEvent != null)
            {
                LogMessageEvent(message, type);
            }
            else if (type == LogMessageType.Error)
            {
                System.Windows.MessageBox.Show(message);
            }
        }

        /// <summary>
        /// исходящее сообщение для лога
        /// </summary>
        public event Action<string, LogMessageType> LogMessageEvent;

    }
}


text:
require_relative './quiz_macro_test'

module CheckedAttributes

  def self.included(base)
    base.extend ClassMethods
  end

  module ClassMethods

    def attr_checked(attribute, &validation)
      define_method "#{attribute}=" do |value|
        raise 'Invalid attribute' unless validation.call(value)
        instance_variable_set("@#{attribute}", value)
      end

      define_method attribute do
        instance_variable_get "@#{attribute}"
      end
    end

  end
end

class Person
  include CheckedAttributes

  attr_checked :age do |v|
    v >= 18
  end
end


text:
using namespace Upp;

#define LAYOUTFILE <UniqTest/UniqTest.lay>
#include <CtrlCore/lay.h>

class UniqTest : public WithUniqTestLayout<TopWindow>
{
	private:
	public:
		typedef UniqTest CLASSNAME;
		UniqTest();

		// handles news app instances
		void handleInstance(Vector<String> const &v);

};

#endif


text:
//%LICENSE////////////////////////////////////////////////////////////////
//
// Licensed to The Open Group (TOG) under one or more contributor license
// agreements.  Refer to the OpenPegasusNOTICE.txt file distributed with
// this work for additional information regarding copyright ownership.
// Each contributor licenses this file to you under the OpenPegasus Open
// Source License; you may not use this file except in compliance with the
// License.
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
// to deal in the Software without restriction, including without limitation
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
// and/or sell copies of the Software, and to permit persons to whom the
// Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included
// in all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
// IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
// CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
// SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
//
//////////////////////////////////////////////////////////////////////////
//
//%/////////////////////////////////////////////////////////////////////////

#ifndef __UNIX_REDDROPPERSERVICE_H
#define __UNIX_REDDROPPERSERVICE_H

#include "CIM_DropperService.h"

#include "UNIX_REDDropperServiceDeps.h"

#define PROPERTY_MIN_QUEUE_THRESHOLD				"MinQueueThreshold"
#define PROPERTY_MAX_QUEUE_THRESHOLD				"MaxQueueThreshold"
#define PROPERTY_START_PROBABILITY				"StartProbability"
#define PROPERTY_STOP_PROBABILITY				"StopProbability"
#define PROPERTY_THRESHOLD_UNITS				"ThresholdUnits"

class UNIX_REDDropperService :
	public CIM_DropperService
{
public:

	UNIX_REDDropperService();
	~UNIX_REDDropperService();

	virtual Boolean initialize();
	virtual Boolean load(int&);
	virtual Boolean finalize();
	virtual Boolean find(Array<CIMKeyBinding>&);
	virtual Boolean validateKey(CIMKeyBinding&) const;
	virtual void setScope(CIMName);

	virtual Boolean getInstanceID(CIMProperty&) const;
	virtual String getInstanceID() const;
	virtual Boolean getCaption(CIMProperty&) const;
	virtual String getCaption() const;
	virtual Boolean getDescription(CIMProperty&) const;
	virtual String getDescription() const;
	virtual Boolean getElementName(CIMProperty&) const;
	virtual String getElementName() const;
	virtual Boolean getInstallDate(CIMProperty&) const;
	virtual CIMDateTime getInstallDate() const;
	virtual Boolean getName(CIMProperty&) const;
	virtual String getName() const;
	virtual Boolean getOperationalStatus(CIMProperty&) const;
	virtual Array<Uint16> getOperationalStatus() const;
	virtual Boolean getStatusDescriptions(CIMProperty&) const;
	virtual Array<String> getStatusDescriptions() const;
	virtual Boolean getStatus(CIMProperty&) const;
	virtual String getStatus() const;
	virtual Boolean getHealthState(CIMProperty&) const;
	virtual Uint16 getHealthState() const;
	virtual Boolean getCommunicationStatus(CIMProperty&) const;
	virtual Uint16 getCommunicationStatus() const;
	virtual Boolean getDetailedStatus(CIMProperty&) const;
	virtual Uint16 getDetailedStatus() const;
	virtual Boolean getOperatingStatus(CIMProperty&) const;
	virtual Uint16 getOperatingStatus() const;
	virtual Boolean getPrimaryStatus(CIMProperty&) const;
	virtual Uint16 getPrimaryStatus() const;
	virtual Boolean getEnabledState(CIMProperty&) const;
	virtual Uint16 getEnabledState() const;
	virtual Boolean getOtherEnabledState(CIMProperty&) const;
	virtual String getOtherEnabledState() const;
	virtual Boolean getRequestedState(CIMProperty&) const;
	virtual Uint16 getRequestedState() const;
	virtual Boolean getEnabledDefault(CIMProperty&) const;
	virtual Uint16 getEnabledDefault() const;
	virtual Boolean getTimeOfLastStateChange(CIMProperty&) const;
	virtual CIMDateTime getTimeOfLastStateChange() const;
	virtual Boolean getAvailableRequestedStates(CIMProperty&) const;
	virtual Array<Uint16> getAvailableRequestedStates() const;
	virtual Boolean getTransitioningToState(CIMProperty&) const;
	virtual Uint16 getTransitioningToState() const;
	virtual Boolean getSystemCreationClassName(CIMProperty&) const;
	virtual String getSystemCreationClassName() const;
	virtual Boolean getSystemName(CIMProperty&) const;
	virtual String getSystemName() const;
	virtual Boolean getCreationClassName(CIMProperty&) const;
	virtual String getCreationClassName() const;
	virtual Boolean getPrimaryOwnerName(CIMProperty&) const;
	virtual String getPrimaryOwnerName() const;
	virtual Boolean getPrimaryOwnerContact(CIMProperty&) const;
	virtual String getPrimaryOwnerContact() const;
	virtual Boolean getStartMode(CIMProperty&) const;
	virtual String getStartMode() const;
	virtual Boolean getStarted(CIMProperty&) const;
	virtual Boolean getStarted() const;
	virtual Boolean getEnabled(CIMProperty&) const;
	virtual Boolean getEnabled() const;
	virtual Boolean getDropperType(CIMProperty&) const;
	virtual Uint16 getDropperType() const;
	virtual Boolean getOtherDropperType(CIMProperty&) const;
	virtual String getOtherDropperType() const;
	virtual Boolean getAlwaysDrop(CIMProperty&) const;
	virtual Uint16 getAlwaysDrop() const;
	virtual Boolean getDropFrom(CIMProperty&) const;
	virtual Uint16 getDropFrom() const;
	virtual Boolean getDropStartMetric(CIMProperty&) const;
	virtual Uint16 getDropStartMetric() const;
	virtual Boolean getDropMaintainMetric(CIMProperty&) const;
	virtual Uint16 getDropMaintainMetric() const;
	virtual Boolean getMinQueueThreshold(CIMProperty&) const;
	virtual Uint32 getMinQueueThreshold() const;
	virtual Boolean getMaxQueueThreshold(CIMProperty&) const;
	virtual Uint32 getMaxQueueThreshold() const;
	virtual Boolean getStartProbability(CIMProperty&) const;
	virtual Uint32 getStartProbability() const;
	virtual Boolean getStopProbability(CIMProperty&) const;
	virtual Uint32 getStopProbability() const;
	virtual Boolean getThresholdUnits(CIMProperty&) const;
	virtual Uint16 getThresholdUnits() const;

private:
	CIMName currentScope;

#	include "UNIX_REDDropperServicePrivate.h"

};

#endif /* UNIX_REDDROPPERSERVICE */


text:
CanTango.configure do |config|
  config.guest.user Proc.new { Guest.instance }

  config.cache_engine.set :on
  config.permit_engine.set :on
  config.permission_engine.set :on
end