// Path: src/main/java/trabe/AbeInputStream.java
// public class AbeInputStream extends DataInputStream {
//     private final String       PUB_MISSING_ERROR = "Can't read Elements without the public master key.";
// 
//     private AbePublicKey publicKey;
// 
//     public AbeInputStream(InputStream in, AbePublicKey publicKey) {
//     	super(in);
//     	this.publicKey = publicKey;
//     }
// 
//     /**
//      * If you use this constructor you need to manually set the public key before reading any elements.
//      * 
//      * @param in    Underlying input stream
//      */
//     public AbeInputStream(InputStream in) {
//     	this(in, null);
// 	}
// 
// 	public void setPublicKey(AbePublicKey pubKey) {
//         this.publicKey = pubKey;
//     }
// 
//     // only used for the curve parameters and attributes, no need for fancy encodings
//     // since internal attribute representation only uses [a-zA-Z0-9:_]
//     public String readString() throws IOException {
//         int length = readInt();
//         byte[] bytes = new byte[length];
//         readFully(bytes);
//         return new String(bytes, AbeSettings.STRINGS_LOCALE);
//     }
// 
//     public Element readElement() throws IOException {
//         if (readBoolean()) {
//             return null;
//         }
//         if (publicKey == null) throw new IOException(PUB_MISSING_ERROR);
//         int fieldIndex = readInt();
//         int length = readInt();
//         byte[] bytes = new byte[length];
//         readFully(bytes);
//         Element e = publicKey.getPairing().getFieldAt(fieldIndex).newElementFromBytes(bytes);
// 
//         // this is a workaround because it.unisa.dia.gas.plaf.jpbc.field.curve.CurveElement does not serialize the infFlag
//         boolean instOfCurveElementAndInf = readBoolean();
//         if (instOfCurveElementAndInf) {
//             //e.setToZero(); // according to the code this simply sets the infFlag to 1
//             throw new IOException("The point is infinite. This shouldn't happen.");
//         }
//         return e;
//     }
// }
// 
// Path: src/main/java/trabe/AbeOutputStream.java
// public class AbeOutputStream extends DataOutputStream {
//     
//     private final AbePublicKey pubKey;
// 
//     public AbeOutputStream(OutputStream out, AbePublicKey pubKey) {
//         super(out);
//         this.pubKey = pubKey;
//     }
// 
//     // only used for the curve parameters and attributes, no need for fancy encodings
// 
//     /**
//      * Writes a string to the stream with the locale specified in
//      * {@link AbeSettings#STRINGS_LOCALE} and prepends the length of the
//      * serialized bytes.
//      * @param string    String to write
//      * @throws IOException see {@link #write(byte[])}
//      */
//     public void writeString(String string) throws IOException {
//         byte[] bytes = string.getBytes(AbeSettings.STRINGS_LOCALE);
//         writeInt(bytes.length);
//         write(bytes);
//     }
// 
//     public void writeElement(Element elem) throws IOException {
//         writeBoolean(elem == null);
//         if (elem == null) {
//             return;
//         }
//         writeInt(pubKey.getPairing().getFieldIndex(elem.getField()));
//         byte[] bytes = elem.toBytes();
//         writeInt(bytes.length);
//         write(bytes);
// 
//         // this is a workaround because it.unisa.dia.gas.plaf.jpbc.field.curve.CurveElement does not serialize the infFlag
//         writeBoolean(elem instanceof CurveElement && elem.isZero());
//         if (elem instanceof CurveElement && elem.isZero()) {
//             throw new IOException("Infinite element detected. They should not happen.");
//         }
//     }
// 
// }


import it.unisa.dia.gas.jpbc.Element;
import trabe.AbeInputStream;
import trabe.AbeOutputStream;
import java.io.IOException;

package trabe.lw14.policy;



/**
 *
 */
public class LsssMatrixCell {
    public int i;
    public int j;
    public int value;
    public String attribute;
    public Element hashedElement;

    private LsssMatrixCell(){}

    public LsssMatrixCell(int i, int j, int value, String attribute, Element hashedElement) {
        this.i = i;
        this.j = j;
        this.value = value;
        this.attribute = attribute;
        this.hashedElement = hashedElement;
    }

    public String toString(){
        return "["+i+","+j+"] " + attribute + ": " + value + "(" + hashedElement + ")";
    }

    public void writeToStream(AbeOutputStream stream) throws IOException {
        stream.writeInt(value);
        stream.writeString(attribute);
        stream.writeElement(hashedElement);
    }


// Path: src/main/java/trabe/AbeInputStream.java
// public class AbeInputStream extends DataInputStream {
//     private final String       PUB_MISSING_ERROR = "Can't read Elements without the public master key.";
// 
//     private AbePublicKey publicKey;
// 
//     public AbeInputStream(InputStream in, AbePublicKey publicKey) {
//     	super(in);
//     	this.publicKey = publicKey;
//     }
// 
//     /**
//      * If you use this constructor you need to manually set the public key before reading any elements.
//      * 
//      * @param in    Underlying input stream
//      */
//     public AbeInputStream(InputStream in) {
//     	this(in, null);
// 	}
// 
// 	public void setPublicKey(AbePublicKey pubKey) {
//         this.publicKey = pubKey;
//     }
// 
//     // only used for the curve parameters and attributes, no need for fancy encodings
//     // since internal attribute representation only uses [a-zA-Z0-9:_]
//     public String readString() throws IOException {
//         int length = readInt();
//         byte[] bytes = new byte[length];
//         readFully(bytes);
//         return new String(bytes, AbeSettings.STRINGS_LOCALE);
//     }
// 
//     public Element readElement() throws IOException {
//         if (readBoolean()) {
//             return null;
//         }
//         if (publicKey == null) throw new IOException(PUB_MISSING_ERROR);
//         int fieldIndex = readInt();
//         int length = readInt();
//         byte[] bytes = new byte[length];
//         readFully(bytes);
//         Element e = publicKey.getPairing().getFieldAt(fieldIndex).newElementFromBytes(bytes);
// 
//         // this is a workaround because it.unisa.dia.gas.plaf.jpbc.field.curve.CurveElement does not serialize the infFlag
//         boolean instOfCurveElementAndInf = readBoolean();
//         if (instOfCurveElementAndInf) {
//             //e.setToZero(); // according to the code this simply sets the infFlag to 1
//             throw new IOException("The point is infinite. This shouldn't happen.");
//         }
//         return e;
//     }
// }
// 
// Path: src/main/java/trabe/AbeOutputStream.java
// public class AbeOutputStream extends DataOutputStream {
//     
//     private final AbePublicKey pubKey;
// 
//     public AbeOutputStream(OutputStream out, AbePublicKey pubKey) {
//         super(out);
//         this.pubKey = pubKey;
//     }
// 
//     // only used for the curve parameters and attributes, no need for fancy encodings
// 
//     /**
//      * Writes a string to the stream with the locale specified in
//      * {@link AbeSettings#STRINGS_LOCALE} and prepends the length of the
//      * serialized bytes.
//      * @param string    String to write
//      * @throws IOException see {@link #write(byte[])}
//      */
//     public void writeString(String string) throws IOException {
//         byte[] bytes = string.getBytes(AbeSettings.STRINGS_LOCALE);
//         writeInt(bytes.length);
//         write(bytes);
//     }
// 
//     public void writeElement(Element elem) throws IOException {
//         writeBoolean(elem == null);
//         if (elem == null) {
//             return;
//         }
//         writeInt(pubKey.getPairing().getFieldIndex(elem.getField()));
//         byte[] bytes = elem.toBytes();
//         writeInt(bytes.length);
//         write(bytes);
// 
//         // this is a workaround because it.unisa.dia.gas.plaf.jpbc.field.curve.CurveElement does not serialize the infFlag
//         writeBoolean(elem instanceof CurveElement && elem.isZero());
//         if (elem instanceof CurveElement && elem.isZero()) {
//             throw new IOException("Infinite element detected. They should not happen.");
//         }
//     }
// 
// }


// Path: src/main/java/trabe/lw14/policy/LsssMatrixCell.java
import it.unisa.dia.gas.jpbc.Element;
import trabe.AbeInputStream;
import trabe.AbeOutputStream;
import java.io.IOException;

package trabe.lw14.policy;



/**
 *
 */
public class LsssMatrixCell {
    public int i;
    public int j;
    public int value;
    public String attribute;
    public Element hashedElement;

    private LsssMatrixCell(){}

    public LsssMatrixCell(int i, int j, int value, String attribute, Element hashedElement) {
        this.i = i;
        this.j = j;
        this.value = value;
        this.attribute = attribute;
        this.hashedElement = hashedElement;
    }

    public String toString(){
        return "["+i+","+j+"] " + attribute + ": " + value + "(" + hashedElement + ")";
    }

    public void writeToStream(AbeOutputStream stream) throws IOException {
        stream.writeInt(value);
        stream.writeString(attribute);
        stream.writeElement(hashedElement);
    }


    public static LsssMatrixCell readFromStream(AbeInputStream stream) throws IOException {
