Skip to content

Update package layouts & ship continuous profiler in dd-trace/NuGet#3060

Merged
andrewlock merged 18 commits into
masterfrom
andrew/package-refactory
Aug 11, 2022
Merged

Update package layouts & ship continuous profiler in dd-trace/NuGet#3060
andrewlock merged 18 commits into
masterfrom
andrew/package-refactory

Conversation

@andrewlock

@andrewlock andrewlock commented Aug 8, 2022

Copy link
Copy Markdown
Member

Summary of changes

  • Refactors all installers to use the unified package layouts
  • Adds profiler to the distribution NuGet, the dd-trace tool, and windows-tracer-home.zip (for AAS)
  • Allow enabling debug logs for native loader
  • Start to simplify build

Reason for change

We need to ship the continuous profiler with all the existing installation mechanisms. That was not going to be possible with the existing package layouts and assumptions, consequently we have adopted a package layout which:

  • Is based on the dd-trace layout, where the arch-specific versions are in subfolders linux-x64, win-x86 etc
  • Places a symlink to the native loader in the root of the package where necessary for backwards compatibility.

This also will hopefully simplify some of the build/test code, though much of that will later come in subsequent refactoring.

Implementation details

Prior to these changes, each platform had a slightly different package layout, which also meant the build process was rather convoluted, required copying files around and renaming, and generally wasn't idempotent (e.g. you couldn't run ZipMonitoringHome twice without a clean in between). As well as fixing the package layouts this PR goes someway to cleaning up the build. For example:

  • Everything is built/published directly to MonitoringHomeDirectory. The TracerHomeDirectory and ProfilerHomeDirectory build variables have gone; everything goes into monitoring home.
  • The dlls build directly as Datadog.Profiler.Native, Datadog.Tracer.Native, and Datadog.Trace.ClrProfiler.Native (native loader). The profiler's api wrapper dll remains as Datadog.Linux.ApiWrapper.x64 for back compat reasons. There is no renaming of dlls as part of the build anymore
  • More of the packaging (e.g. for dd-trace and the NuGet) is done in Nuke, instead of using Azure DevOps tasks. That gives us extra portability and makes it easier to test locally. The yaml pipline should only upload and download files to the same logical directory, it shouldn't be "moving stuff around".
  • Various other minor changes
  • Fixes some of the logic AppSec use to locate the loader, which has been incorrect for some time.
  • Enable debug logs for the native loader when DD_TRACE_DEBUG=. ⚠️ I just copy-pasted this code, someone more C++y should probably clean this up 😄

The main changes are obviously to the package layout for each of the install mechanisms.

windows-tracer-home.zip

The tracer home zip is used by AAS, and has been updated to include the continuous profiler. The layout has not changed significantly here, but the continuous profiler and native loader have been added.

image

MSI

The MSI layout has changed significantly. Prior to this PR, after install, the MSI had the following folder layout.

BEFORE

For the x64 installer, the C:\Program Files\Datadog\.NET Tracer and C:\Program Files (x86)\Datadog\.NET Tracer respectively look like this:

image

For the x86 installer, C:\Program Files (x86)\Datadog\.NET Tracer looks like this:

image

AFTER

After this PR, the file names have been normalized to match other platforms, and the layout has been changed to remove the /tracer and /continuousprofiler subfolders. The x64 installer also now deploys entirely to Program Files, which also resolves a long-standing issue around controlling the install folder:
image

and the x86 installer folder looks like this:

image

This is obviously a big change, but luckily the MSI is where we have the most flexibility to rearrange things, as we register the dll via the com ID, so we shouldn't have to worry about paths. We now don't register the dll via COM, and instead provide the paths, which actually gives us more flexibility to fix the package layout

Linux installers .deb/tar/rpm

Note All the linux installer packages have the same layout once unpacked, so I only show the tar folders as an example

BEFORE

Prior to this PR, the package layouts for Linux looked like this.

image

Note that they all look the same, but they're not; the native files in each one are different!

AFTER

After this PR, each package layout is unique.

image

For backwards compatibility reasons:

  • We include a symlink from the "root" dll to the "arch-specific" dll. This is necessary because users will have environment variables pointing to the root file and removing it would break them. I've tested symlinks with all the package types and they seamlessly unpack, so this is the best option I think
  • The API wrapper dll for the profiler must remain in the same location. This is for the same reason - users will have added that path to an environment variable
  • The libddwaf.so symlink in the root may not be necessary, but seemed safest. Could/should re-evaluate that one I think
  • The loader.conf file contains the relative path to the native tracer/profiler. So the contents of the file in the root folder is different to the one in the arch-specific folder.

NuGet / dd-trace tool

The NuGet layout is essentially unchanged, but now includes the native loader + profiler for each platform. The NuGet and the dd-tool use the same layout, so I'm only showing the one example here:

BEFORE

image

AFTER

image

Note The addition of all the extra native dlls increases the package size by ~12MB. It's not higher, because we weren't previously stripping the dll info, which we now are! 🙂

