top logo menu kitty mascot
AROS.ORG Developers Localization Bounties

log

Index


--background_logresource-- logAddEntryA() logAddListener() logCmpStr()
logCopyStr() logCopyStrFmtA() logDeleteBroadcast() logEventBroadcast()
logFinalise() logGetEntryAttrs() logInitialise() logLockEntries()
logNextEntry() logRawDoFmtA() logRawDoFmtCBA() logRemEntry()
logRemListener() logUnlockEntries()    

--background_logresource--

Notes

This resource serves as a base interface to AROS's logging mechanisms.

It provides centralized collection and management of structured log messages
from system and application components, enabling uniform diagnostics and
analysis capabilities across the OS.

Messages are stored as dynamically allocated nodes
which are organized into two linked lists:
    - A global list maintained by the log.resource itself
    - A per-producer list

Entries are added using `logAddEntryA()` with a RawDoFmt-style format string
and metadata such as component, subcomponent, originator, and event ID.

Each entry stores:
    - A human-readable formatted message (`le_Entry`)
    - Producer and originator info (`lep_Producer`, `lectx_Originator`)
    - Component tags (`le_Node.ln_Name`, `lep_Node.ln_Name`)
    - Time/date stamp (`le_DateStamp`)
    - Priority flags and event identifiers

Consumers may iterate over entries using `logNextEntry()` with an `entryHandle` pointer,
which is updated in place to walk through the list. Constants `LOGEntry_First` and
`LOGEntry_Last` mark the bounds of traversal.

Attributes of each entry can be queried with `logGetEntryAttrs()`, which takes a
taglist and returns selected fields such as LOGMA_Entry, LOGMA_Flags, LOGMA_Component,
and others.

`logRemEntry()` unlinks entries and may queue their disposal on the
service task. This does not guarantee complete deallocation.

`logLockEntries()` and `logUnlockEntries()` serialize cooperating readers
with insertion, but do not exclude every entry-removal path.

The log.resource is self-contained and allocates memory via the producer's
memory pool (`lrh_Pool`) to simplify cleanup and ownership tracking.

logAddEntryA()

Synopsis

struct logEntry * logAddEntryA(
         ULONG flags,
         APTR loghandle,
         STRPTR sub,
         STRPTR src,
         ULONG eventid,
         STRPTR fmtstr,
         RAWARG fmtdata );

struct logEntry * logAddEntry(
         ULONG flags,
         APTR loghandle,
         STRPTR sub,
         STRPTR src,
         ULONG eventid,
         STRPTR fmtstr,
         ... );

Function

Creates and queues a new log entry associated with the given
logging handle. The entry includes timestamp, event ID,
optional subsystem/source strings, originator information,
and a formatted message string built from 'fmtstr' and 'fmtdata'.

Inputs

flags     - Logging flags and priority level (LOGM_*).
loghandle - Handle to an open log resource (struct LogResHandle *).
sub       - Optional subsystem string, may be NULL.
src       - Optional source string, may be NULL.
eventid   - User-supplied event identifier.
fmtstr    - Format string for the log message.
fmtdata   - Argument data matching the format string.

Result

Pointer to a logEntry structure if successful,
or NULL if the entry could not be created.

Example

struct logEntry *e = logAddEntryA(LOGM_Flag_Info, myLogHandle,
    "filesystem", "disk.device", 42,
    "Mounted volume %s", (RAWARG)"DH0:");

Notes

The returned logEntry is owned by log.resource and should not
be modified or freed by the caller. The timestamp source depends
on availability of DOS, timer.device, or kernel facilities.

Bugs

Kernel timestamp support is incomplete (marked TODO in source).

logAddListener()

Synopsis

struct logListenerHook * logAddListener(
         struct MsgPort * mp,
         ULONG msgmask );

Function

Register a message port for selected log notifications.

Inputs

mp - Live message port, or NULL. Keep it valid until registration
     has ended and all queued notifications have been handled.
msgmask - Event bits EHMF_* combined with LOGF_Flag_Type_* bits.

Result

A listener handle for logDeleteBroadcast() and logRemListener(),
or NULL for a NULL port or listener-handle allocation failure.

Notes

A notification matches only if msgmask contains its event bit and
all of its entry-type bits. To receive all defined types and events,
use LOGF_Flag_Type_All | EHMF_ALLEVENTS. Existing entries are not
replayed. Registration order follows the port's priority at this call.

