Full SSH support for RSA.
This commit is contained in:
110
src/rsa/mod.rs
110
src/rsa/mod.rs
@@ -40,6 +40,8 @@ use cryptonum::signed::{EGCD,ModInv};
|
||||
use cryptonum::unsigned::{CryptoNum,PrimeGen};
|
||||
use cryptonum::unsigned::{U256,U512,U1024,U1536,U2048,U3072,U4096,U7680,U8192,U15360};
|
||||
use rand::RngCore;
|
||||
#[cfg(test)]
|
||||
use std::fmt;
|
||||
use std::ops::Sub;
|
||||
use super::KeyPair;
|
||||
|
||||
@@ -60,6 +62,114 @@ pub struct RSAKeyPair<R: RSAMode> {
|
||||
pub private: RSAPrivateKey<R>
|
||||
}
|
||||
|
||||
#[derive(PartialEq)]
|
||||
pub enum RSAPair {
|
||||
R512(RSAPublicKey<U512>, RSAPrivateKey<U512>),
|
||||
R1024(RSAPublicKey<U1024>, RSAPrivateKey<U1024>),
|
||||
R2048(RSAPublicKey<U2048>, RSAPrivateKey<U2048>),
|
||||
R3072(RSAPublicKey<U3072>, RSAPrivateKey<U3072>),
|
||||
R4096(RSAPublicKey<U4096>, RSAPrivateKey<U4096>),
|
||||
R8192(RSAPublicKey<U8192>, RSAPrivateKey<U8192>),
|
||||
R15360(RSAPublicKey<U15360>, RSAPrivateKey<U15360>),
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
impl fmt::Debug for RSAPair {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> Result<(), fmt::Error>
|
||||
{
|
||||
match self {
|
||||
RSAPair::R512(_,_) => f.write_str("512-bit RSA key pair"),
|
||||
RSAPair::R1024(_,_) => f.write_str("1024-bit RSA key pair"),
|
||||
RSAPair::R2048(_,_) => f.write_str("2048-bit RSA key pair"),
|
||||
RSAPair::R3072(_,_) => f.write_str("3072-bit RSA key pair"),
|
||||
RSAPair::R4096(_,_) => f.write_str("4096-bit RSA key pair"),
|
||||
RSAPair::R8192(_,_) => f.write_str("8192-bit RSA key pair"),
|
||||
RSAPair::R15360(_,_) => f.write_str("15360-bit RSA key pair"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl KeyPair for RSAPair {
|
||||
type Public = RSAPublic;
|
||||
type Private = RSAPrivate;
|
||||
|
||||
fn new(pu: RSAPublic, pr: RSAPrivate) -> RSAPair
|
||||
{
|
||||
match (pu, pr) {
|
||||
(RSAPublic::Key512(pbl), RSAPrivate::Key512(prv)) =>
|
||||
RSAPair::R512(pbl, prv),
|
||||
(RSAPublic::Key1024(pbl), RSAPrivate::Key1024(prv)) =>
|
||||
RSAPair::R1024(pbl, prv),
|
||||
(RSAPublic::Key2048(pbl), RSAPrivate::Key2048(prv)) =>
|
||||
RSAPair::R2048(pbl, prv),
|
||||
(RSAPublic::Key3072(pbl), RSAPrivate::Key3072(prv)) =>
|
||||
RSAPair::R3072(pbl, prv),
|
||||
(RSAPublic::Key4096(pbl), RSAPrivate::Key4096(prv)) =>
|
||||
RSAPair::R4096(pbl, prv),
|
||||
(RSAPublic::Key8192(pbl), RSAPrivate::Key8192(prv)) =>
|
||||
RSAPair::R8192(pbl, prv),
|
||||
(RSAPublic::Key15360(pbl), RSAPrivate::Key15360(prv)) =>
|
||||
RSAPair::R15360(pbl, prv),
|
||||
_ =>
|
||||
panic!("Unmatched public/private arguments to RSAPair::new()")
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl RSAPair {
|
||||
pub fn sign(&self, signhash: &SigningHash, msg: &[u8]) -> Vec<u8>
|
||||
{
|
||||
match self {
|
||||
RSAPair::R512(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R1024(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R2048(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R3072(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R4096(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R8192(_,prv) => prv.sign(signhash, msg),
|
||||
RSAPair::R15360(_,prv) => prv.sign(signhash, msg),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn verify(&self, signhash: &SigningHash, msg: &[u8], sig: &[u8]) -> bool
|
||||
{
|
||||
match self {
|
||||
RSAPair::R512(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R1024(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R2048(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R3072(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R4096(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R8192(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
RSAPair::R15360(pbl,_) => pbl.verify(signhash, msg, sig),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn public(&self) -> RSAPublic
|
||||
{
|
||||
match self {
|
||||
&RSAPair::R512(ref pbl,_) => RSAPublic::Key512(pbl.clone()),
|
||||
&RSAPair::R1024(ref pbl,_) => RSAPublic::Key1024(pbl.clone()),
|
||||
&RSAPair::R2048(ref pbl,_) => RSAPublic::Key2048(pbl.clone()),
|
||||
&RSAPair::R3072(ref pbl,_) => RSAPublic::Key3072(pbl.clone()),
|
||||
&RSAPair::R4096(ref pbl,_) => RSAPublic::Key4096(pbl.clone()),
|
||||
&RSAPair::R8192(ref pbl,_) => RSAPublic::Key8192(pbl.clone()),
|
||||
&RSAPair::R15360(ref pbl,_) => RSAPublic::Key15360(pbl.clone()),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn private(&self) -> RSAPrivate
|
||||
{
|
||||
match self {
|
||||
&RSAPair::R512(_,ref prv) => RSAPrivate::Key512(prv.clone()),
|
||||
&RSAPair::R1024(_,ref prv) => RSAPrivate::Key1024(prv.clone()),
|
||||
&RSAPair::R2048(_,ref prv) => RSAPrivate::Key2048(prv.clone()),
|
||||
&RSAPair::R3072(_,ref prv) => RSAPrivate::Key3072(prv.clone()),
|
||||
&RSAPair::R4096(_,ref prv) => RSAPrivate::Key4096(prv.clone()),
|
||||
&RSAPair::R8192(_,ref prv) => RSAPrivate::Key8192(prv.clone()),
|
||||
&RSAPair::R15360(_,ref prv) => RSAPrivate::Key15360(prv.clone()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! generate_rsa_pair
|
||||
{
|
||||
($uint: ident, $half: ident, $iterations: expr) => {
|
||||
|
||||
@@ -5,12 +5,14 @@ use rsa::errors::RSAError;
|
||||
use rsa::oaep::OAEPParams;
|
||||
use rsa::signing_hashes::SigningHash;
|
||||
|
||||
#[derive(Clone,PartialEq)]
|
||||
pub struct RSAPrivateKey<R: RSAMode>
|
||||
{
|
||||
pub(crate) nu: R::Barrett,
|
||||
pub(crate) d: R
|
||||
}
|
||||
|
||||
#[derive(Clone,PartialEq)]
|
||||
pub enum RSAPrivate {
|
||||
Key512(RSAPrivateKey<U512>),
|
||||
Key1024(RSAPrivateKey<U1024>),
|
||||
|
||||
@@ -12,13 +12,14 @@ use simple_asn1::{ASN1Block,ASN1DecodeErr,ASN1EncodeErr,
|
||||
use std::fmt;
|
||||
use utils::TranslateNums;
|
||||
|
||||
#[derive(PartialEq)]
|
||||
#[derive(Clone,PartialEq)]
|
||||
pub struct RSAPublicKey<R: RSAMode> {
|
||||
pub(crate) n: R,
|
||||
pub(crate) nu: R::Barrett,
|
||||
pub(crate) e: R
|
||||
}
|
||||
|
||||
#[derive(Clone,PartialEq)]
|
||||
pub enum RSAPublic {
|
||||
Key512( RSAPublicKey<U512>),
|
||||
Key1024( RSAPublicKey<U1024>),
|
||||
@@ -135,6 +136,21 @@ impl ToASN1 for RSAPublic {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
impl fmt::Debug for RSAPublic {
|
||||
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
|
||||
match self {
|
||||
RSAPublic::Key512(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key1024(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key2048(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key3072(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key4096(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key8192(x) => write!(fmt, "RSA:{:?}", x),
|
||||
RSAPublic::Key15360(x) => write!(fmt, "RSA:{:?}", x)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
macro_rules! generate_rsa_public
|
||||
{
|
||||
($num: ident, $bar: ident, $var: ident, $size: expr) => {
|
||||
|
||||
Reference in New Issue
Block a user