From 21a0685ef69e9d634600622b19ea970c6f58ef03 Mon Sep 17 00:00:00 2001 From: Sean Hall Date: Thu, 6 Oct 2022 16:37:14 -0500 Subject: Add Netfx bundle extension and netfx:DotNetCoreSearch. Remove built-in .NET Core packages since they update too quickly. Fixes 6257 --- src/ext/NetFx/NetFx.wixext.sln | 38 ++++- src/ext/NetFx/be/NetfxBundleExtension.cpp | 102 +++++++++++++ src/ext/NetFx/be/NetfxBundleExtension.h | 17 +++ src/ext/NetFx/be/detectnetcore.cpp | 140 +++++++++++++++++ src/ext/NetFx/be/detectnetcore.h | 9 ++ src/ext/NetFx/be/netfxbe.cpp | 62 ++++++++ src/ext/NetFx/be/netfxbe.def | 8 + src/ext/NetFx/be/netfxbe.vcxproj | 77 ++++++++++ src/ext/NetFx/be/netfxsearch.cpp | 149 ++++++++++++++++++ src/ext/NetFx/be/netfxsearch.h | 76 ++++++++++ src/ext/NetFx/be/precomp.cpp | 3 + src/ext/NetFx/be/precomp.h | 33 ++++ src/ext/NetFx/netcoresearch/netcoresearch.cpp | 158 ++++++++++++++++++++ src/ext/NetFx/netcoresearch/netcoresearch.h | 10 ++ src/ext/NetFx/netcoresearch/netcoresearch.vcxproj | 73 +++++++++ src/ext/NetFx/netcoresearch/packages.config | 9 ++ src/ext/NetFx/netcoresearch/precomp.cpp | 3 + src/ext/NetFx/netcoresearch/precomp.h | 18 +++ src/ext/NetFx/netfx.cmd | 7 +- .../WixToolsetTest.Netfx/NetfxExtensionFixture.cs | 3 + .../UsingDotNetCorePackages/BundleLatest.wxs | 11 +- .../UsingDotNetCorePackages/BundleLatest_x64.wxs | 8 +- .../UsingDotNetCorePackages/NetCore3.1.12_x64.wxs | 58 +++++++ .../UsingDotNetCorePackages/NetCore3.1.12_x86.wxs | 58 +++++++ .../UsingDotNetCorePackages/NetCore3_Platform.wxi | 49 ++++++ src/ext/NetFx/wixext/NetFxCompiler.cs | 166 +++++++++++++++++++++ src/ext/NetFx/wixext/NetFxExtensionData.cs | 3 +- .../NetFx/wixext/Symbols/NetFxNativeImageSymbol.cs | 23 ++- .../wixext/Symbols/NetFxNetCoreSearchSymbol.cs | 77 ++++++++++ .../NetFx/wixext/Symbols/NetfxSymbolDefinitions.cs | 49 ++++-- src/ext/NetFx/wixlib/NetCore3.1.12_x64.wxs | 58 ------- src/ext/NetFx/wixlib/NetCore3.1.12_x86.wxs | 58 ------- src/ext/NetFx/wixlib/NetCore3.1_x64.wxs | 22 --- src/ext/NetFx/wixlib/NetCore3.1_x86.wxs | 22 --- src/ext/NetFx/wixlib/NetCore3_Platform.wxi | 65 -------- src/ext/NetFx/wixlib/NetCoreShared.wxs | 4 +- .../NetFx/wixlib/NetfxBundleExtension_Platform.wxi | 15 ++ .../NetFx/wixlib/NetfxBundleExtension_arm64.wxs | 7 + src/ext/NetFx/wixlib/NetfxBundleExtension_x64.wxs | 7 + src/ext/NetFx/wixlib/NetfxBundleExtension_x86.wxs | 7 + src/ext/NetFx/wixlib/netfx.wixproj | 12 +- src/ext/Util/be/UtilBundleExtension.cpp | 12 +- src/ext/Util/be/beDecor.h | 13 -- src/ext/Util/be/detectsha2support.cpp | 8 +- src/ext/Util/be/precomp.h | 2 +- src/ext/Util/be/utilbe.vcxproj | 1 - src/ext/Util/be/utilsearch.cpp | 20 ++- .../Util/wixext/Symbols/UtilSymbolDefinitions.cs | 2 - src/ext/beDecor.h | 13 ++ src/libs/dutil/WixToolset.DUtil/inc/procutil.h | 3 +- src/libs/dutil/WixToolset.DUtil/procutil.cpp | 3 +- .../TestBA/TestBAWixlib/NetCore6.0.9_x86.wxs | 58 +++++++ .../TestBA/TestBAWixlib/NetCore6_Platform.wxi | 49 ++++++ .../burn/TestData/TestBA/TestBAWixlib/TestBA.wxs | 2 +- .../TestBA/TestBAWixlib/testbawixlib.wixproj | 1 + .../TestBA/TestBAWixlib_x64/NetCore6.0.9_x64.wxs | 58 +++++++ .../TestBA/TestBAWixlib_x64/TestBA_x64.wxs | 2 +- .../TestData/TestBA/TestBAWixlib_x64/WixBA_x64.wxs | 2 +- .../TestBAWixlib_x64/testbawixlib_x64.wixproj | 1 + 59 files changed, 1721 insertions(+), 303 deletions(-) create mode 100644 src/ext/NetFx/be/NetfxBundleExtension.cpp create mode 100644 src/ext/NetFx/be/NetfxBundleExtension.h create mode 100644 src/ext/NetFx/be/detectnetcore.cpp create mode 100644 src/ext/NetFx/be/detectnetcore.h create mode 100644 src/ext/NetFx/be/netfxbe.cpp create mode 100644 src/ext/NetFx/be/netfxbe.def create mode 100644 src/ext/NetFx/be/netfxbe.vcxproj create mode 100644 src/ext/NetFx/be/netfxsearch.cpp create mode 100644 src/ext/NetFx/be/netfxsearch.h create mode 100644 src/ext/NetFx/be/precomp.cpp create mode 100644 src/ext/NetFx/be/precomp.h create mode 100644 src/ext/NetFx/netcoresearch/netcoresearch.cpp create mode 100644 src/ext/NetFx/netcoresearch/netcoresearch.h create mode 100644 src/ext/NetFx/netcoresearch/netcoresearch.vcxproj create mode 100644 src/ext/NetFx/netcoresearch/packages.config create mode 100644 src/ext/NetFx/netcoresearch/precomp.cpp create mode 100644 src/ext/NetFx/netcoresearch/precomp.h create mode 100644 src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x64.wxs create mode 100644 src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x86.wxs create mode 100644 src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3_Platform.wxi create mode 100644 src/ext/NetFx/wixext/Symbols/NetFxNetCoreSearchSymbol.cs delete mode 100644 src/ext/NetFx/wixlib/NetCore3.1.12_x64.wxs delete mode 100644 src/ext/NetFx/wixlib/NetCore3.1.12_x86.wxs delete mode 100644 src/ext/NetFx/wixlib/NetCore3.1_x64.wxs delete mode 100644 src/ext/NetFx/wixlib/NetCore3.1_x86.wxs delete mode 100644 src/ext/NetFx/wixlib/NetCore3_Platform.wxi create mode 100644 src/ext/NetFx/wixlib/NetfxBundleExtension_Platform.wxi create mode 100644 src/ext/NetFx/wixlib/NetfxBundleExtension_arm64.wxs create mode 100644 src/ext/NetFx/wixlib/NetfxBundleExtension_x64.wxs create mode 100644 src/ext/NetFx/wixlib/NetfxBundleExtension_x86.wxs delete mode 100644 src/ext/Util/be/beDecor.h create mode 100644 src/ext/beDecor.h create mode 100644 src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6.0.9_x86.wxs create mode 100644 src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6_Platform.wxi create mode 100644 src/test/burn/TestData/TestBA/TestBAWixlib_x64/NetCore6.0.9_x64.wxs diff --git a/src/ext/NetFx/NetFx.wixext.sln b/src/ext/NetFx/NetFx.wixext.sln index 8316ac91..b8b72eb8 100644 --- a/src/ext/NetFx/NetFx.wixext.sln +++ b/src/ext/NetFx/NetFx.wixext.sln @@ -1,8 +1,12 @@  Microsoft Visual Studio Solution File, Format Version 12.00 -# Visual Studio 15 -VisualStudioVersion = 15.0.27130.2010 +# Visual Studio Version 17 +VisualStudioVersion = 17.3.32811.315 MinimumVisualStudioVersion = 15.0.26124.0 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "netcoresearch", "netcoresearch\netcoresearch.vcxproj", "{A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "netfxbe", "be\netfxbe.vcxproj", "{B65719C0-B2CC-45F9-AF33-6F147F741ADB}" +EndProject Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "netfxca", "ca\netfxca.vcxproj", "{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}" EndProject Project("{930C7802-8A8C-48F9-8165-68863BCCD9DD}") = "netfx", "wixlib\netfx.wixproj", "{45E4A6AC-3190-4E17-83F0-9935FFA5DC2B}" @@ -21,14 +25,40 @@ Global Release|x86 = Release|x86 EndGlobalSection GlobalSection(ProjectConfigurationPlatforms) = postSolution + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|Any CPU.ActiveCfg = Debug|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|Any CPU.Build.0 = Debug|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|x64.ActiveCfg = Debug|x64 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|x64.Build.0 = Debug|x64 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|x86.ActiveCfg = Debug|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Debug|x86.Build.0 = Debug|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|Any CPU.ActiveCfg = Release|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|Any CPU.Build.0 = Release|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|x64.ActiveCfg = Release|x64 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|x64.Build.0 = Release|x64 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|x86.ActiveCfg = Release|Win32 + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937}.Release|x86.Build.0 = Release|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|Any CPU.ActiveCfg = Debug|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|Any CPU.Build.0 = Debug|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|x64.ActiveCfg = Debug|x64 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|x64.Build.0 = Debug|x64 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|x86.ActiveCfg = Debug|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Debug|x86.Build.0 = Debug|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|Any CPU.ActiveCfg = Release|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|Any CPU.Build.0 = Release|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|x64.ActiveCfg = Release|x64 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|x64.Build.0 = Release|x64 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|x86.ActiveCfg = Release|Win32 + {B65719C0-B2CC-45F9-AF33-6F147F741ADB}.Release|x86.Build.0 = Release|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|Any CPU.ActiveCfg = Debug|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|Any CPU.Build.0 = Debug|Win32 - {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|x64.ActiveCfg = Debug|Win32 + {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|x64.ActiveCfg = Debug|x64 + {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|x64.Build.0 = Debug|x64 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|x86.ActiveCfg = Debug|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Debug|x86.Build.0 = Debug|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|Any CPU.ActiveCfg = Release|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|Any CPU.Build.0 = Release|Win32 - {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|x64.ActiveCfg = Release|Win32 + {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|x64.ActiveCfg = Release|x64 + {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|x64.Build.0 = Release|x64 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|x86.ActiveCfg = Release|Win32 {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.Release|x86.Build.0 = Release|Win32 {45E4A6AC-3190-4E17-83F0-9935FFA5DC2B}.Debug|Any CPU.ActiveCfg = Debug|x86 diff --git a/src/ext/NetFx/be/NetfxBundleExtension.cpp b/src/ext/NetFx/be/NetfxBundleExtension.cpp new file mode 100644 index 00000000..838a97c1 --- /dev/null +++ b/src/ext/NetFx/be/NetfxBundleExtension.cpp @@ -0,0 +1,102 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" +#include "BextBaseBundleExtension.h" + +class CWixNetfxBundleExtension : public CBextBaseBundleExtension +{ +public: // IBundleExtension + virtual STDMETHODIMP Search( + __in LPCWSTR wzId, + __in LPCWSTR wzVariable + ) + { + HRESULT hr = S_OK; + + hr = NetfxSearchExecute(&m_searches, wzId, wzVariable, m_pEngine, m_sczBaseDirectory); + + return hr; + } + +public: //CBextBaseBundleExtension + virtual STDMETHODIMP Initialize( + __in const BUNDLE_EXTENSION_CREATE_ARGS* pCreateArgs + ) + { + HRESULT hr = S_OK; + LPWSTR sczModulePath = NULL; + IXMLDOMDocument* pixdManifest = NULL; + IXMLDOMNode* pixnBundleExtension = NULL; + + hr = __super::Initialize(pCreateArgs); + BextExitOnFailure(hr, "CBextBaseBundleExtension initialization failed."); + + hr = PathForCurrentProcess(&sczModulePath, m_hInstance); + BextExitOnFailure(hr, "Failed to get bundle extension path."); + + hr = PathGetDirectory(sczModulePath, &m_sczBaseDirectory); + BextExitOnFailure(hr, "Failed to get bundle extension base directory."); + + hr = XmlLoadDocumentFromFile(m_sczBundleExtensionDataPath, &pixdManifest); + BextExitOnFailure(hr, "Failed to load bundle extension manifest from path: %ls", m_sczBundleExtensionDataPath); + + hr = BextGetBundleExtensionDataNode(pixdManifest, NETFX_BUNDLE_EXTENSION_ID, &pixnBundleExtension); + BextExitOnFailure(hr, "Failed to get BundleExtension '%ls'", NETFX_BUNDLE_EXTENSION_ID); + + hr = NetfxSearchParseFromXml(&m_searches, pixnBundleExtension); + BextExitOnFailure(hr, "Failed to parse searches from bundle extension manifest."); + + LExit: + ReleaseObject(pixnBundleExtension); + ReleaseObject(pixdManifest); + ReleaseStr(sczModulePath); + + return hr; + } + +public: + CWixNetfxBundleExtension( + __in HINSTANCE hInstance, + __in IBundleExtensionEngine* pEngine + ) : CBextBaseBundleExtension(pEngine) + { + m_searches = { }; + m_hInstance = hInstance; + m_sczBaseDirectory = NULL; + } + + ~CWixNetfxBundleExtension() + { + NetfxSearchUninitialize(&m_searches); + ReleaseStr(m_sczBaseDirectory); + } + +private: + NETFX_SEARCHES m_searches; + HINSTANCE m_hInstance; + LPWSTR m_sczBaseDirectory; +}; + +HRESULT NetfxBundleExtensionCreate( + __in HINSTANCE hInstance, + __in IBundleExtensionEngine* pEngine, + __in const BUNDLE_EXTENSION_CREATE_ARGS* pArgs, + __out IBundleExtension** ppBundleExtension + ) +{ + HRESULT hr = S_OK; + CWixNetfxBundleExtension* pExtension = NULL; + + pExtension = new CWixNetfxBundleExtension(hInstance, pEngine); + BextExitOnNull(pExtension, hr, E_OUTOFMEMORY, "Failed to create new CWixNetfxBundleExtension."); + + hr = pExtension->Initialize(pArgs); + BextExitOnFailure(hr, "CWixNetfxBundleExtension initialization failed."); + + *ppBundleExtension = pExtension; + pExtension = NULL; + +LExit: + ReleaseObject(pExtension); + return hr; +} diff --git a/src/ext/NetFx/be/NetfxBundleExtension.h b/src/ext/NetFx/be/NetfxBundleExtension.h new file mode 100644 index 00000000..0746dbed --- /dev/null +++ b/src/ext/NetFx/be/NetfxBundleExtension.h @@ -0,0 +1,17 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + + +// constants + +#define NETFX_BUNDLE_EXTENSION_ID BUNDLE_EXTENSION_DECORATION(L"NetfxBundleExtension") + + +// function declarations + +HRESULT NetfxBundleExtensionCreate( + __in HINSTANCE hInstance, + __in IBundleExtensionEngine* pEngine, + __in const BUNDLE_EXTENSION_CREATE_ARGS* pArgs, + __out IBundleExtension** ppBundleExtension + ); diff --git a/src/ext/NetFx/be/detectnetcore.cpp b/src/ext/NetFx/be/detectnetcore.cpp new file mode 100644 index 00000000..42156692 --- /dev/null +++ b/src/ext/NetFx/be/detectnetcore.cpp @@ -0,0 +1,140 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" + +HRESULT DetectNetCore( + __in NETFX_NET_CORE_PLATFORM platform, + __in NETFX_NET_CORE_RUNTIME_TYPE runtimeType, + __in LPCWSTR wzMajorVersion, + __in LPCWSTR wzBaseDirectory, + __inout LPWSTR* psczLatestVersion + ) +{ + HRESULT hr = S_OK; + LPCWSTR wzRuntimeType = NULL; + LPCWSTR wzPlatformName = NULL; + LPWSTR sczExePath = NULL; + LPWSTR sczCommandLine = NULL; + HANDLE hProcess = NULL; + HANDLE hStdOutErr = INVALID_HANDLE_VALUE; + BYTE* rgbOutput = NULL; + DWORD cbOutput = 0; + DWORD cbTotalRead = 0; + DWORD cbRead = 0; + DWORD dwExitCode = 0; + + ReleaseNullStr(*psczLatestVersion); + + switch (runtimeType) + { + case NETFX_NET_CORE_RUNTIME_TYPE_ASPNET: + wzRuntimeType = L"Microsoft.AspNetCore.App"; + break; + case NETFX_NET_CORE_RUNTIME_TYPE_CORE: + wzRuntimeType = L"Microsoft.NETCore.App"; + break; + case NETFX_NET_CORE_RUNTIME_TYPE_DESKTOP: + wzRuntimeType = L"Microsoft.WindowsDesktop.App"; + break; + default: + BextExitWithRootFailure(hr, E_INVALIDARG, "Unknown runtime type: %u", runtimeType); + break; + } + + switch (platform) + { + case NETFX_NET_CORE_PLATFORM_ARM64: + wzPlatformName = L"arm64"; + break; + case NETFX_NET_CORE_PLATFORM_X64: + wzPlatformName = L"x64"; + break; + case NETFX_NET_CORE_PLATFORM_X86: + wzPlatformName = L"x86"; + break; + default: + BextExitWithRootFailure(hr, E_INVALIDARG, "Unknown platform: %u", platform); + break; + } + + hr = StrAllocFormatted(&sczExePath, L"%ls%ls\\netcoresearch.exe", wzBaseDirectory, wzPlatformName); + BextExitOnFailure(hr, "Failed to build netcoresearch.exe path."); + + hr = StrAllocFormatted(&sczCommandLine, L"\"%ls\" %ls %ls", sczExePath, wzMajorVersion, wzRuntimeType); + BextExitOnFailure(hr, "Failed to build netcoresearch.exe command line."); + + hr = ProcExecute(sczExePath, sczCommandLine, &hProcess, NULL, &hStdOutErr); + if (HRESULT_FROM_WIN32(ERROR_EXE_MACHINE_TYPE_MISMATCH) == hr) + { + ExitFunction1(hr = S_FALSE); + } + BextExitOnFailure(hr, "Failed to run: %ls", sczCommandLine); + + cbOutput = 64; + + rgbOutput = reinterpret_cast(MemAlloc(cbOutput, TRUE)); + BextExitOnNull(rgbOutput, hr, E_OUTOFMEMORY, "Failed to alloc output string."); + + while (::ReadFile(hStdOutErr, rgbOutput + cbTotalRead, cbOutput - cbTotalRead, &cbRead, NULL)) + { + cbTotalRead += cbRead; + + if (cbTotalRead == cbOutput) + { + cbOutput *= 2; + + LPVOID pvNew = MemReAlloc(rgbOutput, cbOutput, TRUE); + BextExitOnNull(pvNew, hr, E_OUTOFMEMORY, "Failed to realloc output string."); + + rgbOutput = reinterpret_cast(pvNew); + } + } + + if (ERROR_BROKEN_PIPE != ::GetLastError()) + { + BextExitWithLastError(hr, "Failed to read netcoresearch.exe output."); + } + + hr = ProcWaitForCompletion(hProcess, INFINITE, &dwExitCode); + BextExitOnFailure(hr, "Failed to wait for netcoresearch.exe to exit."); + + if (0 != dwExitCode) + { + BextExitWithRootFailure(hr, E_UNEXPECTED, "netcoresearch.exe failed with exit code: 0x%x\r\nOutput:\r\n%hs", dwExitCode, rgbOutput); + } + + if (*rgbOutput) + { + hr = StrAllocStringAnsi(psczLatestVersion, reinterpret_cast(rgbOutput), 0, CP_UTF8); + BextExitOnFailure(hr, "Failed to widen output string: %hs", rgbOutput); + } + +LExit: + ReleaseFileHandle(hStdOutErr); + ReleaseHandle(hProcess); + ReleaseMem(rgbOutput); + ReleaseStr(sczCommandLine); + ReleaseStr(sczExePath); + + return hr; +} + +HRESULT NetfxPerformDetectNetCore( + __in LPCWSTR wzVariable, + __in NETFX_SEARCH* pSearch, + __in IBundleExtensionEngine* pEngine, + __in LPCWSTR wzBaseDirectory + ) +{ + HRESULT hr = S_OK; + LPWSTR sczLatestVersion = FALSE; + + hr = DetectNetCore(pSearch->NetCoreSearch.platform, pSearch->NetCoreSearch.runtimeType, pSearch->NetCoreSearch.sczMajorVersion, wzBaseDirectory, &sczLatestVersion); + BextExitOnFailure(hr, "DetectNetCore failed."); + + hr = pEngine->SetVariableVersion(wzVariable, sczLatestVersion); + BextExitOnFailure(hr, "Failed to set variable '%ls' to '%ls'", wzVariable, sczLatestVersion); + +LExit: + return hr; +} diff --git a/src/ext/NetFx/be/detectnetcore.h b/src/ext/NetFx/be/detectnetcore.h new file mode 100644 index 00000000..ef93b39b --- /dev/null +++ b/src/ext/NetFx/be/detectnetcore.h @@ -0,0 +1,9 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +HRESULT NetfxPerformDetectNetCore( + __in LPCWSTR wzVariable, + __in NETFX_SEARCH* pSearch, + __in IBundleExtensionEngine* pEngine, + __in LPCWSTR wzBaseDirectory + ); diff --git a/src/ext/NetFx/be/netfxbe.cpp b/src/ext/NetFx/be/netfxbe.cpp new file mode 100644 index 00000000..3a34cea3 --- /dev/null +++ b/src/ext/NetFx/be/netfxbe.cpp @@ -0,0 +1,62 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" +#include "BextBaseBundleExtensionProc.h" + +static HINSTANCE vhInstance = NULL; +static IBundleExtension* vpBundleExtension = NULL; + +// function definitions + +extern "C" BOOL WINAPI DllMain( + __in HINSTANCE hInstance, + __in DWORD dwReason, + __in LPVOID /*pvReserved*/ + ) +{ + switch(dwReason) + { + case DLL_PROCESS_ATTACH: + vhInstance = hInstance; + break; + + case DLL_PROCESS_DETACH: + vhInstance = NULL; + break; + } + + return TRUE; +} + +extern "C" HRESULT WINAPI BundleExtensionCreate( + __in const BUNDLE_EXTENSION_CREATE_ARGS* pArgs, + __inout BUNDLE_EXTENSION_CREATE_RESULTS* pResults + ) +{ + HRESULT hr = S_OK; + IBundleExtensionEngine* pEngine = NULL; + + hr = XmlInitialize(); + ExitOnFailure(hr, "Failed to initialize XML."); + + hr = BextInitializeFromCreateArgs(pArgs, &pEngine); + ExitOnFailure(hr, "Failed to initialize bext"); + + hr = NetfxBundleExtensionCreate(vhInstance, pEngine, pArgs, &vpBundleExtension); + BextExitOnFailure(hr, "Failed to create WixNetfxBundleExtension"); + + pResults->pfnBundleExtensionProc = BextBaseBundleExtensionProc; + pResults->pvBundleExtensionProcContext = vpBundleExtension; + +LExit: + ReleaseObject(pEngine); + + return hr; +} + +extern "C" void WINAPI BundleExtensionDestroy() +{ + BextUninitialize(); + ReleaseNullObject(vpBundleExtension); + XmlUninitialize(); +} diff --git a/src/ext/NetFx/be/netfxbe.def b/src/ext/NetFx/be/netfxbe.def new file mode 100644 index 00000000..c6605241 --- /dev/null +++ b/src/ext/NetFx/be/netfxbe.def @@ -0,0 +1,8 @@ +; Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + + +LIBRARY "netfxbe" + +EXPORTS + BundleExtensionCreate + BundleExtensionDestroy diff --git a/src/ext/NetFx/be/netfxbe.vcxproj b/src/ext/NetFx/be/netfxbe.vcxproj new file mode 100644 index 00000000..00588764 --- /dev/null +++ b/src/ext/NetFx/be/netfxbe.vcxproj @@ -0,0 +1,77 @@ + + + + + + + Debug + ARM64 + + + Release + ARM64 + + + Debug + X64 + + + Release + X64 + + + Debug + Win32 + + + Release + Win32 + + + + + {B65719C0-B2CC-45F9-AF33-6F147F741ADB} + DynamicLibrary + netfxbe + Unicode + netfxbe.def + WiX Toolset Netfx BundleExtension + + + + + + + msi.lib + + + + + + + + + Create + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/be/netfxsearch.cpp b/src/ext/NetFx/be/netfxsearch.cpp new file mode 100644 index 00000000..3c12161d --- /dev/null +++ b/src/ext/NetFx/be/netfxsearch.cpp @@ -0,0 +1,149 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" + + +STDMETHODIMP NetfxSearchParseFromXml( + __in NETFX_SEARCHES* pSearches, + __in IXMLDOMNode* pixnBundleExtension + ) +{ + HRESULT hr = S_OK; + IXMLDOMNodeList* pixnNodes = NULL; + IXMLDOMNode* pixnNode = NULL; + DWORD cNodes = 0; + BSTR bstrNodeName = NULL; + + // Select Netfx search nodes. + hr = XmlSelectNodes(pixnBundleExtension, L"NetFxNetCoreSearch", &pixnNodes); + BextExitOnFailure(hr, "Failed to select Netfx search nodes."); + + // Get Netfx search node count. + hr = pixnNodes->get_length((long*)&cNodes); + BextExitOnFailure(hr, "Failed to get Netfx search node count."); + + if (!cNodes) + { + ExitFunction(); + } + + // Allocate memory for searches. + pSearches->rgSearches = (NETFX_SEARCH*)MemAlloc(sizeof(NETFX_SEARCH) * cNodes, TRUE); + BextExitOnNull(pSearches->rgSearches, hr, E_OUTOFMEMORY, "Failed to allocate memory for search structs."); + + pSearches->cSearches = cNodes; + + // Parse search elements. + for (DWORD i = 0; i < cNodes; ++i) + { + NETFX_SEARCH* pSearch = &pSearches->rgSearches[i]; + + hr = XmlNextElement(pixnNodes, &pixnNode, &bstrNodeName); + BextExitOnFailure(hr, "Failed to get next node."); + + // @Id + hr = XmlGetAttributeEx(pixnNode, L"Id", &pSearch->sczId); + BextExitOnFailure(hr, "Failed to get @Id."); + + // Read type specific attributes. + if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, 0, bstrNodeName, -1, L"NetFxNetCoreSearch", -1)) + { + pSearch->Type = NETFX_SEARCH_TYPE_NET_CORE_SEARCH; + + // @RuntimeType + hr = XmlGetAttributeUInt32(pixnNode, L"RuntimeType", reinterpret_cast(&pSearch->NetCoreSearch.runtimeType)); + BextExitOnFailure(hr, "Failed to get @RuntimeType."); + + // @Platform + hr = XmlGetAttributeUInt32(pixnNode, L"Platform", reinterpret_cast(&pSearch->NetCoreSearch.platform)); + BextExitOnFailure(hr, "Failed to get @Platform."); + + // @MajorVersion + hr = XmlGetAttributeEx(pixnNode, L"MajorVersion", &pSearch->NetCoreSearch.sczMajorVersion); + BextExitOnFailure(hr, "Failed to get @MajorVersion."); + } + else + { + BextExitWithRootFailure(hr, E_UNEXPECTED, "Unexpected element name: %ls", bstrNodeName); + } + + // prepare next iteration + ReleaseNullObject(pixnNode); + ReleaseNullBSTR(bstrNodeName); + } + +LExit: + ReleaseBSTR(bstrNodeName); + ReleaseObject(pixnNode); + ReleaseObject(pixnNodes); + + return hr; +} + +void NetfxSearchUninitialize( + __in NETFX_SEARCHES* pSearches + ) +{ + if (pSearches->rgSearches) + { + for (DWORD i = 0; i < pSearches->cSearches; ++i) + { + NETFX_SEARCH* pSearch = &pSearches->rgSearches[i]; + + ReleaseStr(pSearch->sczId); + } + MemFree(pSearches->rgSearches); + } +} + +STDMETHODIMP NetfxSearchExecute( + __in NETFX_SEARCHES* pSearches, + __in LPCWSTR wzSearchId, + __in LPCWSTR wzVariable, + __in IBundleExtensionEngine* pEngine, + __in LPCWSTR wzBaseDirectory + ) +{ + HRESULT hr = S_OK; + NETFX_SEARCH* pSearch = NULL; + + hr = NetfxSearchFindById(pSearches, wzSearchId, &pSearch); + BextExitOnFailure(hr, "Search id '%ls' is unknown to the util extension.", wzSearchId); + + switch (pSearch->Type) + { + case NETFX_SEARCH_TYPE_NET_CORE_SEARCH: + hr = NetfxPerformDetectNetCore(wzVariable, pSearch, pEngine, wzBaseDirectory); + break; + default: + hr = E_UNEXPECTED; + } + +LExit: + return hr; +} + +STDMETHODIMP NetfxSearchFindById( + __in NETFX_SEARCHES* pSearches, + __in LPCWSTR wzId, + __out NETFX_SEARCH** ppSearch + ) +{ + HRESULT hr = S_OK; + + for (DWORD i = 0; i < pSearches->cSearches; ++i) + { + NETFX_SEARCH* pSearch = &pSearches->rgSearches[i]; + + if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, 0, pSearch->sczId, -1, wzId, -1)) + { + *ppSearch = pSearch; + ExitFunction1(hr = S_OK); + } + } + + hr = E_NOTFOUND; + +LExit: + return hr; +} diff --git a/src/ext/NetFx/be/netfxsearch.h b/src/ext/NetFx/be/netfxsearch.h new file mode 100644 index 00000000..ae250690 --- /dev/null +++ b/src/ext/NetFx/be/netfxsearch.h @@ -0,0 +1,76 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + + +// constants + +enum NETFX_SEARCH_TYPE +{ + NETFX_SEARCH_TYPE_NONE, + NETFX_SEARCH_TYPE_NET_CORE_SEARCH, +}; + +enum NETFX_NET_CORE_RUNTIME_TYPE +{ + NETFX_NET_CORE_RUNTIME_TYPE_CORE, + NETFX_NET_CORE_RUNTIME_TYPE_ASPNET, + NETFX_NET_CORE_RUNTIME_TYPE_DESKTOP, +}; + +enum NETFX_NET_CORE_PLATFORM +{ + NETFX_NET_CORE_PLATFORM_X86, + NETFX_NET_CORE_PLATFORM_X64, + NETFX_NET_CORE_PLATFORM_ARM64, +}; + + +// structs + +typedef struct _NETFX_SEARCH +{ + LPWSTR sczId; + + NETFX_SEARCH_TYPE Type; + union + { + struct + { + NETFX_NET_CORE_RUNTIME_TYPE runtimeType; + NETFX_NET_CORE_PLATFORM platform; + LPWSTR sczMajorVersion; + } NetCoreSearch; + }; +} NETFX_SEARCH; + +typedef struct _NETFX_SEARCHES +{ + NETFX_SEARCH* rgSearches; + DWORD cSearches; +} NETFX_SEARCHES; + + +// function declarations + +STDMETHODIMP NetfxSearchParseFromXml( + __in NETFX_SEARCHES* pSearches, + __in IXMLDOMNode* pixnBundleExtension + ); + +void NetfxSearchUninitialize( + __in NETFX_SEARCHES* pSearches + ); + +STDMETHODIMP NetfxSearchExecute( + __in NETFX_SEARCHES* pSearches, + __in LPCWSTR wzSearchId, + __in LPCWSTR wzVariable, + __in IBundleExtensionEngine* pEngine, + __in LPCWSTR wzBaseDirectory + ); + +STDMETHODIMP NetfxSearchFindById( + __in NETFX_SEARCHES* pSearches, + __in LPCWSTR wzId, + __out NETFX_SEARCH** ppSearch + ); diff --git a/src/ext/NetFx/be/precomp.cpp b/src/ext/NetFx/be/precomp.cpp new file mode 100644 index 00000000..37664a1c --- /dev/null +++ b/src/ext/NetFx/be/precomp.cpp @@ -0,0 +1,3 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" diff --git a/src/ext/NetFx/be/precomp.h b/src/ext/NetFx/be/precomp.h new file mode 100644 index 00000000..33aea9bc --- /dev/null +++ b/src/ext/NetFx/be/precomp.h @@ -0,0 +1,33 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + + +#include +#include +#include +#include + +#include + +#include + +#include +#include +#include +#include +#include +#include +#include + +#include +#include + +#include +#include +#include +#include + +#include "..\..\beDecor.h" +#include "netfxsearch.h" +#include "detectnetcore.h" +#include "NetfxBundleExtension.h" diff --git a/src/ext/NetFx/netcoresearch/netcoresearch.cpp b/src/ext/NetFx/netcoresearch/netcoresearch.cpp new file mode 100644 index 00000000..b2dad9a8 --- /dev/null +++ b/src/ext/NetFx/netcoresearch/netcoresearch.cpp @@ -0,0 +1,158 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" + +struct NETCORESEARCH_STATE +{ + LPCWSTR wzTargetName; + DWORD dwMajorVersion; + VERUTIL_VERSION* pVersion; +}; + +static HRESULT GetDotnetEnvironmentInfo( + __in DWORD dwMajorVersion, + __in_z LPCWSTR wzTargetName, + __inout VERUTIL_VERSION** ppVersion + ); +static void HOSTFXR_CALLTYPE GetDotnetEnvironmentInfoResult( + __in const hostfxr_dotnet_environment_info* pInfo, + __in LPVOID pvContext + ); + +int __cdecl wmain(int argc, LPWSTR argv[]) +{ + HRESULT hr = S_OK; + DWORD dwMajorVersion = 0; + VERUTIL_VERSION* pVersion = NULL; + LPSTR pszVersion = NULL; + + ::SetConsoleCP(CP_UTF8); + + ConsoleInitialize(); + + if (argc != 3) + { + ExitFunction1(hr = E_INVALIDARG); + } + + hr = StrStringToUInt32(argv[1], 0, reinterpret_cast(&dwMajorVersion)); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to get target version from: %ls", argv[1]); + + hr = GetDotnetEnvironmentInfo(dwMajorVersion, argv[2], &pVersion); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to search for .NET Core."); + + if (pVersion) + { + hr = StrAnsiAllocString(&pszVersion, pVersion->sczVersion, 0, CP_UTF8); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to convert version to UTF-8."); + + ConsoleWrite(CONSOLE_COLOR_NORMAL, "%hs", pszVersion); + } + +LExit: + ReleaseStr(pszVersion); + ReleaseVerutilVersion(pVersion); + ConsoleUninitialize(); + return hr; +} + +static HRESULT GetDotnetEnvironmentInfo( + __in DWORD dwMajorVersion, + __in_z LPCWSTR wzTargetName, + __inout VERUTIL_VERSION** ppVersion + ) +{ + HRESULT hr = S_OK; + LPWSTR sczProcessPath = NULL; + LPWSTR sczHostfxrPath = NULL; + HMODULE hModule = NULL; + hostfxr_get_dotnet_environment_info_fn pfnGetDotnetEnvironmentInfo = NULL; + NETCORESEARCH_STATE state = { }; + + state.dwMajorVersion = dwMajorVersion; + state.wzTargetName = wzTargetName; + + hr = PathForCurrentProcess(&sczProcessPath, NULL); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to get process path."); + + hr = PathGetDirectory(sczProcessPath, &sczHostfxrPath); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to get process directory."); + + hr = StrAllocConcat(&sczHostfxrPath, L"hostfxr.dll", 0); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to build hostfxr path."); + + hModule = ::LoadLibraryExW(sczHostfxrPath, NULL, LOAD_WITH_ALTERED_SEARCH_PATH); + ConsoleExitOnNullWithLastError(hModule, hr, CONSOLE_COLOR_RED, "Failed to load hostfxr."); + + pfnGetDotnetEnvironmentInfo = (hostfxr_get_dotnet_environment_info_fn)::GetProcAddress(hModule, "hostfxr_get_dotnet_environment_info"); + ConsoleExitOnNullWithLastError(pfnGetDotnetEnvironmentInfo, hr, CONSOLE_COLOR_RED, "Failed to get address for hostfxr_get_dotnet_environment_info."); + + hr = pfnGetDotnetEnvironmentInfo(NULL, NULL, GetDotnetEnvironmentInfoResult, &state); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to get .NET Core environment info."); + + if (state.pVersion) + { + *ppVersion = state.pVersion; + state.pVersion = NULL; + } + +LExit: + ReleaseVerutilVersion(state.pVersion); + ReleaseStr(sczHostfxrPath); + ReleaseStr(sczProcessPath); + + if (hModule) + { + ::FreeLibrary(hModule); + } + + return hr; +} + +static void HOSTFXR_CALLTYPE GetDotnetEnvironmentInfoResult( + __in const hostfxr_dotnet_environment_info* pInfo, + __in LPVOID pvContext + ) +{ + NETCORESEARCH_STATE* pState = reinterpret_cast(pvContext); + HRESULT hr = S_OK; + VERUTIL_VERSION* pFrameworkVersion = NULL; + int nCompare = 0; + + for (size_t i = 0; i < pInfo->framework_count; ++i) + { + const hostfxr_dotnet_environment_framework_info* pFrameworkInfo = pInfo->frameworks + i; + ReleaseVerutilVersion(pFrameworkVersion); + + if (CSTR_EQUAL != ::CompareStringW(LOCALE_INVARIANT, NORM_IGNORECASE, pState->wzTargetName, -1, pFrameworkInfo->name, -1)) + { + continue; + } + + hr = VerParseVersion(pFrameworkInfo->version, 0, FALSE, &pFrameworkVersion); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to parse framework version: %ls", pFrameworkInfo->version); + + if (pFrameworkVersion->dwMajor != pState->dwMajorVersion) + { + continue; + } + + if (pState->pVersion) + { + hr = VerCompareParsedVersions(pState->pVersion, pFrameworkVersion, &nCompare); + ConsoleExitOnFailure(hr, CONSOLE_COLOR_RED, "Failed to compare versions."); + + if (nCompare > -1) + { + continue; + } + } + + ReleaseVerutilVersion(pState->pVersion); + pState->pVersion = pFrameworkVersion; + pFrameworkVersion = NULL; + } + +LExit: + ReleaseVerutilVersion(pFrameworkVersion); +} diff --git a/src/ext/NetFx/netcoresearch/netcoresearch.h b/src/ext/NetFx/netcoresearch/netcoresearch.h new file mode 100644 index 00000000..d25b13f9 --- /dev/null +++ b/src/ext/NetFx/netcoresearch/netcoresearch.h @@ -0,0 +1,10 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +// TODO: remove when definition is provided in hostfxr.h. +typedef int32_t(HOSTFXR_CALLTYPE* hostfxr_get_dotnet_environment_info_fn)( + const char_t* dotnet_root, + void* reserved, + hostfxr_get_dotnet_environment_info_result_fn result, + void* result_context + ); diff --git a/src/ext/NetFx/netcoresearch/netcoresearch.vcxproj b/src/ext/NetFx/netcoresearch/netcoresearch.vcxproj new file mode 100644 index 00000000..b5f12f07 --- /dev/null +++ b/src/ext/NetFx/netcoresearch/netcoresearch.vcxproj @@ -0,0 +1,73 @@ + + + + + + Debug + ARM64 + + + Release + ARM64 + + + Debug + Win32 + + + Release + Win32 + + + Debug + x64 + + + Release + x64 + + + + + {A7FD9EF2-68CF-4C8E-AD81-3E8A6C7E1937} + Application + Unicode + Console + netcoresearch + + + + + + + $(Platform) + x86 + ..\..\..\..\packages\runtime.win-$(NetHostPlatform).Microsoft.NETCore.DotNetAppHost.6.0.4\runtimes\win-$(NetHostPlatform)\native\ + ..\..\..\..\packages\runtime.win-$(NetHostPlatform).Microsoft.NETCore.DotNetHostResolver.6.0.4\runtimes\win-$(NetHostPlatform)\native\ + $(NetHostPath) + + + + + + Create + + + + + + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/netcoresearch/packages.config b/src/ext/NetFx/netcoresearch/packages.config new file mode 100644 index 00000000..ad26db1c --- /dev/null +++ b/src/ext/NetFx/netcoresearch/packages.config @@ -0,0 +1,9 @@ + + + + + + + + + \ No newline at end of file diff --git a/src/ext/NetFx/netcoresearch/precomp.cpp b/src/ext/NetFx/netcoresearch/precomp.cpp new file mode 100644 index 00000000..37664a1c --- /dev/null +++ b/src/ext/NetFx/netcoresearch/precomp.cpp @@ -0,0 +1,3 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include "precomp.h" diff --git a/src/ext/NetFx/netcoresearch/precomp.h b/src/ext/NetFx/netcoresearch/precomp.h new file mode 100644 index 00000000..24023ec2 --- /dev/null +++ b/src/ext/NetFx/netcoresearch/precomp.h @@ -0,0 +1,18 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include + +#include "netcoresearch.h" diff --git a/src/ext/NetFx/netfx.cmd b/src/ext/NetFx/netfx.cmd index 182630b3..65cd1dcb 100644 --- a/src/ext/NetFx/netfx.cmd +++ b/src/ext/NetFx/netfx.cmd @@ -2,14 +2,19 @@ @pushd %~dp0 @set _C=Debug +@set _L=%~dp0..\..\..\build\logs :parse_args @if /i "%1"=="release" set _C=Release @if not "%1"=="" shift & goto parse_args @echo NetFx.wixext build %_C% +:: Restore +nuget restore netcoresearch\packages.config || exit /b +msbuild -t:Restore -p:Configuration=%_C% || exit /b + :: Build -msbuild -Restore -p:Configuration=%_C% || exit /b +msbuild -p:Configuration=%_C% -bl:%_L%\netfx_build.binlog || exit /b :: Test dotnet test -c %_C% --no-build test\WixToolsetTest.Netfx || exit /b diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/NetfxExtensionFixture.cs b/src/ext/NetFx/test/WixToolsetTest.Netfx/NetfxExtensionFixture.cs index 4b8b826e..8db3db46 100644 --- a/src/ext/NetFx/test/WixToolsetTest.Netfx/NetfxExtensionFixture.cs +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/NetfxExtensionFixture.cs @@ -25,6 +25,8 @@ namespace WixToolsetTest.Netfx { "build", Path.Combine(bundleSourceFolder, "BundleLatest.wxs"), + Path.Combine(bundleSourceFolder, "NetCore3.1.12_x86.wxs"), + Path.Combine(bundleSourceFolder, "NetCore3.1.12_x64.wxs"), "-ext", TestData.Get(@"WixToolset.Bal.wixext.dll"), "-ext", TestData.Get(@"WixToolset.Netfx.wixext.dll"), "-intermediateFolder", intermediateFolder, @@ -50,6 +52,7 @@ namespace WixToolsetTest.Netfx { "build", Path.Combine(bundleSourceFolder, "BundleLatest_x64.wxs"), + Path.Combine(bundleSourceFolder, "NetCore3.1.12_x64.wxs"), "-ext", TestData.Get(@"WixToolset.Bal.wixext.dll"), "-ext", TestData.Get(@"WixToolset.Netfx.wixext.dll"), "-intermediateFolder", intermediateFolder, diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest.wxs b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest.wxs index 8e3d2c30..b7b55747 100644 --- a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest.wxs +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest.wxs @@ -1,12 +1,15 @@ - + - - - + + + + + + diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest_x64.wxs b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest_x64.wxs index fc42ac99..3588686a 100644 --- a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest_x64.wxs +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/BundleLatest_x64.wxs @@ -1,12 +1,12 @@ - + - - - + + + diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x64.wxs b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x64.wxs new file mode 100644 index 00000000..20b266a5 --- /dev/null +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x64.wxs @@ -0,0 +1,58 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x86.wxs b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x86.wxs new file mode 100644 index 00000000..4bd97492 --- /dev/null +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3.1.12_x86.wxs @@ -0,0 +1,58 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3_Platform.wxi b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3_Platform.wxi new file mode 100644 index 00000000..f0b97d33 --- /dev/null +++ b/src/ext/NetFx/test/WixToolsetTest.Netfx/TestData/UsingDotNetCorePackages/NetCore3_Platform.wxi @@ -0,0 +1,49 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/wixext/NetFxCompiler.cs b/src/ext/NetFx/wixext/NetFxCompiler.cs index 90aa8bcb..739618e9 100644 --- a/src/ext/NetFx/wixext/NetFxCompiler.cs +++ b/src/ext/NetFx/wixext/NetFxCompiler.cs @@ -39,6 +39,19 @@ namespace WixToolset.Netfx this.ParseHelper.UnexpectedElement(parentElement, element); break; } + break; + case "Bundle": + case "Fragment": + switch (element.Name.LocalName) + { + case "DotNetCoreSearch": + this.ParseDotNetCoreSearchElement(intermediate, section, element); + break; + case "DotNetCoreSearchRef": + this.ParseDotNetCoreSearchRefElement(intermediate, section, element); + break; + } + break; default: this.ParseHelper.UnexpectedElement(parentElement, element); @@ -46,6 +59,159 @@ namespace WixToolset.Netfx } } + private void ParseDotNetCoreSearchElement(Intermediate intermediate, IntermediateSection section, XElement element) + { + var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(element); + Identifier id = null; + string variable = null; + string condition = null; + string after = null; + NetCoreSearchRuntimeType? runtimeType = null; + NetCoreSearchPlatform? platform = null; + var majorVersion = CompilerConstants.IntegerNotSet; + + foreach (var attrib in element.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + id = this.ParseHelper.GetAttributeIdentifier(sourceLineNumbers, attrib); + break; + case "Variable": + variable = this.ParseHelper.GetAttributeBundleVariableNameValue(sourceLineNumbers, attrib); + break; + case "Condition": + condition = this.ParseHelper.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "After": + after = this.ParseHelper.GetAttributeValue(sourceLineNumbers, attrib); + break; + case "RuntimeType": + var runtimeTypeValue = this.ParseHelper.GetAttributeValue(sourceLineNumbers, attrib); + switch (runtimeTypeValue) + { + case "aspnet": + runtimeType = NetCoreSearchRuntimeType.Aspnet; + break; + case "core": + runtimeType = NetCoreSearchRuntimeType.Core; + break; + case "desktop": + runtimeType = NetCoreSearchRuntimeType.Desktop; + break; + default: + this.Messaging.Write(ErrorMessages.IllegalAttributeValue(sourceLineNumbers, element.Name.LocalName, "RuntimeType", runtimeTypeValue, "aspnet", "core", "desktop")); + break; + } + break; + case "Platform": + var platformValue = this.ParseHelper.GetAttributeValue(sourceLineNumbers, attrib); + switch (platformValue) + { + case "arm64": + platform = NetCoreSearchPlatform.Arm64; + break; + case "x64": + platform = NetCoreSearchPlatform.X64; + break; + case "x86": + platform = NetCoreSearchPlatform.X86; + break; + default: + this.Messaging.Write(ErrorMessages.IllegalAttributeValue(sourceLineNumbers, element.Name.LocalName, "Platform", platformValue, "arm64", "x64", "x86")); + break; + } + break; + case "MajorVersion": + // .NET Core had a different deployment strategy before .NET Core 3.0 which would require different detection logic. + majorVersion = this.ParseHelper.GetAttributeIntegerValue(sourceLineNumbers, attrib, 3, Int32.MaxValue); + break; + default: + this.ParseHelper.UnexpectedAttribute(element, attrib); + break; + } + } + else + { + this.ParseHelper.ParseExtensionAttribute(this.Context.Extensions, intermediate, section, element, attrib); + } + } + + if (id == null) + { + id = this.ParseHelper.CreateIdentifier("dncs", variable, condition, after); + } + + if (!runtimeType.HasValue) + { + this.Messaging.Write(ErrorMessages.ExpectedAttribute(sourceLineNumbers, element.Name.LocalName, "RuntimeType")); + } + + if (!platform.HasValue) + { + this.Messaging.Write(ErrorMessages.ExpectedAttribute(sourceLineNumbers, element.Name.LocalName, "Platform")); + } + + if (majorVersion == CompilerConstants.IntegerNotSet) + { + this.Messaging.Write(ErrorMessages.ExpectedAttribute(sourceLineNumbers, element.Name.LocalName, "MajorVersion")); + } + else if (majorVersion == 4) + { + this.Messaging.Write(ErrorMessages.IllegalAttributeValue(sourceLineNumbers, element.Name.LocalName, "MajorVersion", "4", "3", "5+")); + } + + this.ParseHelper.ParseForExtensionElements(this.Context.Extensions, intermediate, section, element); + + var bundleExtensionId = this.ParseHelper.CreateIdentifierValueFromPlatform("Wix4NetfxBundleExtension", this.Context.Platform, BurnPlatforms.X86 | BurnPlatforms.X64 | BurnPlatforms.ARM64); + if (bundleExtensionId == null) + { + this.Messaging.Write(ErrorMessages.UnsupportedPlatformForElement(sourceLineNumbers, this.Context.Platform.ToString(), element.Name.LocalName)); + } + + if (!this.Messaging.EncounteredError) + { + this.ParseHelper.CreateWixSearchSymbol(section, sourceLineNumbers, element.Name.LocalName, id, variable, condition, after, bundleExtensionId); + + section.AddSymbol(new NetFxNetCoreSearchSymbol(sourceLineNumbers, id) + { + RuntimeType = runtimeType.Value, + Platform = platform.Value, + MajorVersion = majorVersion, + }); + } + } + + private void ParseDotNetCoreSearchRefElement(Intermediate intermediate, IntermediateSection section, XElement element) + { + var sourceLineNumbers = this.ParseHelper.GetSourceLineNumbers(element); + + foreach (var attrib in element.Attributes()) + { + if (String.IsNullOrEmpty(attrib.Name.NamespaceName) || this.Namespace == attrib.Name.Namespace) + { + switch (attrib.Name.LocalName) + { + case "Id": + var refId = this.ParseHelper.GetAttributeIdentifierValue(sourceLineNumbers, attrib); + this.ParseHelper.CreateSimpleReference(section, sourceLineNumbers, NetfxSymbolDefinitions.NetFxNetCoreSearch, refId); + break; + default: + this.ParseHelper.UnexpectedAttribute(element, attrib); + break; + } + } + else + { + this.ParseHelper.ParseExtensionAttribute(this.Context.Extensions, intermediate, section, element, attrib); + } + } + + this.ParseHelper.ParseForExtensionElements(this.Context.Extensions, intermediate, section, element); + } + /// /// Parses a NativeImage element. /// diff --git a/src/ext/NetFx/wixext/NetFxExtensionData.cs b/src/ext/NetFx/wixext/NetFxExtensionData.cs index 0a24ef1e..61d618cf 100644 --- a/src/ext/NetFx/wixext/NetFxExtensionData.cs +++ b/src/ext/NetFx/wixext/NetFxExtensionData.cs @@ -4,7 +4,6 @@ namespace WixToolset.Netfx { using WixToolset.Data; using WixToolset.Extensibility; - using WixToolset.Netfx.Symbols; /// /// The WiX Toolset .NET Framework Extension. @@ -13,7 +12,7 @@ namespace WixToolset.Netfx { public override bool TryGetSymbolDefinitionByName(string name, out IntermediateSymbolDefinition symbolDefinition) { - symbolDefinition = (name == NetfxSymbolDefinitionNames.NetFxNativeImage) ? NetfxSymbolDefinitions.NetFxNativeImage : null; + symbolDefinition = NetfxSymbolDefinitions.ByName(name); return symbolDefinition != null; } diff --git a/src/ext/NetFx/wixext/Symbols/NetFxNativeImageSymbol.cs b/src/ext/NetFx/wixext/Symbols/NetFxNativeImageSymbol.cs index 3803abd6..252c6aba 100644 --- a/src/ext/NetFx/wixext/Symbols/NetFxNativeImageSymbol.cs +++ b/src/ext/NetFx/wixext/Symbols/NetFxNativeImageSymbol.cs @@ -1,5 +1,26 @@ // Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. +namespace WixToolset.Netfx +{ + using WixToolset.Data; + using WixToolset.Netfx.Symbols; + + public static partial class NetfxSymbolDefinitions + { + public static readonly IntermediateSymbolDefinition NetFxNativeImage = new IntermediateSymbolDefinition( + NetfxSymbolDefinitionType.NetFxNativeImage.ToString(), + new[] + { + new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.FileRef), IntermediateFieldType.String), + new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.Priority), IntermediateFieldType.Number), + new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.Attributes), IntermediateFieldType.Number), + new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.ApplicationFileRef), IntermediateFieldType.String), + new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.ApplicationBaseDirectoryRef), IntermediateFieldType.String), + }, + typeof(NetFxNativeImageSymbol)); + } +} + namespace WixToolset.Netfx.Symbols { using WixToolset.Data; @@ -55,4 +76,4 @@ namespace WixToolset.Netfx.Symbols set => this.Set((int)NetFxNativeImageSymbolFields.ApplicationBaseDirectoryRef, value); } } -} \ No newline at end of file +} diff --git a/src/ext/NetFx/wixext/Symbols/NetFxNetCoreSearchSymbol.cs b/src/ext/NetFx/wixext/Symbols/NetFxNetCoreSearchSymbol.cs new file mode 100644 index 00000000..8bf0a24c --- /dev/null +++ b/src/ext/NetFx/wixext/Symbols/NetFxNetCoreSearchSymbol.cs @@ -0,0 +1,77 @@ +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + +namespace WixToolset.Netfx +{ + using WixToolset.Data; + using WixToolset.Netfx.Symbols; + + public static partial class NetfxSymbolDefinitions + { + public static readonly IntermediateSymbolDefinition NetFxNetCoreSearch = new IntermediateSymbolDefinition( + NetfxSymbolDefinitionType.NetFxNetCoreSearch.ToString(), + new[] + { + new IntermediateFieldDefinition(nameof(NetFxNetCoreSearchSymbolFields.RuntimeType), IntermediateFieldType.Number), + new IntermediateFieldDefinition(nameof(NetFxNetCoreSearchSymbolFields.Platform), IntermediateFieldType.Number), + new IntermediateFieldDefinition(nameof(NetFxNetCoreSearchSymbolFields.MajorVersion), IntermediateFieldType.Number), + }, + typeof(NetFxNetCoreSearchSymbol)); + } +} + +namespace WixToolset.Netfx.Symbols +{ + using WixToolset.Data; + + public enum NetCoreSearchRuntimeType + { + Core, + Aspnet, + Desktop, + } + + public enum NetCoreSearchPlatform + { + X86, + X64, + Arm64, + } + + public enum NetFxNetCoreSearchSymbolFields + { + RuntimeType, + Platform, + MajorVersion, + } + + public class NetFxNetCoreSearchSymbol : IntermediateSymbol + { + public NetFxNetCoreSearchSymbol() : base(NetfxSymbolDefinitions.NetFxNetCoreSearch, null, null) + { + } + + public NetFxNetCoreSearchSymbol(SourceLineNumber sourceLineNumber, Identifier id = null) : base(NetfxSymbolDefinitions.NetFxNetCoreSearch, sourceLineNumber, id) + { + } + + public IntermediateField this[NetFxNetCoreSearchSymbolFields index] => this.Fields[(int)index]; + + public NetCoreSearchRuntimeType RuntimeType + { + get => (NetCoreSearchRuntimeType)this.Fields[(int)NetFxNetCoreSearchSymbolFields.RuntimeType].AsNumber(); + set => this.Set((int)NetFxNetCoreSearchSymbolFields.RuntimeType, (int)value); + } + + public NetCoreSearchPlatform Platform + { + get => (NetCoreSearchPlatform)this.Fields[(int)NetFxNetCoreSearchSymbolFields.Platform].AsNumber(); + set => this.Set((int)NetFxNetCoreSearchSymbolFields.Platform, (int)value); + } + + public int MajorVersion + { + get => this.Fields[(int)NetFxNetCoreSearchSymbolFields.MajorVersion].AsNumber(); + set => this.Set((int)NetFxNetCoreSearchSymbolFields.MajorVersion, value); + } + } +} diff --git a/src/ext/NetFx/wixext/Symbols/NetfxSymbolDefinitions.cs b/src/ext/NetFx/wixext/Symbols/NetfxSymbolDefinitions.cs index 3c0f1176..862eba16 100644 --- a/src/ext/NetFx/wixext/Symbols/NetfxSymbolDefinitions.cs +++ b/src/ext/NetFx/wixext/Symbols/NetfxSymbolDefinitions.cs @@ -1,26 +1,47 @@ // Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. -namespace WixToolset.Netfx.Symbols +namespace WixToolset.Netfx { + using System; using WixToolset.Data; + using WixToolset.Data.Burn; - public static class NetfxSymbolDefinitionNames + public enum NetfxSymbolDefinitionType { - public static string NetFxNativeImage { get; } = "NetFxNativeImage"; + NetFxNativeImage, + NetFxNetCoreSearch, } - public static class NetfxSymbolDefinitions + public static partial class NetfxSymbolDefinitions { - public static readonly IntermediateSymbolDefinition NetFxNativeImage = new IntermediateSymbolDefinition( - NetfxSymbolDefinitionNames.NetFxNativeImage, - new[] + public static IntermediateSymbolDefinition ByName(string name) + { + if (!Enum.TryParse(name, out NetfxSymbolDefinitionType type)) { - new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.FileRef), IntermediateFieldType.String), - new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.Priority), IntermediateFieldType.Number), - new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.Attributes), IntermediateFieldType.Number), - new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.ApplicationFileRef), IntermediateFieldType.String), - new IntermediateFieldDefinition(nameof(NetFxNativeImageSymbolFields.ApplicationBaseDirectoryRef), IntermediateFieldType.String), - }, - typeof(NetFxNativeImageSymbol)); + return null; + } + + return ByType(type); + } + + public static IntermediateSymbolDefinition ByType(NetfxSymbolDefinitionType type) + { + switch (type) + { + case NetfxSymbolDefinitionType.NetFxNativeImage: + return NetfxSymbolDefinitions.NetFxNativeImage; + + case NetfxSymbolDefinitionType.NetFxNetCoreSearch: + return NetfxSymbolDefinitions.NetFxNetCoreSearch; + + default: + throw new ArgumentOutOfRangeException(nameof(type)); + } + } + + static NetfxSymbolDefinitions() + { + NetFxNetCoreSearch.AddTag(BurnConstants.BundleExtensionSearchSymbolDefinitionTag); + } } } diff --git a/src/ext/NetFx/wixlib/NetCore3.1.12_x64.wxs b/src/ext/NetFx/wixlib/NetCore3.1.12_x64.wxs deleted file mode 100644 index 3a1f5910..00000000 --- a/src/ext/NetFx/wixlib/NetCore3.1.12_x64.wxs +++ /dev/null @@ -1,58 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/ext/NetFx/wixlib/NetCore3.1.12_x86.wxs b/src/ext/NetFx/wixlib/NetCore3.1.12_x86.wxs deleted file mode 100644 index e3a70daf..00000000 --- a/src/ext/NetFx/wixlib/NetCore3.1.12_x86.wxs +++ /dev/null @@ -1,58 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/ext/NetFx/wixlib/NetCore3.1_x64.wxs b/src/ext/NetFx/wixlib/NetCore3.1_x64.wxs deleted file mode 100644 index 60d7c27f..00000000 --- a/src/ext/NetFx/wixlib/NetCore3.1_x64.wxs +++ /dev/null @@ -1,22 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/ext/NetFx/wixlib/NetCore3.1_x86.wxs b/src/ext/NetFx/wixlib/NetCore3.1_x86.wxs deleted file mode 100644 index cfff07b3..00000000 --- a/src/ext/NetFx/wixlib/NetCore3.1_x86.wxs +++ /dev/null @@ -1,22 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/ext/NetFx/wixlib/NetCore3_Platform.wxi b/src/ext/NetFx/wixlib/NetCore3_Platform.wxi deleted file mode 100644 index 88e672be..00000000 --- a/src/ext/NetFx/wixlib/NetCore3_Platform.wxi +++ /dev/null @@ -1,65 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/ext/NetFx/wixlib/NetCoreShared.wxs b/src/ext/NetFx/wixlib/NetCoreShared.wxs index 2045a5b9..51667117 100644 --- a/src/ext/NetFx/wixlib/NetCoreShared.wxs +++ b/src/ext/NetFx/wixlib/NetCoreShared.wxs @@ -1,8 +1,8 @@ - + - + diff --git a/src/ext/NetFx/wixlib/NetfxBundleExtension_Platform.wxi b/src/ext/NetFx/wixlib/NetfxBundleExtension_Platform.wxi new file mode 100644 index 00000000..e3300534 --- /dev/null +++ b/src/ext/NetFx/wixlib/NetfxBundleExtension_Platform.wxi @@ -0,0 +1,15 @@ + + + + + + + + + + + + + + + diff --git a/src/ext/NetFx/wixlib/NetfxBundleExtension_arm64.wxs b/src/ext/NetFx/wixlib/NetfxBundleExtension_arm64.wxs new file mode 100644 index 00000000..13757dd8 --- /dev/null +++ b/src/ext/NetFx/wixlib/NetfxBundleExtension_arm64.wxs @@ -0,0 +1,7 @@ + + + + + + + diff --git a/src/ext/NetFx/wixlib/NetfxBundleExtension_x64.wxs b/src/ext/NetFx/wixlib/NetfxBundleExtension_x64.wxs new file mode 100644 index 00000000..f6c27a8e --- /dev/null +++ b/src/ext/NetFx/wixlib/NetfxBundleExtension_x64.wxs @@ -0,0 +1,7 @@ + + + + + + + diff --git a/src/ext/NetFx/wixlib/NetfxBundleExtension_x86.wxs b/src/ext/NetFx/wixlib/NetfxBundleExtension_x86.wxs new file mode 100644 index 00000000..76a8358f --- /dev/null +++ b/src/ext/NetFx/wixlib/NetfxBundleExtension_x86.wxs @@ -0,0 +1,7 @@ + + + + + + + diff --git a/src/ext/NetFx/wixlib/netfx.wixproj b/src/ext/NetFx/wixlib/netfx.wixproj index ad7d028c..bc6a1172 100644 --- a/src/ext/NetFx/wixlib/netfx.wixproj +++ b/src/ext/NetFx/wixlib/netfx.wixproj @@ -14,9 +14,15 @@ - - - + + + + + + + + + diff --git a/src/ext/Util/be/UtilBundleExtension.cpp b/src/ext/Util/be/UtilBundleExtension.cpp index 110599fa..23f5d94f 100644 --- a/src/ext/Util/be/UtilBundleExtension.cpp +++ b/src/ext/Util/be/UtilBundleExtension.cpp @@ -28,16 +28,16 @@ public: //CBextBaseBundleExtension IXMLDOMNode* pixnBundleExtension = NULL; hr = __super::Initialize(pCreateArgs); - ExitOnFailure(hr, "CBextBaseBundleExtension initialization failed."); + BextExitOnFailure(hr, "CBextBaseBundleExtension initialization failed."); hr = XmlLoadDocumentFromFile(m_sczBundleExtensionDataPath, &pixdManifest); - ExitOnFailure(hr, "Failed to load bundle extension manifest from path: %ls", m_sczBundleExtensionDataPath); + BextExitOnFailure(hr, "Failed to load bundle extension manifest from path: %ls", m_sczBundleExtensionDataPath); hr = BextGetBundleExtensionDataNode(pixdManifest, UTIL_BUNDLE_EXTENSION_ID, &pixnBundleExtension); - ExitOnFailure(hr, "Failed to get BundleExtension '%ls'", UTIL_BUNDLE_EXTENSION_ID); + BextExitOnFailure(hr, "Failed to get BundleExtension '%ls'", UTIL_BUNDLE_EXTENSION_ID); hr = UtilSearchParseFromXml(&m_searches, pixnBundleExtension); - ExitOnFailure(hr, "Failed to parse searches from bundle extension manifest."); + BextExitOnFailure(hr, "Failed to parse searches from bundle extension manifest."); LExit: ReleaseObject(pixnBundleExtension); @@ -73,10 +73,10 @@ HRESULT UtilBundleExtensionCreate( CWixUtilBundleExtension* pExtension = NULL; pExtension = new CWixUtilBundleExtension(pEngine); - ExitOnNull(pExtension, hr, E_OUTOFMEMORY, "Failed to create new CWixUtilBundleExtension."); + BextExitOnNull(pExtension, hr, E_OUTOFMEMORY, "Failed to create new CWixUtilBundleExtension."); hr = pExtension->Initialize(pArgs); - ExitOnFailure(hr, "CWixUtilBundleExtension initialization failed."); + BextExitOnFailure(hr, "CWixUtilBundleExtension initialization failed."); *ppBundleExtension = pExtension; pExtension = NULL; diff --git a/src/ext/Util/be/beDecor.h b/src/ext/Util/be/beDecor.h deleted file mode 100644 index 2c6a8818..00000000 --- a/src/ext/Util/be/beDecor.h +++ /dev/null @@ -1,13 +0,0 @@ -#pragma once -// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. - - -#if defined(_M_ARM64) -#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_A64" -#elif defined(_M_AMD64) -#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_X64" -#elif defined(_M_ARM) -#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_ARM" -#else -#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_X86" -#endif diff --git a/src/ext/Util/be/detectsha2support.cpp b/src/ext/Util/be/detectsha2support.cpp index 90e349cd..4abfc63c 100644 --- a/src/ext/Util/be/detectsha2support.cpp +++ b/src/ext/Util/be/detectsha2support.cpp @@ -13,7 +13,7 @@ HRESULT DetectSHA2CodeSigning( DWORD er = ERROR_SUCCESS; hr = LoadSystemLibrary(L"wintrust.dll", &hModule); - ExitOnFailure(hr, "Failed to load wintrust.dll"); + BextExitOnFailure(hr, "Failed to load wintrust.dll"); pfn = ::GetProcAddress(hModule, "CryptCATAdminAcquireContext2"); if (pfn) @@ -30,7 +30,7 @@ HRESULT DetectSHA2CodeSigning( } hr = HRESULT_FROM_WIN32(er); - ExitOnFailure(hr, "Failed to probe for CryptCATAdminAcquireContext2 in wintrust.dll"); + BextExitOnFailure(hr, "Failed to probe for CryptCATAdminAcquireContext2 in wintrust.dll"); LExit: ::FreeLibrary(hModule); @@ -48,10 +48,10 @@ HRESULT UtilPerformDetectSHA2CodeSigning( BOOL fSupported = FALSE; hr = DetectSHA2CodeSigning(&fSupported); - ExitOnFailure(hr, "DetectSHA2CodeSigning failed."); + BextExitOnFailure(hr, "DetectSHA2CodeSigning failed."); hr = pEngine->SetVariableNumeric(wzVariable, fSupported ? 1 : 0); - ExitOnFailure(hr, "Failed to set variable '%ls'", wzVariable); + BextExitOnFailure(hr, "Failed to set variable '%ls'", wzVariable); LExit: return hr; diff --git a/src/ext/Util/be/precomp.h b/src/ext/Util/be/precomp.h index bb36b3f3..5ce5744f 100644 --- a/src/ext/Util/be/precomp.h +++ b/src/ext/Util/be/precomp.h @@ -31,7 +31,7 @@ #include #include -#include "beDecor.h" +#include "..\..\beDecor.h" #include "utilsearch.h" #include "detectsha2support.h" #include "UtilBundleExtension.h" diff --git a/src/ext/Util/be/utilbe.vcxproj b/src/ext/Util/be/utilbe.vcxproj index 4e4f80d9..fa39dcf3 100644 --- a/src/ext/Util/be/utilbe.vcxproj +++ b/src/ext/Util/be/utilbe.vcxproj @@ -56,7 +56,6 @@ - diff --git a/src/ext/Util/be/utilsearch.cpp b/src/ext/Util/be/utilsearch.cpp index 7cd2ea09..20a514d8 100644 --- a/src/ext/Util/be/utilsearch.cpp +++ b/src/ext/Util/be/utilsearch.cpp @@ -17,11 +17,11 @@ STDMETHODIMP UtilSearchParseFromXml( // Select Util search nodes. hr = XmlSelectNodes(pixnBundleExtension, L"WixWindowsFeatureSearch", &pixnNodes); - ExitOnFailure(hr, "Failed to select Util search nodes."); + BextExitOnFailure(hr, "Failed to select Util search nodes."); // Get Util search node count. hr = pixnNodes->get_length((long*)&cNodes); - ExitOnFailure(hr, "Failed to get Util search node count."); + BextExitOnFailure(hr, "Failed to get Util search node count."); if (!cNodes) { @@ -30,7 +30,7 @@ STDMETHODIMP UtilSearchParseFromXml( // Allocate memory for searches. pSearches->rgSearches = (UTIL_SEARCH*)MemAlloc(sizeof(UTIL_SEARCH) * cNodes, TRUE); - ExitOnNull(pSearches->rgSearches, hr, E_OUTOFMEMORY, "Failed to allocate memory for search structs."); + BextExitOnNull(pSearches->rgSearches, hr, E_OUTOFMEMORY, "Failed to allocate memory for search structs."); pSearches->cSearches = cNodes; @@ -40,11 +40,11 @@ STDMETHODIMP UtilSearchParseFromXml( UTIL_SEARCH* pSearch = &pSearches->rgSearches[i]; hr = XmlNextElement(pixnNodes, &pixnNode, &bstrNodeName); - ExitOnFailure(hr, "Failed to get next node."); + BextExitOnFailure(hr, "Failed to get next node."); // @Id hr = XmlGetAttributeEx(pixnNode, L"Id", &pSearch->sczId); - ExitOnFailure(hr, "Failed to get @Id."); + BextExitOnFailure(hr, "Failed to get @Id."); // Read type specific attributes. if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, 0, bstrNodeName, -1, L"WixWindowsFeatureSearch", -1)) @@ -53,7 +53,7 @@ STDMETHODIMP UtilSearchParseFromXml( // @Type hr = XmlGetAttributeEx(pixnNode, L"Type", &scz); - ExitOnFailure(hr, "Failed to get @Type."); + BextExitOnFailure(hr, "Failed to get @Type."); if (CSTR_EQUAL == ::CompareStringW(LOCALE_INVARIANT, 0, scz, -1, L"sha2CodeSigning", -1)) { @@ -61,14 +61,12 @@ STDMETHODIMP UtilSearchParseFromXml( } else { - hr = E_INVALIDARG; - ExitOnFailure(hr, "Invalid value for @Type: %ls", scz); + BextExitWithRootFailure(hr, E_INVALIDARG, "Invalid value for @Type: %ls", scz); } } else { - hr = E_UNEXPECTED; - ExitOnFailure(hr, "Unexpected element name: %ls", bstrNodeName); + BextExitWithRootFailure(hr, E_UNEXPECTED, "Unexpected element name: %ls", bstrNodeName); } // prepare next iteration @@ -112,7 +110,7 @@ STDMETHODIMP UtilSearchExecute( UTIL_SEARCH* pSearch = NULL; hr = UtilSearchFindById(pSearches, wzSearchId, &pSearch); - ExitOnFailure(hr, "Search id '%ls' is unknown to the util extension."); + BextExitOnFailure(hr, "Search id '%ls' is unknown to the util extension.", wzSearchId); switch (pSearch->Type) { diff --git a/src/ext/Util/wixext/Symbols/UtilSymbolDefinitions.cs b/src/ext/Util/wixext/Symbols/UtilSymbolDefinitions.cs index 72091c3b..3b357a96 100644 --- a/src/ext/Util/wixext/Symbols/UtilSymbolDefinitions.cs +++ b/src/ext/Util/wixext/Symbols/UtilSymbolDefinitions.cs @@ -33,8 +33,6 @@ namespace WixToolset.Util public static partial class UtilSymbolDefinitions { - public static readonly Version Version = new Version("4.0.0"); - public static IntermediateSymbolDefinition ByName(string name) { if (!Enum.TryParse(name, out UtilSymbolDefinitionType type)) diff --git a/src/ext/beDecor.h b/src/ext/beDecor.h new file mode 100644 index 00000000..2c6a8818 --- /dev/null +++ b/src/ext/beDecor.h @@ -0,0 +1,13 @@ +#pragma once +// Copyright (c) .NET Foundation and contributors. All rights reserved. Licensed under the Microsoft Reciprocal License. See LICENSE.TXT file in the project root for full license information. + + +#if defined(_M_ARM64) +#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_A64" +#elif defined(_M_AMD64) +#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_X64" +#elif defined(_M_ARM) +#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_ARM" +#else +#define BUNDLE_EXTENSION_DECORATION(f) L"Wix4" f L"_X86" +#endif diff --git a/src/libs/dutil/WixToolset.DUtil/inc/procutil.h b/src/libs/dutil/WixToolset.DUtil/inc/procutil.h index 6a641a5b..e7e91705 100644 --- a/src/libs/dutil/WixToolset.DUtil/inc/procutil.h +++ b/src/libs/dutil/WixToolset.DUtil/inc/procutil.h @@ -62,6 +62,7 @@ HRESULT DAPI ProcExec( __out HANDLE *phProcess ); HRESULT DAPI ProcExecute( + __in_z_opt LPCWSTR wzApplicationName, __in_z LPWSTR wzCommand, __out HANDLE *phProcess, __out_opt HANDLE *phChildStdIn, @@ -73,7 +74,7 @@ HRESULT DAPI ProcWaitForCompletion( __out_opt DWORD* pdwReturnCode ); HRESULT DAPI ProcWaitForIds( - __in_ecount(cProcessIds) const DWORD* pdwProcessIds, + __in_ecount(cProcessIds) const DWORD rgdwProcessIds[], __in DWORD cProcessIds, __in DWORD dwMilliseconds ); diff --git a/src/libs/dutil/WixToolset.DUtil/procutil.cpp b/src/libs/dutil/WixToolset.DUtil/procutil.cpp index 376aec6d..f96a1999 100644 --- a/src/libs/dutil/WixToolset.DUtil/procutil.cpp +++ b/src/libs/dutil/WixToolset.DUtil/procutil.cpp @@ -375,6 +375,7 @@ LExit: *******************************************************************/ extern "C" HRESULT DAPI ProcExecute( + __in_z_opt LPCWSTR wzApplicationName, __in_z LPWSTR wzCommand, __out HANDLE *phProcess, __out_opt HANDLE *phChildStdIn, @@ -405,7 +406,7 @@ extern "C" HRESULT DAPI ProcExecute( #pragma prefast(push) #pragma prefast(disable:25028) - if (::CreateProcessW(NULL, + if (::CreateProcessW(wzApplicationName, wzCommand, // command line NULL, // security info NULL, // thread info diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6.0.9_x86.wxs b/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6.0.9_x86.wxs new file mode 100644 index 00000000..6bfef872 --- /dev/null +++ b/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6.0.9_x86.wxs @@ -0,0 +1,58 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6_Platform.wxi b/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6_Platform.wxi new file mode 100644 index 00000000..d508bcaf --- /dev/null +++ b/src/test/burn/TestData/TestBA/TestBAWixlib/NetCore6_Platform.wxi @@ -0,0 +1,49 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib/TestBA.wxs b/src/test/burn/TestData/TestBA/TestBAWixlib/TestBA.wxs index ae162050..2db22e4b 100644 --- a/src/test/burn/TestData/TestBA/TestBAWixlib/TestBA.wxs +++ b/src/test/burn/TestData/TestBA/TestBAWixlib/TestBA.wxs @@ -11,7 +11,7 @@ - + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib/testbawixlib.wixproj b/src/test/burn/TestData/TestBA/TestBAWixlib/testbawixlib.wixproj index 1dbc4f63..6ef417d0 100644 --- a/src/test/burn/TestData/TestBA/TestBAWixlib/testbawixlib.wixproj +++ b/src/test/burn/TestData/TestBA/TestBAWixlib/testbawixlib.wixproj @@ -17,5 +17,6 @@ + \ No newline at end of file diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/NetCore6.0.9_x64.wxs b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/NetCore6.0.9_x64.wxs new file mode 100644 index 00000000..f2345693 --- /dev/null +++ b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/NetCore6.0.9_x64.wxs @@ -0,0 +1,58 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/TestBA_x64.wxs b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/TestBA_x64.wxs index df058958..f6a6382b 100644 --- a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/TestBA_x64.wxs +++ b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/TestBA_x64.wxs @@ -11,7 +11,7 @@ - + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/WixBA_x64.wxs b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/WixBA_x64.wxs index bc5d4080..6cfbc937 100644 --- a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/WixBA_x64.wxs +++ b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/WixBA_x64.wxs @@ -12,7 +12,7 @@ - + diff --git a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/testbawixlib_x64.wixproj b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/testbawixlib_x64.wixproj index 3d714c4e..13f66a86 100644 --- a/src/test/burn/TestData/TestBA/TestBAWixlib_x64/testbawixlib_x64.wixproj +++ b/src/test/burn/TestData/TestBA/TestBAWixlib_x64/testbawixlib_x64.wixproj @@ -29,5 +29,6 @@ + \ No newline at end of file -- cgit v1.2.3-55-g6feb