/*
 * Copyright 2000 Corel Corporation
 * Copyright 2006 Marcus Meissner
 * Copyright 2006 CodeWeavers, Aric Stewart
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include "config.h"
#include "wine/port.h"
#include "wine/library.h"

#include <stdarg.h>
#include <stdio.h>

#include "windef.h"
#include "winbase.h"
#include "wingdi.h"
#include "winuser.h"
#include "twain.h"
#include "gphoto2_i.h"
#include "wine/debug.h"

WINE_DEFAULT_DEBUG_CHANNEL(twain);

#ifdef HAVE_GPHOTO2
static void *libjpeg_handle;
#define MAKE_FUNCPTR(f) static typeof(f) * p##f
MAKE_FUNCPTR(jpeg_std_error);
MAKE_FUNCPTR(jpeg_CreateDecompress);
MAKE_FUNCPTR(jpeg_read_header);
MAKE_FUNCPTR(jpeg_start_decompress);
MAKE_FUNCPTR(jpeg_read_scanlines);
MAKE_FUNCPTR(jpeg_finish_decompress);
MAKE_FUNCPTR(jpeg_destroy_decompress);
#undef MAKE_FUNCPTR

static void *load_libjpeg(void)
{
    if((libjpeg_handle = wine_dlopen(SONAME_LIBJPEG, RTLD_NOW, NULL, 0)) != NULL) {

#define LOAD_FUNCPTR(f) \
    if((p##f = wine_dlsym(libjpeg_handle, #f, NULL, 0)) == NULL) { \
        libjpeg_handle = NULL; \
        return NULL; \
    }

        LOAD_FUNCPTR(jpeg_std_error);
        LOAD_FUNCPTR(jpeg_CreateDecompress);
        LOAD_FUNCPTR(jpeg_read_header);
        LOAD_FUNCPTR(jpeg_start_decompress);
        LOAD_FUNCPTR(jpeg_read_scanlines);
        LOAD_FUNCPTR(jpeg_finish_decompress);
        LOAD_FUNCPTR(jpeg_destroy_decompress);
#undef LOAD_FUNCPTR
    }
    return libjpeg_handle;
}


/* for the jpeg decompressor source manager. */
static void _jpeg_init_source(j_decompress_ptr cinfo) { }

static boolean _jpeg_fill_input_buffer(j_decompress_ptr cinfo) {
    ERR("(), should not get here.\n");
    return FALSE;
}

static void _jpeg_skip_input_data(j_decompress_ptr cinfo,long num_bytes) {
    TRACE("Skipping %ld bytes...\n", num_bytes);
    cinfo->src->next_input_byte += num_bytes;
    cinfo->src->bytes_in_buffer -= num_bytes;
}

static boolean _jpeg_resync_to_restart(j_decompress_ptr cinfo, int desired) {
    ERR("(desired=%d), should not get here.\n",desired);
    return FALSE;
}
static void _jpeg_term_source(j_decompress_ptr cinfo) { }
#endif

/* DG_IMAGE/DAT_CIECOLOR/MSG_GET */
TW_UINT16 GPHOTO2_CIEColorGet (pTW_IDENTITY pOrigin, 
                             TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_EXTIMAGEINFO/MSG_GET */
TW_UINT16 GPHOTO2_ExtImageInfoGet (pTW_IDENTITY pOrigin, 
                                 TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_GRAYRESPONSE/MSG_RESET */
TW_UINT16 GPHOTO2_GrayResponseReset (pTW_IDENTITY pOrigin, 
                                   TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_GRAYRESPONSE/MSG_SET */
TW_UINT16 GPHOTO2_GrayResponseSet (pTW_IDENTITY pOrigin, 
                                 TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_IMAGEFILEXFER/MSG_GET */
TW_UINT16 GPHOTO2_ImageFileXferGet (pTW_IDENTITY pOrigin, 
                                  TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

#ifdef HAVE_GPHOTO2
static TW_UINT16 _get_image_and_startup_jpeg() {
    const char *folder = NULL, *filename = NULL;
    struct gphoto2_file *file;
    const unsigned char *filedata;
    unsigned long filesize;
    int ret;

    if (activeDS.file) /* Already loaded. */
	return TWRC_SUCCESS;

    if(!libjpeg_handle) {
	if(!load_libjpeg()) {
	    FIXME("Failed reading JPEG because unable to find %s\n", SONAME_LIBJPEG);
	    filedata = NULL;
	    return TWRC_FAILURE;
	}
    }

    LIST_FOR_EACH_ENTRY( file, &activeDS.files, struct gphoto2_file, entry ) {
	if (strstr(file->filename,".JPG") || strstr(file->filename,".jpg")) {
	    filename = file->filename;
	    folder = file->folder;
	    TRACE("downloading %s/%s\n", folder, filename);
	    if (file->download) {
		file->download = FALSE; /* mark as done */
		break;
	    }
	}
    }
    gp_file_new (&activeDS.file);
    ret = gp_camera_file_get(activeDS.camera, folder, filename, GP_FILE_TYPE_NORMAL,
			     activeDS.file, activeDS.context);
    if (ret < GP_OK) {
	FIXME("Failed to get file?\n");
	activeDS.twCC = TWCC_SEQERROR;
	return TWRC_FAILURE;
    }
    ret = gp_file_get_data_and_size (activeDS.file, (const char**)&filedata, &filesize);
    if (ret < GP_OK) {
	FIXME("Failed to get file data?\n");
	activeDS.twCC = TWCC_SEQERROR;
	return TWRC_FAILURE;
    }

    /* This is basically so we can use in-memory data for jpeg decompression.
     * We need to have all the functions.
     */
    activeDS.xjsm.next_input_byte	= filedata;
    activeDS.xjsm.bytes_in_buffer	= filesize;
    activeDS.xjsm.init_source	= _jpeg_init_source;
    activeDS.xjsm.fill_input_buffer	= _jpeg_fill_input_buffer;
    activeDS.xjsm.skip_input_data	= _jpeg_skip_input_data;
    activeDS.xjsm.resync_to_restart	= _jpeg_resync_to_restart;
    activeDS.xjsm.term_source	= _jpeg_term_source;

    activeDS.jd.err = pjpeg_std_error(&activeDS.jerr);
    /* jpeg_create_decompress is a macro that expands to jpeg_CreateDecompress - see jpeglib.h
     * jpeg_create_decompress(&jd); */
    pjpeg_CreateDecompress(&activeDS.jd, JPEG_LIB_VERSION, (size_t) sizeof(struct jpeg_decompress_struct));
    activeDS.jd.src = &activeDS.xjsm;
    ret=pjpeg_read_header(&activeDS.jd,TRUE);
    activeDS.jd.out_color_space = JCS_RGB;
    pjpeg_start_decompress(&activeDS.jd);
    if (ret != JPEG_HEADER_OK) {
	ERR("Jpeg image in stream has bad format, read header returned %d.\n",ret);
	gp_file_unref (activeDS.file);
	activeDS.file = NULL;
	return TWRC_FAILURE;
    }
    return TWRC_SUCCESS;
}
#endif

/* DG_IMAGE/DAT_IMAGEINFO/MSG_GET */
TW_UINT16 GPHOTO2_ImageInfoGet (pTW_IDENTITY pOrigin, 
                              TW_MEMREF pData)
{
#ifdef HAVE_GPHOTO2
    pTW_IMAGEINFO pImageInfo = (pTW_IMAGEINFO) pData;

    TRACE("DG_IMAGE/DAT_IMAGEINFO/MSG_GET\n");

    if (activeDS.currentState != 6 && activeDS.currentState != 7) {
        activeDS.twCC = TWCC_SEQERROR;
        return TWRC_FAILURE;
    }
    if (TWRC_SUCCESS != _get_image_and_startup_jpeg()) {
	FIXME("Failed to get an image\n");
        activeDS.twCC = TWCC_SEQERROR;
	return TWRC_FAILURE;
    }
    if (activeDS.currentState == 6)
    {
        /* return general image description information about the image about to be transferred */
        TRACE("Getting parameters\n");
    }
    TRACE("activeDS.jd.output_width = %d\n", activeDS.jd.output_width);
    TRACE("activeDS.jd.output_height = %d\n", activeDS.jd.output_height);
    pImageInfo->Compression	= TWCP_NONE;
    pImageInfo->SamplesPerPixel	= 3;
    pImageInfo->BitsPerSample[0]= 8;
    pImageInfo->BitsPerSample[1]= 8;
    pImageInfo->BitsPerSample[2]= 8;
    pImageInfo->PixelType 	= TWPT_RGB;
    pImageInfo->Planar		= FALSE; /* R-G-B is chunky! */
    pImageInfo->XResolution.Whole = -1;
    pImageInfo->XResolution.Frac = 0;
    pImageInfo->YResolution.Whole = -1;
    pImageInfo->YResolution.Frac = 0;
    pImageInfo->ImageWidth 	= activeDS.jd.output_width;
    pImageInfo->ImageLength 	= activeDS.jd.output_height;
    pImageInfo->BitsPerPixel	= 24;
    return TWRC_SUCCESS;
#else
    return TWRC_FAILURE;
#endif
}

/* DG_IMAGE/DAT_IMAGELAYOUT/MSG_GET */
TW_UINT16 GPHOTO2_ImageLayoutGet (pTW_IDENTITY pOrigin, 
                                TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_IMAGELAYOUT/MSG_GETDEFAULT */
TW_UINT16 GPHOTO2_ImageLayoutGetDefault (pTW_IDENTITY pOrigin, 
                                       TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_IMAGELAYOUT/MSG_RESET */
TW_UINT16 GPHOTO2_ImageLayoutReset (pTW_IDENTITY pOrigin, 
                                  TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_IMAGELAYOUT/MSG_SET */
TW_UINT16 GPHOTO2_ImageLayoutSet (pTW_IDENTITY pOrigin, 
                                TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_IMAGEMEMXFER/MSG_GET */
TW_UINT16 GPHOTO2_ImageMemXferGet (pTW_IDENTITY pOrigin, 
                                 TW_MEMREF pData)
{
#ifdef HAVE_GPHOTO2
    TW_UINT16 twRC = TWRC_SUCCESS;
    pTW_IMAGEMEMXFER pImageMemXfer = (pTW_IMAGEMEMXFER) pData;
    LPBYTE buffer;
    int readrows;
    unsigned int curoff;

    TRACE ("DG_IMAGE/DAT_IMAGEMEMXFER/MSG_GET\n");
    if (activeDS.currentState < 6 || activeDS.currentState > 7) {
        activeDS.twCC = TWCC_SEQERROR;
        return TWRC_FAILURE;
    }
    TRACE("pImageMemXfer.Compression is %d\n", pImageMemXfer->Compression);
    if (activeDS.currentState == 6) {
	if (TWRC_SUCCESS != _get_image_and_startup_jpeg()) {
	    FIXME("Failed to get an image\n");
	    activeDS.twCC = TWCC_SEQERROR;
	    return TWRC_FAILURE;
	}

    if (!activeDS.progressWnd)
        activeDS.progressWnd = TransferringDialogBox(NULL,0);
    TransferringDialogBox(activeDS.progressWnd,0);

        activeDS.currentState = 7;
    } else {
	if (!activeDS.file) {
    	    activeDS.twCC = TWRC_SUCCESS;
	    return TWRC_XFERDONE;
	}
    }

    if (pImageMemXfer->Memory.Flags & TWMF_HANDLE) {
	FIXME("Memory Handle, may not be locked correctly\n");
	buffer = LocalLock(pImageMemXfer->Memory.TheMem);
    } else
	buffer = pImageMemXfer->Memory.TheMem;
   
    memset(buffer,0,pImageMemXfer->Memory.Length);
    curoff = 0; readrows = 0;
    pImageMemXfer->YOffset	= activeDS.jd.output_scanline;
    pImageMemXfer->XOffset	= 0;	/* we do whole strips */
    while ((activeDS.jd.output_scanline<activeDS.jd.output_height) &&
	   ((pImageMemXfer->Memory.Length - curoff) > activeDS.jd.output_width*activeDS.jd.output_components)
    ) {
	JSAMPROW row = buffer+curoff;
	int x = pjpeg_read_scanlines(&activeDS.jd,&row,1);
	if (x != 1) {
		FIXME("failed to read current scanline?\n");
		break;
	}
	readrows++;
	curoff += activeDS.jd.output_width*activeDS.jd.output_components;
    }
    pImageMemXfer->Compression	= TWCP_NONE;
    pImageMemXfer->BytesPerRow	= activeDS.jd.output_components * activeDS.jd.output_width;
    pImageMemXfer->Rows		= readrows;
    pImageMemXfer->Columns	= activeDS.jd.output_width; /* we do whole strips */
    pImageMemXfer->BytesWritten = curoff;

    TransferringDialogBox(activeDS.progressWnd,0);

    if (activeDS.jd.output_scanline == activeDS.jd.output_height) {
        pjpeg_finish_decompress(&activeDS.jd);
        pjpeg_destroy_decompress(&activeDS.jd);
	gp_file_unref (activeDS.file);
	activeDS.file = NULL;
	TRACE("xfer is done!\n");

	/*TransferringDialogBox(activeDS.progressWnd, -1);*/
	twRC = TWRC_XFERDONE;
    }
    activeDS.twCC = TWRC_SUCCESS;
    if (pImageMemXfer->Memory.Flags & TWMF_HANDLE)
        LocalUnlock(pImageMemXfer->Memory.TheMem);
    return twRC;
#else
    return TWRC_FAILURE;
#endif
}

/* DG_IMAGE/DAT_IMAGENATIVEXFER/MSG_GET */
TW_UINT16 GPHOTO2_ImageNativeXferGet (pTW_IDENTITY pOrigin, 
                                    TW_MEMREF pData)
{
#ifdef HAVE_GPHOTO2
    pTW_UINT32 pHandle = (pTW_UINT32) pData;
    HBITMAP hDIB;
    BITMAPINFO bmpInfo;
    LPBYTE bits, oldbits;
    JSAMPROW samprow, oldsamprow;
    HDC dc;

    FIXME("DG_IMAGE/DAT_IMAGENATIVEXFER/MSG_GET: implemented, but expect program crash due to DIB.\n");

/*  NOTE NOTE NOTE NOTE NOTE NOTE NOTE
 *
 *  While this is a mandatory transfer mode and this function
 *  is correctly implemented and fully works, the calling program
 *  will likely crash after calling.
 *
 *  Reason is that there is a lot of example code that does:
 *  bmpinfo = (LPBITMAPINFOHEADER)GlobalLock(hBITMAP); ... pointer access to bmpinfo
 *
 *  Our current HBITMAP handles do not support getting GlobalLocked -> App Crash
 *
 *  This needs a GDI Handle rewrite, at least for DIB sections.
 *  - Marcus
 */
    if (activeDS.currentState != 6) {
        activeDS.twCC = TWCC_SEQERROR;
        return TWRC_FAILURE;
    }
    if (TWRC_SUCCESS != _get_image_and_startup_jpeg()) {
	FIXME("Failed to get an image\n");
	activeDS.twCC = TWCC_OPERATIONERROR;
	return TWRC_FAILURE;
    }
    TRACE("Acquiring image %dx%dx%d bits from gphoto.\n",
	activeDS.jd.output_width, activeDS.jd.output_height,
	activeDS.jd.output_components*8);
    ZeroMemory (&bmpInfo, sizeof (BITMAPINFO));
    bmpInfo.bmiHeader.biSize = sizeof (BITMAPINFOHEADER);
    bmpInfo.bmiHeader.biWidth = activeDS.jd.output_width;
    bmpInfo.bmiHeader.biHeight = -activeDS.jd.output_height;
    bmpInfo.bmiHeader.biPlanes = 1;
    bmpInfo.bmiHeader.biBitCount = activeDS.jd.output_components*8;
    bmpInfo.bmiHeader.biCompression = BI_RGB;
    bmpInfo.bmiHeader.biSizeImage = 0;
    bmpInfo.bmiHeader.biXPelsPerMeter = 0;
    bmpInfo.bmiHeader.biYPelsPerMeter = 0;
    bmpInfo.bmiHeader.biClrUsed = 0;
    bmpInfo.bmiHeader.biClrImportant = 0;
    hDIB = CreateDIBSection ((dc = GetDC(activeDS.hwndOwner)), &bmpInfo,
			     DIB_RGB_COLORS, (LPVOID)&bits, 0, 0);
    if (!hDIB) {
	FIXME("Failed creating DIB.\n");
	gp_file_unref (activeDS.file);
	activeDS.file = NULL;
	activeDS.twCC = TWCC_LOWMEMORY;
	return TWRC_FAILURE;
    }
    samprow = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,activeDS.jd.output_width*activeDS.jd.output_components);
    oldbits = bits;
    oldsamprow = samprow;
    while ( activeDS.jd.output_scanline<activeDS.jd.output_height ) {
	int i, x = pjpeg_read_scanlines(&activeDS.jd,&samprow,1);
	if (x != 1) {
		FIXME("failed to read current scanline?\n");
		break;
	}
	/* We have to convert from RGB to BGR, see MSDN/ BITMAPINFOHEADER */
	for(i=0;i<activeDS.jd.output_width;i++,samprow+=activeDS.jd.output_components) {
	    *(bits++) = *(samprow+2);
	    *(bits++) = *(samprow+1);
	    *(bits++) = *(samprow);
	}
	bits = (LPBYTE)(((UINT_PTR)bits + 3) & ~3);
	samprow = oldsamprow;
    }
    bits = oldbits;
    HeapFree (GetProcessHeap(), 0, samprow);
    gp_file_unref (activeDS.file);
    activeDS.file = NULL;
    ReleaseDC (activeDS.hwndOwner, dc);
    *pHandle = (TW_UINT32)hDIB;
    activeDS.twCC = TWCC_SUCCESS;
    activeDS.currentState = 7;
    return TWRC_XFERDONE;
#else
    return TWRC_FAILURE;
#endif
}

/* DG_IMAGE/DAT_JPEGCOMPRESSION/MSG_GET */
TW_UINT16 GPHOTO2_JPEGCompressionGet (pTW_IDENTITY pOrigin, 
                                    TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_JPEGCOMPRESSION/MSG_GETDEFAULT */
TW_UINT16 GPHOTO2_JPEGCompressionGetDefault (pTW_IDENTITY pOrigin,
                                           
                                           TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_JPEGCOMPRESSION/MSG_RESET */
TW_UINT16 GPHOTO2_JPEGCompressionReset (pTW_IDENTITY pOrigin, 
                                      TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_JPEGCOMPRESSION/MSG_SET */
TW_UINT16 GPHOTO2_JPEGCompressionSet (pTW_IDENTITY pOrigin, 
                                    TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_PALETTE8/MSG_GET */
TW_UINT16 GPHOTO2_Palette8Get (pTW_IDENTITY pOrigin, 
                             TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_PALETTE8/MSG_GETDEFAULT */
TW_UINT16 GPHOTO2_Palette8GetDefault (pTW_IDENTITY pOrigin, 
                                    TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_PALETTE8/MSG_RESET */
TW_UINT16 GPHOTO2_Palette8Reset (pTW_IDENTITY pOrigin, 
                               TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_PALETTE8/MSG_SET */
TW_UINT16 GPHOTO2_Palette8Set (pTW_IDENTITY pOrigin, 
                             TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_RGBRESPONSE/MSG_RESET */
TW_UINT16 GPHOTO2_RGBResponseReset (pTW_IDENTITY pOrigin, 
                                  TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

/* DG_IMAGE/DAT_RGBRESPONSE/MSG_SET */
TW_UINT16 GPHOTO2_RGBResponseSet (pTW_IDENTITY pOrigin, 
                                TW_MEMREF pData)
{
    FIXME ("stub!\n");

    return TWRC_FAILURE;
}

#ifdef HAVE_GPHOTO2
TW_UINT16
_get_gphoto2_file_as_DIB(
    const char *folder, const char *filename, CameraFileType type,
    HWND hwnd, HBITMAP *hDIB
) {
    const unsigned char *filedata;
    unsigned long	filesize;
    int			ret;
    CameraFile		*file;
    struct jpeg_source_mgr		xjsm;
    struct jpeg_decompress_struct	jd;
    struct jpeg_error_mgr		jerr;
    HDC 		dc;
    BITMAPINFO 		bmpInfo;
    LPBYTE		bits, oldbits;
    JSAMPROW		samprow, oldsamprow;

    if(!libjpeg_handle) {
	if(!load_libjpeg()) {
	    FIXME("Failed reading JPEG because unable to find %s\n", SONAME_LIBJPEG);
	    filedata = NULL;
	    return TWRC_FAILURE;
	}
    }

    gp_file_new (&file);
    ret = gp_camera_file_get(activeDS.camera, folder, filename, type, file, activeDS.context);
    if (ret < GP_OK) {
	FIXME("Failed to get file?\n");
	gp_file_unref (file);
	return TWRC_FAILURE;
    }
    ret = gp_file_get_data_and_size (file, (const char**)&filedata, &filesize);
    if (ret < GP_OK) {
	FIXME("Failed to get file data?\n");
	return TWRC_FAILURE;
    }

    /* FIXME: Actually we might get other types than JPEG ... But only handle JPEG for now */
    if (filedata[0] != 0xff) {
	ERR("File %s/%s might not be JPEG, cannot decode!\n", folder, filename);
    }

    /* This is basically so we can use in-memory data for jpeg decompression.
     * We need to have all the functions.
     */
    xjsm.next_input_byte	= filedata;
    xjsm.bytes_in_buffer	= filesize;
    xjsm.init_source	= _jpeg_init_source;
    xjsm.fill_input_buffer	= _jpeg_fill_input_buffer;
    xjsm.skip_input_data	= _jpeg_skip_input_data;
    xjsm.resync_to_restart	= _jpeg_resync_to_restart;
    xjsm.term_source	= _jpeg_term_source;

    jd.err = pjpeg_std_error(&jerr);
    /* jpeg_create_decompress is a macro that expands to jpeg_CreateDecompress - see jpeglib.h
     * jpeg_create_decompress(&jd); */
    pjpeg_CreateDecompress(&jd, JPEG_LIB_VERSION, (size_t) sizeof(struct jpeg_decompress_struct));
    jd.src = &xjsm;
    ret=pjpeg_read_header(&jd,TRUE);
    jd.out_color_space = JCS_RGB;
    pjpeg_start_decompress(&jd);
    if (ret != JPEG_HEADER_OK) {
	ERR("Jpeg image in stream has bad format, read header returned %d.\n",ret);
	gp_file_unref (file);
	return TWRC_FAILURE;
    }

    ZeroMemory (&bmpInfo, sizeof (BITMAPINFO));
    bmpInfo.bmiHeader.biSize = sizeof (BITMAPINFOHEADER);
    bmpInfo.bmiHeader.biWidth = jd.output_width;
    bmpInfo.bmiHeader.biHeight = -jd.output_height;
    bmpInfo.bmiHeader.biPlanes = 1;
    bmpInfo.bmiHeader.biBitCount = jd.output_components*8;
    bmpInfo.bmiHeader.biCompression = BI_RGB;
    bmpInfo.bmiHeader.biSizeImage = 0;
    bmpInfo.bmiHeader.biXPelsPerMeter = 0;
    bmpInfo.bmiHeader.biYPelsPerMeter = 0;
    bmpInfo.bmiHeader.biClrUsed = 0;
    bmpInfo.bmiHeader.biClrImportant = 0;
    *hDIB = CreateDIBSection ((dc = GetDC(hwnd)), &bmpInfo, DIB_RGB_COLORS, (LPVOID)&bits, 0, 0);
    if (!*hDIB) {
	FIXME("Failed creating DIB.\n");
	gp_file_unref (file);
	return TWRC_FAILURE;
    }
    samprow = HeapAlloc(GetProcessHeap(),HEAP_ZERO_MEMORY,jd.output_width*jd.output_components);
    oldbits = bits;
    oldsamprow = samprow;
    while ( jd.output_scanline<jd.output_height ) {
	int i, x = pjpeg_read_scanlines(&jd,&samprow,1);
	if (x != 1) {
	    FIXME("failed to read current scanline?\n");
	    break;
	}
	/* We have to convert from RGB to BGR, see MSDN/ BITMAPINFOHEADER */
	for(i=0;i<jd.output_width;i++,samprow+=jd.output_components) {
	    *(bits++) = *(samprow+2);
	    *(bits++) = *(samprow+1);
	    *(bits++) = *(samprow);
	}
	bits = (LPBYTE)(((UINT_PTR)bits + 3) & ~3);
	samprow = oldsamprow;
    }
    if (hwnd) ReleaseDC (hwnd, dc);
    HeapFree (GetProcessHeap(), 0, samprow);
    gp_file_unref (file);
    return TWRC_SUCCESS;
}
#endif
