Anon
December 29th, 2005, 20:49
Hello. I'm pretty new to RCE, so I hope I don't annoy you too much with my problem.
The program I'm working on functions similar to a media player or a computer in that it allows you to start running something, pause it, stop it, and restart it. The limit is that you can only do so for three minutes before seeing a nag screen and having to restart. The program displays how much time it has been running for with a timer of the form m:ss.hh, where m = minutes, ss = seconds, hh = hundredths of a second. Some possibly useful information is that you can press the "continue" button after the time limit is up, but the nag appears every hundredth of a second thereafter.
I was able to find the code that calls the nag and NOP it. I ran the program to see what would happen, and it still stopped at 3 minutes (it was exactly 3:00.00 on the timer). I couldn't get the program running in Ollydbg because of some exception that it wouldn't accept even if I pressed Shift-F7/F8/F9, so I was pretty discouraged. To make a long story shorter, I loaded it in Wdasm and set a breakpoint on the code that I had NOPed. I found out that the nag actually shows when the timer is 2:59.49.
When I set breakpoints on GetSystemTime, I found that one of the two occurrences of this call always occurs at times of the form m:ss.49, in addition to other times. I also set breakpoints on GetLocalTime and GetTickCount, and I think the information I got could be useful. Namely, those functions aren't called every time the timer increases. For example some hundredths of a second are skipped in certain places: The timer goes directly from 0:00.07 (or maybe 0:00.08) to 0:00.11 without any call to GetTickCount. The calls to GetSystemTime and GetLocalTime are even farther apart with regard to the timer. Even setting breakpoints on every instance of those functions at the same time leads to some skips.
I was able to find the location that caused the current value of the timer to be displayed, and I NOPed that without any difference in the running of the program (other than the timer not showing). Today, I decided to work backwards from the nag code to determine the jump that leads to it. I found it after a while and changed it so that it always takes the good jump. The code is below:
I tested the program, and it ran past the three minutes. However, the timer stopped at 3:11.11. I wasn't sure if it was just the timer stopping, or if the whole program had stopped. To stick to my media player analogy, I loaded a "media file" and found that it just stopped at 3:11.11. There was no error message or anything, it just stopped. To make matters worse, stopping and then restarting the file didn't make it work, like before my edit of the code. I would have to completely exit the program and open it again in order to play a "media file."
This is my current state. I would appreciate any help in what I should do next. I have several questions:
1. How does A0EEBB00 (= 2,700,000,000 decimal) = 3 minutes, or even 2:59.49? I found some possible conversions, but using them to find the equivalent of 3:11.11 and searching for that in the deadlisting didn't produce any results.
2. I know that the stop at 3:11.11 could be caused either by a second time check or by the number of the internally stored time being too large for some operation, but which is more likely? If it's the latter, wouldn't that cause some error other than just freezing the "media file"? If it's the former, then I need to figure out the conversion before I can do anything else.
Thanks for any help.
The program I'm working on functions similar to a media player or a computer in that it allows you to start running something, pause it, stop it, and restart it. The limit is that you can only do so for three minutes before seeing a nag screen and having to restart. The program displays how much time it has been running for with a timer of the form m:ss.hh, where m = minutes, ss = seconds, hh = hundredths of a second. Some possibly useful information is that you can press the "continue" button after the time limit is up, but the nag appears every hundredth of a second thereafter.
I was able to find the code that calls the nag and NOP it. I ran the program to see what would happen, and it still stopped at 3 minutes (it was exactly 3:00.00 on the timer). I couldn't get the program running in Ollydbg because of some exception that it wouldn't accept even if I pressed Shift-F7/F8/F9, so I was pretty discouraged. To make a long story shorter, I loaded it in Wdasm and set a breakpoint on the code that I had NOPed. I found out that the nag actually shows when the timer is 2:59.49.
When I set breakpoints on GetSystemTime, I found that one of the two occurrences of this call always occurs at times of the form m:ss.49, in addition to other times. I also set breakpoints on GetLocalTime and GetTickCount, and I think the information I got could be useful. Namely, those functions aren't called every time the timer increases. For example some hundredths of a second are skipped in certain places: The timer goes directly from 0:00.07 (or maybe 0:00.08) to 0:00.11 without any call to GetTickCount. The calls to GetSystemTime and GetLocalTime are even farther apart with regard to the timer. Even setting breakpoints on every instance of those functions at the same time leads to some skips.
I was able to find the location that caused the current value of the timer to be displayed, and I NOPed that without any difference in the running of the program (other than the timer not showing). Today, I decided to work backwards from the nag code to determine the jump that leads to it. I found it after a while and changed it so that it always takes the good jump. The code is below:
Code:
:00421CF6 81BD0CFFFFFF00BBEEA0 cmp dword ptr [ebp+FFFFFF0C], A0EEBB00
:00421D00 90 nop <-- This used to be 0F82 jle. I
:00421D01 E9E0010000 jmp 00421EE6 <-- changed it to 90E9
* More code here that eventually leads to the nag *
* Possible Ref to Menu: MenuID_006E, Item: "About... F1"
|
* Possible Reference to Dialog: DialogID_0068
|
:00421DD6 6A68 push 00000068
:00421DD8 8B8D04FFFFFF mov ecx, dword ptr [ebp+FFFFFF04]
:00421DDE 51 push ecx
* Reference To: USER32.DialogBoxParamA, Ord:0093h
|
:00421DDF FF15D4624600 Call dword ptr [004662D4] <-- The nag
:00421DE5 8945A8 mov dword ptr [ebp-58], eax
This is my current state. I would appreciate any help in what I should do next. I have several questions:
1. How does A0EEBB00 (= 2,700,000,000 decimal) = 3 minutes, or even 2:59.49? I found some possible conversions, but using them to find the equivalent of 3:11.11 and searching for that in the deadlisting didn't produce any results.
2. I know that the stop at 3:11.11 could be caused either by a second time check or by the number of the internally stored time being too large for some operation, but which is more likely? If it's the latter, wouldn't that cause some error other than just freezing the "media file"? If it's the former, then I need to figure out the conversion before I can do anything else.
Thanks for any help.