Add a function to allow statslog failure.

+ Record all types of failures which lead to log loss
+ Only record eventual failure after the retries to get a accurate log loss count.

Bug: 80538532
Test: manually tested

Change-Id: I23a55e62e140bf22ae5aa9e6c40539d51149cd66
Merged-In: I23a55e62e140bf22ae5aa9e6c40539d51149cd66
(cherry picked from commit ad3a40bf76b670878760738765154448772243fb)
diff --git a/libstats/include/stats_event_list.h b/libstats/include/stats_event_list.h
index 5d174ae..28da270 100644
--- a/libstats/include/stats_event_list.h
+++ b/libstats/include/stats_event_list.h
@@ -24,6 +24,7 @@
 #endif
 void reset_log_context(android_log_context ctx);
 int write_to_logger(android_log_context context, log_id_t id);
+void note_log_drop();
 
 #ifdef __cplusplus
 }
diff --git a/libstats/stats_event_list.c b/libstats/stats_event_list.c
index 3d746db..51408e0 100644
--- a/libstats/stats_event_list.c
+++ b/libstats/stats_event_list.c
@@ -119,6 +119,10 @@
     return retValue;
 }
 
+void note_log_drop() {
+    statsdLoggerWrite.noteDrop();
+}
+
 /* log_init_lock assumed */
 static int __write_to_statsd_initialize_locked() {
     if (!statsdLoggerWrite.open || ((*statsdLoggerWrite.open)() < 0)) {
diff --git a/libstats/statsd_writer.c b/libstats/statsd_writer.c
index 9953bba..afe401f 100644
--- a/libstats/statsd_writer.c
+++ b/libstats/statsd_writer.c
@@ -38,6 +38,7 @@
 #define min(x, y) ((y) ^ (((x) ^ (y)) & -((x) < (y))))
 
 static pthread_mutex_t log_init_lock = PTHREAD_MUTEX_INITIALIZER;
+static atomic_int dropped = 0;
 
 void statsd_writer_init_lock() {
     /*
@@ -59,14 +60,16 @@
 static int statsdOpen();
 static void statsdClose();
 static int statsdWrite(struct timespec* ts, struct iovec* vec, size_t nr);
+static void statsdNoteDrop();
 
 struct android_log_transport_write statsdLoggerWrite = {
-    .name = "statsd",
-    .sock = -EBADF,
-    .available = statsdAvailable,
-    .open = statsdOpen,
-    .close = statsdClose,
-    .write = statsdWrite,
+        .name = "statsd",
+        .sock = -EBADF,
+        .available = statsdAvailable,
+        .open = statsdOpen,
+        .close = statsdClose,
+        .write = statsdWrite,
+        .noteDrop = statsdNoteDrop,
 };
 
 /* log_init_lock assumed */
@@ -131,6 +134,10 @@
     return 1;
 }
 
+static void statsdNoteDrop() {
+    atomic_fetch_add_explicit(&dropped, 1, memory_order_relaxed);
+}
+
 static int statsdWrite(struct timespec* ts, struct iovec* vec, size_t nr) {
     ssize_t ret;
     int sock;
@@ -138,7 +145,6 @@
     struct iovec newVec[nr + headerLength];
     android_log_header_t header;
     size_t i, payloadSize;
-    static atomic_int dropped;
 
     sock = atomic_load(&statsdLoggerWrite.sock);
     if (sock < 0) switch (sock) {
@@ -252,8 +258,6 @@
 
     if (ret > (ssize_t)sizeof(header)) {
         ret -= sizeof(header);
-    } else if (ret == -EAGAIN) {
-        atomic_fetch_add_explicit(&dropped, 1, memory_order_relaxed);
     }
 
     return ret;
diff --git a/libstats/statsd_writer.h b/libstats/statsd_writer.h
index 82e14e0..7289441 100644
--- a/libstats/statsd_writer.h
+++ b/libstats/statsd_writer.h
@@ -38,6 +38,8 @@
     void (*close)();    /* free up resources */
     /* write log to transport, returns number of bytes propagated, or -errno */
     int (*write)(struct timespec* ts, struct iovec* vec, size_t nr);
+    /* note one log drop */
+    void (*noteDrop)();
 };
 
 #endif  // ANDROID_STATS_LOG_STATS_WRITER_H