diff --git a/Cargo.lock b/Cargo.lock
index 624c1c7..471e0ca 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -1,1186 +1,1215 @@
 # This file is automatically @generated by Cargo.
 # It is not intended for manual editing.
 version = 3
 
 [[package]]
 name = "aho-corasick"
 version = "1.1.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "b2969dcb958b36655471fc61f7e416fa76033bdd4bfed0678d8fee1e2d07a1f0"
 dependencies = [
  "memchr",
 ]
 
 [[package]]
 name = "android-tzdata"
 version = "0.1.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e999941b234f3131b00bc13c22d06e8c5ff726d1b6318ac7eb276997bbb4fef0"
 
 [[package]]
 name = "android_system_properties"
 version = "0.1.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "819e7219dbd41043ac279b19830f2efc897156490d7fd6ea916720117ee66311"
 dependencies = [
  "libc",
 ]
 
 [[package]]
 name = "ansi-str"
 version = "0.8.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "1cf4578926a981ab0ca955dc023541d19de37112bc24c1a197bd806d3d86ad1d"
 dependencies = [
  "ansitok",
 ]
 
 [[package]]
 name = "ansitok"
 version = "0.2.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "220044e6a1bb31ddee4e3db724d29767f352de47445a6cd75e1a173142136c83"
 dependencies = [
  "nom",
  "vte",
 ]
 
 [[package]]
 name = "anstream"
 version = "0.6.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "2ab91ebe16eb252986481c5b62f6098f3b698a45e34b5b98200cf20dd2484a44"
 dependencies = [
  "anstyle",
  "anstyle-parse",
  "anstyle-query",
  "anstyle-wincon",
  "colorchoice",
  "utf8parse",
 ]
 
 [[package]]
 name = "anstyle"
 version = "1.0.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7079075b41f533b8c61d2a4d073c4676e1f8b249ff94a393b0595db304e0dd87"
 
 [[package]]
 name = "anstyle-parse"
 version = "0.2.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "317b9a89c1868f5ea6ff1d9539a69f45dffc21ce321ac1fd1160dfa48c8e2140"
 dependencies = [
  "utf8parse",
 ]
 
 [[package]]
 name = "anstyle-query"
 version = "1.0.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b"
 dependencies = [
  "windows-sys",
 ]
 
 [[package]]
 name = "anstyle-wincon"
 version = "3.0.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f0699d10d2f4d628a98ee7b57b289abbc98ff3bad977cb3152709d4bf2330628"
 dependencies = [
  "anstyle",
  "windows-sys",
 ]
 
 [[package]]
 name = "anyhow"
 version = "1.0.75"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a4668cab20f66d8d020e1fbc0ebe47217433c1b6c8f2040faf858554e394ace6"
 
 [[package]]
 name = "arrayvec"
 version = "0.5.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "23b62fc65de8e4e7f52534fb52b0f3ed04746ae267519eef2a83941e8085068b"
 
 [[package]]
 name = "autocfg"
 version = "1.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa"
 
 [[package]]
 name = "bitflags"
 version = "1.3.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
 
 [[package]]
 name = "bitflags"
 version = "2.4.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "327762f6e5a765692301e5bb513e0d9fef63be86bbc14528052b1cd3e6f03e07"
 
 [[package]]
 name = "bumpalo"
 version = "3.14.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7f30e7476521f6f8af1a1c4c0b8cc94f0bee37d91763d0ca2665f299b6cd8aec"
 
 [[package]]
 name = "bytecount"
 version = "0.6.7"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e1e5f035d16fc623ae5f74981db80a439803888314e3a555fd6f04acd51a3205"
 
 [[package]]
 name = "cc"
 version = "1.0.84"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "0f8e7c90afad890484a21653d08b6e209ae34770fb5ee298f9c699fcc1e5c856"
 dependencies = [
  "libc",
 ]
 
 [[package]]
 name = "cfg-if"
 version = "1.0.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
 
 [[package]]
 name = "chrono"
 version = "0.4.31"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7f2c685bad3eb3d45a01354cedb7d5faa66194d1d58ba6e267a8de788f79db38"
 dependencies = [
  "android-tzdata",
  "iana-time-zone",
  "js-sys",
  "num-traits",
  "serde",
  "wasm-bindgen",
  "windows-targets",
 ]
 
 [[package]]
 name = "clap"
 version = "4.4.8"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "2275f18819641850fa26c89acc84d465c1bf91ce57bc2748b28c420473352f64"
 dependencies = [
  "clap_builder",
  "clap_derive",
 ]
 
 [[package]]
 name = "clap-verbosity-flag"
 version = "2.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e5fdbb015d790cfb378aca82caf9cc52a38be96a7eecdb92f31b4366a8afc019"
 dependencies = [
  "clap",
  "log",
 ]
 
 [[package]]
 name = "clap_builder"
 version = "4.4.8"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "07cdf1b148b25c1e1f7a42225e30a0d99a615cd4637eae7365548dd4529b95bc"
 dependencies = [
  "anstream",
  "anstyle",
  "clap_lex",
  "strsim",
 ]
 
 [[package]]
 name = "clap_derive"
 version = "4.4.7"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "cf9804afaaf59a91e75b022a30fb7229a7901f60c755489cc61c9b423b836442"
 dependencies = [
  "heck",
  "proc-macro2",
  "quote",
  "syn 2.0.39",
 ]
 
 [[package]]
 name = "clap_lex"
 version = "0.6.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "702fc72eb24e5a1e48ce58027a675bc24edd52096d5397d4aea7c6dd9eca0bd1"
 
 [[package]]
 name = "codespan-reporting"
 version = "0.11.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3538270d33cc669650c4b093848450d380def10c331d38c768e34cac80576e6e"
 dependencies = [
  "termcolor",
  "unicode-width",
 ]
 
 [[package]]
 name = "colorchoice"
 version = "1.0.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7"
 
 [[package]]
 name = "colored"
 version = "2.0.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "2674ec482fbc38012cf31e6c42ba0177b431a0cb6f15fe40efa5aab1bda516f6"
 dependencies = [
  "is-terminal",
  "lazy_static",
  "windows-sys",
 ]
 
 [[package]]
 name = "core-foundation-sys"
 version = "0.8.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e496a50fda8aacccc86d7529e2c1e0892dbd0f898a6b5645b5561b89c3210efa"
 
 [[package]]
 name = "cxx"
 version = "1.0.110"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7129e341034ecb940c9072817cd9007974ea696844fc4dd582dc1653a7fbe2e8"
 dependencies = [
  "cc",
  "cxxbridge-flags",
  "cxxbridge-macro",
  "link-cplusplus",
 ]
 
 [[package]]
 name = "cxx-build"
 version = "1.0.110"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a2a24f3f5f8eed71936f21e570436f024f5c2e25628f7496aa7ccd03b90109d5"
 dependencies = [
  "cc",
  "codespan-reporting",
  "once_cell",
  "proc-macro2",
  "quote",
  "scratch",
  "syn 2.0.39",
 ]
 
 [[package]]
 name = "cxxbridge-flags"
 version = "1.0.110"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "06fdd177fc61050d63f67f5bd6351fac6ab5526694ea8e359cd9cd3b75857f44"
 
 [[package]]
 name = "cxxbridge-macro"
 version = "1.0.110"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "587663dd5fb3d10932c8aecfe7c844db1bcf0aee93eeab08fac13dc1212c2e7f"
 dependencies = [
  "proc-macro2",
  "quote",
  "syn 2.0.39",
 ]
 
 [[package]]
 name = "darwin-libproc"
 version = "0.1.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "9fb90051930c9a0f09e585762152048e23ac74d20c10590ef7cf01c0343c3046"
 dependencies = [
  "darwin-libproc-sys",
  "libc",
  "memchr",
 ]
 
 [[package]]
 name = "darwin-libproc-sys"
 version = "0.1.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "57cebb5bde66eecdd30ddc4b9cd208238b15db4982ccc72db59d699ea10867c1"
 dependencies = [
  "libc",
 ]
 
 [[package]]
 name = "derive_more"
 version = "0.99.17"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "4fb810d30a7c1953f91334de7244731fc3f3c10d7fe163338a35b9f640960321"
 dependencies = [
  "proc-macro2",
  "quote",
  "syn 1.0.109",
 ]
 
 [[package]]
 name = "env_logger"
 version = "0.10.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "95b3f3e67048839cb0d0781f445682a35113da7121f7c949db0e2be96a4fbece"
 dependencies = [
  "humantime",
  "is-terminal",
  "log",
  "regex",
  "termcolor",
 ]
 
 [[package]]
 name = "equivalent"
 version = "1.0.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
 
 [[package]]
 name = "errno"
 version = "0.3.6"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7c18ee0ed65a5f1f81cac6b1d213b69c35fa47d4252ad41f1486dbd8226fe36e"
 dependencies = [
  "libc",
  "windows-sys",
 ]
 
 [[package]]
 name = "fnv"
 version = "1.0.7"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1"
 
 [[package]]
 name = "glob"
 version = "0.3.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d2fabcfbdc87f4758337ca535fb41a6d701b65693ce38287d856d1674551ec9b"
 
 [[package]]
 name = "global_placeholders"
 version = "0.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d70af3f3fd800923fa445d6fa562e054d8abaf06df926f77dd6dbead1fefb275"
 dependencies = [
  "parking_lot",
 ]
 
 [[package]]
 name = "hashbrown"
 version = "0.14.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f93e7192158dbcda357bdec5fb5788eebf8bbac027f3f33e719d29135ae84156"
 
 [[package]]
 name = "heck"
 version = "0.4.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8"
 
 [[package]]
 name = "hermit-abi"
 version = "0.3.3"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d77f7ec81a6d05a3abb01ab6eb7590f6083d08449fe5a1c8b1e620283546ccb7"
 
 [[package]]
 name = "home"
 version = "0.5.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5444c27eef6923071f7ebcc33e3444508466a76f7a2b93da00ed6e19f30c1ddb"
 dependencies = [
  "windows-sys",
 ]
 
 [[package]]
 name = "humantime"
 version = "2.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "9a3a5bfb195931eeb336b2a7b4d761daec841b97f947d34394601737a7bba5e4"
 
 [[package]]
 name = "iana-time-zone"
 version = "0.1.58"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "8326b86b6cff230b97d0d312a6c40a60726df3332e721f72a1b035f451663b20"
 dependencies = [
  "android_system_properties",
  "core-foundation-sys",
  "iana-time-zone-haiku",
  "js-sys",
  "wasm-bindgen",
  "windows-core",
 ]
 
 [[package]]
 name = "iana-time-zone-haiku"
 version = "0.1.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f31827a206f56af32e590ba56d5d2d085f558508192593743f16b2306495269f"
 dependencies = [
  "cc",
 ]
 
 [[package]]
 name = "indexmap"
 version = "2.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d530e1a18b1cb4c484e6e34556a0d948706958449fca0cab753d649f2bce3d1f"
 dependencies = [
  "equivalent",
  "hashbrown",
 ]
 
 [[package]]
 name = "is-terminal"
 version = "0.4.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "cb0889898416213fab133e1d33a0e5858a48177452750691bde3666d0fdbaf8b"
 dependencies = [
  "hermit-abi",
  "rustix",
  "windows-sys",
 ]
 
 [[package]]
 name = "itoa"
 version = "1.0.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "af150ab688ff2122fcef229be89cb50dd66af9e01a4ff320cc137eecc9bacc38"
 
 [[package]]
 name = "js-sys"
 version = "0.3.65"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "54c0c35952f67de54bb584e9fd912b3023117cbafc0a77d8f3dee1fb5f572fe8"
 dependencies = [
  "wasm-bindgen",
 ]
 
 [[package]]
 name = "lazy_static"
 version = "1.4.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
 
 [[package]]
 name = "libc"
 version = "0.2.150"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "89d92a4743f9a61002fae18374ed11e7973f530cb3a3255fb354818118b2203c"
 
 [[package]]
 name = "link-cplusplus"
 version = "1.0.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "9d240c6f7e1ba3a28b0249f774e6a9dd0175054b52dfbb61b16eb8505c3785c9"
 dependencies = [
  "cc",
 ]
 
 [[package]]
 name = "linux-raw-sys"
 version = "0.4.11"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "969488b55f8ac402214f3f5fd243ebb7206cf82de60d3172994707a4bcc2b829"
 
 [[package]]
 name = "lock_api"
 version = "0.4.11"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3c168f8615b12bc01f9c17e2eb0cc07dcae1940121185446edc3744920e8ef45"
 dependencies = [
  "autocfg",
  "scopeguard",
 ]
 
 [[package]]
 name = "log"
 version = "0.4.20"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "b5e6163cb8c49088c2c36f57875e58ccd8c87c7427f7fbd50ea6710b2f3f2e8f"
 
 [[package]]
 name = "mach"
 version = "0.3.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "b823e83b2affd8f40a9ee8c29dbc56404c1e34cd2710921f2801e2cf29527afa"
 dependencies = [
  "libc",
 ]
 
 [[package]]
 name = "macros-rs"
 version = "0.4.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "0fb0c4278fff6f86cf9a14ed6c8e1a393d798587303418a5706dbec35f667946"
 
 [[package]]
 name = "memchr"
 version = "2.6.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f665ee40bc4a3c5590afb1e9677db74a508659dfd71e126420da8274909a0167"
 
 [[package]]
 name = "memoffset"
 version = "0.6.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce"
 dependencies = [
  "autocfg",
 ]
 
 [[package]]
 name = "minimal-lexical"
 version = "0.2.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a"
 
 [[package]]
 name = "nix"
 version = "0.23.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "8f3790c00a0150112de0f4cd161e3d7fc4b2d8a5542ffc35f099a2562aecb35c"
 dependencies = [
  "bitflags 1.3.2",
  "cc",
  "cfg-if",
  "libc",
  "memoffset",
 ]
 
 [[package]]
 name = "nom"
 version = "7.1.3"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d273983c5a657a70a3e8f2a01329822f3b8c8172b73826411a55751e404a0a4a"
 dependencies = [
  "memchr",
  "minimal-lexical",
 ]
 
 [[package]]
 name = "num-traits"
 version = "0.2.17"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "39e3200413f237f41ab11ad6d161bc7239c84dcb631773ccd7de3dfe4b5c267c"
 dependencies = [
  "autocfg",
 ]
 
 [[package]]
 name = "num_cpus"
 version = "1.16.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43"
 dependencies = [
  "hermit-abi",
  "libc",
 ]
 
 [[package]]
 name = "once_cell"
 version = "1.18.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "dd8b5dd2ae5ed71462c540258bedcb51965123ad7e7ccf4b9a8cafaa4a63576d"
 
 [[package]]
 name = "papergrid"
 version = "0.10.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a2ccbe15f2b6db62f9a9871642746427e297b0ceb85f9a7f1ee5ff47d184d0c8"
 dependencies = [
  "ansi-str",
  "ansitok",
  "bytecount",
  "fnv",
  "unicode-width",
 ]
 
 [[package]]
 name = "parking_lot"
 version = "0.12.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3742b2c103b9f06bc9fff0a37ff4912935851bee6d36f3c02bcc755bcfec228f"
 dependencies = [
  "lock_api",
  "parking_lot_core",
 ]
 
 [[package]]
 name = "parking_lot_core"
 version = "0.9.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "4c42a9226546d68acdd9c0a280d17ce19bfe27a46bf68784e4066115788d008e"
 dependencies = [
  "cfg-if",
  "libc",
- "redox_syscall",
+ "redox_syscall 0.4.1",
  "smallvec",
  "windows-targets",
 ]
 
 [[package]]
 name = "platforms"
 version = "2.0.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e8d0eef3571242013a0d5dc84861c3ae4a652e56e12adf8bdc26ff5f8cb34c94"
 
 [[package]]
 name = "pmc"
-version = "1.1.2"
+version = "1.2.0"
 dependencies = [
  "anyhow",
  "chrono",
  "clap",
  "clap-verbosity-flag",
  "colored",
  "cxx",
  "cxx-build",
  "env_logger",
  "global_placeholders",
  "home",
  "libc",
  "log",
  "macros-rs",
  "once_cell",
  "pretty_env_logger",
  "psutil",
  "regex",
  "serde",
  "serde_json",
+ "simple-logging",
  "tabled",
  "termcolor",
  "toml",
 ]
 
 [[package]]
 name = "pretty_env_logger"
 version = "0.5.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "865724d4dbe39d9f3dd3b52b88d859d66bcb2d6a0acfd5ea68a65fb66d4bdc1c"
 dependencies = [
  "env_logger",
  "log",
 ]
 
 [[package]]
 name = "proc-macro-error"
 version = "1.0.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c"
 dependencies = [
  "proc-macro-error-attr",
  "proc-macro2",
  "quote",
  "syn 1.0.109",
  "version_check",
 ]
 
 [[package]]
 name = "proc-macro-error-attr"
 version = "1.0.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869"
 dependencies = [
  "proc-macro2",
  "quote",
  "version_check",
 ]
 
 [[package]]
 name = "proc-macro2"
 version = "1.0.69"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "134c189feb4956b20f6f547d2cf727d4c0fe06722b20a0eec87ed445a97f92da"
 dependencies = [
  "unicode-ident",
 ]
 
 [[package]]
 name = "psutil"
 version = "3.2.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f866af2b0f8e4b0d2d00aad8a9c5fc48fad33466cd99a64cbb3a4c1505f1a62d"
 dependencies = [
  "cfg-if",
  "darwin-libproc",
  "derive_more",
  "glob",
  "mach",
  "nix",
  "num_cpus",
  "once_cell",
  "platforms",
  "thiserror",
  "unescape",
 ]
 
 [[package]]
 name = "quote"
 version = "1.0.33"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5267fca4496028628a95160fc423a33e8b2e6af8a5302579e322e4b520293cae"
 dependencies = [
  "proc-macro2",
 ]
 
+[[package]]
+name = "redox_syscall"
+version = "0.1.57"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "41cc0f7e4d5d4544e8861606a285bb08d3e70712ccc7d2b84d7c0ccfaf4b05ce"
+
 [[package]]
 name = "redox_syscall"
 version = "0.4.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "4722d768eff46b75989dd134e5c353f0d6296e5aaa3132e776cbdb56be7731aa"
 dependencies = [
  "bitflags 1.3.2",
 ]
 
 [[package]]
 name = "regex"
 version = "1.10.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "380b951a9c5e80ddfd6136919eef32310721aa4aacd4889a8d39124b026ab343"
 dependencies = [
  "aho-corasick",
  "memchr",
  "regex-automata",
  "regex-syntax",
 ]
 
 [[package]]
 name = "regex-automata"
 version = "0.4.3"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5f804c7828047e88b2d32e2d7fe5a105da8ee3264f01902f796c8e067dc2483f"
 dependencies = [
  "aho-corasick",
  "memchr",
  "regex-syntax",
 ]
 
 [[package]]
 name = "regex-syntax"
 version = "0.8.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "c08c74e62047bb2de4ff487b251e4a92e24f48745648451635cec7d591162d9f"
 
 [[package]]
 name = "rustix"
 version = "0.38.22"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "80109a168d9bc0c7f483083244543a6eb0dba02295d33ca268145e6190d6df0c"
 dependencies = [
  "bitflags 2.4.1",
  "errno",
  "libc",
  "linux-raw-sys",
  "windows-sys",
 ]
 
 [[package]]
 name = "ryu"
 version = "1.0.15"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "1ad4cc8da4ef723ed60bced201181d83791ad433213d8c24efffda1eec85d741"
 
 [[package]]
 name = "scopeguard"
 version = "1.2.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "94143f37725109f92c262ed2cf5e59bce7498c01bcc1502d7b9afe439a4e9f49"
 
 [[package]]
 name = "scratch"
 version = "1.0.7"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a3cf7c11c38cb994f3d40e8a8cde3bbd1f72a435e4c49e85d6553d8312306152"
 
 [[package]]
 name = "serde"
 version = "1.0.192"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "bca2a08484b285dcb282d0f67b26cadc0df8b19f8c12502c13d966bf9482f001"
 dependencies = [
  "serde_derive",
 ]
 
 [[package]]
 name = "serde_derive"
 version = "1.0.192"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d6c7207fbec9faa48073f3e3074cbe553af6ea512d7c21ba46e434e70ea9fbc1"
 dependencies = [
  "proc-macro2",
  "quote",
  "syn 2.0.39",
 ]
 
 [[package]]
 name = "serde_json"
 version = "1.0.108"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3d1c7e3eac408d115102c4c24ad393e0821bb3a5df4d506a80f85f7a742a526b"
 dependencies = [
  "itoa",
  "ryu",
  "serde",
 ]
 
 [[package]]
 name = "serde_spanned"
 version = "0.6.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "12022b835073e5b11e90a14f86838ceb1c8fb0325b72416845c487ac0fa95e80"
 dependencies = [
  "serde",
 ]
 
