Skip to content

Memory Inspector Overview

Keltron3030 edited this page Mar 14, 2019 · 33 revisions

Here is an overview of the Memory Inspector and its features. This tool can be found on "RetroAchievements" tab on any emulator integrated with RA.

See also: Memory Digging Tips.

Memory Inspector Dialog

memoryinspector-num

1. Reset to

Click on one of these buttons to start a new test. For most things 8-bit test would be appropriate.

2. Filter Values

Usually filter for either = (equals to) last known value or != (different than) last known value. If you know the exact value you expect something to be, you can use Given Value, or if you're convinced that a value should have increased, you could try > (greater than) or < (less than).

3. Filter!

With every press of this button, you are filtering out values that do not match in memory between the last test and now.

4. Results window

memoryinspector-filter jpg

After filtering you'll see in the results window exactly what happened, how many values you've got and how many are left. Some points to note:

  • Search results show live value changes, so you can more easily identify usable addresses.
  • Search results are highlighted depending on their criteria. For addresses that don't fit the search filter, they will be highlighted in red. This can be disabled on the Highlights checkbox, if preferred.
  • You can also manually exclude any selected addresses from the search. Use Ctrl or Shift to multi-select.
  • Results History: You can move backwards (<<) or forwards (>>) through your previous filtered searches. Keep in mind if you start a new search (such as New 8-bit Test), your history will be cleared.

5. Watching

