Many a crack back in the day was even more simple still, we'd just find and alter the right JE or JNE into a JMP and we're off to the races. As the author found, the tough part is just finding and interpreting where and how the protection was implemented. If throwing the exe in a hex editor gave you access to String Data References (not always the case, but more common than not) then you'd just fail the check you were trying to skip, find that string, hop over into assembly to see what triggered loading that, and then just alter the logic to jump over it when the time comes.
Many years ago I was a technician supporting a few custom programs on thousands of PCs. The developer of one of these programs had added a date check to his code so the program would refuse to run after a set date and each new release would increase this date by a few months so it would stop working after a few weeks if he ever stopped creating new releases. His contract ended and a few weeks later his software, now relied upon by hundreds of sites, stopped working. The contract for the software development was thoroughly checked and legal action against the developer was started but I asked to see if I could resolve the problem in the meantime.
It only took ten minutes with a dissassembler to find the JGT (Jump if greater than) and convert it to a JLT so the software would stop running if the date was before a certain date rather than after. I created a patching tool that simply flipped one bit that was sent out to all the sites and everything was good again. I don't think I'll ever beat the elegance of a single bit flip hack.
If you think it's bad now, the early days of the web were absolutely filled with scumbag grifters who made small fortunes hiring contractors and then refusing to pay.
Many of them disappeared in the y2k dot com bust, but then seem to have reappeared in SF after 2008.
In the late 1990's, my second ever Flash app development client stiffed me on a $10k invoice.
He finally figured out 6 months later that he didn't have the source material to make changes and paid the full invoice in order to get it.
So I took precautions with the next client. It was a small agency that was serving a much larger business.
We were on 30 days net payment terms and I submitted the invoice when the project was done.
They didn't pay and within a couple weeks of gentle reminders, they stopped responding.
I smiled.
Exactly 30 days from the due date, I got a panicked call shrieking about their largest client website being down and did I have anything to do with it?!
I asked them what the hell they were talking about, they don't own a website. They never paid for any websites. I happen to own a website and I would be happy to give them access to it if they want to submit a payment.
They started to threaten legal nonsense, and how they had a "no time bombs clause in the contract."
I laughed because my contract had no such clause. If they signed such a contract with the client, that's not my problem.
I told them I wouldn't release the source files until the check cleared my bank, which could be weeks. A cashier's check arrived that morning and their source files were delivered.
By the end of it, the folks at the agency thanked me because that client wasn't planning to pay them and they hired me for other work (which, they had to prepay for).
Of course I don't know about the OP, but I'd bet the company was trying to stiff that contractor on their last check.
> because that client wasn't planning to pay them
Wait, you mean they used your little ruse as a means to be paid themselves??
Yes they did, and it worked!
Mostly non-malicious example... My employer asked me to write a UI to solve a problem for a handful of people until a proper (giant ever-delayed) migration was finished. Over a couple of weeks I made it work despite not having dealt with MVVM/XAML/Whatever before and I was pretty pleased with the outcome. But it was a hacked together thing! I'm not a real dev and given that I got a promise it wouldn't get distributed.
So, you know, in the program.cs startup I checked the username vs a hardcoded list of people in the relevant teams, and if it wasn't crashed out with an error and a support email address.
About 18 months after I had moved on, I got an email with a screenshot of that error message. it would appear the Milan (something like that) office had got their hands on a copy but it just wouldn't work for them...
Trivial to undo of course, but I did enjoy the throwback!
That's a dangerous fix. What if someone tries to run your new version in the past?
the spacetime paradox is the bigger concern imo. nothing to worry about.
There's a lot of things going on that lead to this.
One, the developers spend more time running this code than we do, and they have to get the program working before we can even use it. So any parts of the program that are hostile to the developers risks killing the entire project. Obfuscating the copy protection can hit a point where it makes bug fixing difficult.
Two, lack of training. If you, me, and Steve each have a bag of tricks we all use to crack games, whichever one of us figures it out gets bragging rights but the game remains cracked. Meanwhile Developer Dan has to be aware of all the tricks in all of our bags together if he wants to keep the three of us out. Only there's not three of us, there's 300. Or today, probably more like 30,000.
Three, lack of motivation, which is itself several different situations. There's a certain amount of passive aggression you can put into a feature you don't even really want to work on. You can lean into any of the other explanations to defend why your code didn't protect from cracking all that much, but it's a checkbox that's trying to prove a negative, and nobody is going to give you any credit for getting it to work right in the same way they give you credit for fixing that corner glitch that the QA people keep bitching about. Or getting that particle animation to work that makes the AOE spells look badass.
Another method (much more common for software that asks for two pieces of information, like a name and a key) is to take a memdump of the process at the "your key is invalid" dialog, find the invalid key you just typed, and hope that a valid key is somewhere nearby in memory. Unlike the assembly trick, this requires 0 programming expertise beyond the ability to type `strings` on the command line.
This works because some programs use a hashing algorithm to calculate the key based on the name, do a strcmp, and pop a messagebox if the keys don't match, without zeroizing the valid key buffer first. If the key buffers are on the stack (or if the two mallocs just happen to use the same region in memory), it is often easy to find a valid key if you know where the invalid one is.
I guess software that derives keys this way is far less common than it once was, but I know of somebody who cracked something using this method just a few years ago, so it still pops up from time to time.
When I was a child, in the 90s, I did this all of the time.
Input a unique string I could watch for, fire up SoftICE, watch for the string, and then step through until the == comparison happened, then either grab the calculated key and input it, or patch the comparison from == to != or just return true, depending on the implementation.
SoftICE was such a gift and pain in the ass.
I did a massive crack that involved a program and it’s inf/dll hardware driver package.
Some of the most rewarding work I’ve done and also just so tedious!
Having to stop the OS like that and accidentally getting to the kernel but then not wanting to lose my position so having to hit step over and step out until just the right place… whew.
Yep. I used SoftICE to do a few of these dongle-workarounds. Amazing and terrible software. :D
Haha yeah. It was mostly just fun for me as a nerdy child who spent way too much time on Astalavista forum.
Cracking and RE were just gateways into a career in (defensive) security for me.
I honestly can’t recall how I even found SoftICE, but my uncle gave me a floppy with LJPEGViewer and the license was written on the disk. Eventually I lost the original but I’ll be dammed if I’m going to use Paint. I fired up SoftICE, managed to break before the “invalid key” dialog, and just did a cute little “return true” and that was that
mellanox switches included an executable keygen in their firmware bundle. It could be used to both generate a key (given feature set) combined with a secret, but could also be used to validate what features a given key gave you (using the secret). Hence, the secret was stored in the binary and was easily visible with strings and one could then just use the tool itself to generate keys.
Sort of reminds me of the DEC PAKGEN tool to generate licenses for the VMS license management facility, which DEC distributed so third-party software vendors could issue licenses for their own software.
To prevent vendor A from creating licenses for vendor B's products, each DEC-issued PAKGEN license only authorized license generation for a specific named vendor's products.
As with all other DEC-supplied VMS software, PAKGEN was licensed through the VMS license management facility.
Thus if you could somehow get a PAKGEN license for the vendor name "DEC", you could use it to generate licenses for arbitrary DEC products.
Including PAKGEN itself.
And you could therefore generate licenses authorizing PAKGEN to generate licenses for arbitrary vendors' products.
The proper thing to do is not to zeroize the correct string memory before comparing. The proper thing is to only store the hash in the binary in the first place, not the correct string. (Although having a 2nd layer of hashing before comparing might also be a good idea, and in that case you would want to zeroize the 1st hash before comparing the 2nd hash.)
You can't not store the correct string in this case, as the key is calculated from the user's email address. There is an infinite number of possible keys. THe only way to check if the key is correct is to recalculate it yourself.
These days, I guess you could make the key an ECDSA signature for a public key embedded in the binary if you were willing to accept such long keys.
> Many a crack back in the day was even more simple still, we'd just find and alter the right JE or JNE into a JMP and we're off to the races.
I did that with dBASE III, which used ProLok "laser protection" from Vault Corporation - a signature burned onto the diskette with a laser. Back then, I found it amazing that Ashton-Tate actually spent money to contract with a copy protection company for something that could be so easily defeated by a teenager reading assembler.
They could have easily just written the same kind of code themselves. An example of the power of marketing over substance.
I was able to replicate that protection mechanism just by scratching a diskette with a pin. The "laser" was a meaninglessly advanced-sounding solution that added no value compared to any other means of damaging a diskette.
I remember doing something similar with Lemmings 3D. You could simply NOP over the JMP into the copy-protection subroutine. It was surprisingly easy.
Made me feel like such a badass hacker at 15 years old.
When I was 10 or so, I "cracked" Slam! Air Hockey for Windows 3.1 by opening the exe in EDIT.COM and replacing some random binary garbage with spaces. After a few attempts, I managed to bypass the shareware dialog but also introduced some weird bugs that I don't recall the details of.
"Cheat enginge"
This was one of those things you really really wanted but once you toyed with it, it sucked the fun out of games and they felt pointless.
> I was able to replicate that protection mechanism just by scratching a diskette with a pin.
How did you figure out where to scratch it? Was the laser mark visible on the original disk, or did you have to read the code and orient based on the diskette's index hole?
Yes, it was apparently very visible: https://martypc.blogspot.com/2024/09/pc-floppy-copy-protecti...
But as I mentioned in a sibling comment, I’m not sure it was ever confirmed that it was really a laser that made that mark.
I described two different scenarios: defeating the protection, and replicating it, e.g. to protect your own software without paying Vault for their "laser" protection.
Defeating the protection didn't involve knowing anything about the laser mark - as the comment I replied to described, it just involved changing a conditional jump to an unconditional one.
Replicating the protection involved causing minor damage on the diskette - the details don't really matter, laser, pin scratch, whatever - then formatting the disk, and registering the pattern of bad sectors created by the damage. A normal copy of the disk didn't replicate those bad sectors exactly, which made it possible to detect that the original disk was not present.
Ha! I remember disk copy programs which read these bad sector patterns and then replicated the error pattern in software (not on physical disk obviously).
Similar stuff was later used for CDs IIRC.
Was ist ever confirmed that it was in fact a laser? I wanted to make a trivia question out of this ProLok protection, because “lasers for copy protection” sounds just weird enough to potentially be a nonsense answer without context, but I couldn’t confirm that the holes were indeed made with lasers, and not with other means.
Good question. I don't know the answer, but I'm quite certain that it didn't really matter what mechanism was used to mark a diskette. Any damage would be equally strong as a way to detect copying.
Yeah, it matters only in “interestingness” or “coolness”.
Their patent (https://patents.google.com/patent/US4785361A/en) doesn’t mention a laser, but of course that doesn’t imply it wasn’t a laser.
I would guess (more or less) identically damaging multiple floppy disks in the same way would be easier with a laser than with something mechanical (e.g. a knife or a drill) (it is fairly easy to control power and duration of a burn), so it might well have been a laser.
On the other hand, disk tracks weren’t exactly tiny at that time in history.
It could be a tiny drop of something corrosive, but with that I’m also still wondering if a laser isn’t simpler, yeah.
I have almost no doubt that it could be a laser, it’s just unfortunate (and maybe a little bit suspicious) that I haven’t found it confirmed anyway. Almost like they wanted it to be a laser (hence the folklore around it), but had to use a less cool method to do it. But of course it might as well just have been a laser, and they for some reason declined to market or even just document it that way, for whatever reason.
A certain automation system vendor uses proper USB license dongles in their PC software but they do not do challenge-response authentication. Instead they send a hardcoded string to the dongle and compare the response against a list that contains various software feature levels.
The whole automation system including machinery costs anywhere from 200k to 1M yet Vendor™ tries to milk the customers dry with a 1.5k software license that lets you manage up to 254 physically* connected systems. I'm pretty sure the license dongle is in reality designed to prevent casual tinkering of parameters, which is something only service techs should do.
*You can circumvent this with serial-over-Ethernet converters, which has resulted in an Industrial Internet of Shit-level security nightmare as companies happily expose their systems over the internet, thinking that license dongles are a substitute for authentication.
I remember I had some demo software that could be enabled with a code. I was just curious and at the code prompt, I entered the debugger. I dumped the process space and there was a nul-terminated string of letters and numbers. I restarted the process and entered them at the prompt and voila, it was enabled.
(I did go on to pay for the software)
I remember an icon editor (or something similar) for Windows 3.1, it was a shareware where you could enter a code to remove the nag screen. No crack was necessary, I basically managed to enter valid registration codes by just typing random numbers. In the end I had enough valid numbers that I could figure out the logic, it was something about the sums of digit groups.
This was true for the 10-digit CD keys Microsoft used for many products in the 90s: the first three digits could be almost anything, and the last seven digits had to sum to a multiple of 7, so, e.g., 111-1111111 was a valid product key (for any product that used the scheme).
I think it was StarCraft where we’d just try random keys until it would work, usually only three or four needed.
I was wondering this actually, why not just skip past the check entirely instead of going through the effort to pass the check without the dongle?
Because sometimes skipping is not enough: https://mrwint.github.io/winter/writeup/writeup.html
Cracking is so fun because we have Slides!