'=========================================================================== ' Subject: XOR ENCRYPTION/DECRYPTION Date: 08-10-96 (12:55) ' Author: Jonathan Leger Code: QB, QBasic, PDS ' Origin: leger@mail.dtx.net Packet: BINARY.ABC '=========================================================================== '(*** XOR.BAS ***) '(*************************************************************************) '(*** This is a small demonstration of the XOR encryption/decryption ***) '(*** method that will encrypt this file (assuming the name is XOR.BAS) ***) '(*** and put it in the file XOR.XOR. If you want it to decrypt the ***) '(*** XOR.XOR file once it's been encrypted, merely change the FILE$ ***) '(*** to XOR.XOR and the OUTPUT$ to XOR.BAS (or whatever). The key ***) '(*** we will be using is 15. You can change that for your purposes, ***) '(*** but the key must be a value from 0 to 255. ***) '(*************************************************************************) '(*** This method of encryption is not very secure, since it can be ***) '(*** broken easily by the brute force method (though it used to be a ***) '(*** very popular form of encryption). However, for most purposes, ***) '(*** such as game high scores or passwords, etc, it serves quite well, ***) '(*** since the person has no way to know that the file was encrypted ***) '(*** using this method, and most people wouldn't think to try and ***) '(*** decrypt it themselves anyway. ***) '(*************************************************************************) '(*** The File.XOR function returns a FALSE value (0) if the input file ***) '(*** (FILE$) does ***) not exist, otherwise it returns TRUE (-1). ***) '(*************************************************************************) DECLARE FUNCTION File.XOR% (FILE$, output$, ekey%, sbarx%, sbary%, sbarlen%) SCREEN 0 WIDTH 80, 25 COLOR 7, 0 CLS FILE$ = "xor.bas" '(*** We'll encrypt this file... ***) output$ = "xor.xor" '(*** ...and put the results here. ***) ekey% = 15 '(*** Our encryption key will be 15. ***) LOCATE 1, 1 PRINT "Using XOR method of encryption/decription on " + UCASE$(FILE$) + "..." '(*** Use a status bar for the encryption. ***) COLOR 15, 1 ErrVal = File.XOR%(FILE$, output$, ekey%, 1, 2, 40) IF ErrVal THEN '(*** No errors! ***) LOCATE 1, 1: COLOR 7, 0 PRINT STRING$(80, " "); LOCATE 1, 1 PRINT "Success! Results in file (" + UCASE$(output$) + ")." ELSE '(*** The file didn't exist! ***) LOCATE 1, 1: COLOR 7, 0 PRINT STRING$(80, " "); LOCATE 1, 1 PRINT "Input file ("; UCASE$(FILE$); ") does not exist." END IF DEFINT A-Z '(*** File.XOR () ****) '(*** ----------- ****) '(*** Thie function will take a file (INPUT$) and XOR each byte with ***) '(*** the given encryption key (EKEY), puting the results into a file ***) '(*** (OUTPUT$). If you want a status bar showing progress, pass the ***) '(*** x and y location of the status bar on-screen (SBARX, SBARY). If ***) '(*** no status bar is desired, pass a 0 for the x and y. SBARLEN is ***) '(*** the length you want the status bar to be. ***) '(*** NOTICE: To unXOR the file, just pass the XORed file the the ***) '(*** function with the _SAME_ encryption key. Given the nature of ***) '(*** XOR, an individual decryption scheme is not needed. Note, too, ***) '(*** that EKEY can only be from 0 to 255. ***) '(*** --------------------------------------------------------------- ***) FUNCTION File.XOR (FILE$, output$, ekey, sbarx, sbary, sbarlen) '(*** Check if the input file passed exist. ***) '(*** If the input file doesn't exist, exit with error ***) '(*** value 0 [FALSE]. ***) filenum = FREEFILE OPEN FILE$ FOR BINARY AS filenum IF LOF(filenum) = 0 THEN '(*** Pass error value back since file didn't exist. ***) File.XOR = 0 CLOSE filenum '(*** Kill the 0 byte file we made by opening it. ***) KILL FILE$ EXIT FUNCTION END IF '(*** Both files exist, open them. ***) CLOSE filenum OPEN FILE$ FOR INPUT AS filenum outputnum = FREEFILE OPEN output$ FOR OUTPUT AS outputnum '(*** If we want a status bar, do the encryption with a status bar! ***) IF sbarx > 0 THEN '(*** Draw empty status bar and reset the byte count# to 0. ***) LOCATE sbary, sbarx: PRINT STRING$(sbarlen, 177); count# = 0 '(*** Encrypt/Decrypt the file. ***) DO WHILE NOT EOF(1) '(*** Read a byte from the file. ***) bytes.left# = LOF(filenum) - LOF(outputnum) IF bytes.left# < 100 THEN read.bytes$ = INPUT$(bytes.left#, filenum) chunk = bytes.left# ELSE read.bytes$ = INPUT$(100, filenum) chunk = 100 END IF '(*** Increment byte count#. ***) count# = count# + chunk '(*** XOR the bytes with encryption key. ***) FOR byte.count = 1 TO chunk changed.byte$ = changed.byte$ + CHR$(ASC(MID$(read.bytes$, byte.count, 1)) XOR ekey) NEXT byte.count '(*** Print it to the output file. ***) PRINT #outputnum, changed.byte$; changed.byte$ = "" '(*** If a chunk of 100 bytes has been read, update status bar. ***) IF count# MOD 1000 = 0 THEN LOCATE sbary, sbarx PRINT STRING$(sbarlen * (count# / LOF(1)), 219); END IF LOOP LOCATE sbary, sbarx PRINT STRING$(sbarlen, 219); ELSE '(*** We didn't want a status bar, so skip the status bar. This will ***) '(*** give some extra speed because the print code is ignored. ***) DO WHILE NOT EOF(1) '(*** Read a byte from the file. ***) bytes.left# = LOF(filenum) - LOF(outputnum) IF bytes.left# < 100 THEN read.bytes$ = INPUT$(bytes.left#, filenum) chunk = bytes.left# ELSE read.bytes$ = INPUT$(100, filenum) chunk = 100 END IF '(*** XOR the bytes with encryption key. ***) FOR byte.count = 1 TO chunk changed.byte$ = changed.byte$ + CHR$(ASC(MID$(read.bytes$, byte.count, 1)) XOR ekey) NEXT byte.count '(*** Print it to the output file. ***) PRINT #outputnum, changed.byte$; changed.byte$ = "" LOOP END IF '(*** Close the files we used. ***) CLOSE filenum, outputnum '(*** All done with no errors, so return a TRUE value. ***) File.XOR = -1 END FUNCTION