ADC MCP3421 sample rate problem
When you repeatedly ask for the configuration byte after the data bytes( 2 in the case of 12/14/16bit and 3 in case of 18bit ) the config register is changing. So if your code counts in the last config value acquired you might miss an RDY flag or get a wrong one.

My code did that and it is a bug.

Workaround is asking the correct amount of bytes or the following code.

/**
 * \brief Reads all mcp3421 registers.
 * 
 * \bug Needs a timeout mechanism or it might hang in a loop if device hardware fails.
 * 
 * It reads mcp3421 and expects either 4 or 3 bytes.
 * If it is in 18-bit all bytes are used.
 * If it is not 18-bit the lower byte is not used.
 * 
 * In 12/14/16-bit the middle byte is set to zero.
 * 
 * \param[in,out]   me          The mcp3421 handle.
 * \param[out]      upper       The first byte.
 * \param[out]      middle      The second byte.
 * \param[out]      lower       The third byte(18bit) or configuration byte(12,14,16bit).
 * \param[out]      config_reg  Register is the 3rd byte(12,14,16bit) in row or the 4rth(18bit).
 * 
 * \retval          0           Success.
 * \retval          1           Failed.
 */
static int mcp3421_read_all( mcp3421_t* me, uint8_t* upper, uint8_t* middle, uint8_t* lower, uint8_t* config_reg )
{
    //TODO: Add timeout_ms
    uint32_t err = 0;
    do 
    {
        /* Read mcp3421 register */
        uint8_t data[4] = { 0x00, 0x00, 0x00, 0x90 };
        if( i2c_master_receive( &amp;(me-&gt;bus), me-&gt;address, data, 4U, MCP3421_TIMEOUT ) )
        {
            /* Exit with error */
            errorHandler();
            return 1;
        }

        /* Get data */
        *config_reg = data[3];//This is config for all data rates.
        if( mcp3421_unmarshal_sample_rate( *config_reg ) == mcp3421_sample_rate_18bit )
        {
            /* 18 bit */
            *upper = data[0];
            *middle = data[1];
            *lower = data[2];
            *config_reg = data[3];
        }
        else
        {
            /* 12/14/16 bit */
            *upper = data[0];
            //*middle = 0;
            *lower = data[1];
            *config_reg = data[2];
        }

        /* Check if registers are updated */
        if( ( (*config_reg) &amp; RDY_Mask ) == 0 )
        {
            /* Exit with success */
            return 0;
        }
        err++;
    }
    while( err&lt;1000 );

    /* Exit with failure */
    errorHandler();
    return 1;
}