milestone 21: abp list exceptions and a regex rule kind
This commit is contained in:
@@ -9,8 +9,10 @@
|
||||
//!
|
||||
//! - `Line.text` is always a slice of the caller's line, never a copy and
|
||||
//! never a dangling pointer into a temporary;
|
||||
//! - `covers_apex` is set only on a `.wildcard` line, because the compiler
|
||||
//! reads it only there;
|
||||
//! - `covers_apex` is set only on a `.wildcard` or an `.exception` line,
|
||||
//! because those are the two anchored forms it describes; the compiler acts
|
||||
//! on it for `.wildcard`, where it emits the apex entry beside the suffix
|
||||
//! one;
|
||||
//! - `wildcard.matches` terminates for any pattern, validated or not, and a
|
||||
//! match implies the domain has at least as many labels as the pattern,
|
||||
//! since every pattern label consumes at least one domain label.
|
||||
@@ -75,6 +77,11 @@ fn formatTarget(format: parsers.Format, smith: *Smith) anyerror!void {
|
||||
|
||||
const parsed = parsers.parseLine(format, line);
|
||||
try expectBorrowed(parsed, line);
|
||||
|
||||
// Exception syntax belongs to the ABP parser alone. A hosts or domains line
|
||||
// that produced one would open an allow hole in a format that has no way to
|
||||
// write one.
|
||||
if (format != .abp) try std.testing.expect(parsed.kind != .exception);
|
||||
}
|
||||
|
||||
/// The sniffer reads whole files, so this one keeps the line breaks.
|
||||
@@ -113,7 +120,12 @@ fn wildcardTarget(_: void, smith: *Smith) anyerror!void {
|
||||
/// The parser contract: `text` is a window into the caller's line, so the
|
||||
/// compiler may keep it for the length of that line and no longer.
|
||||
fn expectBorrowed(parsed: parsers.Line, line: []const u8) !void {
|
||||
if (parsed.covers_apex) try std.testing.expectEqual(parsers.Kind.wildcard, parsed.kind);
|
||||
if (parsed.covers_apex) {
|
||||
try std.testing.expect(parsed.kind == .wildcard or parsed.kind == .exception);
|
||||
}
|
||||
// An exception with no name would compile to an empty allow entry, which
|
||||
// `addCandidate` would then reject as invalid rather than honour.
|
||||
if (parsed.kind == .exception) try std.testing.expect(parsed.text.len != 0);
|
||||
if (parsed.text.len == 0) return;
|
||||
|
||||
const start = @intFromPtr(parsed.text.ptr);
|
||||
@@ -146,6 +158,12 @@ const hosts_line = "0.0.0.0 ads.example.com tracker.example.com # advertising";
|
||||
/// An ABP domain rule, which covers the apex as well as the subdomains.
|
||||
const abp_line = "||ads.example.net^";
|
||||
|
||||
/// The exception forms: the two anchored spellings, the one tolerated modifier,
|
||||
/// and a bare `@@` name, which stays unsupported.
|
||||
const abp_exception = "@@||good.ads.example.net^";
|
||||
const abp_exception_important = "@@||good.ads.example.net^$important";
|
||||
const abp_exception_unanchored = "@@good.ads.example.net";
|
||||
|
||||
/// A regex rule, which every parser counts and skips (PLAN §2.2).
|
||||
const regex_line = "/^ads[0-9]+\\.example\\.org$/";
|
||||
|
||||
@@ -161,6 +179,9 @@ const scheme_anchor = "|https://ads.example.com/track";
|
||||
const corpus = [_][]const u8{
|
||||
sliceInput(hosts_line),
|
||||
sliceInput(abp_line),
|
||||
sliceInput(abp_exception),
|
||||
sliceInput(abp_exception_important),
|
||||
sliceInput(abp_exception_unanchored),
|
||||
sliceInput(regex_line),
|
||||
sliceInput(long_line),
|
||||
sliceInput(element_hiding),
|
||||
|
||||
Reference in New Issue
Block a user