From 48823f080218d5a13dbde2ed152b8144de5afef8 Mon Sep 17 00:00:00 2001 From: Titus Wormer Date: Sat, 29 Oct 2022 12:28:58 +0200 Subject: Fix attention starting and ending in different links MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Example: ```markdown [*]() [*]() ``` There was already code for: ```markdown [*]() x*. *x [*](). ``` But that wasn’t correct for attention at the same depth but in different places. Closes GH-21. Co-authored-by: Christian Murphy --- src/construct/attention.rs | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) (limited to 'src/construct') diff --git a/src/construct/attention.rs b/src/construct/attention.rs index dd87e05..ca7ad2e 100644 --- a/src/construct/attention.rs +++ b/src/construct/attention.rs @@ -92,8 +92,10 @@ use alloc::{vec, vec::Vec}; struct Sequence { /// Marker as a byte (`u8`) used in this sequence. marker: u8, - /// The depth in events where this sequence resides. - balance: usize, + /// We track whether sequences are in balanced events, and where those + /// events start, so that one attention doesn’t start in say, one link, and + /// end in another. + stack: Vec, /// The index into events where this sequence’s `Enter` currently resides. index: usize, /// The (shifted) point where this sequence starts. @@ -172,7 +174,7 @@ pub fn resolve(tokenizer: &mut Tokenizer) -> Option { // An opener matching our closer: if sequence_open.open && sequence_close.marker == sequence_open.marker - && sequence_close.balance == sequence_open.balance + && sequence_close.stack == sequence_open.stack { // If the opening can close or the closing can open, // and the close size *is not* a multiple of three, @@ -219,23 +221,20 @@ pub fn resolve(tokenizer: &mut Tokenizer) -> Option { } tokenizer.map.consume(&mut tokenizer.events); - None } /// Get sequences. fn get_sequences(tokenizer: &mut Tokenizer) -> Vec { let mut index = 0; - let mut balance = 0; + let mut stack = vec![]; let mut sequences = vec![]; while index < tokenizer.events.len() { let enter = &tokenizer.events[index]; - if enter.kind == Kind::Enter { - balance += 1; - - if enter.name == Name::AttentionSequence { + if enter.name == Name::AttentionSequence { + if enter.kind == Kind::Enter { let end = index + 1; let exit = &tokenizer.events[end]; @@ -255,7 +254,7 @@ fn get_sequences(tokenizer: &mut Tokenizer) -> Vec { sequences.push(Sequence { index, - balance, + stack: stack.clone(), start_point: enter.point.clone(), end_point: exit.point.clone(), size: exit.point.index - enter.point.index, @@ -272,8 +271,10 @@ fn get_sequences(tokenizer: &mut Tokenizer) -> Vec { marker, }); } + } else if enter.kind == Kind::Enter { + stack.push(index); } else { - balance -= 1; + stack.pop(); } index += 1; -- cgit