Messages have type struct LogResBroadcastMsg. Remove them from the
port with GetMsg(), then dispose of each with logDeleteBroadcast()
using this listener handle. Do not ReplyMsg() or FreeVec() them.
The target pointer is borrowed, not pinned by the message.
Call from task context; registration may wait on a semaphore.

Bugs

Creation of the listener's message pool is not checked. A non-NULL
handle can therefore contain an unusable pool. Entry lifetime is
not extended for queued messages; removal targets may already be
freed when a listener receives them.

logCmpStr()

Synopsis

int logCmpStr(
         CONST_STRPTR str1,
         CONST_STRPTR str2 );

Function

Compare two NUL-terminated strings using strcmp().

Inputs

str1 - Non-NULL first string.
str2 - Non-NULL second string.

Result

Zero if equal, a negative value if str1 sorts before str2, or a
positive value if it sorts after str2. Only the sign is specified.

Notes

Comparison is case-sensitive and stops at the first unequal byte
or terminator. Neither string is modified or retained. NULL is not
accepted.

See also

logCopyStr()


logCopyStr()

Synopsis

STRPTR logCopyStr(
         CONST_STRPTR name );

Function

Allocate a copy of a NUL-terminated string.

Inputs

name - Source string, or NULL.

Result

A caller-owned copy including the terminating NUL, or NULL for a
NULL source or allocation failure. Release the copy with FreeVec().

Notes

The source is not modified or retained. An empty source produces
an allocated empty string. Call from task context.

logCopyStrFmtA()

Synopsis

STRPTR logCopyStrFmtA(
         CONST_STRPTR fmtstr,
         RAWARG fmtdata );

STRPTR logCopyStrFmt(
         CONST_STRPTR fmtstr,
         ... );

Function

Allocate a string formatted with RawDoFmt().

Inputs

fmtstr - NUL-terminated RawDoFmt() format string, or NULL.
fmtdata - RAWARG data matching fmtstr and the target ABI.

Result

A caller-owned NUL-terminated string, or NULL for a NULL format
or allocation failure. Release the string with FreeVec().

Notes

Formatting runs twice: once to calculate capacity and once to
write the result. Keep the format, argument data and referenced
strings unchanged across both passes. Call from task context.

Bugs

The counting pass excludes newline characters, but the output
pass writes them. Output containing newlines is therefore truncated;
newlines are not simply removed. No truncation status is returned.

logDeleteBroadcast()

Synopsis

void logDeleteBroadcast(
         APTR listener,
         APTR bMsg );

Function

Free one notification received by a listener.

Inputs

listener - Live handle for the listener that received bMsg.
bMsg - Notification already removed from that listener's port,
       not previously freed.

Result

None. bMsg becomes invalid.

Notes

This frees only the notification, not its target entry. Use the
matching listener because the message belongs to its private pool.
Do not call after logRemListener(), which deletes that pool. The
function performs no port removal, ReplyMsg(), origin check or
listener locking; coordinate it with listener teardown.

logEventBroadcast()

Synopsis

VOID logEventBroadcast(
         UBYTE ehmt,
         APTR param1,
         APTR param2 );

Function

Enqueue a notification for each matching listener.

Inputs

ehmt - Event index EHMB_*, not an EHMF_* mask.
param1 - Live log entry pointer used to read its type flags and
         stored as the notification's lrbm_Target.
param2 - Reserved; currently ignored.

Result

None. No delivery count or allocation-failure status is returned.

Notes

Matching requires all bits in
    (entryFlags & LOGM_Flag_TypeMask) | (1L << ehmt)
to be present in the listener mask. Each message's lrbm_MsgType is
the event mask, not the event index. Messages are allocated from
the corresponding listener pool and sent asynchronously with PutMsg().

The caller must keep param1 valid while this function reads it.
The message does not retain or copy the entry. In particular, an
EHMF_REMENTRY target is an identity value, not a safe-to-dereference
entry. Call from task context; the listener semaphore may block.

Bugs

Message allocation failure is not checked before dereferencing
the result. All event types require a live entry in param1 because
the implementation reads entry flags unconditionally; NULL is not
valid even for START or STOP events.

logFinalise()

Synopsis

void logFinalise(
         APTR logProvider );

Function

Locate registered producers by name. Cleanup is not implemented.

Inputs

logProvider - Non-NULL pointer to an object beginning with a
              struct Node whose ln_Name is a valid NUL-terminated
              producer name. A producer handle has this prefix.

Result

None.

Notes

The function compares names but does not unlink providers, remove
entries, release pools or wait for pending events. Returning from
this call does not establish that a producer has been shut down.
Provider-list traversal is not protected internally.

Bugs

The finalization body is a placeholder. No resources are released.

See also

logInitialise()


logGetEntryAttrs()

Synopsis

IPTR logGetEntryAttrs(
         APTR entryHandle,
         struct TagItem * tags );

IPTR logGetEntryAttrsTags(
         APTR entryHandle,
         TAG tag, ... );

Function

Read selected attributes from a published log entry.

Inputs

entryHandle - Live published entry handle, or NULL. Do not pass
              LOGEntry_Last or a freed entry.
tags - Tag list whose ti_Data fields point to writable destinations
       of the types listed below.

Tags

LOGMA_Flags (ULONG *)
    Entry flags with the private high-byte flags removed.
LOGMA_DateStamp (struct DateStamp **)
    Pointer to the entry's stored timestamp.
LOGMA_EventID (ULONG *)
    Event identifier supplied by the producer.
LOGMA_Origin (char **)
    Recorded originating task description.
LOGMA_Component (char **)
    Producer name. Written only if a producer is associated.
LOGMA_SubComponent (char **)
    Subcomponent string supplied when the entry was added.
LOGMA_LogTag (char **)
    Source/tag string supplied when the entry was added.
LOGMA_Entry (char **)
    Formatted message text.

Result

The number of attributes written. Zero is returned for NULL,
a node not marked NT_LOGENTRY, or failure to open utility.library.
Unsupported tags are ignored. Only the first occurrence of each
supported tag is processed; skipped destinations are unchanged.

Notes

Use normal tag-list termination and control tags. String and date
results point into resource-owned storage; they are not copies.
Do not modify or free them. Individual string results may be NULL.
Hold the entry lock and coordinate entry removal before reading or
copying these values. The function does not acquire the entry lock
and may open utility.library; call from task context.

Bugs

LOGMA_Level and LOGMA_Type are not handled. Obtain their bits from
LOGMA_Flags instead. The public LOGMA_Type macro is also malformed
in this version of <resources/log.h>.

logInitialise()

Synopsis

APTR logInitialise(
         APTR logProvider );

Function

Register a log producer and allocate its entry pool.

Inputs

logProvider - Non-NULL pointer to an object beginning with a
              struct Node. ln_Name identifies the producer and
              should point to a NUL-terminated name.

Result

A producer handle for logAddEntryA(), or NULL if the service task
is unavailable, logProvider is NULL, or pool creation fails.

Notes

The name is copied; the provider object is not retained. The
resource owns the returned handle and pool. Do not free them with
FreeVec() or DeletePool(). Call from task context. Provider-list
updates are not protected internally; serialize registrations.

Bugs

Handle allocation is not checked before dereferencing its result.
Name-copy failure can leave a registered handle without a name.
logFinalise() does not yet release the handle or its pool.

logLockEntries()

Synopsis

VOID logLockEntries(
         ULONG flags );

Function

Acquire the resource's entry-list semaphore.

Inputs

flags - LLF_READ or LLF_WRITE. Currently ignored.

Result

None. Returns after acquiring the semaphore.

Notes

Call from task context where waiting is permitted. Both flag values
acquire the same exclusive semaphore. Balance each acquisition with
logUnlockEntries() in the same task.

Hold the lock while traversing entries and inspecting borrowed
attributes. This serializes cooperating users and the service task's
insertion path; it does not establish complete entry-lifetime safety.

Bugs

logRemEntry() does not acquire this semaphore. The service task's
removal and deallocation path does not acquire it either. A held
lock alone cannot protect against every concurrent removal.

logNextEntry()

Synopsis

APTR logNextEntry(
         APTR * entryHandle );

Function

Advance a cursor through the global list of published log entries.

Inputs

entryHandle - Pointer to a writable APTR cursor. Initialize it to
              LOGEntry_First; subsequently retain each returned
              entry or LOGEntry_Last. NULL is accepted.

Result

The next entry, also written to *entryHandle, or LOGEntry_Last
for an empty list or end of traversal. Passing LOGEntry_Last leaves
it unchanged; it does not return the final entry. A NULL cursor
pointer returns NULL.

Notes

Returned entries are borrowed. Hold logLockEntries() during
traversal and coordinate removal separately as described there.
Only pass live published entries from this list as cursors; a stale
address is not made safe by the node-type check. This function does
not acquire a lock or allocate storage.

logRawDoFmtA()

Synopsis

void logRawDoFmtA(
         STRPTR buf,
         ULONG len,
         CONST_STRPTR fmtstr,
         RAWARG fmtdata );

void logRawDoFmt(
         STRPTR buf,
         ULONG len,
         CONST_STRPTR fmtstr,
         ... );

Function

Format RawDoFmt() arguments into a bounded character buffer.

Inputs

buf - Writable buffer of at least len bytes.
len - Buffer capacity, including the terminator.
fmtstr - NUL-terminated RawDoFmt() format string.
fmtdata - RAWARG data matching fmtstr and the target ABI.

Result

None. With non-NULL buf and fmtstr and len greater than zero,
output is NUL-terminated and truncated to at most len - 1 bytes.
Otherwise the buffer is unchanged.

Notes

The formatter still processes the complete format after the buffer
fills. No required-length or truncation result is returned. The
buffer is caller-owned; no storage is allocated. Use RawDoFmt()
format and argument conventions, not a printf() va_list.

logRawDoFmtCBA()

Synopsis

void logRawDoFmtCBA(
         STRPTR buf,
         ULONG len,
         VOID_FUNC cbfunc,
         void * cbdata,
         CONST_STRPTR fmtstr,
         RAWARG fmtdata );

void logRawDoFmtCB(
         STRPTR buf,
         ULONG len,
         VOID_FUNC cbfunc,
         void * cbdata,
         CONST_STRPTR fmtstr,
         ... );

Function

Run RawDoFmt() with a caller-supplied output routine.

Inputs

buf - Writable buffer of at least len bytes.
len - Capacity of buf; must be greater than zero to invoke output.
cbfunc - RawDoFmt()-compatible output routine.
cbdata - Output routine's context, passed unchanged to RawDoFmt().
fmtstr - NUL-terminated RawDoFmt() format string.
fmtdata - RAWARG data matching fmtstr and the target ABI.

Result

None. After formatting, buf[len - 1] is set to NUL. NULL buf,
NULL fmtstr or zero len suppresses the call and leaves buf unchanged.

Notes

buf and len are not passed to the output routine and do not bound
its writes. The routine must implement its own capacity checks
through cbdata. It receives RawDoFmt() output, including the final
NUL, using the RawDoFmt callback ABI. Execution is synchronous;
context and output storage must remain valid until return.
Any allocation, waiting or side effects of the callback are the
callback's responsibility.

logRemEntry()

Synopsis

void logRemEntry(
         struct logEntry * le );

Function

Unlink a published entry and queue its disposal by the service task.

Inputs

le - Live published entry from log.resource, removed at most once,
     or NULL. An entry still awaiting publication is not valid here.

Result

None. NULL has no effect.

Notes

The function removes both global and producer linkage as applicable.
If the service task is running, it queues EHMB_REMENTRY and returns
without waiting for notification or deallocation. Treat the handle
and all borrowed attributes as invalid after requesting removal.
Do not free the entry yourself.

List removal uses Forbid()/Permit(), not the entry semaphore.
Callers must coordinate removal with readers; logLockEntries() alone
does not exclude this path.

Bugs

No node-state or duplicate-removal check is made. If the service
task has stopped, the entry is unlinked but not freed. The service
task does not free the copied subcomponent string. Its removal
notification contains a pointer that it then frees without waiting
for listeners to consume the message.

logRemListener()

Synopsis

VOID logRemListener(
         APTR listener );

Function

Unregister a listener and delete its message pool.

Inputs

listener - Live handle returned by logAddListener(). NULL and
           previously removed handles are invalid.

Result

None. The handle and all allocations from its pool become invalid.

Notes

The listener lock serializes unregistration with broadcasts. It
does not drain the destination port or wait for consumers. Before
removal, coordinate publishers and consumers so no new notification
can arrive and no queued or retained message remains. Dispose of
messages with logDeleteBroadcast() while the handle is still valid.
The message port itself remains caller-owned.

Call from task context; acquiring the listener lock may wait.

Bugs

Deleting the pool invalidates outstanding messages even if they
remain linked on the destination port. The API has no separate
stop-delivery operation that preserves the pool for draining.
Draining the port while broadcasts continue is not a safe shutdown
protocol.

logUnlockEntries()

Synopsis

VOID logUnlockEntries(
         ULONG flags );

Function

Release the semaphore acquired by logLockEntries().

Inputs

flags - LLF_READ or LLF_WRITE. Currently ignored.

Result

None.

Notes

The calling task must own a matching acquisition. Do not use this
call to release another task's lock. Borrowed entry pointers are
not reference-counted and must not be assumed valid after unlocking.