| /* --COPYRIGHT--,ESD |
| * Copyright (c) 2008 Texas Instruments. All rights reserved. |
| * This program and the accompanying materials are made available under the |
| * terms of the Eclipse Public License v1.0 and Eclipse Distribution License |
| * v. 1.0 which accompanies this distribution. The Eclipse Public License is |
| * available at http://www.eclipse.org/legal/epl-v10.html and the Eclipse |
| * Distribution License is available at |
| * http://www.eclipse.org/org/documents/edl-v10.php. |
| * |
| * Contributors: |
| * Texas Instruments - initial implementation |
| * --/COPYRIGHT--*/ |
| /* |
| * ======== Log.xdc ======== |
| */ |
| |
| /*! |
| * ======== Log ======== |
| * Event logging manager |
| * |
| * RTSC modules and the application code generate `{@link #Event Log_Event}` |
| * events by calling the `Log` module's functions. The `Log` module then |
| * passes those events to an `{@link ILogger}` instance assigned to the event |
| * originating module, specified by that module's configuration parameter |
| * `common$.logger`. `ILogger` instances handle events, usually converting |
| * events to `{@link #EventRec Log_EventRec}` records prior to recording, |
| * transmitting, or displaying them. |
| * |
| * All events generated by a target module are stored and displayed by an |
| * `ILogger`, examples of which are instances of |
| * `{@link LoggerBuf xdc.runtime.LoggerBuf}` or |
| * `{@link LoggerSys xdc.runtime.LoggerSys}`. At runtime, modules |
| * generate events through this module, rather than invoking directly their |
| * `ILogger`s. By doing so, modules can be configured to use different |
| * `ILogger` implementations without any changes to their source code. |
| * |
| * A logger instance can accept `Log` events from any module, but a module |
| * can put `Log` events to only one logger instance. There can be one or |
| * more logger instances in a system. All `Log` calls that are not in a |
| * module are controlled by the module `{@link Main xdc.runtime.Main}`. |
| * For example, top-level application code or any existing sources that |
| * simply call the `Log` or `Assert` methods implicitly use the logger |
| * associated with the `Main` module. |
| * |
| * The generation of a `Log` event is controlled by a module's diagnostics |
| * mask, which is described in details in `{@link Diags}`. Each `Log` event |
| * is associated with a mask. `Log` events are generated only when a |
| * particular bit is set in both the `Log` event mask and the module's |
| * diagnostics mask. For example, a `Log` event mask with the |
| * `{@link Diags#USER1 USER1}` bit set is generated only when the `USER1` |
| * bit is also set in the module's diagnostics mask. |
| * |
| * There are two ways to generate `Log` events: |
| * |
| * @p(blist) |
| * - `{@link #write8 Log_write()}`, which is tailored for module writers |
| * and takes full advantage of the XDC configuration model. For example, |
| * the message string associated with the `Log` event need not be a part of |
| * the final application, significantly reducing the "footprint overhead" |
| * of embedding diagnostics in deployed systems. The `Log_write[0-8]()` |
| * functions allow up to 8 values to be passed to the logger. They expect |
| * the logger to handle any formatting. A `Log` event type allows you to |
| * specify the type of event. |
| * - `{@link #print6 Log_print()}`, which is designed for arbitrary C code. |
| * The `Log_print[0-6]()` functions allow up to 6 values to be passed along |
| * with a printf-like format string to the logger. They handle printf-style |
| * formatting. |
| * @p |
| * |
| * Both functions are controlled by the module's diagnostics mask. Their |
| * storage or output is defined by the logger that is assigned to the |
| * module that calls the `Log` methods or to the |
| * `{@link Main xdc.runtime.Main}` module if the caller is not part of a |
| * module. |
| * |
| * The `Log` function call sites are implemented in such a way that an |
| * optimizer can completely eliminate `Log` code from the program if the |
| * `Log` functions have been permanently disabled at configuration time. If |
| * the `Log` functions are permanently turned on at configuration time, |
| * then the optimizer can eliminate all runtime conditional checking and |
| * simply invoke the `Log` functions directly. Runtime checking is performed |
| * only when the `Log` functions are configured to be runtime modifiable. |
| * |
| * The Log calls can also be completely removed by defining the symbol |
| * `xdc_runtime_Log_DISABLE_ALL`. This can be done on the compile line, e.g. |
| * `-Dxdc_runtime_Log_DISABLE_ALL`. This will completely remove the `Log` |
| * statements from any code compiled with this flag, regardless of the |
| * application's logging configuration or your compiler's optimization |
| * settings. |
| * |
| * It is also possible to remove all logging except for |
| * `{@link #error Log_error}`, `{@link #warning Log_warning}`, or |
| * `{@link #info Log_info}` statements. This is done by first defining |
| * `xdc_runtime_Log_DISABLE_ALL`, followed by defining one or more of the |
| * symbols below to leave that type of logging enabled: |
| * @p(blist) |
| * - `xdc_runtime_Log_ENABLE_ERROR` |
| * - `xdc_runtime_Log_ENABLE_WARNING` |
| * - `xdc_runtime_Log_ENABLE_INFO` |
| * @p |
| * For example, to disable all `Log` statements except for `Log_error`, add |
| * the following to the compile line: |
| * @p(code) |
| * -Dxdc_runtime_Log_DISABLE_ALL -Dxdc_runtime_Log_ENABLE_ERROR |
| * @p |
| * |
| * @a(Examples) |
| * Example 1: The following example defines a `Log` event, uses that `Log` |
| * event in a module, and configures the program to generate the `Log` |
| * event. In this example, both `USER1` and `USER2` bits are set in the |
| * event mask. This means that if either bit is set in the module's |
| * diagnostics mask, then the `Log` event will be generated. |
| * |
| * This is a part of the XDC specification file for the `Mod` module |
| * (Mod.xdc): |
| * |
| * @p(code) |
| * import xdc.runtime.Diags; |
| * import xdc.runtime.Log; |
| * |
| * config Log.Event L_someEvent = { |
| * mask: Diags.USER1 | Diags.USER2, |
| * level: Diags.LEVEL1, |
| * msg: "my log event message, arg1: 0x%x, arg2: 0x%x" |
| * }; |
| * @p |
| * |
| * This is a part of the C code implementation of the Mod module: |
| * |
| * @p(code) |
| * #include <xdc/runtime/Log.h> |
| * UInt x, y; |
| * |
| * Log_write2(Mod_L_someEvent, (IArg)x, (IArg)y); |
| * @p |
| * |
| * The following configuration script demonstrates how the application might |
| * control the `Log` statements embedded in the `Mod` module at configuration |
| * time. In this case, the configuration script arranges for the `Log` |
| * statements within the `Mod` module (shown above) to always generate events. |
| * Without these configuration statements, no `Log` events would be generated |
| * by this module. |
| * |
| * This is part of the XDC configuration file for the application: |
| * |
| * @p(code) |
| * var Diags = xdc.useModule('xdc.runtime.Diags'); |
| * var LoggerSys = xdc.useModule('xdc.runtime.LoggerSys'); |
| * var Mod = xdc.useModule('my.pkg.Mod'); |
| * Mod.common$.diags_USER1 = Diags.ALWAYS_ON; |
| * Mod.common$.logger = LoggerSys.create(); |
| * @p |
| * |
| * @p(html) |
| * <hr /> |
| * @p |
| * |
| * Example 2: The following XDC configuration statements turn on enter |
| * and exit logging at configuration time for a module. Without any other |
| * changes in the runtime code, every time a module `Mod`'s function is |
| * being called or exits, an event will be logged. |
| * |
| * @p(code) |
| * var Diags = xdc.useModule('xdc.runtime.Diags'); |
| * var Mod = xdc.useModule('my.pkg.Mod'); |
| * |
| * Mod.common$.diags_ENTER = Diags.ALWAYS_ON; |
| * Mod.common$.diags_EXIT = Diags.ALWAYS_ON; |
| * @p |
| * |
| * @p(html) |
| * <hr /> |
| * @p |
| * |
| * Example 3: The following example configures a module to support enter and |
| * exit logging, but defers the actual activation and deactivation of the |
| * logging until runtime. See the `{@link Diags#setMask Diags_setMask()}` |
| * function for details on specifying the control string. |
| * |
| * This is a part of the XDC configuration file for the application: |
| * |
| * @p(code) |
| * var Diags = xdc.useModule('xdc.runtime.Diags'); |
| * var Mod = xdc.useModule('my.pkg.Mod'); |
| * |
| * Mod.common$.diags_ENTER = Diags.RUNTIME_OFF; |
| * Mod.common$.diags_EXIT = Diags.RUNTIME_OFF; |
| * @p |
| * |
| * This is a part of the C code for the application: |
| * |
| * @p(code) |
| * // turn on enter and exit logging in the module |
| * Diags_setMask("my.pkg.Mod+EX"); |
| * |
| * // turn off enter and exit logging in the module |
| * Diags_setMask("my.pkg.Mod-EX"); |
| * @p |
| */ |
| |
| @CustomHeader |
| @DirectCall |
| |
| module Log { |
| |
| /*! |
| * ======== NUMARGS ======== |
| * Maximum number of arguments supported in `Log` events. |
| */ |
| const Int NUMARGS = 8; |
| |
| /*! |
| * ======== PRINTFID ======== |
| * The `EventId` for `Log_print()` events |
| */ |
| const EventId PRINTFID = 0; |
| |
| /*! |
| * ======== EventDesc ======== |
| * `Log` event descriptor |
| * |
| * Each `Log` event is defined by a `Log` event descriptor. |
| * |
| * The `mask` defines which bits in the module's diagnostics mask |
| * enable this `Log` event. Events "posted" via `Log_write` are only |
| * written to the underlying logger if one of the mask's bits matches |
| * the caller's module diagnostics settings (see |
| * `{@link xdc.runtime.Types#common$}`). |
| * |
| * The 'level' defines the event level of the event. While the diags |
| * bits selected in the 'mask' signify the "category" of the event (e.g. |
| * Entry/Exit, Analysis, Info), the 'level' field allows you to assign |
| * a "priority" or "detail level" to the event relative to other events in |
| * that category. There are four event levels defined by |
| * '{@link xdc.runtime.Diags#EventLevel}'. |
| * |
| * Filtering of events by level is handled by the ILogger implementation. |
| * ILogger implementations which also implement the {@link IFilterLogger} |
| * interface support filtering of events based on priority level. |
| * |
| * Specifying an event level is optional. Events that don't specify a |
| * level will receive Diags.LEVEL1 by default, making them the highest |
| * priority and ensuring that they will not inadvertently be filtered out |
| * by level-based filtering. |
| * |
| * The `msg` defines a printf style format string that defines how to |
| * render the arguments passed along the event in a `Log_write` call. |
| * For a description of the allowable format strings see |
| * `{@link #print6}`. |
| * |
| * @see #write8 |
| * @see #print6 |
| */ |
| metaonly struct EventDesc { |
| Diags.Mask mask; /*! event enable mask */ |
| Diags.EventLevel level; /*! event level relative to other events */ |
| String msg; /*! event "printf" message format string */ |
| }; |
| |
| /*! |
| * ======== EventRec ======== |
| * The target representation of a recorded event |
| * |
| * This structure defines how events are recorded on the target. |
| */ |
| struct EventRec { |
| Types.Timestamp64 tstamp; /*! time event was written */ |
| Bits32 serial; /*! serial number of event */ |
| Types.Event evt; /*! target encoding of an Event */ |
| IArg arg[NUMARGS]; /*! arguments passed via Log_write/print */ |
| } |
| |
| /*! |
| * ======== Event ======== |
| * `Log` event type |
| * |
| * An `Event` is represented on the target as a 32-bit value that can |
| * be decoded offline to recover the `Event` information defined in |
| * a corresponding metaonly `EventDesc`. In addition, `Event`s may be |
| * decoded at runtime via methods provided in this module; see |
| * `{@link #getMask}` and `{@link #getEventId}`. |
| * |
| * When an event is "raised" a `{@link Types#Event Types_Event}` is |
| * created which has the same event ID as the `Log_Event` but also |
| * encodes the module ID of the caller. This new event is passed to |
| * the underlying `{@link ILogger}` module along with any arguments |
| * associated with the event. |
| * |
| * @see #getMask |
| * @see #getEventId |
| */ |
| @Encoded typedef EventDesc Event; |
| |
| /*! |
| * ======== EventId ======== |
| * Unique ID embedded in each `{@link #Event}` |
| * |
| * This ID must be used to compare two `Event`s for equality. Event |
| * ids are not guaranteed to remain constant between different |
| * configurations of an application. For example, adding a module |
| * may cause the event ids of another module to change. |
| * |
| * However, event ids declared by a module are guaranteed to be |
| * consecutive values starting from the first declared |
| * `{@link #Event Log_Event}` and increasing to the last declared |
| * event. As a result, clients of a module can efficiently test ranges |
| * of events and modules can add new events, such as internal trace |
| * events, without breaking clients; simply be careful to add new events |
| * after any existing events in you module's `.xdc` specification. |
| * |
| * @see #getEventId |
| * @see #Event |
| */ |
| typedef Types.RopeId EventId; |
| |
| /*! |
| * ======== L_construct ======== |
| * Lifecycle event posted when an instance is constructed |
| */ |
| config Log.Event L_construct = { |
| mask: Diags.LIFECYCLE, |
| msg: "<-- construct: %p('%s')" |
| }; |
| |
| /*! |
| * ======== L_create ======== |
| * Lifecycle event posted when an instance is created |
| */ |
| config Log.Event L_create = { |
| mask: Diags.LIFECYCLE, |
| msg: "<-- create: %p('%s')" |
| }; |
| |
| /*! |
| * ======== L_destruct ======== |
| * Lifecycle event posted when an instance is destructed |
| */ |
| config Log.Event L_destruct = { |
| mask: Diags.LIFECYCLE, |
| msg: "--> destruct: (%p)" |
| }; |
| |
| /*! |
| * ======== L_delete ======== |
| * Lifecycle event posted when an instance is deleted |
| */ |
| config Log.Event L_delete = { |
| mask: Diags.LIFECYCLE, |
| msg: "--> delete: (%p)" |
| }; |
| |
| /*! |
| * ======== L_error ======== |
| * Error event posted by Log_errorX API |
| * |
| * This event is marked as a STATUS event and given the priority level |
| * of ERROR. |
| * |
| * This event prints the Log call site (%$F) and a format string (%$S) |
| * which is recursively formatted with any additional arguments. |
| */ |
| config Log.Event L_error = { |
| mask: Diags.STATUS, |
| level: Diags.ERROR, |
| msg: "ERROR: %$F%$S" |
| }; |
| |
| /*! |
| * ======== L_warning ======== |
| * Warning event posted by Log_warningX API |
| * |
| * This event is marked as a STATUS event and given the priority level of |
| * WARNING. |
| * |
| * This event prints the Log call site (%$F) and a format string (%$S) |
| * which is recursively formatted with any addition arguments. |
| */ |
| config xdc.runtime.Log.Event L_warning = { |
| mask: Diags.STATUS, |
| level: Diags.WARNING, |
| msg: "WARNING: %$F%$S" |
| }; |
| |
| /*! |
| * ======== L_info ======== |
| * Info event posted by Log_infoX API |
| * |
| * This event is marked as an INFO event. The event priority is not |
| * specified in the event definition. Rather, it is specified as an |
| * argument to the Log_infoX APIs. |
| * |
| * This event prints the Log call site (%$F) and a format string (%$S) |
| * which is recursively formatted with any addition arguments. |
| */ |
| config xdc.runtime.Log.Event L_info = { |
| mask: Diags.INFO, |
| msg: "%$F%$S" |
| }; |
| |
| /*! |
| * ======== L_start ======== |
| * Benchmark event used to log the start of an operation |
| * @_nodoc |
| * |
| * @a(Example) |
| * The following C code shows how to log a simple |
| * benchmark 'start' event along with a user-specified |
| * format string describing the event. |
| * |
| * @p(code) |
| * #include <xdc/runtime/Log.h> |
| * ... |
| * Log_write2(Log_L_start, (IArg)"My benchmark event", (IArg)myUniqueId); |
| * Log_write2(Log_L_stop, (IArg)"My benchmark event", (IArg)myUniqueId); |
| * @p |
| * |
| * @param(fmt) a constant string that provides format specifiers for |
| * up to 6 additional parameters |
| * @param(id) a unique ID used to match benchmark start and stop |
| * events |
| */ |
| config xdc.runtime.Log.Event L_start = { |
| mask: Diags.ANALYSIS, |
| msg: "Start: %$S"}; |
| |
| /*! |
| * ======== L_stop ======== |
| * Benchmark event used to log the end of an operation |
| * @_nodoc |
| * |
| * @a(Example) |
| * The following C code shows how to log a simple |
| * benchmark 'stop' event along with a user-specified |
| * format string describing the event. |
| * |
| * @p(code) |
| * #include <xdc/runtime/Log.h> |
| * ... |
| * Log_write2(Log_L_start, (IArg)"My benchmark event", (IArg)myUniqueId); |
| * Log_write2(Log_L_stop, (IArg)"My benchmark event", (IArg)myUniqueId); |
| * @p |
| * |
| * @param(fmt) a constant string that provides format specifiers for |
| * up to 6 additional parameters |
| * @param(id) a unique ID used to match benchmark start and stop |
| * events |
| */ |
| config xdc.runtime.Log.Event L_stop = { |
| mask: Diags.ANALYSIS, |
| msg: "Stop: %$S"}; |
| |
| /*! |
| * ======== L_startInstance ======== |
| * Benchmark event used to log the start of an operation instance |
| * @_nodoc |
| * |
| * Event parameter provides instance data to differentiate |
| * between multiple instances that can run in parallel. |
| * |
| * @a(Example) |
| * The following C code shows how to log a benchmark |
| * 'startInstance' event along with a user-specified |
| * instance identifier and a format string describing the event. |
| * |
| * @p(code) |
| * #include <xdc/runtime/Log.h> |
| * ... |
| * Log_write3(Log_L_startInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId); |
| * ... |
| * Log_write3(Log_L_stopInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId); |
| * @p |
| * |
| * @param(fmt) a constant string that provides format specifiers for |
| * up to 6 additional parameters |
| * @param(id) a unique ID used to match benchmark start and stop |
| * events |
| * @param(instId) a unique instance ID that can be used to match |
| * instance events |
| */ |
| config xdc.runtime.Log.Event L_startInstance = { |
| mask: Diags.ANALYSIS, |
| msg: "StartInstance: %$S" |
| }; |
| |
| /*! |
| * ======== L_stopInstance ======== |
| * Benchmark event used to log the end of an operation instance |
| * @_nodoc |
| * |
| * Event parameter provides instance data to differentiate |
| * between multiple instances that can run in parallel. |
| * |
| * @a(Example) |
| * The following C code shows how to log a benchmark |
| * 'stopInstance' event along with a user-specified |
| * instance identifier and a format string describing the event. |
| * |
| * @p(code) |
| * #include <xdc/runtime/Log.h> |
| * ... |
| * Log_write3(Log_L_startInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId); |
| * ... |
| * Log_write3(Log_L_stopInstance, (IArg)"My benchmark event", (IArg)uniqueId, (IArg)instId); |
| * @p |
| * |
| * @param(fmt) a constant string that provides format specifiers for |
| * up to 6 additional parameters |
| * @param(id) a unique ID used to match benchmark start and stop |
| * events |
| * @param(instId) a unique instance ID that can be used to match |
| * instance events |
| */ |
| config xdc.runtime.Log.Event L_stopInstance = { |
| mask: Diags.ANALYSIS, |
| msg: "StopInstance: %$S" |
| }; |
| |
| /*! |
| * ======== getMask ======== |
| * Get the `Diags` mask for the specified (encoded) event |
| * |
| * @param(evt) the `Log` event encoding a mask and event ID |
| * |
| * @a(returns) `Diags` mask for the specified event |
| */ |
| @Macro Diags.Mask getMask(Event evt); |
| |
| /*! |
| * ======== getRope ======== |
| * Get RopeId of the Event.msg for the specified (encoded) event |
| * @_nodoc |
| */ |
| @Macro Text.RopeId getRope(Event evt); |
| |
| /*! |
| * ======== getEventId ======== |
| * Get event ID of the specified (encoded) event |
| * |
| * This method is used to compare "known" `Log` events with |
| * "raised" `{@link Types#Event Types_Event}`. |
| * |
| * @param(evt) the `Log` event encoding a mask and event ID |
| * |
| * @a(returns) event ID of the specified event |
| * |
| * @see Types#getEventId |
| */ |
| @Macro EventId getEventId(Event evt); |
| |
| /*! |
| * ======== print0 ======== |
| * Generate a `Log` "print event" with 0 arguments |
| * |
| * @see #print6 |
| */ |
| @Macro Void print0(Diags.Mask mask, CString fmt); |
| |
| /*! |
| * ======== print1 ======== |
| * Generate a `Log` "print event" with 1 argument |
| * |
| * @see #print6 |
| */ |
| @Macro Void print1(Diags.Mask mask, CString fmt, IArg a1); |
| |
| /*! |
| * ======== print2 ======== |
| * Generate a `Log` "print event" with 2 arguments |
| * |
| * @see #print6 |
| */ |
| @Macro Void print2(Diags.Mask mask, CString fmt, IArg a1, IArg a2); |
| |
| /*! |
| * ======== print3 ======== |
| * Generate a `Log` "print event" with 3 arguments |
| * |
| * @see #print6 |
| */ |
| @Macro Void print3(Diags.Mask mask, CString fmt, IArg a1, IArg a2, |
| IArg a3); |
| |
| /*! |
| * ======== print4 ======== |
| * Generate a `Log` "print event" with 4 arguments |
| * |
| * @see #print6 |
| */ |
| @Macro Void print4(Diags.Mask mask, CString fmt, IArg a1, IArg a2, |
| IArg a3, IArg a4); |
| |
| /*! |
| * ======== print5 ======== |
| * Generate a `Log` "print event" with 5 arguments |
| * |
| * @see #print6 |
| */ |
| @Macro Void print5(Diags.Mask mask, CString fmt, IArg a1, IArg a2, |
| IArg a3, IArg a4, IArg a5); |
| |
| /*! |
| * ======== print6 ======== |
| * Generate a `Log` "print event" with 6 arguments |
| * |
| * As a convenience to C (as well as assembly language) programmers, |
| * the `Log` module provides a variation of the ever-popular `printf` |
| * function. |
| * The `print[0-6]` functions generate a `Log` "print event" and route |
| * it to the current module's logger. |
| * |
| * The arguments passed to `print[0-6]` may be characters, integers, |
| * strings, or pointers. However, because the declared type of the |
| * arguments is `{@link xdc IArg}`, all pointer arguments must be cast |
| * to an `IArg` type. `IArg` is an integral type large enough to hold |
| * any pointer or an `int`. So, casting a pointer to an `IArg` does |
| * not cause any loss of information and C's normal integer conversions |
| * make the cast unnecessary for integral arguments. |
| * |
| * The format string can use the following conversion characters. |
| * However, it is important to recall that all arguments referenced by |
| * these conversion characters have been converted to an `IArg` |
| * prior to conversion; so, the use of "length modifiers" should be |
| * avoided. |
| * |
| * @p(code) |
| * Conversion Character Description |
| * ------------------------------------------------ |
| * %c Character |
| * %d Signed integer |
| * %u Unsigned integer |
| * %x Unsigned hexadecimal integer |
| * %o Unsigned octal integer |
| * %s Character string |
| * %p Pointer |
| * %f Single precision floating point (float) |
| * @p |
| * |
| * Format strings, while very convenient, are a well known source of |
| * portability problems: each format specification must precisely match |
| * the types of the arguments passed. Underlying "printf" functions use |
| * the format string to determine how far to advance through their |
| * argument list. For targets where pointer types and integers are the |
| * same size there are no problems. However, suppose a target's pointer |
| * type is larger than its integer type. In this case, because integer |
| * arguments are widened to be of type `IArg`, a format specification of |
| * "%d" causes an underlying `printf()` implementation to read the |
| * extended part of the integer argument as part of the next argument(!). |
| * |
| * To get around this problem and still allow the use of "natural" |
| * format specifications (e.g., `%d` and `%x` with optional width |
| * specifications), `{@link System#aprintf()}` is used which assumes |
| * that all arguments have been widened to be of type `IArg`. |
| * |
| * See `{@link System#printf}` for complete details. |
| * |
| * The `%f` format specifier is used to print a single precision float |
| * value. Note that `%f` assumes that sizeof(Float) <= sizeof(IArg). |
| * Most clients that interpret float values expect that they are |
| * represented in IEEE 754 floating point format. Therefore, it is |
| * recommended that the float values be converted into that format prior |
| * to supplying the values to `Log` functions in cases where targets do |
| * not generate the float values in IEEE 754 floating point format by |
| * default. |
| * |
| * The first argument to a `Log_print` call is the diags category to be |
| * associated with the event. |
| * |
| * It is also possible to associate an event level with the event to |
| * enable filtering of events based on event level. Conceptually, it is |
| * best to regard the event level as completely separate from the event's |
| * diags category; however, the priority value actually occupies a part |
| * of the diags mask. For this reason, it is possible to specify an event |
| * level by OR'ing the level with the diags mask. For example, to print |
| * an `Diags_INFO` event of `Diags_LEVEL2`, you'd simply write: |
| * (Diags_INFO | Diags_LEVEL2) |
| * |
| * Specifying an event level is optional. `Log_print` calls which do not |
| * specify a level will receive the highest priority by default. |
| * |
| * @param(mask) enable bits and optional detail level for this event |
| * @param(fmt) a `printf` style format string |
| * @param(a1) value for first format conversion character |
| * @param(a2) value for second format conversion character |
| * @param(a3) value for third format conversion character |
| * @param(a4) value for fourth format conversion character |
| * @param(a5) value for fifth format conversion character |
| * @param(a6) value for sixth format conversion character |
| * |
| * @a(Examples) |
| * The following example demonstrates a typical usage. |
| * @p(code) |
| * String list[]; |
| * UInt i; |
| * |
| * Log_print2(Diags_USER2, "list[%u] = %s\n", i, (IArg)list[i]); |
| * @p |
| * Note that the `IArg` cast above is only necessary for pointer |
| * arguments; C's normal parameter conversions implicitly convert |
| * integral arguments. |
| * |
| * To simplify the conversion from `float` arguments to `IArg`, |
| * the standard header `xdc/std.h` provides a macro, named floatToArg(), |
| * to do this conversion in a type safe manner. So, the following |
| * statement will print "`float = 2.3456`": |
| * @p(code) |
| * Log_print1(Diags_USER1, "float = %f", floatToArg(2.34567)); |
| * @p |
| * |
| * Note that, if you are formatting events on the target, you must |
| * also add support for floating point to ASCII conversion to |
| * `{@link System#printf}`; for more information, see the |
| * `{@link System#extendedFormats}` reference documenation. For example: |
| * @p(code) |
| * var System = xdc.useModule('xdc.runtime.System'); |
| * System.extendedFormats = "%f"; |
| * @p |
| */ |
| @Macro Void print6(Diags.Mask mask, CString fmt, IArg a1, IArg a2, |
| IArg a3, IArg a4, IArg a5, IArg a6); |
| |
| /*! |
| * ======== error0 ======== |
| * Generate a `Log` "error event" with 0 arguments |
| * |
| * @see #error5 |
| */ |
| @Macro Void error0(CString fmt); |
| |
| /*! |
| * ======== error1 ======== |
| * Generate a `Log` "error event" with 1 argument |
| * |
| * @see #error5 |
| */ |
| @Macro Void error1(CString fmt, IArg a1); |
| |
| /*! |
| * ======== error2 ======== |
| * Generate a `Log` "error event" with 2 arguments |
| * |
| * @see #error5 |
| */ |
| @Macro Void error2(CString fmt, IArg a1, IArg a2); |
| |
| /*! |
| * ======== error3 ======== |
| * Generate a `Log` "error event" with 3 arguments |
| * |
| * @see #error5 |
| */ |
| @Macro Void error3(CString fmt, IArg a1, IArg a2, IArg a3); |
| |
| /*! |
| * ======== error4 ======== |
| * Generate a `Log` "error event" with 4 arguments |
| * |
| * @see #error5 |
| */ |
| @Macro Void error4(CString fmt, IArg a1, IArg a2, IArg a3, |
| IArg a4); |
| |
| /*! |
| * ======== error5 ======== |
| * Generate a `Log` "error event" with 5 arguments |
| * |
| * The Log_error APIs are intended to allow users to easily log error |
| * events in their code. Similar to the Log_print APIs, Log_error does not |
| * require that you define an event. You simply pass an informative error |
| * string which can optionally be formatted with additional arguments. The |
| * error is logged with the predefined event {@link #L_error}. |
| * |
| * Log_error prepends a string to the message which identifies it as an |
| * ERROR and specifies the filename and line number of the Log_error call |
| * site. A simple example: |
| * |
| * @p(code) |
| * Log_error0("Invalid argument"); |
| * @p |
| * This event will be formatted as (assuming that the above call was line |
| * 35 of "MyCode.c") |
| * @p(code) |
| * ERROR at "MyCode.c", line 35: Invalid argument |
| * @p |
| * |
| * Users may provide additional information in the error event, such as |
| * a predefined error code or details of the error. These additional |
| * values will be used to format the string passed to Log_error. |
| * @see #print6 for information about format strings. |
| * |
| * Log_error does not use a variable length argument list--you must call |
| * the appropriate Log_errorX API based on the number of arguments. |
| * |
| * @param(fmt) a reference to a constant error string / fmt string |
| * @param(a1) value for an additional parameter (e.g. an error code) |
| * @param(a2) value for an additional parameter |
| * @param(a3) value for an additional parameter |
| * @param(a4) value for an additional parameter |
| * @param(a5) value for an additional parameter |
| * |
| * @a(Examples) |
| * The following example demonstrates a typical usage. |
| * @p(code) |
| * Int myArg; |
| * |
| * Log_error1("Invalid argument: %d", myArg); |
| * @p |
| * The above event is formatted as, for example: |
| * @p(code) |
| * ERROR: "MyCode.c", line 35: Invalid argument: -1 |
| * @p |
| */ |
| @Macro Void error5(CString fmt, IArg a1, IArg a2, IArg a3, |
| IArg a4, IArg a5); |
| |
| /*! |
| * ======== warning0 ======== |
| * Generate a `Log` "warning event" with 0 arguments |
| * |
| * @see #warning5 |
| */ |
| @Macro Void warning0(CString fmt); |
| |
| /*! |
| * ======== warning1 ======== |
| * Generate a `Log` "warning event" with 1 argument |
| * |
| * @see #warning5 |
| */ |
| @Macro Void warning1(CString fmt, IArg a1); |
| |
| /*! |
| * ======== warning2 ======== |
| * Generate a `Log` "warning event" with 2 arguments |
| * |
| * @see #warning5 |
| */ |
| @Macro Void warning2(CString fmt, IArg a1, IArg a2); |
| |
| /*! |
| * ======== warning3 ======== |
| * Generate a `Log` "warning event" with 3 arguments |
| * |
| * @see #warning5 |
| */ |
| @Macro Void warning3(CString fmt, IArg a1, IArg a2, IArg a3); |
| |
| /*! |
| * ======== warning4 ======== |
| * Generate a `Log` "warning event" with 4 arguments |
| * |
| * @see #warning5 |
| */ |
| @Macro Void warning4(CString fmt, IArg a1, IArg a2, IArg a3, |
| IArg a4); |
| |
| /*! |
| * ======== warning5 ======== |
| * Generate a `Log` "warning event" with 5 arguments |
| * |
| * The Log_warning APIs provide the same features as the Log_error APIs, |
| * but are used to specifically log "warning" events. |
| * @see #error5 |
| * |
| * The Log_warning APIs are equivalent to the Log_error APIs except that |
| * they use the predefined {@link #L_warning} event. Log_warning prepends |
| * a string to the message which identifies it as a WARNING and specifies |
| * the filename and line number of the Log_warning call site. |
| * |
| * @param(fmt) reference to a constant warning string / fmt string |
| * @param(a1) value for an additional parameter (e.g. a warning code) |
| * @param(a2) value for an additional parameter |
| * @param(a3) value for an additional parameter |
| * @param(a4) value for an additional parameter |
| * @param(a5) value for an additional parameter |
| * |
| * @a(Examples) |
| * The following example demonstrates a typical usage. |
| * @p(code) |
| * Int myArg; |
| * |
| * Log_warning1("Value may be too high: %d", myArg); |
| * @p |
| * The above event is formatted as: |
| * @p(code) |
| * WARNING: "MyCode.c", line 50: Value may be too high: 4096 |
| * @p |
| */ |
| @Macro Void warning5(CString fmt, IArg a1, IArg a2, IArg a3, |
| IArg a4, IArg a5); |
| |
| /*! |
| * ======== info0 ======== |
| * Generate a `Log` "info event" with 0 arguments |
| * |
| * @see #info5 |
| */ |
| @Macro Void info0(CString fmt); |
| |
| /*! |
| * ======== info1 ======== |
| * Generate a `Log` "info event" with 1 argument |
| * |
| * @see #info5 |
| */ |
| @Macro Void info1(CString fmt, IArg a1); |
| |
| /*! |
| * ======== info2 ======== |
| * Generate a `Log` "info event" with 2 arguments |
| * |
| * @see #info5 |
| */ |
| @Macro Void info2(CString fmt, IArg a1, IArg a2); |
| |
| /*! |
| * ======== info3 ======== |
| * Generate a `Log` "info event" with 3 arguments |
| * |
| * @see #info5 |
| */ |
| @Macro Void info3(CString fmt, IArg a1, IArg a2, IArg a3); |
| |
| /*! |
| * ======== info4 ======== |
| * Generate a `Log` "info event" with 4 arguments |
| * |
| * @see #info5 |
| */ |
| @Macro Void info4(CString fmt, IArg a1, IArg a2, IArg a3, IArg a4); |
| |
| /*! |
| * ======== info5 ======== |
| * Generate a `Log` "info event" with 5 arguments |
| * |
| * The Log_info APIs are provided for easily logging generic |
| * "informational" events with call site information. They are similar to |
| * the Log_print APIs in that they do not require you to define an event-- |
| * you simply pass an informative printf-style string which can optionally |
| * be formatted with additional arguments. The info record is logged with |
| * the predefined event '{@link #L_info}'. |
| * |
| * The Log_info APIs log the {@link #L_info} event which uses the 'INFO' |
| * diags category. They do not allow you to specify an event priority. |
| * |
| * Log_info prepends the filename and line number of the call site to the |
| * message. |
| * |
| * @param(fmt) reference to a constant event string / fmt string |
| * @param(a1) value for an additional parameter (e.g. an event code) |
| * @param(a2) value for an additional parameter |
| * @param(a3) value for an additional parameter |
| * @param(a4) value for an additional parameter |
| * @param(a5) value for an additional parameter |
| * |
| * @a(Examples) |
| * The following example demonstrates a typical usage. |
| * @p(code) |
| * Int load; |
| * |
| * Log_info1("Current load: %d", load); |
| * @p |
| * The above event is formatted as, for example: |
| * @p(code) |
| * "MyCode.c", line 15: Current load: 25 |
| * @p |
| */ |
| @Macro Void info5(CString fmt, IArg a1, IArg a2, IArg a3, IArg a4, |
| IArg a5); |
| |
| /*! |
| * ======== put0 ======== |
| * Unconditionally put the specified Log event with 0 arguments |
| * |
| * @see #put8 |
| */ |
| @Macro Void put0(Log.Event evt, Types.ModuleId mid); |
| |
| /*! |
| * ======== put1 ======== |
| * Unconditionally put the specified Log event and 1 argument |
| * |
| * @see #put8 |
| */ |
| @Macro Void put1(Log.Event evt, Types.ModuleId mid, IArg a1); |
| |
| /*! |
| * ======== put2 ======== |
| * Unconditionally put the specified Log event and 2 arguments |
| * |
| * @see #put8 |
| */ |
| @Macro Void put2(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2); |
| |
| /*! |
| * ======== put4 ======== |
| * Unconditionally put the specified Log event and 4 arguments |
| * |
| * @see #put8 |
| */ |
| @Macro Void put4(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2, |
| IArg a3, IArg a4); |
| |
| /*! |
| * ======== put8 ======== |
| * Unconditionally put the specified Log event and 8 arguments |
| * |
| * This method unconditionally puts the specified `{@link Event}` |
| * `evt` into the log. The `{@link Types#ModuleId}` `mid` should be the |
| * module ID of the module which is putting the event. |
| * |
| * @param(evt) the Log event to put into the log |
| * @param(mid) module ID of the module putting the event |
| * @param(a1) value for first format conversion character |
| * @param(a2) value for second format conversion character |
| * @param(a3) value for third format conversion character |
| * @param(a4) value for fourth format conversion character |
| * @param(a5) value for fifth format conversion character |
| * @param(a6) value for sixth format conversion character |
| * @param(a7) value for seventh format conversion character |
| * @param(a8) value for eighth format conversion character |
| */ |
| @Macro Void put8(Log.Event evt, Types.ModuleId mid, IArg a1, IArg a2, |
| IArg a3, IArg a4, IArg a5, IArg a6, IArg a7, IArg a8); |
| |
| /*! |
| * ======== write0 ======== |
| * Generate a `Log` event with 0 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write0(Event evt); |
| |
| /*! |
| * ======== write1 ======== |
| * Generate a `Log` event with 1 argument |
| * |
| * @see #write8 |
| */ |
| @Macro Void write1(Event evt, IArg a1); |
| |
| /*! |
| * ======== write2 ======== |
| * Generate a `Log` event with 2 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write2(Event evt, IArg a1, IArg a2); |
| |
| /*! |
| * ======== write3 ======== |
| * Generate a `Log` event with 3 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write3(Event evt, IArg a1, IArg a2, IArg a3); |
| |
| /*! |
| * ======== write4 ======== |
| * Generate a `Log` event with 4 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write4(Event evt, IArg a1, IArg a2, IArg a3, IArg a4); |
| |
| /*! |
| * ======== write5 ======== |
| * Generate a `Log` event with 5 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write5(Event evt, IArg a1, IArg a2, IArg a3, IArg a4, IArg a5); |
| |
| /*! |
| * ======== write6 ======== |
| * Generate a `Log` event with 6 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write6(Event evt, IArg a1, IArg a2, IArg a3, IArg a4, |
| IArg a5, IArg a6); |
| |
| /*! |
| * ======== write7 ======== |
| * Generate a `Log` event with 7 arguments |
| * |
| * @see #write8 |
| */ |
| @Macro Void write7(Event evt, IArg a1, IArg a2, IArg a3, IArg a4, |
| IArg a5, IArg a6, IArg a7); |
| |
| /*! |
| * ======== write8 ======== |
| * Generate a `Log` event with 8 arguments |
| * |
| * If the mask in the specified `Log` event has any bit set which is |
| * also set in the current module's diagnostics mask, then this call to |
| * write will "raise" the given `Log` event. |
| * |
| * @param(evt) the `Log` event to write |
| * @param(a1) value for first format conversion character |
| * @param(a2) value for second format conversion character |
| * @param(a3) value for third format conversion character |
| * @param(a4) value for fourth format conversion character |
| * @param(a5) value for fifth format conversion character |
| * @param(a6) value for sixth format conversion character |
| * @param(a7) value for seventh format conversion character |
| * @param(a8) value for eighth format conversion character |
| */ |
| @Macro Void write8(Event evt, IArg a1, IArg a2, IArg a3, IArg a4, |
| IArg a5, IArg a6, IArg a7, IArg a8); |
| |
| /*! |
| * ======== doPrint ======== |
| * Render an event as text via `{@link System#printf System_printf}` |
| * |
| * This method is not gated and may make more than one call to |
| * `System_printf`. This utility method is typically used within the |
| * implementation of a logger which initializes |
| * `{@link #EventRec Log_EventRec}` structures based on `Log` events |
| * produced by the application. |
| * |
| * @param(evRec) a non`NULL` pointer to an initialized `Log_EventRec` |
| * structure to be formated via |
| * `{@link System#printf System_printf}`. |
| */ |
| Void doPrint(EventRec *evRec); |
| |
| /*! |
| * @_nodoc |
| * ======== lookupEventMessage ======== |
| * Returns the format string for the event with the given id. |
| */ |
| function lookupEventMessage(eventId); |
| |
| /*! |
| * @_nodoc |
| * ======== getTargetArgSize ======== |
| * Returns the target size of a record argument in bytes (not MAUs). |
| */ |
| function getTargetArgSize(); |
| |
| /*! |
| * @_nodoc |
| * ======== lookupEventName ======== |
| */ |
| function lookupEventName(eventId); |
| |
| /*! |
| * @_nodoc |
| * ======== lookupModuleName ======== |
| */ |
| function lookupModuleName(modId); |
| |
| /*! |
| * @_nodoc |
| * ======== getTargetEventRecSize ======== |
| * Returns the record size in bytes (not MAUs). |
| */ |
| function getTargetEventRecSize(); |
| |
| internal: |
| |
| /* |
| * ======== idToInfo ======== |
| * Map event ID strings into a string of the form <eventName>::<eventMsg> |
| */ |
| metaonly config String idToInfo[string] = []; |
| } |