+[[package]]
+name = "simple-logging"
+version = "2.0.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b00d48e85675326bb182a2286ea7c1a0b264333ae10f27a937a72be08628b542"
+dependencies = [
+ "lazy_static",
+ "log",
+ "thread-id",
+]
+
 [[package]]
 name = "smallvec"
 version = "1.11.2"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "4dccd0940a2dcdf68d092b8cbab7dc0ad8fa938bf95787e1b916b0e3d0e8e970"
 
 [[package]]
 name = "strsim"
 version = "0.10.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623"
 
 [[package]]
 name = "syn"
 version = "1.0.109"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237"
 dependencies = [
  "proc-macro2",
  "quote",
  "unicode-ident",
 ]
 
 [[package]]
 name = "syn"
 version = "2.0.39"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "23e78b90f2fcf45d3e842032ce32e3f2d1545ba6636271dcbf24fa306d87be7a"
 dependencies = [
  "proc-macro2",
  "quote",
  "unicode-ident",
 ]
 
 [[package]]
 name = "tabled"
 version = "0.14.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "dfe9c3632da101aba5131ed63f9eed38665f8b3c68703a6bb18124835c1a5d22"
 dependencies = [
  "ansi-str",
  "ansitok",
  "papergrid",
  "tabled_derive",
  "unicode-width",
 ]
 
 [[package]]
 name = "tabled_derive"
 version = "0.6.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "99f688a08b54f4f02f0a3c382aefdb7884d3d69609f785bd253dc033243e3fe4"
 dependencies = [
  "heck",
  "proc-macro-error",
  "proc-macro2",
  "quote",
  "syn 1.0.109",
 ]
 
 [[package]]
 name = "termcolor"
 version = "1.4.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "ff1bc3d3f05aff0403e8ac0d92ced918ec05b666a43f83297ccef5bea8a3d449"
 dependencies = [
  "winapi-util",
 ]
 
 [[package]]
 name = "thiserror"
 version = "1.0.50"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f9a7210f5c9a7156bb50aa36aed4c95afb51df0df00713949448cf9e97d382d2"
 dependencies = [
  "thiserror-impl",
 ]
 
 [[package]]
 name = "thiserror-impl"
 version = "1.0.50"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "266b2e40bc00e5a6c09c3584011e08b06f123c00362c92b975ba9843aaaa14b8"
 dependencies = [
  "proc-macro2",
  "quote",
  "syn 2.0.39",
 ]
 
+[[package]]
+name = "thread-id"
+version = "3.3.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "c7fbf4c9d56b320106cd64fd024dadfa0be7cb4706725fc44a7d7ce952d820c1"
+dependencies = [
+ "libc",
+ "redox_syscall 0.1.57",
+ "winapi",
+]
+
 [[package]]
 name = "toml"
 version = "0.8.8"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a1a195ec8c9da26928f773888e0742ca3ca1040c6cd859c919c9f59c1954ab35"
 dependencies = [
  "serde",
  "serde_spanned",
  "toml_datetime",
  "toml_edit",
 ]
 
 [[package]]
 name = "toml_datetime"
 version = "0.6.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3550f4e9685620ac18a50ed434eb3aec30db8ba93b0287467bca5826ea25baf1"
 dependencies = [
  "serde",
 ]
 
 [[package]]
 name = "toml_edit"
 version = "0.21.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d34d383cd00a163b4a5b85053df514d45bc330f6de7737edfe0a93311d1eaa03"
 dependencies = [
  "indexmap",
  "serde",
  "serde_spanned",
  "toml_datetime",
  "winnow",
 ]
 
 [[package]]
 name = "unescape"
 version = "0.1.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "ccb97dac3243214f8d8507998906ca3e2e0b900bf9bf4870477f125b82e68f6e"
 
 [[package]]
 name = "unicode-ident"
 version = "1.0.12"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "3354b9ac3fae1ff6755cb6db53683adb661634f67557942dea4facebec0fee4b"
 
 [[package]]
 name = "unicode-width"
 version = "0.1.11"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e51733f11c9c4f72aa0c160008246859e340b00807569a0da0e7a1079b27ba85"
 
 [[package]]
 name = "utf8parse"
 version = "0.2.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a"
 
 [[package]]
 name = "version_check"
 version = "0.9.4"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f"
 
 [[package]]
 name = "vte"
 version = "0.10.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "6cbce692ab4ca2f1f3047fcf732430249c0e971bfdd2b234cf2c47ad93af5983"
 dependencies = [
  "arrayvec",
  "utf8parse",
  "vte_generate_state_changes",
 ]
 
 [[package]]
 name = "vte_generate_state_changes"
 version = "0.1.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "d257817081c7dffcdbab24b9e62d2def62e2ff7d00b1c20062551e6cccc145ff"
 dependencies = [
  "proc-macro2",
  "quote",
 ]
 
 [[package]]
 name = "wasm-bindgen"
 version = "0.2.88"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "7daec296f25a1bae309c0cd5c29c4b260e510e6d813c286b19eaadf409d40fce"
 dependencies = [
  "cfg-if",
  "wasm-bindgen-macro",
 ]
 
 [[package]]
 name = "wasm-bindgen-backend"
 version = "0.2.88"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "e397f4664c0e4e428e8313a469aaa58310d302159845980fd23b0f22a847f217"
 dependencies = [
  "bumpalo",
  "log",
  "once_cell",
  "proc-macro2",
  "quote",
  "syn 2.0.39",
  "wasm-bindgen-shared",
 ]
 
 [[package]]
 name = "wasm-bindgen-macro"
 version = "0.2.88"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5961017b3b08ad5f3fe39f1e79877f8ee7c23c5e5fd5eb80de95abc41f1f16b2"
 dependencies = [
  "quote",
  "wasm-bindgen-macro-support",
 ]
 
 [[package]]
 name = "wasm-bindgen-macro-support"
 version = "0.2.88"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "c5353b8dab669f5e10f5bd76df26a9360c748f054f862ff5f3f8aae0c7fb3907"
 dependencies = [
  "proc-macro2",
  "quote",
  "syn 2.0.39",
  "wasm-bindgen-backend",
  "wasm-bindgen-shared",
 ]
 
 [[package]]
 name = "wasm-bindgen-shared"
 version = "0.2.88"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "0d046c5d029ba91a1ed14da14dca44b68bf2f124cfbaf741c54151fdb3e0750b"
 
 [[package]]
 name = "winapi"
 version = "0.3.9"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "5c839a674fcd7a98952e593242ea400abe93992746761e38641405d28b00f419"
 dependencies = [
  "winapi-i686-pc-windows-gnu",
  "winapi-x86_64-pc-windows-gnu",
 ]
 
 [[package]]
 name = "winapi-i686-pc-windows-gnu"
 version = "0.4.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6"
 
 [[package]]
 name = "winapi-util"
 version = "0.1.6"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f29e6f9198ba0d26b4c9f07dbe6f9ed633e1f3d5b8b414090084349e46a52596"
 dependencies = [
  "winapi",
 ]
 
 [[package]]
 name = "winapi-x86_64-pc-windows-gnu"
 version = "0.4.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
 
 [[package]]
 name = "windows-core"
 version = "0.51.1"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "f1f8cf84f35d2db49a46868f947758c7a1138116f7fac3bc844f43ade1292e64"
 dependencies = [
  "windows-targets",
 ]
 
 [[package]]
 name = "windows-sys"
 version = "0.48.0"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9"
 dependencies = [
  "windows-targets",
 ]
 
 [[package]]
 name = "windows-targets"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "9a2fa6e2155d7247be68c096456083145c183cbbbc2764150dda45a87197940c"
 dependencies = [
  "windows_aarch64_gnullvm",
  "windows_aarch64_msvc",
  "windows_i686_gnu",
  "windows_i686_msvc",
  "windows_x86_64_gnu",
  "windows_x86_64_gnullvm",
  "windows_x86_64_msvc",
 ]
 
 [[package]]
 name = "windows_aarch64_gnullvm"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "2b38e32f0abccf9987a4e3079dfb67dcd799fb61361e53e2882c3cbaf0d905d8"
 
 [[package]]
 name = "windows_aarch64_msvc"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "dc35310971f3b2dbbf3f0690a219f40e2d9afcf64f9ab7cc1be722937c26b4bc"
 
 [[package]]
 name = "windows_i686_gnu"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "a75915e7def60c94dcef72200b9a8e58e5091744960da64ec734a6c6e9b3743e"
 
 [[package]]
 name = "windows_i686_msvc"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "8f55c233f70c4b27f66c523580f78f1004e8b5a8b659e05a4eb49d4166cca406"
 
 [[package]]
 name = "windows_x86_64_gnu"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "53d40abd2583d23e4718fddf1ebec84dbff8381c07cae67ff7768bbf19c6718e"
 
 [[package]]
 name = "windows_x86_64_gnullvm"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "0b7b52767868a23d5bab768e390dc5f5c55825b6d30b86c844ff2dc7414044cc"
 
 [[package]]
 name = "windows_x86_64_msvc"
 version = "0.48.5"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538"
 
 [[package]]
 name = "winnow"
 version = "0.5.19"
 source = "registry+https://github.com/rust-lang/crates.io-index"
 checksum = "829846f3e3db426d4cee4510841b71a8e58aa2a76b1132579487ae430ccd9c7b"
 dependencies = [
  "memchr",
 ]
diff --git a/Cargo.toml b/Cargo.toml
index ccdd87b..c109694 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -1,34 +1,35 @@
 [package]
 name = "pmc"
-version = "1.1.2"
+version = "1.2.0"
 edition = "2021"
 license = "MIT"
 repository = "https://lab.themackabu.dev/crates/pmc"
 description = "Process management controller"
 
 [dependencies]
 clap = "4.4.8"
 log = "0.4.20"
 toml = "0.8.8"
 home = "0.5.5"
 cxx = "1.0.110"
 psutil = "3.2.2"
 regex = "1.10.2"
 libc = "0.2.150"
 anyhow = "1.0.75"
 colored = "2.0.4"
 macros-rs = "0.4.2"
 termcolor = "1.4.0"
 once_cell = "1.18.0"
 env_logger = "0.10.1"
 serde_json = "1.0.108"
+simple-logging = "2.0.2"
 pretty_env_logger = "0.5.0"
 clap-verbosity-flag = "2.1.0"
 global_placeholders = "0.1.0"
 tabled = { version = "0.14.0", features = ["color"] }
 chrono = { version = "0.4.23", features = ["serde"] }
 serde = { version = "1.0.192", features = ["derive"] }
 
 [build-dependencies]
 chrono = "0.4.23"
 cxx-build = "1.0.110"
diff --git a/Maidfile.toml b/Maidfile.toml
index 6a2563f..3bb4cff 100644
--- a/Maidfile.toml
+++ b/Maidfile.toml
@@ -1,24 +1,24 @@
 [project]
 name = "pmc"
-version = "1.1.2"
+version = "1.2.0"
 
 [tasks]
 clean = { script = ["rm -rf bin", "mkdir bin"] }
 
 [tasks.build]
 depends = ["clean"]
 script = [
    "cargo zigbuild --release", 
    "cp target/release/pmc bin/pmc"
 ]
 
 [tasks.build.cache]
 path = "src"
 target = ["bin/pmc"]
 
 [tasks.install]
 script = [
    "maid build -q", 
    "sudo cp bin/pmc /usr/local/bin",
     "echo Copied binary!"
 ]
diff --git a/src/daemon/log.rs b/src/daemon/log.rs
new file mode 100644
index 0000000..7e7ad6c
--- /dev/null
+++ b/src/daemon/log.rs
@@ -0,0 +1,17 @@
+use chrono::Local;
+use global_placeholders::global;
+use std::fs::{File, OpenOptions};
+use std::io::{self, Write};
+
+pub struct Logger {
+    file: File,
+}
+
+impl Logger {
+    pub fn new() -> io::Result<Self> {
+        let file = OpenOptions::new().create(true).append(true).open(global!("pmc.daemon.log"))?;
+        Ok(Logger { file })
+    }
+
+    pub fn write(&mut self, message: &str) { writeln!(&mut self.file, "[{}] {}", Local::now().format("%Y-%m-%d %H:%M:%S%.3f"), message).unwrap() }
+}
diff --git a/src/daemon/mod.rs b/src/daemon/mod.rs
index 2f49271..ae2ba99 100644
--- a/src/daemon/mod.rs
+++ b/src/daemon/mod.rs
@@ -1,217 +1,241 @@
-pub mod fork;
+mod fork;
+mod log;
 pub mod pid;
 
 use crate::config;
-use crate::helpers::{self, ColoredString};
+use crate::file;
+use crate::helpers::{self, ColoredString, Id};
 use crate::process::Runner;
 use crate::service;
 
 use chrono::{DateTime, Utc};
 use colored::Colorize;
 use fork::{daemon, Fork};
 use global_placeholders::global;
-use macros_rs::{crashln, string, ternary, then};
+use log::Logger;
+use macros_rs::{crashln, str, string, ternary, then};
 use psutil::process::{MemoryInfo, Process};
 use serde::Serialize;
 use serde_json::json;
 use std::{process, thread::sleep, time::Duration};
 
 use tabled::{
     settings::{
         object::Columns,
         style::{BorderColor, Style},
         themes::Colorization,
         Color, Rotate,
     },
     Table, Tabled,
 };
 
 extern "C" fn handle_termination_signal(_: libc::c_int) {
     pid::remove();
+    let mut log = Logger::new().unwrap();
+    log.write(format!("daemon killed (pid={})", process::id()).as_str());
     unsafe { libc::_exit(0) }
 }
 
 fn restart_process(runner: Runner) {
+    let mut log = Logger::new().unwrap();
     let items = runner.list().iter().filter_map(|(id, item)| Some((id.trim().parse::<usize>().ok()?, item)));
     for (id, item) in items {
         then!(!item.running || pid::running(item.pid as i32), continue);
         let name = &Some(item.name.clone());
         let mut runner_instance = Runner::new();
         runner_instance.restart(id, name);
+        log.write(format!("restarted {} ({id})", item.name).as_str());
     }
 }
 
 pub fn health(format: &String) {
-    let runner = Runner::new();
     let mut pid: Option<i32> = None;
     let mut cpu_percent: Option<f32> = None;
     let mut uptime: Option<DateTime<Utc>> = None;
     let mut memory_usage: Option<MemoryInfo> = None;
+    let runner: Runner = file::read(global!("pmc.dump"));
 
     #[derive(Clone, Debug, Tabled)]
     struct Info {
         #[tabled(rename = "pid file")]
         pid_file: String,
         #[tabled(rename = "fork path")]
         path: String,
         #[tabled(rename = "cpu percent")]
         cpu_percent: String,
         #[tabled(rename = "memory usage")]
         memory_usage: String,
         #[tabled(rename = "daemon type")]
         external: String,
         #[tabled(rename = "process count")]
         process_count: usize,
         uptime: String,
         pid: String,
         status: ColoredString,
     }
 
     impl Serialize for Info {
         fn serialize<S: serde::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
             let trimmed_json = json!({
              "pid_file": &self.pid_file.trim(),
              "path": &self.path.trim(),
              "cpu": &self.cpu_percent.trim(),
              "mem": &self.memory_usage.trim(),
              "process_count": &self.process_count.to_string(),
              "uptime": &self.uptime.trim(),
              "pid": &self.pid.trim(),
              "status": &self.status.0.trim(),
             });
 
             trimmed_json.serialize(serializer)
         }
     }
 
     if pid::exists() {
         if let Ok(process_id) = pid::read() {
             if let Ok(mut process) = Process::new(process_id as u32) {
                 pid = Some(process_id);
                 uptime = Some(pid::uptime().unwrap());
                 memory_usage = process.memory_info().ok();
                 cpu_percent = process.cpu_percent().ok();
             }
         }
     }
 
     let cpu_percent = match cpu_percent {
         Some(percent) => format!("{:.2}%", percent),
         None => string!("0%"),
     };
 
     let memory_usage = match memory_usage {
         Some(usage) => helpers::format_memory(usage.rss()),
         None => string!("0b"),
     };
 
     let uptime = match uptime {
         Some(uptime) => helpers::format_duration(uptime),
         None => string!("none"),
     };
 
     let pid = match pid {
         Some(pid) => string!(pid),
         None => string!("n/a"),
     };
 
     let data = vec![Info {
         pid: pid,
         cpu_percent,
         memory_usage,
         uptime: uptime,
         path: global!("pmc.base"),
         external: global!("pmc.daemon.kind"),
         process_count: runner.list().keys().len(),
         pid_file: format!("{}  ", global!("pmc.pid")),
         status: ColoredString(ternary!(pid::exists(), "online".green().bold(), "stopped".red().bold())),
     }];
 
     let table = Table::new(data.clone())
         .with(Rotate::Left)
         .with(Style::rounded().remove_horizontals())
         .with(Colorization::exact([Color::FG_CYAN], Columns::first()))
         .with(BorderColor::filled(Color::FG_BRIGHT_BLACK))
         .to_string();
 
     if let Ok(json) = serde_json::to_string(&data[0]) {
         match format.as_str() {
             "raw" => println!("{:?}", data[0]),
             "json" => println!("{json}"),
             "default" => {
                 println!("{}\n{table}\n", format!("PMC daemon information").on_bright_white().black());
                 println!(" {}", format!("Use `pmc daemon restart` to restart the daemon").white());
                 println!(" {}", format!("Use `pmc daemon reset` to clean process id values").white());
             }
             _ => {}
         };
     };
 }
 
 pub fn stop() {
     if pid::exists() {
+        let mut log = Logger::new().unwrap();
         println!("{} Stopping PMC daemon", *helpers::SUCCESS);
 
         match pid::read() {
             Ok(pid) => {
                 service::stop(pid as i64);
                 pid::remove();
+                log.write(format!("daemon stopped (pid={pid})").as_str());
                 println!("{} PMC daemon stopped", *helpers::SUCCESS);
             }
             Err(err) => crashln!("{} Failed to read PID file: {}", *helpers::FAIL, err),
         }
     } else {
         crashln!("{} The daemon is not running", *helpers::FAIL)
     }
 }
 
 pub fn start() {
     let external = match global!("pmc.daemon.kind").as_str() {
         "external" => true,
         "default" => false,
         "rust" => false,
         "cc" => true,
         _ => false,
     };
 
     pid::name("PMC Restart Handler Daemon");
     println!("{} Spawning PMC daemon (pmc_base={})", *helpers::SUCCESS, global!("pmc.base"));
 
     if pid::exists() {
         match pid::read() {
             Ok(pid) => then!(!pid::running(pid), pid::remove()),
             Err(_) => crashln!("{} The daemon is already running", *helpers::FAIL),
         }
     }
 
     extern "C" fn init() {
         let config = config::read();
+        let mut log = Logger::new().unwrap();
+
         unsafe { libc::signal(libc::SIGTERM, handle_termination_signal as usize) };
         pid::write(process::id());
+        log.write(format!("new daemon forked (pid={})", process::id()).as_str());
 
         loop {
-            let runner = Runner::new();
+            let runner: Runner = file::read(global!("pmc.dump"));
             then!(!runner.list().is_empty(), restart_process(runner));
             sleep(Duration::from_millis(config.daemon.interval));
         }
     }
 
     println!("{} PMC Successfully daemonized (type={})", *helpers::SUCCESS, global!("pmc.daemon.kind"));
     if external {
         let callback = crate::Callback(init);
         crate::service::try_fork(false, false, callback);
     } else {
         match daemon(false, false) {
             Ok(Fork::Parent(_)) => {}
             Ok(Fork::Child) => init(),
             Err(err) => crashln!("{} Daemon creation failed with code {err}", *helpers::FAIL),
         }
     }
 }
 
 pub fn restart() {
     if pid::exists() {
         stop();
     }
     start();
 }
+
+pub fn reset() {
+    let mut runner = Runner::new();
+    let largest = runner.list().keys().last().cloned();
+
+    match largest {
+        Some(id) => runner.set_id(Id::from(str!(id))),
+        None => println!("{} Cannot reset index, no ID found", *helpers::FAIL),
+    }
+
+    println!("{} PMC Successfully reset (index={})", *helpers::SUCCESS, runner.id);
+}
diff --git a/src/globals.rs b/src/globals.rs
index 6d497c0..afb48e5 100644
--- a/src/globals.rs
+++ b/src/globals.rs
@@ -1,43 +1,40 @@
 use crate::config;
 use crate::file::Exists;
 use crate::helpers;
 
 use global_placeholders::init;
 use macros_rs::crashln;
 use std::fs;
 
 pub fn init() {
     match home::home_dir() {
         Some(path) => {
             let path = path.display();
             if !Exists::folder(format!("{path}/.pmc/")).unwrap() {
                 fs::create_dir_all(format!("{path}/.pmc/")).unwrap();
                 log::info!("created pmc base dir");
             }
 
             let config = config::read();
             if !Exists::folder(config.runner.log_path.clone()).unwrap() {
                 fs::create_dir_all(&config.runner.log_path).unwrap();
                 log::info!("created pmc log dir");
             }
 
             init!("pmc.base", format!("{path}/.pmc/"));
+            init!("pmc.log", format!("{path}/.pmc/pmc.log"));
             init!("pmc.pid", format!("{path}/.pmc/daemon.pid"));
             init!("pmc.dump", format!("{path}/.pmc/process.dump"));
 
-            init!("pmc.config.shell", config.runner.shell);
-            init!("pmc.config.log_path", config.runner.log_path);
-
             init!("pmc.daemon.kind", config.daemon.kind);
-            init!("pmc.daemon.interval", config.daemon.interval);
-            init!("pmc.daemon.logs", format!("{path}/.pmc/daemon.log"));
+            init!("pmc.daemon.log", format!("{path}/.pmc/daemon.log"));
 
             let out = format!("{}/{{}}-out.log", config.runner.log_path);
             let error = format!("{}/{{}}-error.log", config.runner.log_path);
 
             init!("pmc.logs.out", out);
             init!("pmc.logs.error", error);
         }
         None => crashln!("{} Impossible to get your home directory", *helpers::FAIL),
     }
 }
diff --git a/src/helpers.rs b/src/helpers.rs
index 1bfa342..ffdc53a 100644
--- a/src/helpers.rs
+++ b/src/helpers.rs
@@ -1,61 +1,87 @@
 use chrono::{DateTime, Utc};
 use colored::Colorize;
 use core::fmt;
 use once_cell::sync::Lazy;
 use regex::Regex;
 use serde::{Deserialize, Serialize};
+use std::str::FromStr;
 use std::sync::atomic::{AtomicUsize, Ordering};
 
 pub static SUCCESS: Lazy<colored::ColoredString> = Lazy::new(|| "[PMC]".green());
 pub static FAIL: Lazy<colored::ColoredString> = Lazy::new(|| "[PMC]".red());
 
 #[derive(Clone, Debug)]
 pub struct ColoredString(pub colored::ColoredString);
 
 impl serde::Serialize for ColoredString {
     fn serialize<S: serde::ser::Serializer>(&self, serializer: S) -> Result<S::Ok, S::Error> {
         let re = Regex::new(r"\x1B\[([0-9;]+)m").unwrap();
         let colored_string = &self.0;
         let stripped_string = re.replace_all(colored_string, "").to_string();
         serializer.serialize_str(&stripped_string)
     }
 }
 
 impl fmt::Display for ColoredString {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { write!(f, "{}", self.0) }
 }
 
 #[derive(Debug, Deserialize, Serialize)]
 pub struct Id {
     pub counter: AtomicUsize,
 }
 
 impl Id {
     pub fn new(start: usize) -> Self { Id { counter: AtomicUsize::new(start) } }
     pub fn next(&self) -> usize { self.counter.fetch_add(1, Ordering::SeqCst) }
 }
 
+impl FromStr for Id {
+    type Err = &'static str;
+
+    fn from_str(s: &str) -> Result<Self, Self::Err> {
+        if let Ok(value) = s.parse::<usize>() {
+            Ok(Id::new(value))
+        } else {
+            Err("Failed to parse string into usize")
+        }
+    }
+}
+
+impl From<&str> for Id {
+    fn from(s: &str) -> Self {
+        match s.parse::<Id>() {
+            Ok(id) => id,
+            Err(_) => Id::new(0),
+        }
+    }
+}
+
+impl fmt::Display for Id {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { write!(f, "{}", self.counter.load(Ordering::SeqCst)) }
+}
+
 pub fn format_duration(datetime: DateTime<Utc>) -> String {
     let current_time = Utc::now();
     let duration = current_time.signed_duration_since(datetime);
 
     match duration.num_seconds() {
         s if s >= 86400 => format!("{}d", s / 86400),
         s if s >= 3600 => format!("{}h", s / 3600),
         s if s >= 60 => format!("{}m", s / 60),
         s => format!("{}s", s),
     }
 }
 
 pub fn format_memory(bytes: u64) -> String {
     const KB: u64 = 1024;
     const MB: u64 = KB * 1024;
     const GB: u64 = MB * 1024;
 
     match bytes {
         0..=KB if bytes < KB => format!("{}b", bytes),
         KB..=MB if bytes < MB => format!("{:.1}kb", bytes as f64 / KB as f64),
         MB..=GB if bytes < GB => format!("{:.1}mb", bytes as f64 / MB as f64),
         _ => format!("{:.1}gb", bytes as f64 / GB as f64),
     }
 }
diff --git a/src/main.rs b/src/main.rs
index 3ffc003..1d11969 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,173 +1,173 @@
 mod cli;
 mod config;
 mod daemon;
 mod file;
 mod globals;
 mod helpers;
 mod process;
 mod structs;
 
 use crate::structs::Args;
 use clap::{Parser, Subcommand};
 use clap_verbosity_flag::Verbosity;
 use cxx::{type_id, ExternType};
 use macros_rs::{str, string, then};
 
 fn validate_id_script(s: &str) -> Result<Args, String> {
     if let Ok(id) = s.parse::<usize>() {
         Ok(Args::Id(id))
     } else {
         Ok(Args::Script(s.to_owned()))
     }
 }
 
 #[derive(Parser)]
 #[command(version = str!(cli::get_version(false)))]
 struct Cli {
     #[command(subcommand)]
     command: Commands,
     #[clap(flatten)]
     verbose: Verbosity,
 }
 
 #[derive(Subcommand)]
 enum Daemon {
     /// Reset process index
     #[command(alias = "clean")]
     Reset,
     /// Stop daemon
     #[command(alias = "kill")]
     Stop,
     /// Restart daemon
     #[command(alias = "restart", alias = "start")]
     Restore,
     /// Check daemon
     #[command(alias = "info")]
     Health {
         /// Format output
         #[arg(long, default_value_t = string!("default"))]
         format: String,
     },
 }
 
 // add pmc restore command
 #[derive(Subcommand)]
 enum Commands {
     /// Start/Restart a process
     #[command(alias = "restart")]
     Start {
         #[arg(long, help = "process name")]
         name: Option<String>,
         #[clap(value_parser = validate_id_script)]
         args: Option<Args>,
     },
 
     /// Stop/Kill a process
     #[command(alias = "kill")]
     Stop { id: usize },
 
     /// Stop then remove a process
     #[command(alias = "rm")]
     Remove { id: usize },
 
     /// Get env of a process
     #[command(alias = "cmdline")]
     Env { id: usize },
 
     /// Get information of a process
     #[command(alias = "info")]
     Details {
         id: usize,
         /// Format output
         #[arg(long, default_value_t = string!("default"))]
         format: String,
     },
 
     /// List all processes
     #[command(alias = "ls")]
     List {
         /// Format output
         #[arg(long, default_value_t = string!("default"))]
         format: String,
     },
 
     /// Get logs from a process
     Logs {
         id: usize,
         #[arg(long, default_value_t = 15, help = "")]
         lines: usize,
     },
 
     /// Daemon management
     Daemon {
         #[command(subcommand)]
         command: Daemon,
     },
 }
 
 fn main() {
     globals::init();
 
     let cli = Cli::parse();
     let mut env = env_logger::Builder::new();
     env.filter_level(cli.verbose.log_level_filter()).init();
 
     match &cli.command {
         // add --watch
         Commands::Start { name, args } => cli::start(name, args),
         Commands::Stop { id } => cli::stop(id),
         Commands::Remove { id } => cli::remove(id),
         Commands::Env { id } => cli::env(id),
         Commands::Details { id, format } => cli::info(id, format),
         Commands::List { format } => cli::list(format),
         Commands::Logs { id, lines } => cli::logs(id, lines),
 
         Commands::Daemon { command } => match command {
-            Daemon::Reset => {}
             Daemon::Stop => daemon::stop(),
+            Daemon::Reset => daemon::reset(),
             Daemon::Restore => daemon::restart(),
             Daemon::Health { format } => daemon::health(format),
         },
     };
 
     if !matches!(&cli.command, Commands::Daemon { .. }) {
         then!(!daemon::pid::exists(), daemon::start());
     }
 }
 
 #[repr(transparent)]
 pub struct Callback(pub extern "C" fn());
 
 unsafe impl ExternType for Callback {
     type Id = type_id!("Callback");
     type Kind = cxx::kind::Trivial;
 }
 
 #[cxx::bridge]
 pub mod service {
 
     #[repr(u8)]
     enum Fork {
         Parent,
         Child,
     }
 
     pub struct ProcessMetadata {
         pub name: String,
         pub shell: String,
         pub command: String,
         pub log_path: String,
         pub args: Vec<String>,
     }
 
     unsafe extern "C++" {
         include!("pmc/src/include/process.h");
         include!("pmc/src/include/bridge.h");
         include!("pmc/src/include/fork.h");
         type Callback = crate::Callback;
 
         pub fn stop(pid: i64) -> i64;
         pub fn run(metadata: ProcessMetadata) -> i64;
         pub fn try_fork(nochdir: bool, noclose: bool, callback: Callback) -> i32;
     }
 }
diff --git a/src/process/log.rs b/src/process/log.rs
new file mode 100644
index 0000000..558cef3
--- /dev/null
+++ b/src/process/log.rs
@@ -0,0 +1,17 @@
+use chrono::Local;
+use global_placeholders::global;
+use std::fs::{File, OpenOptions};
+use std::io::{self, Write};
+
+pub struct Logger {
+    file: File,
+}
+
+impl Logger {
+    pub fn new() -> io::Result<Self> {
+        let file = OpenOptions::new().create(true).append(true).open(global!("pmc.log"))?;
+        Ok(Logger { file })
+    }
+
+    pub fn write(&mut self, message: &str) { writeln!(&mut self.file, "[{}] {}", Local::now().format("%Y-%m-%d %H:%M:%S%.3f"), message).unwrap() }
+}
diff --git a/src/process/mod.rs b/src/process/mod.rs
index 767e30d..0d7f65e 100644
--- a/src/process/mod.rs
+++ b/src/process/mod.rs
@@ -1,134 +1,142 @@
 mod dump;
+mod log;
 
 use crate::config;
 use crate::file;
 use crate::helpers::{self, Id};
 use crate::service::{run, stop, ProcessMetadata};
 
 use chrono::serde::ts_milliseconds;
 use chrono::{DateTime, Utc};
 use macros_rs::{crashln, string};
 use serde::{Deserialize, Serialize};
 use std::collections::{BTreeMap, HashMap};
 use std::env;
 use std::path::PathBuf;
 
 #[derive(Debug, Deserialize, Serialize)]
 pub struct Process {
     pub pid: i64,
     pub name: String,
     pub path: PathBuf,
     pub script: String,
     pub env: HashMap<String, String>,
     #[serde(with = "ts_milliseconds")]
     pub started: DateTime<Utc>,
+    // pub restarts: u64,
     pub running: bool,
 }
 
 #[derive(Debug, Deserialize, Serialize)]
 pub struct Runner {
-    id: Id,
-    process_list: BTreeMap<String, Process>,
+    pub id: Id,
+    pub process_list: BTreeMap<String, Process>,
 }
 
 impl Runner {
     pub fn new() -> Self {
         let dump = dump::read();
 
         let runner = Runner {
             id: dump.id,
             process_list: dump.process_list,
         };
 
         dump::write(&runner);
         return runner;
     }
 
     pub fn start(&mut self, name: &String, command: &String) {
         let config = config::read().runner;
         let pid = run(ProcessMetadata {
             name: name.clone(),
             log_path: config.log_path,
             command: command.clone(),
             shell: config.shell,
             args: config.args,
         });
 
         self.process_list.insert(
             string!(self.id.next()),
             Process {
                 pid,
                 running: true,
                 path: file::cwd(),
                 name: name.clone(),
                 started: Utc::now(),
                 script: command.clone(),
                 env: env::vars().collect(),
             },
         );
         dump::write(&self);
     }
 
     pub fn stop(&mut self, id: usize) {
         if let Some(item) = self.process_list.get_mut(&string!(id)) {
             stop(item.pid);
             item.running = false;
             dump::write(&self);
         } else {
             crashln!("{} Process ({id}) not found", *helpers::FAIL);
         }
     }
 
     pub fn restart(&mut self, id: usize, name: &Option<String>) {
         if let Some(item) = self.info(id) {
             let script = item.script.clone();
             let path = item.path.clone();
             let env = item.env.clone();
 
             let name = match name {
                 Some(name) => string!(name.trim()),
                 None => string!(item.name.clone()),
             };
 
             if let Err(err) = std::env::set_current_dir(&path) {
                 crashln!("{} Failed to set working directory {:?}\nError: {:#?}", *helpers::FAIL, path, err);
             };
 
             self.stop(id);
 
             let config = config::read().runner;
             let pid = run(ProcessMetadata {
                 name: name.clone(),
                 log_path: config.log_path,
                 command: script.clone(),
                 shell: config.shell,
                 args: config.args,
             });
 
             self.process_list.insert(
                 string!(id),
                 Process {
                     pid,
                     env,
                     name,
                     path,
                     script,
                     running: true,
                     started: Utc::now(),
                 },
             );
             dump::write(&self);
         } else {
             crashln!("{} Failed to restart process ({})", *helpers::FAIL, id);
         }
     }
 
     pub fn remove(&mut self, id: usize) {
         self.stop(id);
         self.process_list.remove(&string!(id));
         dump::write(&self);
     }
 
+    pub fn set_id(&mut self, id: Id) {
+        self.id = id;
+        self.id.next();
+        dump::write(&self);
+    }
+
     pub fn info(&self, id: usize) -> Option<&Process> { self.process_list.get(&string!(id)) }
     pub fn list(&self) -> &BTreeMap<String, Process> { &self.process_list }
 }