More code.

Change-Id: Ie53ea58b3d0e8e906a2e51752ecfbe1e434b4261
diff --git a/Cargo.toml b/Cargo.toml
index b1362de..826ad19 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -4,6 +4,11 @@
 authors = ["Matthias Andreas Benkard <code@mail.matthias.benkard.de>"]
 edition = "2018"
 
+[profile.release]
+lto = true
+opt-level = "z"
+debug = false
+
 [dependencies]
 failure = "0.1.5"
 failure_derive = "0.1.5"
diff --git a/src/main.rs b/src/bin/tut1.rs
similarity index 72%
rename from src/main.rs
rename to src/bin/tut1.rs
index d95b684..83596ad 100644
--- a/src/main.rs
+++ b/src/bin/tut1.rs
@@ -1,15 +1,8 @@
+// Structs, Borrowing
+
 #![allow(dead_code)]
 
-struct Person {
-    age: i32,
-    name: String,
-}
-
-impl ToString for Person {
-    fn to_string(&self) -> String {
-        format!("{} ({})", self.name, self.age)
-    }
-}
+use rust_tutorial::*;
 
 fn greet_person_1(p: Person) {
     println!("Hello {} ({})!", p.name, p.age);
@@ -25,7 +18,10 @@
 
 fn main() {
     // -- Struct instantiation --
-    let mut p = Person { age: 30, name: "Mary".to_string() };
+    let mut p = Person {
+        age: 30,
+        name: "Mary".to_string(),
+    };
 
     // -- Borrowing --
     //greet_person_1(p);
diff --git a/src/bin/tut2.rs b/src/bin/tut2.rs
new file mode 100644
index 0000000..702b870
--- /dev/null
+++ b/src/bin/tut2.rs
@@ -0,0 +1,42 @@
+#![allow(dead_code)]
+#![allow(unused_imports)]
+
+use rust_tutorial::*;
+
+/// Run this to see the disassembly of `compute_sum_of_squares_{1,2}`:
+///
+/// ```bash
+/// cargo objdump --bin tut2 --release -- -d | awk -v RS= '/^tut2::compute_sum_of_squares/'
+/// ```
+
+#[inline(never)]
+fn compute_sum_of_squares_1(xs: &Vec<i32>) -> i32 {
+    let mut acc = 0;
+    for x in xs {
+        acc += x * x;
+    }
+    acc
+}
+
+#[inline(never)]
+fn compute_sum_of_squares_2(xs: &Vec<i32>) -> i32 {
+    xs.iter()
+        .map(|x| x * x)
+        .fold(0, |acc, x| acc + x)
+}
+
+#[test]
+fn test_compute_sum_of_squares() {
+    let numbers = vec![1, 2, 3, 4, 5];
+    assert_eq!(compute_sum_of_squares_1(&numbers), compute_sum_of_squares_2(&numbers));
+}
+
+fn main() {
+    let numbers = vec![1, 2, 3, 4, 5];
+
+    let sum_of_squares_1 = compute_sum_of_squares_1(&numbers);
+    let sum_of_squares_2 = compute_sum_of_squares_2(&numbers);
+
+    println!("sum #1 = {}", sum_of_squares_1);
+    println!("sum #2 = {}", sum_of_squares_2);
+}
diff --git a/src/bin/tut3.rs b/src/bin/tut3.rs
new file mode 100644
index 0000000..a1005a0
--- /dev/null
+++ b/src/bin/tut3.rs
@@ -0,0 +1,39 @@
+// Generic Programming
+
+#![allow(dead_code)]
+#![allow(unused_imports)]
+
+use rust_tutorial::*;
+
+/// Run this to see the disassembly of `compute_sum_of_squares_{1,2}`:
+///
+/// ```bash
+/// cargo objdump --bin tut2 --release -- -d | awk -v RS= '/^tut2::compute_sum_of_squares/'
+/// ```
+
+#[inline(never)]
+fn compute_sum_of_squares_i32(zero: i32, xs: &Vec<i32>) -> i32 {
+    xs[1..].iter()
+        .map(|x| x * x)
+        .fold(zero, |acc, x| acc + x)
+}
+
+#[inline(never)]
+fn compute_sum_of_squares<T>(zero: T, xs: &Vec<T>) -> T
+where
+    T: std::ops::Mul<Output=T> + std::ops::Add<Output=T> + Copy
+{
+    xs[1..].iter()
+        .map(|x| *x * *x)
+        .fold(zero, |acc, x| acc + x)
+}
+
+fn main() {
+    let numbers = vec![1, 2, 3, 4, 5];
+
+    let sum_of_squares_i32 = compute_sum_of_squares_i32(0, &numbers);
+    let sum_of_squares_t   = compute_sum_of_squares(0, &numbers);
+
+    println!("sum i32 = {}", sum_of_squares_i32);
+    println!("sum T   = {}", sum_of_squares_t);
+}
diff --git a/src/bin/tut4.rs b/src/bin/tut4.rs
new file mode 100644
index 0000000..f743435
--- /dev/null
+++ b/src/bin/tut4.rs
@@ -0,0 +1,9 @@
+// Fearless Concurrency
+
+#![allow(dead_code)]
+#![allow(unused_imports)]
+
+use rust_tutorial::*;
+
+fn main() {
+}
diff --git a/src/lib.rs b/src/lib.rs
new file mode 100644
index 0000000..9885774
--- /dev/null
+++ b/src/lib.rs
@@ -0,0 +1,23 @@
+pub struct Person {
+    pub age: i32,
+    pub name: String,
+}
+
+impl ToString for Person {
+    /// # Examples
+    ///
+    /// ```
+    /// use rust_tutorial::Person;
+    ///
+    /// let p = Person { age: 30, name: "Mary".to_string() };
+    /// assert_eq!(p.to_string(), "Mary (30)");
+    /// ```
+    fn to_string(&self) -> String {
+        format!("{} ({})", self.name, self.age)
+    }
+}
+
+#[test]
+fn test_example() {
+    assert_eq!("a", "a");
+}
diff --git a/tests/lib_tests.rs b/tests/lib_tests.rs
new file mode 100644
index 0000000..31c9bac
--- /dev/null
+++ b/tests/lib_tests.rs
@@ -0,0 +1,33 @@
+#![cfg(test)]
+
+use rust_tutorial::*;
+
+#[test]
+fn integration_test_a() {
+    assert_eq!("a", "a");
+}
+
+#[test]
+fn integration_test_b() {
+    assert_eq!("b", "b");
+}
+
+#[test]
+fn integration_test_c() {
+    let c = true;
+    assert!(c);
+}
+
+#[test]
+fn integration_test_d() {
+    assert_ne!(0, 1);
+}
+
+#[test]
+fn integration_test_e() {
+    let p = Person {
+        age: 30,
+        name: "Mary".to_string(),
+    };
+    assert_eq!(p.age, 30);
+}