NAME=afvt args
FILE=bins/elf/ls
CMDS=<<EOF
s main
af
afvt argc
afvt argv
afvt argc int64_t
afvt argc
EOF
EXPECT=<<EOF
int
char **
int64_t
EOF
RUN

NAME=pdf
FILE=bins/elf/ls
CMDS=<<EOF
s main
af
afv
afvj~{}
EOF
EXPECT=<<EOF
arg int argc @ rdi
arg char ** argv @ rsi
var int64_t var_8h @ rsp+0x18
var int64_t var_17h @ rsp+0x27
var int64_t var_18h @ rsp+0x28
var int64_t var_28h @ rsp+0x38
var int64_t var_30h @ rsp+0x40
var int64_t var_32h @ rsp+0x42
var int64_t var_38h @ rsp+0x48
var int64_t var_45h @ rsp+0x55
var int64_t var_46h @ rsp+0x56
var int64_t var_47h @ rsp+0x57
var int64_t var_48h @ rsp+0x58
{
  "reg": [
    {
      "name": "argc",
      "kind": "reg",
      "type": "int",
      "ref": "rdi"
    },
    {
      "name": "argv",
      "kind": "reg",
      "type": "char **",
      "ref": "rsi"
    }
  ],
  "sp": [
    {
      "name": "var_8h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 24
      }
    },
    {
      "name": "var_17h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 39
      }
    },
    {
      "name": "var_18h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 40
      }
    },
    {
      "name": "var_28h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 56
      }
    },
    {
      "name": "var_30h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 64
      }
    },
    {
      "name": "var_32h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 66
      }
    },
    {
      "name": "var_38h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 72
      }
    },
    {
      "name": "var_45h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 85
      }
    },
    {
      "name": "var_46h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 86
      }
    },
    {
      "name": "var_47h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 87
      }
    },
    {
      "name": "var_48h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rsp",
        "offset": 88
      }
    }
  ],
  "bp": [
    
  ]
}
EOF
RUN

NAME=pdf
FILE=bins/elf/test_o
CMDS=<<EOF
e asm.var.summary=0
af
pdf
afv
afvj~{}
EOF
EXPECT=<<EOF
            ;-- section..text:
/ 22: sym.sub (int64_t arg1, int64_t arg2);
|           ; arg int64_t arg1 @ rdi
|           ; arg int64_t arg2 @ rsi
|           ; var int64_t var_4h @ rbp-0x4
|           ; var int64_t var_8h @ rbp-0x8
|           0x08000040      f30f1efa       endbr64                     ; [01] -r-x section size 22 named .text
|           0x08000044      55             push rbp
|           0x08000045      4889e5         mov rbp, rsp
|           0x08000048      897dfc         mov dword [var_4h], edi     ; arg1
|           0x0800004b      8975f8         mov dword [var_8h], esi     ; arg2
|           0x0800004e      8b45fc         mov eax, dword [var_4h]
|           0x08000051      2b45f8         sub eax, dword [var_8h]
|           0x08000054      5d             pop rbp
\           0x08000055      c3             ret
arg int64_t arg1 @ rdi
arg int64_t arg2 @ rsi
var int64_t var_4h @ rbp-0x4
var int64_t var_8h @ rbp-0x8
{
  "reg": [
    {
      "name": "arg1",
      "kind": "reg",
      "type": "int64_t",
      "ref": "rdi"
    },
    {
      "name": "arg2",
      "kind": "reg",
      "type": "int64_t",
      "ref": "rsi"
    }
  ],
  "sp": [
    
  ],
  "bp": [
    {
      "name": "var_4h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rbp",
        "offset": -4
      }
    },
    {
      "name": "var_8h",
      "kind": "var",
      "type": "int64_t",
      "ref": {
        "base": "rbp",
        "offset": -8
      }
    }
  ]
}
EOF
RUN

NAME=afvx
FILE=bins/elf/ls.odd
CMDS=<<EOF
af
afvx
afv=
EOF
EXPECT=<<EOF
afvR
      arg3  0x5312
afvW
      arg3
* arg3
R 0x5312  mov r9, rdx
EOF
RUN

NAME=afvx2
FILE=bins/mach0/mac-ls
CMDS=<<EOF
af
afvx
afv=
EOF
EXPECT=<<EOF
afvR
      argv  0x10000106c
      argc  0x10000106f
  var_640h  0x100001072
  var_648h  0x100001617,0x100001691
  var_654h  0x100001784
  var_650h  0x10000173c,0x100001807,0x10000181c
  var_64ch  0x100001736,0x1000017dd,0x1000017f2
  var_658h  0x1000017d4
  var_660h  0x1000018f1
  var_664h  0x10000190b
  var_670h  0x100001911
   var_34h  0x10000179e
  var_440h  0x1000015f8
   var_30h  0x1000010d6
   var_2eh  0x1000010f0
afvW
      argv
      argc
  var_640h
  var_648h  0x100001079
  var_654h  0x100001137,0x100001315
  var_650h  0x10000114c,0x1000014f2
  var_64ch  0x100001156,0x1000012d8
  var_658h  0x100001160,0x1000014ce
  var_660h  0x100001597
  var_664h  0x1000015a3
  var_670h  0x1000015ad
   var_34h
  var_440h
   var_30h
   var_2eh
* argv
R 0x10000106c  mov rbx, rsi
* argc
R 0x10000106f  mov r14d, edi
* var_640h
R 0x100001072  lea rax, [var_640h]
* var_648h
R 0x100001617  lea rbx, [var_648h]
R 0x100001691  lea rsi, [var_648h]
W 0x100001079  mov qword [var_648h], rax
* var_654h
R 0x100001784  cmp dword [var_654h], 0
W 0x100001137  mov dword [var_654h], 0
W 0x100001315  mov dword [var_654h], 1
* var_650h
R 0x10000173c  or ebx, dword [var_650h]
R 0x100001807  cmp dword [var_650h], 0
R 0x10000181c  cmp dword [var_650h], 0
W 0x10000114c  mov dword [var_650h], 0
W 0x1000014f2  mov dword [var_650h], 1
* var_64ch
R 0x100001736  mov ebx, dword [var_64ch]
R 0x1000017dd  cmp dword [var_64ch], 0
R 0x1000017f2  cmp dword [var_64ch], 0
W 0x100001156  mov dword [var_64ch], 0
W 0x1000012d8  mov dword [var_64ch], 1
* var_658h
R 0x1000017d4  cmp dword [var_658h], 0
W 0x100001160  mov dword [var_658h], 0
W 0x1000014ce  mov dword [var_658h], 1
* var_660h
R 0x1000018f1  mov rax, qword [var_660h]
W 0x100001597  mov qword [var_660h], rcx
* var_664h
R 0x10000190b  mov edi, dword [var_664h]
W 0x1000015a3  mov dword [var_664h], eax
* var_670h
R 0x100001911  mov rsi, qword [var_670h]
W 0x1000015ad  mov qword [var_670h], rax
* var_34h
R 0x10000179e  lea rdi, [var_34h]
* var_440h
R 0x1000015f8  lea rdi, [var_440h]
* var_30h
R 0x1000010d6  lea rdx, [var_30h]
* var_2eh
R 0x1000010f0  movzx eax, word [var_2eh]
EOF
RUN

NAME=Detect register args used only by callee
FILE=-
CMDS=<<EOF
e asm.arch=x86
e asm.bits=64
e anal.cc=ms
wx 40534883ec20418bd8e80a00000003c34883c4205bc3cccc2bca8bc1c3
aa
pd 13
EOF
EXPECT=<<EOF
/ 22: fcn.00000000 (int64_t arg1, int64_t arg2, int64_t arg3);
| `- args(rcx, rdx, r8)
|           0x00000000      4053           push rbx
|           0x00000002      4883ec20       sub rsp, 0x20
|           0x00000006      418bd8         mov ebx, r8d                ; arg3
|           0x00000009      e80a000000     call fcn.00000018
|           0x0000000e      03c3           add eax, ebx
|           0x00000010      4883c420       add rsp, 0x20
|           0x00000014      5b             pop rbx
\           0x00000015      c3             ret
            0x00000016      cc             int3
            0x00000017      cc             int3
            ; CALL XREF from fcn.00000000 @ 0x9(x)
/ 5: fcn.00000018 (int64_t arg1, int64_t arg2);
| `- args(rcx, rdx)
|           0x00000018      2bca           sub ecx, edx                ; arg2
|           0x0000001a      8bc1           mov eax, ecx                ; arg1
\           0x0000001c      c3             ret
EOF
RUN

NAME=Detect register args type used only by callees
FILE=bins/pe/rarg_detection.dll
CMDS=<<EOF
s sym.rarg_detection.dll_funcB
af
s sym.rarg_detection.dll_funcC
af
afv
EOF
EXPECT=<<EOF
arg const char * s @ rcx
arg int64_t arg2 @ rdx
arg int64_t arg3 @ r8
EOF
RUN

NAME=Variables in register save stack area
FILE=bins/pe/testx64.exe
CMDS=<<EOF
s 0x14000184c
af
afv
EOF
EXPECT=<<EOF
var int64_t var_20h @ rsp+0x48
var int64_t var_bp_20h @ rbp+0x20
var int64_t var_18h @ rbp+0x18
var int64_t var_10h @ rbp+0x10
EOF
RUN

NAME=Variable access with misc registers (x86) R2_590 - calling conventions ignored for now
FILE=-
ARGS=-a x86 -b 64
CMDS=<<EOF
e asm.flags=false
e anal.vars.stackname = true
e anal.cc=ms
wx 488bc448895808488970104889781841574881ecb00000008364242000488d48884c8d9c24b0000000498b5b10498b7318498b7b20498be3415fc3
af
aaef
afvx
pdf
EOF
EXPECT=<<EOF
afvR
   var_c0h  0x18
   var_30h  0x21
   var_28h
   var_20h  0x29
   var_18h  0x2d
   var_10h  0x31
   var_a0h
afvW
   var_c0h  0x18
   var_30h
   var_28h
   var_20h  0x3
   var_18h  0x7
   var_10h  0xb
   var_a0h
/ 59: fcn.00000000 ();
|           ; var int64_t var_c0h @ rsp+0x20
|           ; var int64_t var_a0h @ rsp+0x40
|           ; var int64_t var_30h @ rsp+0xb0
|           ; var int64_t var_28h @ rsp+0xb8
|           ; var int64_t var_20h @ rsp+0xc0
|           ; var int64_t var_18h @ rsp+0xc8
|           ; var int64_t var_10h @ rsp+0xd0
|           0x00000000      488bc4         mov rax, var_28h
|           0x00000003      48895808       mov qword [var_20h], rbx
|           0x00000007      48897010       mov qword [var_18h], rsi
|           0x0000000b      48897818       mov qword [var_10h], rdi
|           0x0000000f      4157           push r15
|           0x00000011      4881ecb00000.  sub rsp, 0xb0
|           0x00000018      8364242000     and dword [var_c0h], 0
|           0x0000001d      488d4888       lea rcx, [var_a0h]
|           0x00000021      4c8d9c24b000.  lea r11, [var_30h]
|           0x00000029      498b5b10       mov rbx, qword [var_20h]
|           0x0000002d      498b7318       mov rsi, qword [var_18h]
|           0x00000031      498b7b20       mov rdi, qword [var_10h]
|           0x00000035      498be3         mov rsp, var_30h
|           0x00000038      415f           pop r15
\           0x0000003a      c3             ret
EOF
BROKEN=1
RUN


NAME=Variable access with misc registers (ARM)
FILE=-
ARGS=-a arm -b 16
CMDS=<<EOF
e asm.var.summary=0
e asm.flags=false
e asm.comments=false
e anal.vars.stackname = true
aeim
wx 80b483b000af78600b467b8013467b707b78002b03d07a887b689a6103e07b881a047b689a6100bf0c37bd465df8047b7047
af
aaef
afvx
pdf
EOF
EXPECT=<<EOF
afvR
      arg1  0x6
      arg2  0x8
      arg3  0xc
   var_10h  0x4,0x2c
    var_ch  0x18,0x22
    var_eh  0x16,0x1e
    var_fh  0x10
    var_4h  0x2c
afvW
      arg1
      arg2
      arg3
   var_10h
    var_ch  0x6
    var_eh  0xa
    var_fh  0xe
    var_4h
/ 50: fcn.00000000 (int16_t arg1, int16_t arg2, int16_t arg3);
|           ; arg int16_t arg1 @ r0
|           ; arg int16_t arg2 @ r1
|           ; arg int16_t arg3 @ r2
|           ; var int16_t var_10h @ sp+0x0
|           ; var int8_t var_fh @ sp+0x1
|           ; var int16_t var_eh @ sp+0x2
|           ; var int32_t var_ch @ sp+0x4
|           ; var int16_t var_4h @ sp+0xc
|           0x00000000      80b4           push {r7}
|           0x00000002      83b0           sub sp, 0xc
|           0x00000004      00af           add r7, var_10h
|           0x00000006      7860           str r0, [r7, 4]
|           0x00000008      0b46           mov r3, r1
|           0x0000000a      7b80           strh r3, [r7, 2]
|           0x0000000c      1346           mov r3, r2
|           0x0000000e      7b70           strb r3, [r7, 1]
|           0x00000010      7b78           ldrb r3, [r7, 1]
|           0x00000012      002b           cmp r3, 0
|       ,=< 0x00000014      03d0           beq 0x1e
|       |   0x00000016      7a88           ldrh r2, [r7, 2]
|       |   0x00000018      7b68           ldr r3, [r7, 4]
|       |   0x0000001a      9a61           str r2, [r3, 0x18]
|      ,==< 0x0000001c      03e0           b 0x26
|      |`-> 0x0000001e      7b88           ldrh r3, [r7, 2]
|      |    0x00000020      1a04           lsls r2, r3, 0x10
|      |    0x00000022      7b68           ldr r3, [r7, 4]
|      |    0x00000024      9a61           str r2, [r3, 0x18]
|      `--> 0x00000026      00bf           nop
|           0x00000028      0c37           adds r7, 0xc
|           0x0000002a      bd46           mov sp, r7
|           0x0000002c      5df8047b       ldr r7, [sp], 4
\           0x00000030      7047           bx lr
EOF
RUN

NAME=Takeover variables
FILE=-
ARGS=-a x86 -b 32
CMDS=<<EOF
wx e805000000e80600000039d1742577145589e583ec048b5d088b4d0c895dfc83f90174098b45fc8945fc49ebf28b45fc89ec5dc3
aac
afv  @ 10
afvx @ 10
afv  @ 16
afvx @ 16
EOF
EXPECT=<<EOF
afvR
afvW
arg int32_t arg_8h @ ebp+0x8
arg int32_t arg_ch @ ebp+0xc
var int32_t var_4h @ ebp+0x0
var int32_t var_4h_2 @ ebp-0x4
afvR
    arg_8h  0x16
    arg_ch  0x19
  var_4h_2
    var_4h  0x24,0x2d
afvW
    arg_8h
    arg_ch
  var_4h_2  0x1c
    var_4h  0x27
EOF
RUN


NAME=Stack Variables
FILE=-
ARGS=-a arm -b 16
CMDS=<<EOF
e asm.var.summary=0
e anal.vars.newstack=true
wx 2de9f04fadf54e4da5b088460df1900a0021aaf18007802281463846fff7e0ee4bf2640400214ff448420df5d260fff7d8eec0f2000400214ff48062a4a8fff7
af
afv-arg_690h
afvs 0x690 config char *
pd 1
?e ...
pd 1 @..2a
EOF
EXPECT=<<EOF
/ 66: fcn.00000000 (int16_t arg1, int16_t arg2, int16_t arg_290h, char *config);
|           ; arg int16_t arg1 @ r0
|           ; arg int16_t arg2 @ r1
|           ; arg int16_t arg_290h @ sp+0x290
|           ; arg char *config @ sp+0x748
|           ; var int16_t var_90h @ sp+0x90
|           0x00000000      2de9f04f       push.w {r4, r5, r6, r7, r8, sb, sl, fp, lr}
...
|           0x0000002a      0df5d260       add.w r0, config
EOF
RUN

NAME=arm64 stack variables
FILE=bins/mach0/arm_snippet_1
CMDS=<<EOF
e asm.var.summary=0
e asm.sub.var=true
af
pdf
e asm.sub.var=false
pdf
EOF
EXPECT=<<EOF
            ;-- section.0.__TEXT.__text:
            ;-- entry0:
            ;-- func.100003f64:
/ 68: int main (int argc, char **argv, char **envp);
|           ; arg int argc @ x0
|           ; arg char **argv @ x1
|           ; arg int64_t envp @ sp+0x20
|           ; var int64_t var_8h @ sp+0x8
|           ; var int64_t var_ch @ sp+0xc
|           0x100003f64      ff4300d1       sub sp, sp, 0x10           ; [00] -r-x section size 68 named 0.__TEXT.__text
|           0x100003f68      ff0f00b9       str wzr, [var_ch]          ; argc
|           0x100003f6c      e00b00b9       str w0, [var_8h]           ; argc
|           0x100003f70      e10300f9       str x1, [sp]               ; argv
|           0x100003f74      e80b40b9       ldr w8, [var_8h]
|           0x100003f78      08090071       subs w8, w8, 2
|           0x100003f7c      e8179f1a       cset w8, eq
|       ,=< 0x100003f80      a8000037       tbnz w8, 0, 0x100003f94
|      ,==< 0x100003f84      01000014       b 0x100003f88
|      ||   ; CODE XREF from main @ 0x100003f84(x)
|      `--> 0x100003f88      28008052       mov w8, 1
|       |   0x100003f8c      e80f00b9       str w8, [var_ch]
|      ,==< 0x100003f90      03000014       b 0x100003f9c
|      |`-> 0x100003f94      ff0f00b9       str wzr, [var_ch]          ; argc
|      |,=< 0x100003f98      01000014       b 0x100003f9c
|      ||   ; CODE XREFS from main @ 0x100003f90(x), 0x100003f98(x)
|      ``-> 0x100003f9c      e00f40b9       ldr w0, [var_ch]
|           0x100003fa0      ff430091       add sp, sp, 0x10
\           0x100003fa4      c0035fd6       ret
            ;-- section.0.__TEXT.__text:
            ;-- entry0:
            ;-- func.100003f64:
/ 68: int main (int argc, char **argv, char **envp);
|           ; arg int argc @ x0
|           ; arg char **argv @ x1
|           ; arg int64_t envp @ sp+0x20
|           ; var int64_t var_8h @ sp+0x8
|           ; var int64_t var_ch @ sp+0xc
|           0x100003f64      ff4300d1       sub sp, sp, 0x10           ; [00] -r-x section size 68 named 0.__TEXT.__text
|           0x100003f68      ff0f00b9       str wzr, [sp, 0xc]         ; argc
|           0x100003f6c      e00b00b9       str w0, [sp, 8]            ; argc
|           0x100003f70      e10300f9       str x1, [sp]               ; argv
|           0x100003f74      e80b40b9       ldr w8, [sp, 8]
|           0x100003f78      08090071       subs w8, w8, 2
|           0x100003f7c      e8179f1a       cset w8, eq
|       ,=< 0x100003f80      a8000037       tbnz w8, 0, 0x100003f94
|      ,==< 0x100003f84      01000014       b 0x100003f88
|      ||   ; CODE XREF from main @ 0x100003f84(x)
|      `--> 0x100003f88      28008052       mov w8, 1
|       |   0x100003f8c      e80f00b9       str w8, [sp, 0xc]
|      ,==< 0x100003f90      03000014       b 0x100003f9c
|      |`-> 0x100003f94      ff0f00b9       str wzr, [sp, 0xc]         ; argc
|      |,=< 0x100003f98      01000014       b 0x100003f9c
|      ||   ; CODE XREFS from main @ 0x100003f90(x), 0x100003f98(x)
|      ``-> 0x100003f9c      e00f40b9       ldr w0, [sp, 0xc]
|           0x100003fa0      ff430091       add sp, sp, 0x10
\           0x100003fa4      c0035fd6       ret
EOF
RUN