Any properly formed value in this area will be watched in the Memory Viewer and bound to the code notes on the right. You can highlight and then arrow up and down here to quickly cycle through noted addresses. The addresses must be 0x (that's zero, then letter x), followed by hexadecimal digits.

6. Memory Viewer

Any watched variable and the variables around it will be shown in this window. You can manually arrow up and down in the viewer to advance the address pane or expand the viewer field by dragging the window vertically to view more addresses at once. Additional info can be found below, in the Reading data in the Memory Viewer section.

7. Code Notes

Once you've found a memory address you want to make a note of, ensure the value is entered into the 'Watching' dropdown box. Next you can write a short description in the textbox next to it, and click Save Note. This will send the memory address and your description to the database, so it can be shared with all developers who work on this game.

Click the dropdown arrow to view what memory addresses have been found so far, and you will be shown the description in the box next to it, to tell you what this memory address is for.

Try and keep your descriptions simple and clear, so they can be easily understood. To rename a note, select it in the drop-down menu, update the description, and click Save Note. A dialog will prompt you to overwrite the existing note - check that it is a good change, and click OK.

If you wish to remove a note, select it in the dropdown menu, and click Remove.

8. Memory Bookmarks

When you click on the Open Memory Bookmarker button you'll see this dialog:

memoryinspector-bookmark jpg

With this, you can view multiple designated addresses at once instead of having to shuffle around in the Inspector.

The bookmarks can be renamed by double-clicking their description. If you double-click on the address, you can move straight to that point in the Mem Inspector.

Bookmarked addresses will show in the Memory Inspector as green. From here you can also Freeze any bookmarks.

This is helpful for things like health or consumables. Frozen values can be manipulated directly from the inspector. Keep in mind, freezing occurs 1 frame after gameplay. This means even when frozen, the value will change for atleast one frame before returning to the frozen value. These will always be displayed as yellow.

Reading data in the Memory Viewer

Decimal, Binary and Hexadecimal notations

To work well with the Memory Viewer, it's important to understand at least the basics of binary and hexadecimal numeral notations. Here are good sources of information about this matter without going into extreme details:

The digits used in binary system are 0 and 1. A binary digit is also known as bit. Eight bits is also known as one byte.

The digits used in hexadecimal system are 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, A, B, C, D, E and F. The hexadecimal notation is also known as hex.

The main reasons for the existence of these 2 notations, besides the traditional decimal notation, are:

  • Decimal notation is what humans understand.
  • Binary notation is what computers "understand".
  • Hexadecimal notation can be seen as a middle ground between binary and decimal. Because a single hexadecimal digit represents 4 bits, then a shorter and more understandable notation for humans to work in a way that the computer "understands".

The table below shows the different notations for equivalent values.

Decimal Hexadecimal Binary
0 0x0 0000
1 0x1 0001
2 0x2 0010
3 0x3 0011
4 0x4 0100
5 0x5 0101
6 0x6 0110
7 0x7 0111
8 0x8 1000
9 0x9 1001
10 0xA 1010
11 0xB 1011
12 0xC 1100
13 0xD 1101
14 0xE 1110
15 0xF 1111

More facts about the different number notations:

  • To indicate a value is written in hexadecimal, the prefix 0x is used: 0x10 = 16, 10 = 10.
  • Two hex digits represent 8 bits and can range from 0 to 255.
  • Four hex digits represent 16 bits and can range 0 to 65535.
  • Eight hex digits represent 32 bits and can range from 0to 4294967295.

Memory Viewer modes

The bottom part of the Memory Inspector is what we call the Memory Viewer:

memviewer

You can see data in Memory Viewer using 8, 16 or 32-bit modes.

8-bit mode

By default, the Memory Viewer shows data in 8-bit mode. This displays each byte of memory as a separate two-character hexadecimal value. And each byte has its own address.

Sixteen bytes are shown per line. The address of a byte can be determined by adding the row index (displayed to the left of the viewer) to the column index (displayed above the viewer). Using the image above as an example, the cursor is at 0x002a7 (0x002a0 + 7).

16/32-bit mode

Before we talk about 16-bit mode and 32-bit mode, it's important to know about endianness:

Endianness

Endianness describes the order in which a sequence of bytes are stored in computer systems memory. The two most common types are: Big-Endian (also known as BE) and Little-Endian (also known as LE).

In the Big-Endian order the "big end" of the number (most significant value in the sequence) is stored first (placed at the lowest address). In the image below you see the number 0x12345678 stored at the address 0x100 in the big-endian order. Notice that the most significant byte 0x12 is at the address 0x100:

bigendian

In the Little-Endian order the "little end" of the number (least significant value in the sequence) is stored first. In the image below you see the number 0x12345678 stored at the address 0x100 in the little-endian order. Notice that the least significant byte 0x78 is at the address 0x100:

littleendian

Values that need more then 8-bits (in other words: larger than 255) have to be stored in multiple bytes. However, the emulated systems we use store multi-byte values in little-endian order.

In the image of the Memory Viewer above you can see that at address 0x0002c0 we have the hex value ce and in 0x0002c1 the value is 39. When you switch the viewer to 16-bit mode, the ce and 39 values are grouped at 0x0002c0 and get displayed as 39ce. This happens because it automatically groups every two bytes and displays them as 16-bit hex values.

NOTE: While 16-bit values are usually aligned to even addresses, that's not always the case. There's actually a non-displayed 16-bit value at 0x0002c1. Since the value at 0x0002c1 is 39 and the value at 0x0002c2 is 29, the 16-bit value at 0x0002c1 address is 0x2939.

Similarly, in 32-bit mode, the four bytes from 0x0002c0 to 0x0002c3 are displayed as a single 32-bit value 0x252939ce at address 0x0002c0, but there are also 32-bit values at 0x0002c1, 0x0002c2, and 0x0002c3.

Working with sizes smaller than 8-bit

In addition to the 8-bit, 16-bit and 32-bit sizes described above, there are additional sizes that can be used when writing achievements (in the Achievement Editor).

Single bits

In the memory viewer when an 8-bit address is selected you will see something like the image below (in the image: a byte with the value 6f is selected; the bits are highlighted with an orange circle):

bitfields

It is very common in games to store important information as a single bit. As a bit can only have two possible values (1 or 0), sometimes it's used to mean "yes" or "no", "on" or "off", "have item" or "no item", etc. Some games, specially those with limited memory space, use bit switches a lot.

Important: You can refer to each one of those bits individually in the Achievement Editor.

Common meaning of bit switches in a game memory:

  • have an item
  • button pressed (very common)
  • area explored
  • in game trigger activated
  • cheat activated
  • in demo mode

In the memory viewer you can only input hex values, then it's important to know equivalence of values between hex and binary notations. You can see the table in the "Decimal, Binary and Hexadecimal notations" section, but the usual is to use a calculator (the default calculator on MS Windows on the programmer view can do the job).

Upper4 and Lower4

Upper4 is the upper four bits of a byte (bit: 7, 6, 5, 4), displayed as a single hexadecimal character. Lower4 is the lower four bits of a byte (bit: 3, 2, 1, 0), displayed as a single hexadecimal character.

Looking at the memory size diagram below, a byte at address 0x00a274 is selected (value 0x23). The first character, 2 is the Upper4 value. The second character 3 is the Lower4 value.

Occasionally you will only be interested working with a single hexadecimal digit. Using the memory size diagram as an example, an achievement condition where Upper4 0x00a274 = 0x2 would be true. A condition where Lower4 0x00a274 = 0x3 would be true.

Memory Sizes diagram

memsizes

Wiki Home Page

General

Developers


Portugues

Geral

Desenvolvedores


Español

General

Desarrolladores

Clone this wiki locally
You can’t perform that action at this time.
You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.