<commit_before>#![allow(non_snake_case)]

use std::str::from_utf8;

use rustc_serialize::json;
use curl::http;

pub struct Keystore{
    endpoint: String
}

impl Keystore {
    pub fn new(address: &str) ->  Keystore {
        Keystore {
            endpoint: format!("http://{}/v1/kv", address)
        }
    }

    pub fn set_key(&self, key: String, value: String) {
        let url = format!("{}/{}", self.endpoint, key);
        let resp = http::handle()
            .put(url, &value)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            panic!("Consul: Error setting a key!");
        }
    }

    pub fn acquire_lock(&self, key: String, address: &String, session_id: &String) -> bool {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}?acquire={}", self.endpoint, key, session_id);
        }
        else {
            url = format!("{}/{}?acquire={}", self.endpoint, key, session_id);
        }
        let resp = http::handle()
            .put(url, address)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            panic!("Consul: Error acquiring a lock!");
        }
        let result = from_utf8(resp.get_body()).unwrap();
        if result == "true" {
            return true;
        }
        false
    }

    pub fn release_lock(&self, key: String, address: &str, session_id: &String) -> bool {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}?release={}", self.endpoint, key, session_id);
        }
        else {
            url = format!("{}/{}?release={}", self.endpoint, key, session_id);
        }
        let resp = http::handle()
            .put(url, address)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            panic!("Consul: Error releasing a lock!");
        }
        let result = from_utf8(resp.get_body()).unwrap();
        if result == "true" {
            return true;
        }
        false
    }

    pub fn get_key(&self, key: String) -> Option<String> {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}", self.endpoint, key);
        }
        else {
            url = format!("{}/{}", self.endpoint, key);
        }
        let resp = http::handle().get(url).exec().unwrap();
        let result = from_utf8(resp.get_body()).unwrap();
        if resp.get_code() != 200 {
            return None;
        }
        let json_data = match json::Json::from_str(result) {
            Ok(value) => value,
            Err(err) => panic!("consul: Could not convert to json: {:?}. Err: {}", result, err)
        };
        let v_json = json_data.as_array().unwrap();
        super::get_string(&v_json[0], &["Value"])
    }

    pub fn delete_key(&self, key: String) {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}", self.endpoint, key);
        }
        else {
            url = format!("{}/{}", self.endpoint, key);
        }
        let resp = http::handle().delete(url).exec().unwrap();
//         let result = from_utf8(resp.get_body()).unwrap();
        if resp.get_code() != 200 {
            panic!("Could not delete key: {}", key);
        }
    }

}
<commit_msg>Bugfixes<commit_after>#![allow(non_snake_case)]

use std::str::from_utf8;

use rustc_serialize::json;
use curl::http;

pub struct Keystore{
    endpoint: String
}

impl Keystore {
    pub fn new(address: &str) ->  Keystore {
        Keystore {
            endpoint: format!("http://{}/v1/kv", address)
        }
    }

    pub fn set_key(&self, key: String, value: String) {
        let url = format!("{}/{}", self.endpoint, key);
        let resp = http::handle()
            .put(url, &value)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            panic!("Consul: Error setting a key!");
        }
    }

    pub fn acquire_lock(&self, key: String, address: &String, session_id: &String) -> bool {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}?acquire={}", self.endpoint, key, session_id);
        }
        else {
            url = format!("{}/{}?acquire={}", self.endpoint, key, session_id);
        }
        let resp = http::handle()
            .put(url, address)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            println!("Consul: Error acquiring a lock!");
            return false;
        }
        let result = from_utf8(resp.get_body()).unwrap();
        if result == "true" {
            return true;
        }
        false
    }

    pub fn release_lock(&self, key: String, address: &str, session_id: &String) -> bool {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}?release={}", self.endpoint, key, session_id);
        }
        else {
            url = format!("{}/{}?release={}", self.endpoint, key, session_id);
        }
        let resp = http::handle()
            .put(url, address)
            .content_type("application/json")
            .exec().unwrap();
        if resp.get_code() != 200 {
            panic!("Consul: Error releasing a lock!");
        }
        let result = from_utf8(resp.get_body()).unwrap();
        if result == "true" {
            return true;
        }
        false
    }

    pub fn get_key(&self, key: String) -> Option<String> {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}", self.endpoint, key);
        }
        else {
            url = format!("{}/{}", self.endpoint, key);
        }
        let resp = http::handle().get(url).exec().unwrap();
        let result = from_utf8(resp.get_body()).unwrap();
        if resp.get_code() != 200 {
            return None;
        }
        let json_data = match json::Json::from_str(result) {
            Ok(value) => value,
            Err(err) => panic!("consul: Could not convert to json: {:?}. Err: {}", result, err)
        };
        let v_json = json_data.as_array().unwrap();
        super::get_string(&v_json[0], &["Value"])
    }

    pub fn delete_key(&self, key: String) {
        let url;
        if key.to_owned().into_bytes()[0] == 0x2f {
            url = format!("{}{}", self.endpoint, key);
        }
        else {
            url = format!("{}/{}", self.endpoint, key);
        }
        let resp = http::handle().delete(url).exec().unwrap();
//         let result = from_utf8(resp.get_body()).unwrap();
        if resp.get_code() != 200 {
            panic!("Could not delete key: {}", key);
        }
    }

}
<|endoftext|>


<commit_before>//! Implementation of IRC codec for Tokio.
use bytes::BytesMut;
use tokio_io::codec::{Decoder, Encoder};

use error;
use line::LineCodec;
use message::Message;

/// An IRC codec built around an inner codec.
pub struct IrcCodec {
    inner: LineCodec,
}

impl IrcCodec {
    /// Creates a new instance of IrcCodec wrapping a LineCodec with the specific encoding.
    pub fn new(label: &str) -> error::Result<IrcCodec> {
        LineCodec::new(label).map(|codec| IrcCodec { inner: codec })
    }

    /// Sanitizes the input string by cutting up to (and including) the first occurence of a line
    /// terminiating phrase (`\r\n`, `\r`, or `\n`). This is used in sending messages back to
    /// prevent the injection of additional commands.
    pub(crate) fn sanitize(mut data: String) -> String {
        // n.b. ordering matters here to prefer "\r\n" over "\r"
        if let Some((pos, len)) = ["\r\n", "\r", "\n"]
            .iter()
            .flat_map(|needle| data.find(needle).map(|pos| (pos, needle.len())))
            .min_by_key(|&(pos, _)| pos)
        {
            data.truncate(pos + len);
        }
        data
    }

}

impl Decoder for IrcCodec {
    type Item = Message;
    type Error = error::ProtocolError;

    fn decode(&mut self, src: &mut BytesMut) -> error::Result<Option<Message>> {
        self.inner.decode(src).and_then(|res| {
            res.map_or(Ok(None), |msg| msg.parse::<Message>().map(Some))
        })
    }
}

impl Encoder for IrcCodec {
    type Item = Message;
    type Error = error::ProtocolError;

    fn encode(&mut self, msg: Message, dst: &mut BytesMut) -> error::Result<()> {
        self.inner.encode(IrcCodec::sanitize(msg.to_string()), dst)
    }
}
<commit_msg>Made IrcCodec::sanitize part of the public API and improved documentation a bit.<commit_after>//! Implementation of IRC codec for Tokio.
use bytes::BytesMut;
use tokio_io::codec::{Decoder, Encoder};

use error;
use line::LineCodec;
use message::Message;

/// An IRC codec built around an inner codec.
pub struct IrcCodec {
    inner: LineCodec,
}

impl IrcCodec {
    /// Creates a new instance of IrcCodec wrapping a LineCodec with the specific encoding.
    pub fn new(label: &str) -> error::Result<IrcCodec> {
        LineCodec::new(label).map(|codec| IrcCodec { inner: codec })
    }

    /// Sanitizes the input string by cutting up to (and including) the first occurence of a line
    /// terminiating phrase (`\r\n`, `\r`, or `\n`). This is used in sending messages through the
    /// codec to prevent the injection of additional commands.
    pub fn sanitize(mut data: String) -> String {
        // n.b. ordering matters here to prefer "\r\n" over "\r"
        if let Some((pos, len)) = ["\r\n", "\r", "\n"]
            .iter()
            .flat_map(|needle| data.find(needle).map(|pos| (pos, needle.len())))
            .min_by_key(|&(pos, _)| pos)
        {
            data.truncate(pos + len);
        }
        data
    }

}

impl Decoder for IrcCodec {
    type Item = Message;
    type Error = error::ProtocolError;

    fn decode(&mut self, src: &mut BytesMut) -> error::Result<Option<Message>> {
        self.inner.decode(src).and_then(|res| {
            res.map_or(Ok(None), |msg| msg.parse::<Message>().map(Some))
        })
    }
}

impl Encoder for IrcCodec {
    type Item = Message;
    type Error = error::ProtocolError;

    fn encode(&mut self, msg: Message, dst: &mut BytesMut) -> error::Result<()> {
        self.inner.encode(IrcCodec::sanitize(msg.to_string()), dst)
    }
}
<|endoftext|>


<commit_before>//!
//! A convenient structure to store and load settings.
//!
//! It is meant for items that are rarely read and stored, like command line flags or
//! application configuration.
//!
//! `knob::Settings` expects all values to implement `Show` + `FromStr` and stores them as
//! strings internally. This allows sideloading of settings through multiple means, e.g.
//! the command line or a simple config file. knob is not meant for structured data. If
//! you want to load such data, store the location of the data as a Knob setting and do
//! the loading parsing yourself.
//!
//! `knob` is typesafe in a sense that it will return you the type you wanted back if possible and
//! fails otherwise.
//!
//! `knob` allows you to decorate the `Settings` structure yourself for convenience (see examples).
//!
//! # Storing and fetching values
//!
//! The following example shows you how to store an IP address in `knob`:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use std::io::net::ip::IpAddr;
//! use knob::Settings;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set("ip", "0.0.0.0");
//!   let socket: IpAddr = settings.fetch("ip").unwrap();
//!   assert_eq!(socket.to_str(), "0.0.0.0".to_owned());
//! }
//! ~~~
//!
//! This works the same for IPv6 addresses:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::IpAddr;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set("ip", "::0.0.0.1");
//!   let socket: IpAddr = settings.fetch("ip").unwrap();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! # Providing your own keys
//!
//! You can use enums as keys, as long as they implement `Show`:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::IpAddr;
//!
//! #[deriving(Show)]
//! enum Keys {
//!   Port,
//!   Ip,
//!   Addr,
//! }
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set(Ip, "::0.0.0.1");
//!   let socket: IpAddr = settings.fetch(Ip).unwrap();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! # Registering command line options
//!
//! `knob` allows you to register command line options to read from the command line later.
//!
//! The options are `getopts` option groups.
//!
//! If the loading of the command line args fails, an error will be returned.
//!
//! ~~~{.rust}
//! extern crate getopts;
//! extern crate knob;
//!
//! use getopts::optopt;
//! use knob::Settings;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.opt(optopt("p", "port", "the port to bind to", "4000"));
//!   settings.opt(optopt("e", "environment", "the environment to run in", ""));
//!   let errors = settings.load_os_args();
//!   if errors.is_some() {
//!     println!("{}", settings.usage("Try one of these:"));
//!   }
//! }
//! ~~~
//!
//! # Decorating the settings struct
//!
//! To make matters more convenient, you can implement a decorator
//! to implement your own loading behaviour.
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::{IpAddr,Ipv4Addr,SocketAddr};
//!
//! #[deriving(Show)]
//! enum Keys {
//!   Port,
//!   Ip,
//!   Addr,
//! }
//!
//! pub trait SocketSettings {
//!   fn socket(&self) -> SocketAddr;
//!   fn port(&self) -> u16;
//!   fn ip(&self) -> IpAddr;
//! }
//!
//! impl SocketSettings for Settings {
//!   fn socket(&self) -> SocketAddr {
//!     self.fetch_with(Addr, |addr| {
//!       match addr {
//!         Some(socket_addr) => { socket_addr },
//!         None => {
//!           let port: u16 = self.port();
//!           let ip: IpAddr = self.ip();
//!           SocketAddr { ip: ip, port: port }
//!         }
//!       }
//!     })
//!   }
//!
//!   fn port(&self) -> u16 {
//!     self.fetch(Port).unwrap_or(8080)
//!   }
//!
//!   fn ip(&self) -> IpAddr {
//!     self.fetch(Ip).unwrap_or(Ipv4Addr(127,0,0,1))
//!   }
//! }
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set(Ip, "::0.0.0.1");
//!   let socket: IpAddr = settings.ip();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! knob goes up to 11.

#![crate_id = "github.com/skade/knob#knob:1.1.1"]
#![crate_type = "lib"]
#![comment = "A convenient Rust settings system"]
#![license = "MIT"]

extern crate getopts;
extern crate collections;

use collections::hashmap::HashMap;
use std::os;
use std::from_str::FromStr;
use std::to_str::ToStr;

use getopts::{usage,getopts,OptGroup};
use getopts::Fail_;

/// The settings structure we save the options and settings in.
#[deriving(Clone)]
pub struct Settings {
  store: HashMap<~str,~str>,
  options: Box<Vec<OptGroup>>,
}

impl Settings {
  /// Create a new Settings struct.
  pub fn new() -> Settings {
    Settings { store: HashMap::new(), options: box Vec::new() }
  }

  /// Set a settings key to a value. The value will be serialized.
  pub fn set<A: ToStr, T: ToStr>(&mut self, setting: A, value: T) {
    self.store.swap(setting.to_str(), value.to_str());
  }

  /// Set a value using an Option struct. The value will only be set if the
  /// Some value is given. This way, you can avoid unwrapping the result of a
  /// previous operation by yourself.
  pub fn set_opt<A: ToStr, T: ToStr>(&mut self, setting: A, value: Option<T>) {
    if !value.is_none() {
      self.store.swap(setting.to_str(), value.unwrap().to_str());
    }
  }

  /// Fetch a setting for a key. Fails if the setting is present but could not be
  /// parsed.
  pub fn fetch<A: ToStr, T: FromStr>(&self, setting: A) -> Option<T> {
    match self.store.find(&setting.to_str()) {
      Some(string) => {
        let value = from_str(string.to_owned());
        if value.is_none() {
          fail!("setting could not be parsed:" + setting.to_str())
        }
        value
      },
      None => { None }
    }
  }

  /// Fetch a setting for a key and pass it to given function. The result of the function
  /// will be returned.
  pub fn fetch_with<A: ToStr, T: FromStr>(&self, setting: A, f: |Option<T>| -> T) -> T {
    let value = self.fetch(setting.to_str());
    f(value)
  }

  /// Register a commandline for laster use with load_args.
  ///
  /// Currently, only optopt and reqopt are properly supported.
  pub fn opt(&mut self, opt: OptGroup) {
    self.options.push(opt);
  }

  /// Load the command line argument given by the OS.
  ///
  /// Optionally returns failures.
  pub fn load_os_args(&mut self) -> Option<Fail_> {
    let args = os::args();
    self.load_args(args)
  }

  /// Load a list of command line arguments.
  ///
  /// Automatically sets "knob.progname" to the name of the program.
  ///
  /// Optionally returns failures.
  pub fn load_args(&mut self, args: Vec<~str>) -> Option<Fail_> {
    let ref prog_name = args.get(0);

    self.set("knob.progname", prog_name.clone());

    let matches = match getopts(args.tail(), self.options.as_slice()) {
      Ok(m) => { m }
      Err(fail) => { return Some(fail) }
    };

    let given_options = self.options.clone();
    for opt in given_options.iter() {
      let opt_strings = &[opt.short_name.clone(), opt.long_name.clone()];
      self.set_opt(opt.long_name.clone(), matches.opts_str(opt_strings))
    };
    None
  }

  /// Returns the usage string for the stored OptGroups. Pass `brief`
  /// to have it included.
  pub fn usage(&self, brief: &str) -> ~str {
    usage(brief, self.options.as_slice())
  }
}

<commit_msg>Make docs and code of `set_opt` clearer<commit_after>//!
//! A convenient structure to store and load settings.
//!
//! It is meant for items that are rarely read and stored, like command line flags or
//! application configuration.
//!
//! `knob::Settings` expects all values to implement `Show` + `FromStr` and stores them as
//! strings internally. This allows sideloading of settings through multiple means, e.g.
//! the command line or a simple config file. knob is not meant for structured data. If
//! you want to load such data, store the location of the data as a Knob setting and do
//! the loading parsing yourself.
//!
//! `knob` is typesafe in a sense that it will return you the type you wanted back if possible and
//! fails otherwise.
//!
//! `knob` allows you to decorate the `Settings` structure yourself for convenience (see examples).
//!
//! # Storing and fetching values
//!
//! The following example shows you how to store an IP address in `knob`:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use std::io::net::ip::IpAddr;
//! use knob::Settings;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set("ip", "0.0.0.0");
//!   let socket: IpAddr = settings.fetch("ip").unwrap();
//!   assert_eq!(socket.to_str(), "0.0.0.0".to_owned());
//! }
//! ~~~
//!
//! This works the same for IPv6 addresses:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::IpAddr;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set("ip", "::0.0.0.1");
//!   let socket: IpAddr = settings.fetch("ip").unwrap();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! # Providing your own keys
//!
//! You can use enums as keys, as long as they implement `Show`:
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::IpAddr;
//!
//! #[deriving(Show)]
//! enum Keys {
//!   Port,
//!   Ip,
//!   Addr,
//! }
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set(Ip, "::0.0.0.1");
//!   let socket: IpAddr = settings.fetch(Ip).unwrap();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! # Registering command line options
//!
//! `knob` allows you to register command line options to read from the command line later.
//!
//! The options are `getopts` option groups.
//!
//! If the loading of the command line args fails, an error will be returned.
//!
//! ~~~{.rust}
//! extern crate getopts;
//! extern crate knob;
//!
//! use getopts::optopt;
//! use knob::Settings;
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.opt(optopt("p", "port", "the port to bind to", "4000"));
//!   settings.opt(optopt("e", "environment", "the environment to run in", ""));
//!   let errors = settings.load_os_args();
//!   if errors.is_some() {
//!     println!("{}", settings.usage("Try one of these:"));
//!   }
//! }
//! ~~~
//!
//! # Decorating the settings struct
//!
//! To make matters more convenient, you can implement a decorator
//! to implement your own loading behaviour.
//!
//! ~~~{.rust}
//! extern crate knob;
//!
//! use knob::Settings;
//! use std::io::net::ip::{IpAddr,Ipv4Addr,SocketAddr};
//!
//! #[deriving(Show)]
//! enum Keys {
//!   Port,
//!   Ip,
//!   Addr,
//! }
//!
//! pub trait SocketSettings {
//!   fn socket(&self) -> SocketAddr;
//!   fn port(&self) -> u16;
//!   fn ip(&self) -> IpAddr;
//! }
//!
//! impl SocketSettings for Settings {
//!   fn socket(&self) -> SocketAddr {
//!     self.fetch_with(Addr, |addr| {
//!       match addr {
//!         Some(socket_addr) => { socket_addr },
//!         None => {
//!           let port: u16 = self.port();
//!           let ip: IpAddr = self.ip();
//!           SocketAddr { ip: ip, port: port }
//!         }
//!       }
//!     })
//!   }
//!
//!   fn port(&self) -> u16 {
//!     self.fetch(Port).unwrap_or(8080)
//!   }
//!
//!   fn ip(&self) -> IpAddr {
//!     self.fetch(Ip).unwrap_or(Ipv4Addr(127,0,0,1))
//!   }
//! }
//!
//! fn main() {
//!   let mut settings = Settings::new();
//!   settings.set(Ip, "::0.0.0.1");
//!   let socket: IpAddr = settings.ip();
//!   assert_eq!(socket.to_str(), "::0.0.0.1".to_owned());
//! }
//! ~~~
//!
//! knob goes up to 11.

#![crate_id = "github.com/skade/knob#knob:1.1.1"]
#![crate_type = "lib"]
#![comment = "A convenient Rust settings system"]
#![license = "MIT"]

extern crate getopts;
extern crate collections;

use collections::hashmap::HashMap;
use std::os;
use std::from_str::FromStr;
use std::to_str::ToStr;

use getopts::{usage,getopts,OptGroup};
use getopts::Fail_;

/// The settings structure we save the options and settings in.
#[deriving(Clone)]
pub struct Settings {
  store: HashMap<~str,~str>,
  options: Box<Vec<OptGroup>>,
}

impl Settings {
  /// Create a new Settings struct.
  pub fn new() -> Settings {
    Settings { store: HashMap::new(), options: box Vec::new() }
  }

  /// Set a settings key to a value. The value will be serialized.
  pub fn set<A: ToStr, T: ToStr>(&mut self, setting: A, value: T) {
    self.store.swap(setting.to_str(), value.to_str());
  }

  /// Set a value using an Option struct. The value will only be set if the
  /// value is not None. This way, you can avoid unwrapping the result of a
  /// previous operation by yourself.
  pub fn set_opt<A: ToStr, T: ToStr>(&mut self, setting: A, value: Option<T>) {
    if value.is_some() {
      self.store.swap(setting.to_str(), value.unwrap().to_str());
    }
  }

  /// Fetch a setting for a key. Fails if the setting is present but could not be
  /// parsed.
  pub fn fetch<A: ToStr, T: FromStr>(&self, setting: A) -> Option<T> {
    match self.store.find(&setting.to_str()) {
      Some(string) => {
        let value = from_str(string.to_owned());
        if value.is_none() {
          fail!("setting could not be parsed:" + setting.to_str())
        }
        value
      },
      None => { None }
    }
  }

  /// Fetch a setting for a key and pass it to given function. The result of the function
  /// will be returned.
  pub fn fetch_with<A: ToStr, T: FromStr>(&self, setting: A, f: |Option<T>| -> T) -> T {
    let value = self.fetch(setting.to_str());
    f(value)
  }

  /// Register a commandline for laster use with load_args.
  ///
  /// Currently, only optopt and reqopt are properly supported.
  pub fn opt(&mut self, opt: OptGroup) {
    self.options.push(opt);
  }

  /// Load the command line argument given by the OS.
  ///
  /// Optionally returns failures.
  pub fn load_os_args(&mut self) -> Option<Fail_> {
    let args = os::args();
    self.load_args(args)
  }

  /// Load a list of command line arguments.
  ///
  /// Automatically sets "knob.progname" to the name of the program.
  ///
  /// Optionally returns failures.
  pub fn load_args(&mut self, args: Vec<~str>) -> Option<Fail_> {
    let ref prog_name = args.get(0);

    self.set("knob.progname", prog_name.clone());

    let matches = match getopts(args.tail(), self.options.as_slice()) {
      Ok(m) => { m }
      Err(fail) => { return Some(fail) }
    };

    let given_options = self.options.clone();
    for opt in given_options.iter() {
      let opt_strings = &[opt.short_name.clone(), opt.long_name.clone()];
      self.set_opt(opt.long_name.clone(), matches.opts_str(opt_strings))
    };
    None
  }

  /// Returns the usage string for the stored OptGroups. Pass `brief`
  /// to have it included.
  pub fn usage(&self, brief: &str) -> ~str {
    usage(brief, self.options.as_slice())
  }
}

<|endoftext|>


<commit_before>use analysis::bounds::Bound;
use analysis::imports::Imports;
use analysis::ref_mode::RefMode;
use analysis::rust_type::*;
use analysis::signals;
use analysis::signatures::{Signature, Signatures};
use analysis::trampolines;
use config::{self, GObject, PropertyGenerateFlags};
use env::Env;
use library;
use nameutil;
use traits::*;
use version::Version;

