Problem with precompiled libraw 0.14.7

// typedefinition: somewhere in another h file:
 
typedef libraw_data_t *           (*libraw_init_dll_def)(int v);
typedef void                      (*libraw_set_progress_handler_dll_def)(libraw_data_t*,progress_callback cb,void *datap);
typedef int                       (*libraw_open_file_dll_def)(libraw_data_t*, const char *);
typedef int                       (*libraw_adjust_sizes_info_only_dll_def)(libraw_data_t*);
typedef void                      (*libraw_close_dll_def)(libraw_data_t*);
typedef int                       (*libraw_unpack_dll_def)(libraw_data_t*);
typedef int                       (*libraw_dcraw_process_dll_def)(libraw_data_t* lr);
typedef libraw_processed_image_t* (*libraw_dcraw_make_mem_image_dll_def)(libraw_data_t* lr, int *errc);
typedef void                      (*libraw_dcraw_clear_mem_dll_def)(libraw_processed_image_t*);
typedef void                      (*libraw_recycle_dll_def)(libraw_data_t*);
typedef void                      (*libraw_set_progress_handler_dll_def)(libraw_data_t*,progress_callback cb,void *datap);
typedef const char*               (*libraw_version_dll_def)();
typedef libraw_processed_image_t* (*libraw_dcraw_make_mem_thumb_dll_def)(libraw_data_t* lr, int *errc);
typedef int                       (*libraw_unpack_thumb_dll_def)(libraw_data_t*);
 
// ***********************************************************************************************************************
 
// function pointers declaration from GetProcAddress:
libraw_data_t *           libraw_init_dll (int v);
void                      libraw_set_progress_handler(libraw_data_t*,progress_callback cb,void *datap);
int                       libraw_open_file(libraw_data_t*, const char *filename);
int                       libraw_adjust_sizes_info_only(libraw_data_t *ptr);
void                      libraw_close(libraw_data_t *ptr);
int                       libraw_unpack(libraw_data_t *ptr);
int                       libraw_dcraw_process(libraw_data_t* lr);
libraw_processed_image_t* libraw_dcraw_make_mem_image(libraw_data_t* lr, int *errc);
void                      libraw_dcraw_clear_mem(libraw_processed_image_t*);
void                      libraw_recycle(libraw_data_t *ptr);
const char*               libraw_version();
libraw_processed_image_t* libraw_dcraw_make_mem_thumb(libraw_data_t* lr, int *errc);
int                       libraw_unpack_thumb(libraw_data_t *ptr);
 
// ***********************************************************************************************************************
// function pointers
libraw_init_dll_def                   libraw_init_ptr                   = 0;
libraw_set_progress_handler_dll_def   libraw_set_progress_handler_ptr   = 0;
libraw_open_file_dll_def              libraw_open_file_ptr              = 0;
libraw_adjust_sizes_info_only_dll_def libraw_adjust_sizes_info_only_ptr = 0;
libraw_close_dll_def                  libraw_close_ptr                  = 0;
libraw_unpack_dll_def                 libraw_unpack_ptr                 = 0;
libraw_dcraw_process_dll_def          libraw_dcraw_process_ptr          = 0;
libraw_dcraw_make_mem_image_dll_def   libraw_dcraw_make_mem_image_ptr   = 0;
libraw_dcraw_clear_mem_dll_def        libraw_dcraw_clear_mem_ptr        = 0;
libraw_recycle_dll_def                libraw_recycle_ptr                = 0;
libraw_version_dll_def                libraw_version_ptr                = 0;
libraw_dcraw_make_mem_thumb_dll_def   libraw_dcraw_make_mem_thumb_ptr   = 0;
libraw_unpack_thumb_dll_def           libraw_unpack_thumb_ptr           = 0;
 
// ***********************************************************************************************************************
 
// somewhere in my init function
HMODULE hInstDLL = LoadLibrary ("libraw.dll");
if (hInstDLL)
{
    libraw_init_ptr                   = (libraw_init_dll_def)                   GetProcAddress (hInstDLL, "libraw_init");
    libraw_set_progress_handler_ptr   = (libraw_set_progress_handler_dll_def)   GetProcAddress (hInstDLL, "libraw_set_progress_handler");
    libraw_open_file_ptr              = (libraw_open_file_dll_def)              GetProcAddress (hInstDLL, "libraw_open_file");
    libraw_adjust_sizes_info_only_ptr = (libraw_adjust_sizes_info_only_dll_def) GetProcAddress (hInstDLL, "libraw_adjust_sizes_info_only");
    libraw_close_ptr                  = (libraw_close_dll_def)                  GetProcAddress (hInstDLL, "libraw_close");
    libraw_unpack_ptr                 = (libraw_unpack_dll_def)                 GetProcAddress (hInstDLL, "libraw_unpack");
    libraw_dcraw_process_ptr          = (libraw_dcraw_process_dll_def)          GetProcAddress (hInstDLL, "libraw_dcraw_process");
    libraw_dcraw_make_mem_image_ptr   = (libraw_dcraw_make_mem_image_dll_def)   GetProcAddress (hInstDLL, "libraw_dcraw_make_mem_image");
    libraw_dcraw_clear_mem_ptr        = (libraw_dcraw_clear_mem_dll_def)        GetProcAddress (hInstDLL, "libraw_dcraw_clear_mem");
    libraw_recycle_ptr                = (libraw_recycle_dll_def)                GetProcAddress (hInstDLL, "libraw_recycle");
    libraw_version_ptr                = (libraw_version_dll_def)                GetProcAddress (hInstDLL, "libraw_version");
    libraw_dcraw_make_mem_thumb_ptr   = (libraw_dcraw_make_mem_thumb_dll_def)   GetProcAddress (hInstDLL, "libraw_dcraw_make_mem_thumb");
    libraw_unpack_thumb_ptr           = (libraw_unpack_thumb_dll_def)           GetProcAddress (hInstDLL, "libraw_unpack_thumb");
}
 
// ***********************************************************************************************************************
 
// use C code only
libraw_data_t *ptr = (libraw_data_t*) libraw_init_ptr (0);
if (ptr)
{
    ret = libraw_open_file_ptr (ptr, pfilename);
    if (ret == LIBRAW_SUCCESS)
    {
        ret = libraw_unpack_thumb_ptr (ptr);
        if (ret == LIBRAW_SUCCESS)
        {
            libraw_processed_image_t *thumb = libraw_dcraw_make_mem_thumb_ptr (ptr, &ret); // thumb data is decoded correctly
            if (thumb && ret == LIBRAW_SUCCESS)
            {
                ret = libraw_adjust_sizes_info_only_ptr (ptr);
                if (ret == LIBRAW_SUCCESS)
                {
                    // ptr->idata.make;  decoded correctly
                    // ptr->idata.model; decoded correctly
 
                    // ptr->sizes.width;  decoded correctly
                    // ptr->sizes.height; decoded correctly
 
                    /*
                      iso_speed should be 80
                      shutter   should be 1/1600.0 sec
                      aperture  should be f/3.3
                      focal_len should be 19.2 mm
 
 
                      but I get the following values:
 
                      iso_speed is 0 !! (why?)
                      shutter   is 80
                      aperture  is 1/1600.0 sec
                      focal_len is f/3.3
                    */
 
                    libraw_dcraw_clear_mem_ptr (thumb);
                } // if (ret == LIBRAW_SUCCESS -> libraw_adjust_sizes_info_only
            } // if (thumb)
        } // if (ret == LIBRAW_SUCCESS -> libraw_unpack_thumb
    } // if (ret == LIBRAW_SUCCESS)
 
    if (ptr)
        libraw_close_ptr (ptr);
    ptr = 0;
} // if ptr

I have compiled with Microsoft Visual C++ 6.0 including the latest service packs and SDK 2003 includes+libs.
Everything works fine but iso_speed is _always_ 0.
I have tried it with code alignment of 4, 8 and even 16 bytes. iso_speed is still 0.

(There is no possibility to use another compiler or compile libraw by myself).

Please help :-)

Forums: 

It looks like your code uses

It looks like your code uses different structure fields alignment than in compiled libraw.dll

LibRaw.dll is compiled using Makefile.msvc with Visual Studio 2010 on 64 bit machine. There are no additional compiler flags for structure fields alignment, defaults used.

-- Alex Tutubalin @LibRaw LLC

Solution 8-)

Finally I have found a solution:

I added an alignment before some structures:

__declspec(align(8)) typedef struct
{
float iso_speed;
float shutter;
float aperture;
float focal_len;
time_t timestamp;
unsigned shot_order;
unsigned gpsdata[32];
char desc[512],
artist[64];
} libraw_imgother_t;

__declspec(align(8)) typedef struct
{
unsigned int progress_flags;
unsigned int process_warnings;
libraw_iparams_t idata;
libraw_image_sizes_t sizes;
libraw_colordata_t color;
libraw_imgother_t other;
libraw_thumbnail_t thumbnail;
libraw_rawdata_t rawdata;
ushort (*image)[4] ;
libraw_output_params_t params;
void *parent_class;
} libraw_data_t;

Everything works fine now and I am getting all correct metadata values (ISO...).

I guess, the default structure fields alignment on VS2010 is 8 bytes and not 4 bytes.

Thanks for your help :-)

It looks like I need to set

It looks like I need to set explicit alignment for public structure members.

OK.

-- Alex Tutubalin @LibRaw LLC