This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

TM4C123GE6PZ: Using a structure in a function without ever initializing it

Hello,

The following code snippet is from the Launchpad's lab14:
"g_sISL29023Inst" is a pointer to structure that's passed to the "ISL29023Init" function.
But I don't see that the structure is initialized with any data before the ISL29023Init function call - can you please explain this 

int
main(void)
{
float fAmbient;
uint8_t ui8Mask;
ROM_SysCtlClockSet(SYSCTL_SYSDIV_5|SYSCTL_USE_PLL|SYSCTL_XTAL_16MHZ|SYSCTL_OSC_MAIN);
ROM_SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOD);
ROM_SysCtlPeripheralEnable(SYSCTL_PERIPH_I2C3);
ROM_GPIOPinConfigure(GPIO_PD0_I2C3SCL);
ROM_GPIOPinConfigure(GPIO_PD1_I2C3SDA);
GPIOPinTypeI2CSCL(GPIO_PORTD_BASE, GPIO_PIN_0);
ROM_GPIOPinTypeI2C(GPIO_PORTD_BASE, GPIO_PIN_1);
ROM_IntMasterEnable();
I2CMInit(&g_sI2CInst, I2C3_BASE, INT_I2C3, 0xFF, 0xFF, ROM_SysCtlClockGet());
SysCtlDelay(SysCtlClockGet() / 3);
ISL29023Init(&g_sISL29023Inst, &g_sI2CInst,
ISL29023_I2C_ADDRESS,ISL29023AppCallback, &g_sISL29023Inst);
ISL29023AppI2CWait(__FILE__, __LINE__);
ui8Mask = (ISL29023_CMD_I_OP_MODE_M );
ISL29023ReadModifyWrite(&g_sISL29023Inst, ISL29023_O_CMD_I, ~ui8Mask,
(ISL29023_CMD_I_OP_MODE_ALS_CONT),
ISL29023AppCallback, &g_sISL29023Inst);
ISL29023AppI2CWait(__FILE__, __LINE__);
while(1)
{
ISL29023DataRead(&g_sISL29023Inst, ISL29023AppCallback, &g_sISL29023Inst);
ISL29023AppI2CWait(__FILE__, __LINE__);
ISL29023DataLightVisibleGetFloat(&g_sISL29023Inst, &fAmbient);
}
}


  • It is in the beginning of the file. Please see below. And the tISL29023  type is defined in the sensorlib/isl29023.h

    #include "stdint.h"
    #include "stdbool.h"
    #include "inc/hw_memmap.h"
    #include "inc/hw_ints.h"
    #include "driverlib/debug.h"
    #include "driverlib/gpio.h"
    #include "driverlib/interrupt.h"
    #include "driverlib/pin_map.h"
    #include "driverlib/rom.h"
    #include "driverlib/sysctl.h"
    #include "sensorlib/hw_isl29023.h"
    #include "sensorlib/i2cm_drv.h"
    #include "sensorlib/isl29023.h"
    #define DEBUG

    #define ISL29023_I2C_ADDRESS 0x44 // ISL29023 I2C address
    tI2CMInstance g_sI2CInst; // I2C master driver structure
    tISL29023 g_sISL29023Inst; // ISL29023 sensor driver structure
    volatile unsigned long g_vui8DataFlag; // Data ready flag
    volatile unsigned long g_vui8ErrorFlag; // Error flag

  • Hi,

    I can see the type is defined in isl29023.h and I also see that it's instantiated in the row you highlighted...
    But "g_sISL29023Inst" is a structure with many elements.
    I can't see where these elements are given an initial value.
  • Hi,

      The structure is initialized when ISL29023Init is called. 

    //*****************************************************************************
    //
    //! Initializes the ISL29023 driver.
    //!
    //! \param psInst is a pointer to the ISL29023 instance data.
    //! \param psI2CInst is a pointer to the I2C driver instance data.
    //! \param ui8I2CAddr is the I2C address of the ISL29023 device.
    //! \param pfnCallback is the function to be called when the initialization has
    //! completed (can be \b NULL if a callback is not required).
    //! \param pvCallbackData is a pointer that is passed to the callback function.
    //!
    //! This function initializes the ISL29023 driver, preparing it for operation.
    //! This function also asserts a reset signal to the ISL29023 to clear any
    //! previous configuration data.
    //!
    //! \return Returns 1 if the ISL29023 driver was successfully initialized and 0
    //! if it was not.
    //
    //*****************************************************************************
    uint_fast8_t
    ISL29023Init(tISL29023 *psInst, tI2CMInstance *psI2CInst,
                 uint_fast8_t ui8I2CAddr, tSensorCallback *pfnCallback,
                 void *pvCallbackData)
    {
        //
        // Initialize the ISL29023 instance structure
        //
        psInst->psI2CInst = psI2CInst;
        psInst->ui8Addr = ui8I2CAddr;
        psInst->ui8State = ISL29023_STATE_INIT;
        psInst->ui8Range = ISL29023_CMD_II_RANGE_1K >> ISL29023_CMD_II_RANGE_S;
        psInst->ui8NewRange = ISL29023_CMD_II_RANGE_1K >> ISL29023_CMD_II_RANGE_S;
        psInst->ui8Resolution = (ISL29023_CMD_II_ADC_RES_16 >>
                                 ISL29023_CMD_II_ADC_RES_S);
        psInst->ui8NewResolution = (ISL29023_CMD_II_ADC_RES_16 >>
                                    ISL29023_CMD_II_ADC_RES_S);
    
        //
        // Save the callback information.
        //
        psInst->pfnCallback = pfnCallback;
        psInst->pvCallbackData = pvCallbackData;
    
        //
        // Put the device into power down mode.
        //
        psInst->pui8Data[0] = ISL29023_O_CMD_I;
        psInst->pui8Data[1] = ISL29023_CMD_I_OP_MODE_POWER_DOWN;
        if(I2CMWrite(psInst->psI2CInst, psInst->ui8Addr, psInst->pui8Data, 2,
                     ISL29023Callback, psInst) == 0)
        {
            //
            // The I2C write failed, so move to the idle state and return a
            // failure.
            //
            psInst->ui8State = ISL29023_STATE_IDLE;
            return(0);
        }
    
        //
        // Success
        //
        return(1);

  • Thanks.

    Another question about something that seems strange to me.
    I see that one of the input argument to the "ISL29023Init" is: "ISL29023AppCallback".
    But ISL29023AppCallback is by itself a function that returns void.

    Why have a function call inside as an input argument to another function call ??
  • Yes, this is a form of async callbacks. In C language you can pass a callback function pointer as a argument to a calling function. You first register the callback in the calling function. This is a non-blocking operation. When an event happens the callback function will be called. Below is a good article talking about how callbacks work.

    opensourceforu.com/.../
  • Thanks!

    I'll read it and start another topic if I have any questions.

    I'm having trouble finding the typedef for tSensorCallback of the  "ISL29023Init" init function.

    Can you please point me to the header file that contains it ?

    ISL29023Init(tISL29023 *psInst, tI2CMInstance *psI2CInst,

                uint_fast8_t ui8I2CAddr, tSensorCallback *pfnCallback,

                void *pvCallbackData)

  • Hi,
    I just answered the same question in the other thread. e2e.ti.com/.../734757