[log-stats] Use the Launcher

Put the program into the //src/diagnostics/launcher to save memory
and disk space.

Test: fx build && \
fx test fuchsia-pkg://fuchsia.com/log-stats-tests#meta/log-stats-unit-tests.cmx && \
fx test fuchsia-pkg://fuchsia.com/log-stats-tests#meta/log-stats-integration-tests.cmx

Change-Id: Ia701b5fcd2974e57a210f3d31ba918537274a64c
Reviewed-on: https://fuchsia-review.googlesource.com/c/fuchsia/+/449415
Commit-Queue: Chris Phoenix <cphoenix@google.com>
Reviewed-by: Adam Perry <adamperry@google.com>
Testability-Review: Adam Perry <adamperry@google.com>
diff --git a/src/diagnostics/launcher/BUILD.gn b/src/diagnostics/launcher/BUILD.gn
index c238c0e..9486a3c 100644
--- a/src/diagnostics/launcher/BUILD.gn
+++ b/src/diagnostics/launcher/BUILD.gn
@@ -13,6 +13,7 @@
   deps = [
     "//src/diagnostics/detect:lib",
     "//src/diagnostics/lib/util/v2-argh-wrapper",
+    "//src/diagnostics/log-stats:lib",
     "//src/diagnostics/sampler:lib",
     "//src/lib/fuchsia-async",
     "//src/lib/syslog/rust:syslog",
diff --git a/src/diagnostics/launcher/README.md b/src/diagnostics/launcher/README.md
index 23bea987..22b6b32 100644
--- a/src/diagnostics/launcher/README.md
+++ b/src/diagnostics/launcher/README.md
@@ -28,10 +28,10 @@
 empty struct with `#[derive(FromArgs, Debug, PartialEq)]`.)
     1. Make sure to derive PartialEq on your arg struct.
     1. Annotate your struct with `#[argh(subcommand, name = "your-choice")]`.
-1. Also from lib.rs, export the former `main` funtion with this signature:
+1. Also from lib.rs, export the `main` funtion with this signature:
 `pub async fn main(args: CommandLine) -> Result<(), Error>`
     1. Remove the `#[fasync::run_singlethreaded]` or similar lines.
-    1. Remove syslog initialization; Launcher does that (the tag is "launcher").
+    1. Remove syslog initialization; Launcher does that.
 1. In BUILD.gn, `import("//build/rust/rustc_library.gni")`, change
 `rustc_bin` to `rustc_lib`, and replace `main.rs` with `lib.rs` in `sources`.
 1. In the .cmx for unit tests, change `_bin_test` to `_lib_test`.
diff --git a/src/diagnostics/launcher/src/main.rs b/src/diagnostics/launcher/src/main.rs
index aa37d4c..3fbffee 100644
--- a/src/diagnostics/launcher/src/main.rs
+++ b/src/diagnostics/launcher/src/main.rs
@@ -21,6 +21,7 @@
 #[argh(subcommand)]
 enum ChildArgs {
     Detect(detect::CommandLine),
+    LogStats(log_stats::CommandLine),
     Lapis(sampler::Args),
 }
 
@@ -30,6 +31,7 @@
     let args = v2_argh_wrapper::load_command_line::<LauncherArgs>()?;
     match args.program {
         ChildArgs::Detect(args) => detect::main(args).await,
+        ChildArgs::LogStats(_args) => log_stats::main().await,
         ChildArgs::Lapis(args) => sampler::main(args).await,
     }
 }
diff --git a/src/diagnostics/log-stats/BUILD.gn b/src/diagnostics/log-stats/BUILD.gn
index 38ff237..104ba45 100644
--- a/src/diagnostics/log-stats/BUILD.gn
+++ b/src/diagnostics/log-stats/BUILD.gn
@@ -2,7 +2,7 @@
 # Use of this source code is governed by a BSD-style license that can be
 # found in the LICENSE file.
 
-import("//build/rust/rustc_binary.gni")
+import("//build/rust/rustc_library.gni")
 import("//src/sys/build/components.gni")
 
 group("log-stats") {
@@ -21,7 +21,7 @@
 fuchsia_component("component") {
   component_name = "log-stats"
   manifest = "meta/log-stats.cml"
-  deps = [ ":bin" ]
+  deps = [ "//src/diagnostics/launcher:bin" ]
 }
 
 fuchsia_package("package") {
@@ -32,10 +32,10 @@
 fuchsia_component("component-v1") {
   component_name = "log-stats"
   manifest = "meta/log-stats.cmx"
-  deps = [ ":bin" ]
+  deps = [ "//src/diagnostics/launcher:bin" ]
 }
 
-rustc_binary("bin") {
+rustc_library("lib") {
   name = "log-stats"
   with_unit_tests = true
 
@@ -50,16 +50,17 @@
     "//src/lib/fuchsia-component",
     "//src/lib/syslog",
     "//third_party/rust_crates:anyhow",
+    "//third_party/rust_crates:argh",
     "//third_party/rust_crates:futures",
     "//third_party/rust_crates:tracing",
   ]
 
-  sources = [ "src/main.rs" ]
+  sources = [ "src/lib.rs" ]
 }
 
 fuchsia_unittest_component("log-stats-unit-tests") {
-  executable_path = "bin/log_stats_bin_test"
-  deps = [ ":bin_test" ]
+  executable_path = "bin/log_stats_lib_test"
+  deps = [ ":lib_test" ]
 }
 
 fuchsia_component("log-stats-integration-tests") {
diff --git a/src/diagnostics/log-stats/meta/log-stats.cml b/src/diagnostics/log-stats/meta/log-stats.cml
index 0ea5eb7..ed25cef 100644
--- a/src/diagnostics/log-stats/meta/log-stats.cml
+++ b/src/diagnostics/log-stats/meta/log-stats.cml
@@ -4,7 +4,8 @@
 {
     include: [ "sdk/lib/diagnostics/syslog/client.shard.cml" ],
     program: {
-        binary: "bin/log_stats",
+        binary: "bin/launcher",
+        args: [ "log-stats" ],
     },
     capabilities: [
         {
diff --git a/src/diagnostics/log-stats/meta/log-stats.cmx b/src/diagnostics/log-stats/meta/log-stats.cmx
index a783dd0b..cf39d22 100644
--- a/src/diagnostics/log-stats/meta/log-stats.cmx
+++ b/src/diagnostics/log-stats/meta/log-stats.cmx
@@ -3,7 +3,10 @@
         "sdk/lib/diagnostics/syslog/client.shard.cmx"
     ],
     "program": {
-        "binary": "bin/log_stats"
+        "args": [
+            "log-stats"
+        ],
+        "binary": "bin/launcher"
     },
     "sandbox": {
         "services": [
diff --git a/src/diagnostics/log-stats/src/main.rs b/src/diagnostics/log-stats/src/lib.rs
similarity index 88%
rename from src/diagnostics/log-stats/src/main.rs
rename to src/diagnostics/log-stats/src/lib.rs
index 4838cf1..d5ebded 100644
--- a/src/diagnostics/log-stats/src/main.rs
+++ b/src/diagnostics/log-stats/src/lib.rs
@@ -6,6 +6,7 @@
     debuglog::KERNEL_URL,
     stats::{LogManagerStats, LogSource},
 };
+use argh::FromArgs;
 use diagnostics_reader::{ArchiveReader, Logs};
 use fidl_fuchsia_diagnostics::{ArchiveAccessorMarker, ArchiveAccessorProxy};
 use fuchsia_async as fasync;
@@ -18,9 +19,12 @@
 use futures::{future::join, prelude::*};
 use tracing::*;
 
-#[fasync::run_singlethreaded]
-async fn main() -> Result<(), anyhow::Error> {
-    fuchsia_syslog::init()?;
+/// Empty command line args, just to give Launcher the subcommand name "log-stats"
+#[derive(FromArgs, Debug, PartialEq)]
+#[argh(subcommand, name = "log-stats")]
+pub struct CommandLine {}
+
+pub async fn main() -> Result<(), anyhow::Error> {
     let mut service_fs = ServiceFs::new_local();
     service_fs.take_and_serve_directory_handle()?;