Regarding backwards compatibility:

  • We have never shipped the profiler on these platforms, and you have to manually set the paths, so including Datadog.Linux.ApiWrapper.x64.so in the arch-specific folder seemed like the easiest/best option. Customers will need to set the LD_PRELOAD variable accordingly.
  • Open question I haven't addressed and needs answering: How should customers set LD_PRELOAD when using dd-trace? Should we set it when setting env vars to start the process? Or does the customer have to set it before calling dd-trace? If the former, that should be done in this (or another) PR. If the latter, we could have a problem 😬

Test coverage

Test coverage is primarily provided by the installer smoke tests and existing integration tests.

Additionally:

  • Manual comparison of build output (included screenshots in this PR)
  • Verified that native symbols are published
  • Check there's nothing in the installer smoke-test logs that indicate something wrong.

For the latter point I will do this, but I would appreciate if someone from each team would cast an eye over and makes sure there's nothing untoward, particularly where it comes to native dll interaction (debugger team optional as it's not yet GA) 🙂 . I'll attach some log files here to make it easier, then each team can indicate that they're happy? There are more permutations than below, but I stripped down to the bear minimum IMO😬 Alternatively, just tick away and YOLO it 😉

Other details

There's lots of build cleanup I'd like to do after this, but I'd like to leave that to later PRs as this is complex enough as it is.

It's maybe also worth noting that in all cases other than the linux packages, the native dlls are all in the same folder, and the loader.conf paths all point to files in the same directory. It may be worth considering making loader.conf optional if that gives any start performance benefits (i.e. assume everything in the same directory unless we say otherwise).

@andrewlock andrewlock added area:builds project files, build scripts, pipelines, versioning, releases, packages area:installers labels Aug 8, 2022
@andrewlock
andrewlock requested review from a team as code owners August 8, 2022 15:24
@andrewlock

This comment has been minimized.

@andrewlock

This comment has been minimized.

Comment thread shared/src/msi-installer/Tracer/Files.wxs Outdated
Comment thread shared/src/msi-installer/Tracer/Files.wxs Outdated
Comment thread shared/src/msi-installer/ContinuousProfiler/Files.wxs Outdated
Comment thread shared/src/msi-installer/ContinuousProfiler/Files.wxs Outdated
Comment thread shared/src/msi-installer/shared/Files.wxs Outdated
Comment thread shared/src/msi-installer/shared/Files.wxs Outdated
Comment thread shared/src/msi-installer/shared/Files.wxs Outdated
Logger.Info($"Copying file '{source}' to 'file {dest}'");
CopyFileToDirectory(source, dest, FileExistsPolicy.Overwrite);
var (arch, ext) = GetUnixArchitectureAndExtension();
var sourceDir = ProfilerOutputDirectory / "DDProf-Deploy";

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

This division / overload that Nuke has is really cool

<Component Id="EnvironmentVariablesShared" Guid="{C314A305-9C24-4E46-9ECF-E5EEA703BDEA}" Win64="$(var.Win64)">
<CreateFolder/>
<Environment Id="DD_NATIVELOADER_CONFIGFILE" Name="DD_NATIVELOADER_CONFIGFILE" Action="set" Permanent="no" System="yes" Value="[INSTALLFOLDER]loader.conf" Part="all" />
<?if $(var.Win64) = yes ?>

@zacharycmontoya zacharycmontoya Aug 8, 2022

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I suspected that this would not work when 1) the 64-bit installer is installed and 2) a 32-bit process is being instrumented, and I was able to verify this issue locally. When this happens the loader emits the following log lines:

[2022-08-08 14:01:16.683 | debug | PId: 62804 | TId: 56360] Load: C:\Program Files\Datadog\.NET Tracer\win-x64\Datadog.Tracer.Native.dll
[2022-08-08 14:01:16.683 | warning | PId: 62804 | TId: 56360] Load: Error loading dynamic library 'C:\Program Files\Datadog\.NET Tracer\win-x64\Datadog.Tracer.Native.dll': 02F66CA0

This is only an issue with the MSI and specifically the 64-bit installer because we have to globally set DD_NATIVELOADER_CONFIGFILE for all applications, but the config loader must be able to select the native bits that match the process bitness. To handle this correctly, I think we'll need to do the following:

  1. Install the loader.conf at the [INSTALLFOLDER] location
  2. This loader.conf will need to include the win-x64 and win-x86 subdirectories in its lookup paths
  3. Always set DD_NATIVELOADER_CONFIGFILE to point to the [INSTALLFOLDER]loader.conf location

Compared to the BEFORE state, the only change should be the loader.conf file. The new loader.conf should look like the following:

#Profiler
PROFILER;{BD1A650D-AC5D-4896-B64F-D6FA25D6B26A};win-x64;.\win-x64\Datadog.Profiler.Native.dll
PROFILER;{BD1A650D-AC5D-4896-B64F-D6FA25D6B26A};win-x86;.\win-x86\Datadog.Profiler.Native.dll

#Tracer
TRACER;{50DA5EED-F1ED-B00B-1055-5AFE55A1ADE5};win-x64;.\win-x64\Datadog.Tracer.Native.dll
TRACER;{50DA5EED-F1ED-B00B-1055-5AFE55A1ADE5};win-x86;.\win-x86\Datadog.Tracer.Native.dll

