Skip to content

Conversation

@VSadov
Copy link
Member

@VSadov VSadov commented Jul 29, 2020

The following changes were made:

  • Copy executable PE sections in LayoutILOnly, if there are any, into executable memory.
  • Apply relocs if R2R code is present.
  • Exception stuff (RtlAddFunctionTable / RtlDeleteFunctionTable for non-x86 unwind).

Fixes:#39409

@VSadov VSadov added NO-MERGE The PR is not ready for merge yet (see discussion for detailed reasons) NO-REVIEW Experimental/testing PR, do NOT review it labels Jul 29, 2020
@Dotnet-GitSync-Bot Dotnet-GitSync-Bot added the area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI label Jul 29, 2020
@VSadov VSadov force-pushed the winr2r branch 10 times, most recently from c5ac18a to c4997aa Compare August 2, 2020 23:07
@VSadov
Copy link
Member Author

VSadov commented Aug 3, 2020

Timing execution of HelloWorld app

=== baseline (not singlefile, self-contained app):
$ time for i in {1..10}; do ./hello.exe > /dev/null; done

real 0m0.954s
user 0m0.030s
sys 0m0.199s

=== singlefile app before this change:
$ time for i in {1..10}; do ./hello.exe > /dev/null; done

real 0m1.216s
user 0m0.030s
sys 0m0.137s

=== singlefile app after this change:
$ time for i in {1..10}; do ./hello.exe > /dev/null; done

real 0m0.909s
user 0m0.030s
sys 0m0.121s

@VSadov VSadov changed the title [WIP] Allow execution of R2R code in singlefile app on windows. Allow execution of R2R code in singlefile app on windows. Aug 3, 2020
@VSadov VSadov marked this pull request as ready for review August 3, 2020 19:48
@VSadov VSadov added area-Host and removed NO-MERGE The PR is not ready for merge yet (see discussion for detailed reasons) NO-REVIEW Experimental/testing PR, do NOT review it area-CodeGen-coreclr CLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI labels Aug 3, 2020
@ghost
Copy link

ghost commented Aug 3, 2020

Tagging subscribers to this area: @vitek-karas, @swaroop-sridhar, @agocke
See info in area-owners.md if you want to be subscribed.

@VSadov VSadov requested review from jkotas and vitek-karas August 3, 2020 19:49
@VSadov
Copy link
Member Author

VSadov commented Aug 3, 2020

I think this is ready to be reviewed.

@VSadov VSadov requested a review from janvorli August 3, 2020 20:28
@VSadov
Copy link
Member Author

VSadov commented Aug 3, 2020

cc:@agocke

Copy link
Member

Choose a reason for hiding this comment

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

We should not be leaving any pages mapped as RWX.

Copy link
Member Author

@VSadov VSadov Aug 4, 2020

Choose a reason for hiding this comment

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

I have seen this used in other cases.

MemAccessControl = PAGE_EXECUTE_READWRITE;

, so I assumed we may need to keep fidelity with what PE says - if it is RWX section then it should be mapped to RWX memory.

In reality, I think I have never seen RWX actually happening here. I think R2R code is always RX, perhaps intentionally.
I think for our purposes we could just handle RWX case as RX here.

Copy link
Member

Choose a reason for hiding this comment

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

The Windows PE loader ignores executable permissions for IL-only images. It will never map executable sections in IL images as executable, even if the PE file asks for it.

This was defense-in-depth security mitigation, implemented long time in .NET Framework days. It is probably not as important now compared to how important it used to be, but it would not hurt to keep it.

Copy link
Member Author

Choose a reason for hiding this comment

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

The memory must be executable so that we could execute code. It does not need to be writeable though. Not for R2R stuff.
I have changed this to PAGE_EXECUTE_READ for executable sections regardless of writeability.

Copy link
Member

Choose a reason for hiding this comment

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

Is this going to enable loading R2R images via e.g. Load(byte[]) ? I am not sure whether it is something we want to enable.

Copy link
Member Author

Choose a reason for hiding this comment

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

Is the concern that we would do redundant relocations or that the R2R code might be made to run via reflection?

Assuming that R2R code does the same thing as corresponding IL, I do not see problems with the latter. Perhaps even a good thing.

That is - if that actually works.
I did not think that Load(byte[]) might hit this codepath. I will have to check what really happens.

Copy link
Member Author

Choose a reason for hiding this comment

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

I checked Load(byte[]) scenario and it appears to not using this codepath. Load(byte[]) creates RawImageLayout and that does not come here.

Copy link
Member Author

@VSadov VSadov Aug 5, 2020

Choose a reason for hiding this comment

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

ConvertedImageLayout is used explicitly when loading from a Bundle.
There is also another codepath that could lead to creating ConvertedImageLayout. I am not sure if it is used and in what cases.

It should be possible to remember that the file was loaded form a bundle and perform the above just in those cases to be sure it does not enable more scenarios than needed.

Copy link
Member Author

Choose a reason for hiding this comment

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

Added m_isInBundle to ConvertedImageLayout - to make sure this does not get enabled in other cases.

Copy link
Member Author

@VSadov VSadov Aug 6, 2020

Choose a reason for hiding this comment

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

In theory it is possible that ConvertedImageLayout could be used for other purposes, but even if it happens it seems to be rare. I have made a trial change where creating ConvertedImageLayout not for a purpose of a file in a bundle would assert and throw, and the change passed all CI tests. (#40403)

Anyways, we now should be relocating only when ConvertedImageLayout was created for a file in a bundle. If the other scenarios are reachable, they will still retain previous behavior.

Copy link
Member

@jkotas jkotas left a comment

Choose a reason for hiding this comment

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

LGTM

@jkotas jkotas merged commit 9b2f548 into dotnet:master Aug 6, 2020
@VSadov
Copy link
Member Author

VSadov commented Aug 6, 2020

Thanks!!!

@VSadov VSadov deleted the winr2r branch August 6, 2020 22:01
Jacksondr5 pushed a commit to Jacksondr5/runtime that referenced this pull request Aug 10, 2020
* Keep executable PE sections executable in LayoutILOnly.

* Install unwind handlers if present

* do not do RtlAddFunctionTable on x86

* Check for Cor header before checking for R2R header.

* Delete function table in image dtor

* Avoid PAGE_EXECUTE_READWRITE, we should not need writeable for R2R

* Do relocations in ConvertedImageLayout only if the file is in a bundle. (otherwise R2R stays disabled)
@karelz karelz added this to the 5.0.0 milestone Aug 18, 2020
@ghost ghost locked as resolved and limited conversation to collaborators Dec 8, 2020
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants