fromEd25519Seed static method

String fromEd25519Seed(
  1. Uint8List seed
)

Creates a not encrypted PKCS#8 file from a 32-Byte-Ed25519-Seed.

PKCS#8 structure (RFC8410) with OID 1.3.101.112 (Ed25519):

PrivateKeyInfo ::= SEQUENCE { version INTEGER (0), privateKeyAlgorithm SEQUENCE { algorithm OBJECT IDENTIFIER (1.3.101.112), parameters (ABSENT oder NULL) }, privateKey OCTET STRING -- the seed }

Implementation

static String fromEd25519Seed(Uint8List seed) {
  if (seed.length != 32) {
    throw ArgumentError('Ed25519-Seed has to be of length 32 byte');
  }

  final offsetSeed = Uint8List(2 + seed.length);
  offsetSeed[0] = 0x04;
  offsetSeed[1] = 0x20;
  offsetSeed.setRange(2, 2 + seed.length, seed);

  final versionAsn = ASN1Integer(BigInt.zero);

  final algIdAsn = ASN1Sequence();
  final oidEd25519 = ASN1ObjectIdentifier.fromIdentifierString('1.3.101.112');
  algIdAsn.add(oidEd25519);
  final privateKeyAsn = ASN1OctetString(
    octets: Uint8List.fromList(offsetSeed.toList()),
  );

  final topLevel = ASN1Sequence();
  topLevel.add(versionAsn);
  topLevel.add(algIdAsn);
  topLevel.add(privateKeyAsn);

  // to DER code
  final derBytes = topLevel.encode();

  final base64Text = base64.encode(derBytes.toList());
  const lineLength = 64;
  final buffer = StringBuffer('-----BEGIN PRIVATE KEY-----\n');
  for (var i = 0; i < base64Text.length; i += lineLength) {
    buffer.writeln(
      base64Text.substring(
        i,
        (i + lineLength < base64Text.length)
            ? i + lineLength
            : base64Text.length,
      ),
    );
  }
  buffer.write('-----END PRIVATE KEY-----');

  return buffer.toString();
}