@zacharycmontoya zacharycmontoya Aug 8, 2022

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I started a thread here where I suggested we could move all of the 32-bit assets into the Program Files (x86) folder just like Datadog.Trace.ClrProfiler.Native.dll, since that's required to be placed there. If we did that AND we did not set DD_NATIVELOADER_CONFIGFILE globally, then what would happen is the loader DLL would look in its directory for a loader.conf file. Since all of the 64-bit files (and the loader) would be in the same directory as the 64-bit Datadog.Trace.ClrProfiler.Native.dll loader and all of the 32-bit files (and the loader) would be in the same directory as the 32-bit Datadog.Trace.ClrProfiler.Native.dll loader, this should fix the issue I surfaced. This seems to me like the cleanest solution that addresses both issues. What do you think?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I think having everything 32-bit in the 32-bit program folder makes a lot of sense. My only question is whether having all the managed dlls in a separate folder away from the native loaders becomes an issue then.. It breaks the "clean, unified layout" we currently have (but the MSI breaks that anyway by having two install locations).

Essentially it's a question of whether it's better to have

  • x86 assets all in the same location
  • simple loader conf
  • tracer home cannot be inferred from native dll locations, and is in a separate location

or

  • native loader separate from x86 native dlls + loader conf
  • tweaked loader conf
  • tracer home can be inferred from native tracer etc

I was initially thinking the first approach, but now I'm leaning to the second approach...

Also... I didn't realise we don't have any 32-bit on x64 tests in CI 😬 We should have one at least! I'll try adding a smoke test separately...

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Have we considered installing all the files into a single base location, either Program Files or Program Files (x86) or other, instead of splitting them up? I think we can do that now that we have the win-x64 and win-x86 folders, and it could make things simpler by keeping everything contained in a single path (like all the other packages). On the other hand, this may require some MSI trickery, since MSI can be finicky about what is x64 vs x86.

Related: there is a long-standing bug where we allow users to change the tracer installation path, but that only applies to the files in Program Files. Users cannot change where the Program Files (x86) files are installed. We've had support cases of users not wanting to install anything into C:\, for example, but that is currently not possible.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Have we considered installing all the files into a single base location, either Program Files or Program Files (x86) or other, instead of splitting them up?

MSIs aren't my strong point, so I don't know why we split them up at all (I thought we always had the win-x64 and winx-86 folders). I assumed it was because we register via the ID with the MSI, not using the profiler path, so I assumed the profiler had to be in the expected folder (i.e. Program Files (X86) for 32-bit processes)

If we can avoid it, I'm strongly in favour of not splitting them up! Especially if it solves additional issues.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

Awesome!

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Those changes look good to me! We should also update our docs to remove the unnecessary COR_PROFILER/CORECLR_PROFILER GUID.

Question: As we now set the COR_PROFILER/CORECLR_PROFILER GUID as a machine-wide env var, should we remove it from the IIS registry keys to avoid the duplication?

I say go for it 👍🏼

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I think it's always clearer for the user (or troubleshooter) to have all the config variables in the same place. If we are setting the IIS variables in the registry I find it always usefull to have them all together, althaough some of them could be declared globally.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I think it's always clearer for the user (or troubleshooter) to have all the config variables in the same place.

The trouble is we need to support IIS, windows services and ad-hoc apps. With the approach we've taken here, users only need to set COR_ENABLE_PROFILING for the windows services or for the standalone apps, nothing else needs setting.

If we don't take this approach then either:

  • We require customers to set the env var paths to the profiler correctly when running windows services etc. That's potentially 4/8 env vars... I think it's better to only require the COR_ENABLE_PROFILING/CORECLR_ENABLE_PROFILING variables, as they're harder to screw up
  • Duplicate config variables in multiple places, i.e. globally and in IIS. There's more chances for things to go out sync then

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

@zacharycmontoya

Copy link
Copy Markdown
Contributor

By the way, some of the installer smoke tests haven't run because they require some extra variables to be set. Can you make sure they all get run before merging?

Comment thread tracer/test/Datadog.Trace.TestHelpers/EnvironmentHelper.cs
Comment thread profiler/src/Demos/Samples.WindowsService01/ReadMe.md Outdated
Comment thread profiler/src/Demos/Samples.WindowsService01/ReadMe.md Outdated
Comment thread profiler/src/ProfilerEngine/Directory.Build.targets Outdated
Comment thread tracer/build/_build/Build.cs Outdated
Comment thread tracer/build/_build/Build.Steps.cs Outdated
Comment thread tracer/build/_build/Build.Steps.cs Outdated
Comment thread profiler/test/Datadog.Profiler.IntegrationTests/Helpers/EnvironmentHelper.cs Outdated
Comment thread .azure-pipelines/ultimate-pipeline.yml
Comment thread .azure-pipelines/ultimate-pipeline.yml
@andrewlock

This comment has been minimized.

@andrewlock

This comment has been minimized.

@andrewlock

Copy link
Copy Markdown
Member Author

