From 706540a6330d9e9dc490aa50b02e76116a103d64 Mon Sep 17 00:00:00 2001 From: Jacopo Date: Wed, 19 Jun 2024 09:52:59 +0200 Subject: [PATCH] Port last changes from HEY --- lib/homographic_spoofing/detector/idn.rb | 14 +++++++++++++- test/detector/email_address_test.rb | 11 +++++++++-- test/detector/idn_test.rb | 3 ++- test/detector/local_test.rb | 2 +- test/detector/quoted_string_test.rb | 2 +- 5 files changed, 26 insertions(+), 6 deletions(-) diff --git a/lib/homographic_spoofing/detector/idn.rb b/lib/homographic_spoofing/detector/idn.rb index eed39eb..f67e6bd 100644 --- a/lib/homographic_spoofing/detector/idn.rb +++ b/lib/homographic_spoofing/detector/idn.rb @@ -61,6 +61,18 @@ def contexts end def public_suffix - @public_suffix ||= PublicSuffix.parse(domain, ignore_private: true) + @public_suffix ||= icann_domain || non_icann_domain + end + + def icann_domain + PublicSuffix.parse(domain, ignore_private: true) if PublicSuffix.valid?(domain) + end + + def non_icann_domain + if PublicSuffix::List.default.find(domain, default: nil, ignore_private: true).present? + PublicSuffix::Domain.new(domain) + else + raise PublicSuffix::DomainInvalid + end end end diff --git a/test/detector/email_address_test.rb b/test/detector/email_address_test.rb index 9fba5d8..981b517 100644 --- a/test/detector/email_address_test.rb +++ b/test/detector/email_address_test.rb @@ -7,11 +7,11 @@ class HomographicSpoofing::Detector::EmailAddressTest < ActiveSupport::TestCase end test "detect local part" do - assert_attack "tᴡitter@twitter.com" + assert_attack "t\u{1D21}itter@twitter.com" # tᴡitter@twitter.com end test "detect idn" do - assert_attack "jacopo@tᴡitter.com" + assert_attack "jacopo@t\u{1D21}itter.com" # jacopo@tᴡitter.com end test "ignore nil email address parts" do @@ -23,6 +23,13 @@ class HomographicSpoofing::Detector::EmailAddressTest < ActiveSupport::TestCase assert_safe "jacopo" end + test "private domains are allowed but idn attacks are detected" do + assert_safe "someone.from@notaires.fr" + assert_attack "someone.from@n\u{1D0F}taires.fr" # someone.from@nᴏtaires.fr + assert_safe "someone.from@blogspot.com" + assert_attack "someone.from@bl\u{1D0F}gspot.com" # someone.from@blᴏgspot.com + end + private def assert_attack(email_address) assert HomographicSpoofing::Detector::EmailAddress.detected?(email_address), "No attack detected for #{email_address}." diff --git a/test/detector/idn_test.rb b/test/detector/idn_test.rb index 61b5352..6a8f14b 100644 --- a/test/detector/idn_test.rb +++ b/test/detector/idn_test.rb @@ -12,6 +12,7 @@ class HomographicSpoofing::Detector::IdnTest < ActiveSupport::TestCase test "Valid mixed scripts" do assert_safe("おaかbがcキdギeクf.co.jp") # Latin, Hiragana, Katakana assert_safe("aㄉbㄊcde夕f.com") # Latin, Bopomofo, Han + assert_safe("example.বাংলা") # Latin, Bengali end test "Invalid mixed scripts" do @@ -265,8 +266,8 @@ class HomographicSpoofing::Detector::IdnTest < ActiveSupport::TestCase end test "PublixSuffix parsing errors" do - assert_attack("nic.bd", reason: "invalid_domain") assert_attack(" ", reason: "invalid_domain") + assert_attack("example|.com", reason: "disallowed_characters") end private diff --git a/test/detector/local_test.rb b/test/detector/local_test.rb index ade2b85..e8ebc90 100644 --- a/test/detector/local_test.rb +++ b/test/detector/local_test.rb @@ -37,7 +37,7 @@ class HomographicSpoofing::Detector::LocalTest < ActiveSupport::TestCase test "Unicode NFKC format" do # Invalid unicode - assert_attack("text".force_encoding("ISO-8859-1"), reason: "invalid_unicode") + assert_attack("text".encode("ISO-8859-1"), reason: "invalid_unicode") assert_attack("1𝟤3rf".unicode_normalize(:nfc), reason: "nfkc") assert_safe("scope") end diff --git a/test/detector/quoted_string_test.rb b/test/detector/quoted_string_test.rb index 8b1d016..cf98769 100644 --- a/test/detector/quoted_string_test.rb +++ b/test/detector/quoted_string_test.rb @@ -3,7 +3,7 @@ class HomographicSpoofing::Detector::QuotedStringTest < ActiveSupport::TestCase test "Unicode NFC format" do # Invalid unicode - assert_attack("text".force_encoding("ISO-8859-1"), reason: "invalid_unicode") + assert_attack("text".dup.force_encoding("ISO-8859-1"), reason: "invalid_unicode") assert_attack("1A\u030A3rf", reason: "nfc") assert_safe("scope") end