Could you hire me? Contact me if you like what I’ve done in this article and think I can create value for your company with my skills.

July 9, 2008 / by Zsolt Soczó

Küzdelem az SQL Server 2008 RC0 telepítővel (debug war)

Hetek óta nincs SQL Serverem (jó, időm se volt), mert nem ment fel az RC0. Egyes komponensek nem mentek fel, pl. a database engine, ami azért hiányzott.
A probléma oka nyilvánvalóan az volt, hogy fenn volt előtte a februári CTP, ami odaganézott a merevlemezre ide-oda.
Ezért bőszen nekiálltam feszítővassal, lángvágóval, és kiszedtem az általam azonosított maradványokat a registryből, a fájlrendszerből, gacból. Erre ilyen hiba kezdett jönni:

2008-07-08 22:19:22 Slp: Microsoft.SqlServer.Setup.Chainer.Workflow.ActionExecutionException: MsiGetProductInfo failed to retrieve ProductVersion for package with Product Code = '{7D3F6746-94DE-4E1F-94F9-933B68EB68C4}'. Error code: 1605. ---> System.InvalidOperationException: MsiGetProductInfo failed to retrieve ProductVersion for package with Product Code = '{7D3F6746-94DE-4E1F-94F9-933B68EB68C4}'. Error code: 1605.
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Configuration.MsiExtension.SetFeatureInstallStateAction.FillInstallPropertyByProductCode(PackageInstallProperty pkg, String prodCode)
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Configuration.MsiExtension.SetFeatureInstallStateAction.FillInstallProperty(PackageInstallProperty pkg)
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Configuration.MsiExtension.SetFeatureInstallStateAction.ExecuteAction(String actionId)
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Chainer.Infrastructure.Action.Execute(String actionId, TextWriter errorStream)
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Setup.Chainer.Workflow.ActionInvocation.InvokeAction(WorkflowObject metabase, TextWriter statusStream)
2008-07-08 22:19:22 Slp:    at Microsoft.SqlServer.Setup.Chainer.Workflow.PendingActions.InvokeActions(WorkflowObject metaDb, TextWriter loggingStream)

Google nem adott kézzelfogható eredményt.

Reflectorral megnéztem, mi történik ezekben a metódusokban?

private void FillInstallPropertyByProductCode(PackageInstallProperty pkg, string prodCode); 
Declaring Type: Microsoft.SqlServer.Configuration.MsiExtension.SetFeatureInstallStateAction 
Assembly: Microsoft.SqlServer.Configuration.MsiExtension, Version=10.0.0.0 

Ez a kód a gyanús benne:

errorCode = MsiNativeMethods.MsiGetProductInfo(pkg.ProductCode, “Language”, lpValueBuf, ref capacity);
if (errorCode != 0)
{
throw new InvalidOperationException(SR.MsiGetProductInfoFailedToRetrieveProductVesrionByProductCode(pkg.ProductCode, errorCode));
}

Ismer valami ProductCode-ot, ennek akarja lekérni a verzióját, de nem sikerül, mert kézzel már leirtottam a darabjait.

Honnan veszi a beteg ProductCode-ot? CTRL-R, analyze. Itt hívják meg a fenti metódust:

private void FillInstallProperty(PackageInstallProperty pkg);

Ebben:

installedProductCodeList = this.msiMetadata.GetInstalledProductCodeList(packageAttributes);
if ((installedProductCodeList != null) && (installedProductCodeList.Count > 0))
{
this.FillInstallPropertyByProductCode(pkg, installedProductCodeList[0]);
}

Szóval a GetInstalledProductCodeList adja vissza a rossz prod code-ot. Ő belül ezt hívja meg:

errorCode = MsiNativeMethods.MsiEnumRelatedProducts(packageUpgradeCode, 0, iProductIndex, lpProductBuf);

MsiEnumRelatedProducts, ez adja vissza a baromságot. Ez már natív függvény, az MSI.DLL-ben. Elő a debuggerrel! Nem, nem a VS-re lesz szükség, az kis gyík a nagytesóhoz, a WinDbg-hez képest, ehhez az kevés.

