1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 #include "IDNBlocklistUtils.h"
7 #include "mozilla/Preferences.h"
8 #include "nsStringFwd.h"
13 static constexpr char16_t sBlocklistPairs
[][2] = {
14 #include "IDNCharacterBlocklist.inc"
17 void RemoveCharFromBlocklist(char16_t aChar
,
18 nsTArray
<BlocklistRange
>& aBlocklist
) {
19 auto pos
= aBlocklist
.BinaryIndexOf(aChar
, BlocklistPairToCharComparator());
20 if (pos
== nsTArray
<BlocklistRange
>::NoIndex
) {
24 auto& pair
= aBlocklist
[pos
];
26 // If the matched range has a length of one, we can just remove it
27 if (pair
.second
== pair
.first
) {
28 aBlocklist
.RemoveElementAt(pos
);
32 // If the character matches the first element in the range, just update
34 if (aChar
== pair
.first
) {
35 pair
.first
= pair
.first
+ 1;
39 // Also if it matches the last character in the range, we just update it.
40 if (aChar
== pair
.second
) {
41 pair
.second
= pair
.second
- 1;
45 // Our character is in the middle of the range, splitting it in two.
46 // We update the matched range to reflect the values before the character,
47 // and insert a new range that represents the values after.
48 char16_t lastElement
= pair
.second
;
49 pair
.second
= aChar
- 1;
50 aBlocklist
.InsertElementAt(pos
+ 1,
51 std::make_pair(char16_t(aChar
+ 1), lastElement
));
54 void InitializeBlocklist(nsTArray
<BlocklistRange
>& aBlocklist
) {
56 for (auto const& arr
: sBlocklistPairs
) {
57 // The hardcoded pairs are already sorted.
58 aBlocklist
.AppendElement(std::make_pair(arr
[0], arr
[1]));
61 nsAutoString extraAllowed
;
63 Preferences::GetString("network.IDN.extra_allowed_chars", extraAllowed
);
64 if (NS_SUCCEEDED(rv
) && !extraAllowed
.IsEmpty()) {
65 const char16_t
* cur
= extraAllowed
.BeginReading();
66 const char16_t
* end
= extraAllowed
.EndReading();
67 // Characters in the allowed list are removed from the blocklist.
68 for (; cur
< end
; ++cur
) {
69 RemoveCharFromBlocklist(*cur
, aBlocklist
);
73 nsAutoString extraBlocked
;
74 rv
= Preferences::GetString("network.IDN.extra_blocked_chars", extraBlocked
);
75 // We add each extra blocked character to the blocklist as a separate range.
76 if (NS_SUCCEEDED(rv
) && !extraBlocked
.IsEmpty()) {
77 for (size_t i
= 0; i
< extraBlocked
.Length(); ++i
) {
78 aBlocklist
.AppendElement(
79 std::make_pair(extraBlocked
[i
], extraBlocked
[i
]));
81 aBlocklist
.Sort(BlocklistEntryComparator());
86 } // namespace mozilla