2

From the demangled name, I know that a function takes an std::string const& as a parameter but when generating psuedo-c code with Hex-Rays' decompiler it autodetects the parameters as (int a1, int a2, int a3)

How can I fix the function signature Hex-Rays' is generating?

screenshot of IDA graph view

int __fastcall EncodeUtil::getDecryptStr(int a1, int a2, int a3)
{
  int v3; // r7
  unsigned int i; // r5
  char v5; // r6
  int v7; // [sp+4h] [bp-1Ch]
  int v8; // [sp+8h] [bp-18h]

  v7 = a2;
  v8 = a3;
  v3 = a1;
  HttpUtility::URLDecode(&v7);
  for ( i = 0; i < *(_DWORD *)(v7 - 12); ++i )
  {
    sub_3B25D0(&v7);
    v5 = byte_41A7DD[i & 7];
    *(_BYTE *)(v7 + i) ^= v5;
    sub_3B25D0(&v7);
    if ( !*(_BYTE *)(v7 + i) )
    {
      sub_3B25D0(&v7);
      *(_BYTE *)(v7 + i) ^= v5;
    }
  }
  sub_3B2E20(v3, &v7);
  sub_3B1CCC(&v7);
  return v3;
}
  • It looks like they have different calling conventions. – EWD-0- Jan 24 '18 at 10:27
  • 1
    @armnostrong: You should have specified that you are dealing with ARM targets... – perror Jan 24 '18 at 13:08
  • @armnotstrong: Do you know what compiler was used? The structure of an std::string is going to vary wildly based upon that – Avery3R Jan 25 '18 at 2:31
  • @Avery3R all I know is that this was a project of cocos2dx compiled for android device – armnotstrong Jan 25 '18 at 3:02
  • @perror sorry for the inconvenience – armnotstrong Jan 25 '18 at 3:02
1

It looks like hex-rays mistakenly thought there were three parameters instead of two. If you look at the start of the function's disassembly R1 and R2 are not saved, only R0 is. You should be able to just change the function signature to int __fastcall EncodeUtil::getDecryptStr(void* pString). The default key to do so is Y. If you have a struct definition for std::string you can replace the void* in the signature with an std::string*

  • 1
    FYI PUSH {R0-R2} saves R0, R1 and R2. – Igor Skochinsky Jan 25 '18 at 8:53
  • Ah yeah, I meant saved in another register to be used within this function later, like it did with MOV R7, R0. R1 and R2 are definitely used somewhere in this function later, but I'm willing to bet they're assigned to first before they're read from. – Avery3R Jan 25 '18 at 20:37

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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