dd-lib 0.2.1

library functions for a clone of the unix coreutil dd
Documentation
//! # dd: convert and copy a file  
//!
//! ## SYNOPSIS         
//! dd \[OPERAND\]...
//! dd OPTION
//! ## DESCRIPTION         
//! Copy a file converting and formatting according to the operands.
//!
//! ## [`opts`]
//! Note: the parsing of numeric arguments is a little unusual and allows for
//! numeric suffixes. See the documentation of [opts::number] and
//! [opts::number::units];
//!
//! - **bs**=BYTES: read and write up to BYTES bytes at a time (default: 512).
//!   - **overrides ibs and obs**
//!
//! - **cbs**=BYTES: convert BYTES bytes at a time
//!
//! - **conv**=[`CONVS`][opts::Conv]: convert the file as per the coma
//!   separated symbol list
//!
//! - **count**=N: copy only N input blocks
//!
//! - **ibs**=BYTES: read up to BYTES bytes at a time (default: 512)
//!
//! - **if**=FILE: read from FILE instead of stdin
//!
//! - **iflag**=[`FLAGS`][opts::In]: read as per the comma separated   symbol
//!   list
//!
//! - **obs**=BYTES: write BYTES bytes at a time (default: 512)
//!
//! - **of**=FILE: write to FILE instead of stdout
//!
//! - **oflag**=[`FLAGS`][opts::Out]: write as per the comma separated   symbol
//!   list
//!
//! - **seek**=N: skip N obs-sized blocks at start of output
//!
//! - **skip**=N: skip N ibs-sized blocks at start of input
//!
//! - **status=[LEVEL][opts::StatusLevel]**: the level of information to print
//!   to stderr
//!
//!    none: suppresses everything but error messages,
//!    progress //! - **shows** periodic transfer statistics
//!    noxfer: suppresses the final transfer statistics,
//!
//!
//! ### [Units][opts::number::units]:

//! ### [`CONV`][opts::Conv]
//! Each CONV symbol may be:

//! 
//! - **ascii**  from EBCDIC to ASCII

//! 
//! - **ebcdic** from ASCII to EBCDIC

//! 
//! - **ibm**    from ASCII to alternate EBCDIC

//! 
//! - **block**  pad newline-terminated records with spaces to cbs-size

//! 
//! - **unblock** replace trailing spaces in cbs-size records with newline

//! 
//! - **lcase**  change upper case to lower case

//! 
//! - **ucase**  change lower case to upper case

//! 
//! - **sparse** try to seek rather than write the output for NUL input blocks

//! 
//! - **swab**   swap every pair of input bytes

//! 
//! - **sync**   pad every input block with NULs to ibs-size; when used with
//!   block or unblock, pad with spaces rather than NULs

//! 
//! - **excl**   fail if the output file already exists

//! 
//! - **nocreat** do not create the output file

//! 
//! - **notrunc** do not truncate the output file

//! 
//! - **noerror** continue after read errors

//! 
//! - **fdatasync**
//! physically write output file data before finishing
//! - **fsync**  likewise, but also write metadata

//! ### SIGNALS
//! Sending a USR1 signal to a running 'dd' process makes it print I/O
//! statistics to standard error and then resume copying.
//!
//!
//! ### OPTIONS
//! --help display this help and exit
//! --version
//! output version information and exit
//! ### AUTHOR         
//! Originally Written by Paul Rubin, David MacKenzie, and Stuart Kemp.
//! Clone written _only_ by looking at man page by Efron Licht
//! input, output, and encoding

pub mod io;
pub mod opts;
pub mod units;
use io::{Converter, ErrHandler, Reader, Writer};
pub use results::{Result, Success};

mod results;

#[cfg(test)]
extern crate tempfile;
#[macro_use]
extern crate bitflags;
extern crate encoding8;

#[cfg(test)]
mod tests;

/// The dd utility copies the standard input to the standard output.  Input data
/// is read and written in n-byte blocks (default `512`).  If input reads are
/// short, input from multiple reads are aggregated to form the output block.
/// When finished, dd displays the number of complete and partial input and
/// output blocks and truncated input records to the standard error output.
pub fn dd(o: &opts::Opts) -> Result<Success> {
    let stderr = std::io::stderr();
    let lock = stderr.lock();
    dd_pipe_err(o, lock)
}

/// dd, piping standard error to E
pub fn dd_pipe_err<E>(o: &opts::Opts, err: E) -> Result<Success>
where
    E: std::io::Write, // in practice, this is always stderr
{
    let (stdin, stdout) = (std::io::stdin(), std::io::stdout());
    let r = Reader::new(&stdin, o)?;
    let mut w = Writer::new(&stdout, o)?;
    let c = Converter::new(o)?;
    let e = ErrHandler::new(err, o);
    match o.mode {
        opts::Mode::Block(n) => io::copy::block(r, &mut w, c, e, n),
        opts::Mode::Unblock(n) => io::copy::unblock(r, &mut w, c, e, n),
        opts::Mode::Standard => io::copy::standard(r, &mut w, c, e),
    }
}