3

When reversing Unity dll, the decompiler (i.e. dnSpy) sometimes would create a class with 2 constructors, which are mostly identical apart from some specific field set / not set.

Here is an example:

public TurretShootOrder(IGalaxyTarget target, string sectionName, GalaxyWeaponDefinition galaxyWeaponDefinition, float startShootTime, Vector3 startRandomDispersion, float startImpactTime, float endShootTime, Vector3 endRandomDispersion, float endImpactTime, int shootCount, float missProportion, int flags = 0, int salvoId = 0, int salvoTotalShootCount = 0, int inSalvoFirstShootIndex = 0)
{


    this.target = target;
    this.sectionName = sectionName;

AND:

public TurretShootOrder(IGalaxyTarget target, IGalaxyModuleSection targetSection, GalaxyWeaponDefinition galaxyWeaponDefinition, float startShootTime, Vector3 startRandomDispersion, float startImpactTime, float endShootTime, Vector3 endRandomDispersion, float endImpactTime, int shootCount, float missProportion, int flags = 0, int salvoId = 0, int salvoTotalShootCount = 0, int inSalvoFirstShootIndex = 0)
{
    this.target = target;
    this.sectionName = string.Empty;

As you can see the second implementation doesn't set the sectionName on initialization. Otherwise these constructors are identical.

So, how do I combine these 2 constructors together?

8
  • 1
    What do you mean, "how do you combine them together"? "Combining" functions, regardless of whether they are identical or not, is not generally something that a decompiler does. Mar 20, 2023 at 15:19
  • It is common in OO-languages to have classes with multiple constructors. So there is no need to "combine" them.
    – Robert
    Mar 20, 2023 at 15:43
  • @RolfRolles Well, these are 2 constructors for the same class. As you can see from the names. They are not functions, so I can't simply rename one of them. I am not aware of any technique to "overload" constructors either. Since the question. I mean, I don't need necessarily "combine" them in a sense replacing both of them with a generic constuctor containing both definitions, but my question is really what do I do in this case - split the class in to 2? Any other solutions?
    – Irbis77
    Mar 20, 2023 at 17:59
  • @Robert Hmm, if I keep both of them, then I get: "The call is ambiguous between the following methods or properties... " during the compilation. And as I said I can't rename one of them since it is a constructor. So, just wonder how I initialise this class now.
    – Irbis77
    Mar 20, 2023 at 18:03
  • 1
    The issue comes from the fact that the compiler doesn't know what type the null is in the second parameter: it could either be IGalaxyModuleSection or string. C# is not my forte, but in C++, I would resolve this by putting a cast on the null parameter, like (IGalaxyModuleSection*)nullptr. I don't know if the same trick would work in C#. Mar 20, 2023 at 19:01

1 Answer 1

1

Based on the discussion in comments and further investigation, when the class is instantiated like this:

 TurretShootOrder turretShootOrder2 = new TurretShootOrder(firstFakeTarget, null, ....

then it is neccessary to decide, which type the second parameter has in this case. Is it String or IGalaxyModuleSection?

In the above example according to C# rules it can't be a String. As then it won't be equal to null, but to "" (Empty.String). Which points to the type of that second parameter, which in this case is IGalaxyModuleSection.

Thus, there is a missing variable introduction in the code where the class got instantiated. So, the (simplified) solution could look like this:

 IGalaxyModuleSection targetSection = null;
     TurretShootOrder turretShootOrder2 = new TurretShootOrder(firstFakeTarget, targetSection, .
1
  • Please mark your answer as accepted. Mar 20, 2023 at 20:44

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.