Jump to content

DMIAPI.LIB

From EDM2

DMIAPI.LIB is the import library for the Desktop Management Interface (DMI) procedural helper library, distributed with the IBM OS/2 Developer's Toolkit. It provides linker stubs for the four runtime functions in DMIAPI.DLL that simplify DMI component installation and CI instrumentation code.

File size in the OS/2 Warp 4.52 Toolkit 4.5: 1,536 bytes (2001-10-02).

Source DLL: DMIAPI.DLL.

Copyright: Intel Corporation 1992–1994; International Business Machines Corporation 1993–1996.

Overview: Desktop Management Interface (DMI)

The Desktop Management Interface (DMI) is an open standard defined by the Desktop Management Task Force (DMTF) that provides a standardized way for management applications to query hardware and software configuration information from a computer. DMI 2.0 (the version supported by OS/2 Warp 4) defines a three-tier architecture:

Tier Name Role
1 Management Application (CI side) Sends DMI commands to enumerate components, read attributes, set attributes, invoke group procedures
2 Service Layer (SL) Central broker daemon (DMISL.EXE) that routes requests between management applications and instrumentation components; maintains the MIF database
3 Instrumentation Component (MI side) DLL or process that provides live attribute data for a hardware or software component; registers with the SL via a MIF file

All communication passes through the Service Layer. Management applications and instrumentation components never communicate directly.

MIF Files

A MIF (Management Information Format) file is a text description of a component's attributes. It defines:

  • Component — the top-level manageable entity (e.g. "IBM ThinkPad BIOS")
  • Groups — logical collections of related attributes (e.g. "System Information", "Memory")
  • Attributes — individual data items within a group, each with a type, access mode, and optional enumeration values

Attribute types: MIF_COUNTER (monotonic 32-bit), MIF_COUNTER64, MIF_GAUGE (up/down 32-bit), MIF_INTEGER, MIF_INTEGER64, MIF_OCTETSTRING, MIF_DISPLAYSTRING, MIF_DATE (26-byte timestamp).

Attribute access modes: MIF_READ_ONLY, MIF_READ_WRITE, MIF_WRITE_ONLY, MIF_UNSUPPORTED, MIF_UNKNOWN.

Command Architecture

DMI commands are identified by integer codes in the iCommand field of a DMI_MgmtCommand_t header:

Group Range Commands
Miscellaneous 0x0100–0x01FF DmiRegisterMgmtCmd, DmiUnregisterMgmtCmd, DmiCancelCmd
List 0x0200–0x02FF DmiListComponentCmd, DmiListFirstComponentCmd, DmiListNextComponentCmd, DmiListComponentDescCmd, DmiListGroupCmd, DmiListFirstGroupCmd, DmiListNextGroupCmd, DmiListGroupDescCmd, DmiListAttributeCmd, DmiListFirstAttributeCmd, DmiListNextAttributeCmd, DmiListAttributeDescCmd, DmiListGroupPragmaCmd
Get/Set 0x0300–0x03FF DmiGetAttributeCmd, DmiSetAttributeCmd, DmiSetReserveAttributeCmd, DmiSetReleaseAttributeCmd, DmiGetRowCmd, DmiGetFirstRowCmd, DmiGetNextRowCmd
CI 0x0400–0x04FF DmiRegisterCiCmd, DmiUnregisterCiCmd, DmiCiInstallCmd, DmiCiUninstallCmd

Core Structures

DMI_MgmtCommand_t

The header that begins every DMI command block:

Field Type Description
iLevelCheck DMI_UNSIGNED Magic value DMI_LEVEL_CHECK (0x444D3131 = "DM11"). Verified by the SL to confirm DMI 2.0 compatibility.
iCommand DMI_UNSIGNED Command code (see table above)
iCmdLen DMI_UNSIGNED Total length of the command structure in bytes
iMgmtHandle DMI_UNSIGNED Management handle returned by DmiRegisterMgmtCmd; identifies the calling management application to the SL
iCmdHandle DMI_UNSIGNED Caller-defined handle echoed back in the confirm callback; used to correlate async responses
osLanguage DMI_OFFSET Offset within the command block to a language string (e.g. "English"); 0 = default
oSecurity DMI_OFFSET Offset to a DMI_Security_t block; 0 = no security
iCnfBufLen DMI_UNSIGNED Size of the confirm buffer pointed to by pCnfBuf
pCnfBuf void * Pointer to the buffer that receives the confirm (response) data
iRequestCount DMI_UNSIGNED Number of request items in a batch command
iCnfCount DMI_UNSIGNED Filled by SL: number of confirm items returned
iStatus DMI_UNSIGNED Filled by SL: completion status
DmiCiCommand DMI_CiCommand_t CI sub-command block for component interface operations

DMI_Indicate_t

Structure passed to DmiIndicate() when a component raises an event:

Field Type Description
iLevelCheck DMI_UNSIGNED DMI_LEVEL_CHECK magic
iIndicationType DMI_UNSIGNED Type: DMI_EVENT_INDICATION (1), DMI_INSTALL_INDICATION (2), DMI_UNINSTALL_INDICATION (3), DMI_INSTALL_LANGUAGE_MAPPING (4)
iCmdLen DMI_UNSIGNED Total size of this structure in bytes
iComponentId DMI_UNSIGNED Component ID of the component raising the event
DmiTimeStamp DMI_TimeStamp_t 26-byte timestamp: YYYYMMDDHHMMSS.mmmmmm+UUU (ISO format, padded for alignment)
pResponseFunc DMI_FUNC3_OUT Callback invoked by the SL when the indication has been processed
oIndicationData DMI_OFFSET Offset to event-specific data (DMI_ListComponentCnf_t for install/uninstall, DMI_EventData_t for events)

DmiCiControl_t

The control structure passed to and from DmiCiProcess() to dispatch a CI request to the instrumentation skeleton:

Field Type Description
pRequestBuffer union * Pointer to the incoming command (DmiMgmtCommand, DmiGetAttributeReq, DmiSetAttributeReq, or DmiGetRowReq)
pConfirmBuffer union * Pointer to the outgoing confirm buffer (DmiGetAttributeCnf[] or DmiGetRowCnf)
DmiConfirmFunc DMI_FUNC3_OUT The confirm callback; DmiCiProcess() calls this after filling the confirm buffer
ciCancelFlag CiBoolean Set to CiTrue by the SL when it requests that this command be cancelled mid-execution
dmiConfirm DmiConfirm Confirm data block (iLevelCheck, pDmiMgmtCommand, iStatus)
ciKeyList DmiCiAttribute_t * Array of key attributes (group key values) filled by the CI skeleton code for table-row lookups
MaxKeyCount DMI_UNSIGNED Maximum number of key attributes allowed for this component
CiGetAttribute CI_FUNC_IN1 Callback: retrieve one attribute value (component ID, group ID, attribute ID, row key list)
CiGetNextAttribute CI_FUNC_IN1 Callback: retrieve next attribute in sequence
CiReleaseAttribute CI_FUNC_IN2 Callback: release a previously retrieved attribute value
CiReserveAttribute CI_FUNC_IN2 Callback: reserve an attribute for a set operation (locks the attribute)
CiSetAttribute CI_FUNC_IN2 Callback: write a new attribute value

API

DmiInstall

DmiLibInstallData_t * DMI_FUNC_ENTRY
DmiInstall(DMI_UNSIGNED       iFileCount,
           DmiLibFileData_t  *dmiLibFileList,
           DMI_STRING        *pDmiDir,
           DmiLibBoolean_t    iDefineDmiDir,
           DMI_FUNC_OUT       StatusCall);

Registers a new DMI component with the Service Layer by submitting one or more MIF files (and optional SNMP mapping files). This is the primary function an instrumentation component calls at startup.

iFileCount
Number of entries in dmiLibFileList.
dmiLibFileList
Array of DmiLibFileData_t structures, each specifying one file:
  • iFileType: MifFileName (2) — pFileData is a path string to a .MIF file; MifFilePointer (3) — pFileData points to the MIF content in memory. SNMP mapping file types (4, 5) are also accepted for components that expose SNMP MIB mappings.
  • pFileData: the file path or in-memory pointer depending on iFileType.
pDmiDir
Path to the DMI working directory where the SL stores compiled MIF database files. If iDefineDmiDir is DmiLibTrue, the DMIDIR environment variable is set to this path.
iDefineDmiDir
DmiLibTrue — set the DMIDIR environment variable to pDmiDir. DmiLibFalse — use the existing DMIDIR environment variable.
StatusCall
Callback entry point of type DMI_UNSIGNED DMI_FUNC_CALLBACK StatusCall(void *message). The SL calls this during MIF compilation with diagnostic and progress message strings (null-terminated). Pass NULL to suppress MIF compiler output.
Return value
Pointer to a DmiLibInstallData_t structure:
  • iComponentId: the component ID assigned by the SL (used in all subsequent DMI commands referencing this component)
  • iDmiLibStatus: library-level status — DmiLibSlInstallNoError (2) on success; DmiLibCannotRunServiceLayer, DmiLibCannotOpenSourceFile, DmiLibCannotAllocateMemory, etc. on failure.
  • iSlStatus: raw status code returned by the Service Layer.

DmiInvoke

DMI_UNSIGNED DMI_FUNC_ENTRY DmiInvoke(void *dmiCommand);

The MI (instrumentation) entry point called by the Service Layer to dispatch a DMI command to the instrumentation component. This is the inbound entry point of an instrumentation DLL — the SL calls it with the address of a DMI_MgmtCommand_t (or a command-specific structure that begins with one).

The instrumentation component implements DmiInvoke() and exports it. DmiInvoke() examines iCommand to determine the command type (Get, Set, List, Invoke group procedure, etc.), reads or writes the attribute data in the component's internal state, fills the confirm buffer (pCnfBuf), and calls the confirm callback (DmiCiCommand.pConfirmFunc).

The sDmiInvoke exported data symbol is the DMI_FUNC_ENTRY-typed function pointer to DmiInvoke(), used by the SL when binding to the instrumentation DLL.

DmiIndicate

DMI_UNSIGNED DMI_FUNC_ENTRY DmiIndicate(DMI_Indicate_t *dmiIndication);

Sends a DMI indication (event notification or install/uninstall notification) from the instrumentation component to the Service Layer. The SL routes the indication to all management applications that have registered for indications on this component.

Indication types
  • DMI_EVENT_INDICATION (1) — component-defined event (e.g. a temperature threshold exceeded, a disk failure predicted). The oIndicationData offset points to a DMI_EventData_t block containing the event group ID and attribute values at the time of the event.
  • DMI_INSTALL_INDICATION (2) — component has just registered with the SL (sent automatically by DmiInstall(); rarely sent manually).
  • DMI_UNINSTALL_INDICATION (3) — component is about to unregister.
  • DMI_INSTALL_LANGUAGE_MAPPING (4) — a localized language mapping is being installed for this component's MIF strings.
Return value
0 on success; non-zero SL error code on failure (e.g. SL not running, invalid component ID).

DmiCiProcess

DMI_UNSIGNED DMI_FUNC_ENTRY
DmiCiProcess(DmiCiControl_t *Command, void *dmiCommand);

The CI (component interface) request dispatcher. Called by the instrumentation component's DmiInvoke() implementation to dispatch an incoming Get or Set command to the appropriate attribute access callback.

DmiCiProcess() examines the command type in Command->pRequestBuffer->dmiMgmtCommand.iCommand and calls the appropriate callback in the DmiCiControl_t:

  • For DmiGetAttributeCmd / DmiGetRowCmd → calls Command->CiGetAttribute() or Command->CiGetNextAttribute(), fills the confirm buffer, and invokes Command->DmiConfirmFunc.
  • For DmiSetAttributeCmd → calls Command->CiReserveAttribute(), then Command->CiSetAttribute(), then Command->CiReleaseAttribute().
  • If Command->ciCancelFlag is CiTrue, the operation is abandoned mid-execution.

This function eliminates most of the boilerplate in the CI skeleton (CiSkel.c) by centralizing command dispatch, confirm buffer management, and cancel detection.

Usage

Include Files

Header Contents
dmiapi.h DmiInstall(), DmiIndicate(), DmiCiProcess() prototypes; DmiLibInstallData_t, DmiLibFileData_t, DmiCiControl_t, DmiCiAttribute_t structures; DmiLib* error constants
dmi.h DMI_MgmtCommand_t, DMI_Indicate_t, DMI_TimeStamp_t, DMI_String, all command code constants (Dmi*Cmd), all attribute type constants (MIF_*), DMI_FUNC_IN/DMI_FUNC_OUT typedefs
os_dmi.h OS/2-specific DMI platform macros: _FAR, DMI_FUNC_ENTRY, DMI_FUNC_CALLBACK, DMI_UNSIGNED typedef, OS/2 IPC handle types

Build instructions

IBM VisualAge C++ / ILINK

icc -O2 -Gm -c micomp.c
ilink /PM:VIO micomp.obj os2386.lib dmiapi.lib

OpenWatcom

wcl386 -bt=os2 -mf -c micomp.c
wlink system os2v2 file micomp.obj library os2386.lib library dmiapi.lib

EMX/GCC

gcc -Zomf -c micomp.c
gcc -Zomf -o micomp.exe micomp.o -los2386 -ldmiapi

Minimal DMI Component Registration

The typical sequence for an instrumentation DLL or process to register with the Service Layer:

#include <dmiapi.h>
#include <dmi.h>
#include <stdio.h>

/* MIF compiler message callback */
DMI_UNSIGNED DMI_FUNC_CALLBACK StatusPrint(void FAR *msg)
{
    printf("MIF: %s\n", (char *)msg);
    return 0;
}

int main(void)
{
    /* Describe the MIF file to install */
    DmiLibFileData_t fileList[1];
    fileList[0].iFileType  = MifFileName;
    fileList[0].pFileData  = (DMI_STRING *)"\x0E\x00ThinkPad.mif"; /* length-prefixed */

    /* Register the component with the SL */
    DmiLibInstallData_t *pResult = DmiInstall(
        1,            /* one file */
        fileList,
        NULL,         /* use existing DMIDIR */
        DmiLibFalse,
        StatusPrint); /* print compiler messages */

    if (!pResult || pResult->iDmiLibStatus != DmiLibSlInstallNoError) {
        printf("DmiInstall failed: lib=%u sl=%u\n",
               pResult ? pResult->iDmiLibStatus : 0,
               pResult ? pResult->iSlStatus     : 0);
        return 1;
    }

    printf("Registered as component ID %u\n", pResult->iComponentId);

    /* Component runs its event loop here, handling
       DmiInvoke() calls from the SL ...             */

    return 0;
}

Sending an Event Indication

#include <dmiapi.h>
#include <dmi.h>
#include <string.h>

void SendThermalEvent(DMI_UNSIGNED componentId)
{
    DMI_Indicate_t ind;
    memset(&ind, 0, sizeof(ind));

    ind.iLevelCheck      = DMI_LEVEL_CHECK;
    ind.iIndicationType  = DMI_EVENT_INDICATION;
    ind.iCmdLen          = sizeof(ind);
    ind.iComponentId     = componentId;
    /* DmiTimeStamp filled with current time ... */
    ind.pResponseFunc    = NULL; /* no async callback needed */
    ind.oIndicationData  = 0;   /* no additional event data */

    DmiIndicate(&ind);
}

Error Codes

DMIAPI.LIB defines its own error code namespace distinct from OS/2 and from the SL status codes:

Constant Value Meaning
DmiLibDirInstallNoError 1 MIF directory install succeeded (no SL confirmation needed)
DmiLibSlInstallNoError 2 SL install succeeded; iComponentId is valid
DmiLibIllegalFileType 0x101 iFileType was not a valid MIF or SNMP mapping type
DmiLibCannotCloseDestinationFile 0x201 Error closing compiled MIF output file
DmiLibCannotCreateDestinationFile 0x202 Cannot create MIF output file (check DMIDIR permissions)
DmiLibCannotCreateDirectory 0x203 Cannot create DMIDIR directory
DmiLibCannotOpenSourceFile 0x204 MIF source file not found or unreadable
DmiLibCannotReadSourceFile 0x205 Error reading MIF source file
DmiLibCannotWriteDestinationFile 0x206 Error writing compiled MIF output
DmiLibCannotExecuteInstallCommand 0x301 Could not execute the SL install command
DmiLibCannotRunServiceLayer 0x302 Service Layer (DMISL.EXE) is not running
DmiLibCannotAllocateMemory 0x401 Memory allocation failure
DmiLibCannotSetDmiDirEnvironmentVariable 0x402 Cannot set DMIDIR environment variable
DmiLibDmiDirEnvironmentVariableNotDefined 0x403 DMIDIR not set and pDmiDir was NULL

Relationship to the Full DMI Protocol

DMIAPI.LIB is a thin helper layer. The full DMI protocol is implemented at a lower level through direct IPC with DMISL.EXE (the Service Layer) using OS/2 named pipes. DMIAPI.LIB provides:

Function What it wraps
DmiInstall MIF file compilation + IPC call to DMISL to register a component
DmiInvoke The instrumentation DLL's own exported entry point (not a wrapper — this is the SL callback target)
DmiIndicate IPC call to DMISL to post an indication
DmiCiProcess In-process dispatch of attribute Get/Set/Reserve/Release to the CI skeleton callbacks

Management applications that only query DMI data (they do not implement instrumentation) do not need DMIAPI.LIB. They send DMI_MgmtCommand_t structures directly through named pipe IPC to DMISL.EXE, or they use the higher-level DMI Workbench APIs.

Version History

Version Date Notes
DMI 1.0 1992 Intel/DMTF initial specification. DMI_LEVEL_CHECK_V1 = 0x444D4931 ("DMI1").
DMI 2.0 1993–1994 DMTF extended: tabular groups (rows), SNMP mapping, 64-bit counters, group procedures (Invoke), language mappings. DMI_LEVEL_CHECK = 0x444D3131 ("DM11"). IBM joined the specification effort.
OS/2 Warp 4 integration 1996 IBM ships DMISL.EXE and DMIAPI.DLL as part of OS/2 Warp 4 Hardware Manager / Client/Server Pack.
Final Toolkit 4.5 release 2001-10-02 File size 1,536 bytes. No new functions; Intel/IBM copyright headers updated.

See Also