UINT MsiEnumRelatedProducts(
  __in   LPCTSTR lpUpgradeCode,
  __in   DWORD dwReserved,
  __in   DWORD iProductIndex,
  __out  LPTSTR lpProductBuf
);

WinDbg-vel töréspont beállít a fenti függvényre. A törésponthoz be lehet állítani akciót a WinDbg-ben, ebben kiíratom a függvény első és 4. paraméterét, az 1-re keres rá, a 4.-ben jön vissza a baromság.

bu msi!MsiEnumRelatedProductsW+0x64 "du poi(esp+0x4);du poi(esp+0x10);g"

Ez a breakpoint szintax. Breapoint Unresolved (szimbolikus, futás közben oldja fel), az msi.dll MsiEnumRelatedProductsW függvényére, de nem a belépési pontjára, hanem 64h offsettel hátrébb (ez a függvény ret utasítása, azért ez kell, mert itt már ki van töltve a 4. paraméter).
Az akció rész idézőjelek között van, ez fut le, ha becsap a töréspont. du: dump unicode data. A poi feloldja az ESP+4 címet, onnan írjuk ki a stringet. Ugye ESP a visszatérési címre mutat, ESP+4 az első paraméterre, ami egy LPCTSTR, esetünkben LPCWSTR, ezt oldja fel a poi, a du meg kííratja. A 10h címen van a 4. paraméter. A g parancs futtatja tovább a kódot, azaz a töréspont valójában csak kiírja a számomra szükséges infókat, és a program fut tovább.

{65A00972-4629-4343-AAF7-9C35CE25CD84} erre kérdeznek rá, és {7D3F6746-94DE-4E1F-94F9-933B68EB68C4} rá a válasz, pont, ami a hibaüzenetben is jött.

No, honnan a francból szedi fel a 65A00972… GUID-ot? Bármennyire is bosszantó, se a fájlrendszerben, se a registryben nem találtam meg azt a kódot. Fukk.

Elő a procmonnal. Ugye az a gond, hogy detektál valami darabkát egy korábbi verzióból, de az MSI-ket már nem leli hozzá. Beállítottam szűrési feltételt, hogy a setup100.exe process név és a Path tartalmazza az UpgradeCode stringet. Kiderült, hogy miután megtalálja ezt:
HKEY_CLASSES_ROOT\Installer\UpgradeCodes\27900A5692643434AA7FC953EC52DC48
leáll a telepítés. Ezek szerint ez valami korábbi SQL Server verzió darabja lehet. Átneveztem ezt kicsit, hogy ne találja meg a telepítő. Ettől továbbment a telepítő, de befagyott. Kiirtottam az összes keresett UpgradeCode-ot és voalá, sikeresen felment a szerver.

Finnyás egy kis köcsög lett ez a verzió. Jó, tudom, nem illik szétszabni kézzel a registry-t, de akkor is. :)

Could you hire me? Contact me if you like what I’ve done in this article and think I can create value for your company with my skills.

LEAVE A COMMENT

1 COMMENTS

  • Hamurabi July 9, 2008

    Hehhehhe… azért ebben:
    {65A00972-4629-4343-AAF7-9C35CE25CD84}
    és ebben
    27900A5692643434AA7FC953EC52DC48
    van némi közös.

    Nézzük csak így a másodikat:
    27900A56-9264-3434-AA7F-C953EC52DC48
    Na?

    Jól meg kellene furkósbotozni az ilyent aki kitalálta :-D

    Én is megküzdöttem az sql 2008 ctp5->rc0 upgradeval.

    Jól beszart, és NINCS rá támogatás. Google sincs, ahogy te is tapasztaltad… Da túl vagyok rajta. Mostmár rutinból bármikor :-)

    És nálam elsőre letöltött telepítőnél kiderült, hogy a redist.cab hibás volt… áááá