-
Notifications
You must be signed in to change notification settings - Fork 1.4k
[WIP-FEATURE] MSBuild server node #7489
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
[WIP-FEATURE] MSBuild server node #7489
Conversation
ladipro
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Leaving a few comments inline.
| byte? ExpectedVersionInFirstByte { get; } | ||
| } | ||
|
|
||
| internal readonly struct Handshake : IHandshake |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: Better make it a class because the struct will be boxed on the way out of GetHandshake anyway.
| } | ||
|
|
||
| internal readonly struct Handshake | ||
| internal interface IHandshake |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If I'm reading the sources correctly, the only place where handshake needs to be accessed in a generic way is NodeEndpointOutOfProcBase.GetHandshake. This has exactly one caller in PacketPumpProc and only one method is called on the handshake: RetrieveHandshakeComponents.
So overall it looks like this interface may be an overkill and we could instead have something like RetrieveHandshakeComponents (suggestion: name it GetHandshakeData?) directly on NodeEndpointOutOfProcBase.
| // We currently use 6 bits of this 32-bit integer. Very old builds will instantly reject any handshake that does not start with F5 or 06; slightly old builds always lead with 00. | ||
| // This indicates in the first byte that we are a modern build. | ||
| _options = (int)nodeType | (CommunicationsUtilities.handshakeVersion << 24); | ||
| string? handshakeSalt = Environment.GetEnvironmentVariable("MSBUILDNODEHANDSHAKESALT"); | ||
| var msBuildFile = new FileInfo(msBuildLocation); | ||
| var msBuildDirectory = msBuildFile.DirectoryName; | ||
| _salt = ComputeHandshakeHash(handshakeSalt + msBuildDirectory); | ||
| Version fileVersion = new Version(FileVersionInfo.GetVersionInfo(msBuildLocation).FileVersion ?? string.Empty); | ||
| _fileVersionMajor = fileVersion.Major; | ||
| _fileVersionMinor = fileVersion.Minor; | ||
| _fileVersionBuild = fileVersion.Build; | ||
| _fileVersionRevision = fileVersion.Revision; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: Some of this code looks copied from the original Handshake. Do you think it would be worth deduping? By introducing a base class or a helper method maybe.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you explain why we need a new handshake at all? The point of the original handshake is that both sides need to come up with the same thing. I don't like the idea of adding a new thing here without good justification.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I had same question. Handshake from prototype was a little bit different, but I had to align it with current codebase, so it looks almost same now. The main difference is that server doesn't need session ID. We can remove duplicates by (for example) inheritance - if it's OK to change the original handshake from value type to reference type.
cc: @rokonec
|
I didn't review the code but it's of course critical that the CLI-MSBuild pipe is tested to ensure it's secured in the same way as the MSBuild-MSBUild pipes are: the user at both ends must be the same user and (on Windows) elevation level. In .NET Core there's API to do this: while MSBuild builds against .NET Framework it has to continue to do it manually. |
|
Hello @danmoseley, client-server communication uses same IPC infrastructure with user and elevation checking as the current nodes. It's implemented in base class and we didn't change it. |
…ity when the build is initiated by server.
src/Build/BackEnd/Components/Communications/ServerNodeEndpointOutOfProc.cs
Outdated
Show resolved
Hide resolved
src/Build/BackEnd/Components/Communications/ServerNodeEndpointOutOfProc.cs
Outdated
Show resolved
Hide resolved
| string serverRunningMutexName = $@"Global\server-running-{pipeName}"; | ||
| _serverBusyMutexName = $@"Global\server-busy-{pipeName}"; | ||
|
|
||
| // TODO: shall we address possible race condition. It is harmless as it, with acceptable probability, just cause unnecessary process spawning |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This race condition will be most probably handled by client. Please change this command to describe our decision about how will client handle it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There would be mutex "Global\server-launch-{_pipeName}" for starting server process in a client. This does not guarantee that some other client, if anybody writes it, would not introduce a race condition, so the fast quit from server process in this case is still needed.
|
If this is no longer a WIP, can you remove the [WIP-FEATURE] in the title? Looks like the test failures are from an overload of GetHandshakeOptions not being found. |
|
@Forgind, we marked it as WIP as we will merge the code to the feature branch with the client implementation. It will make the work more efficient and we will continue with changes. |
Fixes #7372
Context
MSBuild server is a new node that accepts build request from client. This approach avoids spawning a new MSBuild process for every build from CLI tools like .NET SDK.
Changes Made
This PR implements a new node capable to accept and validate pipe connection, receive and invoke build commands, send console messages to client and inform about build result.
Testing
Tests will be added.
Notes
This is only draft as some areas need more care:
-consoleLoggerParameters:ForceConsoleColorparameter from client, but we have to find a better way.Some aspects will be implemented in different PR: