/*
 * Copyright 1999 Marcus Meissner
 * Copyright 2002-2003 Michael Günnewig
 *
 * 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 <stdarg.h>

#define COBJMACROS

#include "windef.h"
#include "winbase.h"
#include "winnls.h"
#include "wingdi.h"
#include "winuser.h"
#include "winreg.h"
#include "winerror.h"

#include "ole2.h"
#include "shellapi.h"
#include "shlobj.h"
#include "vfw.h"
#include "msacm.h"

#include "avifile_private.h"

#include "wine/debug.h"
#include "wine/unicode.h"

WINE_DEFAULT_DEBUG_CHANNEL(avifile);


/***********************************************************************
 * for AVIBuildFilterW -- uses fixed size table
 */
#define MAX_FILTERS 30 /* 30 => 7kB */

typedef struct _AVIFilter {
  WCHAR szClsid[40];
  WCHAR szExtensions[MAX_FILTERS * 7];
} AVIFilter;

/***********************************************************************
 * for AVISaveOptions
 */
static struct {
  UINT                  uFlags;
  INT                   nStreams;
  PAVISTREAM           *ppavis;
  LPAVICOMPRESSOPTIONS *ppOptions;
  INT                   nCurrent;
} SaveOpts;

/***********************************************************************
 * copied from dlls/ole32/compobj.c
 */
static HRESULT AVIFILE_CLSIDFromString(LPCSTR idstr, LPCLSID id)
{
  BYTE const *s;
  BYTE *p;
  INT   i;
  BYTE table[256];

  if (!idstr) {
    memset(id, 0, sizeof(CLSID));
    return S_OK;
  }

  /* validate the CLSID string */
  if (lstrlenA(idstr) != 38)
    return CO_E_CLASSSTRING;

  s = (BYTE const*)idstr;
  if ((s[0]!='{') || (s[9]!='-') || (s[14]!='-') || (s[19]!='-') ||
      (s[24]!='-') || (s[37]!='}'))
    return CO_E_CLASSSTRING;

  for (i = 1; i < 37; i++) {
    if ((i == 9) || (i == 14) || (i == 19) || (i == 24))
      continue;
    if (!(((s[i] >= '0') && (s[i] <= '9'))  ||
        ((s[i] >= 'a') && (s[i] <= 'f'))  ||
        ((s[i] >= 'A') && (s[i] <= 'F')))
       )
      return CO_E_CLASSSTRING;
  }

  TRACE("%s -> %p\n", s, id);

  /* quick lookup table */
  memset(table, 0, 256);

  for (i = 0; i < 10; i++)
    table['0' + i] = i;

  for (i = 0; i < 6; i++) {
    table['A' + i] = i+10;
    table['a' + i] = i+10;
  }

  /* in form {XXXXXXXX-XXXX-XXXX-XXXX-XXXXXXXXXXXX} */
  p = (BYTE *) id;

  s++;	/* skip leading brace  */
  for (i = 0; i < 4; i++) {
    p[3 - i] = table[*s]<<4 | table[*(s+1)];
    s += 2;
  }
  p += 4;
  s++;	/* skip - */

  for (i = 0; i < 2; i++) {
    p[1-i] = table[*s]<<4 | table[*(s+1)];
    s += 2;
  }
  p += 2;
  s++;	/* skip - */

  for (i = 0; i < 2; i++) {
    p[1-i] = table[*s]<<4 | table[*(s+1)];
    s += 2;
  }
  p += 2;
  s++;	/* skip - */

  /* these are just sequential bytes */
  for (i = 0; i < 2; i++) {
    *p++ = table[*s]<<4 | table[*(s+1)];
    s += 2;
  }
  s++;	/* skip - */

  for (i = 0; i < 6; i++) {
    *p++ = table[*s]<<4 | table[*(s+1)];
    s += 2;
  }

  return S_OK;
}

static BOOL AVIFILE_GetFileHandlerByExtension(LPCWSTR szFile, LPCLSID lpclsid)
{
  CHAR   szRegKey[25];
  CHAR   szValue[100];
  LPWSTR szExt = strrchrW(szFile, '.');
  LONG   len = sizeof(szValue) / sizeof(szValue[0]);

  if (szExt == NULL)
    return FALSE;

  szExt++;

  wsprintfA(szRegKey, "AVIFile\\Extensions\\%.3ls", szExt);
  if (RegQueryValueA(HKEY_CLASSES_ROOT, szRegKey, szValue, &len) != ERROR_SUCCESS)
    return FALSE;

  return (AVIFILE_CLSIDFromString(szValue, lpclsid) == S_OK);
}

/***********************************************************************
 *		AVIFileInit		(AVIFIL32.@)
 */
void WINAPI AVIFileInit(void) {
  OleInitialize(NULL);
}

/***********************************************************************
 *		AVIFileExit		(AVIFIL32.@)
 */
void WINAPI AVIFileExit(void) {
  /* need to free ole32.dll if we are the last exit call */
  /* OleUninitialize() */
  FIXME("(): stub!\n");
}

/***********************************************************************
 *		AVIFileOpen		(AVIFIL32.@)
 *		AVIFileOpenA		(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileOpenA(PAVIFILE *ppfile, LPCSTR szFile, UINT uMode,
			    LPCLSID lpHandler)
{
  LPWSTR  wszFile = NULL;
  HRESULT hr;
  int     len;

  TRACE("(%p,%s,0x%08X,%s)\n", ppfile, debugstr_a(szFile), uMode,
	debugstr_guid(lpHandler));

  /* check parameters */
  if (ppfile == NULL || szFile == NULL)
    return AVIERR_BADPARAM;

  /* convert ASCII string to Unicode and call unicode function */
  len = MultiByteToWideChar(CP_ACP, 0, szFile, -1, NULL, 0);
  if (len <= 0)
    return AVIERR_BADPARAM;

  wszFile = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
  if (wszFile == NULL)
    return AVIERR_MEMORY;

  MultiByteToWideChar(CP_ACP, 0, szFile, -1, wszFile, len);

  hr = AVIFileOpenW(ppfile, wszFile, uMode, lpHandler);

  HeapFree(GetProcessHeap(), 0, wszFile);

  return hr;
}

/***********************************************************************
 *		AVIFileOpenW		(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileOpenW(PAVIFILE *ppfile, LPCWSTR szFile, UINT uMode,
			    LPCLSID lpHandler)
{
  IPersistFile *ppersist = NULL;
  CLSID         clsidHandler;
  HRESULT       hr;

  TRACE("(%p,%s,0x%X,%s)\n", ppfile, debugstr_w(szFile), uMode,
	debugstr_guid(lpHandler));

  /* check parameters */
  if (ppfile == NULL || szFile == NULL)
    return AVIERR_BADPARAM;

  *ppfile = NULL;

  /* if no handler then try guessing it by extension */
  if (lpHandler == NULL) {
    if (! AVIFILE_GetFileHandlerByExtension(szFile, &clsidHandler))
      clsidHandler = CLSID_AVIFile;
  } else
    clsidHandler = *lpHandler;

  /* create instance of handler */
  hr = CoCreateInstance(&clsidHandler, NULL, CLSCTX_INPROC, &IID_IAVIFile, (LPVOID*)ppfile);
  if (FAILED(hr) || *ppfile == NULL)
    return hr;

  /* ask for IPersistFile interface for loading/creating the file */
  hr = IAVIFile_QueryInterface(*ppfile, &IID_IPersistFile, (LPVOID*)&ppersist);
  if (FAILED(hr) || ppersist == NULL) {
    IAVIFile_Release(*ppfile);
    *ppfile = NULL;
    return hr;
  }

  hr = IPersistFile_Load(ppersist, szFile, uMode);
  IPersistFile_Release(ppersist);
  if (FAILED(hr)) {
    IAVIFile_Release(*ppfile);
    *ppfile = NULL;
  }

  return hr;
}

/***********************************************************************
 *		AVIFileAddRef		(AVIFIL32.@)
 */
ULONG WINAPI AVIFileAddRef(PAVIFILE pfile)
{
  TRACE("(%p)\n", pfile);

  if (pfile == NULL) {
    ERR(": bad handle passed!\n");
    return 0;
  }

  return IAVIFile_AddRef(pfile);
}

/***********************************************************************
 *		AVIFileRelease		(AVIFIL32.@)
 */
ULONG WINAPI AVIFileRelease(PAVIFILE pfile)
{
  TRACE("(%p)\n", pfile);

  if (pfile == NULL) {
    ERR(": bad handle passed!\n");
    return 0;
  }

  return IAVIFile_Release(pfile);
}

/***********************************************************************
 *		AVIFileInfo		(AVIFIL32.@)
 *		AVIFileInfoA		(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileInfoA(PAVIFILE pfile, LPAVIFILEINFOA afi, LONG size)
{
  AVIFILEINFOW afiw;
  HRESULT      hres;

  TRACE("(%p,%p,%d)\n", pfile, afi, size);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;
  if ((DWORD)size < sizeof(AVIFILEINFOA))
    return AVIERR_BADSIZE;

  hres = IAVIFile_Info(pfile, &afiw, sizeof(afiw));

  memcpy(afi, &afiw, sizeof(*afi) - sizeof(afi->szFileType));
  WideCharToMultiByte(CP_ACP, 0, afiw.szFileType, -1, afi->szFileType,
		      sizeof(afi->szFileType), NULL, NULL);
  afi->szFileType[sizeof(afi->szFileType) - 1] = 0;

  return hres;
}

/***********************************************************************
 *		AVIFileInfoW		(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileInfoW(PAVIFILE pfile, LPAVIFILEINFOW afiw, LONG size)
{
  TRACE("(%p,%p,%d)\n", pfile, afiw, size);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_Info(pfile, afiw, size);
}

/***********************************************************************
 *		AVIFileGetStream	(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileGetStream(PAVIFILE pfile, PAVISTREAM *avis,
				DWORD fccType, LONG lParam)
{
  TRACE("(%p,%p,'%4.4s',%d)\n", pfile, avis, (char*)&fccType, lParam);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_GetStream(pfile, avis, fccType, lParam);
}

/***********************************************************************
 *		AVIFileCreateStream	(AVIFIL32.@)
 *		AVIFileCreateStreamA	(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileCreateStreamA(PAVIFILE pfile, PAVISTREAM *ppavi,
				    LPAVISTREAMINFOA psi)
{
  AVISTREAMINFOW	psiw;

  TRACE("(%p,%p,%p)\n", pfile, ppavi, psi);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  /* Only the szName at the end is different */
  memcpy(&psiw, psi, sizeof(*psi) - sizeof(psi->szName));
  MultiByteToWideChar(CP_ACP, 0, psi->szName, -1, psiw.szName,
		      sizeof(psiw.szName) / sizeof(psiw.szName[0]));

  return IAVIFile_CreateStream(pfile, ppavi, &psiw);
}