#[derive(Debug)]
pub struct Property {
    pub name: String,
    pub var_name: String,
    pub typ: library::TypeId,
    pub is_get: bool,
    pub func_name: String,
    pub nullable: library::Nullable,
    pub get_out_ref_mode: RefMode,
    pub set_in_ref_mode: RefMode,
    pub version: Option<Version>,
    pub deprecated_version: Option<Version>,
    pub bound: Option<Bound>,
}

pub fn analyze(
    env: &Env,
    props: &[library::Property],
    type_tid: library::TypeId,
    generate_trait: bool,
    trampolines: &mut trampolines::Trampolines,
    obj: &GObject,
    imports: &mut Imports,
    signatures: &Signatures,
    deps: &[library::TypeId],
) -> (Vec<Property>, Vec<signals::Info>) {
    let mut properties = Vec::new();
    let mut notify_signals = Vec::new();

    for prop in props {
        let configured_properties = obj.properties.matched(&prop.name);
        if configured_properties.iter().any(|f| f.ignore) {
            continue;
        }

        if env.is_totally_deprecated(prop.deprecated_version) {
            continue;
        }

        let (getter, setter, notify_signal) = analyze_property(
            env,
            prop,
            type_tid,
            &configured_properties,
            generate_trait,
            trampolines,
            obj,
            imports,
            signatures,
            deps,
        );

        if let Some(notify_signal) = notify_signal {
            notify_signals.push(notify_signal);
        }

        if getter.is_none() && setter.is_none() {
            continue;
        }

        let type_string = rust_type(env, prop.typ);
        let used_type_string = used_rust_type(env, prop.typ);
        if let Some(prop) = getter {
            if let Ok(ref s) = used_type_string {
                imports.add_used_type(s, prop.version);
            }
            if type_string.is_ok() {
                imports.add("gobject_ffi", prop.version);
                imports.add("glib::Value", prop.version);
                imports.add("glib::StaticType", prop.version);
            }

            properties.push(prop);
        }
        if let Some(prop) = setter {
            if let Ok(ref s) = used_type_string {
                imports.add_used_type(s, prop.version);
            }
            if type_string.is_ok() {
                imports.add("gobject_ffi", prop.version);
                imports.add("glib::Value", prop.version);
            }

            if prop.bound.is_some() {
                imports.add("glib", prop.version);
                imports.add("glib::object::IsA", prop.version);
            }

            properties.push(prop);
        }
    }

    (properties, notify_signals)
}

fn analyze_property(
    env: &Env,
    prop: &library::Property,
    type_tid: library::TypeId,
    configured_properties: &[&config::properties::Property],
    generate_trait: bool,
    trampolines: &mut trampolines::Trampolines,
    obj: &GObject,
    imports: &mut Imports,
    signatures: &Signatures,
    deps: &[library::TypeId],
) -> (Option<Property>, Option<Property>, Option<signals::Info>) {
    let name = prop.name.clone();

    let prop_version = configured_properties
        .iter()
        .filter_map(|f| f.version)
        .min()
        .or(prop.version)
        .or_else(|| Some(env.config.min_cfg_version));
    let generate = configured_properties
        .iter()
        .filter_map(|f| f.generate)
        .next();
    let generate_set = generate.is_some();
    let generate = generate.unwrap_or_else(PropertyGenerateFlags::all);

    let name_for_func = nameutil::signal_to_snake(&name);
    let var_name = nameutil::mangle_keywords(&*name_for_func).into_owned();
    let get_func_name = format!("get_property_{}", name_for_func);
    let set_func_name = format!("set_property_{}", name_for_func);
    let check_get_func_name = format!("get_{}", name_for_func);
    let check_set_func_name = format!("set_{}", name_for_func);

    let mut readable = prop.readable;
    let mut writable = if prop.construct_only {
        false
    } else {
        prop.writable
    };
    if generate_set && generate.contains(PropertyGenerateFlags::GET) && !readable {
        warn!(
            "Attempt to generate getter for notreadable property \"{}\"",
            name
        );
    }
    if generate_set && generate.contains(PropertyGenerateFlags::SET) && !writable {
        warn!(
            "Attempt to generate setter for nonwritable property \"{}\"",
            name
        );
    }
    readable &= generate.contains(PropertyGenerateFlags::GET);
    writable &= generate.contains(PropertyGenerateFlags::SET);
    let notifable = generate.contains(PropertyGenerateFlags::NOTIFY);

    if readable {
        let (has, version) = Signature::has_for_property(env, &check_get_func_name,
                                                         true, prop.typ, signatures, deps);
        if has && (env.is_totally_deprecated(version) || version <= prop_version) {
            readable = false;
        }
    }
    if writable {
        let (has, version) = Signature::has_for_property(env, &check_set_func_name,
                                                         false, prop.typ, signatures, deps);
        if has && (env.is_totally_deprecated(version) || version <= prop_version) {
            writable = false;
        }
    }

    let get_out_ref_mode = RefMode::of(env, prop.typ, library::ParameterDirection::Return);
    let mut set_in_ref_mode = RefMode::of(env, prop.typ, library::ParameterDirection::In);
    if set_in_ref_mode == RefMode::ByRefMut {
        set_in_ref_mode = RefMode::ByRef;
    }
    let nullable = library::Nullable(set_in_ref_mode.is_ref());
    let getter = if readable {
        Some(Property {
            name: name.clone(),
            var_name: String::new(),
            typ: prop.typ,
            is_get: true,
            func_name: get_func_name,
            nullable,
            get_out_ref_mode,
            set_in_ref_mode,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            bound: None,
        })
    } else {
        None
    };

    let setter = if writable {
        let bound = Bound::get_for_property_setter(env, &var_name, prop.typ, nullable);
        Some(Property {
            name: name.clone(),
            var_name,
            typ: prop.typ,
            is_get: false,
            func_name: set_func_name,
            nullable,
            get_out_ref_mode,
            set_in_ref_mode,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            bound,
        })
    } else {
        None
    };

    let mut used_types: Vec<String> = Vec::with_capacity(4);
    let trampoline_name = trampolines::analyze(
        env,
        &library::Signal {
            name: format!("notify::{}", name),
            parameters: Vec::new(),
            ret: library::Parameter {
                name: "".into(),
                typ: env.library
                    .find_type(library::INTERNAL_NAMESPACE, "none")
                    .unwrap(),
                c_type: "none".into(),
                instance_parameter: false,
                direction: library::ParameterDirection::Return,
                transfer: library::Transfer::None,
                caller_allocates: false,
                nullable: library::Nullable(false),
                allow_none: false,
                array_length: None,
                is_error: false,
                doc: None,
                scope: library::ParameterScope::None,
                closure: None,
                destroy: None,
            },
            is_action: false,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            doc: None,
            doc_deprecated: None,
        },
        type_tid,
        generate_trait,
        &[],
        trampolines,
        obj,
        &mut used_types,
        prop_version,
    );

    let notify_signal = if notifable && trampoline_name.is_ok() {
        imports.add_used_types(&used_types, prop_version);
        if generate_trait {
            imports.add("glib", prop_version);
            imports.add("glib::object::Downcast", prop_version);
        }
        imports.add("glib::signal::connect", prop_version);
        imports.add("glib::signal::SignalHandlerId", prop_version);
        imports.add("std::mem::transmute", prop_version);
        imports.add("std::boxed::Box as Box_", prop_version);
        imports.add("glib_ffi", prop_version);

        Some(signals::Info {
            connect_name: format!("connect_property_{}_notify", name_for_func),
            signal_name: format!("notify::{}", name),
            trampoline_name,
            action_emit_name: None,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            doc_hidden: false,
        })
    } else {
        None
    };

    (getter, setter, notify_signal)
}
<commit_msg>Don't generate notify for ConstructOnly properties<commit_after>use analysis::bounds::Bound;
use analysis::imports::Imports;
use analysis::ref_mode::RefMode;
use analysis::rust_type::*;
use analysis::signals;
use analysis::signatures::{Signature, Signatures};
use analysis::trampolines;
use config::{self, GObject, PropertyGenerateFlags};
use env::Env;
use library;
use nameutil;
use traits::*;
use version::Version;

#[derive(Debug)]
pub struct Property {
    pub name: String,
    pub var_name: String,
    pub typ: library::TypeId,
    pub is_get: bool,
    pub func_name: String,
    pub nullable: library::Nullable,
    pub get_out_ref_mode: RefMode,
    pub set_in_ref_mode: RefMode,
    pub version: Option<Version>,
    pub deprecated_version: Option<Version>,
    pub bound: Option<Bound>,
}

pub fn analyze(
    env: &Env,
    props: &[library::Property],
    type_tid: library::TypeId,
    generate_trait: bool,
    trampolines: &mut trampolines::Trampolines,
    obj: &GObject,
    imports: &mut Imports,
    signatures: &Signatures,
    deps: &[library::TypeId],
) -> (Vec<Property>, Vec<signals::Info>) {
    let mut properties = Vec::new();
    let mut notify_signals = Vec::new();

    for prop in props {
        let configured_properties = obj.properties.matched(&prop.name);
        if configured_properties.iter().any(|f| f.ignore) {
            continue;
        }

        if env.is_totally_deprecated(prop.deprecated_version) {
            continue;
        }

        let (getter, setter, notify_signal) = analyze_property(
            env,
            prop,
            type_tid,
            &configured_properties,
            generate_trait,
            trampolines,
            obj,
            imports,
            signatures,
            deps,
        );

        if let Some(notify_signal) = notify_signal {
            notify_signals.push(notify_signal);
        }

        if getter.is_none() && setter.is_none() {
            continue;
        }

        let type_string = rust_type(env, prop.typ);
        let used_type_string = used_rust_type(env, prop.typ);
        if let Some(prop) = getter {
            if let Ok(ref s) = used_type_string {
                imports.add_used_type(s, prop.version);
            }
            if type_string.is_ok() {
                imports.add("gobject_ffi", prop.version);
                imports.add("glib::Value", prop.version);
                imports.add("glib::StaticType", prop.version);
            }

            properties.push(prop);
        }
        if let Some(prop) = setter {
            if let Ok(ref s) = used_type_string {
                imports.add_used_type(s, prop.version);
            }
            if type_string.is_ok() {
                imports.add("gobject_ffi", prop.version);
                imports.add("glib::Value", prop.version);
            }

            if prop.bound.is_some() {
                imports.add("glib", prop.version);
                imports.add("glib::object::IsA", prop.version);
            }

            properties.push(prop);
        }
    }

    (properties, notify_signals)
}

