@@ -84,60 +84,6 @@ pub(super) struct ReaderState {
8484}
8585
8686impl ReaderState {
87- /// Wraps content of `buf` into the [`Event::End`] event. Does the check that
88- /// end name matches the last opened start name if `self.config.check_end_names` is set.
89- pub fn emit_end < ' b > ( & mut self , buf : & ' b [ u8 ] ) -> Result < Event < ' b > > {
90- // Strip the `/` character. `content` contains data between `</` and `>`
91- let content = & buf[ 1 ..] ;
92- // XML standard permits whitespaces after the markup name in closing tags.
93- // Let's strip them from the buffer before comparing tag names.
94- let name = if self . config . trim_markup_names_in_closing_tags {
95- if let Some ( pos_end_name) = content. iter ( ) . rposition ( |& b| !is_whitespace ( b) ) {
96- & content[ ..pos_end_name + 1 ]
97- } else {
98- content
99- }
100- } else {
101- content
102- } ;
103-
104- let decoder = self . decoder ( ) ;
105-
106- // Get the index in self.opened_buffer of the name of the last opened tag
107- match self . opened_starts . pop ( ) {
108- Some ( start) => {
109- if self . config . check_end_names {
110- let expected = & self . opened_buffer [ start..] ;
111- if name != expected {
112- let expected = decoder. decode ( expected) . unwrap_or_default ( ) . into_owned ( ) ;
113- // #513: In order to allow error recovery we should drop content of the buffer
114- self . opened_buffer . truncate ( start) ;
115-
116- // Report error at start of the end tag at `<` character
117- // -2 for `<` and `>`
118- self . last_error_offset = self . offset - buf. len ( ) - 2 ;
119- return Err ( Error :: IllFormed ( IllFormedError :: MismatchedEndTag {
120- expected,
121- found : decoder. decode ( name) . unwrap_or_default ( ) . into_owned ( ) ,
122- } ) ) ;
123- }
124- }
125-
126- self . opened_buffer . truncate ( start) ;
127- }
128- None => {
129- // Report error at start of the end tag at `<` character
130- // -2 for `<` and `>`
131- self . last_error_offset = self . offset - buf. len ( ) - 2 ;
132- return Err ( Error :: IllFormed ( IllFormedError :: UnmatchedEndTag (
133- decoder. decode ( name) . unwrap_or_default ( ) . into_owned ( ) ,
134- ) ) ) ;
135- }
136- }
137-
138- Ok ( Event :: End ( BytesEnd :: wrap ( name. into ( ) ) ) )
139- }
140-
14187 /// Get the decoder, used to decode bytes, read by this reader, to the strings.
14288 ///
14389 /// If [`encoding`] feature is enabled, the used encoding may change after
@@ -369,7 +315,56 @@ impl ReaderState {
369315 debug_assert ! ( content. starts_with( b"</" ) , "{:?}" , Bytes ( content) ) ;
370316 debug_assert ! ( content. ends_with( b">" ) , "{:?}" , Bytes ( content) ) ;
371317
372- self . emit_end ( & content[ 1 ..content. len ( ) - 1 ] )
318+ let buf = & content[ 1 ..content. len ( ) - 1 ] ;
319+ // Strip the `/` character. `content` contains data between `</` and `>`
320+ let content = & buf[ 1 ..] ;
321+ // XML standard permits whitespaces after the markup name in closing tags.
322+ // Let's strip them from the buffer before comparing tag names.
323+ let name = if self . config . trim_markup_names_in_closing_tags {
324+ if let Some ( pos_end_name) = content. iter ( ) . rposition ( |& b| !is_whitespace ( b) ) {
325+ & content[ ..pos_end_name + 1 ]
326+ } else {
327+ content
328+ }
329+ } else {
330+ content
331+ } ;
332+
333+ let decoder = self . decoder ( ) ;
334+
335+ // Get the index in self.opened_buffer of the name of the last opened tag
336+ match self . opened_starts . pop ( ) {
337+ Some ( start) => {
338+ if self . config . check_end_names {
339+ let expected = & self . opened_buffer [ start..] ;
340+ if name != expected {
341+ let expected = decoder. decode ( expected) . unwrap_or_default ( ) . into_owned ( ) ;
342+ // #513: In order to allow error recovery we should drop content of the buffer
343+ self . opened_buffer . truncate ( start) ;
344+
345+ // Report error at start of the end tag at `<` character
346+ // -2 for `<` and `>`
347+ self . last_error_offset = self . offset - buf. len ( ) - 2 ;
348+ return Err ( Error :: IllFormed ( IllFormedError :: MismatchedEndTag {
349+ expected,
350+ found : decoder. decode ( name) . unwrap_or_default ( ) . into_owned ( ) ,
351+ } ) ) ;
352+ }
353+ }
354+
355+ self . opened_buffer . truncate ( start) ;
356+ }
357+ None => {
358+ // Report error at start of the end tag at `<` character
359+ // -2 for `<` and `>`
360+ self . last_error_offset = self . offset - buf. len ( ) - 2 ;
361+ return Err ( Error :: IllFormed ( IllFormedError :: UnmatchedEndTag (
362+ decoder. decode ( name) . unwrap_or_default ( ) . into_owned ( ) ,
363+ ) ) ) ;
364+ }
365+ }
366+
367+ Ok ( Event :: End ( BytesEnd :: wrap ( name. into ( ) ) ) )
373368 }
374369 FeedResult :: EncodingUtf8Like ( _)
375370 | FeedResult :: EncodingUtf16BeLike ( _)
0 commit comments