---------------Match It!--------------- A 4am crack 2016-03-02 --------------------------------------- Name: Match It! Version: 4.8 Genre: educational Year: 1984 Author: Nancy E. Post Publisher: The Regents / ALA Company Media: single-sided 5.25-inch floppy OS: DOS 3.3 Previous cracks: none Similar cracks: #582 Place Value Recognition II #573 The States Game #572 Decimals Practice #501 Speed Reader II #492 Fractions Practice #395 Algebra Volume 3 v1.2 ~ Chapter 0 You Might Run On For A Long Time Run On, Ducking And Dodging COPYA immediate disk read error Locksmith Fast Disk Backup unable to read any track EDD 4 bit copy (no sync, no count) no errors, but copy hangs on boot Copy ][+ nibble editor all tracks use standard prologues (address: D5 AA 96, data: D5 AA AD) but modified epilogues (address: FF FF FF, data: FF FF FF) Disk Fixer ["O" -> "Input/Output Control"] set Address Epilogue to "FF FF FF" set Data Epilogue to "FF FF FF" Success! All tracks readable! T00 -> looks like a DOS 3.3 RWTS T11 -> DOS 3.3 disk catalog T01,S09 -> startup program is "STARTMI" Why didn't COPYA work? modified epilogue bytes (every track) Why didn't Locksmith FDB work? modified epilogue bytes (every track) Why didn't my EDD copy work? probably a nibble check during boot Next steps: 1. AUTOTRACE to capture RWTS 2. Advanced Demuffin to convert disk to standard format 3. Post-Demuffin Patcher to get RWTS to read standard format 4. Find nibble check and bypass it ~ Chapter 1 Here We Are Now Going To The East Side I Pick Up My Friends And We Start To Ride [S6,D1=original disk] [S6,D2=blank disk] [S5,D1=my work disk] ]PR#5 CAPTURING BOOT0 ...reboots slot 6... ...reboots slot 5... SAVING BOOT0 /!\ BOOT0 JUMPS TO ($BBFE) CAPTURING BOOT1 ...reboots slot 6... ...reboots slot 5... SAVING BOOT1 SAVING RWTS ]BRUN ADVANCED DEMUFFIN 1.5 ["5" to switch to slot 5] ["R" to load a new RWTS module] --> At $B8, load "RWTS" from drive 1 ["6" to switch to slot 6] ["C" to convert disk] --v-- ADVANCED DEMUFFIN 1.5 (C) 1983, 2014 ORIGINAL BY THE STACK UPDATES BY 4AM =======PRESS ANY KEY TO CONTINUE======= TRK:R.................................. +.5: 0123456789ABCDEF0123456789ABCDEF012 SC0:................................... SC1:................................... SC2:................................... SC3:................................... SC4:................................... SC5:................................... SC6:................................... SC7:................................... SC8:................................... SC9:................................... SCA:R.................................. SCB:................................... SCC:................................... SCD:................................... SCE:................................... SCF:................................... ======================================= 16SC $00,$00-$22,$0F BY1.0 S6,D1->S6,D2 --^-- Hmm. Even the disk's own RWTS can't read T00,S0A. I'm hoping that part of the copy protection and not a bad disk. ]PR#5 ... ]CATALOG,S6,D2 C1983 DSR^C#254 156 FREE *A 012 STARTMI *T 002 ANTONYMS0 *T 002 ANTONYMS1 *T 002 ANTONYMS2 *B 005 BLIPPO MOD1.SET *A 008 DELFILE *A 017 DELRECORD *B 002 FILL.OBJ0 T 003 GAMEFILE T 002 HALL *T 002 SYNONYMS2 *T 002 HOMONYMS0 *T 002 HOMONYMS1 *T 002 HOMONYMS2 *B 005 HOUR GLASS.SET *A 011 INSTRUCTIONS *A 023 INTROMI-HIGH *A 015 INTROMI-LOW T 005 MATCHFILE *B 016 MIABS.B *A 021 MIHI *A 019 MILO *B 002 MU.OBJ0 *A 011 OPTIONS *B 033 PIC.FRAME *T 002 RHYMING WORDS0 *T 002 RHYMING WORDS1 *T 002 RHYMING WORDS2 *A 019 SCORE *T 002 SYNONYMS0 *A 046 UTILMI-HIGH *A 024 UTILMI-LOW *A 017 TRANSFER *T 002 SYNONYMS1 [S6,D1=demuffin'd copy] ]PR#6 ...still hangs on boot... ~ Chapter 2 I'm Gonna Ask You To Look Away ]PR#5 ... ]BLOAD BOOT0,A$800 ]CALL -151 *801L . . all normal, until... . 084A- 6C FE BB JMP ($BBFE) *BLOAD BOOT1,A$2600 *FE89G FE93G ; disconnect DOS *B600<2600.2FFFM ; move RWTS into place *BBFE.BBFF BBFE- 00 BB *BB00L ; Ah, I recognize this routine already. ; It was used by several different ; publishers, and it apparently had ; tweakable options. Turning off an ; option would generate code that makes ; no sense at first glance. ; First, set the RUN flag so that, even ; if I manage to break out to a BASIC ; prompt, any command will act like RUN BB00- A9 FF LDA #$FF BB02- 85 D6 STA $D6 ; Some disks have a "LDA $C08E,X" here ; to require that the disk be write- ; protected. With the option off, it's ; just an unconditional jump. BB04- BD 8D C0 LDA $C08D,X BB07- A9 FF LDA #$FF BB09- EA NOP BB0A- 30 05 BMI $BB11 ;[always skipped] ;BB0C- A2 B1 LDX #$B1 ;BB0E- 4C F0 BB JMP $BBF0 ; Check the low-level reset vector (I ; think this was protection against ; "boot inspectors" like Watson ; that installed themselves in the ; language card and left it active ; during boot) BB11- AD FD FF LDA $FFFD BB14- C9 FA CMP #$FA BB16- F0 05 BEQ $BB1D BB18- A2 B2 LDX #$B2 BB1A- 4C F0 BB JMP $BBF0 BB1D- BD 8C C0 LDA $C08C,X ; Set the first character of the input ; buffer. This can be checked later to ; ensure that an attacker (me) hasn't ; interrupted the boot and been ; typing things. BB20- A9 D7 LDA #$D7 BB22- 8D 00 02 STA $0200 ; look for a magic nibble sequence on ; track $00 BB25- BD 8C C0 LDA $C08C,X BB28- 10 FB BPL $BB25 BB2A- C9 EB CMP #$EB BB2C- D0 F7 BNE $BB25 BB2E- BD 8C C0 LDA $C08C,X BB31- 10 FB BPL $BB2E BB33- C9 D5 CMP #$D5 BB35- D0 EE BNE $BB25 BB37- BD 8C C0 LDA $C08C,X BB3A- 10 FB BPL $BB37 BB3C- C9 AA CMP #$AA BB3E- D0 E5 BNE $BB25 ; wipe most of memory ($0800..$95FF) ; although, ironically, not the part ; I'm using for boot tracing BB40- A9 4C LDA #$4C BB42- A0 00 LDY #$00 BB44- 99 00 95 STA $9500,Y BB47- 88 DEY BB48- D0 FA BNE $BB44 BB4A- CE 46 BB DEC $BB46 BB4D- AD 46 BB LDA $BB46 BB50- C9 07 CMP #$07 BB52- D0 EC BNE $BB40 ; fiddle with the RWTS to ignore ; epilogue bytes BB54- A9 18 LDA #$18 BB56- 8D 42 B9 STA $B942 ; sector $0A BB59- A9 0A LDA #$0A BB5B- 8D ED B7 STA $B7ED BB5E- D0 05 BNE $BB65 ...[some zeroes used for data later]... ; track $00 BB65- A9 00 LDA #$00 BB67- 8D EC B7 STA $B7EC ; into $4000 BB6A- 8D F0 B7 STA $B7F0 BB6D- A9 40 LDA #$40 BB6F- 8D F1 B7 STA $B7F1 ; read command BB72- A9 01 LDA #$01 BB74- 8D F4 B7 STA $B7F4 ; set up rest of RWTS table BB77- 8D F8 B7 STA $B7F8 BB7A- 8D EA B7 STA $B7EA BB7D- 8E E9 B7 STX $B7E9 BB80- 8E F7 B7 STX $B7F7 ; more RWTS fiddling, so sector reads ; save raw nibble data in $6C00 range BB83- A0 6C LDY #$6C BB85- 8C 10 B9 STY $B910 BB88- 8C CE B8 STY $B8CE BB8B- 8C D2 B8 STY $B8D2 BB8E- 88 DEY BB8F- 8C 21 B9 STY $B921 ; a sector read, with modified RWTS BB92- 20 E7 BB JSR $BBE7 ; copy the raw nibble data elsewhere BB95- A0 55 LDY #$55 BB97- B9 00 6C LDA $6C00,Y BB9A- 99 00 5C STA $5C00,Y BB9D- 88 DEY BB9E- 10 F7 BPL $BB97 BBA0- AD 02 6B LDA $6B02 BBA3- 85 06 STA $06 ; another sector read BBA5- 20 E7 BB JSR $BBE7 BBA8- AD 02 6B LDA $6B02 BBAB- 85 07 STA $07 ; and another BBAD- 20 E7 BB JSR $BBE7 BBB0- AD 02 6B LDA $6B02 BBB3- 85 08 STA $08 ; compare this read's nibble data to ; the previous read's nibble data BBB5- A0 55 LDY #$55 BBB7- B9 00 6C LDA $6C00,Y BBBA- D9 00 5C CMP $5C00,Y ; fail if anything doesn't match BBBD- D0 2F BNE $BBEE BBBF- 88 DEY BBC0- 10 F5 BPL $BBB7 ; more comparisons of the side effects ; generated by the modified RWTS BBC2- A5 06 LDA $06 BBC4- C5 07 CMP $07 BBC6- D0 04 BNE $BBCC BBC8- C5 08 CMP $08 BBCA- F0 17 BEQ $BBE3 ; success path is here -- ; first, restore the RWTS code BBCC- A9 38 LDA #$38 BBCE- 8D 42 B9 STA $B942 BBD1- A0 BC LDY #$BC BBD3- 8C 10 B9 STY $B910 BBD6- 8C CE B8 STY $B8CE BBD9- 8C D2 B8 STY $B8D2 BBDC- 88 DEY BBDD- 8C 21 B9 STY $B921 ; then continue with boot1 as normal BBE0- 4C 00 B7 JMP $B700 BBE3- 4C 54 BB JMP $BB54 ... BBE7- A9 B7 LDA #$B7 BBE9- A0 E8 LDY #$E8 BBEB- 4C B5 B7 JMP $B7B5 ; failure path from comparison at $BBBD BBEE- A2 B3 LDX #$B3 ; general failure path is here -- ; clear screen, show text screen, write ; error code, and jump to The Badlands BBF0- 20 58 FC JSR $FC58 BBF3- 20 2D FF JSR $FF2D BBF6- 8E 03 04 STX $0403 BBF9- 4C 5B B7 JMP $B75B I'm guessing my non-working copy never got as far as wiping main memory, since the search for the nibble sequence is unconditional and neverending. That explains the behavior I saw -- it spun forever with the drive motor on, and it never got off track 0. The important takeaway here is that there don't appear to be any long-term side effects of this copy protection. If it succeeds, it restores everything that it modified (in the RWTS code), then it just jumps to $B700 to start the boot1 phase. But that's it; nothing else seems to rely on some magic number that it pulls from the raw nibbles or anything. It doesn't decrypt anything. It doesn't even clear the carry flag. ~ Chapter 3 No One Can Stop Us Now 'Cause We Are All Made Of Stars [S6,D1=demuffin'd copy] [S5,D1=my work disk] ]PR#5 ... ]BRUN PDP ; fix epilogue byte checking in RWTS T00,S03,$91 change FF to DE T00,S03,$9B change FF to AA T00,S03,$35 change FF to DE T00,S03,$3F change FF to AA T00,S02,$9E change FF to DE T00,S02,$A3 change FF to AA T00,S02,$A8 change FF to EB ; neutralize RWTS swappers (called when ; the program needs to switch between ; reading the protected program disk ; and the unprotected data disk -- I ; don't think this disk uses any data ; disks, but the protection is generic) T00,S04,$69 change A9 to 60 T00,S04,$7D change A9 to 60 ; bypass nibble check after boot0 T00,S00,$4B change FEBB to FD08 ; fix nibble translation tables (ooh, I ; didn't see this in my investigation; ; hooray for automation) T00,S04,$29 change AA to 96 T00,S04,$AA change 00 to AA ]PR#6 ...loads DOS then prints "PLEASE USE THE ORIGINAL DISKETTE." and hangs... Wait, what? ~ Chapter 4 I Know You Don't Love Me But You Don't Have To Be So Mean ]PR#5 ... ]LOAD STARTMI,S6,D1 ]LIST 0 REM ]LIST (no output) Ah, the old BASIC trick of embedding DOS commands in the listing. In this case, the command is "FP", which clears the BASIC program from memory.(*) (*) Is it just my modern perspective, or is it absolutely horrifying that a BASIC program can execute arbitrary DOS commands when you list it? "LIST" just seems like it should be idempotent, like HTTP GET. Anyway... ]LOAD STARTMI ]LIST 1, 1 REM IF NORMAL H IF NORMAL H` 2 CALL 2064 Well that's suspicious right off the bat. 2064 = $0810, which means we're calling right in the middle of... this very program. (BASIC programs are loaded at $0800.) ]CALL -151 *810L 0810- AD 1F 9D LDA $9D1F 0813- 48 PHA 0814- AD 1E 9D LDA $9D1E 0817- 48 PHA 0818- 60 RTS [...consults "Beneath Apple DOS"...] OK, $9D1E/F is part of the DOS 3.3 command table. And it's... wait, I must be reading this wrong. It's the "INIT" command. Obviously this program doesn't format itself on boot. The INIT command must be NOP'd out in the original disk's DOS. But what if I boot from another disk? [S6,D1=demuffin'd copy] [S5,D1=DOS 3.3 system master] ]PR#5 ... ]RUN STARTMI,S6,D1 ...formats disk and crashes... Seriously. I've only ever seen malicious behavior like this once. Games by Blue Chip Software (Millionaire, Tycoon, Baron) will intentionally destroy T00,S00 if their protection check fails. But I've never seen a disk that would format itself as punishment for running it from another disk. Still, this is not the behavior I saw when I booted my non-working copy. This is an entirely unrelated protection that I stumbled onto while looking for the other protection. This disk is a minefield. ~ Chapter 5 I Broke Everything New Again Everything That I Owned Continuing the listing (I'll spare you the details of REDOING THE ENTIRE CRACK UP TO THIS POINT BECAUSE MY COPY SELF- DESTRUCTED no I'm not bitter)... ]LIST 5, 5 REM ***STARTMI*** 6 REM **COPYRIGHT NOTICE, L. 6 3000 FF.*** 7 TEXT : HOME :UN = PEEK (512) : IF UN < > 215 THEN VTAB 10: HTAB 1: PRINT "PLEASE US E THE ORIGINAL DISKETTE.": WAIT 1,0 Aha! That is the message I saw on my non-working copy. But what is PEEK(512)? 512 = $0200, which is the first byte of the input buffer. 215 = $D7, which is nothing of consequence. . . [slow realization music] . I was wrong. The protection check at $BB00 did have one tiny side effect: it set $0200 to $D7 (at $BB22). Because I bypassed the entire routine, this never got set, and the HELLO program noticed. For reasons passing all understanding, this failure only warrants a polite message (they even said "please") instead of formatting the entire disk. Not that I'm complaining... To solve this, I'm going to undo some of the patches I did earlier. T00,S00,$4B change "FD 08" back to "FE BB" Then, in lieu of the protection routine at $BB00, I'll put a small routine that sets $0200 to the expected value and unconditionally jumps to $B700 to continue the boot. T00,S05,$00 change to "A9 D7 8D 00 02 4C 00 B7" which looks like this: --v-- T00,S05 ----------- DISASSEMBLY MODE ---------- 0000:A9 D7 LDA #$D7 0002:8D 00 02 STA $0200 0005:4C 00 B7 JMP $B700 --^-- ]PR#6 ...works... After extensive testing, I'm confident that there is no further protection. Quod erat liberandum. --------------------------------------- A 4am crack No. 628 ------------------EOF------------------