Я пытаюсь интерпретировать инструкцию CIL по инструкции. Я использую Mono.Reflection для получения списка инструкций и Я не знаю, как интерпретировать 'ldarga.s' .
Я знаю "ldarga" - Загрузить адрес аргумента в стеке оценки. " но что такое аргумент / индекс 'ldarga.s', т.е. load / pu sh в стеке? - инструкция под IL_0004 следующая список ассемблеров.
другая инструкция "ldarg.0" (без "a") argumet load / pu sh "first" в стеке, "ldarg.1" argumet load / pu sh secound в стеке В другом примере «ldloca.s» - «Загружает адрес локальной переменной по указанному индексу в стек оценки.») индекс находится в операнде инструкции.
Вот мой код I иметь функцию "Funkcja1" в классе Test
public int Funkcja1(int p1, string p2, ProcesTest p3)
{
var zmienalokaln1 = p1;
var zmiennaLokaln2 = p2 + p1.ToString();
Metoda1();
var zmienna3 = zmienalokaln1 + zmiennaLokaln2;
return zmienna + p1 + p2.Length + zmienna3.Length;
}
Функция-ассемблер (генерируется JetBrains dotPeek):
.method public hidebysig instance int32
Funkcja1(
int32 p1,
string p2,
class Cvl.VirtualMachine.Test.ProcesTest p3
) cil managed
{
.maxstack 2
.locals init (
[0] int32 zmienalokaln1,
[1] string zmiennaLokaln2,
[2] string zmienna3,
[3] int32 V_3
)
// [18 9 - 18 10]
IL_0000: nop
// [19 13 - 19 36]
IL_0001: ldarg.1 // p1
IL_0002: stloc.0 // zmienalokaln1
// [20 13 - 20 53]
IL_0003: ldarg.2 // p2
IL_0004: ldarga.s p1
IL_0006: call instance string [System.Runtime]System.Int32::ToString()
IL_000b: call string [System.Runtime]System.String::Concat(string, string)
IL_0010: stloc.1 // zmiennaLokaln2
// [22 13 - 22 23]
IL_0011: ldarg.0 // this
IL_0012: call instance void Cvl.VirtualMachine.Test.ProcesTest::Metoda1()
IL_0017: nop
// [24 13 - 24 59]
IL_0018: ldloca.s zmienalokaln1
IL_001a: call instance string [System.Runtime]System.Int32::ToString()
IL_001f: ldloc.1 // zmiennaLokaln2
IL_0020: call string [System.Runtime]System.String::Concat(string, string)
IL_0025: stloc.2 // zmienna3
// [26 13 - 26 63]
IL_0026: ldarg.0 // this
IL_0027: ldfld int32 Cvl.VirtualMachine.Test.ProcesTest::zmienna
IL_002c: ldarg.1 // p1
IL_002d: add
IL_002e: ldarg.2 // p2
IL_002f: callvirt instance int32 [System.Runtime]System.String::get_Length()
IL_0034: add
IL_0035: ldloc.2 // zmienna3
IL_0036: callvirt instance int32 [System.Runtime]System.String::get_Length()
IL_003b: add
IL_003c: stloc.3 // V_3
IL_003d: br.s IL_003f
// [27 9 - 27 10]
IL_003f: ldloc.3 // V_3
IL_0040: ret
} // end of method ProcesTest::Funkcja1
Из Mono.Reflection.Disassembler.GetInstructions (это собственная методика BaseBase)
![instruction ldarga](https://i.stack.imgur.com/UepdN.png)
Операнд 'p1' ![instrustion ldarga watch](https://i.stack.imgur.com/fHukQ.png)
Мне нужно как-то указать индекс этого параметра ('p1') в списке параметров функции, который в этом случае равен 0 (первый параметр)