/***********************************************************************
 *		AVIFileCreateStreamW	(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileCreateStreamW(PAVIFILE pfile, PAVISTREAM *avis,
				    LPAVISTREAMINFOW asi)
{
  TRACE("(%p,%p,%p)\n", pfile, avis, asi);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_CreateStream(pfile, avis, asi);
}

/***********************************************************************
 *		AVIFileWriteData	(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileWriteData(PAVIFILE pfile,DWORD fcc,LPVOID lp,LONG size)
{
  TRACE("(%p,'%4.4s',%p,%d)\n", pfile, (char*)&fcc, lp, size);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_WriteData(pfile, fcc, lp, size);
}

/***********************************************************************
 *		AVIFileReadData		(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileReadData(PAVIFILE pfile,DWORD fcc,LPVOID lp,LPLONG size)
{
  TRACE("(%p,'%4.4s',%p,%p)\n", pfile, (char*)&fcc, lp, size);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_ReadData(pfile, fcc, lp, size);
}

/***********************************************************************
 *		AVIFileEndRecord	(AVIFIL32.@)
 */
HRESULT WINAPI AVIFileEndRecord(PAVIFILE pfile)
{
  TRACE("(%p)\n", pfile);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return IAVIFile_EndRecord(pfile);
}

/***********************************************************************
 *		AVIStreamAddRef		(AVIFIL32.@)
 */
ULONG WINAPI AVIStreamAddRef(PAVISTREAM pstream)
{
  TRACE("(%p)\n", pstream);

  if (pstream == NULL) {
    ERR(": bad handle passed!\n");
    return 0;
  }

  return IAVIStream_AddRef(pstream);
}

/***********************************************************************
 *		AVIStreamRelease	(AVIFIL32.@)
 */
ULONG WINAPI AVIStreamRelease(PAVISTREAM pstream)
{
  TRACE("(%p)\n", pstream);

  if (pstream == NULL) {
    ERR(": bad handle passed!\n");
    return 0;
  }

  return IAVIStream_Release(pstream);
}

/***********************************************************************
 *		AVIStreamCreate		(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamCreate(PAVISTREAM *ppavi, LONG lParam1, LONG lParam2,
			       LPCLSID pclsidHandler)
{
  HRESULT hr;

  TRACE("(%p,0x%08X,0x%08X,%s)\n", ppavi, lParam1, lParam2,
	debugstr_guid(pclsidHandler));

  if (ppavi == NULL)
    return AVIERR_BADPARAM;

  *ppavi = NULL;
  if (pclsidHandler == NULL)
    return AVIERR_UNSUPPORTED;

  hr = CoCreateInstance(pclsidHandler, NULL, CLSCTX_INPROC, &IID_IAVIStream, (LPVOID*)ppavi);
  if (FAILED(hr) || *ppavi == NULL)
    return hr;

  hr = IAVIStream_Create(*ppavi, lParam1, lParam2);
  if (FAILED(hr)) {
    IAVIStream_Release(*ppavi);
    *ppavi = NULL;
  }

  return hr;
}

/***********************************************************************
 *		AVIStreamInfo		(AVIFIL32.@)
 *		AVIStreamInfoA		(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamInfoA(PAVISTREAM pstream, LPAVISTREAMINFOA asi,
			      LONG size)
{
  AVISTREAMINFOW asiw;
  HRESULT	 hres;

  TRACE("(%p,%p,%d)\n", pstream, asi, size);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;
  if ((DWORD)size < sizeof(AVISTREAMINFOA))
    return AVIERR_BADSIZE;

  hres = IAVIStream_Info(pstream, &asiw, sizeof(asiw));

  memcpy(asi, &asiw, sizeof(asiw) - sizeof(asiw.szName));
  WideCharToMultiByte(CP_ACP, 0, asiw.szName, -1, asi->szName,
		      sizeof(asi->szName), NULL, NULL);
  asi->szName[sizeof(asi->szName) - 1] = 0;

  return hres;
}

/***********************************************************************
 *		AVIStreamInfoW		(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamInfoW(PAVISTREAM pstream, LPAVISTREAMINFOW asi,
			      LONG size)
{
  TRACE("(%p,%p,%d)\n", pstream, asi, size);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_Info(pstream, asi, size);
}

/***********************************************************************
 *		AVIStreamFindSample	(AVIFIL32.@)
 */
LONG WINAPI AVIStreamFindSample(PAVISTREAM pstream, LONG pos, LONG flags)
{
  TRACE("(%p,%d,0x%X)\n", pstream, pos, flags);

  if (pstream == NULL)
    return -1;

  return IAVIStream_FindSample(pstream, pos, flags);
}

/***********************************************************************
 *		AVIStreamReadFormat	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamReadFormat(PAVISTREAM pstream, LONG pos,
				   LPVOID format, LPLONG formatsize)
{
  TRACE("(%p,%d,%p,%p)\n", pstream, pos, format, formatsize);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_ReadFormat(pstream, pos, format, formatsize);
}

/***********************************************************************
 *		AVIStreamSetFormat	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamSetFormat(PAVISTREAM pstream, LONG pos,
				  LPVOID format, LONG formatsize)
{
  TRACE("(%p,%d,%p,%d)\n", pstream, pos, format, formatsize);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_SetFormat(pstream, pos, format, formatsize);
}

/***********************************************************************
 *		AVIStreamRead		(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamRead(PAVISTREAM pstream, LONG start, LONG samples,
			     LPVOID buffer, LONG buffersize,
			     LPLONG bytesread, LPLONG samplesread)
{
  TRACE("(%p,%d,%d,%p,%d,%p,%p)\n", pstream, start, samples, buffer,
	buffersize, bytesread, samplesread);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_Read(pstream, start, samples, buffer, buffersize,
			 bytesread, samplesread);
}

/***********************************************************************
 *		AVIStreamWrite		(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamWrite(PAVISTREAM pstream, LONG start, LONG samples,
			      LPVOID buffer, LONG buffersize, DWORD flags,
			      LPLONG sampwritten, LPLONG byteswritten)
{
  TRACE("(%p,%d,%d,%p,%d,0x%X,%p,%p)\n", pstream, start, samples, buffer,
	buffersize, flags, sampwritten, byteswritten);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_Write(pstream, start, samples, buffer, buffersize,
			  flags, sampwritten, byteswritten);
}

/***********************************************************************
 *		AVIStreamReadData	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamReadData(PAVISTREAM pstream, DWORD fcc, LPVOID lp,
				 LPLONG lpread)
{
  TRACE("(%p,'%4.4s',%p,%p)\n", pstream, (char*)&fcc, lp, lpread);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_ReadData(pstream, fcc, lp, lpread);
}

/***********************************************************************
 *		AVIStreamWriteData	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamWriteData(PAVISTREAM pstream, DWORD fcc, LPVOID lp,
				  LONG size)
{
  TRACE("(%p,'%4.4s',%p,%d)\n", pstream, (char*)&fcc, lp, size);

  if (pstream == NULL)
    return AVIERR_BADHANDLE;

  return IAVIStream_WriteData(pstream, fcc, lp, size);
}

/***********************************************************************
 *		AVIStreamGetFrameOpen	(AVIFIL32.@)
 */
PGETFRAME WINAPI AVIStreamGetFrameOpen(PAVISTREAM pstream,
				       LPBITMAPINFOHEADER lpbiWanted)
{
  PGETFRAME pg = NULL;

  TRACE("(%p,%p)\n", pstream, lpbiWanted);

  if (FAILED(IAVIStream_QueryInterface(pstream, &IID_IGetFrame, (LPVOID*)&pg)) ||
      pg == NULL) {
    pg = AVIFILE_CreateGetFrame(pstream);
    if (pg == NULL)
      return NULL;
  }

  if (FAILED(IGetFrame_SetFormat(pg, lpbiWanted, NULL, 0, 0, -1, -1))) {
    IGetFrame_Release(pg);
    return NULL;
  }

  return pg;
}

/***********************************************************************
 *		AVIStreamGetFrame	(AVIFIL32.@)
 */
LPVOID WINAPI AVIStreamGetFrame(PGETFRAME pg, LONG pos)
{
  TRACE("(%p,%d)\n", pg, pos);

  if (pg == NULL)
    return NULL;

  return IGetFrame_GetFrame(pg, pos);
}

/***********************************************************************
 *		AVIStreamGetFrameClose	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamGetFrameClose(PGETFRAME pg)
{
  TRACE("(%p)\n", pg);

  if (pg != NULL)
    return IGetFrame_Release(pg);
  return 0;
}

/***********************************************************************
 *		AVIMakeCompressedStream	(AVIFIL32.@)
 */
HRESULT WINAPI AVIMakeCompressedStream(PAVISTREAM *ppsCompressed,
				       PAVISTREAM psSource,
				       LPAVICOMPRESSOPTIONS aco,
				       LPCLSID pclsidHandler)
{
  AVISTREAMINFOW asiw;
  CHAR           szRegKey[25];
  CHAR           szValue[100];
  CLSID          clsidHandler;
  HRESULT        hr;
  LONG           size = sizeof(szValue);

  TRACE("(%p,%p,%p,%s)\n", ppsCompressed, psSource, aco,
	debugstr_guid(pclsidHandler));

  if (ppsCompressed == NULL)
    return AVIERR_BADPARAM;
  if (psSource == NULL)
    return AVIERR_BADHANDLE;

  *ppsCompressed = NULL;

  /* if no handler given get default ones based on streamtype */
  if (pclsidHandler == NULL) {
    hr = IAVIStream_Info(psSource, &asiw, sizeof(asiw));
    if (FAILED(hr))
      return hr;

    wsprintfA(szRegKey, "AVIFile\\Compressors\\%4.4s", (char*)&asiw.fccType);
    if (RegQueryValueA(HKEY_CLASSES_ROOT, szRegKey, szValue, &size) != ERROR_SUCCESS)
      return AVIERR_UNSUPPORTED;
    if (AVIFILE_CLSIDFromString(szValue, &clsidHandler) != S_OK)
      return AVIERR_UNSUPPORTED;
  } else
    clsidHandler = *pclsidHandler;

  hr = CoCreateInstance(&clsidHandler, NULL, CLSCTX_INPROC, &IID_IAVIStream, (LPVOID*)ppsCompressed);
  if (FAILED(hr) || *ppsCompressed == NULL)
    return hr;

  hr = IAVIStream_Create(*ppsCompressed, (LPARAM)psSource, (LPARAM)aco);
  if (FAILED(hr)) {
    IAVIStream_Release(*ppsCompressed);
    *ppsCompressed = NULL;
  }

  return hr;
}

/***********************************************************************
 *		AVIMakeFileFromStreams	(AVIFIL32.@)
 */
HRESULT WINAPI AVIMakeFileFromStreams(PAVIFILE *ppfile, int nStreams,
				      PAVISTREAM *ppStreams)
{
  TRACE("(%p,%d,%p)\n", ppfile, nStreams, ppStreams);

  if (nStreams < 0 || ppfile == NULL || ppStreams == NULL)
    return AVIERR_BADPARAM;

  *ppfile = AVIFILE_CreateAVITempFile(nStreams, ppStreams);
  if (*ppfile == NULL)
    return AVIERR_MEMORY;

  return AVIERR_OK;
}

/***********************************************************************
 *		AVIStreamOpenFromFile	(AVIFIL32.@)
 *		AVIStreamOpenFromFileA	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamOpenFromFileA(PAVISTREAM *ppavi, LPCSTR szFile,
				      DWORD fccType, LONG lParam,
				      UINT mode, LPCLSID pclsidHandler)
{
  PAVIFILE pfile = NULL;
  HRESULT  hr;

  TRACE("(%p,%s,'%4.4s',%d,0x%X,%s)\n", ppavi, debugstr_a(szFile),
	(char*)&fccType, lParam, mode, debugstr_guid(pclsidHandler));

  if (ppavi == NULL || szFile == NULL)
    return AVIERR_BADPARAM;

  *ppavi = NULL;

  hr = AVIFileOpenA(&pfile, szFile, mode, pclsidHandler);
  if (FAILED(hr) || pfile == NULL)
    return hr;

  hr = IAVIFile_GetStream(pfile, ppavi, fccType, lParam);
  IAVIFile_Release(pfile);

  return hr;
}

/***********************************************************************
 *		AVIStreamOpenFromFileW	(AVIFIL32.@)
 */
HRESULT WINAPI AVIStreamOpenFromFileW(PAVISTREAM *ppavi, LPCWSTR szFile,
				      DWORD fccType, LONG lParam,
				      UINT mode, LPCLSID pclsidHandler)
{
  PAVIFILE pfile = NULL;
  HRESULT  hr;

  TRACE("(%p,%s,'%4.4s',%d,0x%X,%s)\n", ppavi, debugstr_w(szFile),
	(char*)&fccType, lParam, mode, debugstr_guid(pclsidHandler));

  if (ppavi == NULL || szFile == NULL)
    return AVIERR_BADPARAM;

  *ppavi = NULL;

  hr = AVIFileOpenW(&pfile, szFile, mode, pclsidHandler);
  if (FAILED(hr) || pfile == NULL)
    return hr;

  hr = IAVIFile_GetStream(pfile, ppavi, fccType, lParam);
  IAVIFile_Release(pfile);

  return hr;
}

/***********************************************************************
 *		AVIStreamBeginStreaming	(AVIFIL32.@)
 */
LONG WINAPI AVIStreamBeginStreaming(PAVISTREAM pavi, LONG lStart, LONG lEnd, LONG lRate)
{
  IAVIStreaming* pstream = NULL;
  HRESULT hr;

  TRACE("(%p,%d,%d,%d)\n", pavi, lStart, lEnd, lRate);

  if (pavi == NULL)
    return AVIERR_BADHANDLE;

  hr = IAVIStream_QueryInterface(pavi, &IID_IAVIStreaming, (LPVOID*)&pstream);
  if (SUCCEEDED(hr) && pstream != NULL) {
    hr = IAVIStreaming_Begin(pstream, lStart, lEnd, lRate);
    IAVIStreaming_Release(pstream);
  } else
    hr = AVIERR_OK;

  return hr;
}

/***********************************************************************
 *		AVIStreamEndStreaming	(AVIFIL32.@)
 */
LONG WINAPI AVIStreamEndStreaming(PAVISTREAM pavi)
{
  IAVIStreaming* pstream = NULL;
  HRESULT hr;

  TRACE("(%p)\n", pavi);

  hr = IAVIStream_QueryInterface(pavi, &IID_IAVIStreaming, (LPVOID*)&pstream);
  if (SUCCEEDED(hr) && pstream != NULL) {
    IAVIStreaming_End(pstream);
    IAVIStreaming_Release(pstream);
  }

 return AVIERR_OK;
}

/***********************************************************************
 *		AVIStreamStart		(AVIFIL32.@)
 */
LONG WINAPI AVIStreamStart(PAVISTREAM pstream)
{
  AVISTREAMINFOW asiw;

  TRACE("(%p)\n", pstream);

  if (pstream == NULL)
    return 0;

  if (FAILED(IAVIStream_Info(pstream, &asiw, sizeof(asiw))))
    return 0;

  return asiw.dwStart;
}

/***********************************************************************
 *		AVIStreamLength		(AVIFIL32.@)
 */
LONG WINAPI AVIStreamLength(PAVISTREAM pstream)
{
  AVISTREAMINFOW asiw;

  TRACE("(%p)\n", pstream);

  if (pstream == NULL)
    return 0;

  if (FAILED(IAVIStream_Info(pstream, &asiw, sizeof(asiw))))
    return 0;

  return asiw.dwLength;
}

/***********************************************************************
 *		AVIStreamSampleToTime	(AVIFIL32.@)
 */
LONG WINAPI AVIStreamSampleToTime(PAVISTREAM pstream, LONG lSample)
{
  AVISTREAMINFOW asiw;
  LONG time;

  TRACE("(%p,%d)\n", pstream, lSample);

  if (pstream == NULL)
    return -1;

  if (FAILED(IAVIStream_Info(pstream, &asiw, sizeof(asiw))))
    return -1;
  if (asiw.dwRate == 0)
    return -1;

  /* limit to stream bounds */
  if (lSample < asiw.dwStart)
    lSample = asiw.dwStart;
  if (lSample > asiw.dwStart + asiw.dwLength)
    lSample = asiw.dwStart + asiw.dwLength;

  if (asiw.dwRate / asiw.dwScale < 1000)
    time = (LONG)(((float)lSample * asiw.dwScale * 1000) / asiw.dwRate);
  else
    time = (LONG)(((float)lSample * asiw.dwScale * 1000 + (asiw.dwRate - 1)) / asiw.dwRate);

  TRACE(" -> %d\n",time);
  return time;
}

/***********************************************************************
 *		AVIStreamTimeToSample	(AVIFIL32.@)
 */
LONG WINAPI AVIStreamTimeToSample(PAVISTREAM pstream, LONG lTime)
{
  AVISTREAMINFOW asiw;
  ULONG sample;

  TRACE("(%p,%d)\n", pstream, lTime);

  if (pstream == NULL || lTime < 0)
    return -1;

  if (FAILED(IAVIStream_Info(pstream, &asiw, sizeof(asiw))))
    return -1;
  if (asiw.dwScale == 0)
    return -1;

  if (asiw.dwRate / asiw.dwScale < 1000)
    sample = (LONG)((((float)asiw.dwRate * lTime) / (asiw.dwScale * 1000)));
  else
    sample = (LONG)(((float)asiw.dwRate * lTime + (asiw.dwScale * 1000 - 1)) / (asiw.dwScale * 1000));

  /* limit to stream bounds */
  if (sample < asiw.dwStart)
    sample = asiw.dwStart;
  if (sample > asiw.dwStart + asiw.dwLength)
    sample = asiw.dwStart + asiw.dwLength;

  TRACE(" -> %d\n", sample);
  return sample;
}

/***********************************************************************
 *		AVIBuildFilter		(AVIFIL32.@)
 *		AVIBuildFilterA		(AVIFIL32.@)
 */
HRESULT WINAPI AVIBuildFilterA(LPSTR szFilter, LONG cbFilter, BOOL fSaving)
{
  LPWSTR  wszFilter;
  HRESULT hr;

  TRACE("(%p,%d,%d)\n", szFilter, cbFilter, fSaving);

  /* check parameters */
  if (szFilter == NULL)
    return AVIERR_BADPARAM;
  if (cbFilter < 2)
    return AVIERR_BADSIZE;

  szFilter[0] = 0;
  szFilter[1] = 0;

  wszFilter = HeapAlloc(GetProcessHeap(), 0, cbFilter * sizeof(WCHAR));
  if (wszFilter == NULL)
    return AVIERR_MEMORY;

  hr = AVIBuildFilterW(wszFilter, cbFilter, fSaving);
  if (SUCCEEDED(hr)) {
    WideCharToMultiByte(CP_ACP, 0, wszFilter, cbFilter,
			szFilter, cbFilter, NULL, NULL);
  }

  HeapFree(GetProcessHeap(), 0, wszFilter);

  return hr;
}

/***********************************************************************
 *		AVIBuildFilterW		(AVIFIL32.@)
 */
HRESULT WINAPI AVIBuildFilterW(LPWSTR szFilter, LONG cbFilter, BOOL fSaving)
{
  static const WCHAR all_files[] = { '*','.','*',0,0 };
  static const WCHAR szClsid[] = {'C','L','S','I','D',0};
  static const WCHAR szExtensionFmt[] = {';','*','.','%','s',0};
  static const WCHAR szAVIFileExtensions[] =
    {'A','V','I','F','i','l','e','\\','E','x','t','e','n','s','i','o','n','s',0};

  AVIFilter *lp;
  WCHAR      szAllFiles[40];
  WCHAR      szFileExt[10];
  WCHAR      szValue[128];
  HKEY       hKey;
  DWORD      n, i;
  LONG       size;
  DWORD      count = 0;

  TRACE("(%p,%d,%d)\n", szFilter, cbFilter, fSaving);

  /* check parameters */
  if (szFilter == NULL)
    return AVIERR_BADPARAM;
  if (cbFilter < 2)
    return AVIERR_BADSIZE;

  lp = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, MAX_FILTERS * sizeof(AVIFilter));
  if (lp == NULL)
    return AVIERR_MEMORY;

  /*
   * 1. iterate over HKEY_CLASSES_ROOT\\AVIFile\\Extensions and collect
   *    extensions and CLSIDs
   * 2. iterate over collected CLSIDs and copy its description and its
   *    extensions to szFilter if it fits
   *
   * First filter is named "All multimedia files" and its filter is a
   * collection of all possible extensions except "*.*".
   */
  if (RegOpenKeyW(HKEY_CLASSES_ROOT, szAVIFileExtensions, &hKey) != ERROR_SUCCESS) {
    HeapFree(GetProcessHeap(), 0, lp);
    return AVIERR_ERROR;
  }
  for (n = 0;RegEnumKeyW(hKey, n, szFileExt, sizeof(szFileExt)/sizeof(szFileExt[0])) == ERROR_SUCCESS;n++) {
    /* get CLSID to extension */
    size = sizeof(szValue);
    if (RegQueryValueW(hKey, szFileExt, szValue, &size) != ERROR_SUCCESS)
      break;

    /* search if the CLSID is already known */
    for (i = 1; i <= count; i++) {
      if (lstrcmpW(lp[i].szClsid, szValue) == 0)
	break; /* a new one */
    }

    if (i == count + 1) {
      /* it's a new CLSID */

      /* FIXME: How do we get info's about read/write capabilities? */

      if (count >= MAX_FILTERS) {
	/* try to inform user of our full fixed size table */
	ERR(": More than %d filters found! Adjust MAX_FILTERS in dlls/avifil32/api.c\n", MAX_FILTERS);
	break;
      }

      lstrcpyW(lp[i].szClsid, szValue);

      count++;
    }

    /* append extension to the filter */
    wsprintfW(szValue, szExtensionFmt, szFileExt);
    if (lp[i].szExtensions[0] == 0)
      lstrcatW(lp[i].szExtensions, szValue + 1);
    else
      lstrcatW(lp[i].szExtensions, szValue);

    /* also append to the "all multimedia"-filter */
    if (lp[0].szExtensions[0] == 0)
      lstrcatW(lp[0].szExtensions, szValue + 1);
    else
      lstrcatW(lp[0].szExtensions, szValue);
  }
  RegCloseKey(hKey);

  /* 2. get descriptions for the CLSIDs and fill out szFilter */
  if (RegOpenKeyW(HKEY_CLASSES_ROOT, szClsid, &hKey) != ERROR_SUCCESS) {
    HeapFree(GetProcessHeap(), 0, lp);
    return AVIERR_ERROR;
  }
  for (n = 0; n <= count; n++) {
    /* first the description */
    if (n != 0) {
      size = sizeof(szValue);
      if (RegQueryValueW(hKey, lp[n].szClsid, szValue, &size) == ERROR_SUCCESS) {
	size = lstrlenW(szValue);
	lstrcpynW(szFilter, szValue, cbFilter);
      }
    } else
      size = LoadStringW(AVIFILE_hModule,IDS_ALLMULTIMEDIA,szFilter,cbFilter);

    /* check for enough space */
    size++;
    if (cbFilter < size + lstrlenW(lp[n].szExtensions) + 2) {
      szFilter[0] = 0;
      szFilter[1] = 0;
      HeapFree(GetProcessHeap(), 0, lp);
      RegCloseKey(hKey);
      return AVIERR_BUFFERTOOSMALL;
    }
    cbFilter -= size;
    szFilter += size;

    /* and then the filter */
    lstrcpynW(szFilter, lp[n].szExtensions, cbFilter);
    size = lstrlenW(lp[n].szExtensions) + 1;
    cbFilter -= size;
    szFilter += size;
  }

  RegCloseKey(hKey);
  HeapFree(GetProcessHeap(), 0, lp);

  /* add "All files" "*.*" filter if enough space left */
  size = LoadStringW(AVIFILE_hModule, IDS_ALLFILES,
                     szAllFiles, (sizeof(szAllFiles) - sizeof(all_files))/sizeof(WCHAR)) + 1;
  memcpy( szAllFiles + size, all_files, sizeof(all_files) );
  size += sizeof(all_files) / sizeof(WCHAR);

  if (cbFilter > size) {
    memcpy(szFilter, szAllFiles, size * sizeof(szAllFiles[0]));
    return AVIERR_OK;
  } else {
    szFilter[0] = 0;
    return AVIERR_BUFFERTOOSMALL;
  }
}

static BOOL AVISaveOptionsFmtChoose(HWND hWnd)
{
  LPAVICOMPRESSOPTIONS pOptions = SaveOpts.ppOptions[SaveOpts.nCurrent];
  AVISTREAMINFOW       sInfo;

  TRACE("(%p)\n", hWnd);

  if (pOptions == NULL || SaveOpts.ppavis[SaveOpts.nCurrent] == NULL) {
    ERR(": bad state!\n");
    return FALSE;
  }

  if (FAILED(AVIStreamInfoW(SaveOpts.ppavis[SaveOpts.nCurrent],
			    &sInfo, sizeof(sInfo)))) {
    ERR(": AVIStreamInfoW failed!\n");
    return FALSE;
  }

  if (sInfo.fccType == streamtypeVIDEO) {
    COMPVARS cv;
    BOOL     ret;

    memset(&cv, 0, sizeof(cv));

    if ((pOptions->dwFlags & AVICOMPRESSF_VALID) == 0) {
      memset(pOptions, 0, sizeof(AVICOMPRESSOPTIONS));
      pOptions->fccType    = streamtypeVIDEO;
      pOptions->fccHandler = comptypeDIB;
      pOptions->dwQuality  = (DWORD)ICQUALITY_DEFAULT;
    }

    cv.cbSize     = sizeof(cv);
    cv.dwFlags    = ICMF_COMPVARS_VALID;
    /*cv.fccType    = pOptions->fccType; */
    cv.fccHandler = pOptions->fccHandler;
    cv.lQ         = pOptions->dwQuality;
    cv.lpState    = pOptions->lpParms;
    cv.cbState    = pOptions->cbParms;
    if (pOptions->dwFlags & AVICOMPRESSF_KEYFRAMES)
      cv.lKey = pOptions->dwKeyFrameEvery;
    else
      cv.lKey = 0;
    if (pOptions->dwFlags & AVICOMPRESSF_DATARATE)
      cv.lDataRate = pOptions->dwBytesPerSecond / 1024; /* need kBytes */
    else
      cv.lDataRate = 0;

    ret = ICCompressorChoose(hWnd, SaveOpts.uFlags, NULL,
			     SaveOpts.ppavis[SaveOpts.nCurrent], &cv, NULL);

    if (ret) {
      pOptions->fccHandler = cv.fccHandler;
      pOptions->lpParms   = cv.lpState;
      pOptions->cbParms   = cv.cbState;
      pOptions->dwQuality = cv.lQ;
      if (cv.lKey != 0) {
	pOptions->dwKeyFrameEvery = cv.lKey;
	pOptions->dwFlags |= AVICOMPRESSF_KEYFRAMES;
      } else
	pOptions->dwFlags &= ~AVICOMPRESSF_KEYFRAMES;
      if (cv.lDataRate != 0) {
	pOptions->dwBytesPerSecond = cv.lDataRate * 1024; /* need bytes */
	pOptions->dwFlags |= AVICOMPRESSF_DATARATE;
      } else
	pOptions->dwFlags &= ~AVICOMPRESSF_DATARATE;
      pOptions->dwFlags  |= AVICOMPRESSF_VALID;
    }
    ICCompressorFree(&cv);

    return ret;
  } else if (sInfo.fccType == streamtypeAUDIO) {
    ACMFORMATCHOOSEW afmtc;
    MMRESULT         ret;
    LONG             size;

    /* FIXME: check ACM version -- Which version is needed? */

    memset(&afmtc, 0, sizeof(afmtc));
    afmtc.cbStruct  = sizeof(afmtc);
    afmtc.fdwStyle  = 0;
    afmtc.hwndOwner = hWnd;

    acmMetrics(NULL, ACM_METRIC_MAX_SIZE_FORMAT, &size);
    if ((pOptions->cbFormat == 0 || pOptions->lpFormat == NULL) && size != 0) {
      pOptions->lpFormat = HeapAlloc(GetProcessHeap(), 0, size);
      if (!pOptions->lpFormat) return FALSE;
      pOptions->cbFormat = size;
    } else if (pOptions->cbFormat < (DWORD)size) {
      void *new_buffer = HeapReAlloc(GetProcessHeap(), 0, pOptions->lpFormat, size);
      if (!new_buffer) return FALSE;
      pOptions->lpFormat = new_buffer;
      pOptions->cbFormat = size;
    }
    afmtc.pwfx  = pOptions->lpFormat;
    afmtc.cbwfx = pOptions->cbFormat;

    size = 0;
    AVIStreamFormatSize(SaveOpts.ppavis[SaveOpts.nCurrent],
			sInfo.dwStart, &size);
    if (size < (LONG)sizeof(PCMWAVEFORMAT))
      size = sizeof(PCMWAVEFORMAT);
    afmtc.pwfxEnum = HeapAlloc(GetProcessHeap(), 0, size);
    if (afmtc.pwfxEnum != NULL) {
      AVIStreamReadFormat(SaveOpts.ppavis[SaveOpts.nCurrent],
			  sInfo.dwStart, afmtc.pwfxEnum, &size);
      afmtc.fdwEnum = ACM_FORMATENUMF_CONVERT;
    }

    ret = acmFormatChooseW(&afmtc);
    if (ret == S_OK)
      pOptions->dwFlags |= AVICOMPRESSF_VALID;

    HeapFree(GetProcessHeap(), 0, afmtc.pwfxEnum);
    return ret == S_OK;
  } else {
    ERR(": unknown streamtype 0x%08X\n", sInfo.fccType);
    return FALSE;
  }
}

static void AVISaveOptionsUpdate(HWND hWnd)
{
  static const WCHAR szVideoFmt[]={'%','l','d','x','%','l','d','x','%','d',0};
  static const WCHAR szAudioFmt[]={'%','s',' ','%','s',0};

  WCHAR          szFormat[128];
  AVISTREAMINFOW sInfo;
  LPVOID         lpFormat;
  LONG           size;

  TRACE("(%p)\n", hWnd);

  SaveOpts.nCurrent = SendDlgItemMessageW(hWnd,IDC_STREAM,CB_GETCURSEL,0,0);
  if (SaveOpts.nCurrent < 0)
    return;

  if (FAILED(AVIStreamInfoW(SaveOpts.ppavis[SaveOpts.nCurrent], &sInfo, sizeof(sInfo))))
    return;

  AVIStreamFormatSize(SaveOpts.ppavis[SaveOpts.nCurrent],sInfo.dwStart,&size);
  if (size > 0) {
    szFormat[0] = 0;

    /* read format to build format description string */
    lpFormat = HeapAlloc(GetProcessHeap(), 0, size);
    if (lpFormat != NULL) {
      if (SUCCEEDED(AVIStreamReadFormat(SaveOpts.ppavis[SaveOpts.nCurrent],sInfo.dwStart,lpFormat, &size))) {
	if (sInfo.fccType == streamtypeVIDEO) {
	  LPBITMAPINFOHEADER lpbi = lpFormat;
	  ICINFO icinfo;

	  wsprintfW(szFormat, szVideoFmt, lpbi->biWidth,
		    lpbi->biHeight, lpbi->biBitCount);

	  if (lpbi->biCompression != BI_RGB) {
	    HIC    hic;

	    hic = ICLocate(ICTYPE_VIDEO, sInfo.fccHandler, lpFormat,
			   NULL, ICMODE_DECOMPRESS);
	    if (hic != NULL) {
	      if (ICGetInfo(hic, &icinfo, sizeof(icinfo)) == S_OK)
		lstrcatW(szFormat, icinfo.szDescription);
	      ICClose(hic);
	    }
	  } else {
	    LoadStringW(AVIFILE_hModule, IDS_UNCOMPRESSED,
			icinfo.szDescription,
			sizeof(icinfo.szDescription)/sizeof(icinfo.szDescription[0]));
	    lstrcatW(szFormat, icinfo.szDescription);
	  }
	} else if (sInfo.fccType == streamtypeAUDIO) {
	  ACMFORMATTAGDETAILSW aftd;
	  ACMFORMATDETAILSW    afd;

	  memset(&aftd, 0, sizeof(aftd));
	  memset(&afd, 0, sizeof(afd));

	  aftd.cbStruct     = sizeof(aftd);
	  aftd.dwFormatTag  = afd.dwFormatTag =
	    ((PWAVEFORMATEX)lpFormat)->wFormatTag;
	  aftd.cbFormatSize = afd.cbwfx = size;

	  afd.cbStruct      = sizeof(afd);
	  afd.pwfx          = lpFormat;

	  if (acmFormatTagDetailsW(NULL, &aftd,
				   ACM_FORMATTAGDETAILSF_FORMATTAG) == S_OK) {
	    if (acmFormatDetailsW(NULL,&afd,ACM_FORMATDETAILSF_FORMAT) == S_OK)
	      wsprintfW(szFormat, szAudioFmt, afd.szFormat, aftd.szFormatTag);
	  }
	}
      }
      HeapFree(GetProcessHeap(), 0, lpFormat);
    }

    /* set text for format description */
    SetDlgItemTextW(hWnd, IDC_FORMATTEXT, szFormat);

    /* Disable option button for unsupported streamtypes */
    if (sInfo.fccType == streamtypeVIDEO ||
	sInfo.fccType == streamtypeAUDIO)
      EnableWindow(GetDlgItem(hWnd, IDC_OPTIONS), TRUE);
    else
      EnableWindow(GetDlgItem(hWnd, IDC_OPTIONS), FALSE);
  }

}

static INT_PTR CALLBACK AVISaveOptionsDlgProc(HWND hWnd, UINT uMsg,
                                              WPARAM wParam, LPARAM lParam)
{
  DWORD dwInterleave;
  BOOL  bIsInterleaved;
  INT   n;

  /*TRACE("(%p,%u,0x%04X,0x%08lX)\n", hWnd, uMsg, wParam, lParam);*/

  switch (uMsg) {
  case WM_INITDIALOG:
    SaveOpts.nCurrent = 0;
    if (SaveOpts.nStreams == 1) {
      EndDialog(hWnd, AVISaveOptionsFmtChoose(hWnd));
      return TRUE;
    }

    /* add streams */
    for (n = 0; n < SaveOpts.nStreams; n++) {
      AVISTREAMINFOW sInfo;

      AVIStreamInfoW(SaveOpts.ppavis[n], &sInfo, sizeof(sInfo));
      SendDlgItemMessageW(hWnd, IDC_STREAM, CB_ADDSTRING,
			  0L, (LPARAM)sInfo.szName);
    }

    /* select first stream */
    SendDlgItemMessageW(hWnd, IDC_STREAM, CB_SETCURSEL, 0, 0);
    SendMessageW(hWnd, WM_COMMAND, MAKELONG(IDC_STREAM, CBN_SELCHANGE), (LPARAM)hWnd);

    /* initialize interleave */
    if (SaveOpts.ppOptions[0] != NULL &&
	(SaveOpts.ppOptions[0]->dwFlags & AVICOMPRESSF_VALID)) {
      bIsInterleaved = (SaveOpts.ppOptions[0]->dwFlags & AVICOMPRESSF_INTERLEAVE);
      dwInterleave = SaveOpts.ppOptions[0]->dwInterleaveEvery;
    } else {
      bIsInterleaved = TRUE;
      dwInterleave   = 0;
    }
    CheckDlgButton(hWnd, IDC_INTERLEAVE, bIsInterleaved);
    SetDlgItemInt(hWnd, IDC_INTERLEAVEEVERY, dwInterleave, FALSE);
    EnableWindow(GetDlgItem(hWnd, IDC_INTERLEAVEEVERY), bIsInterleaved);
    break;
  case WM_COMMAND:
    switch (LOWORD(wParam)) {
    case IDOK:
      /* get data from controls and save them */
      dwInterleave   = GetDlgItemInt(hWnd, IDC_INTERLEAVEEVERY, NULL, 0);
      bIsInterleaved = IsDlgButtonChecked(hWnd, IDC_INTERLEAVE);
      for (n = 0; n < SaveOpts.nStreams; n++) {
	if (SaveOpts.ppOptions[n] != NULL) {
	  if (bIsInterleaved) {
	    SaveOpts.ppOptions[n]->dwFlags |= AVICOMPRESSF_INTERLEAVE;
	    SaveOpts.ppOptions[n]->dwInterleaveEvery = dwInterleave;
	  } else
	    SaveOpts.ppOptions[n]->dwFlags &= ~AVICOMPRESSF_INTERLEAVE;
	}
      }
      /* fall through */
    case IDCANCEL:
      EndDialog(hWnd, LOWORD(wParam) == IDOK);
      break;
    case IDC_INTERLEAVE:
      EnableWindow(GetDlgItem(hWnd, IDC_INTERLEAVEEVERY),
		   IsDlgButtonChecked(hWnd, IDC_INTERLEAVE));
      break;
    case IDC_STREAM:
      if (HIWORD(wParam) == CBN_SELCHANGE) {
	/* update control elements */
	AVISaveOptionsUpdate(hWnd);
      }
      break;
    case IDC_OPTIONS:
      AVISaveOptionsFmtChoose(hWnd);
      break;
    };
    return TRUE;
  };

  return FALSE;
}

/***********************************************************************
 *		AVISaveOptions		(AVIFIL32.@)
 */
BOOL WINAPI AVISaveOptions(HWND hWnd, UINT uFlags, INT nStreams,
			   PAVISTREAM *ppavi, LPAVICOMPRESSOPTIONS *ppOptions)
{
  LPAVICOMPRESSOPTIONS pSavedOptions = NULL;
  INT ret, n;

  TRACE("(%p,0x%X,%d,%p,%p)\n", hWnd, uFlags, nStreams,
	ppavi, ppOptions);

  /* check parameters */
  if (nStreams <= 0 || ppavi == NULL || ppOptions == NULL)
    return AVIERR_BADPARAM;

  /* save options in case the user presses cancel */
  if (nStreams > 1) {
    pSavedOptions = HeapAlloc(GetProcessHeap(), 0, nStreams * sizeof(AVICOMPRESSOPTIONS));
    if (pSavedOptions == NULL)
      return FALSE;

    for (n = 0; n < nStreams; n++) {
      if (ppOptions[n] != NULL)
	memcpy(pSavedOptions + n, ppOptions[n], sizeof(AVICOMPRESSOPTIONS));
    }
  }

  SaveOpts.uFlags    = uFlags;
  SaveOpts.nStreams  = nStreams;
  SaveOpts.ppavis    = ppavi;
  SaveOpts.ppOptions = ppOptions;

  ret = DialogBoxW(AVIFILE_hModule, MAKEINTRESOURCEW(IDD_SAVEOPTIONS),
		   hWnd, AVISaveOptionsDlgProc);

  if (ret == -1)
    ret = FALSE;

  /* restore options when user pressed cancel */
  if (pSavedOptions != NULL) {
    if (ret == FALSE) {
      for (n = 0; n < nStreams; n++) {
	if (ppOptions[n] != NULL)
	  memcpy(ppOptions[n], pSavedOptions + n, sizeof(AVICOMPRESSOPTIONS));
      }
    }
    HeapFree(GetProcessHeap(), 0, pSavedOptions);
  }

  return ret;
}

/***********************************************************************
 *		AVISaveOptionsFree	(AVIFIL32.@)
 */
HRESULT WINAPI AVISaveOptionsFree(INT nStreams,LPAVICOMPRESSOPTIONS*ppOptions)
{
  TRACE("(%d,%p)\n", nStreams, ppOptions);

  if (nStreams < 0 || ppOptions == NULL)
    return AVIERR_BADPARAM;

  for (nStreams--; nStreams >= 0; nStreams--) {
    if (ppOptions[nStreams] != NULL) {
      ppOptions[nStreams]->dwFlags &= ~AVICOMPRESSF_VALID;

      if (ppOptions[nStreams]->lpParms != NULL) {
	HeapFree(GetProcessHeap(), 0, ppOptions[nStreams]->lpParms);
	ppOptions[nStreams]->lpParms = NULL;
	ppOptions[nStreams]->cbParms = 0;
      }
      if (ppOptions[nStreams]->lpFormat != NULL) {
	HeapFree(GetProcessHeap(), 0, ppOptions[nStreams]->lpFormat);
	ppOptions[nStreams]->lpFormat = NULL;
	ppOptions[nStreams]->cbFormat = 0;
      }
    }
  }

  return AVIERR_OK;
}