fn analyze_property(
    env: &Env,
    prop: &library::Property,
    type_tid: library::TypeId,
    configured_properties: &[&config::properties::Property],
    generate_trait: bool,
    trampolines: &mut trampolines::Trampolines,
    obj: &GObject,
    imports: &mut Imports,
    signatures: &Signatures,
    deps: &[library::TypeId],
) -> (Option<Property>, Option<Property>, Option<signals::Info>) {
    let type_name = type_tid.full_name(&env.library);
    let name = prop.name.clone();

    let prop_version = configured_properties
        .iter()
        .filter_map(|f| f.version)
        .min()
        .or(prop.version)
        .or_else(|| Some(env.config.min_cfg_version));
    let generate = configured_properties
        .iter()
        .filter_map(|f| f.generate)
        .next();
    let generate_set = generate.is_some();
    let generate = generate.unwrap_or_else(PropertyGenerateFlags::all);

    let name_for_func = nameutil::signal_to_snake(&name);
    let var_name = nameutil::mangle_keywords(&*name_for_func).into_owned();
    let get_func_name = format!("get_property_{}", name_for_func);
    let set_func_name = format!("set_property_{}", name_for_func);
    let check_get_func_name = format!("get_{}", name_for_func);
    let check_set_func_name = format!("set_{}", name_for_func);

    let mut readable = prop.readable;
    let mut writable = if prop.construct_only {
        false
    } else {
        prop.writable
    };
    let mut notifable = !prop.construct_only;
    if generate_set && generate.contains(PropertyGenerateFlags::GET) && !readable {
        warn!(
            "Attempt to generate getter for notreadable property \"{}.{}\"",
            type_name, name
        );
    }
    if generate_set && generate.contains(PropertyGenerateFlags::SET) && !writable {
        warn!(
            "Attempt to generate setter for nonwritable property \"{}.{}\"",
            type_name, name
        );
    }
    readable &= generate.contains(PropertyGenerateFlags::GET);
    writable &= generate.contains(PropertyGenerateFlags::SET);
    if generate_set {
        notifable = generate.contains(PropertyGenerateFlags::NOTIFY);
    }

    if readable {
        let (has, version) = Signature::has_for_property(env, &check_get_func_name,
                                                         true, prop.typ, signatures, deps);
        if has && (env.is_totally_deprecated(version) || version <= prop_version) {
            readable = false;
        }
    }
    if writable {
        let (has, version) = Signature::has_for_property(env, &check_set_func_name,
                                                         false, prop.typ, signatures, deps);
        if has && (env.is_totally_deprecated(version) || version <= prop_version) {
            writable = false;
        }
    }

    let get_out_ref_mode = RefMode::of(env, prop.typ, library::ParameterDirection::Return);
    let mut set_in_ref_mode = RefMode::of(env, prop.typ, library::ParameterDirection::In);
    if set_in_ref_mode == RefMode::ByRefMut {
        set_in_ref_mode = RefMode::ByRef;
    }
    let nullable = library::Nullable(set_in_ref_mode.is_ref());
    let getter = if readable {
        Some(Property {
            name: name.clone(),
            var_name: String::new(),
            typ: prop.typ,
            is_get: true,
            func_name: get_func_name,
            nullable,
            get_out_ref_mode,
            set_in_ref_mode,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            bound: None,
        })
    } else {
        None
    };

    let setter = if writable {
        let bound = Bound::get_for_property_setter(env, &var_name, prop.typ, nullable);
        Some(Property {
            name: name.clone(),
            var_name,
            typ: prop.typ,
            is_get: false,
            func_name: set_func_name,
            nullable,
            get_out_ref_mode,
            set_in_ref_mode,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            bound,
        })
    } else {
        None
    };

    let mut used_types: Vec<String> = Vec::with_capacity(4);
    let trampoline_name = trampolines::analyze(
        env,
        &library::Signal {
            name: format!("notify::{}", name),
            parameters: Vec::new(),
            ret: library::Parameter {
                name: "".into(),
                typ: env.library
                    .find_type(library::INTERNAL_NAMESPACE, "none")
                    .unwrap(),
                c_type: "none".into(),
                instance_parameter: false,
                direction: library::ParameterDirection::Return,
                transfer: library::Transfer::None,
                caller_allocates: false,
                nullable: library::Nullable(false),
                allow_none: false,
                array_length: None,
                is_error: false,
                doc: None,
                scope: library::ParameterScope::None,
                closure: None,
                destroy: None,
            },
            is_action: false,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            doc: None,
            doc_deprecated: None,
        },
        type_tid,
        generate_trait,
        &[],
        trampolines,
        obj,
        &mut used_types,
        prop_version,
    );

    let notify_signal = if notifable && trampoline_name.is_ok() {
        imports.add_used_types(&used_types, prop_version);
        if generate_trait {
            imports.add("glib", prop_version);
            imports.add("glib::object::Downcast", prop_version);
        }
        imports.add("glib::signal::connect", prop_version);
        imports.add("glib::signal::SignalHandlerId", prop_version);
        imports.add("std::mem::transmute", prop_version);
        imports.add("std::boxed::Box as Box_", prop_version);
        imports.add("glib_ffi", prop_version);

        Some(signals::Info {
            connect_name: format!("connect_property_{}_notify", name_for_func),
            signal_name: format!("notify::{}", name),
            trampoline_name,
            action_emit_name: None,
            version: prop_version,
            deprecated_version: prop.deprecated_version,
            doc_hidden: false,
        })
    } else {
        None
    };

    (getter, setter, notify_signal)
}
<|endoftext|>


<commit_before>/*
Module: rand

Random number generation
*/
#[abi = "cdecl"]
native mod rustrt {
    type rctx;
    fn rand_new() -> rctx;
    fn rand_next(c: rctx) -> u32;
    fn rand_free(c: rctx);
}

/* Section: Types */

/*
Obj: rng

A random number generator
*/
type rng = obj {
    /*
    Method: next

    Return the next random integer
    */
    fn next() -> u32;

    /*
    Method: next_float

    Return the next random float
    */
    fn next_float() -> float;
};

resource rand_res(c: rustrt::rctx) { rustrt::rand_free(c); }

/* Section: Operations */

/*
Function: mk_rng

Create a random number generator
*/
fn mk_rng() -> rng {
    obj rt_rng(c: @rand_res) {
        fn next() -> u32 { ret rustrt::rand_next(**c); }
        fn next_float() -> float {
          let u1 = rustrt::rand_next(**c) as float;
          let u2 = rustrt::rand_next(**c) as float;
          let u3 = rustrt::rand_next(**c) as float;
          let scale = u32::max_value as float;
          ret ((u1 / scale + u2) / scale + u3) / scale;
        }
    }
    ret rt_rng(@rand_res(rustrt::rand_new()));
}
// Local Variables:
// mode: rust;
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// compile-command: "make -k -C $RBUILD 2>&1 | sed -e 's/\\/x\\//x:\\//g'";
// End:
<commit_msg>remove compile-command from local variable blocks<commit_after>/*
Module: rand

Random number generation
*/
#[abi = "cdecl"]
native mod rustrt {
    type rctx;
    fn rand_new() -> rctx;
    fn rand_next(c: rctx) -> u32;
    fn rand_free(c: rctx);
}

/* Section: Types */

/*
Obj: rng

A random number generator
*/
type rng = obj {
    /*
    Method: next

    Return the next random integer
    */
    fn next() -> u32;

    /*
    Method: next_float

    Return the next random float
    */
    fn next_float() -> float;
};

resource rand_res(c: rustrt::rctx) { rustrt::rand_free(c); }

/* Section: Operations */

/*
Function: mk_rng

Create a random number generator
*/
fn mk_rng() -> rng {
    obj rt_rng(c: @rand_res) {
        fn next() -> u32 { ret rustrt::rand_next(**c); }
        fn next_float() -> float {
          let u1 = rustrt::rand_next(**c) as float;
          let u2 = rustrt::rand_next(**c) as float;
          let u3 = rustrt::rand_next(**c) as float;
          let scale = u32::max_value as float;
          ret ((u1 / scale + u2) / scale + u3) / scale;
        }
    }
    ret rt_rng(@rand_res(rustrt::rand_new()));
}
// Local Variables:
// mode: rust;
// fill-column: 78;
// indent-tabs-mode: nil
// c-basic-offset: 4
// buffer-file-coding-system: utf-8-unix
// End:
<|endoftext|>


<commit_before>extern crate amq_protocol_codegen;

use amq_protocol_codegen::*;

use std::collections::BTreeMap;
use std::env;
use std::fs::File;
use std::io::Write;
use std::path::Path;

fn main() {
    let out_dir     = env::var("OUT_DIR").expect("OUT_DIR is not defined");
    let dest_path   = Path::new(&out_dir).join("protocol.rs");
    let mut f       = File::create(&dest_path).expect("Failed to create protocol.rs");
    let specs       = AMQProtocolDefinition::load();
    let mut codegen = CodeGenerator::new().register_amqp_helpers();
    let mut data    = BTreeMap::new();

    codegen.register_template_string("protocol", include_str!(concat!(env!("CARGO_MANIFEST_DIR"), "/templates/protocol.rs")).to_string()).expect("Failed to register protocol template");
    data.insert("protocol".to_string(), specs);

    writeln!(f, "{}", codegen.render("protocol", &data).expect("Failed to render protocol template")).expect("Failed to generate protocol.rs");
}
<commit_msg>protocol: use simple_codegen<commit_after>extern crate amq_protocol_codegen;

use amq_protocol_codegen::{CodeGenerator, HandlebarsAMQPExtension};

use std::env;

fn main() {
    let out_dir  = env::var("OUT_DIR").expect("OUT_DIR is not defined");
    let template = include_str!(concat!(env!("CARGO_MANIFEST_DIR"), "/templates/protocol.rs"));

    CodeGenerator::simple_codegen(&out_dir, "protocol", "protocol", template, "protocol");
}
<|endoftext|>


<commit_before>#![allow(non_snake_case)]

use rustc_serialize::{Encodable, Encoder, Decodable, Decoder};
use rustc_serialize::json::Object;

pub enum LocationStrategy {
    Css,
    LinkText,
    PartialLinkText,
    XPath,
}

impl Encodable for LocationStrategy {
    fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
        match self {
            &LocationStrategy::Css => s.emit_str("css selector"),
            &LocationStrategy::LinkText => s.emit_str("link text"),
            &LocationStrategy::PartialLinkText => s.emit_str("partial link text"),
            &LocationStrategy::XPath => s.emit_str("xpath"),
        }
    }
}

#[derive(RustcDecodable, Debug)]
pub struct WebDriverError {
    pub error: String,
    pub message: String,
}

#[derive(RustcEncodable)]
pub struct NewSessionCmd {
    required: Object,
}

impl NewSessionCmd {
    pub fn new() -> Self {
        NewSessionCmd {
            required: Object::new(),
        }
    }

// TODO firefox specifc prefs
// [moz:firefoxOptions][prefs][name] = value;

}

#[derive(RustcDecodable)]
pub struct Session {
    pub sessionId: String,
}

#[derive(RustcEncodable)]
pub struct GoCmd {
    pub url: String,
}

#[derive(RustcDecodable)]
pub struct Value<T> {
    pub value: T,
}

#[derive(RustcDecodable)]
pub struct CurrentTitle {
    pub title: String,
}

#[derive(RustcEncodable)]
pub struct SwitchWindowCmd<'a> {
    pub handle: &'a str,
}

#[derive(RustcDecodable, RustcEncodable)]
pub struct Empty {}

#[derive(RustcEncodable)]
pub struct FindElementCmd<'a> {
    pub using: LocationStrategy,
    pub value: &'a str,
}

pub struct ElementReference {
    pub reference: String,
}

impl Decodable for ElementReference {
    fn decode<D: Decoder>(d: &mut D) -> Result<Self, D::Error> {
        d.read_struct("ElementReference", 2, |d| {
            let reference = try!(d.read_struct_field("element-6066-11e4-a52e-4f735466cecf", 0, |d| d.read_str()));
            Ok(ElementReference { reference: reference })
        })
    }
}

#[derive(RustcDecodable)]
pub struct Cookie {
    name: String,
    value: String,
    path: String,
    domain: String,
    secure: bool,
    httpOnly: bool,
    // TODO: expiry:
}
<commit_msg>Add missing pub attr in Cookie struct<commit_after>#![allow(non_snake_case)]

use rustc_serialize::{Encodable, Encoder, Decodable, Decoder};
use rustc_serialize::json::Object;

pub enum LocationStrategy {
    Css,
    LinkText,
    PartialLinkText,
    XPath,
}

impl Encodable for LocationStrategy {
    fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
        match self {
            &LocationStrategy::Css => s.emit_str("css selector"),
            &LocationStrategy::LinkText => s.emit_str("link text"),
            &LocationStrategy::PartialLinkText => s.emit_str("partial link text"),
            &LocationStrategy::XPath => s.emit_str("xpath"),
        }
    }
}

#[derive(RustcDecodable, Debug)]
pub struct WebDriverError {
    pub error: String,
    pub message: String,
}

#[derive(RustcEncodable)]
pub struct NewSessionCmd {
    required: Object,
}

impl NewSessionCmd {
    pub fn new() -> Self {
        NewSessionCmd {
            required: Object::new(),
        }
    }

// TODO firefox specifc prefs
// [moz:firefoxOptions][prefs][name] = value;

}

#[derive(RustcDecodable)]
pub struct Session {
    pub sessionId: String,
}

#[derive(RustcEncodable)]
pub struct GoCmd {
    pub url: String,
}

#[derive(RustcDecodable)]
pub struct Value<T> {
    pub value: T,
}

#[derive(RustcDecodable)]
pub struct CurrentTitle {
    pub title: String,
}

#[derive(RustcEncodable)]
pub struct SwitchWindowCmd<'a> {
    pub handle: &'a str,
}

#[derive(RustcDecodable, RustcEncodable)]
pub struct Empty {}

#[derive(RustcEncodable)]
pub struct FindElementCmd<'a> {
    pub using: LocationStrategy,
    pub value: &'a str,
}

pub struct ElementReference {
    pub reference: String,
}

impl Decodable for ElementReference {
    fn decode<D: Decoder>(d: &mut D) -> Result<Self, D::Error> {
        d.read_struct("ElementReference", 2, |d| {
            let reference = try!(d.read_struct_field("element-6066-11e4-a52e-4f735466cecf", 0, |d| d.read_str()));
            Ok(ElementReference { reference: reference })
        })
    }
}

#[derive(RustcDecodable)]
pub struct Cookie {
    pub name: String,
    pub value: String,
    pub path: String,
    pub domain: String,
    pub secure: bool,
    pub httpOnly: bool,
    // TODO: expiry:
}
<|endoftext|>


<commit_before>// Copyright 2019 TiKV Project Authors. Licensed under Apache-2.0.

use crate::grpc_sys::{self, grpc_metadata, grpc_metadata_array};
use std::borrow::Cow;
use std::mem::ManuallyDrop;
use std::{mem, slice, str};

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

const BINARY_ERROR_DETAILS_KEY: &str = "grpc-status-details-bin";

fn normalize_key(key: &str, binary: bool) -> Result<Cow<'_, str>> {
    if key.is_empty() {
        return Err(Error::InvalidMetadata(
            "metadata key should not be empty".to_owned(),
        ));
    }
    let mut is_upper_case = false;
    for b in key.as_bytes() {
        let b = *b;
        if (b'A'..=b'Z').contains(&b) {
            is_upper_case = true;
            continue;
        } else if (b'a'..=b'z').contains(&b)
            || (b'0'..=b'9').contains(&b)
            || b == b'_'
            || b == b'-'
            || b == b'.'
        {
            continue;
        }
        return Err(Error::InvalidMetadata(format!("key {:?} is invalid", key)));
    }
    let key = if is_upper_case {
        Cow::Owned(key.to_ascii_lowercase())
    } else {
        Cow::Borrowed(key)
    };
    if binary {
        if !key.as_bytes().ends_with(b"-bin") {
            return Err(Error::InvalidMetadata(
                "binary key should end with '-bin'".to_owned(),
            ));
        }
    } else if key.as_bytes().ends_with(b"-bin") {
        return Err(Error::InvalidMetadata(
            "non-binary key should not end with '-bin'".to_owned(),
        ));
    }
    Ok(key)
}

/// Builder for immutable Metadata.
pub struct MetadataBuilder {
    arr: Metadata,
}

impl MetadataBuilder {
    /// Create a builder with empty initial capacity.
    pub fn new() -> MetadataBuilder {
        MetadataBuilder::with_capacity(0)
    }

    /// Create a builder with the given value.
    pub fn with_capacity(cap: usize) -> MetadataBuilder {
        MetadataBuilder {
            arr: Metadata::with_capacity(cap),
        }
    }

    /// Add a metadata holding an ASCII value.
    ///
    /// `key` must not use suffix (-bin) indicating a binary valued metadata entry.
    pub fn add_str(&mut self, key: &str, value: &str) -> Result<&mut MetadataBuilder> {
        if !value.is_ascii() {
            return Err(Error::InvalidMetadata(
                "only ascii value is accepted.".to_owned(),
            ));
        }
        for b in value.bytes() {
            if 0 == unsafe { libc::isprint(b as i32) } {
                return Err(Error::InvalidMetadata(
                    "Only printable chars are accepted.".to_owned(),
                ));
            }
        }
        let key = normalize_key(key, false)?;
        Ok(self.add_metadata(&key, value.as_bytes()))
    }

    fn add_metadata(&mut self, key: &str, value: &[u8]) -> &mut MetadataBuilder {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_add(
                &mut self.arr.0,
                key.as_ptr() as _,
                key.len(),
                value.as_ptr() as _,
                value.len(),
            )
        }
        self
    }

    /// Add a metadata holding a binary value.
    ///
    /// `key` needs to have suffix (-bin) indicating a binary valued metadata entry.
    pub fn add_bytes(&mut self, key: &str, value: &[u8]) -> Result<&mut MetadataBuilder> {
        let key = normalize_key(key, true)?;
        Ok(self.add_metadata(&key, value))
    }

    /// Set binary error details to support rich error model.
    ///
    /// See also https://grpc.io/docs/guides/error/#richer-error-model.
    pub(crate) fn set_binary_error_details(&mut self, value: &[u8]) -> &mut MetadataBuilder {
        self.add_metadata(BINARY_ERROR_DETAILS_KEY, value)
    }

    /// Create `Metadata` with configured entries.
    pub fn build(mut self) -> Metadata {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_shrink_to_fit(&mut self.arr.0);
        }
        self.arr
    }
}

/// A collection of metadata entries that can be exchanged during a call.
///
/// gRPC supports these types of metadata:
///
/// - Request headers
///
///     They are sent by the client at the beginning of a remote call before
///     any request messages are sent.
///
/// - Response headers
///
///     They are sent by the server at the beginning of a remote call handler
///     before any response messages are sent.
///
/// - Response trailers
///
///     They are sent by the server at the end of a remote call along with
///     resulting call status.
///
/// Metadata value can be ascii string or bytes. They are distinguish by the
/// key suffix, key of bytes value should have suffix '-bin'.
#[repr(C)]
pub struct Metadata(grpc_metadata_array);

impl Metadata {
    fn with_capacity(cap: usize) -> Metadata {
        unsafe {
            let mut arr = mem::MaybeUninit::uninit();
            grpc_sys::grpcwrap_metadata_array_init(arr.as_mut_ptr(), cap);
            Metadata(arr.assume_init())
        }
    }

    /// Returns the count of metadata entries.
    #[inline]
    pub fn len(&self) -> usize {
        self.0.count
    }

    /// Returns true if there is no metadata entries.
    #[inline]
    pub fn is_empty(&self) -> bool {
        self.0.count == 0
    }

    /// Returns the metadata entry at the `index`.
    ///
    /// `None` is returned if out of bound.
    pub fn get(&self, index: usize) -> Option<(&str, &[u8])> {
        if self.0.count <= index {
            return None;
        }
        let (mut key_len, mut val_len) = (0, 0);
        unsafe {
            let key = grpc_sys::grpcwrap_metadata_array_get_key(&self.0, index, &mut key_len);
            let val = grpc_sys::grpcwrap_metadata_array_get_value(&self.0, index, &mut val_len);
            let key_str = str::from_utf8_unchecked(slice::from_raw_parts(key as _, key_len));
            let val_bytes = slice::from_raw_parts(val as *const u8, val_len);
            Some((key_str, val_bytes))
        }
    }

    /// Returns an iterator over the metadata entries.
    pub fn iter(&self) -> MetadataIter<'_> {
        MetadataIter {
            data: self,
            index: 0,
        }
    }

    /// Decomposes a Metadata array into its raw components.
    ///
    /// Returns the raw pointer to the underlying data, the length of the vector (in elements),
    /// and the allocated capacity of the data (in elements). These are the same arguments in
    /// the same order as the arguments to from_raw_parts.
    ///
    /// After calling this function, the caller is responsible for the memory previously managed
    /// by the Metadata. The only way to do this is to convert the raw pointer, length, and
    /// capacity back into a Metadata with the from_raw_parts function, allowing the destructor
    /// to perform the cleanup.
    pub fn into_raw_parts(self) -> (*mut grpc_metadata, usize, usize) {
        let s = ManuallyDrop::new(self);
        (s.0.metadata, s.0.count, s.0.capacity)
    }

    /// Creates a Metadata directly from the raw components of another vector.
    ///
    /// ## Safety
    ///
    /// The operation is safe only if the three arguments are returned from `into_raw_parts`
    /// and only convert once.
    pub unsafe fn from_raw_parts(p: *mut grpc_metadata, len: usize, cap: usize) -> Metadata {
        Metadata(grpc_metadata_array {
            count: len,
            capacity: cap,
            metadata: p,
        })
    }

    /// Search for binary error details.
    pub(crate) fn search_binary_error_details(&self) -> &[u8] {
        for (k, v) in self.iter() {
            if k == BINARY_ERROR_DETAILS_KEY {
                return v;
            }
        }
        &[]
    }
}

impl Clone for Metadata {
    fn clone(&self) -> Metadata {
        let mut builder = MetadataBuilder::with_capacity(self.len());
        for (k, v) in self.iter() {
            // use `add_metadata` to skip validation.
            builder.add_metadata(k, v);
        }
        builder.build()
    }
}

impl Drop for Metadata {
    fn drop(&mut self) {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_cleanup(&mut self.0);
        }
    }
}

unsafe impl Send for Metadata {}

/// Immutable metadata iterator
///
/// This struct is created by the iter method on `Metadata`.
pub struct MetadataIter<'a> {
    data: &'a Metadata,
    index: usize,
}

impl<'a> Iterator for MetadataIter<'a> {
    type Item = (&'a str, &'a [u8]);

    fn next(&mut self) -> Option<Self::Item> {
        let res = self.data.get(self.index);
        if res.is_some() {
            self.index += 1;
        }
        res
    }

    fn size_hint(&self) -> (usize, Option<usize>) {
        let remain = self.data.0.count - self.index;
        (remain, Some(remain))
    }
}

impl<'a> IntoIterator for &'a Metadata {
    type IntoIter = MetadataIter<'a>;
    type Item = (&'a str, &'a [u8]);

    fn into_iter(self) -> MetadataIter<'a> {
        MetadataIter {
            data: self,
            index: 0,
        }
    }
}

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

    #[test]
    fn test_key_check() {
        let mut builder = MetadataBuilder::new();
        // Non-byte key should not end with '-bin'.
        assert!(builder.add_str("key-bin", "value").is_err());
        // Byte key should end with '-bin'.
        assert!(builder.add_bytes("key", b"value").is_err());
        // Key should not be empty.
        assert!(builder.add_str("", "value").is_err());
        // Key should follow the rule ^[a-z0-9_-.]+$
        assert!(builder.add_str(":key", "value").is_err());
        assert!(builder.add_str("key~", "value").is_err());
        assert!(builder.add_str("ke+y", "value").is_err());
        // Only printable ascii value is accepted when `add_str`.
        assert!(builder.add_str("key", "❤").is_err());
        assert!(builder.add_str("key", "\0").is_err());
        assert!(builder.add_str("key", "\n").is_err());

        builder.add_str("key", "value").unwrap();
        builder.add_str("_", "value").unwrap();
        builder.add_str("-", "value").unwrap();
        builder.add_str(".", "value").unwrap();
        builder.add_bytes("key-bin", b"value").unwrap();
    }

    #[test]
    fn test_metadata() {
        let mut builder = MetadataBuilder::new();
        let mut meta_kvs = vec![];
        for i in 0..5 {
            let key = format!("K{}", i);
            let val = format!("v{}", i);
            builder.add_str(&key, &val).unwrap();
            meta_kvs.push((key.to_ascii_lowercase(), val.into_bytes()));
        }
        for i in 5..10 {
            let key = format!("k{}-Bin", i);
            let val = format!("v{}", i);
            builder.add_bytes(&key, val.as_bytes()).unwrap();
            meta_kvs.push((key.to_ascii_lowercase(), val.into_bytes()));
        }
        let metadata = builder.build();
        for (i, (exp, res)) in meta_kvs.iter().zip(&metadata).enumerate() {
            let kv = metadata.get(i).unwrap();
            assert_eq!(kv, res);
            assert_eq!(res, (exp.0.as_str(), exp.1.as_slice()));
        }
        assert!(metadata.get(10).is_none());
        assert_eq!(metadata.len(), 10);
        assert!(!metadata.is_empty());
        {
            let mut iter = metadata.iter();
            for i in 0..10 {
                assert_eq!(iter.size_hint(), (10 - i, Some(10 - i)));
                iter.next();
            }
            assert_eq!(iter.size_hint(), (0, Some(0)));
        }

        let metadata1 = metadata.clone();
        for (x, y) in metadata.iter().zip(&metadata1) {
            assert_eq!(x, y);
        }
        drop(metadata);
        // Ensure deep copy.
        assert!(metadata1.get(0).is_some());

        let empty_metadata = MetadataBuilder::new().build();
        assert!(empty_metadata.is_empty());
        assert_eq!(empty_metadata.len(), 0);
    }
}
<commit_msg>Implement Sync for CallOption (#551)<commit_after>// Copyright 2019 TiKV Project Authors. Licensed under Apache-2.0.

use crate::grpc_sys::{self, grpc_metadata, grpc_metadata_array};
use std::borrow::Cow;
use std::mem::ManuallyDrop;
use std::{mem, slice, str};

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

const BINARY_ERROR_DETAILS_KEY: &str = "grpc-status-details-bin";

fn normalize_key(key: &str, binary: bool) -> Result<Cow<'_, str>> {
    if key.is_empty() {
        return Err(Error::InvalidMetadata(
            "metadata key should not be empty".to_owned(),
        ));
    }
    let mut is_upper_case = false;
    for b in key.as_bytes() {
        let b = *b;
        if (b'A'..=b'Z').contains(&b) {
            is_upper_case = true;
            continue;
        } else if (b'a'..=b'z').contains(&b)
            || (b'0'..=b'9').contains(&b)
            || b == b'_'
            || b == b'-'
            || b == b'.'
        {
            continue;
        }
        return Err(Error::InvalidMetadata(format!("key {:?} is invalid", key)));
    }
    let key = if is_upper_case {
        Cow::Owned(key.to_ascii_lowercase())
    } else {
        Cow::Borrowed(key)
    };
    if binary {
        if !key.as_bytes().ends_with(b"-bin") {
            return Err(Error::InvalidMetadata(
                "binary key should end with '-bin'".to_owned(),
            ));
        }
    } else if key.as_bytes().ends_with(b"-bin") {
        return Err(Error::InvalidMetadata(
            "non-binary key should not end with '-bin'".to_owned(),
        ));
    }
    Ok(key)
}

/// Builder for immutable Metadata.
pub struct MetadataBuilder {
    arr: Metadata,
}

impl MetadataBuilder {
    /// Create a builder with empty initial capacity.
    pub fn new() -> MetadataBuilder {
        MetadataBuilder::with_capacity(0)
    }

    /// Create a builder with the given value.
    pub fn with_capacity(cap: usize) -> MetadataBuilder {
        MetadataBuilder {
            arr: Metadata::with_capacity(cap),
        }
    }

    /// Add a metadata holding an ASCII value.
    ///
    /// `key` must not use suffix (-bin) indicating a binary valued metadata entry.
    pub fn add_str(&mut self, key: &str, value: &str) -> Result<&mut MetadataBuilder> {
        if !value.is_ascii() {
            return Err(Error::InvalidMetadata(
                "only ascii value is accepted.".to_owned(),
            ));
        }
        for b in value.bytes() {
            if 0 == unsafe { libc::isprint(b as i32) } {
                return Err(Error::InvalidMetadata(
                    "Only printable chars are accepted.".to_owned(),
                ));
            }
        }
        let key = normalize_key(key, false)?;
        Ok(self.add_metadata(&key, value.as_bytes()))
    }

    fn add_metadata(&mut self, key: &str, value: &[u8]) -> &mut MetadataBuilder {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_add(
                &mut self.arr.0,
                key.as_ptr() as _,
                key.len(),
                value.as_ptr() as _,
                value.len(),
            )
        }
        self
    }

    /// Add a metadata holding a binary value.
    ///
    /// `key` needs to have suffix (-bin) indicating a binary valued metadata entry.
    pub fn add_bytes(&mut self, key: &str, value: &[u8]) -> Result<&mut MetadataBuilder> {
        let key = normalize_key(key, true)?;
        Ok(self.add_metadata(&key, value))
    }

    /// Set binary error details to support rich error model.
    ///
    /// See also https://grpc.io/docs/guides/error/#richer-error-model.
    pub(crate) fn set_binary_error_details(&mut self, value: &[u8]) -> &mut MetadataBuilder {
        self.add_metadata(BINARY_ERROR_DETAILS_KEY, value)
    }

    /// Create `Metadata` with configured entries.
    pub fn build(mut self) -> Metadata {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_shrink_to_fit(&mut self.arr.0);
        }
        self.arr
    }
}

/// A collection of metadata entries that can be exchanged during a call.
///
/// gRPC supports these types of metadata:
///
/// - Request headers
///
///     They are sent by the client at the beginning of a remote call before
///     any request messages are sent.
///
/// - Response headers
///
///     They are sent by the server at the beginning of a remote call handler
///     before any response messages are sent.
///
/// - Response trailers
///
///     They are sent by the server at the end of a remote call along with
///     resulting call status.
///
/// Metadata value can be ascii string or bytes. They are distinguish by the
/// key suffix, key of bytes value should have suffix '-bin'.
#[repr(C)]
pub struct Metadata(grpc_metadata_array);

impl Metadata {
    fn with_capacity(cap: usize) -> Metadata {
        unsafe {
            let mut arr = mem::MaybeUninit::uninit();
            grpc_sys::grpcwrap_metadata_array_init(arr.as_mut_ptr(), cap);
            Metadata(arr.assume_init())
        }
    }

    /// Returns the count of metadata entries.
    #[inline]
    pub fn len(&self) -> usize {
        self.0.count
    }

    /// Returns true if there is no metadata entries.
    #[inline]
    pub fn is_empty(&self) -> bool {
        self.0.count == 0
    }

    /// Returns the metadata entry at the `index`.
    ///
    /// `None` is returned if out of bound.
    pub fn get(&self, index: usize) -> Option<(&str, &[u8])> {
        if self.0.count <= index {
            return None;
        }
        let (mut key_len, mut val_len) = (0, 0);
        unsafe {
            let key = grpc_sys::grpcwrap_metadata_array_get_key(&self.0, index, &mut key_len);
            let val = grpc_sys::grpcwrap_metadata_array_get_value(&self.0, index, &mut val_len);
            let key_str = str::from_utf8_unchecked(slice::from_raw_parts(key as _, key_len));
            let val_bytes = slice::from_raw_parts(val as *const u8, val_len);
            Some((key_str, val_bytes))
        }
    }

    /// Returns an iterator over the metadata entries.
    pub fn iter(&self) -> MetadataIter<'_> {
        MetadataIter {
            data: self,
            index: 0,
        }
    }

    /// Decomposes a Metadata array into its raw components.
    ///
    /// Returns the raw pointer to the underlying data, the length of the vector (in elements),
    /// and the allocated capacity of the data (in elements). These are the same arguments in
    /// the same order as the arguments to from_raw_parts.
    ///
    /// After calling this function, the caller is responsible for the memory previously managed
    /// by the Metadata. The only way to do this is to convert the raw pointer, length, and
    /// capacity back into a Metadata with the from_raw_parts function, allowing the destructor
    /// to perform the cleanup.
    pub fn into_raw_parts(self) -> (*mut grpc_metadata, usize, usize) {
        let s = ManuallyDrop::new(self);
        (s.0.metadata, s.0.count, s.0.capacity)
    }

    /// Creates a Metadata directly from the raw components of another vector.
    ///
    /// ## Safety
    ///
    /// The operation is safe only if the three arguments are returned from `into_raw_parts`
    /// and only convert once.
    pub unsafe fn from_raw_parts(p: *mut grpc_metadata, len: usize, cap: usize) -> Metadata {
        Metadata(grpc_metadata_array {
            count: len,
            capacity: cap,
            metadata: p,
        })
    }

    /// Search for binary error details.
    pub(crate) fn search_binary_error_details(&self) -> &[u8] {
        for (k, v) in self.iter() {
            if k == BINARY_ERROR_DETAILS_KEY {
                return v;
            }
        }
        &[]
    }
}

impl Clone for Metadata {
    fn clone(&self) -> Metadata {
        let mut builder = MetadataBuilder::with_capacity(self.len());
        for (k, v) in self.iter() {
            // use `add_metadata` to skip validation.
            builder.add_metadata(k, v);
        }
        builder.build()
    }
}

impl Drop for Metadata {
    fn drop(&mut self) {
        unsafe {
            grpc_sys::grpcwrap_metadata_array_cleanup(&mut self.0);
        }
    }
}

unsafe impl Send for Metadata {}
unsafe impl Sync for Metadata {}

/// Immutable metadata iterator
///
/// This struct is created by the iter method on `Metadata`.
pub struct MetadataIter<'a> {
    data: &'a Metadata,
    index: usize,
}

impl<'a> Iterator for MetadataIter<'a> {
    type Item = (&'a str, &'a [u8]);

    fn next(&mut self) -> Option<Self::Item> {
        let res = self.data.get(self.index);
        if res.is_some() {
            self.index += 1;
        }
        res
    }

    fn size_hint(&self) -> (usize, Option<usize>) {
        let remain = self.data.0.count - self.index;
        (remain, Some(remain))
    }
}

impl<'a> IntoIterator for &'a Metadata {
    type IntoIter = MetadataIter<'a>;
    type Item = (&'a str, &'a [u8]);

    fn into_iter(self) -> MetadataIter<'a> {
        MetadataIter {
            data: self,
            index: 0,
        }
    }
}

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

    #[test]
    fn test_key_check() {
        let mut builder = MetadataBuilder::new();
        // Non-byte key should not end with '-bin'.
        assert!(builder.add_str("key-bin", "value").is_err());
        // Byte key should end with '-bin'.
        assert!(builder.add_bytes("key", b"value").is_err());
        // Key should not be empty.
        assert!(builder.add_str("", "value").is_err());
        // Key should follow the rule ^[a-z0-9_-.]+$
        assert!(builder.add_str(":key", "value").is_err());
        assert!(builder.add_str("key~", "value").is_err());
        assert!(builder.add_str("ke+y", "value").is_err());
        // Only printable ascii value is accepted when `add_str`.
        assert!(builder.add_str("key", "❤").is_err());
        assert!(builder.add_str("key", "\0").is_err());
        assert!(builder.add_str("key", "\n").is_err());

        builder.add_str("key", "value").unwrap();
        builder.add_str("_", "value").unwrap();
        builder.add_str("-", "value").unwrap();
        builder.add_str(".", "value").unwrap();
        builder.add_bytes("key-bin", b"value").unwrap();
    }

    #[test]
    fn test_metadata() {
        let mut builder = MetadataBuilder::new();
        let mut meta_kvs = vec![];
        for i in 0..5 {
            let key = format!("K{}", i);
            let val = format!("v{}", i);
            builder.add_str(&key, &val).unwrap();
            meta_kvs.push((key.to_ascii_lowercase(), val.into_bytes()));
        }
        for i in 5..10 {
            let key = format!("k{}-Bin", i);
            let val = format!("v{}", i);
            builder.add_bytes(&key, val.as_bytes()).unwrap();
            meta_kvs.push((key.to_ascii_lowercase(), val.into_bytes()));
        }
        let metadata = builder.build();
        for (i, (exp, res)) in meta_kvs.iter().zip(&metadata).enumerate() {
            let kv = metadata.get(i).unwrap();
            assert_eq!(kv, res);
            assert_eq!(res, (exp.0.as_str(), exp.1.as_slice()));
        }
        assert!(metadata.get(10).is_none());
        assert_eq!(metadata.len(), 10);
        assert!(!metadata.is_empty());
        {
            let mut iter = metadata.iter();
            for i in 0..10 {
                assert_eq!(iter.size_hint(), (10 - i, Some(10 - i)));
                iter.next();
            }
            assert_eq!(iter.size_hint(), (0, Some(0)));
        }

        let metadata1 = metadata.clone();
        for (x, y) in metadata.iter().zip(&metadata1) {
            assert_eq!(x, y);
        }
        drop(metadata);
        // Ensure deep copy.
        assert!(metadata1.get(0).is_some());

        let empty_metadata = MetadataBuilder::new().build();
        assert!(empty_metadata.is_empty());
        assert_eq!(empty_metadata.len(), 0);
    }
}
<|endoftext|>


