Brian Lam


Software Engineer

Crackme Solution 3 - NoREpls 1.1

For today’s crackme, we will be attempting yet another one by dtm of 0x00sec. We will again be helping poor edgyReggie with ensuring that his crackme is safe from reverse engineering after cracking his first program. He thinks he has the solution to stop reverse engineering and he also invalidated the old serial number. Let’s prove him wrong again 🙂 The link to this crackme — er I mean software can be found here. Jeez. I keep getting these two mixed up… 😦 As always, I will be mirroring the link in case the link dies. It can be found here.

We already have some experience with this software from our previous attempt to crack it found here and can make the following assumptions:

  1. It is still written in C.
  2. It still has IsDebuggerPresent which is used to detect debuggers.
  3. The previous key was invalidated as mentioned in the new crackme.
  4. The invalid serial number String is still found in aInvalidSerialN.

With these assumptions in mind, we can approach this crackme similarly to what was attempted last time. We will x-ref up to see what refers to aInvalidSerialN.

_config.yml

Again, there is only one reference. We will follow it. This looks very similar to what was in NoREpls:

_config.yml

Like the previous crackme, there is a function responsible for indicating an invalid serial number, which is jumped to if the register AL is equal to zero. If it doesn’t equal zero, it proceeds to the push 40h instruction. Let’s take a look back at this instruction: .text:00401483 call sub_4013B0

This looks very similar to the function that we saw last time except we do not have the serial number hardcoded in here:

NoREpls 1.1: _config.yml

NoREpls: _config.yml

Should we give up? No. Of course not.

We will keep trying, but we can now confirm that edgyReggie has invalidated our previous serial number and he also no longer stores the serial number in plain-text anymore, which makes our job a bit trickier, but we love a good challenge. 🙂

Scrolling down a little bit further, we notice this:

_config.yml

I wonder what aTk9srvbmuy1nru is… could Tk9SRVBMUy1NRUtJLTMwSDItQU1OMy00OUpG be the new serial number? Let’s try it out.

Bummer! It didn’t work. But that was totally expected. edgyReggie is smarter than that now. However, this String could come in nifty… let’s keep that in mind for now. In the meantime, let’s look a little bit before that string being pushed. Let’s take a look at this instruction:

.text:00401417 call sub_401330

This instruction calls for the following function. Let’s hop into it and see what is there.

_config.yml

Interesting. We can see a few calls to CryptBinaryToStringA. With a bit of searching online we can find the documentation of CryptoBinaryToStringA(), and we realize this function can crypt an array of bytes to a base64 string or hex string. Now, remember that string that we found earlier? Let’s take a look at it.

Tk9SRVBMUy1NRUtJLTMwSDItQU1OMy00OUpG

Obviously, this isn’t a hex-string, since HEX is only A-F and 0-9 (inclusive on both). Could it be Base64? Yes, it could be. The length of that string is 36. Base64 encoded Strings should have length that is a multiple of 4. Also, a Base64 encoded String can contain A-Z and 0-9 as well. This is technically safe enough to assume that this is a Base64 encoded String, however we should probably confirm it is Base64. Looking back the documentation of CryptBinaryToStringA, we notice the following:

_config.yml

Now let’s look back at our Assembly code:

_config.yml

If the dwFlags parameter is 1, it is encoded as a Base64 String without headers.

From those instructions, you can see what values are being passed in as parameters to CryptBinaryToStringA(). The first parameter is being passed in whatever is in register edi. But what is the value of what is in register edi? Let’s scroll up to see what edi is.

_config.yml

At the highlighted instruction, it indicates that the value of edi is whatever was the value of edx. Now, we need to figure out what is the value of edx. Let’s x-ref up to see what calls sub_401330.

_config.yml

There is only result. So we’ll hop that.

_config.yml

From here, we notice that the second parameter to sub_401330 is the address of “String”. It is fairly safe to say that the String that we noted earlier is likely a Base64 encoded String. Now let’s try decoding it to see if it gives a serial number. Using a Base64 decoder, we get the following string from decoding the String we had earlier: NOREPLS-MEKI-30H2-AMN3-49JF. That looks like a working serial number. Let’s try it out!

_config.yml

Hurray! It works. We’ve proven that edgyReggie’s software still isn’t safe yet from cracking. 🙂 Let’s go get some bubb–wait a second. Our registration doesn’t persist on restarting the program. We really should ensure that our NoREpls is always going to be a full version. To do this, we will need to patch the executable file. We’ll cover this later. 😉

Written on March 3, 2019
< < Go back