emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Building Emacs overflowed pure space


From: YAMAMOTO Mitsuharu
Subject: Re: Building Emacs overflowed pure space
Date: Tue, 25 Jul 2006 10:14:05 +0900
User-agent: Wanderlust/2.14.0 (Africa) SEMI/1.14.6 (Maruoka) FLIM/1.14.6 (Marutamachi) APEL/10.6 Emacs/22.0.50 (sparc-sun-solaris2.8) MULE/5.0 (SAKAKI)

>>>>> On Sun, 23 Jul 2006 01:11:48 +0200, address@hidden (Kim F. Storm) said:

>>> If the string data in the pure storage can be assumed to be
>>> completely read-only (including the preloading stage), another
>>> hack could be considered.  That is, sharing postfixes of string
>>> data among multiple pure strings.  The following experimental
>>> patch shows another ~40KB reduction of the pure storage usage.  (A
>>> slow and naive but reliable version not using Boyer-Moore also
>>> shows the same size of reduction.)
>> 
> I tried the exact the same thing (using the naive version), but the
> dumped emacs crashed immediately after loadup, thinking that "nil"
> was a filename...  So I didn't think it was safe to do this.

I'm not sure if this should be counted as an objection.  If so, can I
have a look at the code just to make sure?

BTW, a condition was missing at the entrance of the function in my
previous patch.  Below is a revised one:

                                     YAMAMOTO Mitsuharu
                                address@hidden

Index: src/alloc.c
===================================================================
RCS file: /cvsroot/emacs/emacs/src/alloc.c,v
retrieving revision 1.397
diff -c -p -r1.397 alloc.c
*** src/alloc.c 20 Jul 2006 01:01:04 -0000      1.397
--- src/alloc.c 23 Jul 2006 04:21:49 -0000
*************** check_pure_size ()
*** 4767,4772 ****
--- 4767,4839 ----
  }
  
  
+ /* Find the byte sequence {DATA[0], ..., DATA[NBYTES-1], '\0'} from
+    the non-Lisp data pool of the pure storage, and return its start
+    address.  Return NULL if not found.  */
+ 
+ static char *
+ find_string_data_in_pure (data, nbytes)
+      char *data;
+      int nbytes;
+ {
+   int i, skip, bm_skip[256], last_char_skip, infinity, start, start_max;
+   unsigned char *p;
+   char *non_lisp_beg;
+ 
+   if (pure_bytes_used_non_lisp < nbytes + 1)
+     return NULL;
+ 
+   /* Set up the Boyer-Moore table.  */
+   skip = nbytes + 1;
+   for (i = 0; i < 256; i++)
+     bm_skip[i] = skip;
+ 
+   p = (unsigned char *) data;
+   while (--skip > 0)
+     bm_skip[*p++] = skip;
+ 
+   last_char_skip = bm_skip['\0'];
+ 
+   non_lisp_beg = purebeg + pure_size - pure_bytes_used_non_lisp;
+   start_max = pure_bytes_used_non_lisp - (nbytes + 1);
+ 
+   /* See the comments in the function `boyer_moore' (search.c) for the
+      use of `infinity'.  */
+   infinity = pure_bytes_used_non_lisp + 1;
+   bm_skip['\0'] = infinity;
+ 
+   p = (unsigned char *) non_lisp_beg + nbytes;
+   start = 0;
+   do
+     {
+       /* Check the last character (== '\0').  */
+       do
+       {
+         start += bm_skip[*(p + start)];
+       }
+       while (start <= start_max);
+ 
+       if (start < infinity)
+       /* Couldn't find the last character.  */
+       return NULL;
+ 
+       /* No less than `infinity' means we could find the last
+        character at `p[start - infinity]'.  */
+       start -= infinity;
+ 
+       /* Check the remaining characters.  */
+       if (memcmp (data, non_lisp_beg + start, nbytes) == 0)
+       /* Found.  */
+       return non_lisp_beg + start;
+ 
+       start += last_char_skip;
+     }
+   while (start <= start_max);
+ 
+   return NULL;
+ }
+ 
+ 
  /* Return a string allocated in pure space.  DATA is a buffer holding
     NCHARS characters, and NBYTES bytes of string data.  MULTIBYTE
     non-zero means make the result string multibyte.
*************** make_pure_string (data, nchars, nbytes, 
*** 4785,4795 ****
    struct Lisp_String *s;
  
    s = (struct Lisp_String *) pure_alloc (sizeof *s, Lisp_String);
!   s->data = (unsigned char *) pure_alloc (nbytes + 1, -1);
    s->size = nchars;
    s->size_byte = multibyte ? nbytes : -1;
-   bcopy (data, s->data, nbytes);
-   s->data[nbytes] = '\0';
    s->intervals = NULL_INTERVAL;
    XSETSTRING (string, s);
    return string;
--- 4852,4866 ----
    struct Lisp_String *s;
  
    s = (struct Lisp_String *) pure_alloc (sizeof *s, Lisp_String);
!   s->data = find_string_data_in_pure (data, nbytes);
!   if (s->data == NULL)
!     {
!       s->data = (unsigned char *) pure_alloc (nbytes + 1, -1);
!       bcopy (data, s->data, nbytes);
!       s->data[nbytes] = '\0';
!     }
    s->size = nchars;
    s->size_byte = multibyte ? nbytes : -1;
    s->intervals = NULL_INTERVAL;
    XSETSTRING (string, s);
    return string;




reply via email to

[Prev in Thread] Current Thread [Next in Thread]