Skip to content

Commit 0f970a7

Browse files
committed
replay attack policy "reject" for AEAD-2022 ciphers
- add "default" policy, which is "reject" for AEAD-2022 and "ignore" for AEAD, Stream ciphers
1 parent 6c5b478 commit 0f970a7

File tree

2 files changed

+24
-2
lines changed

2 files changed

+24
-2
lines changed

crates/shadowsocks/src/config.rs

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -817,6 +817,12 @@ impl From<PathBuf> for ManagerAddr {
817817
/// Policy for handling replay attack requests
818818
#[derive(Debug, Clone, Copy, Eq, PartialEq)]
819819
pub enum ReplayAttackPolicy {
820+
/// Default strategy based on protocol
821+
///
822+
/// SIP022 (AEAD-2022): Reject
823+
/// SIP004 (AEAD): Ignore
824+
/// Stream: Ignore
825+
Default,
820826
/// Ignore it completely
821827
Ignore,
822828
/// Try to detect replay attack and warn about it
@@ -827,13 +833,14 @@ pub enum ReplayAttackPolicy {
827833

828834
impl Default for ReplayAttackPolicy {
829835
fn default() -> ReplayAttackPolicy {
830-
ReplayAttackPolicy::Ignore
836+
ReplayAttackPolicy::Default
831837
}
832838
}
833839

834840
impl Display for ReplayAttackPolicy {
835841
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
836842
match *self {
843+
ReplayAttackPolicy::Default => f.write_str("default"),
837844
ReplayAttackPolicy::Ignore => f.write_str("ignore"),
838845
ReplayAttackPolicy::Detect => f.write_str("detect"),
839846
ReplayAttackPolicy::Reject => f.write_str("reject"),
@@ -856,6 +863,7 @@ impl FromStr for ReplayAttackPolicy {
856863

857864
fn from_str(s: &str) -> Result<Self, Self::Err> {
858865
match s {
866+
"default" => Ok(ReplayAttackPolicy::Default),
859867
"ignore" => Ok(ReplayAttackPolicy::Ignore),
860868
"detect" => Ok(ReplayAttackPolicy::Detect),
861869
"reject" => Ok(ReplayAttackPolicy::Reject),

crates/shadowsocks/src/context.rs

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ impl Context {
3535
pub fn new(config_type: ServerType) -> Context {
3636
Context {
3737
replay_protector: ReplayProtector::new(config_type),
38-
replay_policy: ReplayAttackPolicy::Reject,
38+
replay_policy: ReplayAttackPolicy::Default,
3939
dns_resolver: Arc::new(DnsResolver::system_resolver()),
4040
ipv6_first: false,
4141
}
@@ -101,6 +101,20 @@ impl Context {
101101
}
102102

103103
match self.replay_policy {
104+
ReplayAttackPolicy::Default => {
105+
#[cfg(feature = "aead-cipher-2022")]
106+
if method.is_aead_2022() {
107+
return if self.replay_protector.check_nonce_and_set(method, nonce) {
108+
let err = io::Error::new(io::ErrorKind::Other, "detected repeated nonce (iv/salt)");
109+
Err(err)
110+
} else {
111+
Ok(())
112+
};
113+
}
114+
115+
// AEAD, Stream should ignore by default
116+
Ok(())
117+
}
104118
ReplayAttackPolicy::Ignore => Ok(()),
105119
ReplayAttackPolicy::Detect => {
106120
if self.replay_protector.check_nonce_and_set(method, nonce) {

0 commit comments

Comments
 (0)