Skip to content

How to emulate Expression.This() when using CompileToMethod #28774

Closed
@rikimaru0345

Description

@rikimaru0345

I'm using System.Linq.Expressions to implement formatters (serializers) for any type T.
At runtime everything works fine, but now I want to support IL2CPP (Unitys ahead-of-time compiler).
So I thought I'd just get a list of all types to be serialized in my serializer, and then compile those expressions using CompileToMethod and then saving them in an assembly.
That way - for IL2CPP - no code has to be compiled at runtime.

The issue is that the constants in the expression tree can't be saved, which is no surprise.
Each formatter (expression tree) has can have 0-N sub formatters that it uses to serialize the individual fields of its type. For example: A formatter IFormatter<Person> generated for class Person { public int Age; public string Name; } would itself contain IFormatter<int> and IFormatter<string> in order to serialize the two fields.

Ok, so it's obvious to me why this doesn't work.
So my idea now is to somehow replace the constants (the sub formatters) in the expression trees with fields!
So instead of genrating the two expressions (serialize and deserialize) of the IFormatter<Person> on their own, I would use DynamicType/TypeBuilder to generate a type that has fields for the needed formatters.
A Expression.Constant(stringFormatterInstance); I would generate something like Expression.MakeMemberAccess(???, stringFormatterField).

Now my problem is, there's no Expression.This() is there?
Also the LambdaCompiler seems to always want to include some sort of closure object. Maybe I can manually instantiate that somehow and use it as my "this"?

I'm a bit confused now regarding what my options are to actually solve this.
Maybe there's some other way to replace the constants when loading the generated assembly?
The solution obviously can't be anything that uses dynamic code generation, as the whole point is to have this run on an AOT platform.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions