Function: set-match-data

set-match-data is a function defined in search.c.

Signature

(set-match-data LIST &optional RESEAT)

Documentation

Set internal data on last search match from elements of LIST.

LIST should have been created by calling match-data previously.

If optional arg RESEAT is non-nil, make markers on LIST point nowhere.

View in manual

Probably introduced at or before Emacs version 22.1.

Aliases

store-match-data

Source Code

// Defined in /usr/src/emacs/src/search.c
{
  ptrdiff_t i;
  register Lisp_Object marker;

  if (running_asynch_code)
    save_search_regs ();

  CHECK_LIST (list);

  /* Unless we find a marker with a buffer or an explicit buffer
     in LIST, assume that this match data came from a string.  */
  last_thing_searched = Qt;

  /* Allocate registers if they don't already exist.  */
  {
    ptrdiff_t length = list_length (list) / 2;

    if (length > search_regs.num_regs)
      {
	ptrdiff_t num_regs = search_regs.num_regs;
	search_regs.start =
	  xpalloc (search_regs.start, &num_regs, length - num_regs,
		   min (PTRDIFF_MAX, UINT_MAX), sizeof *search_regs.start);
	search_regs.end =
	  xrealloc (search_regs.end, num_regs * sizeof *search_regs.end);

	for (i = search_regs.num_regs; i < num_regs; i++)
	  search_regs.start[i] = -1;

	search_regs.num_regs = num_regs;
      }

    for (i = 0; CONSP (list); i++)
      {
	marker = XCAR (list);
	if (BUFFERP (marker))
	  {
	    last_thing_searched = marker;
	    break;
	  }
	if (i >= length)
	  break;
	if (NILP (marker))
	  {
	    search_regs.start[i] = -1;
	    list = XCDR (list);
	  }
	else
	  {
	    Lisp_Object from;
	    Lisp_Object m;

	    m = marker;
	    if (MARKERP (marker))
	      {
		if (XMARKER (marker)->buffer == 0)
		  XSETFASTINT (marker, 0);
		else
		  XSETBUFFER (last_thing_searched, XMARKER (marker)->buffer);
	      }

	    CHECK_FIXNUM_COERCE_MARKER (marker);
	    from = marker;

	    if (!NILP (reseat) && MARKERP (m))
	      {
		unchain_marker (XMARKER (m));
		XSETCAR (list, Qnil);
	      }

	    if ((list = XCDR (list), !CONSP (list)))
	      break;

	    m = marker = XCAR (list);

	    if (MARKERP (marker) && XMARKER (marker)->buffer == 0)
	      XSETFASTINT (marker, 0);

	    CHECK_FIXNUM_COERCE_MARKER (marker);
	    if (PTRDIFF_MIN <= XFIXNUM (from) && XFIXNUM (from) <= PTRDIFF_MAX
		&& PTRDIFF_MIN <= XFIXNUM (marker)
		&& XFIXNUM (marker) <= PTRDIFF_MAX)
	      {
		search_regs.start[i] = XFIXNUM (from);
		search_regs.end[i] = XFIXNUM (marker);
	      }
	    else
	      {
		search_regs.start[i] = -1;
	      }

	    if (!NILP (reseat) && MARKERP (m))
	      {
		unchain_marker (XMARKER (m));
		XSETCAR (list, Qnil);
	      }
	  }
	list = XCDR (list);
      }

    for (; i < search_regs.num_regs; i++)
      search_regs.start[i] = -1;
  }

  return Qnil;
}