diff --git a/Cargo.lock b/Cargo.lock
index a687b991876a5570c85a19cc24776e8a154299bf..cc9f8add6d65838894bd4f9215a46e38f36fc2f7 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -172,7 +172,6 @@ dependencies = [
  "ion_sys 0.1.0",
  "itoa 0.4.2 (registry+https://github.com/rust-lang/crates.io-index)",
  "lazy_static 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
- "libloading 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "liner 0.4.5 (git+https://gitlab.redox-os.org/redox-os/liner)",
  "rand 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)",
  "regex 1.0.2 (registry+https://github.com/rust-lang/crates.io-index)",
diff --git a/Cargo.toml b/Cargo.toml
index 777eefd4643dbb6a02b6c048f36dd311cb4d359c..daf60683b4c73bfcdbc34ebe17e326f1764f75d1 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -61,8 +61,5 @@ path = "src/lib/lib.rs"
 lto = true
 panic = "abort"
 
-[target."cfg(all(unix, not(target_os = \"redox\")))".dependencies]
-libloading = "0.5"
-
 [patch.crates-io]
 liner = { git = "https://gitlab.redox-os.org/redox-os/liner" }
diff --git a/src/lib/lib.rs b/src/lib/lib.rs
index 4dff149b4ed2cf27f09ed03e414d4b69c5e880a5..32c7979804023706b8ee0a723f306a6a3daa5ea1 100644
--- a/src/lib/lib.rs
+++ b/src/lib/lib.rs
@@ -12,8 +12,6 @@ extern crate glob;
 extern crate itoa;
 #[macro_use]
 extern crate lazy_static;
-#[cfg(all(unix, not(target_os = "redox")))]
-extern crate libloading;
 extern crate liner;
 extern crate regex;
 extern crate small;
diff --git a/src/lib/parser/shell_expand/mod.rs b/src/lib/parser/shell_expand/mod.rs
index 97e180fb0f758057f5fa3e8597df1e5e9b2b6905..5707eefdb43acfd03dc644ee075543d34eec3a4c 100644
--- a/src/lib/parser/shell_expand/mod.rs
+++ b/src/lib/parser/shell_expand/mod.rs
@@ -537,7 +537,7 @@ fn expand_single_string_token<E: Expander>(
     }
 
     if output.as_str() != "" {
-        expanded_words.push(output.into());
+        expanded_words.push(output);
     }
     expanded_words
 }
diff --git a/src/lib/parser/shell_expand/words/methods/arrays.rs b/src/lib/parser/shell_expand/words/methods/arrays.rs
index 4918e59b83bd2e71ddc9fd0b96be46a2eca57bab..d6ed6a0fed1725fa79da7352f920ef5c17b1f617 100644
--- a/src/lib/parser/shell_expand/words/methods/arrays.rs
+++ b/src/lib/parser/shell_expand/words/methods/arrays.rs
@@ -29,11 +29,7 @@ impl<'a> ArrayMethod<'a> {
 
     fn lines<E: Expander>(&self, expand_func: &E) -> Result<Array, &'static str> {
         let variable = self.resolve_var(expand_func);
-        Ok(variable
-            .lines()
-            .into_iter()
-            .map(|line| types::Str::from(line))
-            .collect())
+        Ok(variable.lines().into_iter().map(types::Str::from).collect())
     }
 
     fn chars<E: Expander>(&self, expand_func: &E) -> Result<Array, &'static str> {
diff --git a/src/lib/parser/shell_expand/words/methods/strings.rs b/src/lib/parser/shell_expand/words/methods/strings.rs
index c6acd7aa223cbbc128b6967783fefdc06789b6cd..f2e38ac9411f50732fc5326e56d91764da329155 100644
--- a/src/lib/parser/shell_expand/words/methods/strings.rs
+++ b/src/lib/parser/shell_expand/words/methods/strings.rs
@@ -7,16 +7,10 @@ use super::{
 };
 use parser::assignments::is_array;
 use regex::Regex;
-use shell::plugins::methods::{self, MethodArguments, StringMethodPlugins};
 use small;
 use std::path::Path;
-use sys;
 use unicode_segmentation::UnicodeSegmentation;
 
-lazy_static! {
-    static ref STRING_METHODS: StringMethodPlugins = methods::collect();
-}
-
 pub(crate) fn unescape(input: &str) -> Result<small::String, &'static str> {
     let mut check = false;
     let mut out = small::String::with_capacity(input.len());
@@ -303,8 +297,6 @@ impl<'a> StringMethod<'a> {
                 let second_array = pattern.array();
                 let first_maybe: Option<String> = if first_str != "" {
                     Some(first_str.to_string())
-                } else if first_str == "" {
-                    None
                 } else {
                     None
                 };
@@ -339,36 +331,9 @@ impl<'a> StringMethod<'a> {
                     }
                 };
             }
-            method => {
-                if sys::is_root() {
-                    eprintln!("ion: root is not allowed to execute plugins");
-                    return;
-                }
-
-                let pattern = pattern.array().collect::<Vec<_>>();
-                let args = if variable.starts_with('@') || is_array(variable) {
-                    MethodArguments::Array(
-                        expand_string(variable, expand, false).into_vec(),
-                        pattern,
-                    )
-                } else if let Some(value) = expand.string(variable, false) {
-                    MethodArguments::StringArg(value, pattern)
-                } else if is_expression(variable) {
-                    let expanded = expand_string(variable, expand, false);
-                    match expanded.len() {
-                        0 => MethodArguments::NoArgs,
-                        1 => MethodArguments::StringArg(expanded[0].clone(), pattern),
-                        _ => MethodArguments::Array(expanded.into_vec(), pattern),
-                    }
-                } else {
-                    MethodArguments::NoArgs
-                };
-
-                match STRING_METHODS.execute(method, args) {
-                    Ok(Some(string)) => output.push_str(&string),
-                    Ok(None) => (),
-                    Err(why) => eprintln!("ion: method plugin: {}", why),
-                }
+            _ => {
+                eprintln!("ion: method namespace not found");
+                return;
             }
         }
     }
diff --git a/src/lib/parser/statement/splitter.rs b/src/lib/parser/statement/splitter.rs
index 5828867db0d22edea7eaad5275389536805b584f..8805481009047be1673fe62c5dc5a59b6938e023 100644
--- a/src/lib/parser/statement/splitter.rs
+++ b/src/lib/parser/statement/splitter.rs
@@ -313,12 +313,10 @@ impl<'a> Iterator for StatementSplitter<'a> {
                 }
                 b' ' if else_found => {
                     let output = &self.data[else_pos..self.read - 1].trim();
-                    if !output.is_empty() {
-                        if "if" != *output {
-                            self.read = else_pos;
-                            self.flags.remove(Flags::AND | Flags::OR);
-                            return Some(Ok(StatementVariant::Default("else")));
-                        }
+                    if !output.is_empty() && "if" != *output {
+                        self.read = else_pos;
+                        self.flags.remove(Flags::AND | Flags::OR);
+                        return Some(Ok(StatementVariant::Default("else")));
                     }
                     else_found = false;
                 }
diff --git a/src/lib/shell/assignments.rs b/src/lib/shell/assignments.rs
index 64fb3a349bebe1416cb6cd0ed591e5a59e1a2015..3c98c2e88d441a7f1ca600b230205c03ea338e5e 100644
--- a/src/lib/shell/assignments.rs
+++ b/src/lib/shell/assignments.rs
@@ -360,7 +360,7 @@ impl VariableStore for Shell {
                                     };
 
                                     let action: Box<
-                                        Fn(f64) -> f64,
+                                        dyn Fn(f64) -> f64,
                                     > = match operator {
                                         Operator::Add => Box::new(|src| src + value),
                                         Operator::Divide => Box::new(|src| src / value),
@@ -447,11 +447,11 @@ impl VariableStore for Shell {
                                     match self.variables.get_mut(key.name) {
                                         Some(VariableType::HashMap(hmap)) => {
                                             hmap.entry(index.clone())
-                                                .or_insert(VariableType::Str(value));
+                                                .or_insert_with(|| VariableType::Str(value));
                                         }
                                         Some(VariableType::BTreeMap(bmap)) => {
                                             bmap.entry(index.clone())
-                                                .or_insert(VariableType::Str(value));
+                                                .or_insert_with(|| VariableType::Str(value));
                                         }
                                         Some(VariableType::Array(array)) => {
                                             let index_num = match index.parse::<usize>() {
diff --git a/src/lib/shell/binary/readln.rs b/src/lib/shell/binary/readln.rs
index 91ba2fcbfa0385b358a4f309b24a99ef57cffbbd..d3a8a443d9ae7744ac4b09a18d241c55991334c2 100644
--- a/src/lib/shell/binary/readln.rs
+++ b/src/lib/shell/binary/readln.rs
@@ -21,7 +21,7 @@ pub(crate) fn readln(shell: &mut Shell) -> Option<String> {
                 // Collect each result into a vector to avoid borrowing issues.
                 .collect::<Vec<types::Str>>();
 
-        loop {
+        {
             let prompt = handle_prompt(shell.prompt()).unwrap();
             let vars = &shell.variables;
             let builtins = &shell.builtins;
@@ -124,7 +124,7 @@ pub(crate) fn readln(shell: &mut Shell) -> Option<String> {
                 // Handles Ctrl + C
                 Err(ref err) if err.kind() == ErrorKind::Interrupted => return None,
                 // Handles Ctrl + D
-                Err(ref err) if err.kind() == ErrorKind::UnexpectedEof => break,
+                Err(ref err) if err.kind() == ErrorKind::UnexpectedEof => (),
                 Err(err) => {
                     eprintln!("ion: liner: {}", err);
                     return None;
diff --git a/src/lib/shell/mod.rs b/src/lib/shell/mod.rs
index 08d7a44eba9e8d470d53bbc1784b390d8efe2edc..555d89625b0207738a3c6c255bb053d424d8ff9c 100644
--- a/src/lib/shell/mod.rs
+++ b/src/lib/shell/mod.rs
@@ -12,7 +12,6 @@ pub mod fork_function;
 mod history;
 mod job;
 pub(crate) mod pipe_exec;
-pub(crate) mod plugins;
 pub(crate) mod signals;
 pub mod status;
 pub mod variables;
diff --git a/src/lib/shell/plugins/library_iter/mod.rs b/src/lib/shell/plugins/library_iter/mod.rs
deleted file mode 100644
index 2c5a0f74d3e884913d0250e0c67399ad9e3c0317..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/library_iter/mod.rs
+++ /dev/null
@@ -1,9 +0,0 @@
-#[cfg(target_os = "redox")]
-mod redox;
-// #[cfg(target_os = "redox")]
-// pub(crate) use self::redox::*;
-
-#[cfg(all(unix, not(target_os = "redox")))]
-mod unix;
-#[cfg(all(unix, not(target_os = "redox")))]
-pub(crate) use self::unix::*;
diff --git a/src/lib/shell/plugins/library_iter/redox.rs b/src/lib/shell/plugins/library_iter/redox.rs
deleted file mode 100644
index 72745aab3365f273ddbdb3b88b7ef258083507b5..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/library_iter/redox.rs
+++ /dev/null
@@ -1,21 +0,0 @@
-use std::fs::ReadDir;
-use types;
-
-pub(crate) struct Library;
-
-/// Grabs all `Library` entries found within a given directory
-pub(crate) struct LibraryIterator {
-    directory: ReadDir,
-}
-
-impl LibraryIterator {
-    pub(crate) fn new(directory: ReadDir) -> LibraryIterator { LibraryIterator { directory } }
-}
-
-impl Iterator for LibraryIterator {
-    // The `Identifier` is the name of the namespace for which values may be pulled.
-    // The `Library` is a handle to dynamic library loaded into memory.
-    type Item = (types::Str, Library);
-
-    fn next(&mut self) -> Option<(types::Str, Library)> { None }
-}
diff --git a/src/lib/shell/plugins/library_iter/unix.rs b/src/lib/shell/plugins/library_iter/unix.rs
deleted file mode 100644
index 45b985bf29cd84b165ee2b7016eb464e5e851ded..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/library_iter/unix.rs
+++ /dev/null
@@ -1,52 +0,0 @@
-use libloading::Library;
-use std::fs::ReadDir;
-use types;
-
-/// Grabs all `Library` entries found within a given directory
-pub(crate) struct LibraryIterator {
-    directory: ReadDir,
-}
-
-impl LibraryIterator {
-    pub(crate) fn new(directory: ReadDir) -> LibraryIterator { LibraryIterator { directory } }
-}
-
-impl Iterator for LibraryIterator {
-    // The `Identifier` is the name of the namespace for which values may be pulled.
-    // The `Library` is a handle to dynamic library loaded into memory.
-    type Item = (types::Str, Library);
-
-    fn next(&mut self) -> Option<(types::Str, Library)> {
-        while let Some(entry) = self.directory.next() {
-            let entry = if let Ok(entry) = entry {
-                entry
-            } else {
-                continue;
-            };
-            let path = entry.path();
-            // An entry is a library if it is a file with a 'so' extension.
-            if path.is_file() && path.extension().map_or(false, |ext| ext == "so") {
-                // The identifier will be the file name of that file, without the extension.
-                let identifier = match path.file_stem().unwrap().to_str() {
-                    Some(filename) => types::Str::from(filename),
-                    None => {
-                        eprintln!("ion: namespace plugin has invalid filename");
-                        continue;
-                    }
-                };
-
-                // This will attempt to load the library into memory.
-                match Library::new(path.as_os_str()) {
-                    Ok(library) => return Some((identifier, library)),
-                    Err(why) => {
-                        eprintln!("ion: failed to load library: {:?}, {:?}", path, why);
-                        continue;
-                    }
-                }
-            } else {
-                continue;
-            }
-        }
-        None
-    }
-}
diff --git a/src/lib/shell/plugins/methods/mod.rs b/src/lib/shell/plugins/methods/mod.rs
deleted file mode 100644
index 286d5815aedba6635c57f138c25635754fa83cdc..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/methods/mod.rs
+++ /dev/null
@@ -1,9 +0,0 @@
-#[cfg(target_os = "redox")]
-mod redox;
-#[cfg(target_os = "redox")]
-pub(crate) use self::redox::*;
-
-#[cfg(all(unix, not(target_os = "redox")))]
-mod unix;
-#[cfg(all(unix, not(target_os = "redox")))]
-pub(crate) use self::unix::*;
diff --git a/src/lib/shell/plugins/methods/redox.rs b/src/lib/shell/plugins/methods/redox.rs
deleted file mode 100644
index 655c2d143038346d29867ddf608d12cc637904f7..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/methods/redox.rs
+++ /dev/null
@@ -1,28 +0,0 @@
-use super::super::StringError;
-use small;
-
-pub(crate) enum MethodArguments {
-    StringArg(small::String, Vec<small::String>),
-    Array(Vec<small::String>, Vec<small::String>),
-    NoArgs,
-}
-
-pub(crate) struct StringMethodPlugins;
-
-impl StringMethodPlugins {
-    pub(crate) fn execute(
-        &self,
-        _function: &str,
-        _arguments: MethodArguments,
-    ) -> Result<Option<small::String>, StringError> {
-        Ok(None)
-    }
-
-    pub(crate) fn new() -> StringMethodPlugins { StringMethodPlugins }
-}
-
-/// Collects all dynamically-loaded namespaces and their associated symbols all at once.
-///
-/// This function is meant to be called with `lazy_static` to ensure that there isn't a
-/// cost to collecting all this information when the shell never uses it in the first place!
-pub(crate) fn collect() -> StringMethodPlugins { StringMethodPlugins::new() }
diff --git a/src/lib/shell/plugins/methods/unix.rs b/src/lib/shell/plugins/methods/unix.rs
deleted file mode 100644
index 65720c35f3d0ab4b5f44408813dc38bb08871ad2..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/methods/unix.rs
+++ /dev/null
@@ -1,246 +0,0 @@
-use super::super::{config_dir, LibraryIterator, StringError};
-use fnv::FnvHashMap;
-use libloading::{os::unix::Symbol as RawSymbol, Library, Symbol};
-use small;
-use std::{ffi::CString, fs::read_dir, mem::forget, os::raw::c_char, ptr, slice, str};
-use types;
-
-/// Either one or the other will be set. Optional status can be conveyed by setting the
-/// corresponding field to `NULL`. Libraries importing this structure should check for nullness.
-#[repr(C)]
-pub(crate) struct RawMethodArguments {
-    key_ptr:       *mut c_char,
-    key_array_ptr: *mut *mut c_char,
-    args_ptr:      *mut *mut c_char,
-    key_len:       usize,
-    args_len:      usize,
-}
-
-pub(crate) enum MethodArguments {
-    StringArg(small::String, Vec<small::String>),
-    Array(Vec<small::String>, Vec<small::String>),
-    NoArgs,
-}
-
-impl From<MethodArguments> for RawMethodArguments {
-    fn from(arg: MethodArguments) -> RawMethodArguments {
-        match arg {
-            MethodArguments::StringArg(string, args) => {
-                let args_len = args.len();
-                let mut args = args
-                    .iter()
-                    .map(|x| unsafe {
-                        CString::from_vec_unchecked(x.as_bytes().to_owned()).into_raw()
-                    })
-                    .collect::<Vec<*mut c_char>>();
-                args.shrink_to_fit();
-                let args_ptr = args.as_mut_ptr();
-                forget(args);
-
-                RawMethodArguments {
-                    key_ptr: unsafe {
-                        CString::from_vec_unchecked(string.as_bytes().to_owned()).into_raw()
-                    },
-                    key_array_ptr: ptr::null_mut(),
-                    args_ptr,
-                    key_len: 1,
-                    args_len,
-                }
-            }
-            MethodArguments::Array(array, args) => {
-                let key_len = array.len();
-                let mut key_array = array
-                    .iter()
-                    .map(|x| unsafe {
-                        CString::from_vec_unchecked(x.as_bytes().to_owned()).into_raw()
-                    })
-                    .collect::<Vec<*mut c_char>>();
-                let key_array_ptr = key_array.as_mut_ptr();
-                forget(key_array);
-
-                let args_len = args.len();
-                let mut args = args
-                    .iter()
-                    .map(|x| unsafe {
-                        CString::from_vec_unchecked(x.as_bytes().to_owned()).into_raw()
-                    })
-                    .collect::<Vec<*mut c_char>>();
-                args.shrink_to_fit();
-                let args_ptr = args.as_mut_ptr();
-                forget(args);
-
-                RawMethodArguments {
-                    key_ptr: ptr::null_mut(),
-                    key_array_ptr,
-                    args_ptr,
-                    key_len,
-                    args_len,
-                }
-            }
-            MethodArguments::NoArgs => RawMethodArguments {
-                key_ptr:       ptr::null_mut(),
-                key_array_ptr: ptr::null_mut(),
-                args_ptr:      ptr::null_mut(),
-                key_len:       0,
-                args_len:      0,
-            },
-        }
-    }
-}
-
-/// Contains all dynamically-loaded libraries and their symbols.
-///
-/// The purpose of the structure is to: A) hold a `Library` handle to the dynamically-loaded
-/// plugin to ensure that the plugin remains loaded in memory, and it's contained symbols
-/// remain validly-executable; and B) holds a map of functions that may be executed within
-/// the namespace.
-pub(crate) struct StringMethodPlugins {
-    #[allow(dead_code)]
-    /// Contains all of the loaded libraries from whence the symbols were
-    /// obtained.
-    libraries: Vec<Library>,
-    /// A map of all the symbols that were collected from the above libraries.
-    pub symbols:
-        FnvHashMap<types::Str, RawSymbol<unsafe extern "C" fn(RawMethodArguments) -> *mut c_char>>,
-}
-
-impl StringMethodPlugins {
-    /// Attempts to execute a function within a dynamically-loaded namespace.
-    ///
-    /// If the function exists, it is executed, and it's return value is then converted into a
-    /// proper Rusty type.
-    pub(crate) fn execute(
-        &self,
-        function: &str,
-        arguments: MethodArguments,
-    ) -> Result<Option<String>, StringError> {
-        let func = self
-            .symbols
-            .get(function)
-            .ok_or_else(|| StringError::FunctionMissing(function.into()))?;
-        unsafe {
-            let data = (*func)(RawMethodArguments::from(arguments));
-            if data.is_null() {
-                Ok(None)
-            } else {
-                match CString::from_raw(data as *mut c_char).to_str() {
-                    Ok(string) => Ok(Some(string.to_owned())),
-                    Err(_) => Err(StringError::UTF8Result),
-                }
-            }
-        }
-    }
-
-    pub(crate) fn load(&mut self, library: Library) -> Result<(), StringError> {
-        unsafe {
-            {
-                // The `index` function contains a list of functions provided by the library.
-                let index: Symbol<unsafe extern "C" fn() -> *const u8> =
-                    library.get(b"index\0").map_err(StringError::SymbolErr)?;
-                let symbol_list = index();
-
-                // Yet we need to convert the raw stream of binary into a native slice if we
-                // want to properly reason about the contents of said aforementioned stream.
-                let (mut start, mut counter) = (0, 0usize);
-                let symbol_list: &[u8] = {
-                    let mut byte = *symbol_list.offset(0);
-                    while byte != b'\0' {
-                        counter += 1;
-                        byte = *symbol_list.offset(counter as isize);
-                    }
-                    slice::from_raw_parts(symbol_list, counter)
-                };
-                counter = 0;
-
-                // Each function symbol is delimited by spaces, so this will slice our
-                // newly-created byte slice on each space, and then attempt to load and
-                // store that symbol for future use.
-                for &byte in symbol_list {
-                    if byte == b' ' {
-                        if start == counter {
-                            start += 1;
-                        } else {
-                            // Grab a slice and ensure that the name of the function is UTF-8.
-                            let slice = &symbol_list[start..counter];
-                            let identifier = str::from_utf8(slice)
-                                .map(types::Str::from)
-                                .map_err(|_| StringError::UTF8Function)?;
-
-                            // To obtain the symbol, we need to create a new `\0`-ended byte array.
-                            // TODO: There's no need to use a vector here. An array will do fine.
-                            let mut symbol = Vec::new();
-                            symbol.reserve_exact(slice.len() + 1);
-                            symbol.extend_from_slice(slice);
-                            symbol.push(b'\0');
-
-                            // Then attempt to load that symbol from the dynamic library.
-                            let symbol: Symbol<
-                                unsafe extern "C" fn(RawMethodArguments) -> *mut c_char,
-                            > = library
-                                .get(symbol.as_slice())
-                                .map_err(StringError::SymbolErr)?;
-
-                            // And finally add the name of the function and it's function into the
-                            // map.
-                            self.symbols.insert(identifier, symbol.into_raw());
-                            start = counter + 1;
-                        }
-                    }
-                    counter += 1;
-                }
-
-                // Identical to the logic in the loop above. Handles any unparsed stragglers
-                // that have been left over.
-                if counter != start {
-                    let slice = &symbol_list[start..];
-                    let identifier = str::from_utf8(slice)
-                        .map(types::Str::from)
-                        .map_err(|_| StringError::UTF8Function)?;
-                    let mut symbol = Vec::new();
-                    symbol.reserve_exact(slice.len() + 1);
-                    symbol.extend_from_slice(slice);
-                    symbol.push(b'\0');
-                    let symbol: Symbol<
-                        unsafe extern "C" fn(RawMethodArguments) -> *mut c_char,
-                    > = library
-                        .get(symbol.as_slice())
-                        .map_err(StringError::SymbolErr)?;
-                    self.symbols.insert(identifier, symbol.into_raw());
-                }
-            }
-
-            self.libraries.push(library);
-            Ok(())
-        }
-    }
-
-    pub(crate) fn new() -> StringMethodPlugins {
-        StringMethodPlugins {
-            libraries: Vec::new(),
-            symbols:   FnvHashMap::default(),
-        }
-    }
-}
-
-/// Collects all dynamically-loaded namespaces and their associated symbols all at once.
-///
-/// This function is meant to be called with `lazy_static` to ensure that there isn't a
-/// cost to collecting all this information when the shell never uses it in the first place!
-pub(crate) fn collect() -> StringMethodPlugins {
-    let mut methods = StringMethodPlugins::new();
-    if let Some(mut path) = config_dir() {
-        path.push("methods");
-        path.push("strings");
-        match read_dir(&path).map(LibraryIterator::new) {
-            Ok(iterator) => for (_, library) in iterator {
-                if let Err(why) = methods.load(library) {
-                    eprintln!("ion: string method error: {}", why);
-                }
-            },
-            Err(why) => {
-                eprintln!("ion: unable to read methods plugin directory: {}", why);
-            }
-        }
-    }
-    methods
-}
diff --git a/src/lib/shell/plugins/mod.rs b/src/lib/shell/plugins/mod.rs
deleted file mode 100644
index b2d391848f1b2c948b0ba064e17fac4fd93edc8a..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/mod.rs
+++ /dev/null
@@ -1,27 +0,0 @@
-mod library_iter;
-pub mod methods;
-pub mod namespaces;
-mod string;
-
-#[cfg(not(target_os = "redox"))]
-pub(crate) use self::library_iter::*;
-pub(crate) use self::string::StringError;
-
-use std::path::PathBuf;
-use xdg::BaseDirectories;
-
-pub(crate) fn config_dir() -> Option<PathBuf> {
-    match BaseDirectories::with_prefix("ion") {
-        Ok(base_dirs) => match base_dirs.create_config_directory("plugins") {
-            Ok(path) => Some(path),
-            Err(err) => {
-                eprintln!("ion: unable to create config directory: {:?}", err);
-                None
-            }
-        },
-        Err(err) => {
-            eprintln!("ion: unable to get config directory: {:?}", err);
-            None
-        }
-    }
-}
diff --git a/src/lib/shell/plugins/namespaces/mod.rs b/src/lib/shell/plugins/namespaces/mod.rs
deleted file mode 100644
index 286d5815aedba6635c57f138c25635754fa83cdc..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/namespaces/mod.rs
+++ /dev/null
@@ -1,9 +0,0 @@
-#[cfg(target_os = "redox")]
-mod redox;
-#[cfg(target_os = "redox")]
-pub(crate) use self::redox::*;
-
-#[cfg(all(unix, not(target_os = "redox")))]
-mod unix;
-#[cfg(all(unix, not(target_os = "redox")))]
-pub(crate) use self::unix::*;
diff --git a/src/lib/shell/plugins/namespaces/redox.rs b/src/lib/shell/plugins/namespaces/redox.rs
deleted file mode 100644
index 787565379d67e003d15990da133565c612d30b29..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/namespaces/redox.rs
+++ /dev/null
@@ -1,19 +0,0 @@
-use fnv::FnvHashMap;
-
-use super::super::StringError;
-use types;
-
-pub(crate) struct StringNamespace;
-
-impl StringNamespace {
-    pub(crate) fn execute(&self, _function: types::Str) -> Result<Option<types::Str>, StringError> {
-        Ok(None)
-    }
-
-    pub(crate) fn new() -> Result<StringNamespace, StringError> { Ok(StringNamespace) }
-}
-
-pub(crate) fn collect() -> FnvHashMap<types::Str, StringNamespace> {
-    eprintln!("ion: Redox doesn't support plugins yet");
-    FnvHashMap::default()
-}
diff --git a/src/lib/shell/plugins/namespaces/unix.rs b/src/lib/shell/plugins/namespaces/unix.rs
deleted file mode 100644
index 9e4d5e33853ad2bc646a595c31b00ba5777cc357..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/namespaces/unix.rs
+++ /dev/null
@@ -1,156 +0,0 @@
-use super::super::{config_dir, LibraryIterator, StringError};
-use fnv::FnvHashMap;
-use libloading::{os::unix::Symbol as RawSymbol, Library, Symbol};
-use std::{ffi::CString, fs::read_dir, os::raw::c_char, slice, str};
-use types;
-
-/// A dynamically-loaded string namespace from an external library.
-///
-/// The purpose of the structure is to: A) hold a `Library` handle to the dynamically-loaded
-/// plugin to ensure that the plugin remains loaded in memory, and it's contained symbols
-/// remain validly-executable; and B) holds a map of functions that may be executed within
-/// the namespace.
-pub(crate) struct StringNamespace {
-    /// This field, although never used directly, is required to exist in order to ensure
-    /// that each element in the `symbols` field remains relevant. When Rust can support
-    /// self-referencing lifetimes, we won't need to hold raw symbols anymore.
-    #[allow(dead_code)]
-    library: Library,
-    /// A hash map of symbols collected from the `Library` stored in the `library` field.
-    /// These are considered raw because they have their lifetimes erased.
-    symbols: FnvHashMap<types::Str, RawSymbol<unsafe extern "C" fn() -> *mut c_char>>,
-}
-
-impl StringNamespace {
-    /// Attempts to execute a function within a dynamically-loaded namespace.
-    ///
-    /// If the function exists, it is executed, and it's return value is then converted into a
-    /// proper Rusty type.
-    pub(crate) fn execute(&self, function: types::Str) -> Result<Option<String>, StringError> {
-        let func = self
-            .symbols
-            .get(&function)
-            .ok_or_else(|| StringError::FunctionMissing(function.clone()))?;
-        unsafe {
-            let data = (*func)();
-            if data.is_null() {
-                Ok(None)
-            } else {
-                match CString::from_raw(data as *mut c_char).to_str() {
-                    Ok(string) => Ok(Some(string.to_owned())),
-                    Err(_) => Err(StringError::UTF8Result),
-                }
-            }
-        }
-    }
-
-    pub(crate) fn new(library: Library) -> Result<StringNamespace, StringError> {
-        unsafe {
-            let mut symbols = FnvHashMap::default();
-            {
-                // The `index` function contains a list of functions provided by the library.
-                let index: Symbol<unsafe extern "C" fn() -> *const u8> =
-                    library.get(b"index\0").map_err(StringError::SymbolErr)?;
-                let symbol_list = index();
-
-                // Yet we need to convert the raw stream of binary into a native slice if we
-                // want to properly reason about the contents of said aforementioned stream.
-                let (mut start, mut counter) = (0, 0usize);
-                let symbol_list: &[u8] = {
-                    let mut byte = *symbol_list.offset(0);
-                    while byte != b'\0' {
-                        counter += 1;
-                        byte = *symbol_list.offset(counter as isize);
-                    }
-                    slice::from_raw_parts(symbol_list, counter)
-                };
-                counter = 0;
-
-                // Each function symbol is delimited by spaces, so this will slice our
-                // newly-created byte slice on each space, and then attempt to load and
-                // store that symbol for future use.
-                for &byte in symbol_list {
-                    if byte == b' ' {
-                        if start == counter {
-                            start += 1;
-                        } else {
-                            // Grab a slice and ensure that the name of the function is UTF-8.
-                            let slice = &symbol_list[start..counter];
-                            let identifier = str::from_utf8(slice)
-                                .map(types::Str::from)
-                                .map_err(|_| StringError::UTF8Function)?;
-
-                            // To obtain the symbol, we need to create a new `\0`-ended byte array.
-                            // TODO: There's no need to use a vector here. An array will do fine.
-                            let mut symbol = Vec::new();
-                            symbol.reserve_exact(slice.len() + 1);
-                            symbol.extend_from_slice(slice);
-                            symbol.push(b'\0');
-
-                            // Then attempt to load that symbol from the dynamic library.
-                            let symbol: Symbol<
-                                unsafe extern "C" fn() -> *mut c_char,
-                            > = library
-                                .get(symbol.as_slice())
-                                .map_err(StringError::SymbolErr)?;
-
-                            // And finally add the name of the function and it's function into the
-                            // map.
-                            symbols.insert(identifier, symbol.into_raw());
-                            start = counter + 1;
-                        }
-                    }
-                    counter += 1;
-                }
-
-                // Identical to the logic in the loop above. Handles any unparsed stragglers
-                // that have been left over.
-                if counter != start {
-                    let slice = &symbol_list[start..];
-                    let identifier = str::from_utf8(slice)
-                        .map(types::Str::from)
-                        .map_err(|_| StringError::UTF8Function)?;
-                    let mut symbol = Vec::new();
-                    symbol.reserve_exact(slice.len() + 1);
-                    symbol.extend_from_slice(slice);
-                    symbol.push(b'\0');
-                    let symbol: Symbol<unsafe extern "C" fn() -> *mut c_char> = library
-                        .get(symbol.as_slice())
-                        .map_err(StringError::SymbolErr)?;
-                    symbols.insert(identifier, symbol.into_raw());
-                }
-            }
-
-            Ok(StringNamespace { library, symbols })
-        }
-    }
-}
-
-/// Collects all dynamically-loaded namespaces and their associated symbols all at once.
-///
-/// This function is meant to be called with `lazy_static` to ensure that there isn't a
-/// cost to collecting all this information when the shell never uses it in the first place!
-pub(crate) fn collect() -> FnvHashMap<types::Str, StringNamespace> {
-    let mut hashmap = FnvHashMap::default();
-    if let Some(mut path) = config_dir() {
-        path.push("namespaces");
-        path.push("strings");
-        match read_dir(&path).map(LibraryIterator::new) {
-            Ok(iterator) => for (identifier, library) in iterator {
-                match StringNamespace::new(library) {
-                    Ok(namespace) => {
-                        hashmap.insert(identifier, namespace);
-                    }
-                    Err(why) => {
-                        eprintln!("ion: string namespace error: {}", why);
-                        continue;
-                    }
-                }
-            },
-            Err(why) => {
-                eprintln!("ion: unable to read namespaces plugin directory: {}", why);
-            }
-        }
-    }
-    hashmap
-}
diff --git a/src/lib/shell/plugins/string.rs b/src/lib/shell/plugins/string.rs
deleted file mode 100644
index a587ec0baea11cc620b43f5f6772a81042304fe5..0000000000000000000000000000000000000000
--- a/src/lib/shell/plugins/string.rs
+++ /dev/null
@@ -1,36 +0,0 @@
-use std::{
-    fmt::{self, Display, Formatter},
-    io,
-};
-use types;
-
-#[derive(Debug)]
-/// A possible error that can be caused when attempting to obtain or execute a
-/// function that is supposed to return a string from across the FFI boundaries.
-pub(crate) enum StringError {
-    /// This occurs when a symbol could not be loaded from the library in question. It is an
-    /// error that infers that the problem is with the plugin, not Ion itself.
-    SymbolErr(io::Error),
-    /// Function names must be valid UTF-8. If they aren't something's wrong
-    /// with the plugin.
-    UTF8Function,
-    /// The result from a plugin must be valid UTF-8. If it isn't, the plugin's
-    /// bad.
-    UTF8Result,
-    /// This infers that the user called a function that doesn't exist in the library. Bad
-    /// user, bad.
-    FunctionMissing(types::Str),
-}
-
-impl Display for StringError {
-    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
-        match *self {
-            StringError::SymbolErr(ref error) => write!(f, "symbol error: {}", error),
-            StringError::UTF8Function => write!(f, "function has invalid UTF-8 name"),
-            StringError::UTF8Result => write!(f, "result is not valid UTF-8"),
-            StringError::FunctionMissing(ref func) => {
-                write!(f, "{} doesn't exist in namespace", func)
-            }
-        }
-    }
-}
diff --git a/src/lib/shell/variables/mod.rs b/src/lib/shell/variables/mod.rs
index 6a71f5095cb858b4e0a67edf7948e0ba33c6565d..818abdc7d5c364003f54d1301eb6f3bbf8bc91a7 100644
--- a/src/lib/shell/variables/mod.rs
+++ b/src/lib/shell/variables/mod.rs
@@ -2,7 +2,6 @@ use super::{
     colors::Colors,
     directory_stack::DirectoryStack,
     flow_control::Function,
-    plugins::namespaces::{self, StringNamespace},
     status::{FAILURE, SUCCESS},
 };
 use fnv::FnvHashMap;
@@ -14,15 +13,11 @@ use std::{
     mem,
     ops::{Deref, DerefMut},
 };
-use sys::{self, env as sys_env, geteuid, getpid, getuid, is_root, variables as self_sys};
+use sys::{self, env as sys_env, geteuid, getpid, getuid, variables as self_sys};
 use types::{self, Array};
 use unicode_segmentation::UnicodeSegmentation;
 use xdg::BaseDirectories;
 
-lazy_static! {
-    static ref STRING_NAMESPACES: FnvHashMap<types::Str, StringNamespace> = namespaces::collect();
-}
-
 #[derive(Clone, Debug, PartialEq)]
 pub enum VariableType {
     Str(types::Str),
@@ -244,7 +239,10 @@ impl Default for Variables {
         );
 
         // Initialize the HOST variable
-        env::set_var("HOST", &self_sys::get_host_name().unwrap_or("?".to_owned()));
+        env::set_var(
+            "HOST",
+            &self_sys::get_host_name().unwrap_or_else(|| "?".to_owned()),
+        );
 
         Variables {
             flags:   0,
@@ -257,8 +255,6 @@ impl Default for Variables {
     }
 }
 
-const PLUGIN: u8 = 1;
-
 impl Variables {
     pub fn new_scope(&mut self, namespace: bool) {
         self.current += 1;
@@ -497,36 +493,9 @@ impl Variables {
                             .map(|s| T::from(VariableType::Str(s.into()))),
                     }
                 }
-                Some((_, variable)) => {
-                    if is_root() {
-                        eprintln!("ion: root is not allowed to execute plugins");
-                        return None;
-                    }
-
-                    if !self.has_plugin_support() {
-                        eprintln!(
-                            "ion: plugins are disabled. Considering enabling them with `let \
-                             NS_PLUGINS = 1`"
-                        );
-                        return None;
-                    }
-
-                    // Attempt to obtain the given namespace from our lazily-generated map of
-                    // namespaces.
-                    if let Some(namespace) = STRING_NAMESPACES.get(name) {
-                        // Attempt to execute the given function from that namespace, and map it's
-                        // results.
-                        match namespace.execute(variable.into()) {
-                            Ok(value) => value.map(|s| T::from(VariableType::Str(s.into()))),
-                            Err(why) => {
-                                eprintln!("ion: string namespace error: {}: {}", name, why);
-                                None
-                            }
-                        }
-                    } else {
-                        eprintln!("ion: unsupported namespace: '{}'", name);
-                        None
-                    }
+                Some((..)) => {
+                    eprintln!("ion: unsupported namespace: '{}'", name);
+                    None
                 }
             }
         } else if specified_type == TypeId::of::<types::Alias>() {
@@ -615,7 +584,7 @@ impl Variables {
         handle_type!(hashmap_action, types::HashMap, HashMap);
         handle_type!(function_action, Function, Function);
 
-        let mut upper_action = {
+        let upper_action = {
             let action = match self.get_mut(&name) {
                 Some(VariableType::Str(ref mut str_)) => string_action(name, &var, str_),
                 Some(VariableType::Alias(ref mut alias)) => alias_action(name, &var, alias),
@@ -780,12 +749,6 @@ impl Variables {
         }
         SUCCESS
     }
-
-    pub(crate) fn disable_plugins(&mut self) { self.flags &= !PLUGIN; }
-
-    pub(crate) fn enable_plugins(&mut self) { self.flags |= PLUGIN; }
-
-    pub(crate) fn has_plugin_support(&self) -> bool { self.flags & PLUGIN == PLUGIN }
 }
 
 #[cfg(test)]
diff --git a/src/lib/types.rs b/src/lib/types.rs
index 05826d50e3e66c28a48bf78af6cb628939fdf972..4cbcac3722445c97634b2d86121492c751ae78e3 100644
--- a/src/lib/types.rs
+++ b/src/lib/types.rs
@@ -59,6 +59,7 @@ macro_rules! array [
     ( $($x:expr), *) => ({
         let mut _arr = Array::new();
         $(_arr.push($x.into());)*
+        #[allow(let_and_return)]
         _arr
     })
 ];