[Try 3] msadp32.acm: block align and adpcm extra data

Vincent Pelletier plr.vincent at gmail.com
Tue Feb 3 12:30:19 CST 2009


Based heavily on Stefano Guidoni's patch[1].
- changed while loops into if + modulo
- mention MSDN page providing used formula

[1] http://www.winehq.org/pipermail/wine-patches/2009-January/068200.html
-- 
Vincent Pelletier
-------------- next part --------------
From 895b672cf94fef5d5d8aeb38b1bf1b21a0400027 Mon Sep 17 00:00:00 2001
From: Vincent Pelletier <plr.vincent at gmail.com>
Date: Sun, 1 Feb 2009 09:51:31 +0100
Subject: msadp32.acm : block align and adpcm extra data

---
 dlls/msadp32.acm/msadp32.c |   37 +++++++++++++++++++++++++++++--------
 1 files changed, 29 insertions(+), 8 deletions(-)

diff --git a/dlls/msadp32.acm/msadp32.c b/dlls/msadp32.acm/msadp32.c
index 40b8260..550d8cf 100644
--- a/dlls/msadp32.acm/msadp32.c
+++ b/dlls/msadp32.acm/msadp32.c
@@ -618,6 +618,9 @@ static	LRESULT	ADPCM_StreamClose(PACMDRVSTREAMINSTANCE adsi)
  */
 static	LRESULT ADPCM_StreamSize(const ACMDRVSTREAMINSTANCE *adsi, PACMDRVSTREAMSIZE adss)
 {
+    DWORD nblocks;
+    WORD wSamplesPerBlock;
+    /* wSamplesPerBlock formula comes from MSDN ADPCMWAVEFORMAT page.*/
     switch (adss->fdwSize)
     {
     case ACM_STREAMSIZEF_DESTINATION:
@@ -625,14 +628,20 @@ static	LRESULT ADPCM_StreamSize(const ACMDRVSTREAMINSTANCE *adsi, PACMDRVSTREAMS
 	if (adsi->pwfxSrc->wFormatTag == WAVE_FORMAT_PCM &&
 	    adsi->pwfxDst->wFormatTag == WAVE_FORMAT_ADPCM)
         {
-	    /* don't take block overhead into account, doesn't matter too much */
-	    adss->cbSrcLength = adss->cbDstLength * 4;
+	    wSamplesPerBlock = adsi->pwfxDst->nBlockAlign * 2 / adsi->pwfxDst->nChannels - 12;
+	    nblocks = adss->cbDstLength / adsi->pwfxDst->nBlockAlign;
+	    if (nblocks == 0)
+		return ACMERR_NOTPOSSIBLE;
+	    adss->cbSrcLength = nblocks * adsi->pwfxSrc->nBlockAlign * wSamplesPerBlock;
 	}
         else if (adsi->pwfxSrc->wFormatTag == WAVE_FORMAT_ADPCM &&
                  adsi->pwfxDst->wFormatTag == WAVE_FORMAT_PCM)
         {
-	    FIXME("misses the block header overhead\n");
-	    adss->cbSrcLength = 256 + adss->cbDstLength / 4;
+	    wSamplesPerBlock = adsi->pwfxSrc->nBlockAlign * 2 / adsi->pwfxSrc->nChannels - 12;
+	    nblocks = adss->cbDstLength / (adsi->pwfxDst->nBlockAlign * wSamplesPerBlock);
+	    if (nblocks == 0)
+		return ACMERR_NOTPOSSIBLE;
+	    adss->cbSrcLength = nblocks * adsi->pwfxSrc->nBlockAlign;
 	}
         else
         {
@@ -644,14 +653,26 @@ static	LRESULT ADPCM_StreamSize(const ACMDRVSTREAMINSTANCE *adsi, PACMDRVSTREAMS
 	if (adsi->pwfxSrc->wFormatTag == WAVE_FORMAT_PCM &&
 	    adsi->pwfxDst->wFormatTag == WAVE_FORMAT_ADPCM)
         {
-	    FIXME("misses the block header overhead\n");
-	    adss->cbDstLength = 256 + adss->cbSrcLength / 4;
+	    wSamplesPerBlock = adsi->pwfxDst->nBlockAlign * 2 / adsi->pwfxDst->nChannels - 12;
+	    nblocks = adss->cbSrcLength / (adsi->pwfxSrc->nBlockAlign * wSamplesPerBlock);
+	    if (nblocks == 0)
+		return ACMERR_NOTPOSSIBLE;
+	    if (adss->cbSrcLength % (adsi->pwfxSrc->nBlockAlign * wSamplesPerBlock));
+		/* Round block count up. */
+		nblocks++;
+	    adss->cbDstLength = nblocks * adsi->pwfxSrc->nBlockAlign;
 	}
         else if (adsi->pwfxSrc->wFormatTag == WAVE_FORMAT_ADPCM &&
                  adsi->pwfxDst->wFormatTag == WAVE_FORMAT_PCM)
         {
-	    /* don't take block overhead into account, doesn't matter too much */
-	    adss->cbDstLength = adss->cbSrcLength * 4;
+	    wSamplesPerBlock = adsi->pwfxSrc->nBlockAlign * 2 / adsi->pwfxSrc->nChannels - 12;
+	    nblocks = adss->cbSrcLength / adsi->pwfxSrc->nBlockAlign;
+	    if (nblocks == 0)
+		return ACMERR_NOTPOSSIBLE;
+	    if (adss->cbSrcLength % adsi->pwfxSrc->nBlockAlign)
+		/* Round block count up. */
+		nblocks++;
+	    adss->cbDstLength = nblocks * adsi->pwfxSrc->nBlockAlign * wSamplesPerBlock;
 	}
         else
         {
-- 
1.5.6.5



More information about the wine-patches mailing list