2

I have following code disassembled by ghidra:

PUSH      EBX
PUSH      dword ptr [EBP + param_1]             wchar_t * _Format for swprintf
PUSH      u_%s\%s_0040eb88                      size_t _Count for swprintf
PUSH      dword ptr [EBP + param_3]             wchar_t * _String for swprintf
CALL      dword ptr [->MSVCRT.DLL::swprintf]

The 2nd parameter is unicode string %s\%s, but it should be size_t parameter, because swprintf function requires count parameter

This is another code which uses the same function:

LEA       EAX=>local_4dc,[0xfffffb28 + EBP]
PUSH      EAX                                        wchar_t * _Format for swprintf
LEA       EAX=>windowsDir,[0xfffffd30 + EBP]
PUSH      _Count_0040f40c                            size_t _Count for swprintf
PUSH      EAX                                        wchar_t * _String for swprintf
CALL      EDI=>MSVCRT.DLL::swprintf

Again, _Count_0040f40c is unicode string %/Program Data detected as _Count

Ghidra has correct function signature:

int swprintf (wchar_t * _String, size_t _Count, wchar_t * _Format, ...)

Normal count parameter is always missing, what Ghidra detects doesn't refer to number type variable. It looks like if all functions were compiled without it. All those memory variables ghidra detects as count parameters are actually format parameters. If there was actual count parameter every time swprintf was called, everything would be looking good.

2
  • Are you sure that the actually called function is swprintf? Maybe Ghidra got this wrong, and the actually called function is sprintf or similar? Dec 19, 2019 at 8:31
  • no, this is swprintf, I checked it with ht disassembler
    – M. Kalter
    Dec 19, 2019 at 11:49

1 Answer 1

1

It seems the picked prototype is incorrect. The original version of swprintf does not have the count parameter. From the VS 9.0 (2008) CRT sources:

#ifndef _COUNT_

int __cdecl _swprintf (
        wchar_t *string,
        const wchar_t *format,
        ...
        )
#else  /* _COUNT_ */

#ifndef _SWPRINTFS_ERROR_RETURN_FIX
/* Here we implement _snwprintf without the
return value bugfix */

int __cdecl _snwprintf (
        wchar_t *string,
        size_t count,
        const wchar_t *format,
        ...
        )
#else  /* _SWPRINTFS_ERROR_RETURN_FIX */
int __cdecl _swprintf_c (
        wchar_t *string,
        size_t count,
        const wchar_t *format,
        ...
        )
#endif  /* _SWPRINTFS_ERROR_RETURN_FIX */
4

Your Answer

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

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