diff --git a/src/blog.rs b/src/blog.rs
index 3124ae18e53a8f7887fd0e2f547a0caaf31d67e0..e2ab4ec4fa1c51cbff30c76521593a3aabc8fd1d 100644
--- a/src/blog.rs
+++ b/src/blog.rs
@@ -5,8 +5,8 @@ use fnv::FnvHashMap;
 use warp::hyper::StatusCode;
 
 use crate::{
-    favicon::Favicon, image::MyImage, load::load_from_path, misc::Misc, path::UrlPath, post::Post,
-    resp::Response, style::Style,
+    config::Logo, favicon::Favicon, image::MyImage, load::load_from_path, misc::Misc,
+    path::UrlPath, post::Post, resp::Response, style::Style,
 };
 
 pub struct Blog {
@@ -19,10 +19,16 @@ pub struct Blog {
     misc: Vec<Misc>,
     custom_style: Option<Style>,
     favicon: Option<Favicon>,
+    logo: Option<Logo>,
 }
 
 impl Blog {
-    pub fn new(name: String, description: String, base_path: &Path) -> Result<Self, Error> {
+    pub fn new(
+        name: String,
+        description: String,
+        base_path: &Path,
+        logo: Option<Logo>,
+    ) -> Result<Self, Error> {
         let pages = load_from_path(base_path, &base_path.join("pages"), "pages")?;
         let posts = load_from_path(base_path, &base_path.join("posts"), "posts")?;
         let imgs = load_from_path(base_path, &base_path.join("assets/img"), "")?;
@@ -39,6 +45,7 @@ impl Blog {
             misc,
             custom_style,
             favicon,
+            logo,
         })
     }
 
@@ -56,7 +63,36 @@ impl Blog {
 
         content.push_str("</table>");
 
-        Ok(dress_page(name, None, &content, &self.pages, &self.favicon))
+        Ok(self.dress_page(None, &content))
+    }
+
+    fn dress_page(&self, title: Option<&str>, content: &str) -> String {
+        let title = match title {
+            Some(title) => format!("{} | {}", title.trim(), self.name.trim()),
+            None => self.name.trim().to_string(),
+        };
+
+        let favicons = match &self.favicon {
+            Some(f) => f.html(),
+            None => "",
+        };
+
+        let logo = match &self.logo {
+            Some(logo) => format!(
+                r#"<img src="{}" width="{}" height="{}" alt="{}" class="align-right" />"#,
+                logo.path, logo.width, logo.height, logo.alt
+            ),
+            None => "".to_string(),
+        };
+
+        let mut page_links = String::new();
+        for p in &self.pages {
+            page_links.push_str(&p.link_short());
+        }
+
+        format!(
+            r#"<!DOCTYPE html><html lang="en"><head><meta name="viewport" content="width=device-width, initial-scale=1"><link rel="stylesheet" href="/style.css" />{favicons}<title>{title}</title></head><body><div><a href="/">Home</a>{page_links}{logo}</div><hr>{content}</body></html>"#
+        )
     }
 }
 
@@ -84,13 +120,13 @@ impl TryFrom<Blog> for RenderedBlog {
         let mut pages = FnvHashMap::default();
 
         for p in &b.posts {
-            let body = dress_page(&b.name, Some(&p.title), &p.html()?, &b.pages, &b.favicon);
+            let body = b.dress_page(Some(&p.title), &p.html()?);
 
             insert_path(&mut pages, &p.url, Response::html(body))?;
         }
 
         for p in &b.pages {
-            let body = dress_page(&b.name, Some(&p.title), &p.html()?, &b.pages, &b.favicon);
+            let body = b.dress_page(Some(&p.title), &p.html()?);
 
             insert_path(&mut pages, &p.url, Response::html(body))?;
         }
@@ -105,23 +141,19 @@ impl TryFrom<Blog> for RenderedBlog {
         let home = b.home()?;
         insert_path(&mut pages, "/", Response::html(home))?;
 
-        for img in b.imgs {
-            let (original_url, original, thumbnail_url, thumbnail) = img.into_responses()?;
+        for img in &b.imgs {
+            let (original_url, original, thumbnail_url, thumbnail) =
+                img.clone().into_responses()?;
             insert_path(&mut pages, &thumbnail_url, thumbnail)?;
             insert_path(&mut pages, &original_url, original)?;
         }
 
-        for m in b.misc {
-            insert_path(&mut pages, &m.url.clone(), m.response())?;
+        for m in &b.misc {
+            insert_path(&mut pages, &m.url.clone(), m.clone().response())?;
         }
 
-        let not_found = Response::html(dress_page(
-            &b.name,
-            Some("Page not found"),
-            include_str!("assets/404.html"),
-            &b.pages,
-            &b.favicon,
-        ));
+        let not_found =
+            Response::html(b.dress_page(Some("Page not found"), include_str!("assets/404.html")));
 
         if let Some(fav) = b.favicon {
             for (p, r) in fav.responses {
@@ -152,30 +184,3 @@ fn insert_path(
 
     Ok(())
 }
-
-fn dress_page(
-    site_name: &str,
-    title: Option<&str>,
-    content: &str,
-    pages: &[Post],
-    favicon: &Option<Favicon>,
-) -> String {
-    let title = match title {
-        Some(title) => format!("{} | {}", title.trim(), site_name.trim()),
-        None => site_name.trim().to_string(),
-    };
-
-    let favicons = match favicon {
-        Some(f) => f.html(),
-        None => "",
-    };
-
-    let mut page_links = String::new();
-    for p in pages {
-        page_links.push_str(&p.link_short());
-    }
-
-    format!(
-        r#"<!DOCTYPE html><html lang="en"><head><meta name="viewport" content="width=device-width, initial-scale=1"><link rel="stylesheet" href="/style.css" />{favicons}<title>{title}</title></head><body><div><a href="/">Home</a>{page_links}<img src="/img/logo.png" class="align-right" /></div><hr>{content}</body></html>"#
-    )
-}
diff --git a/src/config.rs b/src/config.rs
index 36a749bc75901555d9b5d5d6452e737c1848f6e1..03a9fb6e5a04d363e375d6986840353580d55d84 100644
--- a/src/config.rs
+++ b/src/config.rs
@@ -3,11 +3,20 @@ use std::fs;
 use anyhow::anyhow;
 use serde::Deserialize;
 
+#[derive(Deserialize)]
+pub struct Logo {
+    pub path: String,
+    pub width: String,
+    pub height: String,
+    pub alt: String,
+}
+
 #[derive(Deserialize)]
 pub struct Config {
     pub name: String,
     pub description: String,
     pub path: String,
+    pub logo: Option<Logo>,
 }
 
 impl Config {
diff --git a/src/image.rs b/src/image.rs
index 312688f14a14d640c6b3a63b96f092d19437f569..1c3b3a01cd1db9bf6686cc1f9bd9feca9a3e3999 100644
--- a/src/image.rs
+++ b/src/image.rs
@@ -9,6 +9,7 @@ use crate::{
     util::slugify,
 };
 
+#[derive(Clone)]
 pub struct MyImage {
     original: DynamicImage,
     thumbnail: DynamicImage,
diff --git a/src/main.rs b/src/main.rs
index 2d8fb83c1f0064435e461b768f277f6d34427dc7..e99c73a3f8dc56c3d06be489fa27a9c5b3d0b4b0 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -53,11 +53,15 @@ async fn handle_request(
 async fn main() {
     let config = Config::load().unwrap();
 
-    let blog: RenderedBlog =
-        Blog::new(config.name, config.description, &PathBuf::from(config.path))
-            .unwrap()
-            .try_into()
-            .unwrap();
+    let blog: RenderedBlog = Blog::new(
+        config.name,
+        config.description,
+        &PathBuf::from(config.path),
+        config.logo,
+    )
+    .unwrap()
+    .try_into()
+    .unwrap();
     let blog = Arc::new(RwLock::new(blog));
 
     let blog_filter = warp::any().map(move || blog.clone());
diff --git a/src/misc.rs b/src/misc.rs
index 7e327e3ce7b3e616ccd56aff9db20848656373b4..a92ed2b7550febc8d1768c86a28e2d0abe172a52 100644
--- a/src/misc.rs
+++ b/src/misc.rs
@@ -8,6 +8,7 @@ use crate::{
     util::slugify,
 };
 
+#[derive(Clone)]
 pub struct Misc {
     pub url: String,
     content_type: &'static str,