Commit d00cbc3f90806ce1cca690860dfdde5c66625e52

Priyesh Kumar 2020-08-26T19:44:01

[base] Updates to print timestamp and name of `FT_COMPONENT` in logs. * include/freetype/internal/ftdebug.h (FT_LOGGING_TAG, FT_LOGGING_TAG_): New macros to resolve the value of `FT_COMPONENT' into a string. (ft_add_tag, ft_remove_tag): New functions to add and remove dlg tags. * src/base/ftdebug.c: Add new variables to control the logging of timestamp and name of `FT_COMPONENT` along with actual logs. (ft_add_tag, ft_remove_tag): Add function definitions. (ft_log_handler): Updates to print timestamp and name of `FT_COMPONENT`. (ft_debug_init) [FT_LOGGING]: Users can now control the logging of timestamp and name of `FT_COMPONENT` by adding tags in the `FT2_DEBUG` environment variable.

diff --git a/ChangeLog b/ChangeLog
index 30c1623..7ab4f50 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,21 @@
+2020-11-28  Priyesh Kumar  <priyeshkkumar@gmail.com>
+
+	[base] Updates to print timestamp and name of `FT_COMPONENT` in logs.
+
+	* include/freetype/internal/ftdebug.h (FT_LOGGING_TAG,
+	FT_LOGGING_TAG_): New macros to resolve the value of `FT_COMPONENT'
+	into a string.
+	(ft_add_tag, ft_remove_tag): New functions to add and remove dlg tags.
+
+	* src/base/ftdebug.c: Add new variables to control the logging of
+	timestamp and name of `FT_COMPONENT` along with actual logs.
+	(ft_add_tag, ft_remove_tag): Add function definitions.
+	(ft_log_handler): Updates to print timestamp and name of
+	`FT_COMPONENT`.
+	(ft_debug_init) [FT_LOGGING]: Users can now control the logging of
+	timestamp and name of `FT_COMPONENT` by adding tags in the
+	`FT2_DEBUG` environment variable.
+
 2020-11-27  Priyesh Kumar  <priyeshkkumar@gmail.com>
 
 	[base] Add functions and variables to print logs to a file.
diff --git a/include/freetype/internal/ftdebug.h b/include/freetype/internal/ftdebug.h
index d56eca0..666c26d 100644
--- a/include/freetype/internal/ftdebug.h
+++ b/include/freetype/internal/ftdebug.h
@@ -106,11 +106,21 @@ FT_BEGIN_HEADER
    */
 #ifdef FT_LOGGING
 
+  /* we need two macros to convert the names of `FT_COMPONENT` to a string */
+#define FT_LOGGING_TAG( x )   FT_LOGGING_TAG_( x )
+#define FT_LOGGING_TAG_( x )  #x
+
+
 #define FT_LOG( level, varformat )                                         \
           do                                                               \
           {                                                                \
+            const char*  dlg_tag = FT_LOGGING_TAG( FT_COMPONENT );         \
+                                                                           \
+                                                                           \
+            ft_add_tag( dlg_tag );                                         \
             if ( ft_trace_levels[FT_TRACE_COMP( FT_COMPONENT )] >= level ) \
               dlg_trace varformat;                                         \
+            ft_remove_tag( dlg_tag );                                      \
           } while( 0 )
 
 #else /* !FT_LOGGING */
@@ -249,10 +259,15 @@ FT_BEGIN_HEADER
    */
 #ifdef FT_LOGGING
 
-#define FT_ERROR( varformat )    \
-          do                     \
-          {                      \
-            dlg_trace varformat; \
+#define FT_ERROR( varformat )                                      \
+          do                                                       \
+          {                                                        \
+            const char*  dlg_tag = FT_LOGGING_TAG( FT_COMPONENT ); \
+                                                                   \
+                                                                   \
+            ft_add_tag( dlg_tag );                                 \
+            dlg_trace varformat;                                   \
+            ft_remove_tag( dlg_tag );                              \
           } while ( 0 )
 
 #else /* !FT_LOGGING */
@@ -372,6 +387,19 @@ FT_BEGIN_HEADER
   FT_BASE( void )
   ft_logging_deinit( void );
 
+
+  /**************************************************************************
+   *
+   * For printing the name of `FT_COMPONENT` along with the actual log we
+   * need to add a tag with the name of `FT_COMPONENT`.
+   *
+   */
+  FT_BASE( void )
+  ft_add_tag( const char*  tag );
+
+  FT_BASE( void )
+  ft_remove_tag( const char*  tag );
+
 #endif /* FT_LOGGING */
 
 
diff --git a/src/base/ftdebug.c b/src/base/ftdebug.c
index b554c6a..e422bc2 100644
--- a/src/base/ftdebug.c
+++ b/src/base/ftdebug.c
@@ -43,6 +43,7 @@
 
 #include <freetype/freetype.h>
 #include <freetype/internal/ftdebug.h>
+#include <freetype/internal/ftobjs.h>
 
 
 #ifdef FT_LOGGING
@@ -56,11 +57,26 @@
    *
    * 2. `ft_fileptr` stores the `FILE*` handle.
    *
-   * Use `static` to avoid 'unused variable' warnings.
+   * 3. `ft_component` is a string that holds the name of `FT_COMPONENT`.
+   *
+   * 4. The flag `ft_component_flag` prints the name of `FT_COMPONENT` along
+   *    with the actual log message if set to true.
+   *
+   * 5. The flag `ft_timestamp_flag` prints time along with the actual log
+   *    message if set to ture.
+   *
+   * 6. `ft_have_newline_char` is used to differentiate between a log
+   *    message with and without a trailing newline character.
+   *
+   * We use `static` to avoid 'unused variable' warnings.
    *
    */
   static const char*  ft_default_trace_level = NULL;
   static FILE*        ft_fileptr             = NULL;
+  static const char*  ft_component           = NULL;
+  static FT_Bool      ft_component_flag      = FALSE;
+  static FT_Bool      ft_timestamp_flag      = FALSE;
+  static FT_Bool      ft_have_newline_char   = TRUE;
 
   dlg_handler  ft_default_log_handler = NULL;
 
@@ -231,6 +247,49 @@
         if ( *p == ' ' || *p == '\t' || *p == ',' || *p == ';' || *p == '=' )
           continue;
 
+#ifdef FT_LOGGING
+
+        /* check extra arguments for logging */
+        if ( *p == '-' )
+        {
+          const char*  r = ++p;
+
+
+          if ( *r == 'v' )
+          {
+            const char*  s = ++r;
+
+
+            ft_component_flag = TRUE;
+
+            if ( *s == 't' )
+            {
+              ft_timestamp_flag = TRUE;
+              p++;
+            }
+
+            p++;
+          }
+
+          else if ( *r == 't' )
+          {
+            const char*  s = ++r;
+
+
+            ft_timestamp_flag = TRUE;
+
+            if ( *s == 'v' )
+            {
+              ft_component_flag = TRUE;
+              p++;
+            }
+
+            p++;
+          }
+        }
+
+#endif /* FT_LOGGING */
+
         /* read toggle name, followed by ':' */
         q = p;
         while ( *p && *p != ':' )
@@ -379,13 +438,45 @@
                   const char*               string,
                   void*                     data )
   {
-    const char*  features = "%c";
+    const char*  features;
 
     FT_UNUSED( data );
 
 
+    if ( ft_timestamp_flag && ft_component_flag && ft_have_newline_char )
+      features = "[%h:%m  %t]    %c";
+    else if ( ft_component_flag && ft_have_newline_char )
+      features = "[%t]    %c";
+    else if ( ft_timestamp_flag && ft_have_newline_char )
+      features = "[%h:%m]    %c";
+    else
+      features = "%c";
+
     dlg_generic_outputf_stream( ft_fileptr, features, origin, string,
                                 dlg_default_output_styles, true );
+
+    if ( strchr( string, '\n' ) )
+      ft_have_newline_char = TRUE;
+    else
+      ft_have_newline_char = FALSE;
+  }
+
+
+  /* documentation is in ftdebug.h */
+  FT_BASE_DEF( void )
+  ft_add_tag( const char*  tag )
+  {
+    ft_component = tag;
+
+    dlg_add_tag( tag, NULL );
+  }
+
+
+  /* documentation is in ftdebug.h */
+  FT_BASE_DEF( void )
+  ft_remove_tag( const char*  tag )
+  {
+    dlg_remove_tag( tag, NULL );
   }
 
 #endif /* FT_LOGGING */