Just a note comparing the size of assets before and after this PR:

  • Datadog.Monitoring.Distribution.2.14.0-beta01.nupkg - 67 MB (+20 MB)
  • datadog-dotnet-apm-2.14.0-1.aarch64.rpm - 12 MB (~unchanged)
  • datadog-dotnet-apm-2.14.0-1.x86_64.rpm - 12 MB (~unchanged)
  • datadog-dotnet-apm-2.14.0-musl.tar.gz - 12 MB (~unchanged)
  • datadog-dotnet-apm-2.14.0.arm64.tar.gz - 12 MB (~unchanged)
  • datadog-dotnet-apm-2.14.0.tar.gz - 12 MB (~unchanged)
  • datadog-dotnet-apm_2.14.0_amd64.deb - 12 MB (~unchanged)
  • datadog-dotnet-apm_2.14.0_arm64.deb - 12 MB (~unchanged)
  • dd-trace-linux-arm64.tar.gz - 50 MB (+10 MB)
  • dd-trace-linux-musl-x64.tar.gz - 50 MB (+10 MB)
  • dd-trace-linux-x64.tar.gz - 50 MB (+10 MB)
  • dd-trace-win-x64.zip - 49 MB (+10 MB)
  • dd-trace.2.14.0.nupkg - 56 MB (+10 MB)
  • datadog-dotnet-apm-2.14.0-x64.msi - 15 MB (~unchanged)
  • datadog-dotnet-apm-2.14.0-x86.msi - 12 MB (~unchanged)

@andrewlock

Copy link
Copy Markdown
Member Author

By the way, some of the installer smoke tests haven't run because they require some extra variables to be set. Can you make sure they all get run before merging?

Just to confirm, all of the installer tests have now been run, either here or here.

@zacharycmontoya zacharycmontoya left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

LGTM. I wasn't 100% sure if the Datadog.Linux.ApiWrapper.x64.so path was correct in all of the files, but if the tests are all passing and the profiling team signs off, then I assume it's good. Nice work and thanks for the phenomenal PR description!

@pierotibou pierotibou left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

LGTM (but not the most knowledgeable on that part clearly).
Thanks a LOT for this huge work and the premilinary work that allow us to make that change with more confidence.

@andrewlock

Copy link
Copy Markdown
Member Author

LGTM. I wasn't 100% sure if the Datadog.Linux.ApiWrapper.x64.so path was correct in all of the files, but if the tests are all passing and the profiling team signs off, then I assume it's good.

The location (and naming) of Datadog.Linux.ApiWrapper.x64.so is a tricky one. It needs to be set by an environment variable on Linux, as in the smoke tests:

ENV LD_PRELOAD=/opt/datadog/continuousprofiler/Datadog.Linux.ApiWrapper.x64.so

As it's a required config for customers, unfortunately, we can't change its location. Hence why the linux installers all keep this file (or a symlink to it) in the continuousprofiler subfolder.

This only applies to the linux installers though:

  • For dd-trace we set that variable, so we can change its location (to be inside the arch-specific folder)
  • For the NuGet package, this wasn't previously supported, so we can document the path that customers need to use as being the arch-specific path

@anna-git

anna-git commented Aug 11, 2022

Copy link
Copy Markdown
Contributor

I checked out the branch, if I run buildtracerhome CompileSamplesWindows RunDotNetSample -SampleName Samples.Security.AspNetCore5 -Framework net5.0 -ExtraEnvVars DD_APPSEC_ENABLED=true it's looking for Datadog.Trace.ClrProfiler.Native.dll in dd-trace-dotnet\shared\bin\monitoring-home\win-x64 which doesnt exist cause it's Datadog.Tracer.Native.dll, is there now a new additional command to run or should the variables be ajusted in AddTracerEnvironmentVariables?


<NativeLinuxX86DeployFilesSrcDir>$(BaseOutputPath)\$(Configuration)-x86\profiler\src\ProfilerEngine\Datadog.Profiler.Native.Linux</NativeLinuxX86DeployFilesSrcDir>
<NativeLinuxX64DeployFilesSrcDir>$(BaseOutputPath)\$(Configuration)-x64\profiler\src\ProfilerEngine\Datadog.Profiler.Native.Linux</NativeLinuxX64DeployFilesSrcDir>
<NativeWindowsDeployFilesSrcDir>$(BaseOutputPath)\$(ConfigBasedRelativeOutputPath)\profiler\src\ProfilerEngine\Datadog.Profiler.Native.Windows</NativeWindowsDeployFilesSrcDir>

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Removing the bitness info in the path might break here. Since x86 and x64 binaries have now the same name, they can be copied into the same folder: I don't know which one will erase the other.
image
Am I missing something?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Removing the bitness info in the path might break here. Since x86 and x64 binaries have now the same name, they can be copied into the same folder: I don't know which one will erase the other.

I mean, yes, they can be overwritten, but if they are, then we have a build problem 😄 They are currently (before and after this change), built to separate folders, e.g. Release-x86 and Release-x64.

When they're copied to DDProf-Deploy they're deployed to the win-x64 and win-x86 folders, so there's again no issue with overwritting AFAICT?

There's a bigger question here for me - why do we need the DDProf-Deploy directory at all? For me, it adds confusion and complexity? It's not where things are built to, so we could just "deploy" them to the Monitoring Home directory, where they end up eventually anyway?

I was a bit torn on the "dropping the bitness from the file names" question, but we ultimately opted for it for consistency, and to reduce the duplication in the arch-specific folders. That, coupled with the fact we have to drop it in some cases for back compat reasons led us to this state... I think we can safely add it back in later though if it's an issue, it's only the Datadog.Trace.ClrProfiler.Native file we can't ever rename 🙂

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

When they're copied to DDProf-Deploy they're deployed to the win-x64 and win-x86 folders, so there's again no issue with overwritting AFAICT?
Where is this done?
The $(BaseOutputPath)$(ConfigBasedRelativeOutputPath) does not seem to contain the bitness

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Where is this done?
The (ConfigBasedRelativeOutputPath) does not seem to contain the bitness

ConfigBasedRelativeOutputPath contains the bitness 🙂 It's (e.g.) Release-x86 or Release-x64

<NativeX64DeployFiles Include="$(NativeWindowsX64DeployFilesSrcDir)\*.dll" />
<NativeX64DeployFiles Include="$(NativeWindowsX64DeployFilesSrcDir)\*.pdb" />
<NativeX64DeployFiles Include="$(NativeLinuxX64DeployFilesSrcDir)\*.so" />
<NativeDeployFiles Include="$(NativeWindowsDeployFilesSrcDir)\*.dll" />

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Same comment

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Also, the simple answer is that NativeWindowsDeployFilesSrcDir is different for different architectures 🙂

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

I have to admit that I don't see NativeWindowsDeployFilesSrcDir set.
However, is it the "source" from which the files will be copied (could be different because generated during the build)?
Here, I'm talking about the destination in DDProf-Deploy

@andrewlock andrewlock Aug 11, 2022

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

I have to admit that I don't see NativeWindowsDeployFilesSrcDir set.
It's set on line 46, on your previous comment, and includes Release-x64 etc in the path.

Here, I'm talking about the destination in DDProf-Deploy

The destination is given by DeployDirectoryBase, which is DDProf-Deploy/win-x64 and DDProf-Deploy/win-x86 respectively.

On linux we currently still build to the root, as we only build one architecture. We would need to update the CMakefile etc to account for that if we start building for multiple arches at once on Linux. But that's a current issue too, so there's no change in that


<AllDeployFiles Include="@(NativeX86DeployFiles)" />
<AllDeployFiles Include="@(NativeX64DeployFiles)" />
<AllDeployFiles Include="@(NativeDeployFiles)" />

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Same comment

<Message Text="[PrepareDeployDirectory] NativeWindowsX64DeployFilesSrcDir: '$(NativeWindowsX64DeployFilesSrcDir)'" Importance="high" />
<Message Text="[PrepareDeployDirectory] NativeLinuxX86DeployFilesSrcDir: '$(NativeLinuxX86DeployFilesSrcDir)'" Importance="high" />
<Message Text="[PrepareDeployDirectory] NativeLinuxX64DeployFilesSrcDir: '$(NativeLinuxX64DeployFilesSrcDir)'" Importance="high" />
<Message Text="[PrepareDeployDirectory] NativeWindowsDeployFilesSrcDir: '$(NativeWindowsDeployFilesSrcDir)'" Importance="high" />

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Same comment

<?include $(sys.CURRENTDIR)\Config.wxi?>
<Fragment>
<ComponentGroup Id="ContinuousProfiler.Files" Directory="ContinuousProfiler">
<ComponentGroup Id="ContinuousProfiler.Files" Directory="INSTALLFOLDER">

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

What are the files that will be copied in this root folder for the profiler?
I'm not sure we have any since we got rid of Datadog.AutoInstrumentation.Profiler.Managed.dll

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

You're right, there aren't any! The Tracer has this too, I'm not sure exactly why it's there, not sure if it's required or not. I'll try cleaning it up in a subsequent PR

.EnableNoRestore()
.EnableNoBuild()
.SetProcessEnvironmentVariable("TracerHomeDirectory", TracerHomeDirectory)
.SetProcessEnvironmentVariable("TracerHomeDirectory", MonitoringHomeDirectory)

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Won't this cause some confusion? In other places in this PR, it seemed like we are deprecating the concept of a "TracerHome", but maybe I misinterpreted?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

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

Won't this cause some confusion? In other places in this PR, it seemed like we are deprecating the concept of a "TracerHome", but maybe I misinterpreted?

Yep, we're deprecating the use of TracerHome, there's still some cleanup to do to remove all traces of it though 🙂 I'll push that to a later PR for simplicity

@OmerRaviv OmerRaviv left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

I only did a quick superficial pass to verify that I don't see any thing that stands out for the debugger, but LGTM!

@andrewlock

Copy link
Copy Markdown
Member Author

I checked out the branch, if I run buildtracerhome CompileSamplesWindows RunDotNetSample -SampleName Samples.Security.AspNetCore5 -Framework net5.0 -ExtraEnvVars DD_APPSEC_ENABLED=true it's looking for Datadog.Trace.ClrProfiler.Native.dll in dd-trace-dotnet\shared\bin\monitoring-home\win-x64 which doesnt exist cause it's Datadog.Tracer.Native.dll, is there now a new additional command to run or should the variables be ajusted in AddTracerEnvironmentVariables?

Yep, you will always need to run BuildNativeLoader in addition to BuildTracerHome now - I haven't added it as a direct dependency, because each team (profiling, tracing) needs to build it separately, but we don't want to build it twice 🙂

I think I can definitely improve this in a later PR by making it a direct dependency and re-working some things!

@andrewlock

Copy link
Copy Markdown
Member Author

Benchmarks Report 🐌

Benchmarks for #3060 compared to master:

  • 5 benchmarks are faster, with geometric mean 13.583
  • 4 benchmarks have fewer allocations

The following thresholds were used for comparing the benchmark speeds:

  • Mann–Whitney U test with statistical test for significance of 5%
  • Only results indicating a difference greater than 10% and 0.3 ns are considered.

Allocation changes below 0.5% are ignored.

Benchmark details

Benchmarks.Trace.AgentWriterBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master WriteAndFlushEnrichedTraces net472 718μs 230ns 861ns 0.359 0 0 3.18 KB
master WriteAndFlushEnrichedTraces netcoreapp3.1 450μs 137ns 492ns 0 0 0 2.58 KB
#3060 WriteAndFlushEnrichedTraces net472 716μs 172ns 598ns 0.355 0 0 3.18 KB
#3060 WriteAndFlushEnrichedTraces netcoreapp3.1 463μs 160ns 619ns 0 0 0 2.58 KB
Benchmarks.Trace.AppSecBodyBenchmark - Faster 🎉 Fewer allocations 🎉

Faster 🎉 in #3060

Benchmark base/diff Base Median (ns) Diff Median (ns) Modality
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleMoreComplexBody‑net472 91.755 16,927.50 184.49
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleMoreComplexBody‑netcoreapp3.1 61.439 14,413.83 234.60
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleSimpleBody‑net472 9.359 1,704.44 182.12
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleSimpleBody‑netcoreapp3.1 7.750 1,822.71 235.19

Fewer allocations 🎉 in #3060

Benchmark Base Allocated Diff Allocated Change Change %
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleSimpleBody‑netcoreapp3.1 1.37 KB 424 B -944 B -69.01%
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleSimpleBody‑net472 1.49 KB 425 B -1.07 KB -71.51%
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleMoreComplexBody‑netcoreapp3.1 7.85 KB 400 B -7.45 KB -94.90%
Benchmarks.Trace.AppSecBodyBenchmark.AllCycleMoreComplexBody‑net472 8.75 KB 401 B -8.35 KB -95.42%

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master AllCycleSimpleBody net472 1.7μs 1.42ns 5.32ns 0.237 0 0 1.49 KB
master AllCycleSimpleBody netcoreapp3.1 1.82μs 1.64ns 6.14ns 0.0183 0 0 1.37 KB
master AllCycleMoreComplexBody net472 16.9μs 17.5ns 67.9ns 1.39 0.0246 0 8.75 KB
master AllCycleMoreComplexBody netcoreapp3.1 14.4μs 18.1ns 65.1ns 0.108 0 0 7.85 KB
master BodyExtractorSimpleBody net472 248ns 0.213ns 0.826ns 0.0573 0 0 361 B
master BodyExtractorSimpleBody netcoreapp3.1 224ns 0.234ns 0.876ns 0.00382 0 0 272 B
master BodyExtractorMoreComplexBody net472 14.5μs 10.3ns 38.5ns 1.21 0.0216 0 7.62 KB
master BodyExtractorMoreComplexBody netcoreapp3.1 12μs 15.4ns 57.6ns 0.0897 0 0 6.75 KB
#3060 AllCycleSimpleBody net472 182ns 0.143ns 0.535ns 0.0675 9.19E-05 0 425 B
#3060 AllCycleSimpleBody netcoreapp3.1 235ns 0.314ns 1.22ns 0.00586 0 0 424 B
#3060 AllCycleMoreComplexBody net472 185ns 0.146ns 0.546ns 0.0637 0 0 401 B
#3060 AllCycleMoreComplexBody netcoreapp3.1 234ns 0.239ns 0.926ns 0.00539 0 0 400 B
#3060 BodyExtractorSimpleBody net472 266ns 0.118ns 0.425ns 0.0573 0 0 361 B
#3060 BodyExtractorSimpleBody netcoreapp3.1 231ns 0.264ns 1.02ns 0.00376 0 0 272 B
#3060 BodyExtractorMoreComplexBody net472 14.3μs 31.1ns 120ns 1.2 0.0214 0 7.62 KB
#3060 BodyExtractorMoreComplexBody netcoreapp3.1 12.2μs 12.1ns 45.4ns 0.0907 0 0 6.75 KB
Benchmarks.Trace.AspNetCoreBenchmark - Unknown 🤷 Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master SendRequest net472 0ns 0ns 0ns 0 0 0 0 b
master SendRequest netcoreapp3.1 179μs 154ns 597ns 0.178 0 0 20.33 KB
#3060 SendRequest net472 0ns 0ns 0ns 0 0 0 0 b
#3060 SendRequest netcoreapp3.1 178μs 122ns 473ns 0.178 0 0 20.33 KB
Benchmarks.Trace.DbCommandBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master ExecuteNonQuery net472 1.54μs 0.822ns 3.08ns 0.126 0.000771 0 794 B
master ExecuteNonQuery netcoreapp3.1 1.26μs 0.338ns 1.26ns 0.0107 0 0 824 B
#3060 ExecuteNonQuery net472 1.55μs 0.359ns 1.39ns 0.126 0.000773 0 794 B
#3060 ExecuteNonQuery netcoreapp3.1 1.33μs 0.553ns 2.07ns 0.0108 0 0 824 B
Benchmarks.Trace.ElasticsearchBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master CallElasticsearch net472 2.25μs 0.417ns 1.56ns 0.159 0 0 1 KB
master CallElasticsearch netcoreapp3.1 1.44μs 1.05ns 4.08ns 0.0136 0 0 984 B
master CallElasticsearchAsync net472 2.34μs 0.764ns 2.86ns 0.18 0 0 1.14 KB
master CallElasticsearchAsync netcoreapp3.1 1.52μs 0.378ns 1.46ns 0.0144 0 0 1.1 KB
#3060 CallElasticsearch net472 2.19μs 0.725ns 2.81ns 0.159 0 0 1 KB
#3060 CallElasticsearch netcoreapp3.1 1.34μs 0.667ns 2.58ns 0.0129 0 0 984 B
#3060 CallElasticsearchAsync net472 2.25μs 0.841ns 3.03ns 0.181 0 0 1.14 KB
#3060 CallElasticsearchAsync netcoreapp3.1 1.44μs 0.603ns 2.26ns 0.0151 0 0 1.1 KB
Benchmarks.Trace.GraphQLBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master ExecuteAsync net472 2.39μs 5.41ns 21ns 0.199 0 0 1.26 KB
master ExecuteAsync netcoreapp3.1 1.56μs 1.75ns 6.78ns 0.0166 0 0 1.22 KB
#3060 ExecuteAsync net472 2.5μs 5.41ns 20.2ns 0.2 0 0 1.26 KB
#3060 ExecuteAsync netcoreapp3.1 1.61μs 2.16ns 8.38ns 0.0161 0 0 1.22 KB
Benchmarks.Trace.HttpClientBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master SendAsync net472 5μs 6.38ns 24.7ns 0.394 0 0 2.48 KB
master SendAsync netcoreapp3.1 3.15μs 4.14ns 15.5ns 0.0316 0 0 2.36 KB
#3060 SendAsync net472 4.95μs 7.13ns 27.6ns 0.392 0 0 2.48 KB
#3060 SendAsync netcoreapp3.1 3.19μs 6.14ns 23.8ns 0.0317 0 0 2.36 KB
Benchmarks.Trace.ILoggerBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master EnrichedLog net472 2.87μs 1.75ns 6.76ns 0.263 0 0 1.66 KB
master EnrichedLog netcoreapp3.1 2.35μs 0.736ns 2.75ns 0.0236 0 0 1.73 KB
#3060 EnrichedLog net472 2.74μs 1.28ns 4.97ns 0.263 0 0 1.66 KB
#3060 EnrichedLog netcoreapp3.1 2.3μs 0.743ns 2.78ns 0.0233 0 0 1.73 KB
Benchmarks.Trace.Log4netBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master EnrichedLog net472 147μs 72.3ns 280ns 0.666 0.222 0 4.5 KB
master EnrichedLog netcoreapp3.1 114μs 218ns 845ns 0.056 0 0 4.38 KB
#3060 EnrichedLog net472 148μs 78.2ns 303ns 0.672 0.224 0 4.5 KB
#3060 EnrichedLog netcoreapp3.1 112μs 138ns 534ns 0.056 0 0 4.38 KB
Benchmarks.Trace.NLogBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master EnrichedLog net472 5.43μs 10.2ns 39.5ns 0.543 0.0027 0 3.43 KB
master EnrichedLog netcoreapp3.1 4.22μs 6.96ns 26.9ns 0.0524 0 0 3.8 KB
#3060 EnrichedLog net472 5.38μs 9.15ns 35.4ns 0.544 0.00268 0 3.43 KB
#3060 EnrichedLog netcoreapp3.1 4.28μs 8.37ns 32.4ns 0.0514 0 0 3.8 KB
Benchmarks.Trace.RedisBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master SendReceive net472 2.08μs 0.941ns 3.65ns 0.193 0 0 1.22 KB
master SendReceive netcoreapp3.1 1.63μs 0.7ns 2.71ns 0.0164 0 0 1.21 KB
#3060 SendReceive net472 2μs 0.594ns 2.22ns 0.193 0 0 1.22 KB
#3060 SendReceive netcoreapp3.1 1.7μs 0.332ns 1.2ns 0.0162 0 0 1.21 KB
Benchmarks.Trace.SerilogBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master EnrichedLog net472 4.71μs 0.78ns 3.02ns 0.328 0 0 2.08 KB
master EnrichedLog netcoreapp3.1 4.23μs 1.1ns 3.82ns 0.0211 0 0 1.69 KB
#3060 EnrichedLog net472 4.78μs 1.41ns 5.48ns 0.33 0 0 2.08 KB
#3060 EnrichedLog netcoreapp3.1 4.2μs 1.21ns 4.36ns 0.021 0 0 1.69 KB
Benchmarks.Trace.SpanBenchmark - Faster 🎉 Same allocations ✔️

Faster 🎉 in #3060

Benchmark base/diff Base Median (ns) Diff Median (ns) Modality
Benchmarks.Trace.SpanBenchmark.StartFinishScope‑net472 1.131 1,172.19 1,036.45

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master StartFinishSpan net472 824ns 0.151ns 0.545ns 0.104 0 0 658 B
master StartFinishSpan netcoreapp3.1 758ns 0.279ns 1.08ns 0.00872 0 0 648 B
master StartFinishScope net472 1.17μs 0.237ns 0.916ns 0.117 0 0 738 B
master StartFinishScope netcoreapp3.1 883ns 0.303ns 1.09ns 0.0102 0 0 768 B
#3060 StartFinishSpan net472 859ns 0.438ns 1.58ns 0.104 0 0 658 B
#3060 StartFinishSpan netcoreapp3.1 738ns 0.339ns 1.31ns 0.00851 0 0 648 B
#3060 StartFinishScope net472 1.04μs 0.389ns 1.51ns 0.117 0 0 738 B
#3060 StartFinishScope netcoreapp3.1 851ns 0.232ns 0.835ns 0.0103 0 0 768 B
Benchmarks.Trace.TraceAnnotationsBenchmark - Same speed ✔️ Same allocations ✔️

Raw results

Branch Method Toolchain Mean StdError StdDev Gen 0 Gen 1 Gen 2 Allocated
master RunOnMethodBegin net472 1.28μs 0.359ns 1.39ns 0.117 0 0 738 B
master RunOnMethodBegin netcoreapp3.1 1.01μs 0.471ns 1.82ns 0.0106 0 0 768 B
#3060 RunOnMethodBegin net472 1.25μs 0.185ns 0.665ns 0.117 0 0 738 B
#3060 RunOnMethodBegin netcoreapp3.1 1.03μs 0.507ns 1.9ns 0.0103 0 0 768 B

@anna-git

Copy link
Copy Markdown
Contributor

LGTM for appsec, thank you for fixing the paths!!

@dromanol

Copy link
Copy Markdown
Contributor

I think it is always a good improvement to simplify things, and this cleans up file path hell. Great job.

@andrewlock

Copy link
Copy Markdown
Member Author

Code Coverage Report 📊

✔️ Merging #3060 into master will not change line coverage
✔️ Merging #3060 into master will not change branch coverage
⛔ Merging #3060 into master will will increase complexity by 3

master #3060 Change
Lines 16870 / 22912 16746 / 22885
Lines % 74% 73% 0% ✔️
Branches 10065 / 14230 10028 / 14234
Branches % 71% 70% 0% ✔️
Complexity 15293 15296 3

View the full report for further details:

Datadog.Trace Breakdown ✔️

master #3060 Change
Lines % 74% 73% 0% ✔️
Branches % 71% 70% 0% ✔️
Complexity 15293 15296 3

The following classes have significant coverage changes.

File Line coverage change Branch coverage change Complexity change
Datadog.Trace.AppSec.Waf.NativeBindings.ReducedRegistryAccess -80% -50% 0 ✔️
Datadog.Trace.Ci.GitInfo -17% -11% 0 ✔️
Datadog.Trace.Ci.CIVisibility 7% ✔️ 7% ✔️ 0 ✔️

View the full reports for further details:

@chrisnas chrisnas left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

LGTM

@andrewlock
andrewlock merged commit ce14f17 into master Aug 11, 2022
@andrewlock
andrewlock deleted the andrew/package-refactory branch August 11, 2022 13:46
@github-actions github-actions Bot added this to the vNext milestone Aug 11, 2022
andrewlock added a commit that referenced this pull request May 21, 2026
## Summary of changes

Updates the fallback path when loading the native loader (runtime ID
store) to use an absolute path

## Reason for change

By default, we load the native loader using an env var set by the loader
itself. This is the default approach, but there's also a fallback in
case this is not set for some reason.

On Windows only, we were using just the filename to load the library,
which can be ambiguous depending on dll search paths. This changes the
Windows lookup to use an absolute path like we do on Linux

## Implementation details

Remove the `#ifdef` for Windows, and construct the full path in both
cases.

## Test coverage

Should be covered by existing tests

## Other details

Note that the old comment of "the native loader is in the parent
directory" has been incorrect since #3060 (v2.14.0, back in 2022 😅)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area:builds project files, build scripts, pipelines, versioning, releases, packages area:installers

Projects

None yet

Development

Successfully merging this pull request may close these issues.

10 participants