/***********************************************************************
 *		AVISaveVA		(AVIFIL32.@)
 */
HRESULT WINAPI AVISaveVA(LPCSTR szFile, CLSID *pclsidHandler,
			 AVISAVECALLBACK lpfnCallback, int nStream,
			 PAVISTREAM *ppavi, LPAVICOMPRESSOPTIONS *plpOptions)
{
  LPWSTR  wszFile = NULL;
  HRESULT hr;
  int     len;

  TRACE("%s,%p,%p,%d,%p,%p)\n", debugstr_a(szFile), pclsidHandler,
	lpfnCallback, nStream, ppavi, plpOptions);

  if (szFile == NULL || ppavi == NULL || plpOptions == NULL)
    return AVIERR_BADPARAM;

  /* convert ASCII string to Unicode and call Unicode function */
  len = MultiByteToWideChar(CP_ACP, 0, szFile, -1, NULL, 0);
  if (len <= 0)
    return AVIERR_BADPARAM;

  wszFile = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
  if (wszFile == NULL)
    return AVIERR_MEMORY;

  MultiByteToWideChar(CP_ACP, 0, szFile, -1, wszFile, len);

  hr = AVISaveVW(wszFile, pclsidHandler, lpfnCallback,
		 nStream, ppavi, plpOptions);

  HeapFree(GetProcessHeap(), 0, wszFile);

  return hr;
}

/***********************************************************************
 *		AVIFILE_AVISaveDefaultCallback	(internal)
 */
static BOOL WINAPI AVIFILE_AVISaveDefaultCallback(INT progress)
{
  TRACE("(%d)\n", progress);

  return FALSE;
}

/***********************************************************************
 *		AVISaveVW		(AVIFIL32.@)
 */
HRESULT WINAPI AVISaveVW(LPCWSTR szFile, CLSID *pclsidHandler,
			 AVISAVECALLBACK lpfnCallback, int nStreams,
			 PAVISTREAM *ppavi, LPAVICOMPRESSOPTIONS *plpOptions)
{
  LONG           lStart[MAX_AVISTREAMS];
  PAVISTREAM     pOutStreams[MAX_AVISTREAMS];
  PAVISTREAM     pInStreams[MAX_AVISTREAMS];
  AVIFILEINFOW   fInfo;
  AVISTREAMINFOW sInfo;

  PAVIFILE       pfile = NULL; /* the output AVI file */
  LONG           lFirstVideo = -1;
  int            curStream;

  /* for interleaving ... */
  DWORD          dwInterleave = 0; /* interleave rate */
  DWORD          dwFileInitialFrames;
  LONG           lFileLength;
  LONG           lSampleInc;

  /* for reading/writing the data ... */
  LPVOID         lpBuffer = NULL;
  LONG           cbBuffer;        /* real size of lpBuffer */
  LONG           lBufferSize;     /* needed bytes for format(s), etc. */
  LONG           lReadBytes;
  LONG           lReadSamples;
  HRESULT        hres;

  TRACE("(%s,%p,%p,%d,%p,%p)\n", debugstr_w(szFile), pclsidHandler,
	lpfnCallback, nStreams, ppavi, plpOptions);

  if (szFile == NULL || ppavi == NULL || plpOptions == NULL)
    return AVIERR_BADPARAM;
  if (nStreams >= MAX_AVISTREAMS) {
    WARN("Can't write AVI with %d streams only supports %d -- change MAX_AVISTREAMS!\n", nStreams, MAX_AVISTREAMS);
    return AVIERR_INTERNAL;
  }

  if (lpfnCallback == NULL)
    lpfnCallback = AVIFILE_AVISaveDefaultCallback;

  /* clear local variable(s) */
  for (curStream = 0; curStream < nStreams; curStream++) {
    pInStreams[curStream]  = NULL;
    pOutStreams[curStream] = NULL;
  }

  /* open output AVI file (create it if it doesn't exist) */
  hres = AVIFileOpenW(&pfile, szFile, OF_CREATE|OF_SHARE_EXCLUSIVE|OF_WRITE,
		      pclsidHandler);
  if (FAILED(hres))
    return hres;
  AVIFileInfoW(pfile, &fInfo, sizeof(fInfo)); /* for dwCaps */

  /* initialize our data structures part 1 */
  for (curStream = 0; curStream < nStreams; curStream++) {
    PAVISTREAM pCurStream = ppavi[curStream];

    hres = AVIStreamInfoW(pCurStream, &sInfo, sizeof(sInfo));
    if (FAILED(hres))
      goto error;

    /* search first video stream and check for interleaving */
    if (sInfo.fccType == streamtypeVIDEO) {
      /* remember first video stream -- needed for interleaving */
      if (lFirstVideo < 0)
	lFirstVideo = curStream;
    } else if (!dwInterleave) {
      /* check if any non-video stream wants to be interleaved */
      WARN("options.flags=0x%X options.dwInterleave=%u\n",plpOptions[curStream]->dwFlags,plpOptions[curStream]->dwInterleaveEvery);
      if (plpOptions[curStream] != NULL &&
	  plpOptions[curStream]->dwFlags & AVICOMPRESSF_INTERLEAVE)
	dwInterleave = plpOptions[curStream]->dwInterleaveEvery;
    }

    /* create de-/compressed stream interface if needed */
    pInStreams[curStream] = NULL;
    if (plpOptions[curStream] != NULL) {
      if (plpOptions[curStream]->fccHandler ||
	  plpOptions[curStream]->lpFormat != NULL) {
	DWORD dwKeySave = plpOptions[curStream]->dwKeyFrameEvery;

	if (fInfo.dwCaps & AVIFILECAPS_ALLKEYFRAMES)
	  plpOptions[curStream]->dwKeyFrameEvery = 1;

	hres = AVIMakeCompressedStream(&pInStreams[curStream], pCurStream,
				       plpOptions[curStream], NULL);
	plpOptions[curStream]->dwKeyFrameEvery = dwKeySave;
	if (FAILED(hres) || pInStreams[curStream] == NULL) {
	  pInStreams[curStream] = NULL;
	  goto error;
	}

	/* test stream interface and update stream-info */
	hres = AVIStreamInfoW(pInStreams[curStream], &sInfo, sizeof(sInfo));
	if (FAILED(hres))
	  goto error;
      }
    }

    /* now handle streams which will only be copied */
    if (pInStreams[curStream] == NULL) {
      pCurStream = pInStreams[curStream] = ppavi[curStream];
      AVIStreamAddRef(pCurStream);
    } else
      pCurStream = pInStreams[curStream];

    lStart[curStream] = sInfo.dwStart;
  } /* for all streams */

  /* check that first video stream is the first stream */
  if (lFirstVideo > 0) {
    PAVISTREAM pTmp = pInStreams[lFirstVideo];
    LONG lTmp = lStart[lFirstVideo];

    pInStreams[lFirstVideo] = pInStreams[0];
    pInStreams[0] = pTmp;
    lStart[lFirstVideo] = lStart[0];
    lStart[0] = lTmp;
    lFirstVideo = 0;
  }

  /* allocate buffer for formats, data, etc. of an initial size of 64 kBytes*/
  cbBuffer = 0x00010000;
  lpBuffer = HeapAlloc(GetProcessHeap(), 0, cbBuffer);
  if (lpBuffer == NULL) {
    hres = AVIERR_MEMORY;
    goto error;
  }

  AVIStreamInfoW(pInStreams[0], &sInfo, sizeof(sInfo));
  lFileLength = sInfo.dwLength;
  dwFileInitialFrames = 0;
  if (lFirstVideo >= 0) {
    /* check for correct version of the format
     *  -- need at least BITMAPINFOHEADER or newer
     */
    lSampleInc = 1;
    lBufferSize = cbBuffer;
    hres = AVIStreamReadFormat(pInStreams[lFirstVideo], AVIStreamStart(pInStreams[lFirstVideo]), lpBuffer, &lBufferSize);
    if (lBufferSize < (LONG)sizeof(BITMAPINFOHEADER))
      hres = AVIERR_INTERNAL;
    if (FAILED(hres))
      goto error;
  } else /* use one second blocks for interleaving if no video present */
    lSampleInc = AVIStreamTimeToSample(pInStreams[0], 1000000);

  /* create output streams */
  for (curStream = 0; curStream < nStreams; curStream++) {
    AVIStreamInfoW(pInStreams[curStream], &sInfo, sizeof(sInfo));

    sInfo.dwInitialFrames = 0;
    if (dwInterleave != 0 && curStream > 0 && sInfo.fccType != streamtypeVIDEO) {
      /* 750 ms initial frames for non-video streams */
      sInfo.dwInitialFrames = AVIStreamTimeToSample(pInStreams[0], 750);
    }

    hres = AVIFileCreateStreamW(pfile, &pOutStreams[curStream], &sInfo);
    if (pOutStreams[curStream] != NULL && SUCCEEDED(hres)) {
      /* copy initial format for this stream */
      lBufferSize = cbBuffer;
      hres = AVIStreamReadFormat(pInStreams[curStream], sInfo.dwStart,
				 lpBuffer, &lBufferSize);
      if (FAILED(hres))
	goto error;
      hres = AVIStreamSetFormat(pOutStreams[curStream], 0, lpBuffer, lBufferSize);
      if (FAILED(hres))
	goto error;

      /* try to copy stream handler data */
      lBufferSize = cbBuffer;
      hres = AVIStreamReadData(pInStreams[curStream], ckidSTREAMHANDLERDATA,
			       lpBuffer, &lBufferSize);
      if (SUCCEEDED(hres) && lBufferSize > 0) {
	hres = AVIStreamWriteData(pOutStreams[curStream],ckidSTREAMHANDLERDATA,
				  lpBuffer, lBufferSize);
	if (FAILED(hres))
	  goto error;
      }

      if (dwFileInitialFrames < sInfo.dwInitialFrames)
	dwFileInitialFrames = sInfo.dwInitialFrames;
      lReadBytes =
	AVIStreamSampleToSample(pOutStreams[0], pInStreams[curStream],
				sInfo.dwLength);
      if (lFileLength < lReadBytes)
	lFileLength = lReadBytes;
    } else {
      /* creation of de-/compression stream interface failed */
      WARN("creation of (de-)compression stream failed for stream %d\n",curStream);
      AVIStreamRelease(pInStreams[curStream]);
      if (curStream + 1 >= nStreams) {
	/* move the others one up */
	PAVISTREAM *ppas = &pInStreams[curStream];
	int            n = nStreams - (curStream + 1);

	do {
	  *ppas = pInStreams[curStream + 1];
	} while (--n);
      }
      nStreams--;
      curStream--;
    }
  } /* create output streams for all input streams */

  /* have we still something to write, or lost everything? */
  if (nStreams <= 0)
    goto error;

  if (dwInterleave) {
    LONG lCurFrame = -dwFileInitialFrames;

    /* interleaved file */
    if (dwInterleave == 1)
      AVIFileEndRecord(pfile);

    for (; lCurFrame < lFileLength; lCurFrame += lSampleInc) {
      for (curStream = 0; curStream < nStreams; curStream++) {
	LONG lLastSample;

	hres = AVIStreamInfoW(pOutStreams[curStream], &sInfo, sizeof(sInfo));
	if (FAILED(hres))
	  goto error;

	/* initial frames phase at the end for this stream? */
	if (-(LONG)sInfo.dwInitialFrames > lCurFrame)
	  continue;

	if ((lFileLength - lSampleInc) <= lCurFrame) {
	  lLastSample = AVIStreamLength(pInStreams[curStream]);
	  lFirstVideo = lLastSample + AVIStreamStart(pInStreams[curStream]);
	} else {
	  if (curStream != 0) {
	    lFirstVideo =
	      AVIStreamSampleToSample(pInStreams[curStream], pInStreams[0],
				      (sInfo.fccType == streamtypeVIDEO ? 
				       (LONG)dwInterleave : lSampleInc) +
				      sInfo.dwInitialFrames + lCurFrame);
	  } else
	    lFirstVideo = lSampleInc + (sInfo.dwInitialFrames + lCurFrame);

	  lLastSample = AVIStreamEnd(pInStreams[curStream]);
	  if (lLastSample <= lFirstVideo)
	    lFirstVideo = lLastSample;
	}

	/* copy needed samples now */
	WARN("copy from stream %d samples %d to %d...\n",curStream,
	      lStart[curStream],lFirstVideo);
	while (lFirstVideo > lStart[curStream]) {
	  DWORD flags = 0;

	  /* copy format in case it can change */
	  lBufferSize = cbBuffer;
	  hres = AVIStreamReadFormat(pInStreams[curStream], lStart[curStream],
				     lpBuffer, &lBufferSize);
	  if (FAILED(hres))
	    goto error;
	  AVIStreamSetFormat(pOutStreams[curStream], lStart[curStream],
			     lpBuffer, lBufferSize);

	  /* try to read data until we got it, or error */
	  do {
	    hres = AVIStreamRead(pInStreams[curStream], lStart[curStream],
				 lFirstVideo - lStart[curStream], lpBuffer,
				 cbBuffer, &lReadBytes, &lReadSamples);
	  } while ((hres == AVIERR_BUFFERTOOSMALL) &&
		   (lpBuffer = HeapReAlloc(GetProcessHeap(), 0, lpBuffer, cbBuffer *= 2)) != NULL);
	  if (lpBuffer == NULL)
	    hres = AVIERR_MEMORY;
	  if (FAILED(hres))
	    goto error;

	  if (AVIStreamIsKeyFrame(pInStreams[curStream], (LONG)sInfo.dwStart))
	    flags = AVIIF_KEYFRAME;
	  hres = AVIStreamWrite(pOutStreams[curStream], -1, lReadSamples,
				lpBuffer, lReadBytes, flags, NULL, NULL);
	  if (FAILED(hres))
	    goto error;

	  lStart[curStream] += lReadSamples;
	}
	lStart[curStream] = lFirstVideo;
      } /* stream by stream */

      /* need to close this block? */
      if (dwInterleave == 1) {
	hres = AVIFileEndRecord(pfile);
	if (FAILED(hres))
	  break;
      }

      /* show progress */
      if (lpfnCallback(MulDiv(dwFileInitialFrames + lCurFrame, 100,
			      dwFileInitialFrames + lFileLength))) {
	hres = AVIERR_USERABORT;
	break;
      }
    } /* copy frame by frame */
  } else {
    /* non-interleaved file */

    for (curStream = 0; curStream < nStreams; curStream++) {
      /* show progress */
      if (lpfnCallback(MulDiv(curStream, 100, nStreams))) {
	hres = AVIERR_USERABORT;
	goto error;
      }

      AVIStreamInfoW(pInStreams[curStream], &sInfo, sizeof(sInfo));

      if (sInfo.dwSampleSize != 0) {
	/* sample-based data like audio */
	while (sInfo.dwStart < sInfo.dwLength) {
	  LONG lSamples = cbBuffer / sInfo.dwSampleSize;

	  /* copy format in case it can change */
	  lBufferSize = cbBuffer;
	  hres = AVIStreamReadFormat(pInStreams[curStream], sInfo.dwStart,
				     lpBuffer, &lBufferSize);
	  if (FAILED(hres))
	    goto error;
	  AVIStreamSetFormat(pOutStreams[curStream], sInfo.dwStart,
			     lpBuffer, lBufferSize);

	  /* limit to stream boundaries */
	  if (lSamples != (LONG)(sInfo.dwLength - sInfo.dwStart))
	    lSamples = sInfo.dwLength - sInfo.dwStart;

	  /* now try to read until we get it, or an error occurs */
	  do {
	    lReadBytes   = cbBuffer;
	    lReadSamples = 0;
	    hres = AVIStreamRead(pInStreams[curStream],sInfo.dwStart,lSamples,
				 lpBuffer,cbBuffer,&lReadBytes,&lReadSamples);
	  } while ((hres == AVIERR_BUFFERTOOSMALL) &&
		   (lpBuffer = HeapReAlloc(GetProcessHeap(), 0, lpBuffer, cbBuffer *= 2)) != NULL);
	  if (lpBuffer == NULL)
	    hres = AVIERR_MEMORY;
	  if (FAILED(hres))
	    goto error;
	  if (lReadSamples != 0) {
	    sInfo.dwStart += lReadSamples;
	    hres = AVIStreamWrite(pOutStreams[curStream], -1, lReadSamples,
				  lpBuffer, lReadBytes, 0, NULL , NULL);
	    if (FAILED(hres))
	      goto error;

	    /* show progress */
	    if (lpfnCallback(MulDiv(sInfo.dwStart,100,nStreams*sInfo.dwLength)+
			     MulDiv(curStream, 100, nStreams))) {
	      hres = AVIERR_USERABORT;
	      goto error;
	    }
	  } else {
	    if ((sInfo.dwLength - sInfo.dwStart) != 1) {
	      hres = AVIERR_FILEREAD;
	      goto error;
	    }
	  }
	}
      } else {
	/* block-based data like video */
	for (; sInfo.dwStart < sInfo.dwLength; sInfo.dwStart++) {
	  DWORD flags = 0;

	  /* copy format in case it can change */
	  lBufferSize = cbBuffer;
	  hres = AVIStreamReadFormat(pInStreams[curStream], sInfo.dwStart,
				     lpBuffer, &lBufferSize);
	  if (FAILED(hres))
	    goto error;
	  AVIStreamSetFormat(pOutStreams[curStream], sInfo.dwStart,
			     lpBuffer, lBufferSize);

	  /* try to read block and resize buffer if necessary */
	  do {
	    lReadSamples = 0;
	    lReadBytes   = cbBuffer;
	    hres = AVIStreamRead(pInStreams[curStream], sInfo.dwStart, 1,
				 lpBuffer, cbBuffer,&lReadBytes,&lReadSamples);
	  } while ((hres == AVIERR_BUFFERTOOSMALL) &&
		   (lpBuffer = HeapReAlloc(GetProcessHeap(), 0, lpBuffer, cbBuffer *= 2)) != NULL);
	  if (lpBuffer == NULL)
	    hres = AVIERR_MEMORY;
	  if (FAILED(hres))
	    goto error;
	  if (lReadSamples != 1) {
	    hres = AVIERR_FILEREAD;
	    goto error;
	  }

	  if (AVIStreamIsKeyFrame(pInStreams[curStream], (LONG)sInfo.dwStart))
	    flags = AVIIF_KEYFRAME;
	  hres = AVIStreamWrite(pOutStreams[curStream], -1, lReadSamples,
				lpBuffer, lReadBytes, flags, NULL, NULL);
	  if (FAILED(hres))
	    goto error;

	  /* show progress */
	  if (lpfnCallback(MulDiv(sInfo.dwStart,100,nStreams*sInfo.dwLength)+
			   MulDiv(curStream, 100, nStreams))) {
	    hres = AVIERR_USERABORT;
	    goto error;
	  }
	} /* copy all blocks */
      }
    } /* copy data stream by stream */
  }

 error:
  HeapFree(GetProcessHeap(), 0, lpBuffer);
  if (pfile != NULL) {
    for (curStream = 0; curStream < nStreams; curStream++) {
      if (pOutStreams[curStream] != NULL)
	AVIStreamRelease(pOutStreams[curStream]);
      if (pInStreams[curStream] != NULL)
	AVIStreamRelease(pInStreams[curStream]);
    }

    AVIFileRelease(pfile);
  }

  return hres;
}

/***********************************************************************
 *		CreateEditableStream	(AVIFIL32.@)
 */
