Marcus Meissner wrote: > > Hi, > > Siedler 3 tries to use MCIAVI to display a movie. Some features of MCI > still have some problems. > > - S3 opens the movie with mciSendString: > "open AVIVideo!E:\S3\Add\001\01_00_00.dat alias test" > and further references it using 'status test window handle' and the like. > mciSendString itself did not support aliases yet. Implemented. > > - mciavi.dll loads a commandtable using: > MCILOADCOMMANDRESOURCE(0x03a6,0x03a70070 "mciavi",0x0000) > note that dwType is 0. > > mciLoadCommandResource16() added another command table to entry 0, > which was not found by MCI_GetCommandTable() (0 is already used by > "CORE". The driver now has 2 'status' commands in its tables, where > the 'CORE' entry was wrong. I added a lookup for multiple tables. > (It probably should find out the correct place for the table in > mciLoadCommandResource16().) Marcus, got a look to the issues you brought up: 1/ regarding the first one, I rewrote the fix to be consistent with the rest of mciSendString (and fixed a bug in returned values - foudn while I was testing it -, and a memory leak) 2/ regarding the second one, the bug was not in command table storage but in the way Wine was linking a loaded specific command table with a driver. the driver specific command tables shall be returned in the structure passed with the DRV_OPEN message. This was ok in case of a 32 bit MCI driver, but the message parameters mapping was wrong for 16 drivers, hence not storing a relevant specific command table (if the driver did load it, as in your case). I hope the attached patch should fix your issues (if it does, Alexandre please use this patch instead) A+ -- --------------- Eric Pouech (http://perso.wanadoo.fr/eric.pouech/) "The future will be better tomorrow", Vice President Dan Quayle
Name: mci ChangeLog: fixed loading of 16 bit MCI drivers (for command tables) fixed alias handling in mciSendString GenDate: 2000/12/16 09:46:47 UTC ModifiedFiles: dlls/winmm/mci.c AddedFiles: =================================================================== RCS file: /home/cvs/cvsroot/wine/wine/dlls/winmm/mci.c,v retrieving revision 1.15 diff -u -u -r1.15 mci.c --- dlls/winmm/mci.c 2000/12/13 20:20:14 1.15 +++ dlls/winmm/mci.c 2000/12/16 09:43:15 @@ -437,19 +437,19 @@ } else { MCI_MapType res; - switch (res = MCI_MapMsg32ATo16(0, MCI_OPEN_DRIVER, 0, &lp)) { + switch (res = MCI_MapMsg32ATo16(0, DRV_OPEN, 0, &lp)) { case MCI_MAP_MSGERROR: - TRACE("Not handled yet (MCI_OPEN_DRIVER)\n"); + TRACE("Not handled yet (DRV_OPEN)\n"); break; case MCI_MAP_NOMEM: - TRACE("Problem mapping msg=MCI_OPEN_DRIVER from 32a to 16\n"); + TRACE("Problem mapping msg=DRV_OPEN from 32a to 16\n"); break; case MCI_MAP_OK: case MCI_MAP_OKMEM: if ((wmd->hDriver = OpenDriverA(drvTyp, "mci", lp))) wmd->bIs32 = FALSE; if (res == MCI_MAP_OKMEM) - MCI_UnMapMsg32ATo16(0, MCI_OPEN_DRIVER, 0, lp); + MCI_UnMapMsg32ATo16(0, DRV_OPEN, 0, lp); break; } } @@ -843,6 +843,7 @@ int offset = 0; DWORD data[MCI_DATA_SIZE]; LPCSTR lpCmd = 0; + LPSTR devAlias = NULL; LPWINE_MM_IDATA iData = MULTIMEDIA_GetIData(); BOOL bAutoOpen = FALSE; @@ -906,6 +907,16 @@ dwFlags |= MCI_OPEN_ELEMENT; data[3] = (DWORD)dev; } + if ((devAlias = strstr(args," alias "))) { + devAlias += 7; + tmp = strchr(devAlias,' '); + if (tmp) *tmp = '\0'; + data[4] = (DWORD)HEAP_strdupA(GetProcessHeap(), 0, devAlias); + if (tmp) *tmp = ' '; + /* should be done in regular options parsing */ + /* dwFlags |= MCI_OPEN_ALIAS; */ + } + dwRet = MCI_LoadMciDriver(iData, devType, &wmd); HeapFree(GetProcessHeap(), 0, devType); if (dwRet) { @@ -992,13 +1003,12 @@ dwRet = MCI_SendCommand(wmd->wDeviceID, MCI_GetMessage(lpCmd), dwFlags, (DWORD)data, TRUE); } TRACE("=> 1/ %lx (%s)\n", dwRet, lpstrRet); - if (dwRet) goto errCleanUp; - dwRet = MCI_HandleReturnValues(iData, dwRet, wmd, lpCmd, data, lpstrRet, uRetLen); TRACE("=> 2/ %lx (%s)\n", dwRet, lpstrRet); errCleanUp: HeapFree(GetProcessHeap(), 0, verb); + HeapFree(GetProcessHeap(), 0, devAlias); return dwRet; } @@ -1762,9 +1772,27 @@ default: size = sizeof(MCI_GENERIC_PARMS); break; } break; + case DRV_OPEN: + { + LPMCI_OPEN_DRIVER_PARMSA modp32a = (LPMCI_OPEN_DRIVER_PARMSA)(*lParam); + char* ptr = +SEGPTR_ALLOC(sizeof(LPMCI_OPEN_DRIVER_PARMSA) + sizeof(MCI_OPEN_DRIVER_PARMS16)); + LPMCI_OPEN_DRIVER_PARMS16 modp16; + + + if (ptr) { + *(LPMCI_OPEN_DRIVER_PARMSA*)(ptr) = modp32a; + modp16 = (LPMCI_OPEN_DRIVER_PARMS16)(ptr + +sizeof(LPMCI_OPEN_DRIVER_PARMSA)); + modp16->wDeviceID = modp32a->wDeviceID; + modp16->lpstrParams = modp32a->lpstrParams ? +SEGPTR_GET(SEGPTR_STRDUP(modp32a->lpstrParams)) : 0; + /* other fields are gonna be filled by the driver, don't copy them */ + } else { + return MCI_MAP_NOMEM; + } + *lParam = (LPARAM)SEGPTR_GET(ptr) + sizeof(LPMCI_OPEN_DRIVER_PARMSA); + } + return MCI_MAP_OKMEM; case DRV_LOAD: case DRV_ENABLE: - case DRV_OPEN: case DRV_CLOSE: case DRV_DISABLE: case DRV_FREE: @@ -1946,9 +1974,20 @@ /* FIXME: see map function */ break; + case DRV_OPEN: + if (lParam) { + LPMCI_OPEN_DRIVER_PARMS16 modp16 = +(LPMCI_OPEN_DRIVER_PARMS16)MapSL(lParam); + LPMCI_OPEN_DRIVER_PARMSA modp32a = +*(LPMCI_OPEN_DRIVER_PARMSA*)((char*)modp16 - sizeof(LPMCI_OPEN_DRIVER_PARMSA)); + + modp32a->wCustomCommandTable = modp16->wCustomCommandTable; + modp32a->wType = modp16->wType; + + if (modp16->lpstrParams && !SEGPTR_FREE(MapSL(modp16->lpstrParams))) + FIXME("bad free line=%d\n", __LINE__); + } + return MCI_MAP_OK; case DRV_LOAD: case DRV_ENABLE: - case DRV_OPEN: case DRV_CLOSE: case DRV_DISABLE: case DRV_FREE: