/ firmware / src / services / ssh / types.rs
types.rs
  1  use super::error;
  2  use super::wire;
  3  
  4  use ed25519_dalek::{SigningKey, VerifyingKey};
  5  use embedded_io_async::{ErrorType, Read, Write};
  6  use rand::{CryptoRng, Rng};
  7  
  8  /// Secret key associated with a host server.
  9  #[derive(Debug)]
 10  pub enum SecretKey {
 11      /// An Ed25519 secret key.
 12      Ed25519 {
 13          /// The secret key.
 14          secret_key: SigningKey,
 15      },
 16  }
 17  
 18  /// Public key associated with a user identity.
 19  #[derive(Clone, Copy, Debug, Eq, PartialEq)]
 20  pub enum PublicKey {
 21      /// An Ed25519 public key.
 22      Ed25519 {
 23          /// The public key.
 24          public_key: VerifyingKey,
 25      },
 26  }
 27  
 28  impl<'a> From<&'a PublicKey> for wire::PublicKey<'a> {
 29      fn from(value: &'a PublicKey) -> Self {
 30          match value {
 31              PublicKey::Ed25519 { public_key } => Self::Ed25519 {
 32                  public_key: public_key.as_bytes(),
 33              },
 34          }
 35      }
 36  }
 37  
 38  /// Authentication method that a user may choose.
 39  #[derive(Clone, Copy, Debug, Eq, PartialEq)]
 40  pub enum AuthMethod {
 41      /// No authentication provided.
 42      None,
 43      /// Public-key authentication.
 44      PublicKey(PublicKey),
 45  }
 46  
 47  /// Request associated with an SSH channel.
 48  #[derive(Clone, Copy, Debug)]
 49  pub enum Request<T> {
 50      /// User requested a shell.
 51      Shell,
 52      /// User requested the execution of a command.
 53      Exec(T),
 54  }
 55  
 56  /// Description of aspects of the server's behavior.
 57  pub trait Behavior {
 58      /// The underlying stream type.
 59      type Stream: Read + Write;
 60  
 61      /// The underlying stream type to be used.
 62      fn stream(&mut self) -> &mut Self::Stream;
 63  
 64      /// The underlying random type.
 65      type Random: CryptoRng + Rng;
 66  
 67      /// The underlying random type to be used.
 68      fn random(&mut self) -> &mut Self::Random;
 69  
 70      /// The secret key advertised by the server.
 71      fn host_secret_key(&self) -> &SecretKey;
 72  
 73      /// The server's identification string.
 74      ///
 75      /// This will be sent to the client during the initial version handshake. It must
 76      /// comply with RFC4253 section 4.2 except it should not contain the final CR LF.
 77      fn server_id(&self) -> &'static str {
 78          "SSH-2.0-microvisor"
 79      }
 80  
 81      /// Allow a given user to authenticate with a given auth method.
 82      ///
 83      /// Returns None if the user's auth method is not acceptable (e.g. public key does
 84      /// not match a whitelist), otherwise returns a type representing a user identity.
 85      ///
 86      /// This may be called more than once if the client uses probe requests.
 87      fn allow_user(&mut self, username: &str, auth_method: &AuthMethod) -> Option<Self::User>;
 88  
 89      /// Type representing an authenticated user.
 90      type User: Clone;
 91  
 92      /// Whether to allow shell channel requests.
 93      ///
 94      /// Note that if this returns true, the server code must be prepared to handle shell
 95      /// requests by accepting interactive input in ways similar to a real shell process.
 96      fn allow_shell(&self) -> bool {
 97          false
 98      }
 99  
100      /// Called when the client requests a PTY with terminal dimensions.
101      fn on_pty_request(&mut self, _width: u32, _height: u32) {}
102  
103      /// Type representing a user-supplied command.
104      type Command: Clone;
105  
106      /// Parse a user-supplied command string into a command.
107      ///
108      /// It is not permitted to "fail" to parse a command, instead just represent invalid
109      /// commands as a "print usage" command variant so as to handle all possible inputs.
110      fn parse_command(&mut self, command: &str) -> Self::Command;
111  }
112  
113  /// Convenience type alias describing the transport error type for a given behavior type.
114  pub type TransportError<T> = error::Error<<<T as Behavior>::Stream as ErrorType>::Error>;