1f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrompackage org.bouncycastle.crypto;
2f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
3f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom/**
4f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom * a wrapper for block ciphers with a single byte block size, so that they
5f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom * can be treated like stream ciphers.
6f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom */
7f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrompublic class StreamBlockCipher
8f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    implements StreamCipher
9f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom{
10f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    private BlockCipher  cipher;
11f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
12f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    private byte[]  oneByte = new byte[1];
13f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
14f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
15f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * basic constructor.
16f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     *
17f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param cipher the block cipher to be wrapped.
18f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @exception IllegalArgumentException if the cipher has a block size other than
19f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * one.
20f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
21f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public StreamBlockCipher(
22f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        BlockCipher cipher)
23f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
24f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        if (cipher.getBlockSize() != 1)
25f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        {
26f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom            throw new IllegalArgumentException("block cipher block size != 1.");
27f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        }
28f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
29f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        this.cipher = cipher;
30f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
31f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
32f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
33f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * initialise the underlying cipher.
34f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     *
35f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param forEncryption true if we are setting up for encryption, false otherwise.
36f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param params the necessary parameters for the underlying cipher to be initialised.
37f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
38f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public void init(
39f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        boolean forEncryption,
40f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        CipherParameters params)
41f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
42f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        cipher.init(forEncryption, params);
43f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
44f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
45f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
46f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * return the name of the algorithm we are wrapping.
47f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     *
48f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @return the name of the algorithm we are wrapping.
49f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
50f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public String getAlgorithmName()
51f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
52f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        return cipher.getAlgorithmName();
53f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
54f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
55f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
56f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * encrypt/decrypt a single byte returning the result.
57f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     *
58f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param in the byte to be processed.
59f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @return the result of processing the input byte.
60f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
61f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public byte returnByte(
62f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        byte    in)
63f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
64f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        oneByte[0] = in;
65f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
66f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        cipher.processBlock(oneByte, 0, oneByte, 0);
67f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
68f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        return oneByte[0];
69f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
70f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
71f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
72f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * process a block of bytes from in putting the result into out.
73f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     *
74f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param in the input byte array.
75f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param inOff the offset into the in array where the data to be processed starts.
76f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param len the number of bytes to be processed.
77f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param out the output buffer the processed bytes go into.
78f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @param outOff the offset into the output byte array the processed data stars at.
79f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * @exception DataLengthException if the output buffer is too small.
80f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
81f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public void processBytes(
82f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        byte[]  in,
83f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        int     inOff,
84f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        int     len,
85f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        byte[]  out,
86f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        int     outOff)
87f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        throws DataLengthException
88f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
89f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        if (outOff + len > out.length)
90f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        {
91f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom            throw new DataLengthException("output buffer too small in processBytes()");
92f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        }
93f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
94f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        for (int i = 0; i != len; i++)
95f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        {
96f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom                cipher.processBlock(in, inOff + i, out, outOff + i);
97f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        }
98f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
99f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom
100f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    /**
101f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * reset the underlying cipher. This leaves it in the same state
102f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     * it was at after the last init (if there was one).
103f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom     */
104f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    public void reset()
105f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    {
106f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom        cipher.reset();
107f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom    }
108f7433bf801526ab2a93e1cadb7a25ded87f43ed4Brian Carlstrom}
109