Subject: Re: bug#38407: 27.0.50; infinite loop with display of large file without newlines

From: Eli Zaretskii <[email-masked]>
Date: Tue, 03 Dec 2019 18:05:42 +0200

> From: Robert Pluim <[email-masked]>
> Cc: Phil Sainty <[email-masked]>,  [email-masked],
>   [email-masked]
> Date: Tue, 03 Dec 2019 12:20:26 +0100
> 
> >>>>> On Mon, 02 Dec 2019 11:27:10 +0100, Robert Pluim <[email-masked]> said:
> 		  /* Otherwise, we can wrap here.  */
> 		  SAVE_IT (wrap_it, *it, wrap_data);          <=====
> 		  may_wrap = false;
> 		}
> 	    }
> 	}
> 
> That SAVE_IT is what causes the __memmove_avx_unaligned_erms to show
> up so high in the trace (via bidi_shelve_cache).

Yes, I was wondering about that myself.  But we need more details to
understand better what, if anything, can be done about this.

First, which part of SAVE_IT causes this?  I'm guessing it's this
part:

  #define SAVE_IT(ITCOPY, ITORIG, CACHE)	\
    do {					\
      if (CACHE)				\
	bidi_unshelve_cache (CACHE, true);	\
      ITCOPY = ITORIG;				\
      CACHE = bidi_shelve_cache ();		\  <<<<<<<<<<<<
    } while (false)

If that is true, then I think the offending part of bidi_shelve_cache
is this:

  alloc = (bidi_shelve_header_size
	   + bidi_cache_idx * sizeof (struct bidi_it));
  databuf = xmalloc (alloc);
  bidi_cache_total_alloc += alloc;

  memcpy (databuf, &bidi_cache_idx, sizeof (bidi_cache_idx));
  memcpy (databuf + sizeof (bidi_cache_idx),                      <<<<<<<
	  bidi_cache, bidi_cache_idx * sizeof (struct bidi_it));  <<<<<<<
  memcpy (databuf + sizeof (bidi_cache_idx)
	  + bidi_cache_idx * sizeof (struct bidi_it),
	  bidi_cache_start_stack, sizeof (bidi_cache_start_stack));

And if this guess is also true, then I think the problem is that
databuf + sizeof (bidi_cache_idx) is unaligned on 64-bit systems,
since bidi_cache_idx is an int.

Could you verify the above guesses?

Thanks.