random access stream cipher Some time ago I was working in a pet project for a type of database engine. And I thought about securing the data in disk with encryption.. and since the main code was already developed.. I had a few requirements..


a simple stream class that I could hook instead of my file stream had
to support random access (both read/write at random positions)
be able to work at any byte position (since the data might not be aligned)
encrypt/decrypt only the requested data, not the all file,(because the file maybe several MB)
fast encryption/decryption, since this was for a database system


nowhere on the web I found information about this, or implementation of such code.
Normal stream ciphers don't support random access/lookup, and block ciphers require the data to be aligned and in fixed blocks.. 
So I thought about developing my own. I do know that developing your own encryption is always a bad choice.. but this was kind of theoretical exercise..

So I would like to present you the code.. just to see how far of I am from a security point of view

First the stream is initialized with a password.. but that password is not used for the encryption itself.. it is used as a seed to scramble an array of 256 values in hope of of increasing the key space

public CipherStream(String sKey,Stream oStream) 
{
    _oStream = oStream;
    //initialize key space
    _oVector = new byte[256];
    for(int i = 0; i &lt;= 255; i++)
    _oVector[i] = (byte)i;
    //shuffle the keyspace
    for (int i = 0; i &lt;= 255; i++)//shuffle the box
    {
        //shuffle this item with other
        //other is chosen by char(i) of password
        //and the currently shuffling vector(I)
        // this means that even repeating passwords 'aaaaaa' will produce random results
        int j = ((sKey[i % sKey.Length]) + _oVector[i]) % 256;
        byte cTemp = _oVector[i];
        _oVector[i] = _oVector[j];
        _oVector[j] = cTemp;
    }
}


after this all we have to do is choose the cipher byte for the position we are trying to read/write from.. in my implementation I used xor, witch I know is not the most safe.. but that is can be changed and is not the core of the algorithm..

public override void Write(byte[] buffer, int offset, int count)
{
    long nPosition = this.Position;
    for (int i = offset; i &lt; count; i++)
    {
        byte oPlain = buffer[i];
        byte nKey = GetKey(nPosition);
        byte oCypher = (byte)(oPlain ^ nKey);

        buffer[i] = oCypher;

        nPosition++;
    }
    _oStream.Write(buffer, offset, count);
}


the 'key' to the byte is chosen from the key vector dependently from the position we are trying to access.. calculations are done so that there are no repetitions and the chosen value is as random as possible

private byte GetKey(long nPosition) 
{
    byte nOffset = _oVector[nPosition % _oVector.Length];
    byte nOffset2 = _oVector[(nPosition / (nOffset + 1)) % _oVector.Length];

    int nDif = nOffset - nOffset2;
    if (nDif &lt; 0)
        nDif += 255;
    byte nKey = (Byte)(nDif % 256);

    return nKey;
}


I did try to render the stream as a bitmap.. just so make sure no patterns where obvious.. and did some fine tunning there.. and it seemed ok..

the best I can describe this algorithm is a 'deterministic predictable pseudo-random generator'
where I can just ask 'give me the nth random number', and the seed is a 2048 bit vector
that is initialized randomly with a password..

how far am I from a solution? Is this completely insecure? or there is not even point of trying because there is no solution for this 'random access stream'  problem?
The idea


  'deterministic predictable pseudo-random generator' where I can just ask 'give me the nth random number'


is already known, and there are some stream ciphers that work like this (like CTR mode of a block cipher, or the Salsa/ChaCha family of stream ciphers).
Usually they don't produce a single byte, but some larger block of consecutive key stream bytes, which is more efficient if you don't have single bytes to encrypt, and (as mentioned by user4982's answer) doesn't restrict you, as you don't have to use all these key stream bytes to encrypt/decrypt your piece of data.

I won't look at your specific cipher (it is too much on the code level for me), but it is probably not a secure one.

The idea itself (even when implemented with an perfectly secure stream cipher) has a problem when used for random access file encryption: You will be having (at several points of time) different pieces of data encrypted with the same piece of keystream, which then leads to the two-times-pad problem, if a potential attacker could look at your encrypted file at different points in time.

You'll need to reencrypt larger blocks with a new initialization vector to avoid this.