Skip to content

Commit d277c1f

Browse files
committed
Translated the class memory layout scheme
1 parent b917173 commit d277c1f

File tree

2 files changed

+752
-1
lines changed

2 files changed

+752
-1
lines changed

jekyll/_posts/2018-03-12-steam-api-calls-forwarding.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -177,7 +177,7 @@ $
177177

178178
And here is what we need! Let's curtain the Gabe Newell's portraint, if you have one, and open `steamclient.so` in the IDA. A quick keyword search shows an interesting set of strings which follow the pattern: `CAdapterSteamClient0XX`, where XX is the version number. What is even more curious, in the file there are lines with pattern `CAdapterSteamYYYY0XX`, where XX is also the version number, and YYYY is the name of the Steam API class for all other interfaces. The analysis of cross-references allows to find a table of virtual methods for each of the classes with such names easily. Thus, the summary scheme for each class will look like this:
179179

180-
![](https://habrastorage.org/webt/hf/e4/4i/hfe44isvt4vsanajaro-oesru0k.png)
180+
<img src="{{site.baseurl}}/assets/news/images/winesteam/ClassLayoutEng.svg" alt="The class memory layout" style="width:100%"/>
181181

182182
The method table is found, but we have absolutely no information about the signatures of these methods. But this problem turned out to be [solvable](https://toster.ru/answer?answer_id=1156239)(the source in Russian) by calculating the maximum depth of the stack the method tries to access. So we can make an utility that will be receiving the `steamclient.so` library to the input, and forms a list of classes of all versions, as well as their methods at the output. It remains only to generate a wrapper code for the method calls conversion based on the list. The task does not look simple, especially considering that the method signature itself is not known to us, we know only the depth of the stack where the method call arguments end. The situation is aggravated by the peculiarities of the in-memory structures return, namely the presence of a hidden argument - pointer to the memory where the structure should be written. This pointer in all call conventions is extracted from the stack by the callee, so we can easily detect it by the `ret $4` instruction in the assembler code of methods in `steamclient.so`. But even so, the amount of non-trivial code generation is huge.
183183

0 commit comments

Comments
 (0)