/*	Konton2.h	*/
/*	Copyright (C) 2002, 2003, 2004 by J. David Sexton. All rights reserved.	*/

/*
	"Konton" is Japanese for "primordial chaos."  It's pronounced "kone-tone."
	Konton2 is a stream cipher that encrypts byte-by-byte. It features feedback
	from the encryption and decryption functions so that different plaintexts
	encrypted with the same key are encrypted with different keystreams.

	KonSetCryptKey only needs to be called when the key is changed or initially set.
		The key can be any length from zero bytes to the limit of the size_t type.
		Before it returns, KonSetCryptKey calls KonInitCrypt; a call to KonInitCrypt
		immediately after a call to KonSetCryptKey is unnecessary but harmless.
	KonInitCrypt initializes the state data using the key set by KonSetCryptKey.
		KonInitCrypt is called before a set of data is encrypted or decrypted.
	KonIndexState initializes the state data using the key set by KonSetCryptKey and
		an index value. In indexed encryption and decryption, the data is processed
		in blocks with each block accompanied by its index value. KonIndexState is
		called with the index value before each block of data is encrypted or 
		decrypted. After KonIndexState is called, KonInitCrypt must not be called.
	KonDoubleIndexState is just like KonIndexState, except that it uses two index
		values instead of one, thus squaring the number of blocks that can be
		index-encrypted with the same key.
	KonQuadrupleIndexState is just like KonIndexState, except that it uses four index
		values instead of one, thus raising to the fourth power the number of blocks
		that can be index-encrypted with the same key.
	KonCryptSynch encrypts and decrypts data without the feedback mentioned above;
		the keystream is unaffected by the plaintext. In this mode Konton2 runs as
		a synchronous stream cipher. This mode lacks the error propagation of
		Konton2's normal mode used by all the other encryption and decryption
		functions.
	KonEncryptData encrypts data with the feedback mentioned above.
	KonDecryptData decrypts data encrypted with KonEncryptData.
	KonEncryptASCII encrypts only those bytes with values > 31 and < 127, and it
		encrypts them into bytes with values > 31 and < 127. In other words, it
		encrypts ASCII text into ASCII text and leaves other bytes untouched.
	KonDecryptASCII decrypts text encrypted with KonEncryptASCII.
	KonEncryptText encrypts only those bytes with values > 31, and it encrypts them
		into bytes with values > 31. In other words, it encrypts text into text
		and leaves other bytes untouched.
	KonDecryptText decrypts text encrypted with KonEncryptText.
	KonZapCrypt zeros all of the state data.
	KonNextPRndNum is Konton2's PRNG.
*/

#ifndef Konton_H
#define Konton_H

#include 
#include "KonTyps2.h"

	void	KonSetCryptKey (register KonEnvStruct *theEnv, const void *theKey,
						size_t keyLength);
	void	KonInitCrypt (register KonEnvStruct *theEnv);
	void	KonIndexState (register KonEnvStruct *theEnv,
						register Kon4ByteInt theIndex);
	void	KonDoubleIndexState (register KonEnvStruct *theEnv,
						register Kon4ByteInt aIndex,
						register Kon4ByteInt bIndex);
	void	KonQuadrupleIndexState (register KonEnvStruct *theEnv,
						register Kon4ByteInt aIndex,
						register Kon4ByteInt bIndex,
						register Kon4ByteInt cIndex,
						register Kon4ByteInt dIndex);
	void	KonCryptSynch (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonEncryptData (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonDecryptData (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonEncryptASCII (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonDecryptASCII (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonEncryptText (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonDecryptText (register KonEnvStruct *theEnv, void *theData,
						size_t theLength);
	void	KonZapCrypt (register KonEnvStruct *theEnv);
Kon4ByteInt	KonNextPRndNum (register KonEnvStruct *theEnv);

#endif

/*

Here is some example code which shows how to call Konton2 functions.

#include "Konton2.h"

			Prototype non-Konton2 functions.
void	OSHoldMemoryFunction (void *theBlock, size_t theLength);
void	OSUnholdMemoryFunction (void *theBlock, size_t theLength);
void	MyGetCryptKeyFunction (void *theKey, size_t theLength);
void	MyEraseKeyFunction (void *theKey, size_t theLength);
void	MySendOrStoreDataFunction (void *theData, size_t theLength);
void	MyReceiveOrRetrieveDataFunction (void *theData, size_t theLength);

			Declare the KonEnvStruct variable.
KonEnvStruct	gKonEnv;


			Now we're inside a function.

			Declare data blocks, the key, and the index for indexed encryption.
unsigned char	theData [kDataLength];
unsigned char	otherData [kOtherDataLength];
unsigned char	theKey [kMyKeyLength];
Kon4ByteInt		theIndex;

			It's important that we don't allow the KonEnvStruct variable
			or the key to be written to the disk by OSes that use virtual memory.
			We really SHOULD follow the same rule for the plaintext to be
			encrypted.
OSHoldMemoryFunction (&gKonEnv, sizeof (gKonEnv));
OSHoldMemoryFunction (theKey, sizeof (theKey));

			Get and then set the key
MyGetCryptKeyFunction (theKey, sizeof (theKey));
KonSetCryptKey (&gKonEnv, theKey, sizeof (theKey));

			Erase the key, then we can unhold it.
MyEraseKeyFunction (theKey, sizeof (theKey));
OSUnholdMemoryFunction (theKey, sizeof (theKey));

			We don't have to call KonInitCrypt here because the last
			thing KonSetCryptKey does is call it.
			It wouldn't do any harm if we called it anyway.

			Encrypt some stuff.
KonEncryptData (&gKonEnv, theData, sizeof (theData));

			We're going to encrypt some other stuff with the same key,
			so this time we MUST call KonInitCrypt.
KonInitCrypt (&gKonEnv);
KonEncryptData (&gKonEnv, otherData, sizeof (otherData));

			We're going to decrypt what we encrypted above, so we have to call
			KonInitCrypt again.
KonInitCrypt (&gKonEnv);
KonDecryptData (&gKonEnv, theData, sizeof (theData));

			Now we'll do some indexed encryption and decryption.
			We'll assume that KonSetCryptKey has already been called.

			First we have to call KonIndexState with the index of the block.
			Note that after we call KonIndexState we DON'T call KonInitCrypt.
KonIndexState (&gKonEnv, theIndex);

			Encrypt the data.
KonEncryptData (&gKonEnv, theData, sizeof (theData));

			Send (or store) the index and the data.
MySendOrStoreDataFunction (&theIndex, sizeof (theIndex));
MySendOrStoreDataFunction (theData, sizeof (theData));

			Now we'll do indexed decryption. Once again,
			we'll assume that KonSetCryptKey has already been called.

			Receive (or retrieve) the index and the data.
MyReceiveOrRetrieveDataFunction (&theIndex, sizeof (theIndex));
MyReceiveOrRetrieveDataFunction (theData, sizeof (theData));

			Call KonIndexState with the index of the block,
			but don't call KonInitCrypt.
KonIndexState (&gKonEnv, theIndex);

			Decrypt the data.
KonDecryptData (&gKonEnv, theData, sizeof (theData));

			We're finished with all our encryption and decryption.

			Wipe our KonEnvStruct variable clean, then we can unhold it.
KonZapCrypt (&gKonEnv);
OSUnholdMemoryFunction (&gKonEnv, sizeof (gKonEnv));

*/

    Source: geocities.com/da5id65536