Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix DevSetupAgent logging and some other fixes. #2566

Merged
merged 3 commits into from
Apr 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions HyperVExtension/src/DevSetupAgent/Logging.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

using Windows.Storage;

namespace HyperVExtension.DevSetupAgent;

public class Logging
{
public static readonly string LogExtension = ".dhlog";

public static readonly string LogFolderName = "Logs";

public static readonly string AppName = "DevSetupAgent";

public static readonly string DefaultLogFileName = "hyperv_setup";

private static readonly Lazy<string> _logFolderRoot = new(() => Path.Combine(Path.GetTempPath(), AppName, LogFolderName));

public static readonly string LogFolderRoot = _logFolderRoot.Value;
}
6 changes: 6 additions & 0 deletions HyperVExtension/src/DevSetupAgent/NativeMethods.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,14 @@ CLSCTX
WIN32_ERROR
S_OK
E_FAIL
E_UNEXPECTED
LsaEnumerateLogonSessions
LsaGetLogonSessionData
Windows.Win32.Security.Authentication.Identity.LsaFreeReturnBuffer
SECURITY_LOGON_TYPE
STATUS_SUCCESS
MakeAbsoluteSD
ConvertStringSecurityDescriptorToSecurityDescriptor
LocalAlloc
LocalFree
SDDL_REVISION_1
108 changes: 88 additions & 20 deletions HyperVExtension/src/DevSetupAgent/Program.cs
Original file line number Diff line number Diff line change
@@ -1,41 +1,109 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

using System.ComponentModel;
using System.Runtime.InteropServices;
using HyperVExtension.DevSetupAgent;
using HyperVExtension.HostGuestCommunication;
using Serilog;
using Windows.Win32;
using Windows.Win32.Foundation;
using Windows.Win32.Security;
using Windows.Win32.System.Com;

unsafe
{
// TODO: Set real security descriptor to allow access from System+Admns+Interactive Users
var hr = PInvoke.CoInitializeSecurity(
new(null),
-1,
null,
null,
RPC_C_AUTHN_LEVEL.RPC_C_AUTHN_LEVEL_DEFAULT,
RPC_C_IMP_LEVEL.RPC_C_IMP_LEVEL_IDENTIFY,
null,
EOLE_AUTHENTICATION_CAPABILITIES.EOAC_NONE);

if (hr < 0)
{
Marshal.ThrowExceptionForHR(hr);
}
}

// Set up Logging
Environment.SetEnvironmentVariable("DEVHOME_LOGS_ROOT", Path.Join(HyperVExtension.DevSetupEngine.Logging.LogFolderRoot, "HyperV"));
Environment.SetEnvironmentVariable("DEVHOME_LOGS_ROOT", Path.Join(Logging.LogFolderRoot, "HyperV"));
var configuration = new ConfigurationBuilder()
.AddJsonFile("appsettings_hypervsetupagent.json")
.Build();
Log.Logger = new LoggerConfiguration()
.ReadFrom.Configuration(configuration)
.CreateLogger();

unsafe
{
PSECURITY_DESCRIPTOR absolutSd = new(null);
PSID ownerSid = new(null);
PSID groupSid = new(null);
ACL* dacl = default;
ACL* sacl = default;

try
{
// O:PSG:BU Owner Principal Self, Group Built-in Users
// (A;;0x3;;;SY) Allow Local System
// (A;;0x3;;;IU) Allow Interactive User
var accessPermission = "O:PSG:BUD:(A;;0x3;;;SY)(A;;0x3;;;IU)";
uint securityDescriptorSize;
PInvoke.ConvertStringSecurityDescriptorToSecurityDescriptor(accessPermission, PInvoke.SDDL_REVISION_1, out var securityDescriptor, &securityDescriptorSize);

uint absoluteSdSize = default;
uint daclSize = default;
uint saclSize = default;
uint ownerSize = default;
uint groupSize = default;

if (PInvoke.MakeAbsoluteSD(securityDescriptor, absolutSd, ref absoluteSdSize, null, ref daclSize, null, ref saclSize, ownerSid, ref ownerSize, groupSid, ref groupSize))
{
throw new HResultException(HRESULT.E_UNEXPECTED);
Copy link
Contributor

@huzaifa-d huzaifa-d Apr 9, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggestion: Add a brief message describing the error and where it failed.

}

var error = Marshal.GetLastWin32Error();
if (error != (int)WIN32_ERROR.ERROR_INSUFFICIENT_BUFFER)
{
throw new Win32Exception(error);
}

absolutSd = new(PInvoke.LocalAlloc(Windows.Win32.System.Memory.LOCAL_ALLOC_FLAGS.LPTR, absoluteSdSize));
dacl = (ACL*)PInvoke.LocalAlloc(Windows.Win32.System.Memory.LOCAL_ALLOC_FLAGS.LPTR, daclSize);
sacl = (ACL*)PInvoke.LocalAlloc(Windows.Win32.System.Memory.LOCAL_ALLOC_FLAGS.LPTR, saclSize);
ownerSid = new(PInvoke.LocalAlloc(Windows.Win32.System.Memory.LOCAL_ALLOC_FLAGS.LPTR, ownerSize));
groupSid = new(PInvoke.LocalAlloc(Windows.Win32.System.Memory.LOCAL_ALLOC_FLAGS.LPTR, groupSize));

if (!PInvoke.MakeAbsoluteSD(securityDescriptor, absolutSd, ref absoluteSdSize, dacl, ref daclSize, sacl, ref saclSize, ownerSid, ref ownerSize, groupSid, ref groupSize))
{
throw new HResultException(Marshal.GetLastWin32Error());
}

var hr = PInvoke.CoInitializeSecurity(
absolutSd,
-1,
null,
null,
RPC_C_AUTHN_LEVEL.RPC_C_AUTHN_LEVEL_DEFAULT,
RPC_C_IMP_LEVEL.RPC_C_IMP_LEVEL_IDENTIFY,
null,
EOLE_AUTHENTICATION_CAPABILITIES.EOAC_NONE);

if (hr < 0)
{
Marshal.ThrowExceptionForHR(hr);
}
}
finally
{
if (sacl != default)
{
PInvoke.LocalFree((HLOCAL)sacl);
}

if (dacl != default)
{
PInvoke.LocalFree((HLOCAL)dacl);
}

if (groupSid != default)
{
PInvoke.LocalFree((HLOCAL)groupSid.Value);
}

if (ownerSid != default)
{
PInvoke.LocalFree((HLOCAL)ownerSid.Value);
}
}
}

var host = Host.CreateDefaultBuilder(args)
.UseWindowsService(options =>
{
Expand Down
7 changes: 5 additions & 2 deletions HyperVExtension/src/DevSetupAgent/Requests/ErrorRequest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,11 @@ namespace HyperVExtension.DevSetupAgent;
/// </summary>
internal class ErrorRequest : IHostRequest
{
public ErrorRequest(IRequestMessage requestMessage)
public ErrorRequest(IRequestMessage requestMessage, Exception? ex = null)
{
Timestamp = DateTime.UtcNow;
RequestId = requestMessage.RequestId!;
Error = ex;
}

public virtual uint Version { get; set; } = 1;
Expand All @@ -27,6 +28,8 @@ public ErrorRequest(IRequestMessage requestMessage)

public virtual IHostResponse Execute(ProgressHandler progressHandler, CancellationToken stoppingToken)
{
return new ErrorResponse(RequestId);
return new ErrorResponse(RequestId, Error);
}

private Exception? Error { get; }
}
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,6 @@ public IHostRequest CreateRequest(IRequestContext requestContext)
{
if (_requestFactories.TryGetValue(requestType, out var createRequest))
{
// TODO: Try/catch error.
requestContext.JsonData = requestJson!;
return createRequest(requestContext);
}
Expand Down
15 changes: 12 additions & 3 deletions HyperVExtension/src/DevSetupAgent/Responses/ErrorResponse.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,20 @@ namespace HyperVExtension.DevSetupAgent;
/// </summary>
internal sealed class ErrorResponse : ResponseBase
{
public ErrorResponse(string requestId)
public ErrorResponse(string requestId, Exception? error)
: base(requestId)
{
Status = Windows.Win32.Foundation.HRESULT.E_FAIL;
ErrorDescription = "Missing Request data.";
if (error != null)
{
ErrorDescription = error.Message;
Status = (uint)error.HResult;
}
else
{
ErrorDescription = "Missing Request data.";
Status = Windows.Win32.Foundation.HRESULT.E_FAIL;
}

GenerateJsonData();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ public ErrorUnsupportedRequestResponse(string requestId, string requestType)
: base(requestId, requestType)
{
Status = Windows.Win32.Foundation.HRESULT.E_FAIL;
ErrorDescription = "Missing Request type.";
ErrorDescription = "Unsupported Request type.";
GenerateJsonData();
}
}
8 changes: 5 additions & 3 deletions HyperVExtension/src/DevSetupEngine/Logging.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,13 @@ public class Logging
{
public static readonly string LogExtension = ".dhlog";

public static readonly string LogFolderName = "Logs";
public static readonly string LogFolderName = "Logs";

public static readonly string AppName = "DevSetupEngine";

public static readonly string DefaultLogFileName = "hyperv_setup";

private static readonly Lazy<string> _logFolderRoot = new(() => Path.Combine(ApplicationData.Current.TemporaryFolder.Path, LogFolderName));
private static readonly Lazy<string> _logFolderRoot = new(() => Path.Combine(Path.GetTempPath(), AppName, LogFolderName));

public static readonly string LogFolderRoot = _logFolderRoot.Value;
}
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

namespace HyperVExtension.CommunicationWithGuest;
namespace HyperVExtension.HostGuestCommunication;

internal sealed class HResultException : Exception
public sealed class HResultException : Exception
{
public HResultException(int resultCode, string? description = null)
: base(description)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

using HyperVExtension.HostGuestCommunication;
using HyperVExtension.Models;
using Microsoft.Windows.DevHome.SDK;
using Windows.Foundation;
Expand Down
Loading
Loading