<commit_before>#![allow(non_snake_case)]
//! OrcV2

pub mod ee;
pub mod lljit;

use error::LLVMErrorRef;
use prelude::*;
use target_machine::LLVMTargetMachineRef;

pub type LLVMOrcJITTargetAddress = u64;

/// Generic linkage flags for a symbol definition.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMJITSymbolGenericFlags {
    LLVMJITSymbolGenericFlagsExported = 1,
    LLVMJITSymbolGenericFlagsWeak = 2,
}

/// Target specific flags for a symbol definition.
pub type LLVMJITTargetSymbolFlags = u8;

/// Linkage flags for a symbol definition.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITSymbolFlags {
    GenericFlags: u8,
    TargetFlags: u8,
}

/// An evaluated symbol address and flags.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITEvaluatedSymbol {
    Address: LLVMOrcJITTargetAddress,
    Flags: LLVMJITSymbolFlags,
}

#[derive(Debug)]
pub enum LLVMOrcOpaqueExecutionSession {}
pub type LLVMOrcExecutionSessionRef = *mut LLVMOrcOpaqueExecutionSession;

/// Error reporter function.
pub type LLVMOrcErrorReporterFunction = extern "C" fn(Ctx: *mut ::libc::c_void, Err: LLVMErrorRef);

#[derive(Debug)]
pub enum LLVMOrcOpaqueSymbolStringPool {}
/// A reference to an orc::SymbolStringPool.
pub type LLVMOrcSymbolStringPoolRef = *mut LLVMOrcOpaqueSymbolStringPool;

#[derive(Debug)]
pub enum LLVMOrcQuaqueSymbolStringPoolEntry {}
pub type LLVMOrcSymbolStringPoolEntryRef = *mut LLVMOrcQuaqueSymbolStringPoolEntry;

/// A pair of a symbol name and an evaluated symbol.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITCSymbolMapPair {
    Name: LLVMOrcSymbolStringPoolEntryRef,
    Sym: LLVMJITEvaluatedSymbol,
}

/// A list of (SymbolStringPtr, JITEvaluatedSymbol) pairs that can be
/// used to construct a SymbolMap.
pub type LLVMOrcCSymbolMapPairs = *mut LLVMJITCSymbolMapPair;

/// Lookup kind. This can be used by definition generators when deciding whether
/// to produce a definition for a requested symbol.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcLookupKind {
    LLVMOrcLookupKindStatic,
    LLVMOrcLookupKindDLSym,
}

/// JITDylib lookup flags. This can be used by definition generators when
/// deciding whether to produce a definition for a requested symbol.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcJITDylibLookupFlags {
    LLVMOrcJITDylibLookupFlagsMatchExportedSymbolsOnly,
    LLVMOrcJITDylibLookupFlagsMatchAllSymbols,
}

/// Symbol lookup flags for lookup sets.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcSymbolLookupFlags {
    LLVMOrcSymbolLookupFlagsRequiredSymbol,
    LLVMOrcSymbolLookupFlagsWeaklyReferencedSymbol,
}

/// An element type for a symbol lookup set.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMOrcCLookupSetElement {
    Name: LLVMOrcSymbolStringPoolEntryRef,
    LookupFlags: LLVMOrcSymbolLookupFlags,
}

/// A set of symbols to look up / generate.
///
/// The list is terminated with an element containing a null pointer for the
/// Name field.
///
/// The creator is responsible for freeing the set and ensuring all strings
/// are retained for the set's lifetime.
pub type LLVMOrcCLookupSet = *mut LLVMOrcCLookupSetElement;

#[derive(Debug)]
pub enum LLVMOrcOpaqueMaterializationUnit {}
pub type LLVMOrcMaterializationUnitRef = *mut LLVMOrcOpaqueMaterializationUnit;

#[derive(Debug)]
pub enum LLVMOrcOpaqueJITDylib {}
pub type LLVMOrcJITDylibRef = *mut LLVMOrcOpaqueJITDylib;

#[derive(Debug)]
pub enum LLVMOrcOpaqueResourceTracker {}
pub type LLVMOrcResourceTrackerRef = *mut LLVMOrcOpaqueResourceTracker;

#[derive(Debug)]
pub enum LLVMOrcOpaqueDefinitionGenerator {}
pub type LLVMOrcDefinitionGeneratorRef = *mut LLVMOrcOpaqueDefinitionGenerator;

#[derive(Debug)]
pub enum LLVMOrcOpaqueLookupState {}
pub type LLVMOrcLookupStateRef = *mut LLVMOrcOpaqueLookupState;

pub type LLVMOrcCAPIDefinitionGeneratorTryToGenerateFunction = extern "C" fn(
    GeneratorObj: LLVMOrcDefinitionGeneratorRef,
    Ctx: *mut ::libc::c_void,
    LookupState: *mut LLVMOrcLookupStateRef,
    Kind: LLVMOrcLookupKind,
    JD: LLVMOrcJITDylibRef,
    JDLookupFlags: LLVMOrcJITDylibLookupFlags,
    LookupSet: LLVMOrcCLookupSet,
    LookupSetSize: usize,
) -> LLVMErrorRef;

pub type LLVMOrcSymbolPredicate =
    extern "C" fn(Ctx: *mut ::libc::c_void, Sym: LLVMOrcSymbolStringPoolEntryRef) -> ::libc::c_int;

#[derive(Debug)]
pub enum LLVMOrcOpaqueThreadSafeContext {}
pub type LLVMOrcThreadSafeContextRef = *mut LLVMOrcOpaqueThreadSafeContext;

#[derive(Debug)]
pub enum LLVMOrcOpaqueThreadSafeModule {}
pub type LLVMOrcThreadSafeModuleRef = *mut LLVMOrcOpaqueThreadSafeModule;

#[derive(Debug)]
pub enum LLVMOrcOpaqueJITTargetMachineBuilder {}
pub type LLVMOrcJITTargetMachineBuilderRef = *mut LLVMOrcOpaqueJITTargetMachineBuilder;

#[derive(Debug)]
pub enum LLVMOrcOpaqueObjectLayer {}
pub type LLVMOrcObjectLayerRef = *mut LLVMOrcOpaqueObjectLayer;

extern "C" {
    pub fn LLVMOrcExecutionSessionSetErrorReporter(
        ES: LLVMOrcExecutionSessionRef,
        ReportError: LLVMOrcErrorReporterFunction,
        Ctx: *mut ::libc::c_void,
    );
    pub fn LLVMOrcExecutionSessionGetSymbolStringPool(
        ES: LLVMOrcExecutionSessionRef,
    ) -> LLVMOrcSymbolStringPoolRef;
    pub fn LLVMOrcSymbolStringPoolClearDeadEntries(SSP: LLVMOrcSymbolStringPoolRef);
    pub fn LLVMOrcExecutionSessionIntern(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcSymbolStringPoolEntryRef;
    pub fn LLVMOrcRetainSymbolStringPoolEntry(S: LLVMOrcSymbolStringPoolEntryRef);
    pub fn LLVMOrcReleaseSymbolStringPoolEntry(S: LLVMOrcSymbolStringPoolEntryRef);
    pub fn LLVMOrcSymbolStringPoolEntryStr(
        S: LLVMOrcSymbolStringPoolEntryRef,
    ) -> *const ::libc::c_char;
    pub fn LLVMOrcReleaseResourceTracker(RT: LLVMOrcResourceTrackerRef);
    pub fn LLVMOrcResourceTrackerTransferTo(
        SrcRT: LLVMOrcResourceTrackerRef,
        DstRT: LLVMOrcResourceTrackerRef,
    );
    pub fn LLVMOrcResourceTrackerRemove(RT: LLVMOrcResourceTrackerRef) -> LLVMErrorRef;
    pub fn LLVMOrcDisposeDefinitionGenerator(DG: LLVMOrcDefinitionGeneratorRef);
    pub fn LLVMOrcDisposeMaterializationUnit(MU: LLVMOrcMaterializationUnitRef);
    pub fn LLVMOrcAbsoluteSymbols(
        Syms: LLVMOrcCSymbolMapPairs,
        NumPairs: usize,
    ) -> LLVMOrcMaterializationUnitRef;
    pub fn LLVMOrcExecutionSessionCreateBareJITDylib(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcJITDylibRef;
    pub fn LLVMOrcExecutionSessionCreateJITDylib(
        ES: LLVMOrcExecutionSessionRef,
        Result_: *mut LLVMOrcJITDylibRef,
        Name: *const ::libc::c_char,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcExecutionSessionGetJITDylibByName(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcJITDylibRef;
    pub fn LLVMOrcJITDylibCreateResourceTracker(
        JD: LLVMOrcJITDylibRef,
    ) -> LLVMOrcResourceTrackerRef;
    pub fn LLVMOrcJITDylibGetDefaultResourceTracker(
        JD: LLVMOrcJITDylibRef,
    ) -> LLVMOrcResourceTrackerRef;
    pub fn LLVMOrcJITDylibDefine(
        JD: LLVMOrcJITDylibRef,
        MU: LLVMOrcMaterializationUnitRef,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcJITDylibClear(JD: LLVMOrcJITDylibRef) -> LLVMErrorRef;
    pub fn LLVMOrcJITDylibAddGenerator(JD: LLVMOrcJITDylibRef, DG: LLVMOrcDefinitionGeneratorRef);
    pub fn LLVMOrcCreateCustomCAPIDefinitionGenerator(
        F: LLVMOrcCAPIDefinitionGeneratorTryToGenerateFunction,
        Ctx: *mut ::libc::c_void,
    ) -> LLVMOrcDefinitionGeneratorRef;
    pub fn LLVMOrcCreateDynamicLibrarySearchGeneratorForProcess(
        Result: *mut LLVMOrcDefinitionGeneratorRef,
        GlobalPrefix: ::libc::c_char,
        Filter: LLVMOrcSymbolPredicate,
        FilterCtx: *mut ::libc::c_void,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcCreateNewThreadSafeContext() -> LLVMOrcThreadSafeContextRef;
    pub fn LLVMOrcThreadSafeContextGetContext(TSCtx: LLVMOrcThreadSafeContextRef)
        -> LLVMContextRef;
    pub fn LLVMOrcDisposeThreadSafeContext(TSCtx: LLVMOrcThreadSafeContextRef);
    pub fn LLVMOrcCreateNewThreadSafeModule(
        M: LLVMModuleRef,
        TSCtx: LLVMOrcThreadSafeContextRef,
    ) -> LLVMOrcThreadSafeModuleRef;
    pub fn LLVMOrcDisposeThreadSafeModule(TSM: LLVMOrcThreadSafeModuleRef);
    pub fn LLVMOrcJITTargetMachineBuilderDetectHost(
        Result: *mut LLVMOrcJITTargetMachineBuilderRef,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcJITTargetMachineBuilderCreateFromTargetMachine(
        TM: LLVMTargetMachineRef,
    ) -> LLVMOrcJITTargetMachineBuilderRef;
    pub fn LLVMOrcDisposeJITTargetMachineBuilder(JTMB: LLVMOrcJITTargetMachineBuilderRef);
    pub fn LLVMOrcDisposeObjectLayer(ObjLayer: LLVMOrcObjectLayerRef);
}
<commit_msg>Correctly make LLVMOrcSymbolPredicate nullable<commit_after>#![allow(non_snake_case)]
//! OrcV2

pub mod ee;
pub mod lljit;

use error::LLVMErrorRef;
use prelude::*;
use target_machine::LLVMTargetMachineRef;

pub type LLVMOrcJITTargetAddress = u64;

/// Generic linkage flags for a symbol definition.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMJITSymbolGenericFlags {
    LLVMJITSymbolGenericFlagsExported = 1,
    LLVMJITSymbolGenericFlagsWeak = 2,
}

/// Target specific flags for a symbol definition.
pub type LLVMJITTargetSymbolFlags = u8;

/// Linkage flags for a symbol definition.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITSymbolFlags {
    GenericFlags: u8,
    TargetFlags: u8,
}

/// An evaluated symbol address and flags.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITEvaluatedSymbol {
    Address: LLVMOrcJITTargetAddress,
    Flags: LLVMJITSymbolFlags,
}

#[derive(Debug)]
pub enum LLVMOrcOpaqueExecutionSession {}
pub type LLVMOrcExecutionSessionRef = *mut LLVMOrcOpaqueExecutionSession;

/// Error reporter function.
pub type LLVMOrcErrorReporterFunction = extern "C" fn(Ctx: *mut ::libc::c_void, Err: LLVMErrorRef);

#[derive(Debug)]
pub enum LLVMOrcOpaqueSymbolStringPool {}
/// A reference to an orc::SymbolStringPool.
pub type LLVMOrcSymbolStringPoolRef = *mut LLVMOrcOpaqueSymbolStringPool;

#[derive(Debug)]
pub enum LLVMOrcQuaqueSymbolStringPoolEntry {}
pub type LLVMOrcSymbolStringPoolEntryRef = *mut LLVMOrcQuaqueSymbolStringPoolEntry;

/// A pair of a symbol name and an evaluated symbol.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMJITCSymbolMapPair {
    Name: LLVMOrcSymbolStringPoolEntryRef,
    Sym: LLVMJITEvaluatedSymbol,
}

/// A list of (SymbolStringPtr, JITEvaluatedSymbol) pairs that can be
/// used to construct a SymbolMap.
pub type LLVMOrcCSymbolMapPairs = *mut LLVMJITCSymbolMapPair;

/// Lookup kind. This can be used by definition generators when deciding whether
/// to produce a definition for a requested symbol.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcLookupKind {
    LLVMOrcLookupKindStatic,
    LLVMOrcLookupKindDLSym,
}

/// JITDylib lookup flags. This can be used by definition generators when
/// deciding whether to produce a definition for a requested symbol.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcJITDylibLookupFlags {
    LLVMOrcJITDylibLookupFlagsMatchExportedSymbolsOnly,
    LLVMOrcJITDylibLookupFlagsMatchAllSymbols,
}

/// Symbol lookup flags for lookup sets.
#[repr(C)]
#[derive(Debug)]
pub enum LLVMOrcSymbolLookupFlags {
    LLVMOrcSymbolLookupFlagsRequiredSymbol,
    LLVMOrcSymbolLookupFlagsWeaklyReferencedSymbol,
}

/// An element type for a symbol lookup set.
#[repr(C)]
#[derive(Debug)]
pub struct LLVMOrcCLookupSetElement {
    Name: LLVMOrcSymbolStringPoolEntryRef,
    LookupFlags: LLVMOrcSymbolLookupFlags,
}

/// A set of symbols to look up / generate.
///
/// The list is terminated with an element containing a null pointer for the
/// Name field.
///
/// The creator is responsible for freeing the set and ensuring all strings
/// are retained for the set's lifetime.
pub type LLVMOrcCLookupSet = *mut LLVMOrcCLookupSetElement;

#[derive(Debug)]
pub enum LLVMOrcOpaqueMaterializationUnit {}
pub type LLVMOrcMaterializationUnitRef = *mut LLVMOrcOpaqueMaterializationUnit;

#[derive(Debug)]
pub enum LLVMOrcOpaqueJITDylib {}
pub type LLVMOrcJITDylibRef = *mut LLVMOrcOpaqueJITDylib;

#[derive(Debug)]
pub enum LLVMOrcOpaqueResourceTracker {}
pub type LLVMOrcResourceTrackerRef = *mut LLVMOrcOpaqueResourceTracker;

#[derive(Debug)]
pub enum LLVMOrcOpaqueDefinitionGenerator {}
pub type LLVMOrcDefinitionGeneratorRef = *mut LLVMOrcOpaqueDefinitionGenerator;

#[derive(Debug)]
pub enum LLVMOrcOpaqueLookupState {}
pub type LLVMOrcLookupStateRef = *mut LLVMOrcOpaqueLookupState;

pub type LLVMOrcCAPIDefinitionGeneratorTryToGenerateFunction = extern "C" fn(
    GeneratorObj: LLVMOrcDefinitionGeneratorRef,
    Ctx: *mut ::libc::c_void,
    LookupState: *mut LLVMOrcLookupStateRef,
    Kind: LLVMOrcLookupKind,
    JD: LLVMOrcJITDylibRef,
    JDLookupFlags: LLVMOrcJITDylibLookupFlags,
    LookupSet: LLVMOrcCLookupSet,
    LookupSetSize: usize,
) -> LLVMErrorRef;

pub type LLVMOrcSymbolPredicate = Option<
    extern "C" fn(Ctx: *mut ::libc::c_void, Sym: LLVMOrcSymbolStringPoolEntryRef) -> ::libc::c_int,
>;

#[derive(Debug)]
pub enum LLVMOrcOpaqueThreadSafeContext {}
pub type LLVMOrcThreadSafeContextRef = *mut LLVMOrcOpaqueThreadSafeContext;

#[derive(Debug)]
pub enum LLVMOrcOpaqueThreadSafeModule {}
pub type LLVMOrcThreadSafeModuleRef = *mut LLVMOrcOpaqueThreadSafeModule;

#[derive(Debug)]
pub enum LLVMOrcOpaqueJITTargetMachineBuilder {}
pub type LLVMOrcJITTargetMachineBuilderRef = *mut LLVMOrcOpaqueJITTargetMachineBuilder;

#[derive(Debug)]
pub enum LLVMOrcOpaqueObjectLayer {}
pub type LLVMOrcObjectLayerRef = *mut LLVMOrcOpaqueObjectLayer;

extern "C" {
    pub fn LLVMOrcExecutionSessionSetErrorReporter(
        ES: LLVMOrcExecutionSessionRef,
        ReportError: LLVMOrcErrorReporterFunction,
        Ctx: *mut ::libc::c_void,
    );
    pub fn LLVMOrcExecutionSessionGetSymbolStringPool(
        ES: LLVMOrcExecutionSessionRef,
    ) -> LLVMOrcSymbolStringPoolRef;
    pub fn LLVMOrcSymbolStringPoolClearDeadEntries(SSP: LLVMOrcSymbolStringPoolRef);
    pub fn LLVMOrcExecutionSessionIntern(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcSymbolStringPoolEntryRef;
    pub fn LLVMOrcRetainSymbolStringPoolEntry(S: LLVMOrcSymbolStringPoolEntryRef);
    pub fn LLVMOrcReleaseSymbolStringPoolEntry(S: LLVMOrcSymbolStringPoolEntryRef);
    pub fn LLVMOrcSymbolStringPoolEntryStr(
        S: LLVMOrcSymbolStringPoolEntryRef,
    ) -> *const ::libc::c_char;
    pub fn LLVMOrcReleaseResourceTracker(RT: LLVMOrcResourceTrackerRef);
    pub fn LLVMOrcResourceTrackerTransferTo(
        SrcRT: LLVMOrcResourceTrackerRef,
        DstRT: LLVMOrcResourceTrackerRef,
    );
    pub fn LLVMOrcResourceTrackerRemove(RT: LLVMOrcResourceTrackerRef) -> LLVMErrorRef;
    pub fn LLVMOrcDisposeDefinitionGenerator(DG: LLVMOrcDefinitionGeneratorRef);
    pub fn LLVMOrcDisposeMaterializationUnit(MU: LLVMOrcMaterializationUnitRef);
    pub fn LLVMOrcAbsoluteSymbols(
        Syms: LLVMOrcCSymbolMapPairs,
        NumPairs: usize,
    ) -> LLVMOrcMaterializationUnitRef;
    pub fn LLVMOrcExecutionSessionCreateBareJITDylib(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcJITDylibRef;
    pub fn LLVMOrcExecutionSessionCreateJITDylib(
        ES: LLVMOrcExecutionSessionRef,
        Result_: *mut LLVMOrcJITDylibRef,
        Name: *const ::libc::c_char,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcExecutionSessionGetJITDylibByName(
        ES: LLVMOrcExecutionSessionRef,
        Name: *const ::libc::c_char,
    ) -> LLVMOrcJITDylibRef;
    pub fn LLVMOrcJITDylibCreateResourceTracker(
        JD: LLVMOrcJITDylibRef,
    ) -> LLVMOrcResourceTrackerRef;
    pub fn LLVMOrcJITDylibGetDefaultResourceTracker(
        JD: LLVMOrcJITDylibRef,
    ) -> LLVMOrcResourceTrackerRef;
    pub fn LLVMOrcJITDylibDefine(
        JD: LLVMOrcJITDylibRef,
        MU: LLVMOrcMaterializationUnitRef,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcJITDylibClear(JD: LLVMOrcJITDylibRef) -> LLVMErrorRef;
    pub fn LLVMOrcJITDylibAddGenerator(JD: LLVMOrcJITDylibRef, DG: LLVMOrcDefinitionGeneratorRef);
    pub fn LLVMOrcCreateCustomCAPIDefinitionGenerator(
        F: LLVMOrcCAPIDefinitionGeneratorTryToGenerateFunction,
        Ctx: *mut ::libc::c_void,
    ) -> LLVMOrcDefinitionGeneratorRef;
    pub fn LLVMOrcCreateDynamicLibrarySearchGeneratorForProcess(
        Result: *mut LLVMOrcDefinitionGeneratorRef,
        GlobalPrefix: ::libc::c_char,
        Filter: LLVMOrcSymbolPredicate,
        FilterCtx: *mut ::libc::c_void,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcCreateNewThreadSafeContext() -> LLVMOrcThreadSafeContextRef;
    pub fn LLVMOrcThreadSafeContextGetContext(TSCtx: LLVMOrcThreadSafeContextRef)
        -> LLVMContextRef;
    pub fn LLVMOrcDisposeThreadSafeContext(TSCtx: LLVMOrcThreadSafeContextRef);
    pub fn LLVMOrcCreateNewThreadSafeModule(
        M: LLVMModuleRef,
        TSCtx: LLVMOrcThreadSafeContextRef,
    ) -> LLVMOrcThreadSafeModuleRef;
    pub fn LLVMOrcDisposeThreadSafeModule(TSM: LLVMOrcThreadSafeModuleRef);
    pub fn LLVMOrcJITTargetMachineBuilderDetectHost(
        Result: *mut LLVMOrcJITTargetMachineBuilderRef,
    ) -> LLVMErrorRef;
    pub fn LLVMOrcJITTargetMachineBuilderCreateFromTargetMachine(
        TM: LLVMTargetMachineRef,
    ) -> LLVMOrcJITTargetMachineBuilderRef;
    pub fn LLVMOrcDisposeJITTargetMachineBuilder(JTMB: LLVMOrcJITTargetMachineBuilderRef);
    pub fn LLVMOrcDisposeObjectLayer(ObjLayer: LLVMOrcObjectLayerRef);
}
<|endoftext|>