diff options
Diffstat (limited to 'src/print.c')
| -rw-r--r-- | src/print.c | 68 |
1 files changed, 52 insertions, 16 deletions
diff --git a/src/print.c b/src/print.c index 8d0a5e2bb3b..4b94d77e876 100644 --- a/src/print.c +++ b/src/print.c | |||
| @@ -1,5 +1,5 @@ | |||
| 1 | /* Lisp object printing and output streams. | 1 | /* Lisp object printing and output streams. |
| 2 | Copyright (C) 1985, 86, 88, 93, 94, 95, 97, 98, 1999, 2000, 01, 2003 | 2 | Copyright (C) 1985, 86, 88, 93, 94, 95, 97, 98, 1999, 2000, 01, 03, 2004 |
| 3 | Free Software Foundation, Inc. | 3 | Free Software Foundation, Inc. |
| 4 | 4 | ||
| 5 | This file is part of GNU Emacs. | 5 | This file is part of GNU Emacs. |
| @@ -601,6 +601,8 @@ temp_output_buffer_setup (bufname) | |||
| 601 | eassert (current_buffer->overlays_after == NULL); | 601 | eassert (current_buffer->overlays_after == NULL); |
| 602 | current_buffer->enable_multibyte_characters | 602 | current_buffer->enable_multibyte_characters |
| 603 | = buffer_defaults.enable_multibyte_characters; | 603 | = buffer_defaults.enable_multibyte_characters; |
| 604 | specbind (Qinhibit_read_only, Qt); | ||
| 605 | specbind (Qinhibit_modification_hooks, Qt); | ||
| 604 | Ferase_buffer (); | 606 | Ferase_buffer (); |
| 605 | XSETBUFFER (buf, current_buffer); | 607 | XSETBUFFER (buf, current_buffer); |
| 606 | 608 | ||
| @@ -789,7 +791,7 @@ A printed representation of an object is text which describes that object. */) | |||
| 789 | if (SBYTES (object) == SCHARS (object)) | 791 | if (SBYTES (object) == SCHARS (object)) |
| 790 | STRING_SET_UNIBYTE (object); | 792 | STRING_SET_UNIBYTE (object); |
| 791 | 793 | ||
| 792 | /* Note that this won't make prepare_to_modify_buffer call | 794 | /* Note that this won't make prepare_to_modify_buffer call |
| 793 | ask-user-about-supersession-threat because this buffer | 795 | ask-user-about-supersession-threat because this buffer |
| 794 | does not visit a file. */ | 796 | does not visit a file. */ |
| 795 | Ferase_buffer (); | 797 | Ferase_buffer (); |
| @@ -927,7 +929,7 @@ DEFUN ("redirect-debugging-output", Fredirect_debugging_output, Sredirect_debugg | |||
| 927 | doc: /* Redirect debugging output (stderr stream) to file FILE. | 929 | doc: /* Redirect debugging output (stderr stream) to file FILE. |
| 928 | If FILE is nil, reset target to the initial stderr stream. | 930 | If FILE is nil, reset target to the initial stderr stream. |
| 929 | Optional arg APPEND non-nil (interactively, with prefix arg) means | 931 | Optional arg APPEND non-nil (interactively, with prefix arg) means |
| 930 | append to existing target file. */) | 932 | append to existing target file. */) |
| 931 | (file, append) | 933 | (file, append) |
| 932 | Lisp_Object file, append; | 934 | Lisp_Object file, append; |
| 933 | { | 935 | { |
| @@ -1218,7 +1220,6 @@ print (obj, printcharfun, escapeflag) | |||
| 1218 | register Lisp_Object printcharfun; | 1220 | register Lisp_Object printcharfun; |
| 1219 | int escapeflag; | 1221 | int escapeflag; |
| 1220 | { | 1222 | { |
| 1221 | print_depth = 0; | ||
| 1222 | old_backquote_output = 0; | 1223 | old_backquote_output = 0; |
| 1223 | 1224 | ||
| 1224 | /* Reset print_number_index and Vprint_number_table only when | 1225 | /* Reset print_number_index and Vprint_number_table only when |
| @@ -1238,6 +1239,7 @@ print (obj, printcharfun, escapeflag) | |||
| 1238 | start = index = print_number_index; | 1239 | start = index = print_number_index; |
| 1239 | /* Construct Vprint_number_table. | 1240 | /* Construct Vprint_number_table. |
| 1240 | This increments print_number_index for the objects added. */ | 1241 | This increments print_number_index for the objects added. */ |
| 1242 | print_depth = 0; | ||
| 1241 | print_preprocess (obj); | 1243 | print_preprocess (obj); |
| 1242 | 1244 | ||
| 1243 | /* Remove unnecessary objects, which appear only once in OBJ; | 1245 | /* Remove unnecessary objects, which appear only once in OBJ; |
| @@ -1262,6 +1264,7 @@ print (obj, printcharfun, escapeflag) | |||
| 1262 | print_number_index = index; | 1264 | print_number_index = index; |
| 1263 | } | 1265 | } |
| 1264 | 1266 | ||
| 1267 | print_depth = 0; | ||
| 1265 | print_object (obj, printcharfun, escapeflag); | 1268 | print_object (obj, printcharfun, escapeflag); |
| 1266 | } | 1269 | } |
| 1267 | 1270 | ||
| @@ -1278,6 +1281,26 @@ print_preprocess (obj) | |||
| 1278 | { | 1281 | { |
| 1279 | int i; | 1282 | int i; |
| 1280 | EMACS_INT size; | 1283 | EMACS_INT size; |
| 1284 | int loop_count = 0; | ||
| 1285 | Lisp_Object halftail; | ||
| 1286 | |||
| 1287 | /* Avoid infinite recursion for circular nested structure | ||
| 1288 | in the case where Vprint_circle is nil. */ | ||
| 1289 | if (NILP (Vprint_circle)) | ||
| 1290 | { | ||
| 1291 | for (i = 0; i < print_depth; i++) | ||
| 1292 | if (EQ (obj, being_printed[i])) | ||
| 1293 | return; | ||
| 1294 | being_printed[print_depth] = obj; | ||
| 1295 | } | ||
| 1296 | |||
| 1297 | /* Give up if we go so deep that print_object will get an error. */ | ||
| 1298 | /* See similar code in print_object. */ | ||
| 1299 | if (print_depth >= PRINT_CIRCLE) | ||
| 1300 | return; | ||
| 1301 | |||
| 1302 | print_depth++; | ||
| 1303 | halftail = obj; | ||
| 1281 | 1304 | ||
| 1282 | loop: | 1305 | loop: |
| 1283 | if (STRINGP (obj) || CONSP (obj) || VECTORP (obj) | 1306 | if (STRINGP (obj) || CONSP (obj) || VECTORP (obj) |
| @@ -1338,8 +1361,15 @@ print_preprocess (obj) | |||
| 1338 | break; | 1361 | break; |
| 1339 | 1362 | ||
| 1340 | case Lisp_Cons: | 1363 | case Lisp_Cons: |
| 1364 | /* Use HALFTAIL and LOOP_COUNT to detect circular lists, | ||
| 1365 | just as in print_object. */ | ||
| 1366 | if (loop_count && EQ (obj, halftail)) | ||
| 1367 | break; | ||
| 1341 | print_preprocess (XCAR (obj)); | 1368 | print_preprocess (XCAR (obj)); |
| 1342 | obj = XCDR (obj); | 1369 | obj = XCDR (obj); |
| 1370 | loop_count++; | ||
| 1371 | if (!(loop_count & 1)) | ||
| 1372 | halftail = XCDR (halftail); | ||
| 1343 | goto loop; | 1373 | goto loop; |
| 1344 | 1374 | ||
| 1345 | case Lisp_Vectorlike: | 1375 | case Lisp_Vectorlike: |
| @@ -1354,6 +1384,7 @@ print_preprocess (obj) | |||
| 1354 | break; | 1384 | break; |
| 1355 | } | 1385 | } |
| 1356 | } | 1386 | } |
| 1387 | print_depth--; | ||
| 1357 | } | 1388 | } |
| 1358 | 1389 | ||
| 1359 | static void | 1390 | static void |
| @@ -1457,7 +1488,7 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1457 | register Lisp_Object printcharfun; | 1488 | register Lisp_Object printcharfun; |
| 1458 | int escapeflag; | 1489 | int escapeflag; |
| 1459 | { | 1490 | { |
| 1460 | char buf[30]; | 1491 | char buf[40]; |
| 1461 | 1492 | ||
| 1462 | QUIT; | 1493 | QUIT; |
| 1463 | 1494 | ||
| @@ -1511,6 +1542,7 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1511 | 1542 | ||
| 1512 | print_depth++; | 1543 | print_depth++; |
| 1513 | 1544 | ||
| 1545 | /* See similar code in print_preprocess. */ | ||
| 1514 | if (print_depth > PRINT_CIRCLE) | 1546 | if (print_depth > PRINT_CIRCLE) |
| 1515 | error ("Apparently circular structure being printed"); | 1547 | error ("Apparently circular structure being printed"); |
| 1516 | #ifdef MAX_PRINT_CHARS | 1548 | #ifdef MAX_PRINT_CHARS |
| @@ -1876,18 +1908,14 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1876 | register unsigned char c; | 1908 | register unsigned char c; |
| 1877 | struct gcpro gcpro1; | 1909 | struct gcpro gcpro1; |
| 1878 | int size_in_chars | 1910 | int size_in_chars |
| 1879 | = (XBOOL_VECTOR (obj)->size + BITS_PER_CHAR - 1) / BITS_PER_CHAR; | 1911 | = ((XBOOL_VECTOR (obj)->size + BOOL_VECTOR_BITS_PER_CHAR - 1) |
| 1912 | / BOOL_VECTOR_BITS_PER_CHAR); | ||
| 1880 | 1913 | ||
| 1881 | GCPRO1 (obj); | 1914 | GCPRO1 (obj); |
| 1882 | 1915 | ||
| 1883 | PRINTCHAR ('#'); | 1916 | PRINTCHAR ('#'); |
| 1884 | PRINTCHAR ('&'); | 1917 | PRINTCHAR ('&'); |
| 1885 | if (sizeof (int) == sizeof (EMACS_INT)) | 1918 | sprintf (buf, "%ld", (long) XBOOL_VECTOR (obj)->size); |
| 1886 | sprintf (buf, "%d", XBOOL_VECTOR (obj)->size); | ||
| 1887 | else if (sizeof (long) == sizeof (EMACS_INT)) | ||
| 1888 | sprintf (buf, "%ld", XBOOL_VECTOR (obj)->size); | ||
| 1889 | else | ||
| 1890 | abort (); | ||
| 1891 | strout (buf, -1, -1, printcharfun, 0); | 1919 | strout (buf, -1, -1, printcharfun, 0); |
| 1892 | PRINTCHAR ('\"'); | 1920 | PRINTCHAR ('\"'); |
| 1893 | 1921 | ||
| @@ -1917,6 +1945,14 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1917 | PRINTCHAR ('\\'); | 1945 | PRINTCHAR ('\\'); |
| 1918 | PRINTCHAR ('f'); | 1946 | PRINTCHAR ('f'); |
| 1919 | } | 1947 | } |
| 1948 | else if (c > '\177') | ||
| 1949 | { | ||
| 1950 | /* Use octal escapes to avoid encoding issues. */ | ||
| 1951 | PRINTCHAR ('\\'); | ||
| 1952 | PRINTCHAR ('0' + ((c >> 6) & 3)); | ||
| 1953 | PRINTCHAR ('0' + ((c >> 3) & 7)); | ||
| 1954 | PRINTCHAR ('0' + (c & 7)); | ||
| 1955 | } | ||
| 1920 | else | 1956 | else |
| 1921 | { | 1957 | { |
| 1922 | if (c == '\"' || c == '\\') | 1958 | if (c == '\"' || c == '\\') |
| @@ -1937,7 +1973,7 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1937 | else if (WINDOWP (obj)) | 1973 | else if (WINDOWP (obj)) |
| 1938 | { | 1974 | { |
| 1939 | strout ("#<window ", -1, -1, printcharfun, 0); | 1975 | strout ("#<window ", -1, -1, printcharfun, 0); |
| 1940 | sprintf (buf, "%d", XFASTINT (XWINDOW (obj)->sequence_number)); | 1976 | sprintf (buf, "%ld", (long) XFASTINT (XWINDOW (obj)->sequence_number)); |
| 1941 | strout (buf, -1, -1, printcharfun, 0); | 1977 | strout (buf, -1, -1, printcharfun, 0); |
| 1942 | if (!NILP (XWINDOW (obj)->buffer)) | 1978 | if (!NILP (XWINDOW (obj)->buffer)) |
| 1943 | { | 1979 | { |
| @@ -1958,8 +1994,8 @@ print_object (obj, printcharfun, escapeflag) | |||
| 1958 | PRINTCHAR (' '); | 1994 | PRINTCHAR (' '); |
| 1959 | strout (SDATA (SYMBOL_NAME (h->weak)), -1, -1, printcharfun, 0); | 1995 | strout (SDATA (SYMBOL_NAME (h->weak)), -1, -1, printcharfun, 0); |
| 1960 | PRINTCHAR (' '); | 1996 | PRINTCHAR (' '); |
| 1961 | sprintf (buf, "%d/%d", XFASTINT (h->count), | 1997 | sprintf (buf, "%ld/%ld", (long) XFASTINT (h->count), |
| 1962 | XVECTOR (h->next)->size); | 1998 | (long) XVECTOR (h->next)->size); |
| 1963 | strout (buf, -1, -1, printcharfun, 0); | 1999 | strout (buf, -1, -1, printcharfun, 0); |
| 1964 | } | 2000 | } |
| 1965 | sprintf (buf, " 0x%lx", (unsigned long) h); | 2001 | sprintf (buf, " 0x%lx", (unsigned long) h); |
| @@ -2082,7 +2118,7 @@ print_object (obj, printcharfun, escapeflag) | |||
| 2082 | break; | 2118 | break; |
| 2083 | 2119 | ||
| 2084 | case Lisp_Misc_Intfwd: | 2120 | case Lisp_Misc_Intfwd: |
| 2085 | sprintf (buf, "#<intfwd to %d>", *XINTFWD (obj)->intvar); | 2121 | sprintf (buf, "#<intfwd to %ld>", (long) *XINTFWD (obj)->intvar); |
| 2086 | strout (buf, -1, -1, printcharfun, 0); | 2122 | strout (buf, -1, -1, printcharfun, 0); |
| 2087 | break; | 2123 | break; |
| 2088 | 2124 | ||