Modyfy Splitter: Additional constructors. Now only k and m are necessary
[splitter-ng] / Splitter-ng-plugin-jerasure / src / jerasureplugin / CodecCauchyGood.java
1 package jerasureplugin;
2
3
4
5 import java.util.ArrayList;
6 import java.util.Collections;
7 import java.util.HashMap;
8 import java.util.List;
9 import java.util.Map;
10 import java.util.Map.Entry;
11
12 import splitterng.plugin.CodecDescription;
13 import splitterng.plugin.interfaces.SplitterCodec;
14 import eu.vandertil.jerasure.jni.Cauchy;
15 import eu.vandertil.jerasure.jni.Jerasure;
16
17 public class CodecCauchyGood implements SplitterCodec {
18
19         public final static String codecID = "JerasureCauchyGood";
20         public final static String codecName = "Jerasure Cauchy Good";
21         public final static String codecDescriptionText = "This Codec implements CauchyReedSolomon coding with a good Jerasure."
22                         + "When m = 2, w <=11 and k <= 1023, it will use the optimal RAID-6 matrix. Otherwise, it generates a good matrix by calling cauchy_original_coding_matrix()"
23                         + "and then cauchy_improve_coding_matrix()."
24                         + "\nRequirements:   (fragmentsize % (packetsize * w)) == 0";
25
26         public final static Map <String, Integer []> codecParameterMinMax;
27         public final static Map <String, Integer> codecParameterDefaults;
28
29         private int k,m,w,packetsize;
30         
31         static {
32                 Map <String, Integer []> tmpMap = new HashMap<String, Integer[]>();
33                 tmpMap.put("k", new Integer[] {new Integer(1),new Integer(Integer.MAX_VALUE)});
34                 tmpMap.put("m", new Integer[] {new Integer(1),new Integer(Integer.MAX_VALUE)});
35                 tmpMap.put("w", new Integer[] {new Integer(1),new Integer(Integer.MAX_VALUE)});
36                 tmpMap.put("packetsize", new Integer[] {new Integer(1),new Integer(Integer.MAX_VALUE)});
37                 
38                 codecParameterMinMax  = Collections.unmodifiableMap(tmpMap);                            
39
40                 Map <String, Integer> tmpMap2 = new HashMap<String, Integer>();
41                 tmpMap2.put("w", new Integer(8));
42                 tmpMap2.put("packetsize", new Integer(8));
43                 
44                 codecParameterDefaults  = Collections.unmodifiableMap(tmpMap2);                         
45         }
46         
47         private static final CodecDescription codecDescription = new CodecDescription(
48         codecID, codecName, codecDescriptionText, codecParameterMinMax, codecParameterDefaults);
49         
50         private int[] matrix;
51         private int[] bitmatrix;
52         private byte[][] coding_ptrs;
53         private byte[][] data_ptrs;
54         private byte[][] dataAndCoding_ptrs;
55  
56         private int [] erasures;
57         private int numerased=0;
58
59         
60         public static final CodecDescription getCodecDescription(){
61                 //System.out.println("JerasureCodecParity: getCodecDescription: "+JerasureCodecParity.codecDescription);
62                 return CodecCauchyGood.codecDescription;
63         }
64         
65         /**
66          * @param codecParameter
67          */
68         public CodecCauchyGood(Map<String, Integer> codecParameter) {
69                 super();
70                 
71                 //Test CodecParameter
72                 for (Entry<String, Integer[]> requiredEntry : codecParameterMinMax
73                                 .entrySet()) {
74                         if (codecParameter.containsKey(requiredEntry.getKey())) {
75                                 // Test ob Parameter vorhanden und in den gültigen grenzen
76                                 // liegen
77                                 //System.out.println("Test" +codecParameter.get(requiredEntry.getKey()) +" "+  requiredEntry.getValue()[0]);
78                                 if (codecParameter.get(requiredEntry.getKey()) < requiredEntry.getValue()[0])
79                                         throw new IllegalArgumentException(
80                                                         "unzulässiger Wert für Parameter: "
81                                                                         + requiredEntry.getKey() + " < "
82                                                                         + requiredEntry.getValue()[0]);
83                                 if (codecParameter.get(requiredEntry.getKey()) > requiredEntry.getValue()[1])
84                                         throw new IllegalArgumentException(
85                                                         "unzulässiger Wert für Parameter: "
86                                                                         + requiredEntry.getKey() + " > "
87                                                                         + requiredEntry.getValue()[1]);
88                         } else if (codecParameterDefaults.containsKey(requiredEntry.getKey())) {
89                                 codecParameter.put(requiredEntry.getKey(), codecParameterDefaults.get(requiredEntry.getKey()));
90                         } else {
91                                 throw new IllegalArgumentException("Missing Codec Parameter: "
92                                                 + requiredEntry.getKey());
93                         }
94                 }
95                 
96                 k=(int)codecParameter.get("k");
97                 m=(int)codecParameter.get("m");
98                 w=(int)codecParameter.get("w");
99                 packetsize=(int)codecParameter.get("packetsize");
100                 matrix= Cauchy.cauchy_good_general_coding_matrix(k, m, w);
101                 bitmatrix = Jerasure.jerasure_matrix_to_bitmatrix(k, m, w, matrix);
102                 erasures = new int [k+m+1];
103                 
104         }
105
106         @Override
107         public byte[][] decode(byte[][] dataAndCoding_ptrs, boolean [] erased){
108                 //TODO Array Testen ob zulässig? eventuell nicht, da es hier bremsen könnte
109                 int fragmentsize = dataAndCoding_ptrs[0].length;
110                 
111                 if (data_ptrs == null || (data_ptrs.length != k) || (data_ptrs[0].length != fragmentsize)){
112                         data_ptrs = new byte[k][fragmentsize];
113                 }                       
114                 
115                 if (coding_ptrs == null || (coding_ptrs.length != m) || (coding_ptrs[0].length != fragmentsize)){
116                         coding_ptrs = new byte[m][fragmentsize];
117                 }
118                 
119                 for (int i=0; i<k ; i++){
120                         data_ptrs[i]=dataAndCoding_ptrs[i];
121                 }
122                 for (int i=k; i<k+m ; i++){
123                         coding_ptrs[i-k]=dataAndCoding_ptrs[i];
124                 }
125                 
126                 //Preparing Erasures
127                 numerased=0;
128                 for (int i=0; i<m+k; i++){
129                         if (erased[i]==true){
130                                 erasures[numerased]=i;
131                                 numerased++;
132                         }
133                 }
134                 erasures[numerased]=-1;
135                 
136
137                 //Jerasure.jerasure_matrix_encode(k, m, w, matrix, data_ptrs, coding_ptrs, blocksize);
138                 Jerasure.jerasure_bitmatrix_decode(k, m, w, bitmatrix, false, erasures, data_ptrs, coding_ptrs, fragmentsize, packetsize);
139
140                 return data_ptrs;
141         }
142
143         @Override
144         public byte[][] encode(byte[][] data_ptrs){
145                 //TODO Array Testen ob zulässig? eventuell nicht, da es hier bremsen könnte
146                 // buffersize%(sizeof(int)*w*k) == 0
147                 int fragmentsize = data_ptrs[0].length;
148                 
149                 if (coding_ptrs == null || (coding_ptrs.length != m) || (coding_ptrs[0].length != fragmentsize)){
150                         coding_ptrs = new byte[m][fragmentsize];
151                 }
152                 
153                 //Jerasure.jerasure_matrix_encode(k, m, w, matrix, data_ptrs, coding_ptrs, blocksize);
154                 Jerasure.jerasure_bitmatrix_encode(k, m, w, bitmatrix, data_ptrs, coding_ptrs, fragmentsize, packetsize);
155                 
156                 if (dataAndCoding_ptrs == null || (dataAndCoding_ptrs.length != k+m) || (dataAndCoding_ptrs[0].length != fragmentsize)){
157                         dataAndCoding_ptrs = new byte[k+m][fragmentsize];
158                 }
159                 //Data Blocks
160                 for (int i=0; i<k ; i++){
161                         dataAndCoding_ptrs[i]=data_ptrs[i];
162                 }
163                 for (int i=k; i<k+m ; i++){
164                         dataAndCoding_ptrs[i]=coding_ptrs[i-k];
165                 }
166                                 
167                 return dataAndCoding_ptrs;
168         }
169
170
171 }