1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
|
using System;
using Org.BouncyCastle.Asn1;
using Org.BouncyCastle.Utilities;
// ASN.1 Encoding for a
// Classic McEliece private key for fully populated:
// <pre>
// McEliecePrivateKey ::= SEQUENCE {
// Version INTEGER {v0(0)} -- version (round 3)
// delta OCTET STRING, -- nonce
// C OCTET STRING, -- column selections
// g OCTET STRING, -- monic irreducible polynomial
// alpha OCTET STRING, -- field orderings
// s OCTET STRING, -- random n-bit string
// PublicKey [0] IMPLICIT McEliecePublicKey OPTIONAL
// -- see next section
// }
// </pre>
namespace Org.BouncyCastle.Pqc.Asn1
{
// TODO[api] Should only be Asn1Encodable
public class CmcePrivateKey
: Asn1Object
{
public static CmcePrivateKey GetInstance(Object o)
{
if (o == null)
return null;
if (o is CmcePrivateKey cmcePrivateKey)
return cmcePrivateKey;
return new CmcePrivateKey(Asn1Sequence.GetInstance(o));
}
private int version;
private byte[] delta;
private byte[] c;
private byte[] g;
private byte[] alpha;
private byte[] s;
private CmcePublicKey publicKey;
public CmcePrivateKey(int version, byte[] delta, byte[] c, byte[] g, byte[] alpha, byte[] s, CmcePublicKey pubKey = null)
{
this.version = version;
if (version != 0)
{
throw new Exception("unrecognized version");
}
this.delta = Arrays.Clone(delta);
this.c = Arrays.Clone(c);
this.g = Arrays.Clone(g);
this.alpha = Arrays.Clone(alpha);
this.s = Arrays.Clone(s);
this.publicKey = pubKey;
}
private CmcePrivateKey(Asn1Sequence seq)
{
version = DerInteger.GetInstance(seq[0]).Value.IntValue;
if (version != 0)
{
throw new Exception("unrecognized version");
}
delta = Arrays.Clone(Asn1OctetString.GetInstance(seq[1]).GetOctets());
c = Arrays.Clone(Asn1OctetString.GetInstance(seq[2]).GetOctets());
g = Arrays.Clone(Asn1OctetString.GetInstance(seq[3]).GetOctets());
alpha = Arrays.Clone(Asn1OctetString.GetInstance(seq[4]).GetOctets());
s = Arrays.Clone(Asn1OctetString.GetInstance(seq[5]).GetOctets());
// todo optional publickey
if(seq.Count == 7)
{
publicKey = CmcePublicKey.GetInstance(seq[6]);
}
}
public int Version => version;
public byte[] Delta => Arrays.Clone(delta);
public byte[] C => Arrays.Clone(c);
public byte[] G => Arrays.Clone(g);
public byte[] Alpha => Arrays.Clone(alpha);
public byte[] S => Arrays.Clone(s);
public CmcePublicKey PublicKey => publicKey;
public Asn1Object ToAsn1Primitive()
{
Asn1EncodableVector v = new Asn1EncodableVector(7);
v.Add(new DerInteger(version));
v.Add(new DerOctetString(delta));
v.Add(new DerOctetString(c));
v.Add(new DerOctetString(g));
v.Add(new DerOctetString(alpha));
v.Add(new DerOctetString(s));
// todo optional publickey
if (publicKey != null)
{
v.Add(new CmcePublicKey(publicKey.T));
}
return new DerSequence(v);
}
internal override IAsn1Encoding GetEncoding(int encoding)
{
return ToAsn1Primitive().GetEncoding(encoding);
}
internal override IAsn1Encoding GetEncodingImplicit(int encoding, int tagClass, int tagNo)
{
return ToAsn1Primitive().GetEncodingImplicit(encoding, tagClass, tagNo);
}
internal sealed override DerEncoding GetEncodingDer()
{
return ToAsn1Primitive().GetEncodingDer();
}
internal sealed override DerEncoding GetEncodingDerImplicit(int tagClass, int tagNo)
{
return ToAsn1Primitive().GetEncodingDerImplicit(tagClass, tagNo);
}
protected override bool Asn1Equals(Asn1Object asn1Object)
{
return ToAsn1Primitive().CallAsn1Equals(asn1Object);
}
protected override int Asn1GetHashCode()
{
return ToAsn1Primitive().CallAsn1GetHashCode();
}
}
}
|