// Copyright 2015 Nathan Sizemore <nathanrsizemore@gmail.com>
//
// This Source Code Form is subject to the terms of the
// Mozilla Public License, v. 2.0. If a copy of the MPL was not
// distributed with this file, You can obtain one at
// http://mozilla.org/MPL/2.0/.
//! hydrogen is a non-blocking Edge Triggered TCP socket lib built atop [epoll][epoll-man-page]
//! with performance, concurrency, and scalability as its main priorities. It takes care of the
//! tedious connection and I/O marshalling across threads, and leaves the specifics of I/O reading
//! and writing up the consumer, through trait implementations.
//!
//! # Streams
//!
//! hydrogen manages the state of connections through [`hydrogen::Stream`][stream-trait]
//! [Trait Objects][trait-objects].
//!
//! # Events
//!
//! hydrogen reports all events to the [`hydrogen::Handler`][handler] passed during creation.
//! Interaction to `hydrogen::Stream` trait objects is made through a simple wrapper,
//! `HydrogenSocket`, to ensure thread safety.
//!
//! # Example Usage
//!
//! The following is a simple snippet using the [simple-stream][simple-stream-repo] crate to
//! provide the non-blocking I/O calls.
//!
//!
//! ```ignore
//! extern crate hydrogen;
//! extern crate simple_stream as ss;
//!
//! use hydrogen;
//! use hydrogen::{Stream as HydrogenStream, HydrogenSocket};
//! use ss::frame::Frame;
//! use ss::frame::simple::{SimpleFrame, SimpleFrameBuilder};
//! use ss::{Socket, Plain, NonBlocking, SocketOptions};
//!
//!
//! #[derive(Clone)]
//! pub struct Stream {
//! inner: Plain<Socket, SimpleFrameBuilder>
//! }
//!
//! impl HydrogenStream for Stream {
//! fn recv(&mut self) -> Result<Vec<Vec<u8>>, Error> {
//! match self.inner.nb_recv() {
//! Ok(frame_vec) => {
//! let mut ret_buf = Vec::<Vec<u8>>::with_capacity(frame_vec.len());
//! for frame in frame_vec.iter() {
//! ret_buf.push(frame.payload());
//! }
//! Ok(ret_buf)
//! }
//! Err(e) => Err(e)
//! }
//! }
//!
//! fn send(&mut self, buf: &[u8]) -> Result<(), Error> {
//! let frame = SimpleFrame::new(buf);
//! self.inner.nb_send(&frame)
//! }
//!
//! fn shutdown(&mut self) -> Result<(), Error> {
//! self.inner.shutdown()
//! }
//! }
//! impl AsRawFd for Stream {
//! fn as_raw_fd(&self) -> RawFd { self.inner.as_raw_fd() }
//! }
//!
//!
//! struct Server;
//! impl hydrogen::Handler for Server {
//! fn on_server_created(&mut self, fd: RawFd) {
//!
//! }
//!
//! fn on_new_connection(&mut self, fd: RawFd) -> Arc<UnsafeCell<HydrogenStream>> {
//!
//! }
//!
//! fn on_data_received(&mut self, socket: HydrogenSocket, buffer: Vec<u8>) {
//!
//! }
//!
//! fn on_connection_removed(&mut self, fd: RawFd, err: Error) {
//!
//! }
//! }
//!
//!
//! fn main() {
//! hydrogen::begin(Server, hydrogen::Config {
//! addr: "0.0.0.0".to_string(),
//! port: 1337,
//! max_threads: 8,
//! pre_allocated: 100000
//! });
//! }
//!
//! ```
//!
//!
//!
//! [epoll-man-page]: http://man7.org/linux/man-pages/man7/epoll.7.html
//! [stream-trait]: https://nathansizemore.github.io/hydrogen/hydrogen/trait.Stream.html
//! [trait-objects]: https://doc.rust-lang.org/book/trait-objects.html
//! [handler]: https://nathansizemore.github.io/hydrogen/hydrogen/trait.Handler.html
//! [simple-stream-repo]: https://github.com/nathansizemore/simple-stream
extern crate log;
extern crate libc;
extern crate errno;
extern crate threadpool;
extern crate simple_slab;
use Error;
use Arc;
use UnsafeCell;
use ;
pub use Config;
pub use HydrogenSocket;
/// Trait object responsible for handling reported I/O events.
/// Events reported to lib consumer.
/// Starts the server with the passed configuration and handler.