-
Notifications
You must be signed in to change notification settings - Fork 516
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
[dotnet] Integrate class handle rewriting into static registrar process. #18456
Changes from 2 commits
441d4d4
4a395e2
4874456
5a88a52
8fd0b1b
f32876a
712115b
2442bdf
51a9207
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
This file was deleted.
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -78,6 +78,9 @@ | |
<Compile Include="..\..\tools\common\ObjCNameIndex.cs"> | ||
<Link>external\ObjCNameIndex.cs</Link> | ||
</Compile> | ||
<Compile Include="..\..\tools\common\Rewriter.cs"> | ||
<Link>external\ObjCNameIndex.cs</Link> | ||
</Compile> | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Not sure why you need this if it's not being implemented as an MSBuild task anymore? |
||
</ItemGroup> | ||
|
||
<ItemGroup> | ||
|
Original file line number | Diff line number | Diff line change | ||||||||
---|---|---|---|---|---|---|---|---|---|---|
|
@@ -8,7 +8,7 @@ | |||||||||
|
||||||||||
#nullable enable | ||||||||||
|
||||||||||
namespace Xamarin.MacDev.Tasks { | ||||||||||
namespace ClassRedirector { | ||||||||||
public class Rewriter { | ||||||||||
const string runtimeName = "ObjCRuntime.Runtime"; | ||||||||||
const string classHandleName = "ObjCRuntime.Runtime/ClassHandles"; | ||||||||||
|
@@ -18,18 +18,23 @@ public class Rewriter { | |||||||||
const string classPtrName = "class_ptr"; | ||||||||||
CSToObjCMap map; | ||||||||||
string pathToXamarinAssembly; | ||||||||||
string [] assembliesToPatch; | ||||||||||
string outputDirectory; | ||||||||||
SimpleAssemblyResolver resolver; | ||||||||||
string? outputDirectory = null; | ||||||||||
Dictionary<string, FieldDefinition> csTypeToFieldDef = new Dictionary<string, FieldDefinition> (); | ||||||||||
IEnumerable<AssemblyDefinition> assemblies; | ||||||||||
AssemblyDefinition xamarinAssembly; | ||||||||||
|
||||||||||
public Rewriter (CSToObjCMap map, string pathToXamarinAssembly, string [] assembliesToPatch, string outputDirectory) | ||||||||||
public Rewriter (CSToObjCMap map, IEnumerable<AssemblyDefinition> assembliesToPatch) | ||||||||||
{ | ||||||||||
this.map = map; | ||||||||||
this.pathToXamarinAssembly = pathToXamarinAssembly; | ||||||||||
this.assembliesToPatch = assembliesToPatch; | ||||||||||
this.outputDirectory = outputDirectory; | ||||||||||
resolver = new SimpleAssemblyResolver (assembliesToPatch); | ||||||||||
this.assemblies = assembliesToPatch; | ||||||||||
var xasm = assembliesToPatch.Select (assem => assem.MainModule).FirstOrDefault (ContainsNativeHandle)?.Assembly; | ||||||||||
if (xasm is null) { | ||||||||||
throw new Exception ("Unable to find Xamarin assembly."); | ||||||||||
} else { | ||||||||||
xamarinAssembly = xasm; | ||||||||||
pathToXamarinAssembly = xamarinAssembly.MainModule.FileName; | ||||||||||
} | ||||||||||
|
||||||||||
} | ||||||||||
|
||||||||||
public void Process () | ||||||||||
|
@@ -41,8 +46,7 @@ public void Process () | |||||||||
Dictionary<string, FieldDefinition> CreateClassHandles () | ||||||||||
{ | ||||||||||
var classMap = new Dictionary<string, FieldDefinition> (); | ||||||||||
using var assemblyStm = new FileStream (pathToXamarinAssembly, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite); | ||||||||||
using var module = ModuleDefinition.ReadModule (assemblyStm); | ||||||||||
var module = xamarinAssembly.MainModule; | ||||||||||
|
||||||||||
var classHandles = LocateClassHandles (module); | ||||||||||
if (classHandles is null) | ||||||||||
|
@@ -58,7 +62,7 @@ Dictionary<string, FieldDefinition> CreateClassHandles () | |||||||||
if (mtClassMapDef is null) | ||||||||||
throw new Exception ($"Unable to find {mtClassMapName} in {pathToXamarinAssembly}"); | ||||||||||
|
||||||||||
var nativeHandle = module.Types.FirstOrDefault (t => t.FullName == nativeHandleName); | ||||||||||
var nativeHandle = LocateNativeHandle (module); | ||||||||||
if (nativeHandle is null) | ||||||||||
throw new Exception ($"Unable to find {nativeHandleName} in {pathToXamarinAssembly}"); | ||||||||||
|
||||||||||
|
@@ -74,7 +78,7 @@ Dictionary<string, FieldDefinition> CreateClassHandles () | |||||||||
classMap [csName] = fieldDef; | ||||||||||
} | ||||||||||
|
||||||||||
module.Write (ToOutputFileName (pathToXamarinAssembly)); | ||||||||||
module.Write (); | ||||||||||
return classMap; | ||||||||||
} | ||||||||||
|
||||||||||
|
@@ -124,6 +128,16 @@ FieldDefinition AddPublicStaticField (TypeDefinition inType, string fieldName, T | |||||||||
return fieldDef; | ||||||||||
} | ||||||||||
|
||||||||||
bool ContainsNativeHandle (ModuleDefinition module) | ||||||||||
{ | ||||||||||
return LocateNativeHandle (module) is not null; | ||||||||||
} | ||||||||||
|
||||||||||
TypeDefinition? LocateNativeHandle (ModuleDefinition module) | ||||||||||
{ | ||||||||||
return AllTypes (module).FirstOrDefault (t => t.FullName == nativeHandleName); | ||||||||||
} | ||||||||||
|
||||||||||
TypeDefinition? LocateClassHandles (ModuleDefinition module) | ||||||||||
{ | ||||||||||
return AllTypes (module).FirstOrDefault (t => t.FullName == classHandleName); | ||||||||||
|
@@ -136,11 +150,10 @@ FieldDefinition AddPublicStaticField (TypeDefinition inType, string fieldName, T | |||||||||
|
||||||||||
void PatchClassPtrUsage (Dictionary<string, FieldDefinition> classMap) | ||||||||||
{ | ||||||||||
foreach (var path in assembliesToPatch) { | ||||||||||
using var stm = new FileStream (path, FileMode.Open, FileAccess.ReadWrite, FileShare.ReadWrite); | ||||||||||
using var module = ModuleDefinition.ReadModule (stm); | ||||||||||
foreach (var assem in assemblies) { | ||||||||||
var module = assem.MainModule; | ||||||||||
PatchClassPtrUsage (classMap, module); | ||||||||||
module.Write (ToOutputFileName (path)); | ||||||||||
module.Write (); | ||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Don't write out the assembly, the linker will do that later. However, it's important to tell the linker that the assembly was changed, and that's done by changing the action: xamarin-macios/tools/dotnet-linker/AppBundleRewriter.cs Lines 1092 to 1094 in cb34bfe
Note that you should only save the assembly if you actually modified 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.
You already added an optimization option here:
62634bd
can't that one be used instead of adding another one?