HRESULT WINAPI CreateEditableStream(PAVISTREAM *ppEditable, PAVISTREAM pSource)
{
  IAVIEditStream *pEdit = NULL;
  HRESULT	  hr;

  TRACE("(%p,%p)\n", ppEditable, pSource);

  if (ppEditable == NULL)
    return AVIERR_BADPARAM;

  *ppEditable = NULL;

  if (pSource != NULL) {
    hr = IAVIStream_QueryInterface(pSource, &IID_IAVIEditStream,
				   (LPVOID*)&pEdit);
    if (SUCCEEDED(hr) && pEdit != NULL) {
      hr = IAVIEditStream_Clone(pEdit, ppEditable);
      IAVIEditStream_Release(pEdit);

      return hr;
    }
  }

  /* need own implementation of IAVIEditStream */
  pEdit = AVIFILE_CreateEditStream(pSource);
  if (pEdit == NULL)
    return AVIERR_MEMORY;

  hr = IAVIEditStream_QueryInterface(pEdit, &IID_IAVIStream,
                                     (LPVOID*)ppEditable);
  IAVIEditStream_Release(pEdit);

  return hr;
}

/***********************************************************************
 *		EditStreamClone		(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamClone(PAVISTREAM pStream, PAVISTREAM *ppResult)
{
  PAVIEDITSTREAM pEdit = NULL;
  HRESULT        hr;

  TRACE("(%p,%p)\n", pStream, ppResult);

  if (pStream == NULL)
    return AVIERR_BADHANDLE;
  if (ppResult == NULL)
    return AVIERR_BADPARAM;

  *ppResult = NULL;

  hr = IAVIStream_QueryInterface(pStream, &IID_IAVIEditStream,(LPVOID*)&pEdit);
  if (SUCCEEDED(hr) && pEdit != NULL) {
    hr = IAVIEditStream_Clone(pEdit, ppResult);

    IAVIEditStream_Release(pEdit);
  } else
    hr = AVIERR_UNSUPPORTED;

  return hr;
}

/***********************************************************************
 *		EditStreamCopy		(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamCopy(PAVISTREAM pStream, LONG *plStart,
			      LONG *plLength, PAVISTREAM *ppResult)
{
  PAVIEDITSTREAM pEdit = NULL;
  HRESULT        hr;

  TRACE("(%p,%p,%p,%p)\n", pStream, plStart, plLength, ppResult);

  if (pStream == NULL)
    return AVIERR_BADHANDLE;
  if (plStart == NULL || plLength == NULL || ppResult == NULL)
    return AVIERR_BADPARAM;

  *ppResult = NULL;

  hr = IAVIStream_QueryInterface(pStream, &IID_IAVIEditStream,(LPVOID*)&pEdit);
  if (SUCCEEDED(hr) && pEdit != NULL) {
    hr = IAVIEditStream_Copy(pEdit, plStart, plLength, ppResult);

    IAVIEditStream_Release(pEdit);
  } else
    hr = AVIERR_UNSUPPORTED;

  return hr;
}

/***********************************************************************
 *		EditStreamCut		(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamCut(PAVISTREAM pStream, LONG *plStart,
			     LONG *plLength, PAVISTREAM *ppResult)
{
  PAVIEDITSTREAM pEdit = NULL;
  HRESULT        hr;

  TRACE("(%p,%p,%p,%p)\n", pStream, plStart, plLength, ppResult);

  if (ppResult != NULL)
    *ppResult = NULL;
  if (pStream == NULL)
    return AVIERR_BADHANDLE;
  if (plStart == NULL || plLength == NULL)
    return AVIERR_BADPARAM;

  hr = IAVIStream_QueryInterface(pStream, &IID_IAVIEditStream,(LPVOID*)&pEdit);
  if (SUCCEEDED(hr) && pEdit != NULL) {
    hr = IAVIEditStream_Cut(pEdit, plStart, plLength, ppResult);

    IAVIEditStream_Release(pEdit);
  } else
    hr = AVIERR_UNSUPPORTED;

  return hr;
}

/***********************************************************************
 *		EditStreamPaste		(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamPaste(PAVISTREAM pDest, LONG *plStart, LONG *plLength,
			       PAVISTREAM pSource, LONG lStart, LONG lEnd)
{
  PAVIEDITSTREAM pEdit = NULL;
  HRESULT        hr;

  TRACE("(%p,%p,%p,%p,%d,%d)\n", pDest, plStart, plLength,
	pSource, lStart, lEnd);

  if (pDest == NULL || pSource == NULL)
    return AVIERR_BADHANDLE;
  if (plStart == NULL || plLength == NULL || lStart < 0)
    return AVIERR_BADPARAM;

  hr = IAVIStream_QueryInterface(pDest, &IID_IAVIEditStream,(LPVOID*)&pEdit);
  if (SUCCEEDED(hr) && pEdit != NULL) {
    hr = IAVIEditStream_Paste(pEdit, plStart, plLength, pSource, lStart, lEnd);

    IAVIEditStream_Release(pEdit);
  } else
    hr = AVIERR_UNSUPPORTED;

  return hr;
}

/***********************************************************************
 *		EditStreamSetInfoA	(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamSetInfoA(PAVISTREAM pstream, LPAVISTREAMINFOA asi,
				  LONG size)
{
  AVISTREAMINFOW asiw;

  TRACE("(%p,%p,%d)\n", pstream, asi, size);

  if (size >= 0 && size < sizeof(AVISTREAMINFOA))
    return AVIERR_BADSIZE;

  memcpy(&asiw, asi, sizeof(asiw) - sizeof(asiw.szName));
  MultiByteToWideChar(CP_ACP, 0, asi->szName, -1,
		      asiw.szName, sizeof(asiw.szName)/sizeof(WCHAR));

  return EditStreamSetInfoW(pstream, &asiw, sizeof(asiw));
}

/***********************************************************************
 *		EditStreamSetInfoW	(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamSetInfoW(PAVISTREAM pstream, LPAVISTREAMINFOW asi,
				  LONG size)
{
  PAVIEDITSTREAM pEdit = NULL;
  HRESULT        hr;

  TRACE("(%p,%p,%d)\n", pstream, asi, size);

  if (size >= 0 && size < sizeof(AVISTREAMINFOA))
    return AVIERR_BADSIZE;

  hr = IAVIStream_QueryInterface(pstream, &IID_IAVIEditStream,(LPVOID*)&pEdit);
  if (SUCCEEDED(hr) && pEdit != NULL) {
    hr = IAVIEditStream_SetInfo(pEdit, asi, size);

    IAVIEditStream_Release(pEdit);
  } else
    hr = AVIERR_UNSUPPORTED;

  return hr;
}

/***********************************************************************
 *		EditStreamSetNameA	(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamSetNameA(PAVISTREAM pstream, LPCSTR szName)
{
  AVISTREAMINFOA asia;
  HRESULT        hres;

  TRACE("(%p,%s)\n", pstream, debugstr_a(szName));

  if (pstream == NULL)
    return AVIERR_BADHANDLE;
  if (szName == NULL)
    return AVIERR_BADPARAM;

  hres = AVIStreamInfoA(pstream, &asia, sizeof(asia));
  if (FAILED(hres))
    return hres;

  memset(asia.szName, 0, sizeof(asia.szName));
  lstrcpynA(asia.szName, szName, sizeof(asia.szName)/sizeof(asia.szName[0]));

  return EditStreamSetInfoA(pstream, &asia, sizeof(asia));
}

/***********************************************************************
 *		EditStreamSetNameW	(AVIFIL32.@)
 */
HRESULT WINAPI EditStreamSetNameW(PAVISTREAM pstream, LPCWSTR szName)
{
  AVISTREAMINFOW asiw;
  HRESULT        hres;

  TRACE("(%p,%s)\n", pstream, debugstr_w(szName));

  if (pstream == NULL)
    return AVIERR_BADHANDLE;
  if (szName == NULL)
    return AVIERR_BADPARAM;

  hres = IAVIStream_Info(pstream, &asiw, sizeof(asiw));
  if (FAILED(hres))
    return hres;

  memset(asiw.szName, 0, sizeof(asiw.szName));
  lstrcpynW(asiw.szName, szName, sizeof(asiw.szName)/sizeof(asiw.szName[0]));

  return EditStreamSetInfoW(pstream, &asiw, sizeof(asiw));
}

/***********************************************************************
 *		AVIClearClipboard	(AVIFIL32.@)
 */
HRESULT WINAPI AVIClearClipboard(void)
{
  TRACE("()\n");

  return AVIERR_UNSUPPORTED; /* OleSetClipboard(NULL); */
}

/***********************************************************************
 *		AVIGetFromClipboard	(AVIFIL32.@)
 */
HRESULT WINAPI AVIGetFromClipboard(PAVIFILE *ppfile)
{
  FIXME("(%p), stub!\n", ppfile);

  *ppfile = NULL;

  return AVIERR_UNSUPPORTED;
}

/***********************************************************************
 *      AVIMakeStreamFromClipboard (AVIFIL32.@)
 */
HRESULT WINAPI AVIMakeStreamFromClipboard(UINT cfFormat, HANDLE hGlobal,
                                          PAVISTREAM * ppstream)
{
  FIXME("(0x%08x,%p,%p), stub!\n", cfFormat, hGlobal, ppstream);

  if (ppstream == NULL)
    return AVIERR_BADHANDLE;

  return AVIERR_UNSUPPORTED;
}

/***********************************************************************
 *		AVIPutFileOnClipboard	(AVIFIL32.@)
 */
HRESULT WINAPI AVIPutFileOnClipboard(PAVIFILE pfile)
{
  FIXME("(%p), stub!\n", pfile);

  if (pfile == NULL)
    return AVIERR_BADHANDLE;

  return AVIERR_UNSUPPORTED;
}

HRESULT WINAPIV AVISaveA(LPCSTR szFile, CLSID * pclsidHandler, AVISAVECALLBACK lpfnCallback,
                        int nStreams, PAVISTREAM pavi, LPAVICOMPRESSOPTIONS lpOptions, ...)
{
    FIXME("(%s,%p,%p,0x%08x,%p,%p), stub!\n", debugstr_a(szFile), pclsidHandler, lpfnCallback,
          nStreams, pavi, lpOptions);

    return AVIERR_UNSUPPORTED;
}

HRESULT WINAPIV AVISaveW(LPCWSTR szFile, CLSID * pclsidHandler, AVISAVECALLBACK lpfnCallback,
                        int nStreams, PAVISTREAM pavi, LPAVICOMPRESSOPTIONS lpOptions, ...)
{
    FIXME("(%s,%p,%p,0x%08x,%p,%p), stub!\n", debugstr_w(szFile), pclsidHandler, lpfnCallback,
          nStreams, pavi, lpOptions);

    return AVIERR_UNSUPPORTED;
}
