aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorKaroly Lorentey2006-06-27 15:06:36 +0000
committerKaroly Lorentey2006-06-27 15:06:36 +0000
commit556b89447234f15d1784a23dadbfe429464463a8 (patch)
treed5b94bbdde7b399bb0ffdf03a01f3e8398ee0afa /src
parent476e9367ec1f440aa23904b7bc482ea4a3b8041c (diff)
parent08b1eb21d5a3f935eb245acf0844a19acc42f57c (diff)
downloademacs-556b89447234f15d1784a23dadbfe429464463a8.tar.gz
emacs-556b89447234f15d1784a23dadbfe429464463a8.zip
Merged from emacs@sv.gnu.org
Patches applied: * emacs@sv.gnu.org/emacs--devo--0--patch-305 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-306 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-307 Update from CVS: lispref/display.texi (Forcing Redisplay): Fix typo. * emacs@sv.gnu.org/emacs--devo--0--patch-308 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-309 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-310 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-311 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-312 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-313 Merge from gnus--rel--5.10 * emacs@sv.gnu.org/emacs--devo--0--patch-314 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-315 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-316 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-317 Merge from gnus--rel--5.10 * emacs@sv.gnu.org/emacs--devo--0--patch-318 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-319 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-320 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-321 Merge from gnus--rel--5.10 * emacs@sv.gnu.org/emacs--devo--0--patch-322 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-323 lisp/play/cookie1.el (cookie): Work properly when there's only one entry * emacs@sv.gnu.org/emacs--devo--0--patch-324 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-325 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-326 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-327 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-328 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-329 Update from CVS * emacs@sv.gnu.org/emacs--devo--0--patch-330 Update from CVS * emacs@sv.gnu.org/gnus--rel--5.10--patch-105 Update from CVS * emacs@sv.gnu.org/gnus--rel--5.10--patch-106 Update from CVS * emacs@sv.gnu.org/gnus--rel--5.10--patch-107 Update from CVS * emacs@sv.gnu.org/gnus--rel--5.10--patch-108 Merge from emacs--devo--0 * emacs@sv.gnu.org/gnus--rel--5.10--patch-109 Clean up merge mistakes * emacs@sv.gnu.org/gnus--rel--5.10--patch-110 Update from CVS git-archimport-id: lorentey@elte.hu--2004/emacs--multi-tty--0--patch-571
Diffstat (limited to 'src')
-rw-r--r--src/.gdbinit138
-rw-r--r--src/ChangeLog165
-rw-r--r--src/callproc.c4
-rw-r--r--src/dired.c10
-rw-r--r--src/dispextern.h41
-rw-r--r--src/dispnew.c133
-rw-r--r--src/eval.c4
-rw-r--r--src/fileio.c8
-rw-r--r--src/lread.c19
-rw-r--r--src/macfns.c26
-rw-r--r--src/macterm.c141
-rw-r--r--src/s/gnu-linux.h9
-rw-r--r--src/syntax.c14
-rw-r--r--src/window.c101
-rw-r--r--src/xdisp.c240
-rw-r--r--src/xfns.c3
-rw-r--r--src/xterm.c139
-rw-r--r--src/xterm.h12
18 files changed, 982 insertions, 225 deletions
diff --git a/src/.gdbinit b/src/.gdbinit
index 54d68dc123d..acdb959a869 100644
--- a/src/.gdbinit
+++ b/src/.gdbinit
@@ -190,12 +190,8 @@ define pitx
190 printf " ch=[%d,%d]", $it->c, $it->len 190 printf " ch=[%d,%d]", $it->c, $it->len
191 end 191 end
192 else 192 else
193 if ($it->what == IT_IMAGE) 193 printf " "
194 printf " IMAGE=%d", $it->image_id 194 output $it->what
195 else
196 printf " "
197 output $it->what
198 end
199 end 195 end
200 if ($it->method != GET_FROM_BUFFER) 196 if ($it->method != GET_FROM_BUFFER)
201 printf " next=" 197 printf " next="
@@ -203,6 +199,12 @@ define pitx
203 if ($it->method == GET_FROM_STRING) 199 if ($it->method == GET_FROM_STRING)
204 printf "[%d]", $it->current.string_pos.charpos 200 printf "[%d]", $it->current.string_pos.charpos
205 end 201 end
202 if ($it->method == GET_FROM_IMAGE)
203 printf "[%d]", $it->image_id
204 end
205 if ($it->method == GET_FROM_COMPOSITION)
206 printf "[%d,%d,%d]", $it->cmp_id, $it->len, $it->cmp_len
207 end
206 end 208 end
207 printf "\n" 209 printf "\n"
208 if ($it->region_beg_charpos >= 0) 210 if ($it->region_beg_charpos >= 0)
@@ -215,6 +217,15 @@ define pitx
215 printf " a+d=%d+%d=%d", $it->ascent, $it->descent, $it->ascent+$it->descent 217 printf " a+d=%d+%d=%d", $it->ascent, $it->descent, $it->ascent+$it->descent
216 printf " max=%d+%d=%d", $it->max_ascent, $it->max_descent, $it->max_ascent+$it->max_descent 218 printf " max=%d+%d=%d", $it->max_ascent, $it->max_descent, $it->max_ascent+$it->max_descent
217 printf "\n" 219 printf "\n"
220 set $i = 0
221 while ($i < $it->sp)
222 set $e = $it->stack[$i]
223 printf "stack[%d]: ", $i
224 output $e->method
225 printf "[%d]", $e->position.charpos
226 printf "\n"
227 set $i = $i + 1
228 end
218end 229end
219document pitx 230document pitx
220Pretty print a display iterator. 231Pretty print a display iterator.
@@ -372,6 +383,121 @@ document pwin
372Pretty print window structure w. 383Pretty print window structure w.
373end 384end
374 385
386define pgx
387 set $g = $arg0
388 if ($g->type == CHAR_GLYPH)
389 if ($g->u.ch >= ' ' && $g->u.ch < 127)
390 printf "CHAR[%c]", $g->u.ch
391 else
392 printf "CHAR[0x%x]", $g->u.ch
393 end
394 end
395 if ($g->type == COMPOSITE_GLYPH)
396 printf "COMP[%d]", $g->u.cmp_id
397 end
398 if ($g->type == IMAGE_GLYPH)
399 printf "IMAGE[%d]", $g->u.img_id
400 end
401 if ($g->type == STRETCH_GLYPH)
402 printf "STRETCH[%d+%d]", $g->u.stretch.height, $g->u.stretch.ascent
403 end
404 xgettype ($g->object)
405 if ($type == Lisp_String)
406 printf " str=%x[%d]", $g->object, $g->charpos
407 else
408 printf " pos=%d", $g->charpos
409 end
410 printf " w=%d a+d=%d+%d", $g->pixel_width, $g->ascent, $g->descent
411 if ($g->face_id != DEFAULT_FACE_ID)
412 printf " face=%d", $g->face_id
413 end
414 if ($g->voffset)
415 printf " vof=%d", $g->voffset
416 end
417 if ($g->multibyte_p)
418 printf " MB"
419 end
420 if ($g->padding_p)
421 printf " PAD"
422 end
423 if ($g->glyph_not_available_p)
424 printf " N/A"
425 end
426 if ($g->overlaps_vertically_p)
427 printf " OVL"
428 end
429 if ($g->left_box_line_p)
430 printf " ["
431 end
432 if ($g->right_box_line_p)
433 printf " ]"
434 end
435 if ($g->slice.x || $g->slice.y || $g->slice.width || $g->slice.height)
436 printf " slice=%d,%d,%d,%d" ,$g->slice.x, $g->slice.y, $g->slice.width, $g->slice.height
437 end
438 printf "\n"
439end
440document pgx
441Pretty print a glyph structure.
442Takes one argument, a pointer to a glyph structure
443end
444
445define pg
446 set $pgidx = 0
447 pgx glyph
448end
449document pg
450Pretty print glyph structure glyph.
451end
452
453define pgi
454 set $pgidx = $arg0
455 pgx (&glyph[$pgidx])
456end
457document pgi
458Pretty print glyph structure glyph[I].
459Takes one argument, a integer I.
460end
461
462define pgn
463 set $pgidx = $pgidx + 1
464 pgx (&glyph[$pgidx])
465end
466document pgn
467Pretty print next glyph structure.
468end
469
470define pgrowx
471 set $row = $arg0
472 set $area = 0
473 set $xofs = $row->x
474 while ($area < 3)
475 set $used = $row->used[$area]
476 if ($used > 0)
477 set $gl0 = $row->glyphs[$area]
478 set $pgidx = 0
479 printf "%s: %d glyphs\n", ($area == 0 ? "LEFT" : $area == 2 ? "RIGHT" : "TEXT"), $used
480 while ($pgidx < $used)
481 printf "%3d %4d: ", $pgidx, $xofs
482 pgx $gl0[$pgidx]
483 set $xofs = $xofs + $gl0[$pgidx]->pixel_width
484 set $pgidx = $pgidx + 1
485 end
486 end
487 set $area = $area + 1
488 end
489end
490document pgrowx
491Pretty print all glyphs in a row structure.
492Takes one argument, a pointer to a row structure.
493end
494
495define pgrow
496 pgrowx row
497end
498document pgrow
499Pretty print all glyphs in row structure row.
500end
375 501
376define xtype 502define xtype
377 xgettype $ 503 xgettype $
diff --git a/src/ChangeLog b/src/ChangeLog
index 5154dc5012e..91694368fe0 100644
--- a/src/ChangeLog
+++ b/src/ChangeLog
@@ -1,3 +1,168 @@
12006-06-25 Kim F. Storm <storm@cua.dk>
2
3 * s/gnu-linux.h (SIGNALS_VIA_CHARACTERS): Define for Linux kernel
4 version 2.4 and later.
5
62006-06-24 Chong Yidong <cyd@stupidchicken.com>
7
8 * xfns.c (Fx_create_frame): Set font parameter directly instead of
9 using x_default_parameter, since x_get_args clears the parm alist.
10
112006-06-24 Eli Zaretskii <eliz@gnu.org>
12
13 * dired.c (directory_files_internal) [WINDOWSNT]: Find files
14 case-insensitively.
15
162006-06-24 Aidan Kehoe <kehoea@parhasard.net>
17
18 * lread.c (read_escape): When an unknown Unicode code point is
19 encountered as a string or character escape, signal an error.
20
212006-06-23 Kim F. Storm <storm@cua.dk>
22
23 * .gdbinit (pitx): Dump iterator stack.
24
25 * xdisp.c (handle_composition_prop): Push iterator on stack.
26 (set_iterator_to_next): Pop iterator at end of composition.
27
282006-06-23 Martin Rudalics <rudalics@gmx.at>
29
30 * fileio.c (Frename_file) [DOS_NT]: Don't try to move directory to
31 itself on DOS_NT platforms, if the old and new names are identical
32 but for the letter-case.
33
342006-06-21 Kim F. Storm <storm@cua.dk>
35
36 * dispextern.h (struct it): Add `position' member to iterator stack.
37 Rename `pos' member to `current'. Rearrange and add comments.
38
39 * xdisp.c (handle_stop): Set it->ignore_overlay_strings_at_pos_p
40 if we get any overlays.
41 (set_cursor_from_row): Don't clobber `end' if we rescan from
42 start_string.
43 (push_it, pop_it): Save it->position.
44
452006-06-19 Richard Stallman <rms@gnu.org>
46
47 * window.c (size_window): New arg FIRST_ONLY. All callers changed.
48 (adjust_window_trailing_edge): Specially compute FIRST_PARALLEL
49 for the case of a top-level window and the following minibuffer.
50 Don't exit because of no `next' when there is a parent.
51 Use the FIRST_ONLY feature when resizing following windows.
52
53 * syntax.c (init_syntax_once): Give most control chars' syntax Spunct.
54
552006-06-17 Kim F. Storm <storm@cua.dk>
56
57 * dispnew.c (update_frame): Check for input pending on entry.
58 (update_window, update_frame_1): Break loop if input is detected.
59
602006-06-16 Francis Litterio <flitterio@gmail.com>
61
62 * xterm.c (x_check_expected_move, handle_one_xevent)
63 (x_set_offset, x_check_fullscreen): Extensive changes to make
64 frame positioning deterministic under X.
65
66 * xterm.h (x_output): Added members left_before_move and
67 top_before_move. Removed members expected_left and expected_top.
68
692006-06-16 Kim F. Storm <storm@cua.dk>
70
71 * dispextern.h (struct it): Add union to iterator stack to save
72 image, composition, and stretch specific paramters.
73
74 * xdisp.c (next_overlay_string): Fix assert.
75 (push_it, pop_it): Handle composition and stretch specific values.
76 Only handle it->slice in image (for now).
77 (back_to_previous_visible_line_start): Continue search if newline is
78 part of a compisition. Simplify.
79 (reseat_1): Set it->object to buffer.
80 (set_iterator_to_next): Set it->object to string or buffer, when
81 setting it->method to GET_FROM_STRING or GET_FROM_BUFFER.
82 (next_element_from_composition): Set it->object to buffer if not
83 from string.
84 (set_cursor_from_row): Only save start of string if not already
85 done to handle multiple strings in a row.
86
87 * .gdbinit (pitx): Show composition parameters.
88 (pgx, pg): New commands to print a glyph structure.
89 (pgi, pgn): New commands to print specific/next glyph.
90 (pgrowx, pgrow): New commands to print all glyphs in a row.
91
922006-06-16 YAMAMOTO Mitsuharu <mituharu@math.s.chiba-u.ac.jp>
93
94 * macfns.c (Fx_display_mm_height, Fx_display_mm_width)
95 [MAC_OS_X_VERSION_MAX_ALLOWED >= 1030]: Use CGDisplayScreenSize.
96
97 * macterm.c (do_app_resume, do_app_suspend): Remove functions.
98 (mac_tsm_resume, mac_tsm_suspend) [USE_MAC_TSM]: New functions.
99 (mac_handle_window_event, XTread_socket) [USE_MAC_TSM]: Use them.
100 (Vmac_ts_script_language_on_focus) [USE_MAC_TSM]: New variable.
101 (syms_of_macterm) [USE_MAC_TSM]: Defvar it.
102 (saved_ts_language, saved_ts_component) [USE_MAC_TSM]: New variables.
103 (mac_initialize_display_info) [MAC_OSX]: Use Quartz Display
104 Services functions to get size of main display in pixels.
105
1062006-06-14 Chong Yidong <cyd@stupidchicken.com>
107
108 * xdisp.c (back_to_previous_visible_line_start): Reset
109 it->continuation_lines_width.
110
1112006-06-14 Richard Stallman <rms@gnu.org>
112
113 * eval.c (Fdefconst): Mark variable as risky.
114
115 * callproc.c (Fcall_process): Doc fix.
116
117 * window.c (adjust_window_trailing_edge): Don't break out of the loop
118 because there's no next window, if there are parallel windows.
119 Do break out when WINDOW is nil.
120
1212006-06-14 Kim F. Storm <storm@cua.dk>
122
123 * dispextern.h (IT_STACK_SIZE): New macro specifying size of
124 iterator stack (instead of hardcoded number). Increase from 2 to
125 4 to make room for propertized overlay strings before and after a
126 display string, image or composition.
127 (struct it): Add image_id and method members to iterator stack.
128
129 * xdisp.c (init_from_display_pos): Don't set it->method and
130 overlay_string_index after pop_it. Add asserts.
131 (handle_stop): Look for overlay strings around a display string,
132 image, or composition. Handle properties on those strings.
133 (next_overlay_string): Don't set string, pos or method after pop_it.
134 (get_overlay_strings_1): Split from get_overlay_strings; don't
135 modify it if no overlay strings are found.
136 (get_overlay_strings): Use get_overlay_strings_1. Always set
137 it->string and it->method.
138 (push_it): Push it->image_id and it->method. Push it->object
139 instead of it->string if method is GET_FROM_IMAGE.
140 (pop_it): Pop it->image_id and it->method. Ppo it->object
141 instead of it->string if method is GET_FROM_IMAGE.
142 Reset it->current.string_pos if popped it->string is nil.
143 (reseat_1): Remove comment dated 19 May 2003. It expressed doubt
144 whether a given change was correct; but the change is correct.
145 Clear it->string_from_display_prop_p.
146 (set_iterator_to_next): Rely on it->method and it->image_id from
147 iterator stack, instead of setting them explicitly after pop_it.
148
149 * dispnew.c (sit_for): Undo 2006-06-01 change. Instead, a
150 negative time forces redisplay even when input is available.
151 (Fsit_for): Doc fix.
152
1532006-06-13 Kim F. Storm <storm@cua.dk>
154
155 * dispnew.c: Modify preemptive redisplay to be based on periodic
156 checks for input.
157 (PERIODIC_PREEMPTION_CHECKING): Define to 1 iff EMACS_HAS_USECS.
158 (Vredisplay_preemption_period): New variable.
159 (syms_of_display): DEFVAR_LISP and initialize it.
160 (preemption_period, preemption_next_check): New variables.
161 (update_frame, update_single_window): Initialize them based on
162 Vredisplay_preemption_period if !force_p.
163 (update_window, update_frame_1): Use them to determine when to
164 check for input.
165
12006-06-03 Aidan Kehoe <kehoea@parhasard.net> 1662006-06-03 Aidan Kehoe <kehoea@parhasard.net>
2 167
3 * lread.c (read_escape): Provide a Unicode character escape 168 * lread.c (read_escape): Provide a Unicode character escape
diff --git a/src/callproc.c b/src/callproc.c
index b2352e9bd55..2f0e569d0c8 100644
--- a/src/callproc.c
+++ b/src/callproc.c
@@ -206,6 +206,10 @@ t (mix it with ordinary output), or a file name string.
206Fourth arg DISPLAY non-nil means redisplay buffer as output is inserted. 206Fourth arg DISPLAY non-nil means redisplay buffer as output is inserted.
207Remaining arguments are strings passed as command arguments to PROGRAM. 207Remaining arguments are strings passed as command arguments to PROGRAM.
208 208
209If executable PROGRAM can't be found as an executable, `call-process'
210signals a Lisp error. `call-process' reports errors in execution of
211the program only through its return and output.
212
209If BUFFER is 0, `call-process' returns immediately with value nil. 213If BUFFER is 0, `call-process' returns immediately with value nil.
210Otherwise it waits for PROGRAM to terminate 214Otherwise it waits for PROGRAM to terminate
211and returns a numeric exit status or a signal description string. 215and returns a numeric exit status or a signal description string.
diff --git a/src/dired.c b/src/dired.c
index 8c7c7fd5ac6..8b5d7851765 100644
--- a/src/dired.c
+++ b/src/dired.c
@@ -175,9 +175,15 @@ directory_files_internal (directory, full, match, nosort, attrs, id_format)
175#ifdef VMS 175#ifdef VMS
176 bufp = compile_pattern (match, 0, 176 bufp = compile_pattern (match, 0,
177 buffer_defaults.downcase_table, 0, 1); 177 buffer_defaults.downcase_table, 0, 1);
178#else 178#else /* !VMS */
179# ifdef WINDOWSNT
180 /* Windows users want case-insensitive wildcards. */
181 bufp = compile_pattern (match, 0,
182 buffer_defaults.case_canon_table, 0, 1);
183# else /* !WINDOWSNT */
179 bufp = compile_pattern (match, 0, Qnil, 0, 1); 184 bufp = compile_pattern (match, 0, Qnil, 0, 1);
180#endif 185# endif /* !WINDOWSNT */
186#endif /* !VMS */
181 } 187 }
182 188
183 /* Note: ENCODE_FILE and DECODE_FILE can GC because they can run 189 /* Note: ENCODE_FILE and DECODE_FILE can GC because they can run
diff --git a/src/dispextern.h b/src/dispextern.h
index ed91d2df76e..6b5705a2865 100644
--- a/src/dispextern.h
+++ b/src/dispextern.h
@@ -1814,6 +1814,8 @@ enum it_method {
1814 NUM_IT_METHODS 1814 NUM_IT_METHODS
1815}; 1815};
1816 1816
1817#define IT_STACK_SIZE 4
1818
1817struct it 1819struct it
1818{ 1820{
1819 /* The window in which we iterate over current_buffer (or a string). */ 1821 /* The window in which we iterate over current_buffer (or a string). */
@@ -1922,22 +1924,47 @@ struct it
1922 from what we previously had. */ 1924 from what we previously had. */
1923 struct iterator_stack_entry 1925 struct iterator_stack_entry
1924 { 1926 {
1925 int stop_charpos;
1926 int face_id;
1927 Lisp_Object string; 1927 Lisp_Object string;
1928 struct display_pos pos;
1929 int end_charpos;
1930 int string_nchars; 1928 int string_nchars;
1929 int end_charpos;
1930 int stop_charpos;
1931 int face_id;
1932
1933 /* Save values specific to a given method. */
1934 union {
1935 /* method == GET_FROM_IMAGE */
1936 struct {
1937 Lisp_Object object;
1938 struct it_slice slice;
1939 int image_id;
1940 } image;
1941 /* method == GET_FROM_COMPOSITION */
1942 struct {
1943 Lisp_Object object;
1944 int c, len;
1945 int cmp_id, cmp_len;
1946 } comp;
1947 /* method == GET_FROM_STRETCH */
1948 struct {
1949 Lisp_Object object;
1950 } stretch;
1951 } u;
1952
1953 /* current text and display positions. */
1954 struct text_pos position;
1955 struct display_pos current;
1931 enum glyph_row_area area; 1956 enum glyph_row_area area;
1957 enum it_method method;
1932 unsigned multibyte_p : 1; 1958 unsigned multibyte_p : 1;
1933 unsigned string_from_display_prop_p : 1; 1959 unsigned string_from_display_prop_p : 1;
1934 unsigned display_ellipsis_p : 1; 1960 unsigned display_ellipsis_p : 1;
1935 struct it_slice slice; 1961
1962 /* properties from display property that are reset by another display property. */
1936 Lisp_Object space_width; 1963 Lisp_Object space_width;
1937 short voffset;
1938 Lisp_Object font_height; 1964 Lisp_Object font_height;
1965 short voffset;
1939 } 1966 }
1940 stack[2]; 1967 stack[IT_STACK_SIZE];
1941 1968
1942 /* Stack pointer. */ 1969 /* Stack pointer. */
1943 int sp; 1970 int sp;
diff --git a/src/dispnew.c b/src/dispnew.c
index c346e94a103..4f63bfa8578 100644
--- a/src/dispnew.c
+++ b/src/dispnew.c
@@ -192,6 +192,28 @@ struct window *frame_row_to_window P_ ((struct window *, int));
192 192
193int redisplay_dont_pause; 193int redisplay_dont_pause;
194 194
195/* Define PERIODIC_PREEMPTION_CHECKING to 1, if micro-second timers
196 are supported, so we can check for input during redisplay at
197 regular intervals. */
198#ifdef EMACS_HAS_USECS
199#define PERIODIC_PREEMPTION_CHECKING 1
200#else
201#define PERIODIC_PREEMPTION_CHECKING 0
202#endif
203
204#if PERIODIC_PREEMPTION_CHECKING
205
206/* If a number (float), check for user input every N seconds. */
207
208Lisp_Object Vredisplay_preemption_period;
209
210/* Redisplay preemption timers. */
211
212static EMACS_TIME preemption_period;
213static EMACS_TIME preemption_next_check;
214
215#endif
216
195/* Nonzero upon entry to redisplay means do not assume anything about 217/* Nonzero upon entry to redisplay means do not assume anything about
196 current contents of actual terminal frame; clear and redraw it. */ 218 current contents of actual terminal frame; clear and redraw it. */
197 219
@@ -3814,6 +3836,28 @@ update_frame (f, force_p, inhibit_hairy_id_p)
3814 int paused_p; 3836 int paused_p;
3815 struct window *root_window = XWINDOW (f->root_window); 3837 struct window *root_window = XWINDOW (f->root_window);
3816 3838
3839#if PERIODIC_PREEMPTION_CHECKING
3840 if (!force_p && NUMBERP (Vredisplay_preemption_period))
3841 {
3842 EMACS_TIME tm;
3843 double p = XFLOATINT (Vredisplay_preemption_period);
3844 int sec, usec;
3845
3846 if (detect_input_pending_ignore_squeezables ())
3847 {
3848 paused_p = 1;
3849 goto do_pause;
3850 }
3851
3852 sec = (int) p;
3853 usec = (p - sec) * 1000000;
3854
3855 EMACS_GET_TIME (tm);
3856 EMACS_SET_SECS_USECS (preemption_period, sec, usec);
3857 EMACS_ADD_TIME (preemption_next_check, tm, preemption_period);
3858 }
3859#endif
3860
3817 if (FRAME_WINDOW_P (f)) 3861 if (FRAME_WINDOW_P (f))
3818 { 3862 {
3819 /* We are working on window matrix basis. All windows whose 3863 /* We are working on window matrix basis. All windows whose
@@ -3895,6 +3939,7 @@ update_frame (f, force_p, inhibit_hairy_id_p)
3895#endif 3939#endif
3896 } 3940 }
3897 3941
3942 do_pause:
3898 /* Reset flags indicating that a window should be updated. */ 3943 /* Reset flags indicating that a window should be updated. */
3899 set_window_update_flags (root_window, 0); 3944 set_window_update_flags (root_window, 0);
3900 3945
@@ -3949,6 +3994,22 @@ update_single_window (w, force_p)
3949 /* Record that this is not a frame-based redisplay. */ 3994 /* Record that this is not a frame-based redisplay. */
3950 set_frame_matrix_frame (NULL); 3995 set_frame_matrix_frame (NULL);
3951 3996
3997#if PERIODIC_PREEMPTION_CHECKING
3998 if (!force_p && NUMBERP (Vredisplay_preemption_period))
3999 {
4000 EMACS_TIME tm;
4001 double p = XFLOATINT (Vredisplay_preemption_period);
4002 int sec, usec;
4003
4004 sec = (int) p;
4005 usec = (p - sec) * 1000000;
4006
4007 EMACS_GET_TIME (tm);
4008 EMACS_SET_SECS_USECS (preemption_period, sec, usec);
4009 EMACS_ADD_TIME (preemption_next_check, tm, preemption_period);
4010 }
4011#endif
4012
3952 /* Update W. */ 4013 /* Update W. */
3953 update_begin (f); 4014 update_begin (f);
3954 update_window (w, force_p); 4015 update_window (w, force_p);
@@ -4108,7 +4169,9 @@ update_window (w, force_p)
4108{ 4169{
4109 struct glyph_matrix *desired_matrix = w->desired_matrix; 4170 struct glyph_matrix *desired_matrix = w->desired_matrix;
4110 int paused_p; 4171 int paused_p;
4172#if !PERIODIC_PREEMPTION_CHECKING
4111 int preempt_count = baud_rate / 2400 + 1; 4173 int preempt_count = baud_rate / 2400 + 1;
4174#endif
4112 extern int input_pending; 4175 extern int input_pending;
4113 extern Lisp_Object do_mouse_tracking; 4176 extern Lisp_Object do_mouse_tracking;
4114 struct redisplay_interface *rif = FRAME_RIF (XFRAME (WINDOW_FRAME (w))); 4177 struct redisplay_interface *rif = FRAME_RIF (XFRAME (WINDOW_FRAME (w)));
@@ -4120,8 +4183,13 @@ update_window (w, force_p)
4120 /* Check pending input the first time so that we can quickly return. */ 4183 /* Check pending input the first time so that we can quickly return. */
4121 if (redisplay_dont_pause) 4184 if (redisplay_dont_pause)
4122 force_p = 1; 4185 force_p = 1;
4123 else 4186#if PERIODIC_PREEMPTION_CHECKING
4187 else if (NILP (Vredisplay_preemption_period))
4188 force_p = 1;
4189#else
4190 else if (!force_p)
4124 detect_input_pending_ignore_squeezables (); 4191 detect_input_pending_ignore_squeezables ();
4192#endif
4125 4193
4126 /* If forced to complete the update, or if no input is pending, do 4194 /* If forced to complete the update, or if no input is pending, do
4127 the update. */ 4195 the update. */
@@ -4193,9 +4261,23 @@ update_window (w, force_p)
4193 detect_input_pending. If it's done too often, 4261 detect_input_pending. If it's done too often,
4194 scrolling large windows with repeated scroll-up 4262 scrolling large windows with repeated scroll-up
4195 commands will too quickly pause redisplay. */ 4263 commands will too quickly pause redisplay. */
4264#if PERIODIC_PREEMPTION_CHECKING
4265 if (!force_p)
4266 {
4267 EMACS_TIME tm, dif;
4268 EMACS_GET_TIME (tm);
4269 EMACS_SUB_TIME (dif, preemption_next_check, tm);
4270 if (EMACS_TIME_NEG_P (dif))
4271 {
4272 EMACS_ADD_TIME (preemption_next_check, tm, preemption_period);
4273 if (detect_input_pending_ignore_squeezables ())
4274 break;
4275 }
4276 }
4277#else
4196 if (!force_p && ++n_updated % preempt_count == 0) 4278 if (!force_p && ++n_updated % preempt_count == 0)
4197 detect_input_pending_ignore_squeezables (); 4279 detect_input_pending_ignore_squeezables ();
4198 4280#endif
4199 changed_p |= update_window_line (w, vpos, 4281 changed_p |= update_window_line (w, vpos,
4200 &mouse_face_overwritten_p); 4282 &mouse_face_overwritten_p);
4201 4283
@@ -5151,11 +5233,16 @@ update_frame_1 (f, force_p, inhibit_id_p)
5151 5233
5152 if (redisplay_dont_pause) 5234 if (redisplay_dont_pause)
5153 force_p = 1; 5235 force_p = 1;
5236#if PERIODIC_PREEMPTION_CHECKING
5237 else if (NILP (Vredisplay_preemption_period))
5238 force_p = 1;
5239#else
5154 else if (!force_p && detect_input_pending_ignore_squeezables ()) 5240 else if (!force_p && detect_input_pending_ignore_squeezables ())
5155 { 5241 {
5156 pause = 1; 5242 pause = 1;
5157 goto do_pause; 5243 goto do_pause;
5158 } 5244 }
5245#endif
5159 5246
5160 /* If we cannot insert/delete lines, it's no use trying it. */ 5247 /* If we cannot insert/delete lines, it's no use trying it. */
5161 if (!FRAME_LINE_INS_DEL_OK (f)) 5248 if (!FRAME_LINE_INS_DEL_OK (f))
@@ -5206,8 +5293,23 @@ update_frame_1 (f, force_p, inhibit_id_p)
5206 } 5293 }
5207 } 5294 }
5208 5295
5209 if ((i - 1) % preempt_count == 0) 5296#if PERIODIC_PREEMPTION_CHECKING
5297 if (!force_p)
5298 {
5299 EMACS_TIME tm, dif;
5300 EMACS_GET_TIME (tm);
5301 EMACS_SUB_TIME (dif, preemption_next_check, tm);
5302 if (EMACS_TIME_NEG_P (dif))
5303 {
5304 EMACS_ADD_TIME (preemption_next_check, tm, preemption_period);
5305 if (detect_input_pending_ignore_squeezables ())
5306 break;
5307 }
5308 }
5309#else
5310 if (!force_p && (i - 1) % preempt_count == 0)
5210 detect_input_pending_ignore_squeezables (); 5311 detect_input_pending_ignore_squeezables ();
5312#endif
5211 5313
5212 update_frame_line (f, i); 5314 update_frame_line (f, i);
5213 } 5315 }
@@ -6434,15 +6536,22 @@ Lisp_Object
6434sit_for (sec, usec, reading, display, initial_display) 6536sit_for (sec, usec, reading, display, initial_display)
6435 int sec, usec, reading, display, initial_display; 6537 int sec, usec, reading, display, initial_display;
6436{ 6538{
6539 int preempt = (sec >= 0) || (sec == 0 && usec >= 0);
6540
6437 swallow_events (display); 6541 swallow_events (display);
6438 6542
6439 if ((detect_input_pending_run_timers (display) 6543 if ((detect_input_pending_run_timers (display) && preempt)
6440 && !redisplay_dont_pause)
6441 || !NILP (Vexecuting_kbd_macro)) 6544 || !NILP (Vexecuting_kbd_macro))
6442 return Qnil; 6545 return Qnil;
6443 6546
6444 if (initial_display) 6547 if (initial_display)
6445 redisplay_preserve_echo_area (2); 6548 {
6549 int count = SPECPDL_INDEX ();
6550 if (!preempt)
6551 specbind (Qredisplay_dont_pause, Qt);
6552 redisplay_preserve_echo_area (2);
6553 unbind_to (count, Qnil);
6554 }
6446 6555
6447 if (sec == 0 && usec == 0) 6556 if (sec == 0 && usec == 0)
6448 return Qt; 6557 return Qt;
@@ -6468,8 +6577,7 @@ Redisplay is preempted as always if input arrives, and does not happen
6468if input is available before it starts. 6577if input is available before it starts.
6469Value is t if waited the full time with no input arriving. 6578Value is t if waited the full time with no input arriving.
6470 6579
6471Redisplay will occur even when input is available if you bind 6580Redisplay will occur even when input is available if SECONDS is negative.
6472`redisplay-dont-pause' to a non-nil value.
6473 6581
6474An obsolete but still supported form is 6582An obsolete but still supported form is
6475\(sit-for SECONDS &optional MILLISECONDS NODISP) 6583\(sit-for SECONDS &optional MILLISECONDS NODISP)
@@ -7000,7 +7108,14 @@ See `buffer-display-table' for more information. */);
7000 doc: /* *Non-nil means update isn't paused when input is detected. */); 7108 doc: /* *Non-nil means update isn't paused when input is detected. */);
7001 redisplay_dont_pause = 0; 7109 redisplay_dont_pause = 0;
7002 7110
7003 /* Initialize `window-system', unless init_display already decided it. */ 7111#if PERIODIC_PREEMPTION_CHECKING
7112 DEFVAR_LISP ("redisplay-preemption-period", &Vredisplay_preemption_period,
7113 doc: /* *The period in seconds between checking for input during redisplay.
7114If input is detected, redisplay is pre-empted, and the input is processed.
7115If nil, never pre-empt redisplay. */);
7116 Vredisplay_preemption_period = make_float (0.10);
7117#endif
7118
7004#ifdef CANNOT_DUMP 7119#ifdef CANNOT_DUMP
7005 if (noninteractive) 7120 if (noninteractive)
7006#endif 7121#endif
diff --git a/src/eval.c b/src/eval.c
index 20f29b5f06b..5f8d266ec7b 100644
--- a/src/eval.c
+++ b/src/eval.c
@@ -195,9 +195,10 @@ int handling_signal;
195 195
196Lisp_Object Vmacro_declaration_function; 196Lisp_Object Vmacro_declaration_function;
197 197
198extern Lisp_Object Qrisky_local_variable;
198 199
199static Lisp_Object funcall_lambda P_ ((Lisp_Object, int, Lisp_Object*)); 200static Lisp_Object funcall_lambda P_ ((Lisp_Object, int, Lisp_Object*));
200 201
201void 202void
202init_eval_once () 203init_eval_once ()
203{ 204{
@@ -895,6 +896,7 @@ usage: (defconst SYMBOL INITVALUE [DOCSTRING]) */)
895 tem = Fpurecopy (tem); 896 tem = Fpurecopy (tem);
896 Fput (sym, Qvariable_documentation, tem); 897 Fput (sym, Qvariable_documentation, tem);
897 } 898 }
899 Fput (sym, Qrisky_local_variable, Qt);
898 LOADHIST_ATTACH (sym); 900 LOADHIST_ATTACH (sym);
899 return sym; 901 return sym;
900} 902}
diff --git a/src/fileio.c b/src/fileio.c
index b2940d46e9e..e5b81ddfd7b 100644
--- a/src/fileio.c
+++ b/src/fileio.c
@@ -2752,7 +2752,13 @@ This is what happens in interactive use with M-x. */)
2752 CHECK_STRING (newname); 2752 CHECK_STRING (newname);
2753 file = Fexpand_file_name (file, Qnil); 2753 file = Fexpand_file_name (file, Qnil);
2754 2754
2755 if (!NILP (Ffile_directory_p (newname))) 2755 if ((!NILP (Ffile_directory_p (newname)))
2756#ifdef DOS_NT
2757 /* If the file names are identical but for the case,
2758 don't attempt to move directory to itself. */
2759 && (NILP (Fstring_equal (Fdowncase (file), Fdowncase (newname))))
2760#endif
2761 )
2756 newname = Fexpand_file_name (Ffile_name_nondirectory (file), newname); 2762 newname = Fexpand_file_name (Ffile_name_nondirectory (file), newname);
2757 else 2763 else
2758 newname = Fexpand_file_name (newname, Qnil); 2764 newname = Fexpand_file_name (newname, Qnil);
diff --git a/src/lread.c b/src/lread.c
index 797ae1078fb..8789ad03e1c 100644
--- a/src/lread.c
+++ b/src/lread.c
@@ -1949,7 +1949,7 @@ read_escape (readcharfun, stringp, byterep)
1949 while (++count <= unicode_hex_count) 1949 while (++count <= unicode_hex_count)
1950 { 1950 {
1951 c = READCHAR; 1951 c = READCHAR;
1952 /* isdigit(), isalpha() may be locale-specific, which we don't 1952 /* isdigit and isalpha may be locale-specific, which we don't
1953 want. */ 1953 want. */
1954 if (c >= '0' && c <= '9') i = (i << 4) + (c - '0'); 1954 if (c >= '0' && c <= '9') i = (i << 4) + (c - '0');
1955 else if (c >= 'a' && c <= 'f') i = (i << 4) + (c - 'a') + 10; 1955 else if (c >= 'a' && c <= 'f') i = (i << 4) + (c - 'a') + 10;
@@ -1962,21 +1962,16 @@ read_escape (readcharfun, stringp, byterep)
1962 } 1962 }
1963 1963
1964 GCPRO1 (readcharfun); 1964 GCPRO1 (readcharfun);
1965 lisp_char = call2(intern("decode-char"), intern("ucs"), 1965 lisp_char = call2 (intern ("decode-char"), intern ("ucs"),
1966 make_number(i)); 1966 make_number (i));
1967 UNGCPRO; 1967 UNGCPRO;
1968 1968
1969 if (EQ(Qnil, lisp_char)) 1969 if (NILP (lisp_char))
1970 { 1970 {
1971 /* This is ugly and horrible and trashes the user's data. */ 1971 error ("Unsupported Unicode code point: U+%x", (unsigned)i);
1972 XSETFASTINT (i, MAKE_CHAR (charset_katakana_jisx0201,
1973 34 + 128, 46 + 128));
1974 return i;
1975 }
1976 else
1977 {
1978 return XFASTINT (lisp_char);
1979 } 1972 }
1973
1974 return XFASTINT (lisp_char);
1980 } 1975 }
1981 1976
1982 default: 1977 default:
diff --git a/src/macfns.c b/src/macfns.c
index 4345cef2611..a053bc66763 100644
--- a/src/macfns.c
+++ b/src/macfns.c
@@ -3070,11 +3070,20 @@ If omitted or nil, that stands for the selected frame's display. */)
3070 (display) 3070 (display)
3071 Lisp_Object display; 3071 Lisp_Object display;
3072{ 3072{
3073 /* MAC_TODO: this is an approximation, and only of the main display */
3074
3075 struct mac_display_info *dpyinfo = check_x_display_info (display); 3073 struct mac_display_info *dpyinfo = check_x_display_info (display);
3074 /* Only of the main display. */
3075#if MAC_OS_X_VERSION_MAX_ALLOWED >= 1030
3076 CGSize size;
3077
3078 BLOCK_INPUT;
3079 size = CGDisplayScreenSize (kCGDirectMainDisplay);
3080 UNBLOCK_INPUT;
3076 3081
3082 return make_number ((int) (size.height + .5f));
3083#else
3084 /* This is an approximation. */
3077 return make_number ((int) (dpyinfo->height * 25.4 / dpyinfo->resy)); 3085 return make_number ((int) (dpyinfo->height * 25.4 / dpyinfo->resy));
3086#endif
3078} 3087}
3079 3088
3080DEFUN ("x-display-mm-width", Fx_display_mm_width, Sx_display_mm_width, 0, 1, 0, 3089DEFUN ("x-display-mm-width", Fx_display_mm_width, Sx_display_mm_width, 0, 1, 0,
@@ -3085,11 +3094,20 @@ If omitted or nil, that stands for the selected frame's display. */)
3085 (display) 3094 (display)
3086 Lisp_Object display; 3095 Lisp_Object display;
3087{ 3096{
3088 /* MAC_TODO: this is an approximation, and only of the main display */
3089
3090 struct mac_display_info *dpyinfo = check_x_display_info (display); 3097 struct mac_display_info *dpyinfo = check_x_display_info (display);
3098 /* Only of the main display. */
3099#if MAC_OS_X_VERSION_MAX_ALLOWED >= 1030
3100 CGSize size;
3101
3102 BLOCK_INPUT;
3103 size = CGDisplayScreenSize (kCGDirectMainDisplay);
3104 UNBLOCK_INPUT;
3091 3105
3106 return make_number ((int) (size.width + .5f));
3107#else
3108 /* This is an approximation. */
3092 return make_number ((int) (dpyinfo->width * 25.4 / dpyinfo->resx)); 3109 return make_number ((int) (dpyinfo->width * 25.4 / dpyinfo->resx));
3110#endif
3093} 3111}
3094 3112
3095DEFUN ("x-display-backing-store", Fx_display_backing_store, 3113DEFUN ("x-display-backing-store", Fx_display_backing_store,
diff --git a/src/macterm.c b/src/macterm.c
index b0765069277..19040392aa5 100644
--- a/src/macterm.c
+++ b/src/macterm.c
@@ -8512,6 +8512,9 @@ static Lisp_Object Qtext_input;
8512static Lisp_Object Qupdate_active_input_area, Qunicode_for_key_event; 8512static Lisp_Object Qupdate_active_input_area, Qunicode_for_key_event;
8513static Lisp_Object Vmac_ts_active_input_overlay; 8513static Lisp_Object Vmac_ts_active_input_overlay;
8514extern Lisp_Object Qbefore_string; 8514extern Lisp_Object Qbefore_string;
8515static Lisp_Object Vmac_ts_script_language_on_focus;
8516static ScriptLanguageRecord saved_ts_language;
8517static Component saved_ts_component;
8515#endif 8518#endif
8516#endif 8519#endif
8517extern int mac_ready_for_apple_events; 8520extern int mac_ready_for_apple_events;
@@ -8861,22 +8864,84 @@ is_emacs_window (WindowPtr win)
8861 return 0; 8864 return 0;
8862} 8865}
8863 8866
8864static void
8865do_app_resume ()
8866{
8867#if USE_MAC_TSM 8867#if USE_MAC_TSM
8868 ActivateTSMDocument (tsm_document_id); 8868static OSStatus
8869mac_tsm_resume ()
8870{
8871 OSStatus err;
8872 ScriptLanguageRecord slrec, *slptr = NULL;
8873
8874 err = ActivateTSMDocument (tsm_document_id);
8875
8876 if (err == noErr)
8877 {
8878 if (EQ (Vmac_ts_script_language_on_focus, Qt))
8879 slptr = &saved_ts_language;
8880 else if (CONSP (Vmac_ts_script_language_on_focus)
8881 && INTEGERP (XCAR (Vmac_ts_script_language_on_focus))
8882 && INTEGERP (XCDR (Vmac_ts_script_language_on_focus)))
8883 {
8884 slrec.fScript = XINT (XCAR (Vmac_ts_script_language_on_focus));
8885 slrec.fLanguage = XINT (XCDR (Vmac_ts_script_language_on_focus));
8886 slptr = &slrec;
8887 }
8888 }
8889
8890 if (slptr)
8891 {
8892#if MAC_OS_X_VERSION_MAX_ALLOWED >= 1020
8893 err = SetDefaultInputMethodOfClass (saved_ts_component, slptr,
8894 kKeyboardInputMethodClass);
8895#else
8896 err = SetDefaultInputMethod (saved_ts_component, slptr);
8869#endif 8897#endif
8898 if (err == noErr)
8899 err = SetTextServiceLanguage (slptr);
8900
8901 /* Seems to be needed on Mac OS X 10.2. */
8902 if (err == noErr)
8903 KeyScript (slptr->fScript | smKeyForceKeyScriptMask);
8904 }
8905
8906 return err;
8870} 8907}
8871 8908
8872static void 8909static OSStatus
8873do_app_suspend () 8910mac_tsm_suspend ()
8874{ 8911{
8875#if USE_MAC_TSM 8912 OSStatus err;
8876 DeactivateTSMDocument (tsm_document_id); 8913 ScriptLanguageRecord slrec, *slptr = NULL;
8914
8915 if (EQ (Vmac_ts_script_language_on_focus, Qt))
8916 {
8917 err = GetTextServiceLanguage (&saved_ts_language);
8918 if (err == noErr)
8919 slptr = &saved_ts_language;
8920 }
8921 else if (CONSP (Vmac_ts_script_language_on_focus)
8922 && INTEGERP (XCAR (Vmac_ts_script_language_on_focus))
8923 && INTEGERP (XCDR (Vmac_ts_script_language_on_focus)))
8924 {
8925 slrec.fScript = XINT (XCAR (Vmac_ts_script_language_on_focus));
8926 slrec.fLanguage = XINT (XCDR (Vmac_ts_script_language_on_focus));
8927 slptr = &slrec;
8928 }
8929
8930 if (slptr)
8931 {
8932#if MAC_OS_X_VERSION_MAX_ALLOWED >= 1020
8933 GetDefaultInputMethodOfClass (&saved_ts_component, slptr,
8934 kKeyboardInputMethodClass);
8935#else
8936 GetDefaultInputMethod (&saved_ts_component, slptr);
8877#endif 8937#endif
8878} 8938 }
8879 8939
8940 err = DeactivateTSMDocument (tsm_document_id);
8941
8942 return err;
8943}
8944#endif
8880 8945
8881static void 8946static void
8882do_apple_menu (SInt16 menu_item) 8947do_apple_menu (SInt16 menu_item)
@@ -9330,12 +9395,12 @@ mac_handle_window_event (next_handler, event, data)
9330#if USE_MAC_TSM 9395#if USE_MAC_TSM
9331 case kEventWindowFocusAcquired: 9396 case kEventWindowFocusAcquired:
9332 result = CallNextEventHandler (next_handler, event); 9397 result = CallNextEventHandler (next_handler, event);
9333 err = ActivateTSMDocument (tsm_document_id); 9398 err = mac_tsm_resume ();
9334 return err == noErr ? noErr : result; 9399 return err == noErr ? noErr : result;
9335 9400
9336 case kEventWindowFocusRelinquish: 9401 case kEventWindowFocusRelinquish:
9337 result = CallNextEventHandler (next_handler, event); 9402 result = CallNextEventHandler (next_handler, event);
9338 err = DeactivateTSMDocument (tsm_document_id); 9403 err = mac_tsm_suspend ();
9339 return err == noErr ? noErr : result; 9404 return err == noErr ? noErr : result;
9340#endif 9405#endif
9341 } 9406 }
@@ -10394,10 +10459,12 @@ XTread_socket (sd, expected, hold_quit)
10394 switch ((er.message >> 24) & 0x000000FF) 10459 switch ((er.message >> 24) & 0x000000FF)
10395 { 10460 {
10396 case suspendResumeMessage: 10461 case suspendResumeMessage:
10397 if ((er.message & resumeFlag) == 1) 10462#if USE_MAC_TSM
10398 do_app_resume (); 10463 if (er.message & resumeFlag)
10464 mac_tsm_resume ();
10399 else 10465 else
10400 do_app_suspend (); 10466 mac_tsm_suspend ();
10467#endif
10401 break; 10468 break;
10402 10469
10403 case mouseMovedMessage: 10470 case mouseMovedMessage:
@@ -10960,7 +11027,6 @@ void
10960mac_initialize_display_info () 11027mac_initialize_display_info ()
10961{ 11028{
10962 struct mac_display_info *dpyinfo = &one_mac_display_info; 11029 struct mac_display_info *dpyinfo = &one_mac_display_info;
10963 GDHandle main_device_handle;
10964 11030
10965 bzero (dpyinfo, sizeof (*dpyinfo)); 11031 bzero (dpyinfo, sizeof (*dpyinfo));
10966 11032
@@ -10976,37 +11042,29 @@ mac_initialize_display_info ()
10976 strcpy (dpyinfo->mac_id_name, "Mac Display"); 11042 strcpy (dpyinfo->mac_id_name, "Mac Display");
10977#endif 11043#endif
10978 11044
10979 main_device_handle = LMGetMainDevice();
10980
10981 dpyinfo->reference_count = 0; 11045 dpyinfo->reference_count = 0;
10982 dpyinfo->resx = 72.0; 11046 dpyinfo->resx = 72.0;
10983 dpyinfo->resy = 72.0; 11047 dpyinfo->resy = 72.0;
10984 dpyinfo->color_p = TestDeviceAttribute (main_device_handle, gdDevType);
10985#ifdef MAC_OSX 11048#ifdef MAC_OSX
10986 /* HasDepth returns true if it is possible to have a 32 bit display, 11049 /* HasDepth returns true if it is possible to have a 32 bit display,
10987 but this may not be what is actually used. Mac OSX can do better. 11050 but this may not be what is actually used. Mac OSX can do better. */
10988 CGMainDisplayID is only available on OSX 10.2 and higher, but the 11051 dpyinfo->color_p = 1;
10989 header for CGGetActiveDisplayList says that the first display returned 11052 dpyinfo->n_planes = CGDisplayBitsPerPixel (kCGDirectMainDisplay);
10990 is the active one, so we use that. */ 11053 dpyinfo->height = CGDisplayPixelsHigh (kCGDirectMainDisplay);
11054 dpyinfo->width = CGDisplayPixelsWide (kCGDirectMainDisplay);
11055#else
10991 { 11056 {
10992 CGDirectDisplayID disp_id[1]; 11057 GDHandle main_device_handle = LMGetMainDevice();
10993 CGDisplayCount disp_count;
10994 CGDisplayErr error_code;
10995
10996 error_code = CGGetActiveDisplayList (1, disp_id, &disp_count);
10997 if (error_code != 0)
10998 error ("No display found, CGGetActiveDisplayList error %d", error_code);
10999 11058
11000 dpyinfo->n_planes = CGDisplayBitsPerPixel (disp_id[0]); 11059 dpyinfo->color_p = TestDeviceAttribute (main_device_handle, gdDevType);
11060 for (dpyinfo->n_planes = 32; dpyinfo->n_planes > 0; dpyinfo->n_planes >>= 1)
11061 if (HasDepth (main_device_handle, dpyinfo->n_planes,
11062 gdDevType, dpyinfo->color_p))
11063 break;
11064 dpyinfo->height = (**main_device_handle).gdRect.bottom;
11065 dpyinfo->width = (**main_device_handle).gdRect.right;
11001 } 11066 }
11002#else
11003 for (dpyinfo->n_planes = 32; dpyinfo->n_planes > 0; dpyinfo->n_planes >>= 1)
11004 if (HasDepth (main_device_handle, dpyinfo->n_planes,
11005 gdDevType, dpyinfo->color_p))
11006 break;
11007#endif 11067#endif
11008 dpyinfo->height = (**main_device_handle).gdRect.bottom;
11009 dpyinfo->width = (**main_device_handle).gdRect.right;
11010 dpyinfo->grabbed = 0; 11068 dpyinfo->grabbed = 0;
11011 dpyinfo->root_window = NULL; 11069 dpyinfo->root_window = NULL;
11012 dpyinfo->image_cache = make_image_cache (); 11070 dpyinfo->image_cache = make_image_cache ();
@@ -11558,6 +11616,15 @@ order. */);
11558 DEFVAR_LISP ("mac-ts-active-input-overlay", &Vmac_ts_active_input_overlay, 11616 DEFVAR_LISP ("mac-ts-active-input-overlay", &Vmac_ts_active_input_overlay,
11559 doc: /* Overlay used to display Mac TSM active input area. */); 11617 doc: /* Overlay used to display Mac TSM active input area. */);
11560 Vmac_ts_active_input_overlay = Qnil; 11618 Vmac_ts_active_input_overlay = Qnil;
11619
11620 DEFVAR_LISP ("mac-ts-script-language-on-focus", &Vmac_ts_script_language_on_focus,
11621 doc: /* *How to change Mac TSM script/language when a frame gets focus.
11622If the value is t, the input script and language are restored to those
11623used in the last focus frame. If the value is a pair of integers, the
11624input script and language codes, which are defined in the Script
11625Manager, are set to its car and cdr parts, respectively. Otherwise,
11626Emacs doesn't set them and thus follows the system default behavior. */);
11627 Vmac_ts_script_language_on_focus = Qnil;
11561#endif 11628#endif
11562} 11629}
11563 11630
diff --git a/src/s/gnu-linux.h b/src/s/gnu-linux.h
index 4ef3db9f2ea..5d247a1c9c8 100644
--- a/src/s/gnu-linux.h
+++ b/src/s/gnu-linux.h
@@ -52,6 +52,9 @@ Boston, MA 02110-1301, USA. */
52#if LINUX_VERSION_CODE >= 0x20000 52#if LINUX_VERSION_CODE >= 0x20000
53#define LINUX_MAP_SHARED_DOES_WORK 53#define LINUX_MAP_SHARED_DOES_WORK
54#endif /* LINUX_VERSION_CODE >= 0x20000 */ 54#endif /* LINUX_VERSION_CODE >= 0x20000 */
55#if LINUX_VERSION_CODE >= 0x20400
56#define LINUX_SIGNALS_VIA_CHARACTERS_DOES_WORK
57#endif /* LINUX_VERSION_CODE >= 0x20400 */
55#endif /* HAVE_LINUX_VERSION_H */ 58#endif /* HAVE_LINUX_VERSION_H */
56#endif /* emacs */ 59#endif /* emacs */
57#endif /* NOT_C_CODE */ 60#endif /* NOT_C_CODE */
@@ -247,9 +250,9 @@ Boston, MA 02110-1301, USA. */
247#define C_DEBUG_SWITCH 250#define C_DEBUG_SWITCH
248#endif 251#endif
249 252
250/* Let's try this out, just in case. 253#ifdef LINUX_SIGNALS_VIA_CHARACTERS_DOES_WORK
251 Nah. Rik Faith <faith@cs.unc.edu> says it doesn't work well. */ 254#define SIGNALS_VIA_CHARACTERS
252/* #define SIGNALS_VIA_CHARACTERS */ 255#endif
253 256
254/* Rob Malouf <malouf@csli.stanford.edu> says: 257/* Rob Malouf <malouf@csli.stanford.edu> says:
255 SYSV IPC is standard a standard part of Linux since version 0.99pl10, 258 SYSV IPC is standard a standard part of Linux since version 0.99pl10,
diff --git a/src/syntax.c b/src/syntax.c
index 1c8d0debbf3..9af4773a01b 100644
--- a/src/syntax.c
+++ b/src/syntax.c
@@ -3122,6 +3122,20 @@ init_syntax_once ()
3122 3122
3123 Vstandard_syntax_table = Fmake_char_table (Qsyntax_table, temp); 3123 Vstandard_syntax_table = Fmake_char_table (Qsyntax_table, temp);
3124 3124
3125 /* Control characters should not be whitespace. */
3126 temp = XVECTOR (Vsyntax_code_object)->contents[(int) Spunct];
3127 for (i = 0; i <= ' ' - 1; i++)
3128 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, i, temp);
3129 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, 0177, temp);
3130
3131 /* Except that a few really are whitespace. */
3132 temp = XVECTOR (Vsyntax_code_object)->contents[(int) Swhitespace];
3133 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, ' ', temp);
3134 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, '\t', temp);
3135 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, '\n', temp);
3136 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, 015, temp);
3137 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, 014, temp);
3138
3125 temp = XVECTOR (Vsyntax_code_object)->contents[(int) Sword]; 3139 temp = XVECTOR (Vsyntax_code_object)->contents[(int) Sword];
3126 for (i = 'a'; i <= 'z'; i++) 3140 for (i = 'a'; i <= 'z'; i++)
3127 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, i, temp); 3141 SET_RAW_SYNTAX_ENTRY (Vstandard_syntax_table, i, temp);
diff --git a/src/window.c b/src/window.c
index e7f2ed93fd3..f3960b96f2a 100644
--- a/src/window.c
+++ b/src/window.c
@@ -65,7 +65,7 @@ static void window_scroll_pixel_based P_ ((Lisp_Object, int, int, int));
65static void window_scroll_line_based P_ ((Lisp_Object, int, int, int)); 65static void window_scroll_line_based P_ ((Lisp_Object, int, int, int));
66static int window_min_size_1 P_ ((struct window *, int)); 66static int window_min_size_1 P_ ((struct window *, int));
67static int window_min_size P_ ((struct window *, int, int, int *)); 67static int window_min_size P_ ((struct window *, int, int, int *));
68static void size_window P_ ((Lisp_Object, int, int, int)); 68static void size_window P_ ((Lisp_Object, int, int, int, int, int));
69static int freeze_window_start P_ ((struct window *, void *)); 69static int freeze_window_start P_ ((struct window *, void *));
70static int window_fixed_size_p P_ ((struct window *, int, int)); 70static int window_fixed_size_p P_ ((struct window *, int, int));
71static void enlarge_window P_ ((Lisp_Object, int, int)); 71static void enlarge_window P_ ((Lisp_Object, int, int));
@@ -2828,17 +2828,23 @@ shrink_windows (total, size, nchildren, shrinkable,
2828 2828
2829/* Set WINDOW's height or width to SIZE. WIDTH_P non-zero means set 2829/* Set WINDOW's height or width to SIZE. WIDTH_P non-zero means set
2830 WINDOW's width. Resize WINDOW's children, if any, so that they 2830 WINDOW's width. Resize WINDOW's children, if any, so that they
2831 keep their proportionate size relative to WINDOW. Propagate 2831 keep their proportionate size relative to WINDOW.
2832 WINDOW's top or left edge position to children. Delete windows 2832
2833 that become too small unless NODELETE_P is non-zero. 2833 If FIRST_ONLY is 1, change only the first of WINDOW's children when
2834 they are in series. If LAST_ONLY is 1, change only the last of
2835 WINDOW's children when they are in series.
2836
2837 Propagate WINDOW's top or left edge position to children. Delete
2838 windows that become too small unless NODELETE_P is non-zero.
2834 2839
2835 If NODELETE_P is 2, that means we do delete windows that are 2840 If NODELETE_P is 2, that means we do delete windows that are
2836 too small, even if they were too small before! */ 2841 too small, even if they were too small before! */
2837 2842
2838static void 2843static void
2839size_window (window, size, width_p, nodelete_p) 2844size_window (window, size, width_p, nodelete_p, first_only, last_only)
2840 Lisp_Object window; 2845 Lisp_Object window;
2841 int size, width_p, nodelete_p; 2846 int size, width_p, nodelete_p;
2847 int first_only, last_only;
2842{ 2848{
2843 struct window *w = XWINDOW (window); 2849 struct window *w = XWINDOW (window);
2844 struct window *c; 2850 struct window *c;
@@ -2913,6 +2919,7 @@ size_window (window, size, width_p, nodelete_p)
2913 2919
2914 if (!NILP (*sideward)) 2920 if (!NILP (*sideward))
2915 { 2921 {
2922 /* We have a chain of parallel siblings whose size should all change. */
2916 for (child = *sideward; !NILP (child); child = c->next) 2923 for (child = *sideward; !NILP (child); child = c->next)
2917 { 2924 {
2918 c = XWINDOW (child); 2925 c = XWINDOW (child);
@@ -2920,9 +2927,45 @@ size_window (window, size, width_p, nodelete_p)
2920 c->left_col = w->left_col; 2927 c->left_col = w->left_col;
2921 else 2928 else
2922 c->top_line = w->top_line; 2929 c->top_line = w->top_line;
2923 size_window (child, size, width_p, nodelete_p); 2930 size_window (child, size, width_p, nodelete_p,
2931 first_only, last_only);
2924 } 2932 }
2925 } 2933 }
2934 else if (!NILP (*forward) && last_only)
2935 {
2936 /* Change the last in a series of siblings. */
2937 Lisp_Object last_child;
2938 int child_size;
2939
2940 for (child = *forward; !NILP (child); child = c->next)
2941 {
2942 c = XWINDOW (child);
2943 last_child = child;
2944 }
2945
2946 child_size = XINT (width_p ? c->total_cols : c->total_lines);
2947 size_window (last_child,
2948 size - old_size + child_size,
2949 width_p, nodelete_p, first_only, last_only);
2950 }
2951 else if (!NILP (*forward) && first_only)
2952 {
2953 /* Change the first in a series of siblings. */
2954 int child_size;
2955
2956 child = *forward;
2957 c = XWINDOW (child);
2958
2959 if (width_p)
2960 c->left_col = w->left_col;
2961 else
2962 c->top_line = w->top_line;
2963
2964 child_size = XINT (width_p ? c->total_cols : c->total_lines);
2965 size_window (child,
2966 size - old_size + child_size,
2967 width_p, nodelete_p, first_only, last_only);
2968 }
2926 else if (!NILP (*forward)) 2969 else if (!NILP (*forward))
2927 { 2970 {
2928 int fixed_size, each, extra, n; 2971 int fixed_size, each, extra, n;
@@ -2930,7 +2973,7 @@ size_window (window, size, width_p, nodelete_p)
2930 int last_pos, first_pos, nchildren, total; 2973 int last_pos, first_pos, nchildren, total;
2931 int *new_sizes = NULL; 2974 int *new_sizes = NULL;
2932 2975
2933 /* Determine the fixed-size portion of the this window, and the 2976 /* Determine the fixed-size portion of this window, and the
2934 number of child windows. */ 2977 number of child windows. */
2935 fixed_size = nchildren = nfixed = total = 0; 2978 fixed_size = nchildren = nfixed = total = 0;
2936 for (child = *forward; !NILP (child); child = c->next, ++nchildren) 2979 for (child = *forward; !NILP (child); child = c->next, ++nchildren)
@@ -2993,7 +3036,7 @@ size_window (window, size, width_p, nodelete_p)
2993 /* Set new height. Note that size_window also propagates 3036 /* Set new height. Note that size_window also propagates
2994 edge positions to children, so it's not a no-op if we 3037 edge positions to children, so it's not a no-op if we
2995 didn't change the child's size. */ 3038 didn't change the child's size. */
2996 size_window (child, new_size, width_p, 1); 3039 size_window (child, new_size, width_p, 1, first_only, last_only);
2997 3040
2998 /* Remember the bottom/right edge position of this child; it 3041 /* Remember the bottom/right edge position of this child; it
2999 will be used to set the top/left edge of the next child. */ 3042 will be used to set the top/left edge of the next child. */
@@ -3012,7 +3055,7 @@ size_window (window, size, width_p, nodelete_p)
3012 int child_size; 3055 int child_size;
3013 c = XWINDOW (child); 3056 c = XWINDOW (child);
3014 child_size = width_p ? XINT (c->total_cols) : XINT (c->total_lines); 3057 child_size = width_p ? XINT (c->total_cols) : XINT (c->total_lines);
3015 size_window (child, child_size, width_p, 2); 3058 size_window (child, child_size, width_p, 2, first_only, last_only);
3016 } 3059 }
3017 } 3060 }
3018} 3061}
@@ -3028,7 +3071,7 @@ set_window_height (window, height, nodelete)
3028 int height; 3071 int height;
3029 int nodelete; 3072 int nodelete;
3030{ 3073{
3031 size_window (window, height, 0, nodelete); 3074 size_window (window, height, 0, nodelete, 0, 0);
3032} 3075}
3033 3076
3034 3077
@@ -3043,7 +3086,7 @@ set_window_width (window, width, nodelete)
3043 int width; 3086 int width;
3044 int nodelete; 3087 int nodelete;
3045{ 3088{
3046 size_window (window, width, 1, nodelete); 3089 size_window (window, width, 1, nodelete, 0, 0);
3047} 3090}
3048 3091
3049/* Change window heights in windows rooted in WINDOW by N lines. */ 3092/* Change window heights in windows rooted in WINDOW by N lines. */
@@ -4281,21 +4324,31 @@ adjust_window_trailing_edge (window, delta, horiz_flag)
4281 { 4324 {
4282 Lisp_Object first_parallel = Qnil; 4325 Lisp_Object first_parallel = Qnil;
4283 4326
4284 p = XWINDOW (window); 4327 if (NILP (window))
4285 parent = p->parent;
4286
4287 if (NILP (XWINDOW (window)->next))
4288 { 4328 {
4329 /* This happens if WINDOW on the previous iteration was
4330 at top level of the window tree. */
4289 Fset_window_configuration (old_config); 4331 Fset_window_configuration (old_config);
4290 error ("No other window following this one"); 4332 error ("Specified window edge is fixed");
4291 } 4333 }
4292 4334
4335 p = XWINDOW (window);
4336 parent = p->parent;
4337
4293 /* See if this level has windows in parallel in the specified 4338 /* See if this level has windows in parallel in the specified
4294 direction. If so, set FIRST_PARALLEL to the first one. */ 4339 direction. If so, set FIRST_PARALLEL to the first one. */
4295 if (horiz_flag) 4340 if (horiz_flag)
4296 { 4341 {
4297 if (! NILP (parent) && !NILP (XWINDOW (parent)->vchild)) 4342 if (! NILP (parent) && !NILP (XWINDOW (parent)->vchild))
4298 first_parallel = XWINDOW (parent)->vchild; 4343 first_parallel = XWINDOW (parent)->vchild;
4344 else if (NILP (parent) && !NILP (p->next))
4345 {
4346 /* Handle the vertical chain of main window and minibuffer
4347 which has no parent. */
4348 first_parallel = window;
4349 while (! NILP (XWINDOW (first_parallel)->prev))
4350 first_parallel = XWINDOW (first_parallel)->prev;
4351 }
4299 } 4352 }
4300 else 4353 else
4301 { 4354 {
@@ -4303,6 +4356,16 @@ adjust_window_trailing_edge (window, delta, horiz_flag)
4303 first_parallel = XWINDOW (parent)->hchild; 4356 first_parallel = XWINDOW (parent)->hchild;
4304 } 4357 }
4305 4358
4359 /* If this level's succession is in the desired dimension,
4360 and this window is the last one, and there is no higher level,
4361 its trailing edge is fixed. */
4362 if (NILP (XWINDOW (window)->next) && NILP (first_parallel)
4363 && NILP (parent))
4364 {
4365 Fset_window_configuration (old_config);
4366 error ("Specified window edge is fixed");
4367 }
4368
4306 /* Don't make this window too small. */ 4369 /* Don't make this window too small. */
4307 if (XINT (CURSIZE (window)) + delta 4370 if (XINT (CURSIZE (window)) + delta
4308 < (horiz_flag ? window_min_width : window_min_height)) 4371 < (horiz_flag ? window_min_width : window_min_height))
@@ -4326,7 +4389,7 @@ adjust_window_trailing_edge (window, delta, horiz_flag)
4326 we will fail and report an error, above.) */ 4389 we will fail and report an error, above.) */
4327 if (NILP (first_parallel)) 4390 if (NILP (first_parallel))
4328 { 4391 {
4329 if (!NILP (XWINDOW (window)->next)) 4392 if (!NILP (p->next))
4330 { 4393 {
4331 /* This may happen for the minibuffer. In that case 4394 /* This may happen for the minibuffer. In that case
4332 the window_deletion_count check below does not work. */ 4395 the window_deletion_count check below does not work. */
@@ -4339,7 +4402,7 @@ adjust_window_trailing_edge (window, delta, horiz_flag)
4339 XSETINT (CURBEG (p->next), 4402 XSETINT (CURBEG (p->next),
4340 XINT (CURBEG (p->next)) + delta); 4403 XINT (CURBEG (p->next)) + delta);
4341 size_window (p->next, XINT (CURSIZE (p->next)) - delta, 4404 size_window (p->next, XINT (CURSIZE (p->next)) - delta,
4342 horiz_flag, 0); 4405 horiz_flag, 0, 1, 0);
4343 break; 4406 break;
4344 } 4407 }
4345 } 4408 }
@@ -4351,7 +4414,7 @@ adjust_window_trailing_edge (window, delta, horiz_flag)
4351 child = XWINDOW (child)->next) 4414 child = XWINDOW (child)->next)
4352 if (! EQ (child, window)) 4415 if (! EQ (child, window))
4353 size_window (child, XINT (CURSIZE (child)) + delta, 4416 size_window (child, XINT (CURSIZE (child)) + delta,
4354 horiz_flag, 0); 4417 horiz_flag, 0, 0, 1);
4355 4418
4356 window = parent; 4419 window = parent;
4357 } 4420 }
diff --git a/src/xdisp.c b/src/xdisp.c
index f87f38dc50e..c7e6eda58ca 100644
--- a/src/xdisp.c
+++ b/src/xdisp.c
@@ -903,6 +903,7 @@ static int display_string P_ ((unsigned char *, Lisp_Object, Lisp_Object,
903static void compute_line_metrics P_ ((struct it *)); 903static void compute_line_metrics P_ ((struct it *));
904static void run_redisplay_end_trigger_hook P_ ((struct it *)); 904static void run_redisplay_end_trigger_hook P_ ((struct it *));
905static int get_overlay_strings P_ ((struct it *, int)); 905static int get_overlay_strings P_ ((struct it *, int));
906static int get_overlay_strings_1 P_ ((struct it *, int, int));
906static void next_overlay_string P_ ((struct it *)); 907static void next_overlay_string P_ ((struct it *));
907static void reseat P_ ((struct it *, struct text_pos, int)); 908static void reseat P_ ((struct it *, struct text_pos, int));
908static void reseat_1 P_ ((struct it *, struct text_pos, int)); 909static void reseat_1 P_ ((struct it *, struct text_pos, int));
@@ -2896,8 +2897,8 @@ init_from_display_pos (it, w, pos)
2896 also ``processed'' overlay strings at ZV. */ 2897 also ``processed'' overlay strings at ZV. */
2897 while (it->sp) 2898 while (it->sp)
2898 pop_it (it); 2899 pop_it (it);
2899 it->current.overlay_string_index = -1; 2900 xassert (it->current.overlay_string_index == -1);
2900 it->method = GET_FROM_BUFFER; 2901 xassert (it->method == GET_FROM_BUFFER);
2901 if (CHARPOS (pos->pos) == ZV) 2902 if (CHARPOS (pos->pos) == ZV)
2902 it->overlay_strings_at_end_processed_p = 1; 2903 it->overlay_strings_at_end_processed_p = 1;
2903 } 2904 }
@@ -3008,7 +3009,19 @@ handle_stop (it)
3008 if (handled == HANDLED_RECOMPUTE_PROPS) 3009 if (handled == HANDLED_RECOMPUTE_PROPS)
3009 break; 3010 break;
3010 else if (handled == HANDLED_RETURN) 3011 else if (handled == HANDLED_RETURN)
3011 return; 3012 {
3013 /* We still want to show before and after strings from
3014 overlays even if the actual buffer text is replaced. */
3015 if (!handle_overlay_change_p || it->sp > 1)
3016 return;
3017 if (!get_overlay_strings_1 (it, 0, 0))
3018 return;
3019 it->ignore_overlay_strings_at_pos_p = 1;
3020 it->string_from_display_prop_p = 0;
3021 handle_overlay_change_p = 0;
3022 handled = HANDLED_RECOMPUTE_PROPS;
3023 break;
3024 }
3012 else if (handled == HANDLED_OVERLAY_STRING_CONSUMED) 3025 else if (handled == HANDLED_OVERLAY_STRING_CONSUMED)
3013 handle_overlay_change_p = 0; 3026 handle_overlay_change_p = 0;
3014 } 3027 }
@@ -4460,6 +4473,8 @@ handle_composition_prop (it)
4460 } 4473 }
4461 return HANDLED_RECOMPUTE_PROPS; 4474 return HANDLED_RECOMPUTE_PROPS;
4462 } 4475 }
4476
4477 push_it (it);
4463 it->method = GET_FROM_COMPOSITION; 4478 it->method = GET_FROM_COMPOSITION;
4464 it->cmp_id = id; 4479 it->cmp_id = id;
4465 it->cmp_len = COMPOSITION_LENGTH (prop); 4480 it->cmp_len = COMPOSITION_LENGTH (prop);
@@ -4529,13 +4544,14 @@ next_overlay_string (it)
4529 int display_ellipsis_p = it->stack[it->sp - 1].display_ellipsis_p; 4544 int display_ellipsis_p = it->stack[it->sp - 1].display_ellipsis_p;
4530 4545
4531 pop_it (it); 4546 pop_it (it);
4532 xassert (it->stop_charpos >= BEGV 4547 xassert (it->sp > 0
4533 && it->stop_charpos <= it->end_charpos); 4548 || it->method == GET_FROM_COMPOSITION
4534 it->string = Qnil; 4549 || (NILP (it->string)
4550 && it->method == GET_FROM_BUFFER
4551 && it->stop_charpos >= BEGV
4552 && it->stop_charpos <= it->end_charpos));
4535 it->current.overlay_string_index = -1; 4553 it->current.overlay_string_index = -1;
4536 SET_TEXT_POS (it->current.string_pos, -1, -1);
4537 it->n_overlay_strings = 0; 4554 it->n_overlay_strings = 0;
4538 it->method = GET_FROM_BUFFER;
4539 4555
4540 /* If we're at the end of the buffer, record that we have 4556 /* If we're at the end of the buffer, record that we have
4541 processed the overlay strings there already, so that 4557 processed the overlay strings there already, so that
@@ -4791,7 +4807,7 @@ load_overlay_strings (it, charpos)
4791 least one overlay string was found. */ 4807 least one overlay string was found. */
4792 4808
4793static int 4809static int
4794get_overlay_strings (it, charpos) 4810get_overlay_strings_1 (it, charpos, compute_stop_p)
4795 struct it *it; 4811 struct it *it;
4796 int charpos; 4812 int charpos;
4797{ 4813{
@@ -4813,12 +4829,13 @@ get_overlay_strings (it, charpos)
4813 /* Make sure we know settings in current_buffer, so that we can 4829 /* Make sure we know settings in current_buffer, so that we can
4814 restore meaningful values when we're done with the overlay 4830 restore meaningful values when we're done with the overlay
4815 strings. */ 4831 strings. */
4816 compute_stop_pos (it); 4832 if (compute_stop_p)
4833 compute_stop_pos (it);
4817 xassert (it->face_id >= 0); 4834 xassert (it->face_id >= 0);
4818 4835
4819 /* Save IT's settings. They are restored after all overlay 4836 /* Save IT's settings. They are restored after all overlay
4820 strings have been processed. */ 4837 strings have been processed. */
4821 xassert (it->sp == 0); 4838 xassert (!compute_stop_p || it->sp == 0);
4822 push_it (it); 4839 push_it (it);
4823 4840
4824 /* Set up IT to deliver display elements from the first overlay 4841 /* Set up IT to deliver display elements from the first overlay
@@ -4830,14 +4847,23 @@ get_overlay_strings (it, charpos)
4830 it->end_charpos = SCHARS (it->string); 4847 it->end_charpos = SCHARS (it->string);
4831 it->multibyte_p = STRING_MULTIBYTE (it->string); 4848 it->multibyte_p = STRING_MULTIBYTE (it->string);
4832 it->method = GET_FROM_STRING; 4849 it->method = GET_FROM_STRING;
4833 } 4850 return 1;
4834 else
4835 {
4836 it->string = Qnil;
4837 it->current.overlay_string_index = -1;
4838 it->method = GET_FROM_BUFFER;
4839 } 4851 }
4840 4852
4853 it->current.overlay_string_index = -1;
4854 return 0;
4855}
4856
4857static int
4858get_overlay_strings (it, charpos)
4859 struct it *it;
4860 int charpos;
4861{
4862 it->string = Qnil;
4863 it->method = GET_FROM_BUFFER;
4864
4865 (void) get_overlay_strings_1 (it, charpos, 1);
4866
4841 CHECK_IT (it); 4867 CHECK_IT (it);
4842 4868
4843 /* Value is non-zero if we found at least one overlay string. */ 4869 /* Value is non-zero if we found at least one overlay string. */
@@ -4861,19 +4887,38 @@ push_it (it)
4861{ 4887{
4862 struct iterator_stack_entry *p; 4888 struct iterator_stack_entry *p;
4863 4889
4864 xassert (it->sp < 2); 4890 xassert (it->sp < IT_STACK_SIZE);
4865 p = it->stack + it->sp; 4891 p = it->stack + it->sp;
4866 4892
4867 p->stop_charpos = it->stop_charpos; 4893 p->stop_charpos = it->stop_charpos;
4868 xassert (it->face_id >= 0); 4894 xassert (it->face_id >= 0);
4869 p->face_id = it->face_id; 4895 p->face_id = it->face_id;
4870 p->string = it->string; 4896 p->string = it->string;
4871 p->pos = it->current; 4897 p->method = it->method;
4898 switch (p->method)
4899 {
4900 case GET_FROM_IMAGE:
4901 p->u.image.object = it->object;
4902 p->u.image.image_id = it->image_id;
4903 p->u.image.slice = it->slice;
4904 break;
4905 case GET_FROM_COMPOSITION:
4906 p->u.comp.object = it->object;
4907 p->u.comp.c = it->c;
4908 p->u.comp.len = it->len;
4909 p->u.comp.cmp_id = it->cmp_id;
4910 p->u.comp.cmp_len = it->cmp_len;
4911 break;
4912 case GET_FROM_STRETCH:
4913 p->u.stretch.object = it->object;
4914 break;
4915 }
4916 p->position = it->position;
4917 p->current = it->current;
4872 p->end_charpos = it->end_charpos; 4918 p->end_charpos = it->end_charpos;
4873 p->string_nchars = it->string_nchars; 4919 p->string_nchars = it->string_nchars;
4874 p->area = it->area; 4920 p->area = it->area;
4875 p->multibyte_p = it->multibyte_p; 4921 p->multibyte_p = it->multibyte_p;
4876 p->slice = it->slice;
4877 p->space_width = it->space_width; 4922 p->space_width = it->space_width;
4878 p->font_height = it->font_height; 4923 p->font_height = it->font_height;
4879 p->voffset = it->voffset; 4924 p->voffset = it->voffset;
@@ -4900,13 +4945,34 @@ pop_it (it)
4900 p = it->stack + it->sp; 4945 p = it->stack + it->sp;
4901 it->stop_charpos = p->stop_charpos; 4946 it->stop_charpos = p->stop_charpos;
4902 it->face_id = p->face_id; 4947 it->face_id = p->face_id;
4948 it->current = p->current;
4949 it->position = p->position;
4903 it->string = p->string; 4950 it->string = p->string;
4904 it->current = p->pos; 4951 if (NILP (it->string))
4952 SET_TEXT_POS (it->current.string_pos, -1, -1);
4953 it->method = p->method;
4954 switch (it->method)
4955 {
4956 case GET_FROM_IMAGE:
4957 it->image_id = p->u.image.image_id;
4958 it->object = p->u.image.object;
4959 it->slice = p->u.image.slice;
4960 break;
4961 case GET_FROM_COMPOSITION:
4962 it->object = p->u.comp.object;
4963 it->c = p->u.comp.c;
4964 it->len = p->u.comp.len;
4965 it->cmp_id = p->u.comp.cmp_id;
4966 it->cmp_len = p->u.comp.cmp_len;
4967 break;
4968 case GET_FROM_STRETCH:
4969 it->object = p->u.comp.object;
4970 break;
4971 }
4905 it->end_charpos = p->end_charpos; 4972 it->end_charpos = p->end_charpos;
4906 it->string_nchars = p->string_nchars; 4973 it->string_nchars = p->string_nchars;
4907 it->area = p->area; 4974 it->area = p->area;
4908 it->multibyte_p = p->multibyte_p; 4975 it->multibyte_p = p->multibyte_p;
4909 it->slice = p->slice;
4910 it->space_width = p->space_width; 4976 it->space_width = p->space_width;
4911 it->font_height = p->font_height; 4977 it->font_height = p->font_height;
4912 it->voffset = p->voffset; 4978 it->voffset = p->voffset;
@@ -5038,6 +5104,7 @@ back_to_previous_visible_line_start (it)
5038 while (IT_CHARPOS (*it) > BEGV) 5104 while (IT_CHARPOS (*it) > BEGV)
5039 { 5105 {
5040 back_to_previous_line_start (it); 5106 back_to_previous_line_start (it);
5107
5041 if (IT_CHARPOS (*it) <= BEGV) 5108 if (IT_CHARPOS (*it) <= BEGV)
5042 break; 5109 break;
5043 5110
@@ -5057,37 +5124,47 @@ back_to_previous_visible_line_start (it)
5057 continue; 5124 continue;
5058 } 5125 }
5059 5126
5060 /* If newline has a display property that replaces the newline with something 5127 if (IT_CHARPOS (*it) <= BEGV)
5061 else (image or text), find start of overlay or interval and continue search 5128 break;
5062 from that point. */
5063 if (IT_CHARPOS (*it) > BEGV)
5064 {
5065 struct it it2 = *it;
5066 int pos;
5067 int beg, end;
5068 Lisp_Object val, overlay;
5069
5070 pos = --IT_CHARPOS (it2);
5071 --IT_BYTEPOS (it2);
5072 it2.sp = 0;
5073 if (handle_display_prop (&it2) == HANDLED_RETURN
5074 && !NILP (val = get_char_property_and_overlay
5075 (make_number (pos), Qdisplay, Qnil, &overlay))
5076 && (OVERLAYP (overlay)
5077 ? (beg = OVERLAY_POSITION (OVERLAY_START (overlay)))
5078 : get_property_and_range (pos, Qdisplay, &val, &beg, &end, Qnil)))
5079 {
5080 if (beg < BEGV)
5081 beg = BEGV;
5082 IT_CHARPOS (*it) = beg;
5083 IT_BYTEPOS (*it) = buf_charpos_to_bytepos (current_buffer, beg);
5084 continue;
5085 }
5086 }
5087 5129
5088 break; 5130 {
5131 struct it it2;
5132 int pos;
5133 int beg, end;
5134 Lisp_Object val, overlay;
5135
5136 /* If newline is part of a composition, continue from start of composition */
5137 if (find_composition (IT_CHARPOS (*it), -1, &beg, &end, &val, Qnil)
5138 && beg < IT_CHARPOS (*it))
5139 goto replaced;
5140
5141 /* If newline is replaced by a display property, find start of overlay
5142 or interval and continue search from that point. */
5143 it2 = *it;
5144 pos = --IT_CHARPOS (it2);
5145 --IT_BYTEPOS (it2);
5146 it2.sp = 0;
5147 if (handle_display_prop (&it2) == HANDLED_RETURN
5148 && !NILP (val = get_char_property_and_overlay
5149 (make_number (pos), Qdisplay, Qnil, &overlay))
5150 && (OVERLAYP (overlay)
5151 ? (beg = OVERLAY_POSITION (OVERLAY_START (overlay)))
5152 : get_property_and_range (pos, Qdisplay, &val, &beg, &end, Qnil)))
5153 goto replaced;
5154
5155 /* Newline is not replaced by anything -- so we are done. */
5156 break;
5157
5158 replaced:
5159 if (beg < BEGV)
5160 beg = BEGV;
5161 IT_CHARPOS (*it) = beg;
5162 IT_BYTEPOS (*it) = buf_charpos_to_bytepos (current_buffer, beg);
5163 }
5089 } 5164 }
5090 5165
5166 it->continuation_lines_width = 0;
5167
5091 xassert (IT_CHARPOS (*it) >= BEGV); 5168 xassert (IT_CHARPOS (*it) >= BEGV);
5092 xassert (IT_CHARPOS (*it) == BEGV 5169 xassert (IT_CHARPOS (*it) == BEGV
5093 || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n'); 5170 || FETCH_BYTE (IT_BYTEPOS (*it) - 1) == '\n');
@@ -5219,15 +5296,11 @@ reseat_1 (it, pos, set_stop_p)
5219 IT_STRING_BYTEPOS (*it) = -1; 5296 IT_STRING_BYTEPOS (*it) = -1;
5220 it->string = Qnil; 5297 it->string = Qnil;
5221 it->method = GET_FROM_BUFFER; 5298 it->method = GET_FROM_BUFFER;
5222 /* RMS: I added this to fix a bug in move_it_vertically_backward 5299 it->object = it->w->buffer;
5223 where it->area continued to relate to the starting point
5224 for the backward motion. Bug report from
5225 Nick Roberts <nick@nick.uklinux.net> on 19 May 2003.
5226 However, I am not sure whether reseat still does the right thing
5227 in general after this change. */
5228 it->area = TEXT_AREA; 5300 it->area = TEXT_AREA;
5229 it->multibyte_p = !NILP (current_buffer->enable_multibyte_characters); 5301 it->multibyte_p = !NILP (current_buffer->enable_multibyte_characters);
5230 it->sp = 0; 5302 it->sp = 0;
5303 it->string_from_display_prop_p = 0;
5231 it->face_before_selective_p = 0; 5304 it->face_before_selective_p = 0;
5232 5305
5233 if (set_stop_p) 5306 if (set_stop_p)
@@ -5706,18 +5779,20 @@ set_iterator_to_next (it, reseat_p)
5706 5779
5707 case GET_FROM_COMPOSITION: 5780 case GET_FROM_COMPOSITION:
5708 xassert (it->cmp_id >= 0 && it->cmp_id < n_compositions); 5781 xassert (it->cmp_id >= 0 && it->cmp_id < n_compositions);
5709 if (STRINGP (it->string)) 5782 xassert (it->sp > 0);
5783 pop_it (it);
5784 if (it->method == GET_FROM_STRING)
5710 { 5785 {
5711 IT_STRING_BYTEPOS (*it) += it->len; 5786 IT_STRING_BYTEPOS (*it) += it->len;
5712 IT_STRING_CHARPOS (*it) += it->cmp_len; 5787 IT_STRING_CHARPOS (*it) += it->cmp_len;
5713 it->method = GET_FROM_STRING; 5788 it->object = it->string;
5714 goto consider_string_end; 5789 goto consider_string_end;
5715 } 5790 }
5716 else 5791 else if (it->method == GET_FROM_BUFFER)
5717 { 5792 {
5718 IT_BYTEPOS (*it) += it->len; 5793 IT_BYTEPOS (*it) += it->len;
5719 IT_CHARPOS (*it) += it->cmp_len; 5794 IT_CHARPOS (*it) += it->cmp_len;
5720 it->method = GET_FROM_BUFFER; 5795 it->object = it->w->buffer;
5721 } 5796 }
5722 break; 5797 break;
5723 5798
@@ -5747,7 +5822,10 @@ set_iterator_to_next (it, reseat_p)
5747 else if (STRINGP (it->string)) 5822 else if (STRINGP (it->string))
5748 it->method = GET_FROM_STRING; 5823 it->method = GET_FROM_STRING;
5749 else 5824 else
5750 it->method = GET_FROM_BUFFER; 5825 {
5826 it->method = GET_FROM_BUFFER;
5827 it->object = it->w->buffer;
5828 }
5751 5829
5752 it->dpvec = NULL; 5830 it->dpvec = NULL;
5753 it->current.dpvec_index = -1; 5831 it->current.dpvec_index = -1;
@@ -5795,9 +5873,8 @@ set_iterator_to_next (it, reseat_p)
5795 && it->sp > 0) 5873 && it->sp > 0)
5796 { 5874 {
5797 pop_it (it); 5875 pop_it (it);
5798 if (STRINGP (it->string)) 5876 if (it->method == GET_FROM_STRING)
5799 goto consider_string_end; 5877 goto consider_string_end;
5800 it->method = GET_FROM_BUFFER;
5801 } 5878 }
5802 } 5879 }
5803 break; 5880 break;
@@ -5809,13 +5886,8 @@ set_iterator_to_next (it, reseat_p)
5809 if the `display' property takes up the whole string. */ 5886 if the `display' property takes up the whole string. */
5810 xassert (it->sp > 0); 5887 xassert (it->sp > 0);
5811 pop_it (it); 5888 pop_it (it);
5812 it->image_id = 0; 5889 if (it->method == GET_FROM_STRING)
5813 if (STRINGP (it->string)) 5890 goto consider_string_end;
5814 {
5815 it->method = GET_FROM_STRING;
5816 goto consider_string_end;
5817 }
5818 it->method = GET_FROM_BUFFER;
5819 break; 5891 break;
5820 5892
5821 default: 5893 default:
@@ -6038,6 +6110,7 @@ next_element_from_ellipsis (it)
6038 setting face_before_selective_p. */ 6110 setting face_before_selective_p. */
6039 it->saved_face_id = it->face_id; 6111 it->saved_face_id = it->face_id;
6040 it->method = GET_FROM_BUFFER; 6112 it->method = GET_FROM_BUFFER;
6113 it->object = it->w->buffer;
6041 reseat_at_next_visible_line_start (it, 1); 6114 reseat_at_next_visible_line_start (it, 1);
6042 it->face_before_selective_p = 1; 6115 it->face_before_selective_p = 1;
6043 } 6116 }
@@ -6226,6 +6299,8 @@ next_element_from_composition (it)
6226 : it->current.pos); 6299 : it->current.pos);
6227 if (STRINGP (it->string)) 6300 if (STRINGP (it->string))
6228 it->object = it->string; 6301 it->object = it->string;
6302 else
6303 it->object = it->w->buffer;
6229 return 1; 6304 return 1;
6230} 6305}
6231 6306
@@ -11687,9 +11762,12 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
11687 } 11762 }
11688 else 11763 else
11689 { 11764 {
11690 string_before_pos = last_pos; 11765 if (string_start == NULL)
11691 string_start = glyph; 11766 {
11692 string_start_x = x; 11767 string_before_pos = last_pos;
11768 string_start = glyph;
11769 string_start_x = x;
11770 }
11693 /* Skip all glyphs from string. */ 11771 /* Skip all glyphs from string. */
11694 do 11772 do
11695 { 11773 {
@@ -11747,25 +11825,25 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
11747 glyph on point by scanning from string_start again. */ 11825 glyph on point by scanning from string_start again. */
11748 Lisp_Object limit; 11826 Lisp_Object limit;
11749 Lisp_Object string; 11827 Lisp_Object string;
11828 struct glyph *stop = glyph;
11750 int pos; 11829 int pos;
11751 11830
11752 limit = make_number (pt_old + 1); 11831 limit = make_number (pt_old + 1);
11753 end = glyph;
11754 glyph = string_start; 11832 glyph = string_start;
11755 x = string_start_x; 11833 x = string_start_x;
11756 string = glyph->object; 11834 string = glyph->object;
11757 pos = string_buffer_position (w, string, string_before_pos); 11835 pos = string_buffer_position (w, string, string_before_pos);
11758 /* If STRING is from overlay, LAST_POS == 0. We skip such glyphs 11836 /* If STRING is from overlay, LAST_POS == 0. We skip such glyphs
11759 because we always put cursor after overlay strings. */ 11837 because we always put cursor after overlay strings. */
11760 while (pos == 0 && glyph < end) 11838 while (pos == 0 && glyph < stop)
11761 { 11839 {
11762 string = glyph->object; 11840 string = glyph->object;
11763 SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string)); 11841 SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
11764 if (glyph < end) 11842 if (glyph < stop)
11765 pos = string_buffer_position (w, glyph->object, string_before_pos); 11843 pos = string_buffer_position (w, glyph->object, string_before_pos);
11766 } 11844 }
11767 11845
11768 while (glyph < end) 11846 while (glyph < stop)
11769 { 11847 {
11770 pos = XINT (Fnext_single_char_property_change 11848 pos = XINT (Fnext_single_char_property_change
11771 (make_number (pos), Qdisplay, Qnil, limit)); 11849 (make_number (pos), Qdisplay, Qnil, limit));
@@ -11773,13 +11851,13 @@ set_cursor_from_row (w, row, matrix, delta, delta_bytes, dy, dvpos)
11773 break; 11851 break;
11774 /* Skip glyphs from the same string. */ 11852 /* Skip glyphs from the same string. */
11775 string = glyph->object; 11853 string = glyph->object;
11776 SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string)); 11854 SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
11777 /* Skip glyphs from an overlay. */ 11855 /* Skip glyphs from an overlay. */
11778 while (glyph < end 11856 while (glyph < stop
11779 && ! string_buffer_position (w, glyph->object, pos)) 11857 && ! string_buffer_position (w, glyph->object, pos))
11780 { 11858 {
11781 string = glyph->object; 11859 string = glyph->object;
11782 SKIP_GLYPHS (glyph, end, x, EQ (glyph->object, string)); 11860 SKIP_GLYPHS (glyph, stop, x, EQ (glyph->object, string));
11783 } 11861 }
11784 } 11862 }
11785 11863
diff --git a/src/xfns.c b/src/xfns.c
index 11552a5a9f7..e0cc89c6ebe 100644
--- a/src/xfns.c
+++ b/src/xfns.c
@@ -3207,8 +3207,7 @@ This function is an internal primitive--use `make-frame' instead. */)
3207 if (! STRINGP (font)) 3207 if (! STRINGP (font))
3208 font = build_string ("fixed"); 3208 font = build_string ("fixed");
3209 3209
3210 x_default_parameter (f, parms, Qfont, font, 3210 x_set_frame_parameters (f, Fcons (Fcons (Qfont, font), Qnil));
3211 "font", "Font", RES_TYPE_STRING);
3212 } 3211 }
3213 3212
3214#ifdef USE_LUCID 3213#ifdef USE_LUCID
diff --git a/src/xterm.c b/src/xterm.c
index 2bfb8a15bb8..975c9c68f39 100644
--- a/src/xterm.c
+++ b/src/xterm.c
@@ -359,7 +359,8 @@ static void x_scroll_bar_report_motion P_ ((struct frame **, Lisp_Object *,
359 Lisp_Object *, Lisp_Object *, 359 Lisp_Object *, Lisp_Object *,
360 unsigned long *)); 360 unsigned long *));
361static void x_check_fullscreen P_ ((struct frame *)); 361static void x_check_fullscreen P_ ((struct frame *));
362static void x_check_expected_move P_ ((struct frame *)); 362static void x_check_expected_move P_ ((struct frame *, int, int));
363static void x_sync_with_move P_ ((struct frame *, int, int, int));
363static int handle_one_xevent P_ ((struct x_display_info *, XEvent *, 364static int handle_one_xevent P_ ((struct x_display_info *, XEvent *,
364 int *, struct input_event *)); 365 int *, struct input_event *));
365static SIGTYPE x_connection_closed P_ ((Display *, char *)); 366static SIGTYPE x_connection_closed P_ ((Display *, char *));
@@ -6686,11 +6687,8 @@ handle_one_xevent (dpyinfo, eventp, finish, hold_quit)
6686 && GTK_WIDGET_MAPPED (FRAME_GTK_OUTER_WIDGET (f))) 6687 && GTK_WIDGET_MAPPED (FRAME_GTK_OUTER_WIDGET (f)))
6687#endif 6688#endif
6688 { 6689 {
6689 /* What we have now is the position of Emacs's own window.
6690 Convert that to the position of the window manager window. */
6691 x_real_positions (f, &f->left_pos, &f->top_pos); 6690 x_real_positions (f, &f->left_pos, &f->top_pos);
6692 6691
6693 x_check_expected_move (f);
6694 if (f->want_fullscreen & FULLSCREEN_WAIT) 6692 if (f->want_fullscreen & FULLSCREEN_WAIT)
6695 f->want_fullscreen &= ~(FULLSCREEN_WAIT|FULLSCREEN_BOTH); 6693 f->want_fullscreen &= ~(FULLSCREEN_WAIT|FULLSCREEN_BOTH);
6696 } 6694 }
@@ -8260,8 +8258,11 @@ x_set_offset (f, xoff, yoff, change_gravity)
8260{ 8258{
8261 int modified_top, modified_left; 8259 int modified_top, modified_left;
8262 8260
8263 if (change_gravity > 0) 8261 if (change_gravity != 0)
8264 { 8262 {
8263 FRAME_X_OUTPUT (f)->left_before_move = f->left_pos;
8264 FRAME_X_OUTPUT (f)->top_before_move = f->top_pos;
8265
8265 f->top_pos = yoff; 8266 f->top_pos = yoff;
8266 f->left_pos = xoff; 8267 f->left_pos = xoff;
8267 f->size_hint_flags &= ~ (XNegative | YNegative); 8268 f->size_hint_flags &= ~ (XNegative | YNegative);
@@ -8279,7 +8280,7 @@ x_set_offset (f, xoff, yoff, change_gravity)
8279 modified_left = f->left_pos; 8280 modified_left = f->left_pos;
8280 modified_top = f->top_pos; 8281 modified_top = f->top_pos;
8281 8282
8282 if (FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_A) 8283 if (change_gravity != 0 && FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_A)
8283 { 8284 {
8284 /* Some WMs (twm, wmaker at least) has an offset that is smaller 8285 /* Some WMs (twm, wmaker at least) has an offset that is smaller
8285 than the WM decorations. So we use the calculated offset instead 8286 than the WM decorations. So we use the calculated offset instead
@@ -8291,13 +8292,26 @@ x_set_offset (f, xoff, yoff, change_gravity)
8291 XMoveWindow (FRAME_X_DISPLAY (f), FRAME_OUTER_WINDOW (f), 8292 XMoveWindow (FRAME_X_DISPLAY (f), FRAME_OUTER_WINDOW (f),
8292 modified_left, modified_top); 8293 modified_left, modified_top);
8293 8294
8294 if (FRAME_VISIBLE_P (f) 8295 x_sync_with_move (f, f->left_pos, f->top_pos,
8295 && FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_UNKNOWN) 8296 FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_UNKNOWN
8296 { 8297 ? 1 : 0);
8297 FRAME_X_OUTPUT (f)->check_expected_move = 1; 8298
8298 FRAME_X_OUTPUT (f)->expected_top = f->top_pos; 8299 /* change_gravity is non-zero when this function is called from Lisp to
8299 FRAME_X_OUTPUT (f)->expected_left = f->left_pos; 8300 programmatically move a frame. In that case, we call
8300 } 8301 x_check_expected_move to discover if we have a "Type A" or "Type B"
8302 window manager, and, for a "Type A" window manager, adjust the position
8303 of the frame.
8304
8305 We call x_check_expected_move if a programmatic move occurred, and
8306 either the window manager type (A/B) is unknown or it is Type A but we
8307 need to compute the top/left offset adjustment for this frame. */
8308
8309 if (change_gravity != 0 &&
8310 (FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_UNKNOWN
8311 || (FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_A
8312 && (FRAME_X_OUTPUT (f)->move_offset_left == 0
8313 && FRAME_X_OUTPUT (f)->move_offset_top == 0))))
8314 x_check_expected_move (f, modified_left, modified_top);
8301 8315
8302 UNBLOCK_INPUT; 8316 UNBLOCK_INPUT;
8303} 8317}
@@ -8332,37 +8346,96 @@ x_check_fullscreen (f)
8332 } 8346 }
8333} 8347}
8334 8348
8335/* If frame parameters are set after the frame is mapped, we need to move 8349/* This function is called by x_set_offset to determine whether the window
8336 the window. 8350 manager interfered with the positioning of the frame. Type A window
8337 Some window managers moves the window to the right position, some 8351 managers position the surrounding window manager decorations a small
8338 moves the outer window manager window to the specified position. 8352 amount above and left of the user-supplied position. Type B window
8339 Here we check that we are in the right spot. If not, make a second 8353 managers position the surrounding window manager decorations at the
8340 move, assuming we are dealing with the second kind of window manager. */ 8354 user-specified position. If we detect a Type A window manager, we
8355 compensate by moving the window right and down by the proper amount. */
8356
8341static void 8357static void
8342x_check_expected_move (f) 8358x_check_expected_move (f, expected_left, expected_top)
8343 struct frame *f; 8359 struct frame *f;
8360 int expected_left;
8361 int expected_top;
8344{ 8362{
8345 if (FRAME_X_OUTPUT (f)->check_expected_move) 8363 int count = 0, current_left = 0, current_top = 0;
8346 { 8364
8347 int expect_top = FRAME_X_OUTPUT (f)->expected_top; 8365 /* x_real_positions returns the left and top offsets of the outermost
8348 int expect_left = FRAME_X_OUTPUT (f)->expected_left; 8366 window manager window around the frame. */
8349 8367
8350 if (expect_top != f->top_pos || expect_left != f->left_pos) 8368 x_real_positions (f, &current_left, &current_top);
8369
8370 if (current_left != expected_left || current_top != expected_top)
8351 { 8371 {
8372 /* It's a "Type A" window manager. */
8373
8374 int adjusted_left;
8375 int adjusted_top;
8376
8352 FRAME_X_DISPLAY_INFO (f)->wm_type = X_WMTYPE_A; 8377 FRAME_X_DISPLAY_INFO (f)->wm_type = X_WMTYPE_A;
8353 FRAME_X_OUTPUT (f)->move_offset_left = expect_left - f->left_pos; 8378 FRAME_X_OUTPUT (f)->move_offset_left = expected_left - current_left;
8354 FRAME_X_OUTPUT (f)->move_offset_top = expect_top - f->top_pos; 8379 FRAME_X_OUTPUT (f)->move_offset_top = expected_top - current_top;
8380
8381 /* Now fix the mispositioned frame's location. */
8355 8382
8356 f->left_pos = expect_left; 8383 adjusted_left = expected_left + FRAME_X_OUTPUT (f)->move_offset_left;
8357 f->top_pos = expect_top; 8384 adjusted_top = expected_top + FRAME_X_OUTPUT (f)->move_offset_top;
8358 x_set_offset (f, expect_left, expect_top, 0); 8385
8386 XMoveWindow (FRAME_X_DISPLAY (f), FRAME_OUTER_WINDOW (f),
8387 adjusted_left, adjusted_top);
8388
8389 x_sync_with_move (f, expected_left, expected_top, 0);
8359 } 8390 }
8360 else if (FRAME_X_DISPLAY_INFO (f)->wm_type == X_WMTYPE_UNKNOWN) 8391 else
8392 /* It's a "Type B" window manager. We don't have to adjust the
8393 frame's position. */
8394
8361 FRAME_X_DISPLAY_INFO (f)->wm_type = X_WMTYPE_B; 8395 FRAME_X_DISPLAY_INFO (f)->wm_type = X_WMTYPE_B;
8396}
8397
8398
8399/* Wait for XGetGeometry to return up-to-date position information for a
8400 recently-moved frame. Call this immediately after calling XMoveWindow.
8401 If FUZZY is non-zero, then LEFT and TOP are just estimates of where the
8402 frame has been moved to, so we use a fuzzy position comparison instead
8403 of an exact comparison. */
8404
8405static void
8406x_sync_with_move (f, left, top, fuzzy)
8407 struct frame *f;
8408 int left, top, fuzzy;
8409{
8410 int count = 0;
8411
8412 while (count++ < 50)
8413 {
8414 int current_left = 0, current_top = 0;
8415
8416 /* In theory, this call to XSync only needs to happen once, but in
8417 practice, it doesn't seem to work, hence the need for the surrounding
8418 loop. */
8419
8420 XSync (FRAME_X_DISPLAY (f), False);
8421 x_real_positions (f, &current_left, &current_top);
8422
8423 if (fuzzy)
8424 {
8425 /* The left fuzz-factor is 10 pixels. The top fuzz-factor is 40
8426 pixels. */
8362 8427
8363 /* Just do this once */ 8428 if (abs (current_left - left) <= 10 && abs (current_top - top) <= 40)
8364 FRAME_X_OUTPUT (f)->check_expected_move = 0; 8429 return;
8365 } 8430 }
8431 else if (current_left == left && current_top == top)
8432 return;
8433 }
8434
8435 /* As a last resort, just wait 0.5 seconds and hope that XGetGeometry
8436 will then return up-to-date position info. */
8437
8438 wait_reading_process_output (0, 500000, 0, 0, Qnil, NULL, 0);
8366} 8439}
8367 8440
8368 8441
diff --git a/src/xterm.h b/src/xterm.h
index 03d7b630d65..4580f3c0744 100644
--- a/src/xterm.h
+++ b/src/xterm.h
@@ -639,18 +639,14 @@ struct x_output
639 FocusOut and LeaveNotify clears EXPLICIT/IMPLICIT. */ 639 FocusOut and LeaveNotify clears EXPLICIT/IMPLICIT. */
640 int focus_state; 640 int focus_state;
641 641
642 /* The latest move we made to FRAME_OUTER_WINDOW. Saved so we can
643 compensate for type A WMs (see wm_type in dpyinfo above). */
644 int expected_top;
645 int expected_left;
646
647 /* The offset we need to add to compensate for type A WMs. */ 642 /* The offset we need to add to compensate for type A WMs. */
648 int move_offset_top; 643 int move_offset_top;
649 int move_offset_left; 644 int move_offset_left;
650 645
651 /* Nonzero if we have made a move and needs to check if the WM placed us 646 /* The frame's left/top offsets before we call XMoveWindow. See
652 at the right position. */ 647 x_check_expected_move. */
653 int check_expected_move; 648 int left_before_move;
649 int top_before_move;
654}; 650};
655 651
656#define No_Cursor (None) 652#define No_Cursor (None)