* Stubed System.ComponentModel/LicenseContext.cs
[mono.git] / mcs / class / corlib / Mono.Security.Cryptography / CryptoTools.cs
1 //
2 // Mono.Security.Cryptography.CryptoTools
3 //      Shared class for common cryptographic functionalities
4 //
5 // Authors:
6 //      Sebastien Pouliot (spouliot@motus.com)
7 //
8 // (C) 2002, 2003 Motus Technologies Inc. (http://www.motus.com)
9 //
10
11 using System;
12 using System.Security.Cryptography;
13
14 namespace Mono.Security.Cryptography {
15
16         public class KeyBuilder {
17         
18                 static private RandomNumberGenerator rng;
19         
20                 static KeyBuilder () 
21                 {
22                         rng = RandomNumberGenerator.Create ();
23                 }
24         
25                 static public byte[] Key (int size) 
26                 {
27                         byte[] key = new byte [size];
28                         rng.GetBytes (key);
29                         return key;
30                 }
31         
32                 static public byte[] IV (int size) 
33                 {
34                         byte[] iv = new byte [size];
35                         rng.GetBytes (iv);
36                         return iv;
37                 }
38         }
39         
40         // Process an array as a sequence of blocks
41         public class BlockProcessor {
42                 private ICryptoTransform transform;
43                 private byte[] block;
44                 private int blockSize;  // in bytes (not in bits)
45                 private int blockCount;
46         
47                 public BlockProcessor (ICryptoTransform transform) 
48                         : this (transform, transform.InputBlockSize) {} 
49         
50                 // some Transforms (like HashAlgorithm descendant) return 1 for
51                 // block size (which isn't their real internal block size)
52                 public BlockProcessor (ICryptoTransform transform, int blockSize)
53                 {
54                         this.transform = transform;
55                         this.blockSize = blockSize;
56                         block = new byte [blockSize];
57                 }
58         
59                 ~BlockProcessor () 
60                 {
61                         // zeroize our block (so we don't retain any information)
62                         Array.Clear (block, 0, blockSize);
63                 }
64         
65                 public void Initialize ()
66                 {
67                         Array.Clear (block, 0, blockSize);
68                         blockCount = 0;
69                 }
70         
71                 public void Core (byte[] rgb) 
72                 {
73                         Core (rgb, 0, rgb.Length);
74                 }
75         
76                 public void Core (byte[] rgb, int ib, int cb) 
77                 {
78                         // 1. fill the rest of the "block"
79                         int n = System.Math.Min (blockSize - blockCount, cb);
80                         Array.Copy (rgb, ib, block, blockCount, n); 
81                         blockCount += n;
82         
83                         // 2. if block is full then transform it
84                         if (blockCount == blockSize) {
85                                 transform.TransformBlock (block, 0, blockSize, block, 0);
86         
87                                 // 3. transform any other full block in specified buffer
88                                 int b = (int) ((cb - n) / blockSize);
89                                 for (int i=0; i < b; i++) {
90                                         transform.TransformBlock (rgb, n, blockSize, block, 0);
91                                         n += blockSize;
92                                 }
93         
94                                 // 4. if data is still present fill the "block" with the remainder
95                                 blockCount = cb - n;
96                                 if (blockCount > 0)
97                                         Array.Copy (rgb, n, block, 0, blockCount);
98                         }
99                 }
100         
101                 public byte[] Final () 
102                 {
103                         return transform.TransformFinalBlock (block, 0, blockCount);
104                 }
105         }
106 }