1    /* 
     2     *  Copyright (c) 2008 Texas Instruments. All rights reserved.
     3     *  This program and the accompanying materials are made available under the
     4     *  terms of the Eclipse Public License v1.0 and Eclipse Distribution License
     5     *  v. 1.0 which accompanies this distribution. The Eclipse Public License is
     6     *  available at http://www.eclipse.org/legal/epl-v10.html and the Eclipse
     7     *  Distribution License is available at
     8     *  http://www.eclipse.org/org/documents/edl-v10.php.
     9     *
    10     *  Contributors:
    11     *      Texas Instruments - initial implementation
    12     * */
    13    /*
    14     *  ======== Log.xdc ========
    15     */
    16    
    17    /*!
    18     *  ======== Log ========
    19     *  Event logging manager
    20     *
    21     *  RTSC modules and the application code generate `{@link #Event Log_Event}`
    22     *  events by calling the `Log` module's functions. The `Log` module then
    23     *  passes those events to an `{@link ILogger}` instance assigned to the event
    24     *  originating module, specified by that module's configuration parameter
    25     *  `common$.logger`. `ILogger` instances handle events, usually converting
    26     *  events to `{@link #EventRec Log_EventRec}` records prior to recording,
    27     *  transmitting, or displaying them.
    28     *
    29     *  All events generated by a target module are stored and displayed by an
    30     *  `ILogger`, examples of which are instances of
    31     *  `{@link LoggerBuf xdc.runtime.LoggerBuf}` or
    32     *  `{@link LoggerSys xdc.runtime.LoggerSys}`. At runtime, modules
    33     *  generate events through this module, rather than invoking directly their
    34     *  `ILogger`s. By doing so,  modules can be configured to use different
    35     *  `ILogger` implementations without any changes to their source code.
    36     *
    37     *  A logger instance can accept `Log` events from any module, but a module
    38     *  can put `Log` events to only one logger instance. There can be one or
    39     *  more logger instances in a system. All `Log` calls that are not in a
    40     *  module are controlled by the module `{@link Main xdc.runtime.Main}`.
    41     *  For example, top-level application code or any existing sources that
    42     *  simply call the `Log` or `Assert` methods implicitly use the logger
    43     *  associated with the `Main` module.
    44     *
    45     *  The generation of a `Log` event is controlled by a module's diagnostics
    46     *  mask, which is described in details in `{@link Diags}`. Each `Log` event
    47     *  is associated with a mask. `Log` events are generated only when a
    48     *  particular bit is set in both the `Log` event mask and the module's
    49     *  diagnostics mask. For example, a `Log` event mask with the
    50     *  `{@link Diags#USER1 USER1}` bit set is generated only when the `USER1`
    51     *  bit is also set in the module's diagnostics mask.
    52     *
    53     *  There are two ways to generate `Log` events:
    54     *
    55     *  @p(blist)
    56     *  - `{@link #write8 Log_write()}`, which is tailored for module writers
    57     *  and takes full advantage of the XDC configuration model. For example,
    58     *  the message string associated with the `Log` event need not be a part of
    59     *  the final application, significantly reducing the "footprint overhead"
    60     *  of embedding diagnostics in deployed systems. The `Log_write[0-8]()`
    61     *  functions allow up to 8 values to be passed to the logger. They expect
    62     *  the logger to handle any formatting. A `Log` event type allows you to
    63     *  specify the type of event.
    64     *  - `{@link #print6 Log_print()}`, which is designed for arbitrary C code.
    65     *  The `Log_print[0-6]()` functions allow up to 6 values to be passed along
    66     *  with a printf-like format string to the logger. They handle printf-style
    67     *  formatting.
    68     *  @p
    69     *
    70     *  Both functions are controlled by the module's diagnostics mask. Their
    71     *  storage or output is defined by the logger that is assigned to the
    72     *  module that calls the `Log` methods or to the
    73     *  `{@link Main xdc.runtime.Main}` module if the caller is not part of a
    74     *  module.
    75     *
    76     *  The `Log` function call sites are implemented in such a way that an
    77     *  optimizer can completely eliminate `Log` code from the program if the
    78     *  `Log` functions have been permanently disabled at configuration time. If
    79     *  the `Log` functions are permanently turned on at configuration time,
    80     *  then the optimizer can eliminate all runtime conditional checking and
    81     *  simply invoke the `Log` functions directly. Runtime checking is performed
    82     *  only when the `Log` functions are configured to be runtime modifiable.
    83     *
    84     *  The Log calls can also be completely removed by defining the symbol
    85     *  `xdc_runtime_Log_DISABLE_ALL`. This can be done on the compile line, e.g.
    86     *  `-Dxdc_runtime_Log_DISABLE_ALL`. This will completely remove the `Log`
    87     *  statements from any code compiled with this flag, regardless of the
    88     *  application's logging configuration or your compiler's optimization
    89     *  settings.
    90     *
    91     *  It is also possible to remove all logging except for
    92     *  `{@link #error Log_error}`, `{@link #warning Log_warning}`, or
    93     *  `{@link #info Log_info}` statements. This is done by first defining
    94     *  `xdc_runtime_Log_DISABLE_ALL`, followed by defining one or more of the
    95     *  symbols below to leave that type of logging enabled:
    96     *  @p(blist)
    97     *  - `xdc_runtime_Log_ENABLE_ERROR`
    98     *  - `xdc_runtime_Log_ENABLE_WARNING`
    99     *  - `xdc_runtime_Log_ENABLE_INFO`
   100     *  @p
   101     *  For example, to disable all `Log` statements except for `Log_error`, add
   102     *  the following to the compile line:
   103     *  @p(code)
   104     *      -Dxdc_runtime_Log_DISABLE_ALL -Dxdc_runtime_Log_ENABLE_ERROR
   105     *  @p
   106     *
   107     *  @a(Examples)
   108     *  Example 1: The following example defines a `Log` event, uses that `Log`
   109     *  event in a module, and configures the program to generate the `Log`
   110     *  event. In this example, both `USER1` and `USER2` bits are set in the
   111     *  event mask. This means that if either bit is set in the module's
   112     *  diagnostics mask, then the `Log` event will be generated.
   113     *
   114     *  This is a part of the XDC specification file for the `Mod` module
   115     *  (Mod.xdc):
   116     *
   117     *  @p(code)
   118     *  import xdc.runtime.Diags;
   119     *  import xdc.runtime.Log;
   120     *
   121     *  config Log.Event L_someEvent = {
   122     *      mask: Diags.USER1 | Diags.USER2,
   123     *      level: Diags.LEVEL1,
   124     *      msg: "my log event message, arg1: 0x%x, arg2: 0x%x"
   125     *  };
   126     *  @p
   127     *
   128     *  This is a part of the C code implementation of the Mod module:
   129     *
   130     *  @p(code)
   131     *  #include <xdc/runtime/Log.h>
   132     *  UInt x, y;
   133     *
   134     *  Log_write2(Mod_L_someEvent, (IArg)x, (IArg)y);
   135     *  @p
   136     *
   137     *  The following configuration script demonstrates how the application might
   138     *  control the `Log` statements embedded in the `Mod` module at configuration
   139     *  time. In this case, the configuration script arranges for the `Log`
   140     *  statements within the `Mod` module (shown above) to always generate events.
   141     *  Without these configuration statements, no `Log` events would be generated
   142     *  by this module.
   143     *
   144     *  This is part of the XDC configuration file for the application:
   145     *
   146     *  @p(code)
   147     *  var Diags = xdc.useModule('xdc.runtime.Diags');
   148     *  var LoggerSys = xdc.useModule('xdc.runtime.LoggerSys');
   149     *  var Mod = xdc.useModule('my.pkg.Mod');
   150     *  Mod.common$.diags_USER1 = Diags.ALWAYS_ON;
   151     *  Mod.common$.logger = LoggerSys.create();
   152     *  @p
   153     *
   154     *  @p(html)
   155     *  <hr />
   156     *  @p
   157     *
   158     *  Example 2: The following XDC configuration statements turn on enter
   159     *  and exit logging at configuration time for a module. Without any other
   160     *  changes in the runtime code, every time a module `Mod`'s function is
   161     *  being called or exits, an event will be logged.
   162     *
   163     *  @p(code)
   164     *  var Diags = xdc.useModule('xdc.runtime.Diags');
   165     *  var Mod = xdc.useModule('my.pkg.Mod');
   166     *
   167     *  Mod.common$.diags_ENTER = Diags.ALWAYS_ON;
   168     *  Mod.common$.diags_EXIT = Diags.ALWAYS_ON;
   169     *  @p
   170     *
   171     *  @p(html)
   172     *  <hr />
   173     *  @p
   174     *
   175     *  Example 3: The following example configures a module to support enter and
   176     *  exit logging, but defers the actual activation and deactivation of the
   177     *  logging until runtime. See the `{@link Diags#setMask Diags_setMask()}`
   178     *  function for details on specifying the control string.
   179     *
   180     *  This is a part of the XDC configuration file for the application:
   181     *
   182     *  @p(code)
   183     *  var Diags = xdc.useModule('xdc.runtime.Diags');
   184     *  var Mod = xdc.useModule('my.pkg.Mod');
   185     *
   186     *  Mod.common$.diags_ENTER = Diags.RUNTIME_OFF;
   187     *  Mod.common$.diags_EXIT = Diags.RUNTIME_OFF;
   188     *  @p
   189     *
   190     *  This is a part of the C code for the application:
   191     *
   192     *  @p(code)
   193     *  // turn on enter and exit logging in the module
   194     *  Diags_setMask("my.pkg.Mod+EX");
   195     *
   196     *  // turn off enter and exit logging in the module
   197     *  Diags_setMask("my.pkg.Mod-EX");
   198     *  @p
   199     */
   200    
   201    @CustomHeader
   202    @DirectCall
   203    @RomConsts
   204    
   205    module Log {
   206    
   207        /*!
   208         *  ======== NUMARGS ========
   209         *  Maximum number of arguments supported in `Log` events.
   210         */
   211        const Int NUMARGS = 8;
   212    
   213        /*!
   214         *  ======== PRINTFID ========
   215         *  The `EventId` for `Log_print()` events
   216         */
   217        const EventId PRINTFID = 0;
   218    
   219        /*!
   220         *  ======== EventDesc ========
   221         *  `Log` event descriptor
   222         *
   223         *  Each `Log` event is defined by a `Log` event descriptor.
   224         *
   225         *  The `mask` defines which bits in the module's diagnostics mask
   226         *  enable this `Log` event.  Events "posted" via `Log_write` are only
   227         *  written to the underlying logger if one of the mask's bits matches
   228         *  the caller's module diagnostics settings (see
   229         *  `{@link xdc.runtime.Types#common$}`).
   230         *
   231         *  The 'level' defines the event level of the event. While the diags
   232         *  bits selected in the 'mask' signify the "category" of the event (e.g.
   233         *  Entry/Exit, Analysis, Info), the 'level' field allows you to assign
   234         *  a "priority" or "detail level" to the event relative to other events in
   235         *  that category. There are four event levels defined by
   236         *  '{@link xdc.runtime.Diags#EventLevel}'.
   237         *
   238         *  Filtering of events by level is handled by the ILogger implementation.
   239         *  ILogger implementations which also implement the {@link IFilterLogger}
   240         *  interface support filtering of events based on priority level.
   241         *
   242         *  Specifying an event level is optional. Events that don't specify a
   243         *  level will receive Diags.LEVEL1 by default, making them the highest
   244         *  priority and ensuring that they will not inadvertently be filtered out
   245         *  by level-based filtering.
   246         *
   247         *  The `msg` defines a printf style format string that defines how to
   248         *  render the arguments passed along the event in a `Log_write` call.
   249         *  For a description of the allowable format strings see
   250         *  `{@link #print6}`.
   251         *
   252         *  @see #write8
   253         *  @see #print6
   254         */
   255        metaonly struct EventDesc {
   256            Diags.Mask          mask;   /*! event enable mask */
   257            Diags.EventLevel    level;  /*! event level relative to other events */
   258            String              msg;    /*! event "printf" message format string */
   259        };
   260    
   261        /*!
   262         *  ======== EventRec ========
   263         *  The target representation of a recorded event
   264         *
   265         *  This structure defines how events are recorded on the target.
   266         */
   267        struct EventRec {
   268            Types.Timestamp64 tstamp;   /*! time event was written */
   269            Bits32 serial;              /*! serial number of event */
   270            Types.Event evt;            /*! target encoding of an Event */
   271            IArg arg[NUMARGS];          /*! arguments passed via Log_write/print */
   272        }
   273    
   274        /*!
   275         *  ======== Event ========
   276         *  `Log` event type
   277         *
   278         *  An `Event` is represented on the target as a 32-bit value that can
   279         *  be decoded offline to recover the `Event` information defined in
   280         *  a corresponding metaonly `EventDesc`.  In addition, `Event`s may be
   281         *  decoded at runtime via methods provided in this module; see
   282         *  `{@link #getMask}` and `{@link #getEventId}`.
   283         *
   284         *  When an event is "raised" a `{@link Types#Event Types_Event}` is
   285         *  created which has the same event ID as the `Log_Event` but also
   286         *  encodes the module ID of the caller.  This new event is passed to
   287         *  the underlying `{@link ILogger}` module along with any arguments
   288         *  associated with the event.
   289         *
   290         *  @see #getMask
   291         *  @see #getEventId
   292         */
   293        @Encoded typedef EventDesc Event;
   294    
   295        /*!
   296         *  ======== EventId ========
   297         *  Unique ID embedded in each `{@link #Event}`
   298         *
   299         *  This ID must be used to compare two `Event`s for equality.  Event
   300         *  ids are not guaranteed to remain constant between different
   301         *  configurations of an application.  For example, adding a module
   302         *  may cause the event ids of another module to change.
   303         *
   304         *  However, event ids declared by a module are guaranteed to be
   305         *  consecutive values starting from the first declared
   306         *  `{@link #Event Log_Event}` and increasing to the last declared
   307         *  event.  As a result, clients of a module can efficiently test ranges
   308         *  of events and modules can add new events, such as internal trace
   309         *  events, without breaking clients; simply be careful to add new events
   310         *  after any existing events in you module's `.xdc` specification.
   311         *
   312         *  @see #getEventId
   313         *  @see #Event
   314         */
   315        typedef Types.RopeId EventId;
   316    
   317        /*!
   318         *  ======== L_construct ========
   319         *  Lifecycle event posted when an instance is constructed
   320         */
   321        config Log.Event L_construct = {
   322            mask: Diags.LIFECYCLE,
   323            msg: "<-- construct: %p('%s')"
   324        };
   325    
   326        /*!
   327         *  ======== L_create ========
   328         *  Lifecycle event posted when an instance is created
   329         */
   330        config Log.Event L_create = {
   331            mask: Diags.LIFECYCLE,
   332            msg: "<-- create: %p('%s')"
   333        };
   334    
   335        /*!
   336         *  ======== L_destruct ========
   337         *  Lifecycle event posted when an instance is destructed
   338         */
   339        config Log.Event L_destruct = {
   340            mask: Diags.LIFECYCLE,
   341            msg: "--> destruct: (%p)"
   342        };
   343    
   344        /*!
   345         *  ======== L_delete ========
   346         *  Lifecycle event posted when an instance is deleted
   347         */
   348        config Log.Event L_delete = {
   349            mask: Diags.LIFECYCLE,
   350            msg: "--> delete: (%p)"
   351        };
   352    
   353        /*!
   354         *  ======== L_error ========
   355         *  Error event posted by Log_errorX API
   356         *
   357         *  This event is marked as a STATUS event and given the priority level
   358         *  of ERROR.
   359         *
   360         *  This event prints the Log call site (%$F) and a format string (%$S)
   361         *  which is recursively formatted with any additional arguments.
   362         */
   363        config Log.Event L_error = {
   364            mask: Diags.STATUS,
   365            level: Diags.ERROR,
   366            msg: "ERROR: %$F%$S"
   367        };
   368    
   369        /*!
   370         *  ======== L_warning ========
   371         *  Warning event posted by Log_warningX API
   372         *
   373         *  This event is marked as a STATUS event and given the priority level of
   374         *  WARNING.
   375         *
   376         *  This event prints the Log call site (%$F) and a format string (%$S)
   377         *  which is recursively formatted with any addition arguments.
   378         */
   379        config xdc.runtime.Log.Event L_warning = {
   380            mask: Diags.STATUS,
   381            level: Diags.WARNING,
   382            msg: "WARNING: %$F%$S"
   383        };
   384    
   385        /*!
   386         *  ======== L_info ========
   387         *  Info event posted by Log_infoX API
   388         *
   389         *  This event is marked as an INFO event. The event priority is not
   390         *  specified in the event definition. Rather, it is specified as an
   391         *  argument to the Log_infoX APIs.
   392         *
   393         *  This event prints the Log call site (%$F) and a format string (%$S)
   394         *  which is recursively formatted with any addition arguments.
   395         */
   396        config xdc.runtime.Log.Event L_info = {
   397            mask: Diags.INFO,
   398            msg: "%$F%$S"
   399        };
   400    
   401        /*!
   402         *  ======== L_start ========
   403         *  Benchmark event used to log the start of an operation
   404         *  @_nodoc
   405         *
   406         *  @a(Example)
   407         *   The following C code shows how to log a simple
   408         *   benchmark 'start' event along with a user-specified
   409         *   format string describing the event.
   410         *
   411         *  @p(code)
   412         *  #include <xdc/runtime/Log.h>
   413         *  ...
   414         *  Log_write2(Log_L_start, (IArg)"My benchmark event", (IArg)myUniqueId);
   415         *  Log_write2(Log_L_stop, (IArg)"My benchmark event", (IArg)myUniqueId);
   416         *  @p
   417         *
   418         *  @param(fmt)     a constant string that provides format specifiers for
   419         *                  up to 6 additional parameters
   420         *  @param(id)      a unique ID used to match benchmark start and stop
   421         *                  events
   422         */
   423        config xdc.runtime.Log.Event L_start = {
   424            mask: Diags.ANALYSIS,
   425            msg: "Start: %$S"};
   426    
   427        /*!
   428         *  ======== L_stop ========
   429         *  Benchmark event used to log the end of an operation
   430         *  @_nodoc
   431         *
   432         *  @a(Example)
   433         *   The following C code shows how to log a simple
   434         *   benchmark 'stop' event along with a user-specified
   435         *   format string describing the event.
   436         *
   437         *  @p(code)
   438         *  #include <xdc/runtime/Log.h>
   439         *  ...
   440         *  Log_write2(Log_L_start, (IArg)"My benchmark event", (IArg)myUniqueId);
   441         *  Log_write2(Log_L_stop, (IArg)"My benchmark event", (IArg)myUniqueId);
   442         *  @p
   443         *
   444         *  @param(fmt)     a constant string that provides format specifiers for
   445         *                  up to 6 additional parameters
   446         *  @param(id)      a unique ID used to match benchmark start and stop
   447         *                  events
   448         */
   449        config xdc.runtime.Log.Event L_stop = {
   450            mask: Diags.ANALYSIS,
   451            msg: "Stop: %$S"};
   452    
   453        /*!
   454         *  ======== L_startInstance ========
   455         *  Benchmark event used to log the start of an operation instance
   456         *  @_nodoc
   457         *
   458         *  Event parameter provides instance data to differentiate
   459         *  between multiple instances that can run in parallel.
   460         *
   461         *  @a(Example)
   462         *   The following C code shows how to log a benchmark
   463         *   'startInstance' event along with a user-specified
   464         *   instance identifier and a format string describing the event.
   465         *
   466         *  @p(code)
   467         *  #include <xdc/runtime/Log.h>
   468         *  ...
   469         *  Log_write3(Log_L_startInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId);
   470         *  ...
   471         *  Log_write3(Log_L_stopInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId);
   472         *  @p
   473         *  
   474         *  @param(fmt)     a constant string that provides format specifiers for
   475         *                  up to 6 additional parameters
   476         *  @param(id)      a unique ID used to match benchmark start and stop
   477         *                  events
   478         *  @param(instId)  a unique instance ID that can be used to match
   479         *                  instance events
   480         */
   481        config xdc.runtime.Log.Event L_startInstance = {
   482            mask: Diags.ANALYSIS,
   483            msg: "StartInstance: %$S"
   484        };
   485    
   486        /*!
   487         *  ======== L_stopInstance ========
   488         *  Benchmark event used to log the end of an operation instance
   489         *  @_nodoc
   490         *
   491         *  Event parameter provides instance data to differentiate
   492         *  between multiple instances that can run in parallel.
   493         *
   494         * @a(Example)
   495         *   The following C code shows how to log a benchmark
   496         *   'stopInstance' event along with a user-specified
   497         *   instance identifier and a format string describing the event.
   498         *
   499         *  @p(code)
   500         *  #include <xdc/runtime/Log.h>
   501         *  ...
   502         *  Log_write3(Log_L_startInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId);
   503         *  ...
   504         *  Log_write3(Log_L_stopInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId);
   505         *  @p
   506         *
   507         *  @param(fmt)     a constant string that provides format specifiers for
   508         *                  up to 6 additional parameters
   509         *  @param(id)      a unique ID used to match benchmark start and stop
   510         *                  events
   511         *  @param(instId)  a unique instance ID that can be used to match
   512         *                  instance events
   513         */
   514        config xdc.runtime.Log.Event L_stopInstance = {
   515            mask: Diags.ANALYSIS,
   516            msg: "StopInstance: %$S"
   517        };
   518    
   519        /*!
   520         *  ======== getMask ========
   521         *  Get the `Diags` mask for the specified (encoded) event
   522         *
   523         *  @param(evt) the `Log` event encoding a mask and event ID
   524         *
   525         *  @a(returns) `Diags` mask for the specified event
   526         */
   527        @Macro Diags.Mask getMask(Event evt);
   528    
   529        /*!
   530         *  ======== getRope ========
   531         *  Get RopeId of the Event.msg for the specified (encoded) event
   532         *  @_nodoc
   533         */
   534        @Macro Text.RopeId getRope(Event evt);
   535    
   536        /*!
   537         *  ======== getEventId ========
   538         *  Get event ID of the specified (encoded) event
   539         *
   540         *  This method is used to compare "known" `Log` events with
   541         *  "raised" `{@link Types#Event Types_Event}`.
   542         *
   543         *  @param(evt) the `Log` event encoding a mask and event ID
   544         *
   545         *  @a(returns) event ID of the specified event
   546         *
   547         *  @see Types#getEventId
   548         */
   549        @Macro EventId getEventId(Event evt);
   550    
   551        /*!
   552         *  ======== print0 ========
   553         *  Generate a `Log` "print event" with 0 arguments
   554         *
   555         *  @see #print6
   556         */
   557        @Macro Void print0(Diags.Mask mask, CString fmt);
   558    
   559        /*!
   560         *  ======== print1 ========
   561         *  Generate a `Log` "print event" with 1 argument
   562         *
   563         *  @see #print6
   564         */
   565        @Macro Void print1(Diags.Mask mask, CString fmt, IArg a1);
   566    
   567        /*!
   568         *  ======== print2 ========
   569         *  Generate a `Log` "print event" with 2 arguments
   570         *
   571         *  @see #print6
   572         */
   573        @Macro Void print2(Diags.Mask mask, CString fmt, IArg a1, IArg a2);
   574    
   575        /*!
   576         *  ======== print3 ========
   577         *  Generate a `Log` "print event" with 3 arguments
   578         *
   579         *  @see #print6
   580         */
   581        @Macro Void print3(Diags.Mask mask, CString fmt, IArg a1, IArg a2,
   582            IArg a3);
   583    
   584        /*!
   585         *  ======== print4 ========
   586         *  Generate a `Log` "print event" with 4 arguments
   587         *
   588         *  @see #print6
   589         */
   590        @Macro Void print4(Diags.Mask mask, CString fmt, IArg a1, IArg a2,
   591            IArg a3, IArg a4);
   592    
   593        /*!
   594         *  ======== print5 ========
   595         *  Generate a `Log` "print event" with 5 arguments
   596         *
   597         *  @see #print6
   598         */
   599        @Macro Void print5(Diags.Mask mask, CString fmt, IArg a1, IArg a2, 
   600            IArg a3, IArg a4, IArg a5);
   601    
   602        /*!
   603         *  ======== print6 ========
   604         *  Generate a `Log` "print event" with 6 arguments
   605         *
   606         *  As a convenience to C (as well as assembly language) programmers,
   607         *  the `Log` module provides a variation of the ever-popular `printf`
   608         *  function.
   609         *  The `print[0-6]` functions generate a `Log` "print event" and route
   610         *  it to the current module's logger.
   611         *
   612         *  The arguments passed to `print[0-6]` may be characters, integers,
   613         *  strings, or pointers.  However, because the declared type of the
   614         *  arguments is `{@link xdc IArg}`, all pointer arguments must be cast
   615         *  to an `IArg` type.  `IArg` is an integral type large enough to hold
   616         *  any pointer or an `int`.  So, casting a pointer to an `IArg` does
   617         *  not cause any loss of information and C's normal integer conversions
   618         *  make the cast unnecessary for integral arguments.
   619         *
   620         *  The format string can use the following conversion characters.
   621         *  However, it is important to recall that all arguments referenced by
   622         *  these conversion characters have been converted to an `IArg`
   623         *  prior to conversion; so, the use of "length modifiers" should be
   624         *  avoided.
   625         *
   626         *  @p(code)
   627         *  Conversion Character    Description
   628         *  ------------------------------------------------
   629         *  %c                      Character
   630         *  %d                      Signed integer
   631         *  %u                      Unsigned integer
   632         *  %x                      Unsigned hexadecimal integer
   633         *  %o                      Unsigned octal integer
   634         *  %s                      Character string
   635         *  %p                      Pointer
   636         *  %f                      Single precision floating point (float)
   637         *  @p
   638         *
   639         *  Format strings, while very convenient, are a well known source of
   640         *  portability problems: each format specification must precisely match
   641         *  the types of the arguments passed. Underlying "printf" functions use
   642         *  the format string to determine how far to advance through their
   643         *  argument list. For targets where pointer types and integers are the
   644         *  same size there are no problems.  However, suppose a target's pointer
   645         *  type is larger than its integer type. In this case, because integer
   646         *  arguments are widened to be of type `IArg`, a format specification of
   647         *  "%d" causes an underlying `printf()` implementation to read the
   648         *  extended part of the integer argument as part of the next argument(!).
   649         *
   650         *  To get around this problem and still allow the use of "natural"
   651         *  format specifications (e.g., `%d` and `%x` with optional width
   652         *  specifications), `{@link System#aprintf()}` is used which assumes
   653         *  that all arguments have been widened to be of type `IArg`.
   654         *
   655         *  See `{@link System#printf}` for complete details.
   656         *
   657         *  The `%f` format specifier is used to print a single precision float
   658         *  value. Note that `%f` assumes that sizeof(Float) <= sizeof(IArg).
   659         *  Most clients that interpret float values expect that they are
   660         *  represented in IEEE 754 floating point format. Therefore, it is
   661         *  recommended that the float values be converted into that format prior
   662         *  to supplying the values to `Log` functions in cases where targets do
   663         *  not generate the float values in IEEE 754 floating point format by
   664         *  default.
   665         *
   666         *  The first argument to a `Log_print` call is the diags category to be
   667         *  associated with the event.
   668         *
   669         *  It is also possible to associate an event level with the event to
   670         *  enable filtering of events based on event level. Conceptually, it is
   671         *  best to regard the event level as completely separate from the event's
   672         *  diags category; however, the priority value actually occupies a part
   673         *  of the diags mask. For this reason, it is possible to specify an event
   674         *  level by OR'ing the level with the diags mask. For example, to print
   675         *  an `Diags_INFO` event of `Diags_LEVEL2`, you'd simply write:
   676         *  (Diags_INFO | Diags_LEVEL2)
   677         *
   678         *  Specifying an event level is optional. `Log_print` calls which do not
   679         *  specify a level will receive the highest priority by default.
   680         *
   681         *  @param(mask)    enable bits and optional detail level for this event
   682         *  @param(fmt)     a `printf` style format string
   683         *  @param(a1)      value for first format conversion character
   684         *  @param(a2)      value for second format conversion character
   685         *  @param(a3)      value for third format conversion character
   686         *  @param(a4)      value for fourth format conversion character
   687         *  @param(a5)      value for fifth format conversion character
   688         *  @param(a6)      value for sixth format conversion character
   689         *
   690         *  @a(Examples)
   691         *  The following example demonstrates a typical usage.
   692         *  @p(code)
   693         *  String  list[];
   694         *  UInt    i;
   695         *
   696         *  Log_print2(Diags_USER2, "list[%u] = %s\n", i, (IArg)list[i]);
   697         *  @p
   698         *  Note that the `IArg` cast above is only necessary for pointer
   699         *  arguments; C's normal parameter conversions implicitly convert
   700         *  integral arguments.
   701         *
   702         *  To simplify the conversion from `float` arguments to `IArg`,
   703         *  the standard header `xdc/std.h` provides a macro, named floatToArg(),
   704         *  to do this conversion in a type safe manner.  So, the following
   705         *  statement will print "`float = 2.3456`":
   706         *  @p(code)
   707         *    Log_print1(Diags_USER1, "float = %f", floatToArg(2.34567));
   708         *  @p
   709         *
   710         *  Note that, if you are formatting events on the target, you must
   711         *  also add support for floating point to ASCII conversion to
   712         *  `{@link System#printf}`; for more information, see the
   713         *  `{@link System#extendedFormats}` reference documenation.  For example:
   714         *  @p(code)
   715         *      var System = xdc.useModule('xdc.runtime.System');
   716         *      System.extendedFormats = "%f";
   717         *  @p
   718         */
   719        @Macro Void print6(Diags.Mask mask, CString fmt, IArg a1, IArg a2, 
   720            IArg a3, IArg a4, IArg a5, IArg a6);
   721    
   722        /*!
   723         *  ======== error0 ========
   724         *  Generate a `Log` "error event" with 0 arguments
   725         *
   726         *  @see #error5
   727         */
   728        @Macro Void error0(CString fmt);
   729    
   730        /*!
   731         *  ======== error1 ========
   732         *  Generate a `Log` "error event" with 1 argument
   733         *
   734         *  @see #error5
   735         */
   736        @Macro Void error1(CString fmt, IArg a1);
   737    
   738        /*!
   739         *  ======== error2 ========
   740         *  Generate a `Log` "error event" with 2 arguments
   741         *
   742         *  @see #error5
   743         */
   744        @Macro Void error2(CString fmt, IArg a1, IArg a2);
   745    
   746        /*!
   747         *  ======== error3 ========
   748         *  Generate a `Log` "error event" with 3 arguments
   749         *
   750         *  @see #error5
   751         */
   752        @Macro Void error3(CString fmt, IArg a1, IArg a2, IArg a3);
   753    
   754        /*!
   755         *  ======== error4 ========
   756         *  Generate a `Log` "error event" with 4 arguments
   757         *
   758         *  @see #error5
   759         */
   760        @Macro Void error4(CString fmt, IArg a1, IArg a2, IArg a3,
   761            IArg a4);
   762    
   763        /*!
   764         *  ======== error5 ========
   765         *  Generate a `Log` "error event" with 5 arguments
   766         *
   767         *  The Log_error APIs are intended to allow users to easily log error
   768         *  events in their code. Similar to the Log_print APIs, Log_error does not
   769         *  require that you define an event. You simply pass an informative error
   770         *  string which can optionally be formatted with additional arguments. The
   771         *  error is logged with the predefined event {@link #L_error}.
   772         *
   773         *  Log_error prepends a string to the message which identifies it as an
   774         *  ERROR and specifies the filename and line number of the Log_error call
   775         *  site. A simple example:
   776         *
   777         *  @p(code)
   778         *  Log_error0("Invalid argument");
   779         *  @p
   780         *  This event will be formatted as (assuming that the above call was line
   781         *  35 of "MyCode.c")
   782         *  @p(code)
   783         *  ERROR at "MyCode.c", line 35: Invalid argument
   784         *  @p
   785         *
   786         *  Users may provide additional information in the error event, such as
   787         *  a predefined error code or details of the error. These additional
   788         *  values will be used to format the string passed to Log_error.
   789         *  @see #print6 for information about format strings.
   790         *
   791         *  Log_error does not use a variable length argument list--you must call
   792         *  the appropriate Log_errorX API based on the number of arguments.
   793         *
   794         *  @param(fmt)      a reference to a constant error string / fmt string
   795         *  @param(a1)       value for an additional parameter (e.g. an error code)
   796         *  @param(a2)       value for an additional parameter
   797         *  @param(a3)       value for an additional parameter
   798         *  @param(a4)       value for an additional parameter
   799         *  @param(a5)       value for an additional parameter
   800         *
   801         *  @a(Examples)
   802         *  The following example demonstrates a typical usage.
   803         *  @p(code)
   804         *  Int myArg;
   805         *
   806         *  Log_error1("Invalid argument: %d", myArg);
   807         *  @p
   808         *  The above event is formatted as, for example:
   809         *  @p(code)
   810         *  ERROR: "MyCode.c", line 35: Invalid argument: -1
   811         *  @p
   812         */
   813        @Macro Void error5(CString fmt, IArg a1, IArg a2, IArg a3,
   814            IArg a4, IArg a5);
   815    
   816        /*!
   817         *  ======== warning0 ========
   818         *  Generate a `Log` "warning event" with 0 arguments
   819         *
   820         *  @see #warning5
   821         */
   822        @Macro Void warning0(CString fmt);
   823    
   824        /*!
   825         *  ======== warning1 ========
   826         *  Generate a `Log` "warning event" with 1 argument
   827         *
   828         *  @see #warning5
   829         */
   830        @Macro Void warning1(CString fmt, IArg a1);
   831    
   832        /*!
   833         *  ======== warning2 ========
   834         *  Generate a `Log` "warning event" with 2 arguments
   835         *
   836         *  @see #warning5
   837         */
   838        @Macro Void warning2(CString fmt, IArg a1, IArg a2);
   839    
   840        /*!
   841         *  ======== warning3 ========
   842         *  Generate a `Log` "warning event" with 3 arguments
   843         *
   844         *  @see #warning5
   845         */
   846        @Macro Void warning3(CString fmt, IArg a1, IArg a2, IArg a3);
   847    
   848        /*!
   849         *  ======== warning4 ========
   850         *  Generate a `Log` "warning event" with 4 arguments
   851         *
   852         *  @see #warning5
   853         */
   854        @Macro Void warning4(CString fmt, IArg a1, IArg a2, IArg a3,
   855            IArg a4);
   856    
   857        /*!
   858         *  ======== warning5 ========
   859         *  Generate a `Log` "warning event" with 5 arguments
   860         *
   861         *  The Log_warning APIs provide the same features as the Log_error APIs,
   862         *  but are used to specifically log "warning" events.
   863         *  @see #error5
   864         *
   865         *  The Log_warning APIs are equivalent to the Log_error APIs except that
   866         *  they use the predefined {@link #L_warning} event. Log_warning prepends
   867         *  a string to the message which identifies it as a WARNING and specifies
   868         *  the filename and line number of the Log_warning call site.
   869         *
   870         *  @param(fmt)     reference to a constant warning string / fmt string
   871         *  @param(a1)      value for an additional parameter (e.g. a warning code)
   872         *  @param(a2)      value for an additional parameter
   873         *  @param(a3)      value for an additional parameter
   874         *  @param(a4)      value for an additional parameter
   875         *  @param(a5)      value for an additional parameter
   876         *
   877         *  @a(Examples)
   878         *  The following example demonstrates a typical usage.
   879         *  @p(code)
   880         *  Int myArg;
   881         *
   882         *  Log_warning1("Value may be too high: %d", myArg);
   883         *  @p
   884         *  The above event is formatted as:
   885         *  @p(code)
   886         *  WARNING: "MyCode.c", line 50: Value may be too high: 4096
   887         *  @p
   888         */
   889        @Macro Void warning5(CString fmt, IArg a1, IArg a2, IArg a3,
   890            IArg a4, IArg a5);      
   891            
   892        /*!
   893         *  ======== info0 ========
   894         *  Generate a `Log` "info event" with 0 arguments
   895         *
   896         *  @see #info5
   897         */
   898        @Macro Void info0(CString fmt);
   899    
   900        /*!
   901         *  ======== info1 ========
   902         *  Generate a `Log` "info event" with 1 argument
   903         *
   904         *  @see #info5
   905         */
   906        @Macro Void info1(CString fmt, IArg a1);
   907    
   908        /*!
   909         *  ======== info2 ========
   910         *  Generate a `Log` "info event" with 2 arguments
   911         *
   912         *  @see #info5
   913         */
   914        @Macro Void info2(CString fmt, IArg a1, IArg a2);
   915    
   916        /*!
   917         *  ======== info3 ========
   918         *  Generate a `Log` "info event" with 3 arguments
   919         *
   920         *  @see #info5
   921         */
   922        @Macro Void info3(CString fmt, IArg a1, IArg a2, IArg a3);
   923    
   924        /*!
   925         *  ======== info4 ========
   926         *  Generate a `Log` "info event" with 4 arguments
   927         *
   928         *  @see #info5
   929         */
   930        @Macro Void info4(CString fmt, IArg a1, IArg a2, IArg a3, IArg a4);
   931    
   932        /*!
   933         *  ======== info5 ========
   934         *  Generate a `Log` "info event" with 5 arguments
   935         *
   936         *  The Log_info APIs are provided for easily logging generic
   937         *  "informational" events with call site information. They are similar to
   938         *  the Log_print APIs in that they do not require you to define an event--
   939         *  you simply pass an informative printf-style string which can optionally
   940         *  be formatted with additional arguments. The info record is logged with
   941         *  the predefined event '{@link #L_info}'.
   942         *
   943         *  The Log_info APIs log the {@link #L_info} event which uses the 'INFO'
   944         *  diags category. They do not allow you to specify an event priority.
   945         *
   946         *  Log_info prepends the filename and line number of the call site to the
   947         *  message.
   948         *
   949         *  @param(fmt)     reference to a constant event string / fmt string
   950         *  @param(a1)      value for an additional parameter (e.g. an event code)
   951         *  @param(a2)      value for an additional parameter
   952         *  @param(a3)      value for an additional parameter
   953         *  @param(a4)      value for an additional parameter
   954         *  @param(a5)      value for an additional parameter
   955         *
   956         *  @a(Examples)
   957         *  The following example demonstrates a typical usage.
   958         *  @p(code)
   959         *  Int load;
   960         *
   961         *  Log_info1("Current load: %d", load);
   962         *  @p
   963         *  The above event is formatted as, for example:
   964         *  @p(code)
   965         *  "MyCode.c", line 15: Current load: 25
   966         *  @p
   967         */
   968        @Macro Void info5(CString fmt, IArg a1, IArg a2, IArg a3, IArg a4,
   969            IArg a5);    
   970                      
   971         /*!
   972         *  ======== put0 ========
   973         *  Unconditionally put the specified Log event with 0 arguments
   974         *
   975         *  @see #put8
   976         */
   977        @Macro Void put0(Log.Event evt, Types.ModuleId mid);
   978    
   979        /*!
   980         *  ======== put1 ========
   981         *  Unconditionally put the specified Log event and 1 argument
   982         *
   983         *  @see #put8
   984         */
   985        @Macro Void put1(Log.Event evt, Types.ModuleId mid, IArg a1);
   986    
   987        /*!
   988         *  ======== put2 ========
   989         *  Unconditionally put the specified Log event and 2 arguments
   990         *
   991         *  @see #put8
   992         */
   993         @Macro Void put2(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2);
   994    
   995        /*!
   996         *  ======== put4 ========
   997         *  Unconditionally put the specified Log event and 4 arguments
   998         *
   999         *  @see #put8
  1000         */
  1001        @Macro Void put4(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2,
  1002                         IArg a3, IArg a4);
  1003    
  1004        /*!
  1005         *  ======== put8 ========
  1006         *  Unconditionally put the specified Log event and 8 arguments
  1007         *
  1008         *  This method unconditionally puts the specified `{@link Event}`
  1009         *  `evt` into the log. The `{@link Types#ModuleId}` `mid` should be the
  1010         *  module ID of the module which is putting the event.
  1011         *
  1012         *  @param(evt)     the Log event to put into the log
  1013         *  @param(mid)     module ID of the module putting the event
  1014         *  @param(a1)      value for first format conversion character
  1015         *  @param(a2)      value for second format conversion character
  1016         *  @param(a3)      value for third format conversion character
  1017         *  @param(a4)      value for fourth format conversion character
  1018         *  @param(a5)      value for fifth format conversion character
  1019         *  @param(a6)      value for sixth format conversion character
  1020         *  @param(a7)      value for seventh format conversion character
  1021         *  @param(a8)      value for eighth format conversion character
  1022         */
  1023        @Macro Void put8(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2,
  1024                         IArg a3, IArg a4, IArg a5, IArg a6, IArg a7, IArg a8);
  1025    
  1026        /*!
  1027         *  ======== write0 ========
  1028         *  Generate a `Log` event with 0 arguments
  1029         *
  1030         *  @see #write8
  1031         */
  1032        @Macro Void write0(Event evt);
  1033    
  1034        /*!
  1035         *  ======== write1 ========
  1036         *  Generate a `Log` event with 1 argument
  1037         *
  1038         *  @see #write8
  1039         */
  1040        @Macro Void write1(Event evt, IArg a1);
  1041    
  1042        /*!
  1043         *  ======== write2 ========
  1044         *  Generate a `Log` event with 2 arguments
  1045         *
  1046         *  @see #write8
  1047         */
  1048        @Macro Void write2(Event evt, IArg a1, IArg a2);
  1049    
  1050        /*!
  1051         *  ======== write3 ========
  1052         *  Generate a `Log` event with 3 arguments
  1053         *
  1054         *  @see #write8
  1055         */
  1056        @Macro Void write3(Event evt, IArg a1, IArg a2, IArg a3);
  1057    
  1058        /*!
  1059         *  ======== write4 ========
  1060         *  Generate a `Log` event with 4 arguments
  1061         *
  1062         *  @see #write8
  1063         */
  1064        @Macro Void write4(Event evt, IArg a1, IArg a2, IArg a3, IArg a4);
  1065    
  1066        /*!
  1067         *  ======== write5 ========
  1068         *  Generate a `Log` event with 5 arguments
  1069         *
  1070         *  @see #write8
  1071         */
  1072        @Macro Void write5(Event evt, IArg a1, IArg a2, IArg a3, IArg a4, IArg a5);
  1073    
  1074        /*!
  1075         *  ======== write6 ========
  1076         *  Generate a `Log` event with 6 arguments
  1077         *
  1078         *  @see #write8
  1079         */
  1080        @Macro Void write6(Event evt, IArg a1, IArg a2, IArg a3, IArg a4,
  1081                            IArg a5, IArg a6);
  1082    
  1083        /*!
  1084         *  ======== write7 ========
  1085         *  Generate a `Log` event with 7 arguments
  1086         *
  1087         *  @see #write8
  1088         */
  1089        @Macro Void write7(Event evt, IArg a1, IArg a2, IArg a3, IArg a4,
  1090                            IArg a5, IArg a6, IArg a7);
  1091    
  1092        /*!
  1093         *  ======== write8 ========
  1094         *  Generate a `Log` event with 8 arguments
  1095         *
  1096         *  If the mask in the specified `Log` event has any bit set which is
  1097         *  also set in the current module's diagnostics mask, then this call to
  1098         *  write will "raise" the given `Log` event.
  1099         *
  1100         *  @param(evt)     the `Log` event to write
  1101         *  @param(a1)      value for first format conversion character
  1102         *  @param(a2)      value for second format conversion character
  1103         *  @param(a3)      value for third format conversion character
  1104         *  @param(a4)      value for fourth format conversion character
  1105         *  @param(a5)      value for fifth format conversion character
  1106         *  @param(a6)      value for sixth format conversion character
  1107         *  @param(a7)      value for seventh format conversion character
  1108         *  @param(a8)      value for eighth format conversion character
  1109         */
  1110        @Macro Void write8(Event evt, IArg a1, IArg a2, IArg a3, IArg a4,
  1111                            IArg a5, IArg a6, IArg a7, IArg a8);
  1112    
  1113        /*!
  1114         *  ======== doPrint ========
  1115         *  Render an event as text via `{@link System#printf System_printf}`
  1116         *
  1117         *  This method is not gated and may make more than one call to
  1118         *  `System_printf`.  This utility method is typically used within the
  1119         *  implementation of a logger which initializes
  1120         *  `{@link #EventRec Log_EventRec}` structures based on `Log` events
  1121         *  produced by the application.
  1122         *
  1123         *  @param(evRec)   a non`NULL` pointer to an initialized `Log_EventRec`
  1124         *                  structure to be formated via
  1125         *                  `{@link System#printf System_printf}`.
  1126         */
  1127        Void doPrint(EventRec *evRec);
  1128    
  1129        /*!
  1130         *  @_nodoc
  1131         *  ======== lookupEventMessage ========
  1132         *  Returns the format string for the event with the given id.
  1133         */
  1134        function lookupEventMessage(eventId);
  1135    
  1136        /*!
  1137         *  @_nodoc
  1138         *  ======== getTargetArgSize ========
  1139         *  Returns the target size of a record argument in bytes (not MAUs).
  1140         */
  1141        function getTargetArgSize();
  1142    
  1143        /*!
  1144         *  @_nodoc
  1145         *  ======== lookupEventName ========
  1146         */
  1147        function lookupEventName(eventId);
  1148    
  1149        /*!
  1150         *  @_nodoc
  1151         *  ======== lookupModuleName ========
  1152         */
  1153        function lookupModuleName(modId);
  1154    
  1155        /*!
  1156         *  @_nodoc
  1157         *  ======== getTargetEventRecSize ========
  1158         *  Returns the record size in bytes (not MAUs).
  1159         */
  1160        function getTargetEventRecSize();
  1161    
  1162    internal:
  1163    
  1164        /*
  1165         *  ======== idToInfo ========
  1166         *  Map event ID strings into a string of the form <eventName>::<eventMsg>
  1167         */
  1168        metaonly config String idToInfo[string] = [];
  1169    }
  1170    /*
  1171     *  @(#) xdc.runtime; 2, 1, 0,0; 7-26-2016 11:46:14; /db/ztree/library/trees/xdc/xdc-B21/src/packages/
  1172     */
  1173