+1998-09-29 SL Baur <steve@altair.xemacs.org>
+
+ * XEmacs 21.2-beta2 is released.
+
+1998-09-27 P. E. Jareth Hein <jareth@camelot.co.jp>
+
+ * regex.c (re_match_2_internal): Add in code to reset lowest_active_reg
+ to prevent memory corruption in the case of jumping out of a series of
+ nested match patterns. This is a rather brute force approach, though.
+
+1998-09-02 Andy Piper <andyp@parallax.co.uk>
+
+ * config.h.in: ditto.
+
+ * s/cygwin32.h: rearrange declarations to cope with cygwin
+ b20. Include cygwin32/version.h if it exists.
+
+1998-09-20 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * device-msw.c (mswindows_init_device): Call new
+ mswindows_enumerate_fonts() function in objects-msw.c instead
+ of font_enum_callback_1() to enumerate fonts.
+
+ font_enum_callback_1() and _2() moved to objects-msw.c.
+
+ * faces.c (complex_vars_of_faces): Make the mswindows default
+ face font fully specified and provide some fallbacks.
+
+ * objects-msw.c: font_enum_callback_1() and _2() moved here
+ from objects-msw.c. Obtain the enumerated font's character
+ sets by table lookup instead of using the locale-specific
+ string provided by Windows.
+
+ New public non-method mswindows_enumerate_fonts() that fills
+ in the supplied mswindows device's font list.
+
+ mswindows_initialize_font_instance: Use the supplied name
+ variable instead of f->name when signalling errors. Match font
+ weights and character sets using lookup tables which handle
+ spaces instead of by frobbing.
+
+1998-09-20 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * process-nt.c: Define an arbitrary limit, FRAGMENT_CODE_SIZE,
+ on the size of code fragments passed to run_in_other_process.
+
+ run_in_other_process(): Use FRAGMENT_CODE_SIZE to determine
+ the amount of memory to allocate in the other process.
+
+ Removed sigkill_code_end(), sigint_code_end() and
+ sig_enable_code_end() since they are now redundant.
+
+ send_signal() and enable_child_signals(): Don't try to work
+ out the end of the code fragments passed to
+ run_in_other_process()
+
+1998-09-10 Kazuyuki IENAGA <ienaga@jsys.co.jp>
+
+ * src/s/freebsd.h: Added __ELF__ and compiler/liker flags for
+ FreeBSD-current.
+
+ * src/unexelf.c: Partially synched with FSF's 20.3.
+
+1998-09-10 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (signal_after_change): Map across indirect buffers
+ here, and not in the upper-level functions.
+ (signal_first_change): Don't check for Armageddon.
+ (signal_before_change): Map across indirect buffers here.
+ (prepare_to_modify_buffer): ...and here.
+
+1998-09-09 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (signal_after_change): Add return value.
+ (buffer_insert_string_1): Use it.
+ (buffer_delete_range): Ditto.
+ (buffer_replace_char): Ditto.
+ (cancel_multiple_change): Map the indirect buffers.
+
+1998-09-06 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (init_buffer_text): Remove INDIRECT_P parameter.
+ (uninit_buffer_text): Ditto.
+
+ * buffer.c (Fmake_indirect_buffer): Implement stricter
+ error-checking.
+
+1998-09-04 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (change_function_restore): Reverse order of
+ function-call and assignment.
+ (first_change_hook_restore): Ditto.
+
+ * extents.c (mark_extent_auxiliary): Mark them.
+ (Fset_extent_property): Set them.
+ (Fextent_property): Get them.
+ (Fextent_properties): Ditto.
+ (vars_of_extents): Set their default.
+
+ * extents.h (struct extent_auxiliary): Add before_change_functions
+ and after_change_functions.
+
+ * insdel.c (signal_before_change): Use it.
+ (signal_after_change): Ditto.
+
+ * extents.c (report_extent_modification): New function.
+
+ * insdel.c (signal_before_change): Don't check for Armageddon.
+ (signal_after_change): Ditto.
+
+1998-09-11 Gunnar Evermann <Gunnar.Evermann@nats.informatik.uni-hamburg.de>
+
+ * redisplay.c (redisplay_window): make sure a new starting point
+ is chosen if it somehow got moved from the beginning of the line
+ -- this can happen because Fwiden was called recently.
+
+ * window.c (Fset_window_start): set start_at_line_beg correctly
+ (Fset_window_buffer): Ditto
+
+1998-09-06 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (init_buffer_text): Remove INDIRECT_P parameter.
+ (uninit_buffer_text): Ditto.
+
+ * buffer.c (Fmake_indirect_buffer): Implement stricter
+ error-checking.
+
+1998-05-14 Jan Vroonhof <vroonhof@math.ethz.ch>
+
+ * emacs.c (main_1): Removed references to *vars_of_filelock.
+
+ * lisp.h: Added Fsystem_name.
+
+ * filelock.c: Replaced by version from FSF 20.2. Now implements
+ locking by using symlinks which is NFS safe. However keep the
+ GCPRO's in lock_file and the calls to callx_in_buffer like our old
+ version (and of course use ansi C, acessor macros, etc).
+
+1998-09-06 Jan Vroonhof <vroonhof@math.ethz.ch>
+
+ * process-unix.c (unix_create_process): Reset SIGHUP handler to
+ SIG_DFL. We now try to conserve any inherted SIG_IGN settings
+ in init_signals_very_early. However these should not be passed
+ on to children attached to the new pty.
+
+1998-08-28 Andy Piper <andyp@parallax.co.uk>
+
+ * glyphs-eimage.c (png_instantiate_unwind): clean up eimage after use.
+
+1998-09-07 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * fileio.c (file-name-directory, file_name_as_directory):
+ Don't call CORRECT_DIR_SEPS, even when #defined WINDOWSNT.
+
+1998-09-02 Andy Piper <andyp@parallax.co.uk>
+
+ * emacs.c (main_1): init_ralloc() if initialised and we have REL_ALLOC
+
+ * ralloc.c: uncomment __morecore.
+
+1998-09-92 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * event-msw.c(winsock_writer): Supply a dummy 4th argument to
+ WriteFile() to fix a winsock 1.x bug on Win95.
+
+1998-08-28 Hrvoje Niksic <hniksic@srce.hr>
+
+ * event-Xt.c (emacs_Xt_mapping_action): Check for device being
+ deleted.
+ (x_event_to_emacs_event): Ditto.
+ (emacs_Xt_handle_focus_event): Ditto.
+ (emacs_Xt_handle_magic_event): Ditto.
+
+ * console-x.h (struct x_device): New flag being_deleted.
+ (DEVICE_X_BEING_DELETED): New macro.
+
+ * device-x.c (x_IO_error_handler): Throw to top-level instead of
+ returning. Before doing that, set the being_deleted flag on the
+ device.
+
+1998-08-27 Hrvoje Niksic <hniksic@srce.hr>
+
+ * device-x.c (x-seppuku-on-epipe): Removed.
+
+1998-08-26 Gunnar Evermann <Gunnar.Evermann@nats.informatik.uni-hamburg.de>
+
+ * frame-x.c (x_delete_frame): Flush the X output buffer after
+ calling XtDestroyWidget to ensure that the windows are really
+ killed right now.
+
+1998-08-26 Hrvoje Niksic <hniksic@srce.hr>
+
+ * menubar-x.c (my_run_hook): New unused function.
+ (pre_activate_callback): Use run_hook for Qactivate_menubar_hook,
+ since we ignore the results of the contained functions anyway.
+
+1998-08-26 P. E. Jareth Hein <jareth@camelot.co.jp>
+
+ * glyphs-eimage.c (gif_instantiate): Fix a crash in handling
+ interlaced GIF files that are smaller than 4 lines high...
+
+1998-08-31 Hrvoje Niksic <hniksic@srce.hr>
+
+ * buffer.c (map_over_sharing_buffers): Deleted.
+
+ * insdel.c (MAP_INDIRECT_BUFFERS): Move to buffer.h.
+
+ * buffer.c (Fkill_buffer): Keep indirect_children updated while
+ killing them.
+
+1998-08-31 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (buffer_insert_string_1): Advance the point bytind in
+ all the buffers.
+ (buffer_delete_range): Ditto.
+
+ * marker.c (init_buffer_markers): Set point-marker to the value of
+ point in an indirect buffer.
+
+1998-08-30 Hrvoje Niksic <hniksic@srce.hr>
+
+ * undo.c (undo_prelude): Test last-undo-buffer against base
+ buffer.
+
+ * insdel.c (MAP_INDIRECT_BUFFERS): Use it.
+
+ * buffer.h (BUFFER_BASE_BUFFER): New macro.
+
+1998-08-30 Hrvoje Niksic <hniksic@srce.hr>
+
+ * insdel.c (init_buffer_text): Initialize it here.
+
+ * line-number.c: Address line_number_cache through buffer->text.
+
+ * buffer.c (mark_buffer): Mark line number cache.
+
+ * bufslots.h (line_number_cache): Move to struct buffer_text.
+
+ * insdel.c (buffer_insert_string_1): Propagate signals and changes
+ across the children buffers.
+ (buffer_delete_range): Ditto.
+ (buffer_replace_char): Ditto.
+ (gap_left): Ditto.
+ (gap_right): Ditto.
+
+ * insdel.c (MAP_INDIRECT_BUFFERS): New macro.
+
+ * buffer.c (Fmake_indirect_buffer): Uncomment.
+
+1998-08-31 Hrvoje Niksic <hniksic@srce.hr>
+
+ * macros.c (Fend_kbd_macro): Remove trailing period from error
+ message.
+ (Fexecute_kbd_macro): Ditto.
+
+1998-08-21 Greg Klanderman <greg@alphatech.com>
+
+ * dired.c (Fuser_name_completion): remove optional 2nd argument.
+ (Fuser_name_completion_1): new function to return uniqueness
+ indication in addition to the user name completion.
+ (user_name_completion): change type of `uniq' argument.
+
+1998-08-19 Michael Sperber [Mr. Preprocessor] <sperber@informatik.uni-tuebingen.de>
+
+ * lread.c (vars_of_lread): Removed `source-directory' variable.
+
+1998-08-22 Hrvoje Niksic <hniksic@srce.hr>
+
+ * fileio.c (Ffile_readable_p): Apply the DOS/Windows logic to
+ Cygwin.
+
+1998-08-19 SL Baur <steve@altair.xemacs.org>
+
+ * dired.c (vars_of_dired): Fix misapplied patch.
+
+1998-08-16 Martin Buchholz <martin@xemacs.org>
+
+ * fns.c (Fremrassq, remrassq_no_quit):
+ A XCAR that should have been an XCDR turned Fremrassq into Fremassq
+
+1998-07-17 Didier Verna <verna@inf.enst.fr>
+
+ * redisplay-x.c (x_get_gc): returns a GC with a FillStipple fill
+ style as foreground GC for faces that have the `dim' property.
+ (x_output_string): when the `dim' face property is set,
+ ensure the gray pixmap has been created, and get a proper
+ foreground GC to draw the text.
+
+1998-08-09 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * event-msw.c (mswindows_wnd_proc): Workaround for a Win95 bug:
+ Manually track the state of the left and right Ctrl and Alt
+ modifiers.
+
+1998-08-07 Matt Stupple <matts@tibco.com>
+
+ * ntproc.c: don't wait on char_consumed at thread entry.
+ Additionally, to get the 'process' marked as finished, ensure
+ that the CHILD_ACTIVE macro returns false, so before exiting
+ close char_avail and set it to NULL, and close other handles
+ to reduce handle leak problems.
+
+1998-08-09 Jonathan Harris <jhar@tardis.ed.ac.uk>
+
+ * menubar-msw.c (displayable_menu_item): take account of menu
+ depth when deciding whether to try to display accelerators.
+
+1998-08-04 Andy Piper <andyp@parallax.co.uk>
+
+ * event-msw.c: use MsgWaitForMultipleObjects if there are no
+ subprocesses.
+
+ * glyphs-msw.c: fix a couple of potential handle leaks.
+
+1998-08-04 P. E. Jareth Hein <jareth@camelot.co.jp>
+
+ * dgif_lib.c gif_io.c gifrlib.h: New files to put GIF
+ *decoding ONLY* back into the core.
+ * glyphs-eimage.c: Change referenced header file for GIF
+ reading to point to the incore version.
+
+1998-07-20 Martin Buchholz <martin@xemacs.org>
+
+ * casefiddle.c (casify_object):
+ Change algorithm from O(N**2) to O(N).
+ Code cleanup.
+ Doc string cleanup.
+
+1998-07-22 Greg Klanderman <greg@alphatech.com>
+
+ * dired.c (file_name_completion_unwind): don't leak the cons.
+
+1998-07-20 Greg Klanderman <greg@alphatech.com>
+
+ * dired.c (Fuser_name_completion): new function.
+ (Fuser_name_all_completions): new function.
+ (user_name_completion): new function.
+ (syms_of_dired): 2 new DEFSUBRs.
+ (vars_of_dired): initialize user name cache vars.
+
+1998-07-29 P. E. Jareth Hein <jareth@camelot.co.jp>
+
+ * glyphs-eimage.c (png_instantiate): Add proper handling for background
+ colors taken from the default face. Also correct a thinko in
+ transparency (not alpha) handling.
+
+1998-07-23 Martin Buchholz <martin@xemacs.org>
+
+ * s/decosf4-0.h: Use a perfectly ordinary link. Nuke BSD crap.
+ * unexalpha.c: ANSI C-ize. Clean compiler warnings.
+ * lread.c (Fload_internal): Be very careful with printfs of
+ size_t's
+ * gui-x.c (menu_name_to_accelerator): tolower wants an `int'
+ argument.
+
+1998-07-27 Gunnar Evermann <Gunnar.Evermann@nats.informatik.uni-hamburg.de>
+
+ * callint.c (Fcall_interactively): GCPRO prompt string before
+ passing it to Fread_key_sequence
+
+1998-07-27 SL Baur <steve@altair.xemacs.org>
+
+ * keymap.c (vars_of_keymap): Initialize Vkey_translation_map and
+ Vvertical_divider_map.
+
+ * mule-canna.c (vars_of_mule_canna): Initialize every symbol to
+ Qnil or 0, none were initialized prior to this change.
+
+ Rename misnamed `V' prefixed integer variables:
+ Vcanna_empty_info, Vcanna_through_info, Vcanna_underline,
+ Vcanna_inhibit_hankakukana, Vcanna_henkan_length, Vcanna_henkan_revPos,
+ Vcanna_henkan_revLen, Vcanna_ichiran_length, Vcanna_ichiran_revPos,
+ Vcanna_ichiran_revLen.
+
+ Rename misnamed `V' prefixed integer variables and initialize
+ properly in the vars_of routine.
+ Vcanna_mode_AlphaMode, Vcanna_mode_EmptyMode, Vcanna_mode_KigoMode,
+ Vcanna_mode_YomiMode, Vcanna_mode_JishuMode, Vcanna_mode_TankouhoMode,
+ Vcanna_mode_IchiranMode, Vcanna_mode_YesNoMode, Vcanna_mode_OnOffMode,
+ Vcanna_mode_AdjustBunsetsuMode, Vcanna_mode_ChikujiYomiMode,
+ Vcanna_mode_ChikujiTanMode, Vcanna_mode_HenkanMode,
+ Vcanna_mode_HenkanNyuryokuMode, Vcanna_mode_ZenHiraHenkanMode,
+ Vcanna_mode_HanHiraHenkanMode, Vcanna_mode_ZenKataHenkanMode,
+ Vcanna_mode_HanKataHenkanMode, Vcanna_mode_HanKataHenkanMode,
+ Vcanna_mode_ZenAlphaHenkanMode, Vcanna_mode_HanAlphaHenkanMode,
+ Vcanna_mode_ZenHiraKakuteiMode, Vcanna_mode_HanHiraKakuteiMode,
+ Vcanna_mode_ZenKataKakuteiMode, Vcanna_mode_HanKataKakuteiMode,
+ Vcanna_mode_ZenAlphaKakuteiMode, Vcanna_mode_HanAlphaKakuteiMode,
+ Vcanna_mode_HexMode, Vcanna_mode_BushuMode, Vcanna_mode_ExtendMode,
+ Vcanna_mode_RussianMode, Vcanna_mode_GreekMode, Vcanna_mode_LineMode,
+ Vcanna_mode_ChangingServerMode, Vcanna_mode_HenkanMethodMode,
+ Vcanna_mode_DeleteDicMode, Vcanna_mode_TourokuMode,
+ Vcanna_mode_TourokuEmptyMode, Vcanna_mode_TourokuHinshiMode,
+ Vcanna_mode_TourokuDicMode, Vcanna_mode_QuotedInsertMode,
+ Vcanna_mode_BubunMuhenkanMode, Vcanna_mode_MountDicMode,
+ Vcanna_fn_SelfInsert, Vcanna_fn_FunctionalInsert,
+ Vcanna_fn_QuotedInsert, Vcanna_fn_JapaneseMode, Vcanna_fn_AlphaMode,
+ Vcanna_fn_HenkanNyuryokuMode, Vcanna_fn_Forward, Vcanna_fn_Backward,
+ Vcanna_fn_Next, Vcanna_fn_Prev, Vcanna_fn_BeginningOfLine,
+ Vcanna_fn_EndOfLine, Vcanna_fn_DeleteNext, Vcanna_fn_DeletePrevious,
+ Vcanna_fn_KillToEndOfLine, Vcanna_fn_Henkan, Vcanna_fn_Kakutei,
+ Vcanna_fn_Extend, Vcanna_fn_Shrink, Vcanna_fn_AdjustBunsetsu,
+ Vcanna_fn_Quit, Vcanna_fn_ConvertAsHex, Vcanna_fn_ConvertAsBushu,
+ Vcanna_fn_KouhoIchiran, Vcanna_fn_BubunMuhenkan, Vcanna_fn_Zenkaku,
+ Vcanna_fn_Hankaku, Vcanna_fn_ExtendMode, Vcanna_fn_ToUpper,
+ Vcanna_fn_Capitalize, Vcanna_fn_ToLower, Vcanna_fn_Hiragana,
+ Vcanna_fn_Katakana, Vcanna_fn_Romaji, Vcanna_fn_BaseHiragana,
+ Vcanna_fn_BaseKatakana, Vcanna_fn_BaseEisu, Vcanna_fn_BaseZenkaku,
+ Vcanna_fn_BaseHankaku, Vcanna_fn_BaseKana, Vcanna_fn_BaseKakutei,
+ Vcanna_fn_BaseHenkan, Vcanna_fn_BaseHiraKataToggle,
+ Vcanna_fn_BaseZenHanToggle, Vcanna_fn_BaseKanaEisuToggle,
+ Vcanna_fn_BaseKakuteiHenkanToggle, Vcanna_fn_BaseRotateForward,
+ Vcanna_fn_BaseRotateBackward, Vcanna_fn_Touroku, Vcanna_fn_HexMode,
+ Vcanna_fn_BushuMode, Vcanna_fn_KigouMode, Vcanna_fn_Mark,
+ Vcanna_fn_TemporalMode, Vcanna_key_Nfer, Vcanna_key_Xfer,
+ Vcanna_key_Up, Vcanna_key_Left, Vcanna_key_Right, Vcanna_key_Down,
+ Vcanna_key_Insert, Vcanna_key_Rollup, Vcanna_key_Rolldown,
+ Vcanna_key_Home, Vcanna_key_Help, Vcanna_key_KP_Key,
+ Vcanna_key_Shift_Nfer, Vcanna_key_Shift_Xfer, Vcanna_key_Shift_Up,
+ Vcanna_key_Shift_Left, Vcanna_key_Shift_Right, Vcanna_key_Shift_Down,
+ Vcanna_key_Cntrl_Nfer, Vcanna_key_Cntrl_Xfer, Vcanna_key_Cntrl_Up,
+ Vcanna_key_Cntrl_Left, Vcanna_key_Cntrl_Right, Vcanna_key_Cntrl_Down
+
+1998-07-16 Jan Vroonhof <vroonhof@math.ethz.ch>
+
+ * event-Xt.c (x_to_emacs_keysym): Return nil for modifier keysyms.
+ (x_event_to_emacs_event): Let x_to_emacs_keysym check for modifier
+ keys thus no longer considering all keysyms on a key.
+
1998-07-19 SL Baur <steve@altair.xemacs.org>
* XEmacs 21.2-beta1 is released.
#undef MARKED_SLOT
((markobj) (buf->extent_info));
+ if (buf->text)
+ ((markobj) (buf->text->line_number_cache));
/* Don't mark normally through the children slot.
(Actually, in this case, it doesn't matter.) */
b->text = &b->own_text;
b->base_buffer = 0;
b->indirect_children = Qnil;
- init_buffer_text (b, 0);
+ init_buffer_text (b);
return finish_init_buffer (b, name);
}
-#if 0 /* #### implement this! Need various changes in insdel.c */
DEFUN ("make-indirect-buffer", Fmake_indirect_buffer, 2, 2,
"bMake indirect buffer (to buffer): \nBName of indirect buffer: ", /*
Create and return an indirect buffer for buffer BASE, named NAME.
*/
(base_buffer, name))
{
- Lisp_Object buf;
- REGISTER struct buffer *b;
+ /* This function can GC */
+
+ /* #### The above interactive specification is totally bogus,
+ because it offers an existing buffer as default answer to the
+ second question. However, the second argument may not BE an
+ existing buffer! */
+ struct buffer *b;
+
+ base_buffer = get_buffer (base_buffer, 1);
#ifdef I18N3
/* #### Doc string should indicate that the buffer name will get
translated. */
#endif
-
+ CHECK_STRING (name);
name = LISP_GETTEXT (name);
- buf = Fget_buffer (name);
- if (!NILP (buf))
- error ("Buffer name `%s' is in use", XSTRING_DATA (name));
-
- base_buffer = Fget_buffer (base_buffer);
- if (NILP (base_buffer))
- error ("No such buffer: `%s'", XSTRING_DATA (XBUFFER (base_buffer)->name));
-
+ if (!NILP (Fget_buffer (name)))
+ signal_simple_error ("Buffer name already in use", name);
if (XSTRING_LENGTH (name) == 0)
error ("Empty string for buffer name is not allowed");
b = allocate_buffer ();
- if (XBUFFER (base_buffer)->base_buffer)
- b->base_buffer = XBUFFER (base_buffer)->base_buffer;
- else
- b->base_buffer = XBUFFER (base_buffer);
+ b->base_buffer = BUFFER_BASE_BUFFER (XBUFFER (base_buffer));
/* Use the base buffer's text object. */
b->text = b->base_buffer->text;
b->indirect_children = Qnil;
- XSETBUFFER (buf, b);
b->base_buffer->indirect_children =
- Fcons (buf, b->base_buffer->indirect_children);
- init_buffer_text (b, 1);
+ Fcons (make_buffer (b), b->base_buffer->indirect_children);
+ init_buffer_text (b);
return finish_init_buffer (b, name);
}
-#endif /* 0 */
\f
return Fcopy_sequence (buf->indirect_children);
}
-/* Map MAPFUN over all buffers that share the same text as BUF
- (this includes BUF). Pass two arguments to MAPFUN: a buffer,
- and CLOSURE. If any invocation of MAPFUN returns non-zero,
- halt immediately and return that value. Otherwise, continue
- the mapping to the end and return 0. */
-
-int
-map_over_sharing_buffers (struct buffer *buf,
- int (*mapfun) (struct buffer *buf, void *closure),
- void *closure)
-{
- int result;
- Lisp_Object tail;
-
- if (buf->base_buffer)
- {
- buf = buf->base_buffer;
- assert (!buf->base_buffer);
- }
-
- result = (mapfun) (buf, closure);
- if (result)
- return result;
-
- LIST_LOOP (tail, buf->indirect_children)
- {
- Lisp_Object buffer = XCAR (tail);
- result = (mapfun) (XBUFFER (buffer), closure);
- if (result)
- return result;
- }
-
- return 0;
-}
-
DEFUN ("buffer-local-variables", Fbuffer_local_variables, 0, 1, 0, /*
Return an alist of variables that are buffer-local in BUFFER.
Most elements look like (SYMBOL . VALUE), describing one variable.
GCPRO1 (buf);
LIST_LOOP (rest, b->indirect_children)
- Fkill_buffer (XCAR (rest));
+ {
+ Fkill_buffer (XCAR (rest));
+ /* Keep indirect_children updated in case a
+ query-function/hook throws. */
+ b->indirect_children = XCDR (rest);
+ }
UNGCPRO;
}
kill_buffer_local_variables (b);
b->name = Qnil;
- uninit_buffer_text (b, !!b->base_buffer);
+ uninit_buffer_text (b);
b->undo_list = Qnil;
uninit_buffer_extents (b);
if (b->base_buffer)
DEFSUBR (Fget_buffer);
DEFSUBR (Fget_file_buffer);
DEFSUBR (Fget_buffer_create);
-#if 0
DEFSUBR (Fmake_indirect_buffer);
-#endif
DEFSUBR (Fgenerate_new_buffer_name);
DEFSUBR (Fbuffer_name);
Bytind mule_bytind_cache[16];
#endif
+ /* Similar to the above, we keep track of positions for which line
+ number has last been calculated. See line-number.c. */
+ Lisp_Object line_number_cache;
+
/* Change data that goes with the text. */
struct buffer_text_change_data *changes;
x = wrong_type_argument (Qbuffer_live_p, (x)); \
} while (0)
+#define BUFFER_BASE_BUFFER(b) ((b)->base_buffer ? (b)->base_buffer : (b))
+
+/* Map over buffers sharing the same text as MPS_BUF. MPS_BUFVAR is a
+ variable that gets the buffer values (beginning with the base
+ buffer, then the children), and MPS_BUFCONS should be a temporary
+ Lisp_Object variable. */
+#define MAP_INDIRECT_BUFFERS(mps_buf, mps_bufvar, mps_bufcons) \
+for (mps_bufcons = Qunbound, \
+ mps_bufvar = BUFFER_BASE_BUFFER (mps_buf); \
+ UNBOUNDP (mps_bufcons) ? \
+ (mps_bufcons = mps_bufvar->indirect_children, \
+ 1) \
+ : (!NILP (mps_bufcons) \
+ && (mps_bufvar = XBUFFER (XCAR (mps_bufcons)), 1) \
+ && (mps_bufcons = XCDR (mps_bufcons), 1)); \
+ )
+
\f
/* NOTE: In all the following macros, we follow these rules concerning
multiple evaluation of the arguments:
the next few times we add a new slot. */
MARKED_SLOT (extra1, extra2, extra3);
#endif
- /* The cache of positions for whilch line number has last been
- calculated. See line-number.c. */
- MARKED_SLOT (line_number_cache);
-
}
case 'k': /* Key sequence (vector of events) */
{
- Lisp_Object tem = Fread_key_sequence (PROMPT (), Qnil, Qnil);
+ struct gcpro ngcpro1;
+ Lisp_Object tem;
+ Lisp_Object key_prompt = PROMPT ();
+
+ NGCPRO1(key_prompt);
+ tem = Fread_key_sequence (key_prompt, Qnil, Qnil);
+ NUNGCPRO;
+
visargs[argnum] = Fkey_description (tem);
/* The following makes `describe-key' not work with
extent-local keymaps and such; and anyway, it's
case 'K': /* Key sequence (vector of events),
no automatic downcasing */
{
- Lisp_Object tem = Fread_key_sequence (PROMPT (), Qnil, Qt);
+ struct gcpro ngcpro1;
+ Lisp_Object tem;
+ Lisp_Object key_prompt = PROMPT ();
+
+ NGCPRO1(key_prompt);
+ tem = Fread_key_sequence (key_prompt, Qnil, Qt);
+ NUNGCPRO;
+
visargs[argnum] = Fkey_description (tem);
/* The following makes `describe-key' not work with
extent-local keymaps and such; and anyway, it's
/* XEmacs case conversion functions.
- Copyright (C) 1985, 1992, 1993, 1994 Free Software Foundation, Inc.
+ Copyright (C) 1985, 1992, 1993, 1994, 1997, 1998 Free Software Foundation, Inc.
This file is part of XEmacs.
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
-/* Synched up with: FSF 19.34. */
+/* Synched up with: FSF 19.34, but substantially rewritten by Martin. */
#include <config.h>
#include "lisp.h"
#include "buffer.h"
-#include "commands.h"
#include "insdel.h"
#include "syntax.h"
casify_object (enum case_action flag, Lisp_Object obj, Lisp_Object buffer)
{
struct buffer *buf = decode_buffer (buffer, 0);
- REGISTER int inword = (flag == CASE_DOWN);
- struct Lisp_Char_Table *syntax_table = XCHAR_TABLE (buf->mirror_syntax_table);
- while (1)
+ retry:
+
+ if (CHAR_OR_CHAR_INTP (obj))
{
- if (CHAR_OR_CHAR_INTP (obj))
- {
- Emchar c;
- CHECK_CHAR_COERCE_INT (obj);
- c = XCHAR (obj);
- if (IN_TRT_TABLE_DOMAIN (c))
- {
- if (inword)
- obj = make_char (DOWNCASE (buf, c));
- else if (!UPPERCASEP (buf, c))
- obj = make_char (UPCASE1 (buf, c));
- }
- return obj;
- }
- if (STRINGP (obj))
+ Emchar c;
+ CHECK_CHAR_COERCE_INT (obj);
+ c = XCHAR (obj);
+ c = (flag == CASE_DOWN) ? DOWNCASE (buf, c) : UPCASE (buf, c);
+ return make_char (c);
+ }
+
+ if (STRINGP (obj))
+ {
+ struct Lisp_Char_Table *syntax_table =
+ XCHAR_TABLE (buf->mirror_syntax_table);
+ Bufbyte *storage =
+ alloca_array (Bufbyte, XSTRING_LENGTH (obj) * MAX_EMCHAR_LEN);
+ Bufbyte *newp = storage;
+ Bufbyte *oldp = XSTRING_DATA (obj);
+ int wordp = 0, wordp_prev;
+
+ while (*oldp)
{
- Charcount i;
- Charcount len = XSTRING_CHAR_LENGTH (obj);
- obj = Fcopy_sequence (obj);
- for (i = 0; i < len; i++)
+ Emchar c = charptr_emchar (oldp);
+ switch (flag)
{
- Emchar c = string_char (XSTRING (obj), i);
- if (inword && flag != CASE_CAPITALIZE_UP)
- c = DOWNCASE (buf, c);
- else if (!UPPERCASEP (buf, c)
- && (!inword || flag != CASE_CAPITALIZE_UP))
- c = UPCASE1 (buf, c);
- set_string_char (XSTRING (obj), i, c);
- if ((int) flag >= (int) CASE_CAPITALIZE)
- inword = WORD_SYNTAX_P (syntax_table, c);
+ case CASE_UP:
+ c = UPCASE (buf, c);
+ break;
+ case CASE_DOWN:
+ c = DOWNCASE (buf, c);
+ break;
+ case CASE_CAPITALIZE:
+ case CASE_CAPITALIZE_UP:
+ wordp_prev = wordp;
+ wordp = WORD_SYNTAX_P (syntax_table, c);
+ if (!wordp) break;
+ if (wordp_prev)
+ {
+ if (flag == CASE_CAPITALIZE)
+ c = DOWNCASE (buf, c);
+ }
+ else
+ c = UPCASE (buf, c);
+ break;
}
- return obj;
+
+ newp += set_charptr_emchar (newp, c);
+ INC_CHARPTR (oldp);
}
- obj = wrong_type_argument (Qchar_or_string_p, obj);
+
+ return make_string (storage, newp - storage);
}
+
+ obj = wrong_type_argument (Qchar_or_string_p, obj);
+ goto retry;
}
DEFUN ("upcase", Fupcase, 1, 2, 0, /*
-Convert argument to upper case and return that.
-The argument may be a character or string. The result has the same type.
-The argument object is not altered--the value is a copy.
+Convert OBJECT to upper case and return that.
+OBJECT may be a character or string. The result has the same type.
+OBJECT is not altered--the value is a copy.
See also `capitalize', `downcase' and `upcase-initials'.
Optional second arg BUFFER specifies which buffer's case tables to use,
and defaults to the current buffer.
*/
- (obj, buffer))
+ (object, buffer))
{
- return casify_object (CASE_UP, obj, buffer);
+ return casify_object (CASE_UP, object, buffer);
}
DEFUN ("downcase", Fdowncase, 1, 2, 0, /*
-Convert argument to lower case and return that.
-The argument may be a character or string. The result has the same type.
-The argument object is not altered--the value is a copy.
+Convert OBJECT to lower case and return that.
+OBJECT may be a character or string. The result has the same type.
+OBJECT is not altered--the value is a copy.
Optional second arg BUFFER specifies which buffer's case tables to use,
and defaults to the current buffer.
*/
- (obj, buffer))
+ (object, buffer))
{
- return casify_object (CASE_DOWN, obj, buffer);
+ return casify_object (CASE_DOWN, object, buffer);
}
DEFUN ("capitalize", Fcapitalize, 1, 2, 0, /*
-Convert argument to capitalized form and return that.
+Convert OBJECT to capitalized form and return that.
This means that each word's first character is upper case
and the rest is lower case.
-The argument may be a character or string. The result has the same type.
-The argument object is not altered--the value is a copy.
+OBJECT may be a character or string. The result has the same type.
+OBJECT is not altered--the value is a copy.
Optional second arg BUFFER specifies which buffer's case tables to use,
and defaults to the current buffer.
*/
- (obj, buffer))
+ (object, buffer))
{
- return casify_object (CASE_CAPITALIZE, obj, buffer);
+ return casify_object (CASE_CAPITALIZE, object, buffer);
}
-/* Like Fcapitalize but change only the initials. */
+/* Like Fcapitalize but change only the initial characters. */
DEFUN ("upcase-initials", Fupcase_initials, 1, 2, 0, /*
-Convert the initial of each word in the argument to upper case.
+Convert the initial of each word in OBJECT to upper case.
Do not change the other letters of each word.
-The argument may be a character or string. The result has the same type.
-The argument object is not altered--the value is a copy.
+OBJECT may be a character or string. The result has the same type.
+OBJECT is not altered--the value is a copy.
Optional second arg BUFFER specifies which buffer's case tables to use,
and defaults to the current buffer.
*/
- (obj, buffer))
+ (object, buffer))
{
- return casify_object (CASE_CAPITALIZE_UP, obj, buffer);
+ return casify_object (CASE_CAPITALIZE_UP, object, buffer);
}
\f
/* flag is CASE_UP, CASE_DOWN or CASE_CAPITALIZE or CASE_CAPITALIZE_UP.
/* This function can GC */
REGISTER Bufpos i;
Bufpos start, end;
- REGISTER int inword = (flag == CASE_DOWN);
struct Lisp_Char_Table *syntax_table = XCHAR_TABLE (buf->mirror_syntax_table);
int mccount;
+ Emchar oldc, c;
+ int wordp = 0, wordp_prev;
if (EQ (b, e))
/* Not modifying because nothing marked */
for (i = start; i < end; i++)
{
- Emchar c = BUF_FETCH_CHAR (buf, i);
- Emchar oldc = c;
+ c = oldc = BUF_FETCH_CHAR (buf, i);
- if (inword && flag != CASE_CAPITALIZE_UP)
- c = DOWNCASE (buf, c);
- else if (!UPPERCASEP (buf, c)
- && (!inword || flag != CASE_CAPITALIZE_UP))
- c = UPCASE1 (buf, c);
-
- if (oldc != c)
+ switch (flag)
{
- buffer_replace_char (buf, i, c, 1, (i == start));
- BUF_MODIFF (buf)++;
+ case CASE_UP:
+ c = UPCASE (buf, oldc);
+ break;
+ case CASE_DOWN:
+ c = DOWNCASE (buf, oldc);
+ break;
+ case CASE_CAPITALIZE:
+ case CASE_CAPITALIZE_UP:
+ /* !!#### need to revalidate the start and end pointers in case
+ the buffer was changed */
+ wordp_prev = wordp;
+ wordp = WORD_SYNTAX_P (syntax_table, c);
+ if (!wordp) continue;
+ if (wordp_prev)
+ {
+ if (flag == CASE_CAPITALIZE)
+ c = DOWNCASE (buf, c);
+ }
+ else
+ c = UPCASE (buf, c);
+ break;
}
- /* !!#### need to revalidate the start and end pointers in case
- the buffer was changed */
- if ((int) flag >= (int) CASE_CAPITALIZE)
- inword = WORD_SYNTAX_P (syntax_table, c);
+
+ if (oldc == c) continue;
+ buffer_replace_char (buf, i, c, 1, (i == start));
+ BUF_MODIFF (buf)++;
}
+
end_multiple_change (buf, mccount);
}
#undef HAVE_ULIMIT_H
#undef HAVE_X11_XLOCALE_H
#undef HAVE_LINUX_VERSION_H
+#undef HAVE_CYGWIN32_VERSION_H
#undef HAVE_INTTYPES_H
#undef HAVE_SYS_UN_H
#undef HAVE_A_OUT_H
extern Lisp_Object Vmswindows_frame_being_created;
extern Lisp_Object mswindows_frame_being_created;
+void mswindows_enumerate_fonts (struct device *d);
+
#endif /* _XEMACS_CONSOLE_MSW_H_ */
/* The X connection of this device. */
Display *display;
+ /* Set by x_IO_error_handler(). */
+ int being_deleted;
+
/* Xt application info. */
Widget Xt_app_shell;
#define FRAME_X_DISPLAY(f) (DEVICE_X_DISPLAY (XDEVICE (f->device)))
#define DEVICE_X_DISPLAY(d) (DEVICE_X_DATA (d)->display)
+#define DEVICE_X_BEING_DELETED(d) (DEVICE_X_DATA (d)->being_deleted)
#define DEVICE_X_VISUAL(d) (DEVICE_X_DATA (d)->visual)
#define DEVICE_X_DEPTH(d) (DEVICE_X_DATA (d)->depth)
#define DEVICE_X_COLORMAP(d) (DEVICE_X_DATA (d)->device_cmap)
#include "frame.h"
#include "sysdep.h"
-#ifndef __CYGWIN32__
-#include <commctrl.h>
-#else
-#define FONTENUMPROC FONTENUMEXPROC
-#define ntmTm ntmentm
-#endif
-
/* win32 DDE management library globals */
#ifdef HAVE_DRAGNDROP
DWORD mswindows_dde_mlid;
Lisp_Object Qinit_pre_mswindows_win, Qinit_post_mswindows_win;
-struct font_enum_t
-{
- HDC hdc;
- struct device *d;
-};
-
/************************************************************************/
/* helpers */
/************************************************************************/
-static int CALLBACK
-font_enum_callback_2 (ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme,
- int FontType, struct font_enum_t *font_enum)
-{
- struct mswindows_font_enum *fontlist, **fonthead;
- char fontname[MSW_FONTSIZE];
-
- /* The enumerated font weights are not to be trusted because:
- * a) lpelfe->elfStyle is only filled in for TrueType fonts.
- * b) Not all Bold and Italic styles of all fonts (inluding some Vector,
- * Truetype and Raster fonts) are enumerated.
- * I guess that fonts for which Bold and Italic styles are generated
- * 'on-the-fly' are not enumerated. It would be overly restrictive to
- * disallow Bold And Italic weights for these fonts, so we just leave
- * weights unspecified. This means that we have to weed out duplicates of
- * those fonts that do get enumerated with different weights. */
-
- if (FontType == 0 /*vector*/ || FontType == TRUETYPE_FONTTYPE)
- /* Scalable, so leave pointsize blank */
- sprintf (fontname, "%s::::%s", lpelfe->elfLogFont.lfFaceName,
- lpelfe->elfScript);
- else
- /* Formula for pointsize->height from LOGFONT docs in Platform SDK */
- sprintf (fontname, "%s::%d::%s", lpelfe->elfLogFont.lfFaceName,
- MulDiv (lpntme->ntmTm.tmHeight - lpntme->ntmTm.tmInternalLeading,
- 72, DEVICE_MSWINDOWS_LOGPIXELSY (font_enum->d)),
- lpelfe->elfScript);
-
- fonthead = &DEVICE_MSWINDOWS_FONTLIST (font_enum->d);
- fontlist = *fonthead;
- while (fontlist)
- if (!strcmp (fontname, fontlist->fontname))
- return 1; /* found a duplicate */
- else
- fontlist = fontlist->next;
-
- /* Insert entry at head */
- fontlist = *fonthead;
- *fonthead = xmalloc (sizeof (struct mswindows_font_enum));
- if (*fonthead == NULL)
- {
- *fonthead = fontlist;
- return 0;
- }
- strcpy ((*fonthead)->fontname, fontname);
- (*fonthead)->next = fontlist;
- return 1;
-}
-
-static int CALLBACK
-font_enum_callback_1 (ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme,
- int FontType, struct font_enum_t *font_enum)
-{
- /* This function gets called once per facename per character set.
- * We call a second callback to enumerate the fonts in each facename */
- return EnumFontFamiliesEx (font_enum->hdc, &lpelfe->elfLogFont,
- (FONTENUMPROC) font_enum_callback_2,
- (LPARAM) font_enum, 0);
-}
-
static Lisp_Object
build_syscolor_string (int index)
{
{
WNDCLASSEX wc;
HDC hdc;
- LOGFONT logfont;
- struct font_enum_t font_enum;
DEVICE_CLASS (d) = Qcolor;
DEVICE_INFD (d) = DEVICE_OUTFD (d) = -1;
DEVICE_MSWINDOWS_HORZSIZE(d) = GetDeviceCaps(hdc, HORZSIZE);
DEVICE_MSWINDOWS_VERTSIZE(d) = GetDeviceCaps(hdc, VERTSIZE);
DEVICE_MSWINDOWS_BITSPIXEL(d) = GetDeviceCaps(hdc, BITSPIXEL);
-
- DEVICE_MSWINDOWS_FONTLIST (d) = NULL;
- logfont.lfCharSet = DEFAULT_CHARSET;
- logfont.lfFaceName[0] = '\0';
- logfont.lfPitchAndFamily = DEFAULT_PITCH;
- font_enum.hdc = hdc;
- font_enum.d = d;
- EnumFontFamiliesEx (hdc, &logfont, (FONTENUMPROC) font_enum_callback_1,
- (LPARAM) (&font_enum), 0);
DeleteDC (hdc);
+ mswindows_enumerate_fonts (d);
+
/* Register the main window class */
wc.cbSize = sizeof (WNDCLASSEX);
wc.style = CS_OWNDC; /* One DC per window */
Lisp_Object Qx_error;
Lisp_Object Qinit_pre_x_win, Qinit_post_x_win;
-/* \e$B@ZJ"\e(B, n. Japanese ritual suicide. */
-int x_seppuku_on_epipe;
-
/* The application class of Emacs. */
Lisp_Object Vx_emacs_application_class;
Lisp_Object dev;
struct device *d = get_device_from_display_1 (disp);
- if (d)
- XSETDEVICE (dev, d);
- else
- dev = Qnil;
+ assert (d != NULL);
+ XSETDEVICE (dev, d);
if (NILP (find_nonminibuffer_frame_not_on_device (dev)))
{
{
warn_when_safe
(Qx, Qcritical,
- "I/O Error %d (%s) on display connection \"%s\"\n"
- " after %lu requests (%lu known processed) with "
- "%d events remaining.\n",
+ "I/O Error %d (%s) on display connection\n"
+ " \"%s\" after after %lu requests (%lu known processed)\n"
+ " with %d events remaining.\n"
+ " Throwing to top level.\n",
errno, strerror (errno), DisplayString (disp),
NextRequest (disp) - 1, LastKnownRequestProcessed (disp),
QLength (disp));
}
+ /* According to X specs, we should not return from this function, or
+ Xlib might just decide to exit(). So we mark the offending
+ console for deletion and throw to top level. */
if (d)
enqueue_magic_eval_event (io_error_delete_device, dev);
+ DEVICE_X_BEING_DELETED (d) = 1;
+ Fthrow (Qtop_level, Qnil);
- /* CvE, July 16, 1996, XEmacs 19.14 */
- /* Test for broken pipe error, which indicates X-server has gone down */
- if (errno == EPIPE && x_seppuku_on_epipe)
- {
- /* Most probably X-server has gone down: Avoid infinite loop by just */
- /* exiting */
- /* slb: This sounds really, really dangerous to do by default, so */
- /* I'm adding a guard to avoid doing this as default behavior */
- stderr_out( "\n\nXEmacs exiting on broken pipe (errno %d, %s)\n",
- errno, strerror(errno));
- exit(errno);
- }
-
- return 0;
+ RETURN_NOT_REACHED (0);
}
DEFUN ("x-debug-mode", Fx_debug_mode, 1, 2, 0, /*
*/ );
Vx_initial_argv_list = Qnil;
- DEFVAR_BOOL ("x-seppuku-on-epipe", &x_seppuku_on_epipe /*
-When non-nil, terminate XEmacs immediately on SIGPIPE from the X server.
-XEmacs doesn't terminate properly on some systems.
-When this variable is non-nil, XEmacs will commit immediate suicide
-when it gets a sigpipe from the X Server.
-*/ );
- x_seppuku_on_epipe = 0;
-
#if defined(MULE) && (defined(LWLIB_MENUBARS_MOTIF) || defined(HAVE_XIM) || defined (USE_XFONTSET))
DEFVAR_LISP ("x-app-defaults-directory", &Vx_app_defaults_directory /*
Used by the Lisp code to communicate to the low level X initialization
void
io_error_delete_device (Lisp_Object device)
{
+ /* Note: it's the console that should get deleted, but
+ delete_device_internal() contains a hack that also deletes the
+ console when called from this function. */
delete_device_internal (XDEVICE (device), 1, 0, 1);
}
#include "opaque.h"
#include "sysfile.h"
#include "sysdir.h"
+#include "systime.h"
+#include "syspwd.h"
Lisp_Object Vcompletion_ignored_extensions;
Lisp_Object Qdirectory_files;
DIR *d;
Lisp_Object obj = XCAR (locative);
- if (NILP (obj))
- return Qnil;
- d = (DIR *)get_opaque_ptr (obj);
- closedir (d);
- free_opaque_ptr (obj);
+ if (!NILP (obj))
+ {
+ d = (DIR *)get_opaque_ptr (obj);
+ closedir (d);
+ free_opaque_ptr (obj);
+ }
free_cons (XCONS (locative));
return Qnil;
}
}
\f
+static Lisp_Object user_name_completion (Lisp_Object user,
+ int all_flag,
+ int *uniq);
+
+DEFUN ("user-name-completion", Fuser_name_completion, 1, 1, 0, /*
+Complete user name USER.
+
+Returns the longest string common to all user names that start
+with USER. If there is only one and USER matches it exactly,
+returns t. Returns nil if there is no user name starting with USER.
+*/
+ (user))
+{
+ return user_name_completion (user, 0, NULL);
+}
+
+DEFUN ("user-name-completion-1", Fuser_name_completion_1, 1, 1, 0, /*
+Complete user name USER.
+
+This function is identical to `user-name-completion', except that
+the cons of the completion and an indication of whether the
+completion was unique is returned.
+
+The car of the returned value is the longest string common to all
+user names that start with USER. If there is only one and USER
+matches it exactly, the car is t. The car is nil if there is no
+user name starting with USER. The cdr of the result is non-nil
+if and only if the completion returned in the car was unique.
+*/
+ (user))
+{
+ int uniq;
+ Lisp_Object completed;
+
+ completed = user_name_completion (user, 0, &uniq);
+ return Fcons (completed, uniq ? Qt : Qnil);
+}
+
+DEFUN ("user-name-all-completions", Fuser_name_all_completions, 1, 1, 0, /*
+Return a list of all completions of user name USER.
+These are all user names which begin with USER.
+*/
+ (user))
+{
+ return user_name_completion (user, 1, NULL);
+}
+
+static Lisp_Object
+user_name_completion_unwind (Lisp_Object locative)
+{
+ Lisp_Object obj1 = XCAR (locative);
+ Lisp_Object obj2 = XCDR (locative);
+ char **cache;
+ int clen, i;
+
+
+ if (!NILP (obj1) && !NILP (obj2))
+ {
+ /* clean up if interrupted building cache */
+ cache = *(char ***)get_opaque_ptr (obj1);
+ clen = *(int *)get_opaque_ptr (obj2);
+ free_opaque_ptr (obj1);
+ free_opaque_ptr (obj2);
+ for (i = 0; i < clen; i++)
+ free (cache[i]);
+ free (cache);
+ }
+
+ free_cons (XCONS (locative));
+ endpwent ();
+
+ return Qnil;
+}
+
+static char **user_cache;
+static int user_cache_len;
+static int user_cache_max;
+static long user_cache_time;
+
+#define USER_CACHE_REBUILD (24*60*60) /* 1 day, in seconds */
+
+static Lisp_Object
+user_name_completion (Lisp_Object user, int all_flag, int *uniq)
+{
+ /* This function can GC */
+ struct passwd *pw;
+ int matchcount = 0;
+ Lisp_Object bestmatch = Qnil;
+ Charcount bestmatchsize = 0;
+ int speccount = specpdl_depth ();
+ int i, cmax, clen;
+ char **cache;
+ Charcount user_name_length;
+ Lisp_Object locative;
+ EMACS_TIME t;
+ struct gcpro gcpro1, gcpro2;
+
+ GCPRO2 (user, bestmatch);
+
+ CHECK_STRING (user);
+
+ user_name_length = XSTRING_CHAR_LENGTH (user);
+
+ /* Cache user name lookups because it tends to be quite slow.
+ * Rebuild the cache occasionally to catch changes */
+ EMACS_GET_TIME (t);
+ if (user_cache &&
+ EMACS_SECS (t) - user_cache_time > USER_CACHE_REBUILD)
+ {
+ for (i = 0; i < user_cache_len; i++)
+ free (user_cache[i]);
+ free (user_cache);
+ user_cache = NULL;
+ user_cache_len = 0;
+ user_cache_max = 0;
+ }
+
+ if (user_cache == NULL || user_cache_max <= 0)
+ {
+ cmax = 200;
+ clen = 0;
+ cache = (char **) malloc (cmax*sizeof (char *));
+
+ setpwent ();
+ locative = noseeum_cons (Qnil, Qnil);
+ XCAR (locative) = make_opaque_ptr ((void *) &cache);
+ XCDR (locative) = make_opaque_ptr ((void *) &clen);
+ record_unwind_protect (user_name_completion_unwind, locative);
+ /* #### may need to slow down interrupts around call to getpwent
+ * below. at least the call to getpwnam in Fuser_full_name
+ * is documented as needing it on irix. */
+ while ((pw = getpwent ()))
+ {
+ if (clen >= cmax)
+ {
+ cmax *= 2;
+ cache = (char **) realloc (cache, cmax*sizeof (char *));
+ }
+
+ QUIT;
+
+ cache[clen++] = strdup (pw->pw_name);
+ }
+ free_opaque_ptr (XCAR (locative));
+ free_opaque_ptr (XCDR (locative));
+ XCAR (locative) = Qnil;
+ XCDR (locative) = Qnil;
+
+ unbind_to (speccount, Qnil); /* free locative cons, endpwent() */
+
+ user_cache_max = cmax;
+ user_cache_len = clen;
+ user_cache = cache;
+ user_cache_time = EMACS_SECS (t);
+ }
+
+ for (i = 0; i < user_cache_len; i++)
+ {
+ Bytecount len;
+ /* scmp() works in chars, not bytes, so we have to compute this: */
+ Charcount cclen;
+ Bufbyte *d_name;
+
+ d_name = (Bufbyte *) user_cache[i];
+ len = strlen (d_name);
+ cclen = bytecount_to_charcount (d_name, len);
+
+ QUIT;
+
+ if (cclen < user_name_length ||
+ 0 <= scmp (d_name, XSTRING_DATA (user), user_name_length))
+ continue;
+
+ matchcount++; /* count matching completions */
+
+ if (all_flag || NILP (bestmatch))
+ {
+ Lisp_Object name = Qnil;
+ struct gcpro ngcpro1;
+ NGCPRO1 (name);
+ /* This is a possible completion */
+ name = make_string (d_name, len);
+ if (all_flag)
+ {
+ bestmatch = Fcons (name, bestmatch);
+ }
+ else
+ {
+ bestmatch = name;
+ bestmatchsize = XSTRING_CHAR_LENGTH (name);
+ }
+ NUNGCPRO;
+ }
+ else
+ {
+ Charcount compare = min (bestmatchsize, cclen);
+ Bufbyte *p1 = XSTRING_DATA (bestmatch);
+ Bufbyte *p2 = d_name;
+ Charcount matchsize = scmp (p1, p2, compare);
+
+ if (matchsize < 0)
+ matchsize = compare;
+ if (completion_ignore_case)
+ {
+ /* If this is an exact match except for case,
+ use it as the best match rather than one that is not
+ an exact match. This way, we get the case pattern
+ of the actual match. */
+ if ((matchsize == cclen
+ && matchsize < XSTRING_CHAR_LENGTH (bestmatch))
+ ||
+ /* If there is no exact match ignoring case,
+ prefer a match that does not change the case
+ of the input. */
+ (((matchsize == cclen)
+ ==
+ (matchsize == XSTRING_CHAR_LENGTH (bestmatch)))
+ /* If there is more than one exact match aside from
+ case, and one of them is exact including case,
+ prefer that one. */
+ && 0 > scmp_1 (p2, XSTRING_DATA (user),
+ user_name_length, 0)
+ && 0 <= scmp_1 (p1, XSTRING_DATA (user),
+ user_name_length, 0)))
+ {
+ bestmatch = make_string (d_name, len);
+ }
+ }
+
+ bestmatchsize = matchsize;
+ }
+ }
+
+ UNGCPRO;
+
+ if (uniq)
+ *uniq = (matchcount == 1);
+
+ if (all_flag || NILP (bestmatch))
+ return bestmatch;
+ if (matchcount == 1 && bestmatchsize == user_name_length)
+ return Qt;
+ return Fsubstring (bestmatch, Qzero, make_int (bestmatchsize));
+}
+
+\f
Lisp_Object
make_directory_hash_table (CONST char *path)
{
DEFSUBR (Fdirectory_files);
DEFSUBR (Ffile_name_completion);
DEFSUBR (Ffile_name_all_completions);
+ DEFSUBR (Fuser_name_completion);
+ DEFSUBR (Fuser_name_completion_1);
+ DEFSUBR (Fuser_name_all_completions);
DEFSUBR (Ffile_attributes);
}
`file-name-all-completions'.
*/ );
Vcompletion_ignored_extensions = Qnil;
+
+ user_cache = NULL;
+ user_cache_len = 0;
+ user_cache_max = 0;
}
#if defined (HAVE_MMAP) && defined (REL_ALLOC)
/* ralloc can only be used if using the GNU memory allocator. */
init_ralloc ();
+#elif defined (REL_ALLOC) && !defined(DOUG_LEA_MALLOC)
+ if (initialized)
+ init_ralloc();
#endif
#ifdef HAVE_SOCKS
vars_of_extents ();
vars_of_faces ();
vars_of_fileio ();
-#ifdef CLASH_DETECTION
- vars_of_filelock ();
-#endif
vars_of_floatfns ();
vars_of_font_lock ();
vars_of_frame ();
might depend on all sorts of things; I'm not sure. */
complex_vars_of_emacs ();
-#ifdef CLASH_DETECTION
- complex_vars_of_filelock ();
-#endif /* CLASH_DETECTION */
-
/* This creates a couple of basic keymaps and depends on Lisp
hashtables and Ffset() (both of which depend on some variables
initialized in the vars_of_*() section) and possibly other
emacs_Xt_mapping_action (Widget w, XEvent* event)
{
struct device *d = get_device_from_display (event->xany.display);
+
+ if (DEVICE_X_BEING_DELETED (d))
+ return;
#if 0
/* nyet. Now this is handled by Xt. */
XRefreshKeyboardMapping (&event->xmapping);
/* simple_p means don't try too hard (ASCII only) */
{
KeySym keysym = 0;
-
+
#ifdef HAVE_XIM
int len;
char buffer[64];
than passing in 0) to avoid crashes on German IRIX */
char dummy[256];
XLookupString (event, dummy, 200, &keysym, 0);
- return x_keysym_to_emacs_keysym (keysym, simple_p);
+ return (IsModifierKey (keysym) || keysym == XK_Mode_switch )
+ ? Qnil : x_keysym_to_emacs_keysym (keysym, simple_p);
}
#endif /* ! XIM_MOTIF */
{
case XLookupKeySym:
case XLookupBoth:
- return x_keysym_to_emacs_keysym (keysym, simple_p);
+ return (IsModifierKey (keysym) || keysym == XK_Mode_switch )
+ ? Qnil : x_keysym_to_emacs_keysym (keysym, simple_p);
case XLookupChars:
{
struct device *d = get_device_from_display (display);
struct x_device *xd = DEVICE_X_DATA (d);
+ if (DEVICE_X_BEING_DELETED (d))
+ /* #### Uh, is this 0 correct? */
+ return 0;
+
set_last_server_timestamp (d, x_event);
switch (x_event->type)
{
Lisp_Object keysym;
XKeyEvent *ev = &x_event->xkey;
- KeyCode keycode = ev->keycode;
-
- if (x_key_is_modifier_p (keycode, d)) /* it's a modifier key */
- return 0;
-
/* This used to compute the frame from the given X window and
store it here, but we really don't care about the frame. */
emacs_event->channel = DEVICE_CONSOLE (d);
keysym = x_to_emacs_keysym (&x_event->xkey, 0);
- /* If the emacs keysym is nil, then that means that the
- X keysym was NoSymbol, which probably means that
- we're in the midst of reading a Multi_key sequence,
- or a "dead" key prefix, or XIM input. Ignore it. */
+ /* If the emacs keysym is nil, then that means that the X
+ keysym was either a Modifier or NoSymbol, which
+ probably means that we're in the midst of reading a
+ Multi_key sequence, or a "dead" key prefix, or XIM
+ input. Ignore it. */
if (NILP (keysym))
return 0;
void
emacs_Xt_handle_focus_event (XEvent *event)
{
+ struct device *d = get_device_from_display (event->xany.display);
+ struct frame *f;
+
+ if (DEVICE_X_BEING_DELETED (d))
+ return;
+
/*
* It's curious that we're using x_any_window_to_frame() instead
* of x_window_to_frame(). I don't know what the impact of this is.
*/
-
- struct frame *f =
- x_any_window_to_frame (get_device_from_display (event->xany.display),
- event->xfocus.window);
+ f = x_any_window_to_frame (d, event->xfocus.window);
if (!f)
/* focus events are sometimes generated just before
a frame is destroyed. */
XEvent *event = &emacs_event->event.magic.underlying_x_event;
struct frame *f = XFRAME (EVENT_CHANNEL (emacs_event));
- if (!FRAME_LIVE_P (f))
+ if (!FRAME_LIVE_P (f) || DEVICE_X_BEING_DELETED (XDEVICE (FRAME_DEVICE (f))))
return;
switch (event->type)
#ifdef HAVE_MSG_SELECT
extern SELECT_TYPE input_wait_mask, non_fake_input_wait_mask;
extern SELECT_TYPE process_only_mask, tty_only_mask;
+SELECT_TYPE zero_mask;
extern int signal_event_pipe_initialized;
int windows_fd;
#endif
{
ResetEvent (str->ov.hEvent);
-
- if (WriteFile ((HANDLE)str->s, data, size, NULL, &str->ov)
+
+ /* Docs indicate that 4th parameter to WriteFile can be NULL since this is
+ * an overlapped operation. This fails on Win95 with winsock 1.x so we
+ * supply a spare address which is ignored by Win95 anyway. Sheesh. */
+ if (WriteFile ((HANDLE)str->s, data, size, (LPDWORD)&str->buffer, &str->ov)
|| GetLastError() == ERROR_IO_PENDING)
str->pending_p = 1;
else
EMACS_TIME_TO_SELECT_TIME (sometime, select_time_to_block);
pointer_to_this = &select_time_to_block;
}
+
+ /* select() is slow and buggy so if we don't have any processes
+ just wait as normal */
+ if (memcmp (&process_only_mask, &zero_mask, sizeof(SELECT_TYPE))==0)
+ {
+ /* Now try getting a message or process event */
+ active = MsgWaitForMultipleObjects (0, mswindows_waitable_handles,
+ FALSE, badly_p ? INFINITE : 0,
+ QS_ALLINPUT);
+
+ if (active == WAIT_TIMEOUT)
+ {
+ /* No luck trying - just return what we've already got */
+ return;
+ }
+ else if (active == WAIT_OBJECT_0)
+ {
+ /* Got your message, thanks */
+ mswindows_drain_windows_queue ();
+ continue;
+ }
+ }
+
active = select (MAXDESC, &temp_mask, 0, 0, pointer_to_this);
if (active == 0)
mswindows_enqueue_misc_user_event (fobj, Qeval, list3 (Qdelete_frame, fobj, Qt));
break;
+ case WM_KEYUP:
+ case WM_SYSKEYUP:
+ /* See Win95 comment under WM_KEYDOWN */
+ {
+ BYTE keymap[256];
+
+ if (wParam == VK_CONTROL)
+ {
+ GetKeyboardState (keymap);
+ keymap [(lParam & 0x1000000) ? VK_RCONTROL : VK_LCONTROL] &= ~0x80;
+ SetKeyboardState (keymap);
+ }
+ else if (wParam == VK_MENU)
+ {
+ GetKeyboardState (keymap);
+ keymap [(lParam & 0x1000000) ? VK_RMENU : VK_LMENU] &= ~0x80;
+ SetKeyboardState (keymap);
+ }
+ };
+ goto defproc;
+
case WM_KEYDOWN:
case WM_SYSKEYDOWN:
+ /* In some locales the right-hand Alt key is labelled AltGr. This key
+ * should produce alternative charcaters when combined with another key.
+ * eg on a German keyboard pressing AltGr+q should produce '@'.
+ * AltGr generates exactly the same keystrokes as LCtrl+RAlt. But if
+ * TranslateMessage() is called with *any* combination of Ctrl+Alt down,
+ * it translates as if AltGr were down.
+ * We get round this by removing all modifiers from the keymap before
+ * calling TranslateMessage() unless AltGr is *really* down. */
{
BYTE keymap[256];
int has_AltGr = mswindows_current_layout_has_AltGr ();
GetKeyboardState (keymap);
mods = mswindows_modifier_state (keymap, has_AltGr);
- /* Handle those keys that TranslateMessage won't generate a WM_CHAR for */
+ /* Handle those keys for which TranslateMessage won't generate a WM_CHAR */
if (!NILP (keysym = mswindows_key_to_emacs_keysym(wParam, mods)))
mswindows_enqueue_keypress_event (hwnd, keysym, mods);
else
int quit_ch = CONSOLE_QUIT_CHAR (XCONSOLE (mswindows_find_console (hwnd)));
BYTE keymap_orig[256];
MSG msg = { hwnd, message, wParam, lParam, GetMessageTime(), (GetMessagePos()) };
+
+ /* GetKeyboardState() does not work as documented on Win95. We have
+ * to loosely track Left and Right modifiers on behalf of the OS,
+ * without screwing up Windows NT which tracks them properly. */
+ if (wParam == VK_CONTROL)
+ keymap [(lParam & 0x1000000) ? VK_RCONTROL : VK_LCONTROL] |= 0x80;
+ else if (wParam == VK_MENU)
+ keymap [(lParam & 0x1000000) ? VK_RMENU : VK_LMENU] |= 0x80;
+
memcpy (keymap_orig, keymap, 256);
/* Remove shift modifier from an ascii character */
mods &= ~MOD_SHIFT;
- /* Clear control and alt modifiers out of the keymap */
+ /* Clear control and alt modifiers unless AltGr is pressed */
keymap [VK_RCONTROL] = 0;
keymap [VK_LMENU] = 0;
if (!has_AltGr || !(keymap [VK_LCONTROL] & 0x80) || !(keymap [VK_RMENU] & 0x80))
}
SetKeyboardState (keymap);
- /* Have some WM_[SYS]CHARS in the queue */
+ /* Maybe generate some WM_[SYS]CHARs in the queue */
TranslateMessage (&msg);
while (PeekMessage (&msg, hwnd, WM_CHAR, WM_CHAR, PM_REMOVE)
windows_fd = open("/dev/windows", O_RDONLY | O_NONBLOCK, 0);
assert (windows_fd>=0);
FD_SET (windows_fd, &input_wait_mask);
- /* for some reason I get blocks on the signal event pipe, which is
- bad...
- signal_event_pipe_initialized = 0; */
+ FD_ZERO(&zero_mask);
#endif
event_stream = mswindows_event_stream;
((markobj) (data->read_only));
((markobj) (data->mouse_face));
((markobj) (data->initial_redisplay_function));
+ ((markobj) (data->before_change_functions));
+ ((markobj) (data->after_change_functions));
return data->parent;
}
|| EQ (prop, Qpriority)
|| EQ (prop, Qface)
|| EQ (prop, Qinitial_redisplay_function)
+ || EQ (prop, Qafter_change_functions)
+ || EQ (prop, Qbefore_change_functions)
|| EQ (prop, Qmouse_face)
|| EQ (prop, Qhighlight)
|| EQ (prop, Qbegin_glyph_layout)
ME_END_CLOSED | ME_MIGHT_MODIFY_EXTENTS);
}
+/* ------------------------------- */
+/* report_extent_modification() */
+/* ------------------------------- */
+struct report_extent_modification_closure {
+ Lisp_Object buffer;
+ Bufpos start, end;
+ int afterp;
+ int speccount;
+};
+
+/* This juggling with the pointer to another file's global variable is
+ kind of yucky. Perhaps I should just export the variable. */
+static int *inside_change_hook_pointer;
+
+static Lisp_Object
+report_extent_modification_restore (Lisp_Object buffer)
+{
+ *inside_change_hook_pointer = 0;
+ if (current_buffer != XBUFFER (buffer))
+ Fset_buffer (buffer);
+ return Qnil;
+}
+
+static int
+report_extent_modification_mapper (EXTENT extent, void *arg)
+{
+ struct report_extent_modification_closure *closure =
+ (struct report_extent_modification_closure *)arg;
+ Lisp_Object exobj, startobj, endobj;
+ Lisp_Object hook = (closure->afterp
+ ? extent_after_change_functions (extent)
+ : extent_before_change_functions (extent));
+ if (NILP (hook))
+ return 0;
+
+ XSETEXTENT (exobj, extent);
+ XSETINT (startobj, closure->start);
+ XSETINT (endobj, closure->end);
+
+ /* Now that we are sure to call elisp, set up an unwind-protect so
+ inside_change_hook gets restored in case we throw. Also record
+ the current buffer, in case we change it. Do the recording only
+ once. */
+ if (closure->speccount == -1)
+ {
+ closure->speccount = specpdl_depth ();
+ record_unwind_protect (report_extent_modification_restore,
+ Fcurrent_buffer ());
+ }
+
+ /* The functions will expect closure->buffer to be the current
+ buffer, so change it if it isn't. */
+ if (current_buffer != XBUFFER (closure->buffer))
+ Fset_buffer (closure->buffer);
+
+ /* #### It's a shame that we can't use any of the existing run_hook*
+ functions here. This is so because all of them work with
+ symbols, to be able to retrieve default values of local hooks.
+ <sigh> */
+
+ if (!CONSP (hook) || EQ (XCAR (hook), Qlambda))
+ call3 (hook, exobj, startobj, endobj);
+ else
+ {
+ Lisp_Object tail;
+ EXTERNAL_LIST_LOOP (tail, hook)
+ call3 (XCAR (tail), exobj, startobj, endobj);
+ }
+ return 0;
+}
+
+void
+report_extent_modification (Lisp_Object buffer, Bufpos start, Bufpos end,
+ int *inside, int afterp)
+{
+ struct report_extent_modification_closure closure;
+
+ closure.buffer = buffer;
+ closure.start = start;
+ closure.end = end;
+ closure.afterp = afterp;
+ closure.speccount = -1;
+
+ inside_change_hook_pointer = inside;
+ *inside = 1;
+
+ map_extents (start, end, report_extent_modification_mapper, (void *)&closure,
+ buffer, NULL, ME_MIGHT_CALL_ELISP);
+
+ if (closure.speccount == -1)
+ *inside = 0;
+ else
+ {
+ /* We mustn't unbind when closure.speccount != -1 because
+ map_extents_bytind has already done that. */
+ assert (*inside == 0);
+ }
+}
+
\f
/************************************************************************/
/* extent properties */
Fset_extent_face (extent, value);
else if (EQ (property, Qinitial_redisplay_function))
Fset_extent_initial_redisplay_function (extent, value);
+ else if (EQ (property, Qbefore_change_functions))
+ set_extent_before_change_functions (e, value);
+ else if (EQ (property, Qafter_change_functions))
+ set_extent_after_change_functions (e, value);
else if (EQ (property, Qmouse_face))
Fset_extent_mouse_face (extent, value);
/* Obsolete: */
return Fextent_face (extent);
else if (EQ (property, Qinitial_redisplay_function))
return extent_initial_redisplay_function (e);
+ else if (EQ (property, Qbefore_change_functions))
+ return extent_before_change_functions (e);
+ else if (EQ (property, Qafter_change_functions))
+ return extent_after_change_functions (e);
else if (EQ (property, Qmouse_face))
return Fextent_mouse_face (extent);
/* Obsolete: */
result = cons3 (Qinitial_redisplay_function,
extent_initial_redisplay_function (anc), result);
+ if (!NILP (extent_before_change_functions (anc)))
+ result = cons3 (Qbefore_change_functions,
+ extent_before_change_functions (anc), result);
+
+ if (!NILP (extent_after_change_functions (anc)))
+ result = cons3 (Qafter_change_functions,
+ extent_after_change_functions (anc), result);
+
if (!NILP (extent_invisible (anc)))
result = cons3 (Qinvisible, extent_invisible (anc), result);
extent_auxiliary_defaults.read_only = Qnil;
extent_auxiliary_defaults.mouse_face = Qnil;
extent_auxiliary_defaults.initial_redisplay_function = Qnil;
+ extent_auxiliary_defaults.before_change_functions = Qnil;
+ extent_auxiliary_defaults.after_change_functions = Qnil;
}
void
unsigned int has_aux :1; /* 6 extent has an aux. structure */
unsigned int start_open :1; /* 7 insertion behavior at start */
unsigned int end_open :1; /* 8 insertion behavior at end */
- unsigned int unused9 :1; /* 9 unused */
- unsigned int unique :1; /* 10 there may be only one attached */
- unsigned int duplicable :1; /* 11 copied to strings by kill/undo */
- unsigned int REPLICATING :1; /* 12 invoke old extent-replica behav.*/
- /* Not used any more */
- unsigned int detachable :1; /* 13 extent detaches if text deleted */
- unsigned int internal :1; /* 14 used by map-extents etc. */
- unsigned int in_red_event :1; /* 15 An event has been spawned for
+ unsigned int unique :1; /* 9 there may be only one attached */
+ unsigned int duplicable :1; /* 10 copied to strings by kill/undo */
+ unsigned int detachable :1; /* 11 extent detaches if text deleted */
+ unsigned int internal :1; /* 12 used by map-extents etc. */
+ unsigned int in_red_event :1; /* 13 An event has been spawned for
initial redisplay.
- Not exported to the lisp level */
- unsigned int unused16 :1; /* 16 unused */
+ (not exported to lisp) */
+ unsigned int unused16 :1; /* 16 unused bits */
/* --- Adding more flags will cause the extent struct to grow by another
word. It's not clear that this would make a difference, however,
because on 32-bit machines things tend to get allocated in chunks
Lisp_Object read_only;
Lisp_Object mouse_face;
Lisp_Object initial_redisplay_function;
+ Lisp_Object before_change_functions, after_change_functions;
int priority;
};
#define extent_read_only(e) extent_aux_field (e, read_only)
#define extent_mouse_face(e) extent_aux_field (e, mouse_face)
#define extent_initial_redisplay_function(e) extent_aux_field (e, initial_redisplay_function)
+#define extent_before_change_functions(e) extent_aux_field (e, before_change_functions)
+#define extent_after_change_functions(e) extent_aux_field (e, after_change_functions)
#define set_extent_begin_glyph(e, value) \
set_extent_aux_field (e, begin_glyph, value)
/* Use Fset_extent_initial_redisplay_function unless you know what you're doing */
#define set_extent_initial_redisplay_function(e, value) \
set_extent_aux_field (e, initial_redisplay_function, value)
+#define set_extent_before_change_functions(e, value) \
+ set_extent_aux_field (e, before_change_functions, value)
+#define set_extent_after_change_functions(e, value) \
+ set_extent_aux_field (e, after_change_functions, value)
#define extent_face(e) extent_normal_field (e, face)
#define extent_begin_glyph_layout(e) extent_normal_field (e, begin_glyph_layout)
Bytind opoint, Bytecount length);
void process_extents_for_deletion (Lisp_Object object, Bytind from,
Bytind to, int destroy_them);
+void report_extent_modification (Lisp_Object, Bufpos, Bufpos, int *, int);
void set_extent_glyph (EXTENT extent, Lisp_Object glyph, int endp,
glyph_layout layout);
inst_list);
#endif /* HAVE_TTY */
#ifdef HAVE_MS_WINDOWS
- inst_list = Fcons (Fcons (list1 (Qmswindows), build_string ("Courier New")),
- inst_list);
+ inst_list = Fcons (Fcons (list1 (Qmswindows),
+ build_string ("Fixedsys:Regular:9::Western")), inst_list);
+ inst_list = Fcons (Fcons (list1 (Qmswindows),
+ build_string ("Courier:Regular:10::Western")), inst_list);
+ inst_list = Fcons (Fcons (list1 (Qmswindows),
+ build_string ("Courier New:Regular:10::Western")), inst_list);
#endif /* HAVE_MS_WINDOWS */
set_specifier_fallback (Fget (Vdefault_face, Qfont, Qnil), inst_list);
}
Bufbyte *res = alloca (MAXPATHLEN + 1);
if (getdefdir (toupper (*beg) - 'A' + 1, res))
{
- if (!IS_DIRECTORY_SEP (res[strlen ((char *) res) - 1]))
- strcat ((char *) res, "/");
+ char *c=((char *) res) + strlen ((char *) res);
+ if (!IS_DIRECTORY_SEP (*c))
+ {
+ *c++ = DIRECTORY_SEP;
+ *c = '\0';
+ }
beg = res;
p = beg + strlen ((char *) beg);
}
}
- CORRECT_DIR_SEPS (beg);
#endif /* WINDOWSNT */
return make_string (beg, p - beg);
}
out[size + 1] = '\0';
}
}
-#ifdef WINDOWSNT
- CORRECT_DIR_SEPS (out);
-#endif
return out;
}
)
dst[slen - 1] = 0;
#endif /* APOLLO */
-#ifdef WINDOWSNT
- CORRECT_DIR_SEPS (dst);
-#endif /* WINDOWSNT */
return 1;
}
if (!NILP (handler))
RETURN_UNGCPRO (call2 (handler, Qfile_readable_p, abspath));
-#ifdef WINDOWSNT
+#if defined(WINDOWSNT) || defined(__CYGWIN32__)
/* Under MS-DOS and Windows, open does not work for directories. */
UNGCPRO;
if (access (XSTRING_DATA (abspath), 0) == 0)
-/* Copyright (C) 1985, 1986, 1987, 1992, 1993, 1994
- Free Software Foundation, Inc.
+/* Copyright (C) 1985, 86, 87, 93, 94, 96 Free Software Foundation, Inc.
-This file is part of XEmacs.
+This file is part of GNU Emacs.
-XEmacs is free software; you can redistribute it and/or modify it
-under the terms of the GNU General Public License as published by the
-Free Software Foundation; either version 2, or (at your option) any
-later version.
+GNU Emacs is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
-XEmacs is distributed in the hope that it will be useful, but WITHOUT
-ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
-FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
-for more details.
+GNU Emacs is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
You should have received a copy of the GNU General Public License
-along with XEmacs; see the file COPYING. If not, write to
+along with GNU Emacs; see the file COPYING. If not, write to
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA. */
-/* Synched up with: FSF 19.30. */
+/* Synced with FSF 20.2 */
#include <config.h>
#include "lisp.h"
#include "syspwd.h"
#include "syssignal.h" /* for kill */
-#ifndef CLASH_DETECTION
-#error CLASH_DETECTION is not defined??
-#endif
-
-/* FSFmacs uses char *lock_dir and char *superlock_file instead of
- the Lisp variables we use. */
-
-/* The name of the directory in which we keep lock files, with a '/'
- appended. */
-Lisp_Object Vlock_directory;
-
-#if 0 /* FSFmacs */
-/* Look in startup.el */
-/* The name of the file in the lock directory which is used to
- arbitrate access to the entire directory. */
-#define SUPERLOCK_NAME "!!!SuperLock!!!"
-#endif
-
-/* The name of the superlock file. This is SUPERLOCK_NAME appended to
- Vlock_directory. */
-Lisp_Object Vsuperlock_file, Vconfigure_superlock_file;
-
Lisp_Object Qask_user_about_supersession_threat;
Lisp_Object Qask_user_about_lock;
-static void lock_superlock (CONST char *lfname);
-static int lock_file_1 (CONST char *lfname, int mode);
-static int lock_if_free (CONST char *lfname);
-static int current_lock_owner (CONST char *);
-static int current_lock_owner_1 (CONST char *);
-
-/* Set LOCK to the name of the lock file for the filename FILE.
- char *LOCK; Lisp_Object FILE;
+#ifdef CLASH_DETECTION
+
+/* The strategy: to lock a file FN, create a symlink .#FN in FN's
+ directory, with link data `user@host.pid'. This avoids a single
+ mount (== failure) point for lock files.
+
+ When the host in the lock data is the current host, we can check if
+ the pid is valid with kill.
+
+ Otherwise, we could look at a separate file that maps hostnames to
+ reboot times to see if the remote pid can possibly be valid, since we
+ don't want Emacs to have to communicate via pipes or sockets or
+ whatever to other processes, either locally or remotely; rms says
+ that's too unreliable. Hence the separate file, which could
+ theoretically be updated by daemons running separately -- but this
+ whole idea is unimplemented; in practice, at least in our
+ environment, it seems such stale locks arise fairly infrequently, and
+ Emacs' standard methods of dealing with clashes suffice.
+
+ We use symlinks instead of normal files because (1) they can be
+ stored more efficiently on the filesystem, since the kernel knows
+ they will be small, and (2) all the info about the lock can be read
+ in a single system call (readlink). Although we could use regular
+ files to be useful on old systems lacking symlinks, nowadays
+ virtually all such systems are probably single-user anyway, so it
+ didn't seem worth the complication.
+
+ Similarly, we don't worry about a possible 14-character limit on
+ file names, because those are all the same systems that don't have
+ symlinks.
+
+ This is compatible with the locking scheme used by Interleaf (which
+ has contributed this implementation for Emacs), and was designed by
+ Ethan Jacobson, Kimbo Mundy, and others.
+
+ --karl@cs.umb.edu/karl@hq.ileaf.com. */
- MAKE_LOCK_NAME assumes you have already verified that Vlock_directory
- is a string. */
-
-#ifndef HAVE_LONG_FILE_NAMES
+\f
+/* Here is the structure that stores information about a lock. */
-#define MAKE_LOCK_NAME(lock, file) \
- (lock = (char *) alloca (14 + XSTRING_LENGTH (Vlock_directory) + 1), \
- fill_in_lock_short_file_name (lock, (file)))
+typedef struct
+{
+ char *user;
+ char *host;
+ unsigned long pid;
+} lock_info_type;
+
+/* When we read the info back, we might need this much more,
+ enough for decimal representation plus null. */
+#define LOCK_PID_MAX (4 * sizeof (unsigned long))
+
+/* Free the two dynamically-allocated pieces in PTR. */
+#define FREE_LOCK_INFO(i) do { xfree ((i).user); xfree ((i).host); } while (0)
+
+/* Write the name of the lock file for FN into LFNAME. Length will be
+ that of FN plus two more for the leading `.#' plus one for the null. */
+#define MAKE_LOCK_NAME(lock, file) \
+ (lock = (char *) alloca (XSTRING_LENGTH(file) + 2 + 1), \
+ fill_in_lock_file_name (lock, (file)))
static void
-fill_in_lock_short_file_name (REGISTER char *lockfile, REGISTER Lisp_Object fn)
+fill_in_lock_file_name (lockfile, fn)
+ register char *lockfile;
+ register Lisp_Object fn;
{
- REGISTER union
- {
- unsigned int word [2];
- unsigned char byte [8];
- } crc;
- REGISTER unsigned char *p, new;
+ register char *p;
- CHECK_STRING (Vlock_directory);
+ strcpy (lockfile, XSTRING_DATA(fn));
- /* 7-bytes cyclic code for burst correction on byte-by-byte basis.
- the used polynomial is D^7 + D^6 + D^3 +1. pot@cnuce.cnr.it */
+ /* Shift the nondirectory part of the file name (including the null)
+ right two characters. Here is one of the places where we'd have to
+ do something to support 14-character-max file names. */
+ for (p = lockfile + strlen (lockfile); p != lockfile && *p != '/'; p--)
+ p[2] = *p;
- crc.word[0] = crc.word[1] = 0;
-
- for (p = XSTRING_DATA (fn); new = *p++; )
- {
- new += crc.byte[6];
- crc.byte[6] = crc.byte[5] + new;
- crc.byte[5] = crc.byte[4];
- crc.byte[4] = crc.byte[3];
- crc.byte[3] = crc.byte[2] + new;
- crc.byte[2] = crc.byte[1];
- crc.byte[1] = crc.byte[0];
- crc.byte[0] = new;
- }
-
- {
- int need_slash = 0;
-
- /* in case lock-directory doesn't end in / */
- if (XSTRING_BYTE (Vlock_directory,
- XSTRING_LENGTH (Vlock_directory) - 1) != '/')
- need_slash = 1;
-
- sprintf (lockfile, "%s%s%.2x%.2x%.2x%.2x%.2x%.2x%.2x",
- (char *) XSTRING_DATA (Vlock_directory),
- need_slash ? "/" : "",
- crc.byte[0], crc.byte[1], crc.byte[2], crc.byte[3],
- crc.byte[4], crc.byte[5], crc.byte[6]);
- }
+ /* Insert the `.#'. */
+ p[1] = '.';
+ p[2] = '#';
}
-#else /* defined HAVE_LONG_FILE_NAMES */
-
-/* +2 for terminating null and possible extra slash */
-#define MAKE_LOCK_NAME(lock, file) \
- (lock = (char *) alloca (XSTRING_LENGTH (file) + \
- XSTRING_LENGTH (Vlock_directory) + 2), \
- fill_in_lock_file_name (lock, (file)))
+/* Lock the lock file named LFNAME.
+ If FORCE is nonzero, we do so even if it is already locked.
+ Return 1 if successful, 0 if not. */
-static void
-fill_in_lock_file_name (REGISTER char *lockfile, REGISTER Lisp_Object fn)
- /* fn must be a Lisp_String! */
+static int
+lock_file_1 (char *lfname,int force)
{
- REGISTER char *p;
-
- CHECK_STRING (Vlock_directory);
+ register int err;
+ char *user_name;
+ char *host_name;
+ char *lock_info_str;
- strcpy (lockfile, (char *) XSTRING_DATA (Vlock_directory));
+ if (STRINGP (Fuser_login_name (Qnil)))
+ user_name = (char *)XSTRING_DATA((Fuser_login_name (Qnil)));
+ else
+ user_name = "";
+ if (STRINGP (Fsystem_name ()))
+ host_name = (char *)XSTRING_DATA((Fsystem_name ()));
+ else
+ host_name = "";
+ lock_info_str = (char *)alloca (strlen (user_name) + strlen (host_name)
+ + LOCK_PID_MAX + 5);
- p = lockfile + strlen (lockfile);
+ sprintf (lock_info_str, "%s@%s.%lu", user_name, host_name,
+ (unsigned long) getpid ());
- if (p == lockfile /* lock-directory is empty?? */
- || *(p - 1) != '/') /* in case lock-directory doesn't end in / */
+ err = symlink (lock_info_str, lfname);
+ if (errno == EEXIST && force)
{
- *p = '/';
- p++;
+ unlink (lfname);
+ err = symlink (lock_info_str, lfname);
}
- strcpy (p, (char *) XSTRING_DATA (fn));
+ return err == 0;
+}
+\f
+/* Return 0 if nobody owns the lock file LFNAME or the lock is obsolete,
+ 1 if another process owns it (and set OWNER (if non-null) to info),
+ 2 if the current process owns it,
+ or -1 if something is wrong with the locking mechanism. */
- for (; *p; p++)
+static int
+current_lock_owner (lock_info_type *owner, char *lfname)
+{
+#ifndef index
+ extern char *rindex (), *index ();
+#endif
+ int o, p, len, ret;
+ int local_owner = 0;
+ char *at, *dot;
+ char *lfinfo = 0;
+ int bufsize = 50;
+ /* Read arbitrarily-long contents of symlink. Similar code in
+ file-symlink-p in fileio.c. */
+ do
+ {
+ bufsize *= 2;
+ lfinfo = (char *) xrealloc (lfinfo, bufsize);
+ len = readlink (lfname, lfinfo, bufsize);
+ }
+ while (len >= bufsize);
+
+ /* If nonexistent lock file, all is well; otherwise, got strange error. */
+ if (len == -1)
{
- if (*p == '/')
- *p = '!';
+ xfree (lfinfo);
+ return errno == ENOENT ? 0 : -1;
}
+
+ /* Link info exists, so `len' is its length. Null terminate. */
+ lfinfo[len] = 0;
+
+ /* Even if the caller doesn't want the owner info, we still have to
+ read it to determine return value, so allocate it. */
+ if (!owner)
+ {
+ owner = (lock_info_type *) alloca (sizeof (lock_info_type));
+ local_owner = 1;
+ }
+
+ /* Parse USER@HOST.PID. If can't parse, return -1. */
+ /* The USER is everything before the first @. */
+ at = index (lfinfo, '@');
+ dot = rindex (lfinfo, '.');
+ if (!at || !dot) {
+ xfree (lfinfo);
+ return -1;
+ }
+ len = at - lfinfo;
+ owner->user = (char *) xmalloc (len + 1);
+ strncpy (owner->user, lfinfo, len);
+ owner->user[len] = 0;
+
+ /* The PID is everything after the last `.'. */
+ owner->pid = atoi (dot + 1);
+
+ /* The host is everything in between. */
+ len = dot - at - 1;
+ owner->host = (char *) xmalloc (len + 1);
+ strncpy (owner->host, at + 1, len);
+ owner->host[len] = 0;
+
+ /* We're done looking at the link info. */
+ xfree (lfinfo);
+
+ /* On current host? */
+ if (STRINGP (Fsystem_name ())
+ && strcmp (owner->host, XSTRING_DATA(Fsystem_name ())) == 0)
+ {
+ if (owner->pid == getpid ())
+ ret = 2; /* We own it. */
+ else if (owner->pid > 0
+ && (kill (owner->pid, 0) >= 0 || errno == EPERM))
+ ret = 1; /* An existing process on this machine owns it. */
+ /* The owner process is dead or has a strange pid (<=0), so try to
+ zap the lockfile. */
+ else if (unlink (lfname) < 0)
+ ret = -1;
+ else
+ ret = 0;
+ }
+ else
+ { /* If we wanted to support the check for stale locks on remote machines,
+ here's where we'd do it. */
+ ret = 1;
+ }
+
+ /* Avoid garbage. */
+ if (local_owner || ret <= 0)
+ {
+ FREE_LOCK_INFO (*owner);
+ }
+ return ret;
}
-#endif /* !defined HAVE_LONG_FILE_NAMES */
+\f
+/* Lock the lock named LFNAME if possible.
+ Return 0 in that case.
+ Return positive if some other process owns the lock, and info about
+ that process in CLASHER.
+ Return -1 if cannot lock for any other reason. */
-static Lisp_Object
-lock_file_owner_name (CONST char *lfname)
+static int
+lock_if_free (lock_info_type *clasher, char *lfname)
{
- struct stat s;
- struct passwd *the_pw = 0;
+ if (lock_file_1 (lfname, 0) == 0)
+ {
+ int locker;
- if (lstat (lfname, &s) == 0)
- the_pw = getpwuid (s.st_uid);
- return (the_pw == 0 ? Qnil : build_string (the_pw->pw_name));
+ if (errno != EEXIST)
+ return -1;
+
+ locker = current_lock_owner (clasher, lfname);
+ if (locker == 2)
+ {
+ FREE_LOCK_INFO (*clasher);
+ return 0; /* We ourselves locked it. */
+ }
+ else if (locker == 1)
+ return 1; /* Someone else has it. */
+
+ return -1; /* Something's wrong. */
+ }
+ return 0;
}
-
-/* lock_file locks file fn,
+/* lock_file locks file FN,
meaning it serves notice on the world that you intend to edit that file.
This should be done only when about to modify a file-visiting
buffer previously unmodified.
- Do not (normally) call lock_buffer for a buffer already modified,
+ Do not (normally) call this for a buffer already modified,
as either the file is already locked, or the user has already
decided to go ahead without locking.
- When lock_buffer returns, either the lock is locked for us,
+ When this returns, either the lock is locked for us,
or the user has said to go ahead without locking.
- If the file is locked by someone else, lock_buffer calls
+ If the file is locked by someone else, this calls
ask-user-about-lock (a Lisp function) with two arguments,
- the file name and the name of the user who did the locking.
+ the file name and info about the user who did the locking.
This function can signal an error, or return t meaning
take away the lock, or return nil meaning ignore the lock. */
-/* The lock file name is the file name with "/" replaced by "!"
- and put in the Emacs lock directory. */
-/* (ie., /ka/king/junk.tex -> /!/!ka!king!junk.tex). */
-
-/* If HAVE_LONG_FILE_NAMES is not defined, the lock file name is the hex
- representation of a 14-bytes CRC generated from the file name
- and put in the Emacs lock directory (not very nice, but it works).
- (ie., /ka/king/junk.tex -> /!/12a82c62f1c6da). */
-
void
lock_file (Lisp_Object fn)
{
/* dmoore - and can destroy current_buffer and all sorts of other
mean nasty things with pointy teeth. If you call this make sure
you protect things right. */
+ /* Somebody updated the code in this function and removed the previous
+ comment. -slb */
- REGISTER Lisp_Object attack, orig_fn;
- REGISTER char *lfname;
- struct gcpro gcpro1, gcpro2;
- Lisp_Object subject_buf = Qnil;
-
- if (NILP (Vlock_directory) || NILP (Vsuperlock_file))
- return;
- CHECK_STRING (fn);
- CHECK_STRING (Vlock_directory);
+ register Lisp_Object attack, orig_fn;
+ register char *lfname, *locker;
+ lock_info_type lock_info;
+ struct gcpro gcpro1,gcpro2;
+ Lisp_Object subject_buf;
GCPRO2 (fn, subject_buf);
orig_fn = fn;
/* See if this file is visited and has changed on disk since it was
visited. */
- subject_buf = Fget_file_buffer (fn);
- if (!NILP (subject_buf)
- && NILP (Fverify_visited_file_modtime (subject_buf))
- && !NILP (Ffile_exists_p (fn)))
- call1_in_buffer (XBUFFER (subject_buf),
- Qask_user_about_supersession_threat, fn);
+ {
+ subject_buf = get_truename_buffer (orig_fn);
+ if (!NILP (subject_buf)
+ && NILP (Fverify_visited_file_modtime (subject_buf))
+ && !NILP (Ffile_exists_p (fn)))
+ call1_in_buffer (XBUFFER(subject_buf),
+ Qask_user_about_supersession_threat, fn);
+ }
/* Try to lock the lock. */
- if (lock_if_free (lfname) <= 0)
- /* Return now if we have locked it, or if lock dir does not exist */
+ if (lock_if_free (&lock_info, lfname) <= 0)
+ /* Return now if we have locked it, or if lock creation failed */
goto done;
/* Else consider breaking the lock */
+ locker = (char *) alloca (strlen (lock_info.user) + strlen (lock_info.host)
+ + LOCK_PID_MAX + 9);
+ sprintf (locker, "%s@%s (pid %lu)", lock_info.user, lock_info.host,
+ lock_info.pid);
+ FREE_LOCK_INFO (lock_info);
+
attack = call2_in_buffer (BUFFERP (subject_buf) ? XBUFFER (subject_buf) :
- current_buffer, Qask_user_about_lock, fn,
- lock_file_owner_name (lfname));
+ current_buffer, Qask_user_about_lock , fn,
+ build_string (locker));
if (!NILP (attack))
/* User says take the lock */
{
- CHECK_STRING (Vsuperlock_file);
- lock_superlock (lfname);
- lock_file_1 (lfname, O_WRONLY);
- unlink ((char *) XSTRING_DATA (Vsuperlock_file));
+ lock_file_1 (lfname, 1);
goto done;
}
/* User says ignore the lock */
UNGCPRO;
}
-
-/* Lock the lock file named LFNAME.
- If MODE is O_WRONLY, we do so even if it is already locked.
- If MODE is O_WRONLY | O_EXCL | O_CREAT, we do so only if it is free.
- Return 1 if successful, 0 if not. */
-
-static int
-lock_file_1 (CONST char *lfname, int mode)
-{
- REGISTER int fd;
- char buf[20];
-
- if ((fd = open (lfname, mode, 0666)) >= 0)
- {
-#if defined(WINDOWSNT)
- chmod(lfname, _S_IREAD|_S_IWRITE);
-#elif defined(USG)
- chmod (lfname, 0666);
-#else
- fchmod (fd, 0666);
-#endif
- sprintf (buf, "%ld ", (long) getpid ());
- write (fd, buf, strlen (buf));
- close (fd);
- return 1;
- }
- else
- return 0;
-}
-
-/* Lock the lock named LFNAME if possible.
- Return 0 in that case.
- Return positive if lock is really locked by someone else.
- Return -1 if cannot lock for any other reason. */
-
-static int
-lock_if_free (CONST char *lfname)
-{
- REGISTER int clasher;
-
- while (lock_file_1 (lfname, O_WRONLY | O_EXCL | O_CREAT) == 0)
- {
- if (errno != EEXIST)
- return -1;
- clasher = current_lock_owner (lfname);
- if (clasher != 0)
- if (clasher != getpid ())
- return (clasher);
- else return (0);
- /* Try again to lock it */
- }
- return 0;
-}
-
-/* Return the pid of the process that claims to own the lock file LFNAME,
- or 0 if nobody does or the lock is obsolete,
- or -1 if something is wrong with the locking mechanism. */
-
-static int
-current_lock_owner (CONST char *lfname)
-{
- int owner = current_lock_owner_1 (lfname);
- if (owner == 0 && errno == ENOENT)
- return (0);
- /* Is it locked by a process that exists? */
- if (owner != 0 && (kill (owner, 0) >= 0 || errno == EPERM))
- return (owner);
- if (unlink (lfname) < 0)
- return (-1);
- return (0);
-}
-
-static int
-current_lock_owner_1 (CONST char *lfname)
-{
- REGISTER int fd;
- char buf[20];
- int tem;
-
- fd = open (lfname, O_RDONLY, 0666);
- if (fd < 0)
- return 0;
- tem = read (fd, buf, sizeof buf);
- close (fd);
- return (tem <= 0 ? 0 : atoi (buf));
-}
-
-\f
void
unlock_file (Lisp_Object fn)
{
- /* This function can GC. */
- /* dmoore - and can destroy current_buffer and all sorts of other
- mean nasty things with pointy teeth. If you call this make sure
- you protect things right. */
-
- REGISTER char *lfname;
- if (NILP (Vlock_directory) || NILP (Vsuperlock_file)) return;
- CHECK_STRING (fn);
- CHECK_STRING (Vlock_directory);
- CHECK_STRING (Vsuperlock_file);
+ register char *lfname;
fn = Fexpand_file_name (fn, Qnil);
MAKE_LOCK_NAME (lfname, fn);
- lock_superlock (lfname);
-
- if (current_lock_owner_1 (lfname) == getpid ())
+ if (current_lock_owner (0, lfname) == 2)
unlink (lfname);
-
- unlink ((char *) XSTRING_DATA (Vsuperlock_file));
-}
-
-static void
-lock_superlock (CONST char *lfname)
-{
- REGISTER int i, fd;
- DIR *lockdir;
-
- for (i = -20; i < 0 &&
- (fd = open ((char *) XSTRING_DATA (Vsuperlock_file),
- O_WRONLY | O_EXCL | O_CREAT, 0666)) < 0;
- i++)
- {
- if (errno != EEXIST)
- return;
-
- /* This seems to be necessary to prevent Emacs from hanging when the
- competing process has already deleted the superlock, but it's still
- in the NFS cache. So we force NFS to synchronize the cache. */
- lockdir = opendir ((char *) XSTRING_DATA (Vlock_directory));
- if (lockdir)
- closedir (lockdir);
-
- emacs_sleep (1);
- }
- if (fd >= 0)
- {
-#if defined(WINDOWSNT)
- chmod(lfname, _S_IREAD|_S_IWRITE);
-#elif defined(USG)
- chmod ((char *) XSTRING_DATA (Vsuperlock_file), 0666);
-#else
- fchmod (fd, 0666);
-#endif
- write (fd, lfname, strlen (lfname));
- close (fd);
- }
}
void
-unlock_all_files (void)
+unlock_all_files ()
{
- /* This function can GC. */
-
- Lisp_Object tail;
- REGISTER struct buffer *b;
- struct gcpro gcpro1;
+ register Lisp_Object tail;
+ register struct buffer *b;
- GCPRO1 (tail);
- for (tail = Vbuffer_alist; GC_CONSP (tail);
- tail = XCDR (tail))
+ for (tail = Vbuffer_alist; GC_CONSP (tail); tail = XCDR (tail))
{
b = XBUFFER (XCDR (XCAR (tail)));
- if (STRINGP (b->file_truename) &&
- BUF_SAVE_MODIFF (b) < BUF_MODIFF (b))
+ if (STRINGP (b->file_truename) && BUF_SAVE_MODIFF (b) < BUF_MODIFF (b))
unlock_file (b->file_truename);
}
- UNGCPRO;
}
-
\f
-DEFUN ("lock-buffer", Flock_buffer, 0, 1, 0, /*
-Lock FILE, if current buffer is modified.
-FILE defaults to current buffer's visited file,
+DEFUN ("lock-buffer", Flock_buffer, 0, 1, 0, /*
+ Lock FILE, if current buffer is modified.\n\
+FILE defaults to current buffer's visited file,\n\
or else nothing is done if current buffer isn't visiting a file.
*/
- (fn))
+ (file))
{
- /* This function can GC */
- /* dmoore - and can destroy current_buffer and all sorts of other
- mean nasty things with pointy teeth. If you call this make sure
- you protect things right. */
-
- if (NILP (fn))
- fn = current_buffer->file_truename;
- CHECK_STRING (fn);
+ if (NILP (file))
+ file = current_buffer->file_truename;
+ CHECK_STRING (file);
if (BUF_SAVE_MODIFF (current_buffer) < BUF_MODIFF (current_buffer)
- && !NILP (fn))
- lock_file (fn);
+ && !NILP (file))
+ lock_file (file);
return Qnil;
}
return Qnil;
}
-\f
/* Unlock the file visited in buffer BUFFER. */
+
void
unlock_buffer (struct buffer *buffer)
{
}
DEFUN ("file-locked-p", Ffile_locked_p, 0, 1, 0, /*
-Return nil if the FILENAME is not locked,
+ Return nil if the FILENAME is not locked,\n\
t if it is locked by you, else a string of the name of the locker.
*/
- (fn))
+ (filename))
{
- /* This function can GC */
- REGISTER char *lfname;
+ Lisp_Object ret;
+ register char *lfname;
int owner;
+ lock_info_type locker;
- if (NILP (Vlock_directory) || NILP (Vsuperlock_file))
- return Qnil;
- CHECK_STRING (Vlock_directory);
+ filename = Fexpand_file_name (filename, Qnil);
- fn = Fexpand_file_name (fn, Qnil);
+ MAKE_LOCK_NAME (lfname, filename);
- MAKE_LOCK_NAME (lfname, fn);
-
- owner = current_lock_owner (lfname);
+ owner = current_lock_owner (&locker, lfname);
if (owner <= 0)
- return Qnil;
- else if (owner == getpid ())
- return Qt;
+ ret = Qnil;
+ else if (owner == 2)
+ ret = Qt;
+ else
+ ret = build_string (locker.user);
+
+ if (owner > 0)
+ FREE_LOCK_INFO (locker);
- return lock_file_owner_name (lfname);
+ return ret;
}
+\f
+/* Initialization functions. */
+
void
syms_of_filelock (void)
{
defsymbol (&Qask_user_about_lock, "ask-user-about-lock");
}
-void
-vars_of_filelock (void)
-{
- DEFVAR_LISP ("lock-directory", &Vlock_directory /*
-Don't change this
-*/ );
- Vlock_directory = Qnil;
- DEFVAR_LISP ("superlock-file", &Vsuperlock_file /*
-Don't change this
-*/ );
- Vsuperlock_file = Qnil;
-}
-void
-complex_vars_of_filelock (void)
-{
- DEFVAR_LISP ("configure-superlock-file", &Vconfigure_superlock_file /*
-For internal use by the build procedure only.
-configure's idea of what SUPERLOCK-FILE will be.
-*/ );
-#ifdef PATH_SUPERLOCK
- Vconfigure_superlock_file = build_string (PATH_SUPERLOCK);
-#else
- Vconfigure_superlock_file = Qnil;
-#endif
- /* All the rest done dynamically by startup.el */
-}
+#endif /* CLASH_DETECTION */
REGISTER Lisp_Object elt, tem;
CONCHECK_CONS (tail);
elt = XCAR (tail);
- if (CONSP (elt) && (tem = XCAR (elt), EQ_WITH_EBOLA_NOTICE (value, tem)))
+ if (CONSP (elt) && (tem = XCDR (elt), EQ_WITH_EBOLA_NOTICE (value, tem)))
{
if (NILP (prev))
list = XCDR (tail);
{
REGISTER Lisp_Object elt, tem;
elt = XCAR (tail);
- if (CONSP (elt) && (tem = XCAR (elt), EQ_WITH_EBOLA_NOTICE (value, tem)))
+ if (CONSP (elt) && (tem = XCDR (elt), EQ_WITH_EBOLA_NOTICE (value, tem)))
{
if (NILP (prev))
list = XCDR (tail);
}
#else
XtDestroyWidget (w);
+ XFlush (XtDisplay(w)); /* make sure the windows are really gone! */
#endif /* EXTERNAL_WIDGET */
if (FRAME_X_GEOM_FREE_ME_PLEASE (f))
--- /dev/null
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+#include "gifrlib.h"
+
+/******************************************************************************
+* Set up the GifFileType structure for use. This must be called first in any *
+* client program. Then, if custom IO or Error functions are desired, call *
+* GifSetIOFunc/GifSetErrorFunc, then call EGifInitWrite. Else call *
+* EGifOpenFileName or EGifOpenFileHandle for standard IO functions. *
+* If setup fails, a NULL pointer is returned. *
+******************************************************************************/
+GifFileType *GifSetup(void)
+{
+ GifIODataType *GifIO;
+ GifFileType *GifFile;
+
+ if ((GifFile = (GifFileType *) malloc(sizeof(GifFileType))) == NULL)
+ return NULL;
+ memset(GifFile, '\0', sizeof(GifFileType));
+ if ((GifIO = (GifIODataType *) malloc(sizeof(GifIODataType))) == NULL) {
+ free((char *) GifFile);
+ return NULL;
+ }
+ memset(GifIO, '\0', sizeof(GifIODataType));
+ GifFile->GifIO = GifIO;
+ return GifFile;
+}
+
+void GifFree(GifFileType *GifFile)
+{
+ GifFilePrivateType *Private;
+
+ if (GifFile == NULL) return;
+
+ Private = (GifFilePrivateType *) GifFile->Private;
+
+ if (GifFile->SavedImages)
+ FreeSavedImages(GifFile);
+ if (GifFile->Image.ColorMap)
+ FreeMapObject(GifFile->Image.ColorMap);
+ if (GifFile->SColorMap)
+ FreeMapObject(GifFile->SColorMap);
+ if (Private)
+ {
+ free(Private);
+ }
+ if (GifFile->GifIO)
+ free(GifFile->GifIO);
+ free(GifFile);
+}
+
+/****************************************************************************
+* Install the specified ReadFunction into the GifFile specified. *
+****************************************************************************/
+void GifSetReadFunc(GifFileType *GifFile, Gif_rw_func ReadFunc, VoidPtr data)
+{
+ GifIODataType *GifIO = (GifIODataType *)GifFile->GifIO;
+ GifIO->ReadFunc = ReadFunc;
+ GifIO->ReadFunc_data = data;
+}
+
+/****************************************************************************
+* Install the specified WriteFunction into the GifFile specified. *
+****************************************************************************/
+void GifSetWriteFunc(GifFileType *GifFile, Gif_rw_func WriteFunc, VoidPtr data)
+{
+ GifIODataType *GifIO = (GifIODataType *)GifFile->GifIO;
+ GifIO->WriteFunc = WriteFunc;
+ GifIO->WriteFunc_data = data;
+}
+
+/****************************************************************************
+* Install the specified CloseFunction into the GifFile specified. *
+****************************************************************************/
+void GifSetCloseFunc(GifFileType *GifFile, Gif_close_func CloseFunc, VoidPtr data)
+{
+ GifIODataType *GifIO = (GifIODataType *)GifFile->GifIO;
+ GifIO->CloseFunc = CloseFunc;
+ GifIO->CloseFunc_data = data;
+}
+
+/****************************************************************************
+* Install the standard IO funcs into the GifFile, including the FILE info *
+****************************************************************************/
+void GifStdIOInit(GifFileType *GifFile, FILE *file, int filehandle)
+{
+ GifStdIODataType *IOData;
+
+ if ((IOData = (GifStdIODataType*)malloc(sizeof(GifStdIODataType))) == NULL)
+ GifInternError(GifFile, GIF_ERR_NOT_ENOUGH_MEM);
+ IOData->File = file;
+ IOData->FileHandle = filehandle;
+ GifSetReadFunc(GifFile, GifStdRead, IOData);
+ GifSetWriteFunc(GifFile, GifStdWrite, IOData);
+ GifSetCloseFunc(GifFile, GifStdFileClose, IOData);
+}
+
+size_t GifStdRead(GifByteType *buf, size_t size, VoidPtr method_data)
+{
+ GifStdIODataType *IOtype = (GifStdIODataType*)method_data;
+ return (fread(buf, 1, size, IOtype->File));
+}
+
+size_t GifStdWrite(GifByteType *buf, size_t size, VoidPtr method_data)
+{
+ GifStdIODataType *IOtype = (GifStdIODataType*)method_data;
+ return (fwrite(buf, 1, size, IOtype->File));
+}
+
+int GifStdFileClose(VoidPtr method_data)
+{
+ int ret;
+ GifStdIODataType *IOtype = (GifStdIODataType*)method_data;
+ ret = fclose(IOtype->File);
+ if (ret == 0 && IOtype->FileHandle != -1)
+ ret = close(IOtype->FileHandle);
+ return ret;
+}
+
+void GifRead(GifByteType *buf, size_t size, GifFileType *GifFile)
+{
+ GifIODataType *GifIO = (GifIODataType*)GifFile->GifIO;
+ if ((*(GifIO->ReadFunc))(buf, size, GifIO->ReadFunc_data) != size)
+ GifError(GifFile, "Read error!");
+}
+
+void GifWrite(GifByteType *buf, size_t size, GifFileType *GifFile)
+{
+ GifIODataType *GifIO = (GifIODataType*)GifFile->GifIO;
+ if ((*(GifIO->WriteFunc))(buf, size, GifIO->WriteFunc_data) != size)
+ GifError(GifFile, "Write error!");
+}
+
+int GifClose(GifFileType *GifFile)
+{
+ GifIODataType *GifIO = (GifIODataType*)GifFile->GifIO;
+ return ((*(GifIO->CloseFunc))(GifIO->CloseFunc_data));
+}
+
+static char *GifErrorString[14] = {
+ "Failed to open given file", /* D_GIF_ERR_OPEN_FAILED */
+ "Failed to read from given file", /* D_GIF_ERR_READ_FAILED */
+ "Given file is NOT a GIF file", /* D_GIF_ERR_NOT_GIF_FILE */
+ "No Screen Descriptor detected", /* D_GIF_ERR_NO_SCRN_DSCR */
+ "No Image Descriptor detected", /* D_GIF_ERR_NO_IMAG_DSCR */
+ "No global or local color map", /* D_GIF_ERR_NO_COLOR_MAP */
+ "Wrong record type detected", /* D_GIF_ERR_WRONG_RECORD */
+ "#Pixels bigger than Width * Height", /* D_GIF_ERR_DATA_TOO_BIG */
+ "Fail to allocate required memory", /* D_GIF_ERR_NOT_ENOUGH_MEM */
+ "Failed to close given file", /* D_GIF_ERR_CLOSE_FAILED */
+ "Given file was not opened for read", /* D_GIF_ERR_CLOSE_FAILED */
+ "Image is defective, decoding aborted", /* D_GIF_ERR_IMAGE_DEFECT */
+ "Image EOF detected before image complete", /* D_GIF_ERR_EOF_TOO_SOON */
+ "Undefined error!",
+};
+
+const char *GetGifError(int error);
+
+/*****************************************************************************
+* Get the last GIF error in human-readable form. *
+*****************************************************************************/
+const char *GetGifError(int error)
+{
+ char *Err;
+
+ switch(error) {
+ case D_GIF_ERR_OPEN_FAILED:
+ Err = GifErrorString[0];
+ break;
+ case D_GIF_ERR_READ_FAILED:
+ Err = GifErrorString[1];
+ break;
+ case D_GIF_ERR_NOT_GIF_FILE:
+ Err = GifErrorString[2];
+ break;
+ case D_GIF_ERR_NO_SCRN_DSCR:
+ Err = GifErrorString[3];
+ break;
+ case D_GIF_ERR_NO_IMAG_DSCR:
+ Err = GifErrorString[4];
+ break;
+ case D_GIF_ERR_NO_COLOR_MAP:
+ Err = GifErrorString[5];
+ break;
+ case D_GIF_ERR_WRONG_RECORD:
+ Err = GifErrorString[6];
+ break;
+ case D_GIF_ERR_DATA_TOO_BIG:
+ Err = GifErrorString[7];
+ break;
+ case D_GIF_ERR_NOT_ENOUGH_MEM:
+ Err = GifErrorString[8];
+ break;
+ case D_GIF_ERR_CLOSE_FAILED:
+ Err = GifErrorString[9];
+ break;
+ case D_GIF_ERR_NOT_READABLE:
+ Err = GifErrorString[10];
+ break;
+ case D_GIF_ERR_IMAGE_DEFECT:
+ Err = GifErrorString[11];
+ break;
+ case D_GIF_ERR_EOF_TOO_SOON:
+ Err = GifErrorString[12];
+ break;
+ default:
+ Err = GifErrorString[13];
+ break;
+ }
+ return Err;
+}
+
+/******************************
+* These are called internally *
+******************************/
+void GifError(GifFileType *GifFile, const char *err_str)
+{
+ GifIODataType *GifIO = (GifIODataType*)GifFile->GifIO;
+ if (GifIO->ErrorFunc)
+ (*(GifIO->ErrorFunc))(err_str, GifIO->ErrorFunc_data);
+ else
+ fprintf(stderr, "GIF FATAL ERROR: %s", err_str);
+ exit(-10);
+}
+
+void GifWarning(GifFileType *GifFile, const char *err_str)
+{
+ GifIODataType *GifIO = (GifIODataType*)GifFile->GifIO;
+ if (GifIO->WarningFunc)
+ (*(GifIO->WarningFunc))(err_str, GifIO->WarningFunc_data);
+}
+
+void GifInternError(GifFileType *GifFile, int error_num)
+{
+ const char *ErrStr = GetGifError(error_num);
+ GifError(GifFile, ErrStr);
+}
+
+void GifInternWarning(GifFileType *GifFile, int error_num)
+{
+ const char *ErrStr = GetGifError(error_num);
+ GifWarning(GifFile, ErrStr);
+}
+
+void GifSetErrorFunc(GifFileType *GifFile, Gif_error_func ErrorFunc, VoidPtr data)
+{
+ GifIODataType *GifIO = (GifIODataType *)GifFile->GifIO;
+ GifIO->ErrorFunc = ErrorFunc;
+ GifIO->ErrorFunc_data = data;
+}
+
+void GifSetWarningFunc(GifFileType *GifFile, Gif_error_func WarningFunc, VoidPtr data)
+{
+ GifIODataType *GifIO = (GifIODataType *)GifFile->GifIO;
+ GifIO->WarningFunc = WarningFunc;
+ GifIO->WarningFunc_data = data;
+}
--- /dev/null
+/******************************************************************************
+* In order to make life a little bit easier when using the GIF file format, *
+* this library was written, and which does all the dirty work... *
+* *
+* Written by Gershon Elber, Jun. 1989 *
+* Hacks by Eric S. Raymond, Sep. 1992 *
+* and Jareth Hein, Jan. 1998 *
+*******************************************************************************
+* History: *
+* 14 Jun 89 - Version 1.0 by Gershon Elber. *
+* 3 Sep 90 - Version 1.1 by Gershon Elber (Support for Gif89, Unique names). *
+* 15 Sep 90 - Version 2.0 by Eric S. Raymond (Changes to suoport GIF slurp) *
+* 26 Jun 96 - Version 3.0 by Eric S. Raymond (Full GIF89 support) *
+* 19 Jan 98 - Version 3.1 by Jareth Hein (Support for user-defined I/O). *
+******************************************************************************/
+
+#ifndef GIF_LIB_H
+#define GIF_LIB_H
+
+#define GIF_ERROR 0
+#define GIF_OK 1
+
+#ifndef TRUE
+#define TRUE 1
+#define FALSE 0
+#endif
+
+#ifndef NULL
+#define NULL 0
+#endif /* NULL */
+
+#define GIF_FILE_BUFFER_SIZE 16384 /* Files uses bigger buffers than usual. */
+
+typedef int GifBooleanType;
+typedef unsigned char GifPixelType;
+typedef unsigned char * GifRowType;
+typedef unsigned char GifByteType;
+
+#ifdef SYSV
+#define VoidPtr char *
+#else
+#define VoidPtr void *
+#endif /* SYSV */
+
+typedef struct GifColorType {
+ GifByteType Red, Green, Blue;
+} GifColorType;
+
+typedef struct ColorMapObject
+{
+ int ColorCount;
+ int BitsPerPixel;
+ GifColorType *Colors; /* on malloc(3) heap */
+}
+ColorMapObject;
+
+typedef struct GifImageDesc {
+ int Left, Top, Width, Height, /* Current image dimensions. */
+ Interlace; /* Sequential/Interlaced lines. */
+ ColorMapObject *ColorMap; /* The local color map */
+} GifImageDesc;
+
+/* I/O operations. If you roll your own, they need to be semantically equivilent to
+ fread/fwrite, with an additional paramater to hold data local to your method. */
+typedef size_t (*Gif_rw_func)(GifByteType *buffer, size_t size, VoidPtr method_data);
+/* Finish up stream. Non-zero return indicates failure */
+typedef int (*Gif_close_func)(VoidPtr close_data);
+/* Error handling function */
+typedef void (*Gif_error_func)(const char *string, VoidPtr error_data);
+
+typedef struct GifFileType {
+ int SWidth, SHeight, /* Screen dimensions. */
+ SColorResolution, /* How many colors can we generate? */
+ SBackGroundColor; /* I hope you understand this one... */
+ ColorMapObject *SColorMap; /* NULL if it doesn't exist. */
+ int ImageCount; /* Number of current image */
+ GifImageDesc Image; /* Block describing current image */
+ struct SavedImage *SavedImages; /* Use this to accumulate file state */
+ VoidPtr Private; /* Don't mess with this! */
+ VoidPtr GifIO; /* Contains all information for I/O */
+} GifFileType;
+
+typedef enum {
+ UNDEFINED_RECORD_TYPE,
+ SCREEN_DESC_RECORD_TYPE,
+ IMAGE_DESC_RECORD_TYPE, /* Begin with ',' */
+ EXTENSION_RECORD_TYPE, /* Begin with '!' */
+ TERMINATE_RECORD_TYPE /* Begin with ';' */
+} GifRecordType;
+
+/******************************************************************************
+* GIF89 extension function codes *
+******************************************************************************/
+
+#define COMMENT_EXT_FUNC_CODE 0xfe /* comment */
+#define GRAPHICS_EXT_FUNC_CODE 0xf9 /* graphics control */
+#define PLAINTEXT_EXT_FUNC_CODE 0x01 /* plaintext */
+#define APPLICATION_EXT_FUNC_CODE 0xff /* application block */
+
+/******************************************************************************
+* IO related routines. Defined in gif_io.c *
+******************************************************************************/
+GifFileType *GifSetup(void);
+void GifFree(GifFileType *GifFile);
+void GifSetReadFunc (GifFileType *GifFile, Gif_rw_func func, VoidPtr data);
+void GifSetWriteFunc(GifFileType *GifFile, Gif_rw_func func, VoidPtr data);
+void GifSetCloseFunc(GifFileType *GifFile, Gif_close_func func, VoidPtr data);
+
+/******************************************************************************
+* O.K., here are the routines one can access in order to decode GIF file: *
+******************************************************************************/
+
+void DGifOpenFileName(GifFileType *GifFile, const char *GifFileName);
+void DGifOpenFileHandle(GifFileType *GifFile, int GifFileHandle);
+void DGifInitRead(GifFileType *GifFile);
+void DGifSlurp(GifFileType *GifFile);
+void DGifGetScreenDesc(GifFileType *GifFile);
+void DGifGetRecordType(GifFileType *GifFile, GifRecordType *GifType);
+void DGifGetImageDesc(GifFileType *GifFile);
+void DGifGetLine(GifFileType *GifFile, GifPixelType *GifLine, int GifLineLen);
+void DGifGetPixel(GifFileType *GifFile, GifPixelType GifPixel);
+void DGifGetComment(GifFileType *GifFile, char *GifComment);
+void DGifGetExtension(GifFileType *GifFile, int *GifExtCode,
+ GifByteType **GifExtension);
+void DGifGetExtensionNext(GifFileType *GifFile, GifByteType **GifExtension);
+void DGifGetCode(GifFileType *GifFile, int *GifCodeSize,
+ GifByteType **GifCodeBlock);
+void DGifGetCodeNext(GifFileType *GifFile, GifByteType **GifCodeBlock);
+void DGifGetLZCodes(GifFileType *GifFile, int *GifCode);
+int DGifCloseFile(GifFileType *GifFile);
+
+#define D_GIF_ERR_OPEN_FAILED 101 /* And DGif possible errors. */
+#define D_GIF_ERR_READ_FAILED 102
+#define D_GIF_ERR_NOT_GIF_FILE 103
+#define D_GIF_ERR_NO_SCRN_DSCR 104
+#define D_GIF_ERR_NO_IMAG_DSCR 105
+#define D_GIF_ERR_NO_COLOR_MAP 106
+#define D_GIF_ERR_WRONG_RECORD 107
+#define D_GIF_ERR_DATA_TOO_BIG 108
+#define GIF_ERR_NOT_ENOUGH_MEM 109
+#define D_GIF_ERR_NOT_ENOUGH_MEM 109
+#define D_GIF_ERR_CLOSE_FAILED 110
+#define D_GIF_ERR_NOT_READABLE 111
+#define D_GIF_ERR_IMAGE_DEFECT 112
+#define D_GIF_ERR_EOF_TOO_SOON 113
+
+/******************************************************************************
+* O.K., here are the error routines *
+******************************************************************************/
+extern void GifSetErrorFunc(GifFileType *GifFile, Gif_error_func func, VoidPtr data);
+extern void GifSetWarningFunc(GifFileType *GifFile, Gif_error_func func, VoidPtr data);
+extern void GifInternError(GifFileType *GifFile, int errnum);
+extern void GifInternWarning(GifFileType *GifFile, int errnum);
+extern void GifError(GifFileType *GifFile, const char *err_str);
+extern void GifWarning(GifFileType *GifFile, const char *err_str);
+
+/*****************************************************************************
+ *
+ * Everything below this point is new after version 1.2, supporting `slurp
+ * mode' for doing I/O in two big belts with all the image-bashing in core.
+ *
+ *****************************************************************************/
+
+/******************************************************************************
+* Support for the in-core structures allocation (slurp mode). *
+******************************************************************************/
+
+/* This is the in-core version of an extension record */
+typedef struct {
+ int ByteCount;
+ char *Bytes; /* on malloc(3) heap */
+} ExtensionBlock;
+
+/* This holds an image header, its unpacked raster bits, and extensions */
+typedef struct SavedImage {
+ GifImageDesc ImageDesc;
+
+ char *RasterBits; /* on malloc(3) heap */
+
+ int Function;
+ int ExtensionBlockCount;
+ ExtensionBlock *ExtensionBlocks; /* on malloc(3) heap */
+} SavedImage;
+
+extern void ApplyTranslation(SavedImage *Image, GifPixelType Translation[]);
+
+extern void MakeExtension(SavedImage *New, int Function);
+extern int AddExtensionBlock(SavedImage *New, int Length, GifByteType *data);
+extern void FreeExtension(SavedImage *Image);
+
+extern SavedImage *MakeSavedImage(GifFileType *GifFile, SavedImage *CopyFrom);
+extern void FreeSavedImages(GifFileType *GifFile);
+
+/* Common defines used by encode/decode functions */
+
+#define COMMENT_EXT_FUNC_CODE 0xfe /* Extension function code for comment. */
+#define GIF_STAMP "GIFVER" /* First chars in file - GIF stamp. */
+#define GIF_STAMP_LEN sizeof(GIF_STAMP) - 1
+#define GIF_VERSION_POS 3 /* Version first character in stamp. */
+#define GIF87_STAMP "GIF87a" /* First chars in file - GIF stamp. */
+#define GIF89_STAMP "GIF89a" /* First chars in file - GIF stamp. */
+
+#define LZ_MAX_CODE 4095 /* Biggest code possible in 12 bits. */
+#define LZ_BITS 12
+
+#define FILE_STATE_READ 0x01
+#define FILE_STATE_WRITE 0x01
+#define FILE_STATE_SCREEN 0x02
+#define FILE_STATE_IMAGE 0x04
+
+#define FLUSH_OUTPUT 4096 /* Impossible code, to signal flush. */
+#define FIRST_CODE 4097 /* Impossible code, to signal first. */
+#define NO_SUCH_CODE 4098 /* Impossible code, to signal empty. */
+
+#define IS_READABLE(Private) (!(Private->FileState & FILE_STATE_READ))
+#define IS_WRITEABLE(Private) (Private->FileState & FILE_STATE_WRITE)
+
+typedef struct GifFilePrivateType {
+ int FileState,
+ BitsPerPixel, /* Bits per pixel (Codes uses at list this + 1). */
+ ClearCode, /* The CLEAR LZ code. */
+ EOFCode, /* The EOF LZ code. */
+ RunningCode, /* The next code algorithm can generate. */
+ RunningBits,/* The number of bits required to represent RunningCode. */
+ MaxCode1, /* 1 bigger than max. possible code, in RunningBits bits. */
+ LastCode, /* The code before the current code. */
+ CrntCode, /* Current algorithm code. */
+ StackPtr, /* For character stack (see below). */
+ CrntShiftState; /* Number of bits in CrntShiftDWord. */
+ unsigned long CrntShiftDWord; /* For bytes decomposition into codes. */
+ unsigned long PixelCount; /* Number of pixels in image. */
+ GifByteType Buf[256]; /* Compressed input is buffered here. */
+ GifByteType Stack[LZ_MAX_CODE]; /* Decoded pixels are stacked here. */
+ GifByteType Suffix[LZ_MAX_CODE+1]; /* So we can trace the codes. */
+ unsigned int Prefix[LZ_MAX_CODE+1];
+} GifFilePrivateType;
+
+typedef struct GifIODataType {
+ Gif_rw_func ReadFunc, WriteFunc; /* Pointers to the functions that will do the I/O */
+ Gif_close_func CloseFunc;
+ VoidPtr ReadFunc_data; /* data to be passed to the read function */
+ VoidPtr WriteFunc_data; /* data to be passed to the write function */
+ VoidPtr CloseFunc_data; /* data to be passed to the close function */
+ Gif_error_func ErrorFunc; /* MUST NOT RETURN (use lng_jmp or exit)! */
+ Gif_error_func WarningFunc; /* For warning messages (can be ignored) */
+ VoidPtr ErrorFunc_data;
+ VoidPtr WarningFunc_data;
+} GifIODataType;
+
+typedef struct GifStdIODataType {
+ FILE *File;
+ int FileHandle;
+} GifStdIODataType;
+
+/* Install StdIO funcs on FILE into GifFile */
+void GifStdIOInit(GifFileType *GifFile, FILE *file, int filehandle);
+
+/* Error checking reads, writes and closes */
+void GifRead(GifByteType *buf, size_t size, GifFileType *GifFile);
+void GifWrite(GifByteType *buf, size_t size, GifFileType *GifFile);
+int GifClose(GifFileType *GifFile);
+
+/* The default Read and Write functions for files */
+size_t GifStdRead(GifByteType *buf, size_t size, VoidPtr method_data);
+size_t GifStdWrite(GifByteType *buf, size_t size, VoidPtr method_data);
+int GifStdFileClose(VoidPtr method_data);
+
+ColorMapObject *MakeMapObject(int ColorCount, GifColorType *ColorMap);
+void FreeMapObject(ColorMapObject *Object);
+
+
+#endif /* GIF_LIB_H */
#include "lstream.h"
#include "console.h"
#include "device.h"
+#include "faces.h"
#include "glyphs.h"
#include "objects.h"
* GIF *
**********************************************************************/
-#include <gifrlib.h>
+#include "gifrlib.h"
static void
gif_validate (Lisp_Object instantiator)
eip = unwind.eimage;
for (i = 0; i < height; i++)
{
- if (interlace && row >= height)
- row = InterlacedOffset[++pass];
+ if (interlace)
+ if (row >= height) {
+ row = InterlacedOffset[++pass];
+ while (row > height)
+ row = InterlacedOffset[++pass];
+ }
eip = unwind.eimage + (row * width * 3);
for (j = 0; j < width; j++)
{
if (data->instream)
fclose (data->instream);
+ if (data->eimage) xfree(data->eimage);
+
return Qnil;
}
for (y = 0; y < height; y++)
row_pointers[y] = unwind.eimage + (width * 3 * y);
+ {
+ /* if the png specifies a background chunk, go ahead and
+ use it, else use what we can get from the default face. */
+ png_color_16 my_background, *image_background;
+ Lisp_Object bkgd = Qnil;
+
+ my_background.red = 0x7fff;
+ my_background.green = 0x7fff;
+ my_background.blue = 0x7fff;
+ bkgd = FACE_BACKGROUND (Vdefault_face, domain);
+ if (!COLOR_INSTANCEP (bkgd))
+ {
+ warn_when_safe (Qpng, Qinfo, "Couldn't get background color!");
+ }
+ else
+ {
+ struct Lisp_Color_Instance *c;
+ Lisp_Object rgblist;
+
+ c = XCOLOR_INSTANCE (bkgd);
+ rgblist = MAYBE_LISP_DEVMETH (XDEVICE (c->device),
+ color_instance_rgb_components,
+ (c));
+ my_background.red = XINT (XCAR (rgblist));
+ my_background.green = XINT (XCAR (XCDR (rgblist)));
+ my_background.blue = XINT (XCAR (XCDR (XCDR (rgblist))));
+ }
+
+ if (png_get_bKGD (png_ptr, info_ptr, &image_background))
+ png_set_background (png_ptr, image_background,
+ PNG_BACKGROUND_GAMMA_FILE, 1, 1.0);
+ else
+ png_set_background (png_ptr, &my_background,
+ PNG_BACKGROUND_GAMMA_SCREEN, 0, 1.0);
+ }
+
/* Now that we're using EImage, ask for 8bit RGB triples for any type
of image*/
/* convert palatte images to full RGB */
/* we can't handle alpha values */
if (info_ptr->color_type & PNG_COLOR_MASK_ALPHA)
png_set_strip_alpha (png_ptr);
- /* rip out any transparancy layers/colors */
- if (png_get_valid (png_ptr, info_ptr, PNG_INFO_tRNS))
- {
- png_set_expand (png_ptr);
- png_set_strip_alpha (png_ptr);
- }
/* tell libpng to strip 16 bit depth files down to 8 bits */
if (info_ptr->bit_depth == 16)
png_set_strip_16 (png_ptr);
png_set_packing (png_ptr);
}
-#if 1 /* tests? or permanent? */
- {
- /* if the png specifies a background chunk, go ahead and
- use it */
- png_color_16 my_background, *image_background;
-
- /* ### how do I get the background of the current frame? */
- my_background.red = 0x7fff;
- my_background.green = 0x7fff;
- my_background.blue = 0x7fff;
-
- if (png_get_bKGD (png_ptr, info_ptr, &image_background))
- png_set_background (png_ptr, image_background,
- PNG_BACKGROUND_GAMMA_FILE, 1, 1.0);
- else
- png_set_background (png_ptr, &my_background,
- PNG_BACKGROUND_GAMMA_SCREEN, 0, 1.0);
- }
-#endif
png_read_image (png_ptr, row_pointers);
png_read_end (png_ptr, info_ptr);
IMAGE_INSTANCE_PIXMAP_HEIGHT (ii),
SRCCOPY))
{
+ DeleteObject (newbmp);
+ DeleteDC (hdcDst);
return 0;
}
IMAGE_INSTANCE_PIXMAP_HEIGHT (ii),
SRCCOPY))
{
+ DeleteObject (newmask);
+ DeleteDC (hdcDst);
return NULL;
}
Many changes for color work and optimizations by Jareth Hein for 21.0
Switch of GIF/JPEG/PNG to new EImage intermediate code by Jareth Hein for 21.0
TIFF code by Jareth Hein for 21.0
+ GIF/JPEG/PNG/TIFF code moved to new glyph-eimage.c for 21.0
TODO:
Convert images.el to C and stick it in here?
instanced as `mono-pixmap', `color-pixmap', or `pointer'.)
'gif
(A GIF87 or GIF89 image; only if GIF support was compiled into this
- XEmacs. Can be instanced as `color-pixmap'.)
+ XEmacs. NOTE: only the first frame of animated gifs will be displayed.
+ Can be instanced as `color-pixmap'.)
'jpeg
(A JPEG image; only if JPEG support was compiled into this XEmacs.
Can be instanced as `color-pixmap'.)
'png
- (A PNG/GIF24 image; only if PNG support was compiled into this XEmacs.
+ (A PNG image; only if PNG support was compiled into this XEmacs.
Can be instanced as `color-pixmap'.)
'tiff
- (A TIFF image; not currently implemented.)
+ (A TIFF image; only if TIFF support was compiled into this XEmacs.
+ Can be instanced as `color-pixmap'.)
'cursor-font
(One of the standard cursor-font names, such as "watch" or
"right_ptr" under X. Under X, this is, more specifically, any
++name;
if (!(*name))
return Qnil;
- if (*name=='_'&&*(name+1))
- return make_char (tolower(*(name+1)));
+ if (*name=='_' && *(name+1))
+ {
+ int accelerator = (int) (unsigned char) (*(name+1));
+ return make_char (tolower (accelerator));
+ }
}
++name;
}
Bufbyte *to, *from;
Bytecount i;
Bytind new_s1;
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
from = BUF_GPT_ADDR (buf);
to = from + BUF_GAP_SIZE (buf);
/* Adjust markers, and buffer data structure, to put the gap at POS.
POS is where the loop above stopped, which may be what was specified
or may be where a quit was detected. */
- adjust_markers (buf, pos, BI_BUF_GPT (buf), BUF_GAP_SIZE (buf));
- adjust_extents (make_buffer (buf), pos, BI_BUF_GPT (buf),
- BUF_GAP_SIZE (buf));
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_markers (mbuf, pos, BI_BUF_GPT (mbuf), BUF_GAP_SIZE (mbuf));
+ }
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_extents (make_buffer (mbuf), pos, BI_BUF_GPT (mbuf),
+ BUF_GAP_SIZE (mbuf));
+ }
SET_BI_BUF_GPT (buf, pos);
SET_GAP_SENTINEL (buf);
#ifdef ERROR_CHECK_EXTENTS
- sledgehammer_extent_check (make_buffer (buf));
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ sledgehammer_extent_check (make_buffer (mbuf));
+ }
#endif
QUIT;
}
Bufbyte *to, *from;
Bytecount i;
Bytind new_s1;
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
to = BUF_GPT_ADDR (buf);
from = to + BUF_GAP_SIZE (buf);
{
int gsize = BUF_GAP_SIZE (buf);
- adjust_markers (buf, BI_BUF_GPT (buf) + gsize, pos + gsize, - gsize);
- adjust_extents (make_buffer (buf), BI_BUF_GPT (buf) + gsize, pos + gsize,
- - gsize);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_markers (mbuf, BI_BUF_GPT (mbuf) + gsize, pos + gsize, - gsize);
+ }
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_extents (make_buffer (mbuf), BI_BUF_GPT (mbuf) + gsize,
+ pos + gsize, - gsize);
+ }
SET_BI_BUF_GPT (buf, pos);
SET_GAP_SENTINEL (buf);
#ifdef ERROR_CHECK_EXTENTS
- sledgehammer_extent_check (make_buffer (buf));
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ sledgehammer_extent_check (make_buffer (mbuf));
+ }
#endif
}
if (pos == BI_BUF_Z (buf))
static Lisp_Object
change_function_restore (Lisp_Object buffer)
{
- Fset_buffer (buffer);
+ /* We should first reset the variable and then change the buffer,
+ because Fset_buffer() can throw. */
inside_change_hook = 0;
+ Fset_buffer (buffer);
return Qnil;
}
static Lisp_Object
first_change_hook_restore (Lisp_Object buffer)
{
- Fset_buffer (buffer);
in_first_change = 0;
+ Fset_buffer (buffer);
return Qnil;
}
if (!in_first_change)
{
- if (!preparing_for_armageddon &&
- !NILP (symbol_value_in_buffer (Qfirst_change_hook, buffer)))
+ if (!NILP (symbol_value_in_buffer (Qfirst_change_hook, buffer)))
{
int speccount = specpdl_depth ();
record_unwind_protect (first_change_hook_restore, buffer);
signal_before_change (struct buffer *buf, Bufpos start, Bufpos end)
{
/* This function can GC */
- Lisp_Object buffer;
- XSETBUFFER (buffer, buf);
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
if (!inside_change_hook)
{
+ Lisp_Object buffer;
+
/* Are we in a multiple-change session? */
if (buf->text->changes->in_multiple_change &&
buf->text->changes->mc_begin != 0)
/* If buffer is unmodified, run a special hook for that case. */
if (BUF_SAVE_MODIFF (buf) >= BUF_MODIFF (buf))
- signal_first_change (buf);
+ {
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ signal_first_change (mbuf);
+ }
+ }
/* Now in any case run the before-change-functions if any. */
- if (!preparing_for_armageddon &&
- (!NILP (symbol_value_in_buffer (Qbefore_change_functions, buffer)) ||
- /* Obsolete, for compatibility */
- !NILP (symbol_value_in_buffer (Qbefore_change_function, buffer))))
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
{
- int speccount = specpdl_depth ();
- record_unwind_protect (change_function_restore, Fcurrent_buffer ());
- set_buffer_internal (buf);
- inside_change_hook = 1;
- va_run_hook_with_args (Qbefore_change_functions, 2,
- make_int (start), make_int (end));
- /* Obsolete, for compatibility */
- va_run_hook_with_args (Qbefore_change_function, 2,
- make_int (start), make_int (end));
- unbind_to (speccount, Qnil);
+ XSETBUFFER (buffer, mbuf);
+ if (!NILP (symbol_value_in_buffer (Qbefore_change_functions, buffer))
+ /* Obsolete, for compatibility */
+ || !NILP (symbol_value_in_buffer (Qbefore_change_function, buffer)))
+ {
+ int speccount = specpdl_depth ();
+ record_unwind_protect (change_function_restore, Fcurrent_buffer ());
+ set_buffer_internal (buf);
+ inside_change_hook = 1;
+ va_run_hook_with_args (Qbefore_change_functions, 2,
+ make_int (start), make_int (end));
+ /* Obsolete, for compatibility */
+ va_run_hook_with_args (Qbefore_change_function, 2,
+ make_int (start), make_int (end));
+ unbind_to (speccount, Qnil);
+ }
+ }
+
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ XSETBUFFER (buffer, mbuf);
+ report_extent_modification (buffer, start, end,
+ &inside_change_hook, 0);
}
/* Only now do we indicate that the before-change-functions have
been called, in case some function throws out. */
buf->text->changes->mc_begin_signaled = 1;
}
-
- /* #### At this point we should map over extents calling
- modification-hooks, insert-before-hooks and insert-after-hooks
- of relevant extents */
}
/* Signal a change immediately after it happens.
Bufpos new_end)
{
/* This function can GC */
- Lisp_Object buffer;
- XSETBUFFER (buffer, buf);
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
- /* always do this. */
- buffer_signal_changed_region (buf, start, new_end);
- font_lock_maybe_update_syntactic_caches (buf, start, orig_end, new_end);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ /* always do this. */
+ buffer_signal_changed_region (mbuf, start, new_end);
+ }
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ /* #### This seems inefficient. Wouldn't it be better to just
+ keep one cache per base buffer? */
+ font_lock_maybe_update_syntactic_caches (mbuf, start, orig_end, new_end);
+ }
if (!inside_change_hook)
{
+ Lisp_Object buffer;
+
if (buf->text->changes->in_multiple_change &&
buf->text->changes->mc_begin != 0)
{
return; /* after-change-functions signalled when all changes done */
}
- if (!preparing_for_armageddon &&
- (!NILP (symbol_value_in_buffer (Qafter_change_functions, buffer)) ||
- /* Obsolete, for compatibility */
- !NILP (symbol_value_in_buffer (Qafter_change_function, buffer))))
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
{
- int speccount = specpdl_depth ();
- record_unwind_protect (change_function_restore, Fcurrent_buffer ());
- set_buffer_internal (buf);
- inside_change_hook = 1;
- /* The actual after-change functions take slightly
- different arguments than what we were passed. */
- va_run_hook_with_args (Qafter_change_functions, 3,
- make_int (start), make_int (new_end),
- make_int (orig_end - start));
- /* Obsolete, for compatibility */
- va_run_hook_with_args (Qafter_change_function, 3,
- make_int (start), make_int (new_end),
- make_int (orig_end - start));
- unbind_to (speccount, Qnil);
+ XSETBUFFER (buffer, mbuf);
+
+ if (!NILP (symbol_value_in_buffer (Qafter_change_functions, buffer))
+ /* Obsolete, for compatibility */
+ || !NILP (symbol_value_in_buffer (Qafter_change_function, buffer)))
+ {
+ int speccount = specpdl_depth ();
+ record_unwind_protect (change_function_restore, Fcurrent_buffer ());
+ set_buffer_internal (buf);
+ inside_change_hook = 1;
+ /* The actual after-change functions take slightly
+ different arguments than what we were passed. */
+ va_run_hook_with_args (Qafter_change_functions, 3,
+ make_int (start), make_int (new_end),
+ make_int (orig_end - start));
+ /* Obsolete, for compatibility */
+ va_run_hook_with_args (Qafter_change_function, 3,
+ make_int (start), make_int (new_end),
+ make_int (orig_end - start));
+ unbind_to (speccount, Qnil);
+ }
}
- }
- /* #### At this point we should map over extents calling
- some sort of modification hooks of relevant extents */
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ XSETBUFFER (buffer, mbuf);
+ report_extent_modification (buffer, start, new_end,
+ &inside_change_hook, 1);
+ }
+ }
}
/* Call this if you're about to change the region of BUFFER from START
/* dmoore - This function can also kill the buffer buf, the current
buffer, and do anything it pleases. So if you call it, be
careful. */
- Lisp_Object buffer;
+ struct buffer *mbuf;
+ Lisp_Object buffer, bufcons;
struct gcpro gcpro1;
- barf_if_buffer_read_only (buf, start, end);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ barf_if_buffer_read_only (mbuf, start, end);
+ }
/* if this is the first modification, see about locking the buffer's
file */
Vdeactivate_mark = Qt;
#endif
- buf->point_before_scroll = Qnil;
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ mbuf->point_before_scroll = Qnil;
+ }
}
\f
Bytind ind;
Charcount cclen;
int move_point = 0;
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
/* Defensive steps just in case a buffer gets deleted and a calling
function doesn't notice it. */
if ((length + BUF_Z (buf)) > EMACS_INT_MAX)
error ("Maximum buffer size exceeded");
- /* theoretically not necessary -- caller should GCPRO */
+ /* theoretically not necessary -- caller should GCPRO.
+ #### buffer_insert_from_buffer_1() doesn't! */
GCPRO1 (reloc);
prepare_to_modify_buffer (buf, pos, pos, !(flags & INSDEL_NO_LOCKING));
insert_invalidate_line_number_cache (buf, pos, nonreloc + offset, length);
- record_insert (buf, pos, cclen);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ record_insert (mbuf, pos, cclen);
+ }
+
BUF_MODIFF (buf)++;
MARK_BUFFERS_CHANGED;
SET_BUF_GAP_SIZE (buf, BUF_GAP_SIZE (buf) - length);
SET_BI_BUF_GPT (buf, BI_BUF_GPT (buf) + length);
- SET_BOTH_BUF_ZV (buf, BUF_ZV (buf) + cclen, BI_BUF_ZV (buf) + length);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ SET_BOTH_BUF_ZV (mbuf, BUF_ZV (mbuf) + cclen, BI_BUF_ZV (mbuf) + length);
+ }
SET_BOTH_BUF_Z (buf, BUF_Z (buf) + cclen, BI_BUF_Z (buf) + length);
SET_GAP_SENTINEL (buf);
buffer_mule_signal_inserted_region (buf, pos, length, cclen);
#endif
- process_extents_for_insertion (make_buffer (buf), ind, length);
- /* We know the gap is at IND so the cast is OK. */
- adjust_markers_for_insert (buf, (Memind) ind, length);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ process_extents_for_insertion (make_buffer (mbuf), ind, length);
+ }
+
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ /* We know the gap is at IND so the cast is OK. */
+ adjust_markers_for_insert (mbuf, (Memind) ind, length);
+ }
/* Point logically doesn't move, but may need to be adjusted because
it's a byte index. point-marker doesn't change because it's a
memory index. */
- if (BI_BUF_PT (buf) > ind)
- JUST_SET_POINT (buf, BUF_PT (buf) + cclen, BI_BUF_PT (buf) + length);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ if (BI_BUF_PT (mbuf) > ind)
+ JUST_SET_POINT (mbuf, BUF_PT (mbuf) + cclen,
+ BI_BUF_PT (mbuf) + length);
+ }
/* Well, point might move. */
if (move_point)
BI_BUF_SET_PT (buf, ind + length);
if (STRINGP (reloc))
- splice_in_string_extents (reloc, buf, ind, length, offset);
+ {
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ splice_in_string_extents (reloc, mbuf, ind, length, offset);
+ }
+ }
if (flags & INSDEL_BEFORE_MARKERS)
{
- /* ind - 1 is correct because the FROM argument is exclusive.
- I formerly used DEC_BYTIND() but that caused problems at the
- beginning of the buffer. */
- adjust_markers (buf, ind - 1, ind, length);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ /* ind - 1 is correct because the FROM argument is exclusive.
+ I formerly used DEC_BYTIND() but that caused problems at the
+ beginning of the buffer. */
+ adjust_markers (mbuf, ind - 1, ind, length);
+ }
}
signal_after_change (buf, pos, pos, pos + cclen);
int flags)
{
/* This function can GC */
+#ifdef ERROR_CHECK_TYPECHECK
assert (STRINGP (str));
+#endif
return buffer_insert_string_1 (buf, pos, 0, str, 0,
XSTRING_LENGTH (str),
flags);
int flags)
{
/* This function can GC */
-
CONST char *translated = GETTEXT (s);
return buffer_insert_string_1 (buf, pos, (CONST Bufbyte *) translated, Qnil,
0, strlen (translated), flags);
{
/* This function can GC */
Bufbyte str[MAX_EMCHAR_LEN];
- Bytecount len;
-
- len = set_charptr_emchar (str, ch);
+ Bytecount len = set_charptr_emchar (str, ch);
return buffer_insert_string_1 (buf, pos, str, Qnil, 0, len, flags);
}
Bytind bi_from, bi_to;
Bytecount bc_numdel;
EMACS_INT shortage;
- Lisp_Object bufobj;
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
/* Defensive steps just in case a buffer gets deleted and a calling
function doesn't notice it. */
if ((numdel = to - from) <= 0)
return;
- XSETBUFFER (bufobj, buf);
-
/* Redisplay needs to know if a newline was in the deleted region.
If we've already marked the changed region as having a deleted
newline there is no use in performing the check. */
{
scan_buffer (buf, '\n', from, to, 1, &shortage, 1);
if (!shortage)
- buf->changes->newline_was_deleted = 1;
+ {
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ mbuf->changes->newline_was_deleted = 1;
+ }
+ }
}
bi_from = bufpos_to_bytind (buf, from);
{
/* avoid moving the gap just to delete from the bottom. */
- record_delete (buf, from, numdel);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ record_delete (mbuf, from, numdel);
+ }
BUF_MODIFF (buf)++;
MARK_BUFFERS_CHANGED;
- /* ### Point used to be modified here, but this causes problems with MULE,
- as point is used to calculate bytinds, and if the offset in bc_numdel causes
- point to move to a non first-byte location, causing some other function to
- throw an assertion in ASSERT_VALID_BYTIND. I've moved the code to right after
- the other movements and adjustments, but before the gap is moved.
- -- jh 970813 */
+ /* #### Point used to be modified here, but this causes problems
+ with MULE, as point is used to calculate bytinds, and if the
+ offset in bc_numdel causes point to move to a non first-byte
+ location, causing some other function to throw an assertion
+ in ASSERT_VALID_BYTIND. I've moved the code to right after
+ the other movements and adjustments, but before the gap is
+ moved. -- jh 970813 */
/* Detach any extents that are completely within the range [FROM, TO],
if the extents are detachable.
- This must come AFTER record_delete(), so that the appropriate extents
- will be present to be recorded, and BEFORE the gap size is increased,
- as otherwise we will be confused about where the extents end. */
- process_extents_for_deletion (bufobj, bi_from, bi_to, 0);
+ This must come AFTER record_delete(), so that the appropriate
+ extents will be present to be recorded, and BEFORE the gap
+ size is increased, as otherwise we will be confused about
+ where the extents end. */
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ process_extents_for_deletion (make_buffer (mbuf), bi_from, bi_to, 0);
+ }
- /* Relocate all markers pointing into the new, larger gap
- to point at the end of the text before the gap. */
- adjust_markers (buf,
- (bi_to + BUF_GAP_SIZE (buf)),
- (bi_to + BUF_GAP_SIZE (buf)),
- (- bc_numdel));
+ /* Relocate all markers pointing into the new, larger gap to
+ point at the end of the text before the gap. */
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_markers (mbuf,
+ (bi_to + BUF_GAP_SIZE (mbuf)),
+ (bi_to + BUF_GAP_SIZE (mbuf)),
+ (- bc_numdel));
+ }
- /* Relocate any extent endpoints just like markers. */
- adjust_extents_for_deletion (bufobj, bi_from, bi_to,
- BUF_GAP_SIZE (buf), bc_numdel, 0);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ /* Relocate any extent endpoints just like markers. */
+ adjust_extents_for_deletion (make_buffer (mbuf), bi_from, bi_to,
+ BUF_GAP_SIZE (mbuf), bc_numdel, 0);
+ }
- /* Relocate point as if it were a marker. */
- if (bi_from < BI_BUF_PT (buf))
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
{
- if (BI_BUF_PT (buf) < bi_to)
- JUST_SET_POINT (buf, from, bi_from);
- else
- JUST_SET_POINT (buf, BUF_PT (buf) - numdel,
- BI_BUF_PT (buf) - bc_numdel);
+ /* Relocate point as if it were a marker. */
+ if (bi_from < BI_BUF_PT (mbuf))
+ {
+ if (BI_BUF_PT (mbuf) < bi_to)
+ JUST_SET_POINT (mbuf, from, bi_from);
+ else
+ JUST_SET_POINT (mbuf, BUF_PT (mbuf) - numdel,
+ BI_BUF_PT (mbuf) - bc_numdel);
+ }
}
SET_BUF_END_GAP_SIZE (buf, BUF_END_GAP_SIZE (buf) + bc_numdel);
- SET_BOTH_BUF_ZV (buf, BUF_ZV (buf) - numdel, BI_BUF_ZV (buf) - bc_numdel);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ SET_BOTH_BUF_ZV (mbuf, BUF_ZV (mbuf) - numdel,
+ BI_BUF_ZV (mbuf) - bc_numdel);
+ }
SET_BOTH_BUF_Z (buf, BUF_Z (buf) - numdel, BI_BUF_Z (buf) - bc_numdel);
SET_GAP_SENTINEL (buf);
}
if (bi_from > BI_BUF_GPT (buf))
gap_right (buf, bi_from);
- record_delete (buf, from, numdel);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ record_delete (mbuf, from, numdel);
+ }
BUF_MODIFF (buf)++;
MARK_BUFFERS_CHANGED;
- /* ### Point used to be modified here, but this causes problems with MULE,
- as point is used to calculate bytinds, and if the offset in bc_numdel causes
- point to move to a non first-byte location, causing some other function to
- throw an assertion in ASSERT_VALID_BYTIND. I've moved the code to right after
- the other movements and adjustments, but before the gap is moved.
- -- jh 970813 */
+ /* #### Point used to be modified here, but this causes problems
+ with MULE, as point is used to calculate bytinds, and if the
+ offset in bc_numdel causes point to move to a non first-byte
+ location, causing some other function to throw an assertion
+ in ASSERT_VALID_BYTIND. I've moved the code to right after
+ the other movements and adjustments, but before the gap is
+ moved. -- jh 970813 */
/* Detach any extents that are completely within the range [FROM, TO],
if the extents are detachable.
This must come AFTER record_delete(), so that the appropriate extents
will be present to be recorded, and BEFORE the gap size is increased,
as otherwise we will be confused about where the extents end. */
- process_extents_for_deletion (bufobj, bi_from, bi_to, 0);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ process_extents_for_deletion (make_buffer (mbuf), bi_from, bi_to, 0);
+ }
- /* Relocate all markers pointing into the new, larger gap
- to point at the end of the text before the gap. */
- adjust_markers (buf,
- (bi_to + BUF_GAP_SIZE (buf)),
- (bi_to + BUF_GAP_SIZE (buf)),
- (- bc_numdel - BUF_GAP_SIZE (buf)));
+ /* Relocate all markers pointing into the new, larger gap to
+ point at the end of the text before the gap. */
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_markers (mbuf,
+ (bi_to + BUF_GAP_SIZE (mbuf)),
+ (bi_to + BUF_GAP_SIZE (mbuf)),
+ (- bc_numdel - BUF_GAP_SIZE (mbuf)));
+ }
/* Relocate any extent endpoints just like markers. */
- adjust_extents_for_deletion (bufobj, bi_from, bi_to, BUF_GAP_SIZE (buf),
- bc_numdel, BUF_GAP_SIZE (buf));
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ adjust_extents_for_deletion (make_buffer (mbuf), bi_from, bi_to,
+ BUF_GAP_SIZE (mbuf),
+ bc_numdel, BUF_GAP_SIZE (mbuf));
+ }
- /* Relocate point as if it were a marker. */
- if (bi_from < BI_BUF_PT (buf))
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
{
- if (BI_BUF_PT (buf) < bi_to)
- JUST_SET_POINT (buf, from, bi_from);
- else
- JUST_SET_POINT (buf, BUF_PT (buf) - numdel,
- BI_BUF_PT (buf) - bc_numdel);
+ /* Relocate point as if it were a marker. */
+ if (bi_from < BI_BUF_PT (mbuf))
+ {
+ if (BI_BUF_PT (mbuf) < bi_to)
+ JUST_SET_POINT (mbuf, from, bi_from);
+ else
+ JUST_SET_POINT (mbuf, BUF_PT (mbuf) - numdel,
+ BI_BUF_PT (mbuf) - bc_numdel);
+ }
}
SET_BUF_GAP_SIZE (buf, BUF_GAP_SIZE (buf) + bc_numdel);
- SET_BOTH_BUF_ZV (buf, BUF_ZV (buf) - numdel, BI_BUF_ZV (buf) - bc_numdel);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ SET_BOTH_BUF_ZV (mbuf, BUF_ZV (mbuf) - numdel,
+ BI_BUF_ZV (mbuf) - bc_numdel);
+ }
SET_BOTH_BUF_Z (buf, BUF_Z (buf) - numdel, BI_BUF_Z (buf) - bc_numdel);
SET_BI_BUF_GPT (buf, bi_from);
SET_GAP_SENTINEL (buf);
#endif
#ifdef ERROR_CHECK_EXTENTS
- sledgehammer_extent_check (bufobj);
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ sledgehammer_extent_check (make_buffer (mbuf));
+ }
#endif
signal_after_change (buf, from, to, from);
/* Replace the character at POS in buffer B with CH. */
void
-buffer_replace_char (struct buffer *b, Bufpos pos, Emchar ch,
+buffer_replace_char (struct buffer *buf, Bufpos pos, Emchar ch,
int not_real_change, int force_lock_check)
{
/* This function can GC */
/* Defensive steps just in case a buffer gets deleted and a calling
function doesn't notice it. */
- if (!BUFFER_LIVE_P (b))
+ if (!BUFFER_LIVE_P (buf))
return;
- curlen = BUF_CHARPTR_COPY_CHAR (b, pos, curstr);
+ curlen = BUF_CHARPTR_COPY_CHAR (buf, pos, curstr);
newlen = set_charptr_emchar (newstr, ch);
if (curlen == newlen)
{
+ struct buffer *mbuf;
+ Lisp_Object bufcons;
+
/* then we can just replace the text. */
- prepare_to_modify_buffer (b, pos, pos + 1,
+ prepare_to_modify_buffer (buf, pos, pos + 1,
!not_real_change || force_lock_check);
/* Defensive steps in case the before-change-functions fuck around */
- if (!BUFFER_LIVE_P (b))
+ if (!BUFFER_LIVE_P (buf))
/* Bad bad pre-change function. */
return;
/* Make args be valid again. prepare_to_modify_buffer() might have
modified the buffer. */
- if (pos < BUF_BEGV (b))
- pos = BUF_BEGV (b);
- if (pos >= BUF_ZV (b))
- pos = BUF_ZV (b) - 1;
- if (pos < BUF_BEGV (b))
+ if (pos < BUF_BEGV (buf))
+ pos = BUF_BEGV (buf);
+ if (pos >= BUF_ZV (buf))
+ pos = BUF_ZV (buf) - 1;
+ if (pos < BUF_BEGV (buf))
/* no more characters in buffer! */
return;
- if (BUF_FETCH_CHAR (b, pos) == '\n')
- b->changes->newline_was_deleted = 1;
+ if (BUF_FETCH_CHAR (buf, pos) == '\n')
+ {
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ mbuf->changes->newline_was_deleted = 1;
+ }
+ }
MARK_BUFFERS_CHANGED;
if (!not_real_change)
{
- record_change (b, pos, 1);
- BUF_MODIFF (b)++;
+ MAP_INDIRECT_BUFFERS (buf, mbuf, bufcons)
+ {
+ record_change (mbuf, pos, 1);
+ }
+ BUF_MODIFF (buf)++;
}
- memcpy (BUF_BYTE_ADDRESS (b, pos), newstr, newlen);
- signal_after_change (b, pos, pos + 1, pos + 1);
+ memcpy (BUF_BYTE_ADDRESS (buf, pos), newstr, newlen);
+
+ signal_after_change (buf, pos, pos + 1, pos + 1);
/* We do not have to adjust the Mule data; we just replaced a
character with another of the same number of bytes. */
* point. Point will drift backward by one position and stay
* there otherwise.
*/
- int movepoint = (pos == BUF_PT (b) - 1);
+ int movepoint = (pos == BUF_PT (buf) - 1);
- buffer_delete_range (b, pos, pos + 1, 0);
+ buffer_delete_range (buf, pos, pos + 1, 0);
/* Defensive steps in case the before-change-functions fuck around */
- if (!BUFFER_LIVE_P (b))
+ if (!BUFFER_LIVE_P (buf))
/* Bad bad pre-change function. */
return;
/* Make args be valid again. prepare_to_modify_buffer() might have
modified the buffer. */
- if (pos < BUF_BEGV (b))
- pos = BUF_BEGV (b);
- if (pos >= BUF_ZV (b))
- pos = BUF_ZV (b) - 1;
- if (pos < BUF_BEGV (b))
+ if (pos < BUF_BEGV (buf))
+ pos = BUF_BEGV (buf);
+ if (pos >= BUF_ZV (buf))
+ pos = BUF_ZV (buf) - 1;
+ if (pos < BUF_BEGV (buf))
/* no more characters in buffer! */
return;
/*
* insertion, which we must do if the deletion moved point
* backward so that it now equals the insertion point.
*/
- buffer_insert_string_1 (b, (movepoint ? -1 : pos),
+ buffer_insert_string_1 (buf, (movepoint ? -1 : pos),
newstr, Qnil, 0, newlen, 0);
}
}
}
void
-init_buffer_text (struct buffer *b, int indirect_p)
+init_buffer_text (struct buffer *b)
{
- if (!indirect_p)
+ if (!b->base_buffer)
{
SET_BUF_GAP_SIZE (b, 20);
BUFFER_ALLOC (b->text->beg, BUF_GAP_SIZE (b) + BUF_END_SENTINEL_SIZE);
}
}
#endif /* MULE */
+ b->text->line_number_cache = Qnil;
BUF_MODIFF (b) = 1;
BUF_SAVE_MODIFF (b) = 1;
}
void
-uninit_buffer_text (struct buffer *b, int indirect_p)
+uninit_buffer_text (struct buffer *b)
{
- if (!indirect_p)
+ if (!b->base_buffer)
{
BUFFER_FREE (b->text->beg);
xfree (b->text->changes);
void barf_if_buffer_read_only (struct buffer *buf, Bufpos from,
Bufpos to);
-void init_buffer_text (struct buffer *b, int indirect_p);
-void uninit_buffer_text (struct buffer *b, int indirect_p);
+void init_buffer_text (struct buffer *b);
+void uninit_buffer_text (struct buffer *b);
#endif /* _XEMACS_INSDEL_H_ */
This keymap works like `function-key-map', but comes after that,
and applies even for keys that have ordinary bindings.
*/ );
+ Vkey_translation_map = Qnil;
DEFVAR_LISP ("vertical-divider-map", &Vvertical_divider_map /*
Keymap which handles mouse clicks over vertical dividers.
*/ );
+ Vvertical_divider_map = Qnil;
DEFVAR_INT ("keymap-tick", &keymap_tick /*
Incremented for each change to any keymap.
#define LINE_NUMBER_LARGE_STRING 256
/* To be used only when you *know* the cache has been allocated! */
-#define LINE_NUMBER_RING(b) (XCAR ((b)->line_number_cache))
-#define LINE_NUMBER_BEGV(b) (XCDR ((b)->line_number_cache))
+#define LINE_NUMBER_RING(b) (XCAR ((b)->text->line_number_cache))
+#define LINE_NUMBER_BEGV(b) (XCDR ((b)->text->line_number_cache))
/* Initialize the cache. Cache is (in pseudo-BNF):
Line number cache should never, ever, be visible to Lisp (because
destructively modifying its elements can cause crashes.) Debug it
- using debug_print (current_buffer->last_number_cache). */
+ using debug_print (current_buffer->text->last_number_cache). */
static void
allocate_line_number_cache (struct buffer *b)
{
- b->line_number_cache = Fcons (make_vector (LINE_NUMBER_RING_SIZE, Qnil),
- Qzero);
+ b->text->line_number_cache = Fcons (make_vector (LINE_NUMBER_RING_SIZE, Qnil),
+ Qzero);
narrow_line_number_cache (b);
}
void
narrow_line_number_cache (struct buffer *b)
{
- if (NILP (b->line_number_cache))
+ if (NILP (b->text->line_number_cache))
return;
if (BUF_BEG (b) == BUF_BEGV (b))
insert_invalidate_line_number_cache (struct buffer *b, Bufpos pos,
CONST Bufbyte *nonreloc, Bytecount length)
{
- if (NILP (b->line_number_cache))
+ if (NILP (b->text->line_number_cache))
return;
if (length > LINE_NUMBER_LARGE_STRING
void
delete_invalidate_line_number_cache (struct buffer *b, Bufpos from, Bufpos to)
{
- if (NILP (b->line_number_cache))
+ if (NILP (b->text->line_number_cache))
return;
if ((to - from) > LINE_NUMBER_LARGE_STRING)
if (cachep)
{
- if (NILP (b->line_number_cache))
+ if (NILP (b->text->line_number_cache))
allocate_line_number_cache (b);
/* If we don't know the line number of BUF_BEGV, calculate it now. */
if (XINT (LINE_NUMBER_BEGV (b)) == -1)
EXFUN (Fsymbol_name, 1);
EXFUN (Fsymbol_plist, 1);
EXFUN (Fsymbol_value, 1);
+EXFUN (Fsystem_name, 0);
EXFUN (Fthrow, 2);
EXFUN (Ftimes, MANY);
EXFUN (Ftruncate, 1);
/* Whether Fload_internal() should ignore .elc files when no suffix is given */
int load_ignore_elc_files;
-/* Directory in which the sources were found. */
-Lisp_Object Vsource_directory;
-
/* Search path for files to be loaded. */
Lisp_Object Vload_path;
if (purify_flag && noninteractive)
{
if (EQ (last_file_loaded, file))
- message_append (" (%d)", purespace_usage() - pure_usage);
+ message_append (" (%ld)",
+ (unsigned long) (purespace_usage() - pure_usage));
else
- message ("Loading %s ...done (%d)", XSTRING_DATA (file),
- purespace_usage() - pure_usage);
+ message ("Loading %s ...done (%ld)", XSTRING_DATA (file),
+ (unsigned long) (purespace_usage() - pure_usage));
}
/*#endif / * DEBUG_XEMACS */
*/ );
load_force_doc_strings = 0;
- DEFVAR_LISP ("source-directory", &Vsource_directory /*
-Directory in which XEmacs sources were found when XEmacs was built.
-You cannot count on them to still be there!
-*/ );
- Vsource_directory = Qnil;
-
/* See read_escape(). */
#if 0
/* Used to be named `puke-on-fsf-keys' */
int repeat;
if (NILP (con->defining_kbd_macro))
- error ("Not defining kbd macro.");
+ error ("Not defining kbd macro");
if (NILP (arg))
repeat = -1;
final = indirect_function (macro, 1);
if (!STRINGP (final) && !VECTORP (final))
- error ("Keyboard macros must be strings or vectors.");
+ error ("Keyboard macros must be strings or vectors");
tem = Fcons (Vexecuting_macro, make_int (executing_macro_index));
record_unwind_protect (pop_kbd_macro, tem);
b->mark = Fmake_marker ();
BUF_MARKERS (b) = 0;
b->point_marker = Fmake_marker ();
- Fset_marker (b->point_marker, make_int (1), buf);
+ Fset_marker (b->point_marker,
+ /* For indirect buffers, point is already set. */
+ b->base_buffer ? make_int (BUF_PT (b)) : make_int (1),
+ buf);
}
void
* "Left Flush\tRight Flush"
*/
static char*
-displayable_menu_item (struct gui_item* pgui_item)
+displayable_menu_item (struct gui_item* pgui_item, int bar_p)
{
/* We construct the name in a static buffer. That's fine, beause
menu items longer than 128 chars are probably programming errors,
/* Left flush part of the string */
ll = gui_item_display_flush_left (pgui_item, buf, MAX_MENUITEM_LENGTH);
- /* Right flush part */
- assert (MAX_MENUITEM_LENGTH > ll + 1);
- lr = gui_item_display_flush_right (pgui_item, buf + ll + 1,
- MAX_MENUITEM_LENGTH - ll - 1);
- if (lr)
- buf [ll] = '\t';
+ /* Right flush part, unless we're at the top-level where it's not allowed */
+ if (!bar_p)
+ {
+ assert (MAX_MENUITEM_LENGTH > ll + 1);
+ lr = gui_item_display_flush_right (pgui_item, buf + ll + 1,
+ MAX_MENUITEM_LENGTH - ll - 1);
+ if (lr)
+ buf [ll] = '\t';
+ }
return buf;
}
static void
populate_menu_add_item (HMENU menu, Lisp_Object path,
- Lisp_Object hash_tab, Lisp_Object item, int flush_right)
+ Lisp_Object hash_tab, Lisp_Object item,
+ int flush_right, int bar_p)
{
MENUITEMINFO item_info;
submenu = create_empty_popup_menu();
item_info.fMask |= MIIM_SUBMENU;
- item_info.dwTypeData = displayable_menu_item (&gui_item);
+ item_info.dwTypeData = displayable_menu_item (&gui_item, bar_p);
item_info.hSubMenu = submenu;
if (!(item_info.fState & MFS_GRAYED))
item_info.wID = (UINT) XINT(id);
item_info.fType |= MFT_STRING;
- item_info.dwTypeData = displayable_menu_item (&gui_item);
+ item_info.dwTypeData = displayable_menu_item (&gui_item, bar_p);
UNGCPRO; /* gui_item */
}
else
{
- signal_simple_error ("Mailformed menu item descriptor", item);
+ signal_simple_error ("Malformed menu item descriptor", item);
}
if (flush_right)
}
else if (populate_p)
populate_menu_add_item (menu, path, hash_tab,
- XCAR (item_desc), flush_right);
+ XCAR (item_desc), flush_right, bar_p);
else
checksum = HASH2 (checksum,
checksum_menu_item (XCAR (item_desc)));
}
#endif /* LWLIB_MENUBARS_LUCID || LWLIB_MENUBARS_MOTIF */
+#if 0
+/* #### Sort of a hack needed to process Vactivate_menubar_hook
+ correctly wrt buffer-local values. A correct solution would
+ involve adding a callback mechanism to run_hook(). This function
+ is currently unused. */
+static int
+my_run_hook (Lisp_Object hooksym, int allow_global_p)
+{
+ /* This function can GC */
+ Lisp_Object tail;
+ Lisp_Object value = Fsymbol_value (hooksym);
+ int changes = 0;
+
+ if (!NILP (value) && (!CONSP (value) || EQ (XCAR (value), Qlambda)))
+ return !EQ (call0 (value), Qt);
+
+ EXTERNAL_LIST_LOOP (tail, value)
+ {
+ if (allow_global_p && EQ (XCAR (tail), Qt))
+ changes |= my_run_hook (Fdefault_value (hooksym), 0);
+ if (!EQ (call0 (XCAR (tail)), Qt))
+ changes = 1;
+ }
+ return changes;
+}
+#endif
+
/* The order in which callbacks are run is funny to say the least.
It's sometimes tricky to avoid running a callback twice, and to
pre_activate_callback (Widget widget, LWLIB_ID id, XtPointer client_data)
{
/* This function can GC */
- struct gcpro gcpro1;
struct device *d = get_device_from_display (XtDisplay (widget));
struct frame *f = x_any_window_to_frame (d, XtWindow (widget));
- Lisp_Object rest = Qnil;
Lisp_Object frame;
- int any_changes = 0;
int count;
/* set in lwlib to the time stamp associated with the most recent menu
replace_widget_value_tree (hack_wv, wv->contents);
free_popup_widget_value_tree (wv);
}
+ else if (!POPUP_DATAP (FRAME_MENUBAR_DATA (f)))
+ return;
else
{
- if (!POPUP_DATAP (FRAME_MENUBAR_DATA (f)))
- return;
+#if 0 /* Unused, see comment below. */
+ int any_changes;
+
/* #### - this menubar update mechanism is expensively anti-social and
the activate-menubar-hook is now mostly obsolete. */
- /* make the activate-menubar-hook be a list of functions, not a single
- function, just to simplify things. */
- if (!NILP (Vactivate_menubar_hook) &&
- (!CONSP (Vactivate_menubar_hook) ||
- EQ (XCAR (Vactivate_menubar_hook), Qlambda)))
- Vactivate_menubar_hook = Fcons (Vactivate_menubar_hook, Qnil);
-
- GCPRO1 (rest);
- for (rest = Vactivate_menubar_hook; !NILP (rest); rest = Fcdr (rest))
- if (!EQ (call0 (XCAR (rest)), Qt))
- any_changes = 1;
-#if 0
+ any_changes = my_run_hook (Qactivate_menubar_hook, 1);
+
/* #### - It is necessary to *ALWAYS* call set_frame_menubar() now that
incremental menus are implemented. If a subtree of a menu has been
updated incrementally (a destructive operation), then that subtree
that an INCREMENTAL_TYPE widget_value can be recreated... Hmmmmm. */
if (any_changes ||
!XFRAME_MENUBAR_DATA (f)->menubar_contents_up_to_date)
-#endif
set_frame_menubar (f, 1, 0);
+#else
+ run_hook (Qactivate_menubar_hook);
+ set_frame_menubar (f, 1, 0);
+#endif
DEVICE_X_MOUSE_TIMESTAMP (XDEVICE (FRAME_DEVICE (f))) =
DEVICE_X_GLOBAL_MOUSE_TIMESTAMP (XDEVICE (FRAME_DEVICE (f))) =
x_focus_timestamp_really_sucks_fix_me_better;
- UNGCPRO;
}
}
static unsigned char buf[KEYTOSTRSIZE];
static char **warning;
-static int Vcanna_empty_info, Vcanna_through_info;
-static int Vcanna_underline;
-static int Vcanna_inhibit_hankakukana;
+static int canna_empty_info, canna_through_info;
+static int canna_underline;
+static int canna_inhibit_hankakukana;
static Lisp_Object Vcanna_kakutei_string;
static Lisp_Object Vcanna_kakutei_yomi;
static Lisp_Object Vcanna_kakutei_romaji;
static Lisp_Object Vcanna_henkan_string;
-static int Vcanna_henkan_length;
-static int Vcanna_henkan_revPos;
-static int Vcanna_henkan_revLen;
+static int canna_henkan_length;
+static int canna_henkan_revPos;
+static int canna_henkan_revLen;
static Lisp_Object Vcanna_ichiran_string;
-static int Vcanna_ichiran_length;
-static int Vcanna_ichiran_revPos;
-static int Vcanna_ichiran_revLen;
+static int canna_ichiran_length;
+static int canna_ichiran_revPos;
+static int canna_ichiran_revLen;
static Lisp_Object Vcanna_mode_string;
static int IRCP_context;
{
Vcanna_henkan_string = make_string (ks->echoStr, ks->length);
#ifndef CANNA_MULE
- Vcanna_henkan_length = ks->length;
- Vcanna_henkan_revPos = ks->revPos;
- Vcanna_henkan_revLen = ks->revLen;
+ canna_henkan_length = ks->length;
+ canna_henkan_revPos = ks->revPos;
+ canna_henkan_revLen = ks->revLen;
#else /* CANNA_MULE */
- if (Vcanna_underline)
+ if (canna_underline)
{
- Vcanna_henkan_length = mule_strlen (ks->echoStr,ks->length);
- Vcanna_henkan_revPos = mule_strlen (ks->echoStr,ks->revPos);
- Vcanna_henkan_revLen = mule_strlen (ks->echoStr+ks->revPos,ks->revLen);
+ canna_henkan_length = mule_strlen (ks->echoStr,ks->length);
+ canna_henkan_revPos = mule_strlen (ks->echoStr,ks->revPos);
+ canna_henkan_revLen = mule_strlen (ks->echoStr+ks->revPos,ks->revLen);
}
else
{
count_char (ks->echoStr, ks->length, ks->revPos, ks->revLen,
- &Vcanna_henkan_length, &Vcanna_henkan_revPos,
- &Vcanna_henkan_revLen);
+ &canna_henkan_length, &canna_henkan_revPos,
+ &canna_henkan_revLen);
}
#endif /* CANNA_MULE */
}
{
Vcanna_ichiran_string = make_string (ks->gline.line, ks->gline.length);
#ifndef CANNA_MULE
- Vcanna_ichiran_length = ks->gline.length;
- Vcanna_ichiran_revPos = ks->gline.revPos;
- Vcanna_ichiran_revLen = ks->gline.revLen;
+ canna_ichiran_length = ks->gline.length;
+ canna_ichiran_revPos = ks->gline.revPos;
+ canna_ichiran_revLen = ks->gline.revLen;
#else /* CANNA_MULE */
count_char (ks->gline.line, ks->gline.length,
- ks->gline.revPos, ks->gline.revLen, &Vcanna_ichiran_length,
- &Vcanna_ichiran_revPos, &Vcanna_ichiran_revLen);
+ ks->gline.revPos, ks->gline.revLen, &canna_ichiran_length,
+ &canna_ichiran_revPos, &canna_ichiran_revLen);
#endif /* CANNA_MULE */
}
}
/* ¤½¤Î¾¤Î¾ðÊó */
- Vcanna_empty_info = (ks->info & KanjiEmptyInfo) ? 1 : 0;
- Vcanna_through_info = (ks->info & KanjiThroughInfo) ? 1 : 0;
+ canna_empty_info = (ks->info & KanjiEmptyInfo) ? 1 : 0;
+ canna_through_info = (ks->info & KanjiThroughInfo) ? 1 : 0;
}
return val;
jrKanjiControl (0, KC_INHIBITHANKAKUKANA, (char *) 1);
#else
/* mule ¤À¤Ã¤¿¤éȾ³Ñ¥«¥¿¥«¥Ê¤â»È¤¨¤ë */
- if (Vcanna_inhibit_hankakukana)
+ if (canna_inhibit_hankakukana)
jrKanjiControl (0, KC_INHIBITHANKAKUKANA, (char *) 1);
#endif
jrKanjiControl (0, KC_YOMIINFO, (char *) 2); /* ¢¨£²: ¥á¼¥Þ»ú¤Þ¤ÇÊÖ¤¹ */
/* variables below this line is constants of Canna */
-static int Vcanna_mode_AlphaMode = IROHA_MODE_AlphaMode;
-static int Vcanna_mode_EmptyMode = IROHA_MODE_EmptyMode;
-static int Vcanna_mode_KigoMode = IROHA_MODE_KigoMode;
-static int Vcanna_mode_YomiMode = IROHA_MODE_YomiMode;
-static int Vcanna_mode_JishuMode = IROHA_MODE_JishuMode;
-static int Vcanna_mode_TankouhoMode = IROHA_MODE_TankouhoMode;
-static int Vcanna_mode_IchiranMode = IROHA_MODE_IchiranMode;
-static int Vcanna_mode_YesNoMode = IROHA_MODE_YesNoMode;
-static int Vcanna_mode_OnOffMode = IROHA_MODE_OnOffMode;
+static int canna_mode_AlphaMode;
+static int canna_mode_EmptyMode;
+static int canna_mode_KigoMode;
+static int canna_mode_YomiMode;
+static int canna_mode_JishuMode;
+static int canna_mode_TankouhoMode;
+static int canna_mode_IchiranMode;
+static int canna_mode_YesNoMode;
+static int canna_mode_OnOffMode;
#ifdef CANNA_MODE_AdjustBunsetsuMode
-static int Vcanna_mode_AdjustBunsetsuMode = CANNA_MODE_AdjustBunsetsuMode;
+static int canna_mode_AdjustBunsetsuMode;
#endif
#ifdef CANNA_MODE_ChikujiYomiMode
-static int Vcanna_mode_ChikujiYomiMode = CANNA_MODE_ChikujiYomiMode;
-static int Vcanna_mode_ChikujiTanMode = CANNA_MODE_ChikujiTanMode;
+static int canna_mode_ChikujiYomiMode;
+static int canna_mode_ChikujiTanMode;
#endif
-static int Vcanna_mode_HenkanMode = IROHA_MODE_HenkanMode;
+static int canna_mode_HenkanMode;
#ifdef CANNA_MODE_HenkanNyuryokuMode
-static int Vcanna_mode_HenkanNyuryokuMode = CANNA_MODE_HenkanNyuryokuMode;
+static int canna_mode_HenkanNyuryokuMode;
#endif
#ifdef CANNA_MODE_ZenHiraHenkanMode
-static int Vcanna_mode_ZenHiraHenkanMode = CANNA_MODE_ZenHiraHenkanMode;
+static int canna_mode_ZenHiraHenkanMode;
#ifdef CANNA_MODE_HanHiraHenkanMode
-static int Vcanna_mode_HanHiraHenkanMode = CANNA_MODE_HanHiraHenkanMode;
+static int canna_mode_HanHiraHenkanMode;
#endif
-static int Vcanna_mode_ZenKataHenkanMode = CANNA_MODE_ZenKataHenkanMode;
-static int Vcanna_mode_HanKataHenkanMode = CANNA_MODE_HanKataHenkanMode;
-static int Vcanna_mode_ZenAlphaHenkanMode = CANNA_MODE_ZenAlphaHenkanMode;
-static int Vcanna_mode_HanAlphaHenkanMode = CANNA_MODE_HanAlphaHenkanMode;
+static int canna_mode_ZenKataHenkanMode;
+static int canna_mode_HanKataHenkanMode;
+static int canna_mode_ZenAlphaHenkanMode;
+static int canna_mode_HanAlphaHenkanMode;
#endif
-static int Vcanna_mode_ZenHiraKakuteiMode = IROHA_MODE_ZenHiraKakuteiMode;
+static int canna_mode_ZenHiraKakuteiMode;
#ifdef CANNA_MODE_HanHiraKakuteiMode
-static int Vcanna_mode_HanHiraKakuteiMode = CANNA_MODE_HanHiraKakuteiMode;
+static int canna_mode_HanHiraKakuteiMode;
#endif
-static int Vcanna_mode_ZenKataKakuteiMode = IROHA_MODE_ZenKataKakuteiMode;
-static int Vcanna_mode_HanKataKakuteiMode = IROHA_MODE_HanKataKakuteiMode;
-static int Vcanna_mode_ZenAlphaKakuteiMode = IROHA_MODE_ZenAlphaKakuteiMode;
-static int Vcanna_mode_HanAlphaKakuteiMode = IROHA_MODE_HanAlphaKakuteiMode;
-static int Vcanna_mode_HexMode = IROHA_MODE_HexMode;
-static int Vcanna_mode_BushuMode = IROHA_MODE_BushuMode;
-static int Vcanna_mode_ExtendMode = IROHA_MODE_ExtendMode;
-static int Vcanna_mode_RussianMode = IROHA_MODE_RussianMode;
-static int Vcanna_mode_GreekMode = IROHA_MODE_GreekMode;
-static int Vcanna_mode_LineMode = IROHA_MODE_LineMode;
-static int Vcanna_mode_ChangingServerMode = IROHA_MODE_ChangingServerMode;
-static int Vcanna_mode_HenkanMethodMode = IROHA_MODE_HenkanMethodMode;
-static int Vcanna_mode_DeleteDicMode = IROHA_MODE_DeleteDicMode;
-static int Vcanna_mode_TourokuMode = IROHA_MODE_TourokuMode;
-static int Vcanna_mode_TourokuEmptyMode = IROHA_MODE_TourokuEmptyMode;
-static int Vcanna_mode_TourokuHinshiMode = IROHA_MODE_TourokuHinshiMode;
-static int Vcanna_mode_TourokuDicMode = IROHA_MODE_TourokuDicMode;
-static int Vcanna_mode_QuotedInsertMode = IROHA_MODE_QuotedInsertMode;
-static int Vcanna_mode_BubunMuhenkanMode = IROHA_MODE_BubunMuhenkanMode;
-static int Vcanna_mode_MountDicMode = IROHA_MODE_MountDicMode;
-
-static int Vcanna_fn_SelfInsert = IROHA_FN_SelfInsert;
-static int Vcanna_fn_FunctionalInsert = IROHA_FN_FunctionalInsert;
-static int Vcanna_fn_QuotedInsert = IROHA_FN_QuotedInsert;
-static int Vcanna_fn_JapaneseMode = IROHA_FN_JapaneseMode;
-static int Vcanna_fn_AlphaMode = IROHA_FN_AlphaMode;
-static int Vcanna_fn_HenkanNyuryokuMode = IROHA_FN_HenkanNyuryokuMode;
-static int Vcanna_fn_Forward = IROHA_FN_Forward;
-static int Vcanna_fn_Backward = IROHA_FN_Backward;
-static int Vcanna_fn_Next = IROHA_FN_Next;
-static int Vcanna_fn_Prev = IROHA_FN_Prev;
-static int Vcanna_fn_BeginningOfLine = IROHA_FN_BeginningOfLine;
-static int Vcanna_fn_EndOfLine = IROHA_FN_EndOfLine;
-static int Vcanna_fn_DeleteNext = IROHA_FN_DeleteNext;
-static int Vcanna_fn_DeletePrevious = IROHA_FN_DeletePrevious;
-static int Vcanna_fn_KillToEndOfLine = IROHA_FN_KillToEndOfLine;
-static int Vcanna_fn_Henkan = IROHA_FN_Henkan;
-static int Vcanna_fn_Kakutei = IROHA_FN_Kakutei;
-static int Vcanna_fn_Extend = IROHA_FN_Extend;
-static int Vcanna_fn_Shrink = IROHA_FN_Shrink;
+static int canna_mode_ZenKataKakuteiMode;
+static int canna_mode_HanKataKakuteiMode;
+static int canna_mode_ZenAlphaKakuteiMode;
+static int canna_mode_HanAlphaKakuteiMode;
+static int canna_mode_HexMode;
+static int canna_mode_BushuMode;
+static int canna_mode_ExtendMode;
+static int canna_mode_RussianMode;
+static int canna_mode_GreekMode;
+static int canna_mode_LineMode;
+static int canna_mode_ChangingServerMode;
+static int canna_mode_HenkanMethodMode;
+static int canna_mode_DeleteDicMode;
+static int canna_mode_TourokuMode;
+static int canna_mode_TourokuEmptyMode;
+static int canna_mode_TourokuHinshiMode;
+static int canna_mode_TourokuDicMode;
+static int canna_mode_QuotedInsertMode;
+static int canna_mode_BubunMuhenkanMode;
+static int canna_mode_MountDicMode;
+
+static int canna_fn_SelfInsert;
+static int canna_fn_FunctionalInsert;
+static int canna_fn_QuotedInsert;
+static int canna_fn_JapaneseMode;
+static int canna_fn_AlphaMode;
+static int canna_fn_HenkanNyuryokuMode;
+static int canna_fn_Forward;
+static int canna_fn_Backward;
+static int canna_fn_Next;
+static int canna_fn_Prev;
+static int canna_fn_BeginningOfLine;
+static int canna_fn_EndOfLine;
+static int canna_fn_DeleteNext;
+static int canna_fn_DeletePrevious;
+static int canna_fn_KillToEndOfLine;
+static int canna_fn_Henkan;
+static int canna_fn_Kakutei;
+static int canna_fn_Extend;
+static int canna_fn_Shrink;
#ifdef CANNA_FN_AdjustBunsetsu
-static int Vcanna_fn_AdjustBunsetsu = CANNA_FN_AdjustBunsetsu;
+static int canna_fn_AdjustBunsetsu;
#endif
-static int Vcanna_fn_Quit = IROHA_FN_Quit;
-static int Vcanna_fn_ConvertAsHex = IROHA_FN_ConvertAsHex;
-static int Vcanna_fn_ConvertAsBushu = IROHA_FN_ConvertAsBushu;
-static int Vcanna_fn_KouhoIchiran = IROHA_FN_KouhoIchiran;
-static int Vcanna_fn_BubunMuhenkan = IROHA_FN_BubunMuhenkan;
-static int Vcanna_fn_Zenkaku = IROHA_FN_Zenkaku;
-static int Vcanna_fn_Hankaku = IROHA_FN_Hankaku;
-static int Vcanna_fn_ToUpper = IROHA_FN_ToUpper;
-static int Vcanna_fn_Capitalize = IROHA_FN_Capitalize;
-static int Vcanna_fn_ToLower = IROHA_FN_ToLower;
-static int Vcanna_fn_Hiragana = IROHA_FN_Hiragana;
-static int Vcanna_fn_Katakana = IROHA_FN_Katakana;
-static int Vcanna_fn_Romaji = IROHA_FN_Romaji;
+static int canna_fn_Quit;
+static int canna_fn_ConvertAsHex;
+static int canna_fn_ConvertAsBushu;
+static int canna_fn_KouhoIchiran;
+static int canna_fn_BubunMuhenkan;
+static int canna_fn_Zenkaku;
+static int canna_fn_Hankaku;
+static int canna_fn_ToUpper;
+static int canna_fn_Capitalize;
+static int canna_fn_ToLower;
+static int canna_fn_Hiragana;
+static int canna_fn_Katakana;
+static int canna_fn_Romaji;
#ifdef CANNA_FN_BaseHiragana
-static int Vcanna_fn_BaseHiragana = CANNA_FN_BaseHiragana;
-static int Vcanna_fn_BaseKatakana = CANNA_FN_BaseKatakana;
-static int Vcanna_fn_BaseEisu = CANNA_FN_BaseEisu;
-static int Vcanna_fn_BaseZenkaku = CANNA_FN_BaseZenkaku;
-static int Vcanna_fn_BaseHankaku = CANNA_FN_BaseHankaku;
-static int Vcanna_fn_BaseKana = CANNA_FN_BaseKana;
-static int Vcanna_fn_BaseKakutei = CANNA_FN_BaseKakutei;
-static int Vcanna_fn_BaseHenkan = CANNA_FN_BaseHenkan;
-static int Vcanna_fn_BaseHiraKataToggle = CANNA_FN_BaseHiraKataToggle;
-static int Vcanna_fn_BaseZenHanToggle = CANNA_FN_BaseZenHanToggle;
-static int Vcanna_fn_BaseKanaEisuToggle = CANNA_FN_BaseKanaEisuToggle;
-static int Vcanna_fn_BaseKakuteiHenkanToggle =
- CANNA_FN_BaseKakuteiHenkanToggle;
-static int Vcanna_fn_BaseRotateForward = CANNA_FN_BaseRotateForward;
-static int Vcanna_fn_BaseRotateBackward = CANNA_FN_BaseRotateBackward;
+static int canna_fn_BaseHiragana;
+static int canna_fn_BaseKatakana;
+static int canna_fn_BaseEisu;
+static int canna_fn_BaseZenkaku;
+static int canna_fn_BaseHankaku;
+static int canna_fn_BaseKana;
+static int canna_fn_BaseKakutei;
+static int canna_fn_BaseHenkan;
+static int canna_fn_BaseHiraKataToggle;
+static int canna_fn_BaseZenHanToggle;
+static int canna_fn_BaseKanaEisuToggle;
+static int canna_fn_BaseKakuteiHenkanToggle;
+static int canna_fn_BaseRotateForward;
+static int canna_fn_BaseRotateBackward;
#endif
-static int Vcanna_fn_ExtendMode = IROHA_FN_ExtendMode;
-static int Vcanna_fn_Touroku = IROHA_FN_Touroku;
-static int Vcanna_fn_HexMode = IROHA_FN_HexMode;
-static int Vcanna_fn_BushuMode = IROHA_FN_BushuMode;
-static int Vcanna_fn_KigouMode = IROHA_FN_KigouMode;
+static int canna_fn_ExtendMode;
+static int canna_fn_Touroku;
+static int canna_fn_HexMode;
+static int canna_fn_BushuMode;
+static int canna_fn_KigouMode;
#ifdef CANNA_FN_Mark
-static int Vcanna_fn_Mark = CANNA_FN_Mark;
+static int canna_fn_Mark;
#endif
#ifdef CANNA_FN_TemporalMode
-static int Vcanna_fn_TemporalMode = CANNA_FN_TemporalMode;
+static int canna_fn_TemporalMode;
#endif
-static int Vcanna_key_Nfer = IROHA_KEY_Nfer;
-static int Vcanna_key_Xfer = IROHA_KEY_Xfer;
-static int Vcanna_key_Up = IROHA_KEY_Up;
-static int Vcanna_key_Left = IROHA_KEY_Left;
-static int Vcanna_key_Right = IROHA_KEY_Right;
-static int Vcanna_key_Down = IROHA_KEY_Down;
-static int Vcanna_key_Insert = IROHA_KEY_Insert;
-static int Vcanna_key_Rollup = IROHA_KEY_Rollup;
-static int Vcanna_key_Rolldown = IROHA_KEY_Rolldown;
-static int Vcanna_key_Home = IROHA_KEY_Home;
-static int Vcanna_key_Help = IROHA_KEY_Help;
-static int Vcanna_key_KP_Key = IROHA_KEY_KP_Key;
-static int Vcanna_key_Shift_Nfer = IROHA_KEY_Shift_Nfer;
-static int Vcanna_key_Shift_Xfer = IROHA_KEY_Shift_Xfer;
-static int Vcanna_key_Shift_Up = IROHA_KEY_Shift_Up;
-static int Vcanna_key_Shift_Left = IROHA_KEY_Shift_Left;
-static int Vcanna_key_Shift_Right = IROHA_KEY_Shift_Right;
-static int Vcanna_key_Shift_Down = IROHA_KEY_Shift_Down;
-static int Vcanna_key_Cntrl_Nfer = IROHA_KEY_Cntrl_Nfer;
-static int Vcanna_key_Cntrl_Xfer = IROHA_KEY_Cntrl_Xfer;
-static int Vcanna_key_Cntrl_Up = IROHA_KEY_Cntrl_Up;
-static int Vcanna_key_Cntrl_Left = IROHA_KEY_Cntrl_Left;
-static int Vcanna_key_Cntrl_Right = IROHA_KEY_Cntrl_Right;
-static int Vcanna_key_Cntrl_Down = IROHA_KEY_Cntrl_Down;
+static int canna_key_Nfer;
+static int canna_key_Xfer;
+static int canna_key_Up;
+static int canna_key_Left;
+static int canna_key_Right;
+static int canna_key_Down;
+static int canna_key_Insert;
+static int canna_key_Rollup;
+static int canna_key_Rolldown;
+static int canna_key_Home;
+static int canna_key_Help;
+static int canna_key_KP_Key;
+static int canna_key_Shift_Nfer;
+static int canna_key_Shift_Xfer;
+static int canna_key_Shift_Up;
+static int canna_key_Shift_Left;
+static int canna_key_Shift_Right;
+static int canna_key_Shift_Down;
+static int canna_key_Cntrl_Nfer;
+static int canna_key_Cntrl_Xfer;
+static int canna_key_Cntrl_Up;
+static int canna_key_Cntrl_Left;
+static int canna_key_Cntrl_Right;
+static int canna_key_Cntrl_Down;
Lisp_Object VCANNA; /* by MORIOKA Tomohiko <morioka@jaist.ac.jp>
1996/6/7 */
DEFVAR_LISP ("canna-kakutei-string", &Vcanna_kakutei_string /*
*/ );
+ Vcanna_kakutei_string = Qnil;
+
DEFVAR_LISP ("canna-kakutei-yomi", &Vcanna_kakutei_yomi /*
*/ );
+ Vcanna_kakutei_yomi = Qnil;
+
DEFVAR_LISP ("canna-kakutei-romaji", &Vcanna_kakutei_romaji /*
*/ );
+ Vcanna_kakutei_romaji = Qnil;
+
DEFVAR_LISP ("canna-henkan-string", &Vcanna_henkan_string /*
*/ );
- DEFVAR_INT ("canna-henkan-length", &Vcanna_henkan_length /*
+ Vcanna_henkan_string = Qnil;
+
+ DEFVAR_INT ("canna-henkan-length", &canna_henkan_length /*
*/ );
- DEFVAR_INT ("canna-henkan-revpos", &Vcanna_henkan_revPos /*
+ canna_henkan_length = 0;
+
+ DEFVAR_INT ("canna-henkan-revpos", &canna_henkan_revPos /*
*/ );
- DEFVAR_INT ("canna-henkan-revlen", &Vcanna_henkan_revLen /*
+ canna_henkan_revPos = 0;
+
+ DEFVAR_INT ("canna-henkan-revlen", &canna_henkan_revLen /*
*/ );
+ canna_henkan_revLen = 0;
+
DEFVAR_LISP ("canna-ichiran-string", &Vcanna_ichiran_string /*
*/ );
- DEFVAR_INT ("canna-ichiran-length", &Vcanna_ichiran_length /*
+ Vcanna_ichiran_string = Qnil;
+
+ DEFVAR_INT ("canna-ichiran-length", &canna_ichiran_length /*
*/ );
- DEFVAR_INT ("canna-ichiran-revpos", &Vcanna_ichiran_revPos /*
+ canna_ichiran_length = 0;
+
+ DEFVAR_INT ("canna-ichiran-revpos", &canna_ichiran_revPos /*
*/ );
- DEFVAR_INT ("canna-ichiran-revlen", &Vcanna_ichiran_revLen /*
+ canna_ichiran_revPos = 0;
+
+ DEFVAR_INT ("canna-ichiran-revlen", &canna_ichiran_revLen /*
*/ );
+ canna_ichiran_revLen = 0;
+
DEFVAR_LISP ("canna-mode-string", &Vcanna_mode_string /*
*/ );
+ Vcanna_mode_string = Qnil;
- DEFVAR_BOOL ("canna-empty-info", &Vcanna_empty_info /*
+ DEFVAR_BOOL ("canna-empty-info", &canna_empty_info /*
For canna
*/ );
- DEFVAR_BOOL ("canna-through-info", &Vcanna_through_info /*
+ canna_empty_info = 0;
+
+ DEFVAR_BOOL ("canna-through-info", &canna_through_info /*
For canna
*/ );
- DEFVAR_BOOL ("canna-underline", &Vcanna_underline /*
+ canna_through_info = 0;
+
+ DEFVAR_BOOL ("canna-underline", &canna_underline /*
For canna
*/ );
- DEFVAR_BOOL ("canna-inhibit-hankakukana", &Vcanna_inhibit_hankakukana /*
+ canna_underline = 0;
+
+ DEFVAR_BOOL ("canna-inhibit-hankakukana", &canna_inhibit_hankakukana /*
For canna
*/ );
+ canna_inhibit_hankakukana = 0;
- DEFVAR_INT ("canna-mode-alpha-mode", &Vcanna_mode_AlphaMode /*
+ DEFVAR_INT ("canna-mode-alpha-mode", &canna_mode_AlphaMode /*
*/ );
- DEFVAR_INT ("canna-mode-empty-mode", &Vcanna_mode_EmptyMode /*
+ canna_mode_AlphaMode = IROHA_MODE_AlphaMode;
+
+ DEFVAR_INT ("canna-mode-empty-mode", &canna_mode_EmptyMode /*
*/ );
- DEFVAR_INT ("canna-mode-kigo-mode", &Vcanna_mode_KigoMode /*
+ canna_mode_EmptyMode = IROHA_MODE_EmptyMode;
+
+ DEFVAR_INT ("canna-mode-kigo-mode", &canna_mode_KigoMode /*
*/ );
- DEFVAR_INT ("canna-mode-yomi-mode", &Vcanna_mode_YomiMode /*
+ canna_mode_KigoMode = IROHA_MODE_KigoMode;
+
+ DEFVAR_INT ("canna-mode-yomi-mode", &canna_mode_YomiMode /*
*/ );
- DEFVAR_INT ("canna-mode-jishu-mode", &Vcanna_mode_JishuMode /*
+ canna_mode_YomiMode = IROHA_MODE_YomiMode;
+
+ DEFVAR_INT ("canna-mode-jishu-mode", &canna_mode_JishuMode /*
*/ );
- DEFVAR_INT ("canna-mode-tankouho-mode", &Vcanna_mode_TankouhoMode /*
+ canna_mode_JishuMode = IROHA_MODE_JishuMode;
+
+ DEFVAR_INT ("canna-mode-tankouho-mode", &canna_mode_TankouhoMode /*
*/ );
- DEFVAR_INT ("canna-mode-ichiran-mode", &Vcanna_mode_IchiranMode /*
+ canna_mode_TankouhoMode = IROHA_MODE_TankouhoMode;
+
+ DEFVAR_INT ("canna-mode-ichiran-mode", &canna_mode_IchiranMode /*
*/ );
- DEFVAR_INT ("canna-mode-yes-no-mode", &Vcanna_mode_YesNoMode /*
+ canna_mode_IchiranMode = IROHA_MODE_IchiranMode;
+
+ DEFVAR_INT ("canna-mode-yes-no-mode", &canna_mode_YesNoMode /*
*/ );
- DEFVAR_INT ("canna-mode-on-off-mode", &Vcanna_mode_OnOffMode /*
+ canna_mode_YesNoMode = IROHA_MODE_YesNoMode;
+
+ DEFVAR_INT ("canna-mode-on-off-mode", &canna_mode_OnOffMode /*
*/ );
+ canna_mode_OnOffMode = IROHA_MODE_OnOffMode;
+
#ifdef CANNA_MODE_AdjustBunsetsuMode
DEFVAR_INT ("canna-mode-adjust-bunsetsu-mode",
- &Vcanna_mode_AdjustBunsetsuMode /*
+ &canna_mode_AdjustBunsetsuMode /*
*/ );
+ canna_mode_AdjustBunsetsuMode = CANNA_MODE_AdjustBunsetsuMode;
#endif
#ifdef CANNA_MODE_ChikujiYomiMode
- DEFVAR_INT ("canna-mode-chikuji-yomi-mode", &Vcanna_mode_ChikujiYomiMode /*
+ DEFVAR_INT ("canna-mode-chikuji-yomi-mode", &canna_mode_ChikujiYomiMode /*
*/ );
+ canna_mode_ChikujiYomiMode = CANNA_MODE_ChikujiYomiMode;
+
DEFVAR_INT ("canna-mode-chikuji-bunsetsu-mode",
- &Vcanna_mode_ChikujiTanMode /*
+ &canna_mode_ChikujiTanMode /*
*/ );
+ canna_mode_ChikujiTanMode = CANNA_MODE_ChikujiTanMode;
#endif
- DEFVAR_INT ("canna-mode-henkan-mode", &Vcanna_mode_HenkanMode /*
+ DEFVAR_INT ("canna-mode-henkan-mode", &canna_mode_HenkanMode /*
*/ );
+ canna_mode_HenkanMode = IROHA_MODE_HenkanMode;
+
#ifdef CANNA_MODE_HenkanNyuryokuMode
DEFVAR_INT ("canna-mode-henkan-nyuuryoku-mode",
- &Vcanna_mode_HenkanNyuryokuMode /*
+ &canna_mode_HenkanNyuryokuMode /*
*/ );
+ canna_mode_HenkanNyuryokuMode = CANNA_MODE_HenkanNyuryokuMode;
#endif
#ifdef CANNA_MODE_ZenHiraHenkanMode
DEFVAR_INT ("canna-mode-zen-hira-henkan-mode",
- &Vcanna_mode_ZenHiraHenkanMode /*
+ &canna_mode_ZenHiraHenkanMode /*
*/ );
+ canna_mode_ZenHiraHenkanMode = CANNA_MODE_ZenHiraHenkanMode;
#ifdef CANNA_MODE_HanHiraHenkanMode
DEFVAR_INT ("canna-mode-han-hira-henkan-mode",
- &Vcanna_mode_HanHiraHenkanMode /*
+ &canna_mode_HanHiraHenkanMode /*
*/ );
+ canna_mode_HanHiraHenkanMode = CANNA_MODE_HanHiraHenkanMode;
#endif
DEFVAR_INT ("canna-mode-zen-kata-henkan-mode",
- &Vcanna_mode_ZenKataHenkanMode /*
+ &canna_mode_ZenKataHenkanMode /*
*/ );
+ canna_mode_ZenKataHenkanMode = CANNA_MODE_ZenKataHenkanMode;
+
DEFVAR_INT ("canna-mode-han-kata-henkan-mode",
- &Vcanna_mode_HanKataHenkanMode /*
+ &canna_mode_HanKataHenkanMode /*
*/ );
+ canna_mode_HanKataHenkanMode = CANNA_MODE_HanKataHenkanMode;
+
DEFVAR_INT ("canna-mode-zen-alpha-henkan-mode",
- &Vcanna_mode_ZenAlphaHenkanMode /*
+ &canna_mode_ZenAlphaHenkanMode /*
*/ );
+ canna_mode_ZenAlphaHenkanMode = CANNA_MODE_ZenAlphaHenkanMode;
+
DEFVAR_INT ("canna-mode-han-alpha-henkan-mode",
- &Vcanna_mode_HanAlphaHenkanMode /*
+ &canna_mode_HanAlphaHenkanMode /*
*/ );
+ canna_mode_HanAlphaHenkanMode = CANNA_MODE_HanAlphaHenkanMode;
#endif
DEFVAR_INT ("canna-mode-zen-hira-kakutei-mode",
- &Vcanna_mode_ZenHiraKakuteiMode /*
+ &canna_mode_ZenHiraKakuteiMode /*
*/ );
+ canna_mode_ZenHiraKakuteiMode = IROHA_MODE_ZenHiraKakuteiMode;
#ifdef CANNA_MODE_HanHiraKakuteiMode
DEFVAR_INT ("canna-mode-han-hira-kakutei-mode",
- &Vcanna_mode_HanHiraKakuteiMode /*
+ &canna_mode_HanHiraKakuteiMode /*
*/ );
+ canna_mode_HanHiraKakuteiMode = CANNA_MODE_HanHiraKakuteiMode;
#endif
DEFVAR_INT ("canna-mode-zen-kata-kakutei-mode",
- &Vcanna_mode_ZenKataKakuteiMode /*
+ &canna_mode_ZenKataKakuteiMode /*
*/ );
+ canna_mode_ZenKataKakuteiMode = IROHA_MODE_ZenKataKakuteiMode;
+
DEFVAR_INT ("canna-mode-han-kata-kakutei-mode",
- &Vcanna_mode_HanKataKakuteiMode /*
+ &canna_mode_HanKataKakuteiMode /*
*/ );
+ canna_mode_HanKataKakuteiMode = IROHA_MODE_HanKataKakuteiMode;
+
DEFVAR_INT ("canna-mode-zen-alpha-kakutei-mode",
- &Vcanna_mode_ZenAlphaKakuteiMode /*
+ &canna_mode_ZenAlphaKakuteiMode /*
*/ );
+ canna_mode_ZenAlphaKakuteiMode = IROHA_MODE_ZenAlphaKakuteiMode;
+
DEFVAR_INT ("canna-mode-han-alpha-kakutei-mode",
- &Vcanna_mode_HanAlphaKakuteiMode /*
+ &canna_mode_HanAlphaKakuteiMode /*
*/ );
- DEFVAR_INT ("canna-mode-hex-mode", &Vcanna_mode_HexMode /*
+ canna_mode_HanAlphaKakuteiMode = IROHA_MODE_HanAlphaKakuteiMode;
+
+ DEFVAR_INT ("canna-mode-hex-mode", &canna_mode_HexMode /*
*/ );
- DEFVAR_INT ("canna-mode-bushu-mode", &Vcanna_mode_BushuMode /*
+ canna_mode_HexMode = IROHA_MODE_HexMode;
+
+ DEFVAR_INT ("canna-mode-bushu-mode", &canna_mode_BushuMode /*
*/ );
- DEFVAR_INT ("canna-mode-extend-mode", &Vcanna_mode_ExtendMode /*
+ canna_mode_BushuMode = IROHA_MODE_BushuMode;
+
+ DEFVAR_INT ("canna-mode-extend-mode", &canna_mode_ExtendMode /*
*/ );
- DEFVAR_INT ("canna-mode-russian-mode", &Vcanna_mode_RussianMode /*
+ canna_mode_ExtendMode = IROHA_MODE_ExtendMode;
+
+ DEFVAR_INT ("canna-mode-russian-mode", &canna_mode_RussianMode /*
*/ );
- DEFVAR_INT ("canna-mode-greek-mode", &Vcanna_mode_GreekMode /*
+ canna_mode_RussianMode = IROHA_MODE_RussianMode;
+
+ DEFVAR_INT ("canna-mode-greek-mode", &canna_mode_GreekMode /*
*/ );
- DEFVAR_INT ("canna-mode-line-mode", &Vcanna_mode_LineMode /*
+ canna_mode_GreekMode = IROHA_MODE_GreekMode;
+
+ DEFVAR_INT ("canna-mode-line-mode", &canna_mode_LineMode /*
*/ );
+ canna_mode_LineMode = IROHA_MODE_LineMode;
+
DEFVAR_INT ("canna-mode-changing-server-mode",
- &Vcanna_mode_ChangingServerMode /*
+ &canna_mode_ChangingServerMode /*
*/ );
+ canna_mode_ChangingServerMode = IROHA_MODE_ChangingServerMode;
+
DEFVAR_INT ("canna-mode-henkan-method-mode",
- &Vcanna_mode_HenkanMethodMode /*
+ &canna_mode_HenkanMethodMode /*
*/ );
- DEFVAR_INT ("canna-mode-delete-dic-mode", &Vcanna_mode_DeleteDicMode /*
+ canna_mode_HenkanMethodMode = IROHA_MODE_HenkanMethodMode;
+
+ DEFVAR_INT ("canna-mode-delete-dic-mode", &canna_mode_DeleteDicMode /*
*/ );
- DEFVAR_INT ("canna-mode-touroku-mode", &Vcanna_mode_TourokuMode /*
+ canna_mode_DeleteDicMode = IROHA_MODE_DeleteDicMode;
+
+ DEFVAR_INT ("canna-mode-touroku-mode", &canna_mode_TourokuMode /*
*/ );
+ canna_mode_TourokuMode = IROHA_MODE_TourokuMode;
+
DEFVAR_INT ("canna-mode-touroku-empty-mode",
- &Vcanna_mode_TourokuEmptyMode /*
+ &canna_mode_TourokuEmptyMode /*
*/ );
+ canna_mode_TourokuEmptyMode = IROHA_MODE_TourokuEmptyMode;
+
DEFVAR_INT ("canna-mode-touroku-hinshi-mode",
- &Vcanna_mode_TourokuHinshiMode /*
+ &canna_mode_TourokuHinshiMode /*
*/ );
- DEFVAR_INT ("canna-mode-touroku-dic-mode", &Vcanna_mode_TourokuDicMode /*
+ canna_mode_TourokuHinshiMode = IROHA_MODE_TourokuHinshiMode;
+
+ DEFVAR_INT ("canna-mode-touroku-dic-mode", &canna_mode_TourokuDicMode /*
*/ );
+ canna_mode_TourokuDicMode = IROHA_MODE_TourokuDicMode;
+
DEFVAR_INT ("canna-mode-quoted-insert-mode",
- &Vcanna_mode_QuotedInsertMode /*
+ &canna_mode_QuotedInsertMode /*
*/ );
+ canna_mode_QuotedInsertMode = IROHA_MODE_QuotedInsertMode;
+
DEFVAR_INT ("canna-mode-bubun-muhenkan-mode",
- &Vcanna_mode_BubunMuhenkanMode /*
+ &canna_mode_BubunMuhenkanMode /*
*/ );
- DEFVAR_INT ("canna-mode-mount-dic-mode", &Vcanna_mode_MountDicMode /*
+ canna_mode_BubunMuhenkanMode = IROHA_MODE_BubunMuhenkanMode;
+
+ DEFVAR_INT ("canna-mode-mount-dic-mode", &canna_mode_MountDicMode /*
*/ );
+ canna_mode_MountDicMode = IROHA_MODE_MountDicMode;
- DEFVAR_INT ("canna-func-self-insert", &Vcanna_fn_SelfInsert /*
+ DEFVAR_INT ("canna-func-self-insert", &canna_fn_SelfInsert /*
*/ );
- DEFVAR_INT ("canna-func-functional-insert", &Vcanna_fn_FunctionalInsert /*
+ canna_fn_SelfInsert = IROHA_FN_SelfInsert;
+
+ DEFVAR_INT ("canna-func-functional-insert", &canna_fn_FunctionalInsert /*
*/ );
- DEFVAR_INT ("canna-func-quoted-insert", &Vcanna_fn_QuotedInsert /*
+ canna_fn_FunctionalInsert = IROHA_FN_FunctionalInsert;
+
+ DEFVAR_INT ("canna-func-quoted-insert", &canna_fn_QuotedInsert /*
*/ );
- DEFVAR_INT ("canna-func-japanese-mode", &Vcanna_fn_JapaneseMode /*
+ canna_fn_QuotedInsert = IROHA_FN_QuotedInsert;
+
+ DEFVAR_INT ("canna-func-japanese-mode", &canna_fn_JapaneseMode /*
*/ );
- DEFVAR_INT ("canna-func-alpha-mode", &Vcanna_fn_AlphaMode /*
+ canna_fn_JapaneseMode = IROHA_FN_JapaneseMode;
+
+ DEFVAR_INT ("canna-func-alpha-mode", &canna_fn_AlphaMode /*
*/ );
+ canna_fn_AlphaMode = IROHA_FN_AlphaMode;
+
DEFVAR_INT ("canna-func-henkan-nyuryoku-mode",
- &Vcanna_fn_HenkanNyuryokuMode /*
+ &canna_fn_HenkanNyuryokuMode /*
*/ );
- DEFVAR_INT ("canna-func-forward", &Vcanna_fn_Forward /*
+ canna_fn_HenkanNyuryokuMode = IROHA_FN_HenkanNyuryokuMode;
+
+ DEFVAR_INT ("canna-func-forward", &canna_fn_Forward /*
*/ );
- DEFVAR_INT ("canna-func-backward", &Vcanna_fn_Backward /*
+ canna_fn_Forward = IROHA_FN_Forward;
+
+ DEFVAR_INT ("canna-func-backward", &canna_fn_Backward /*
*/ );
- DEFVAR_INT ("canna-func-next", &Vcanna_fn_Next /*
+ canna_fn_Backward = IROHA_FN_Backward;
+
+ DEFVAR_INT ("canna-func-next", &canna_fn_Next /*
*/ );
- DEFVAR_INT ("canna-func-previous", &Vcanna_fn_Prev /*
+ canna_fn_Next = IROHA_FN_Next;
+
+ DEFVAR_INT ("canna-func-previous", &canna_fn_Prev /*
*/ );
- DEFVAR_INT ("canna-func-beginning-of-line", &Vcanna_fn_BeginningOfLine /*
+ canna_fn_Prev = IROHA_FN_Prev;
+
+ DEFVAR_INT ("canna-func-beginning-of-line", &canna_fn_BeginningOfLine /*
*/ );
- DEFVAR_INT ("canna-func-end-of-line", &Vcanna_fn_EndOfLine /*
+ canna_fn_BeginningOfLine = IROHA_FN_BeginningOfLine;
+
+ DEFVAR_INT ("canna-func-end-of-line", &canna_fn_EndOfLine /*
*/ );
- DEFVAR_INT ("canna-func-delete-next", &Vcanna_fn_DeleteNext /*
+ canna_fn_EndOfLine = IROHA_FN_EndOfLine;
+
+ DEFVAR_INT ("canna-func-delete-next", &canna_fn_DeleteNext /*
*/ );
- DEFVAR_INT ("canna-func-delete_previous", &Vcanna_fn_DeletePrevious /*
+ canna_fn_DeleteNext = IROHA_FN_DeleteNext;
+
+ DEFVAR_INT ("canna-func-delete_previous", &canna_fn_DeletePrevious /*
*/ );
- DEFVAR_INT ("canna-func-kill-to-end-of-line", &Vcanna_fn_KillToEndOfLine /*
+ canna_fn_DeletePrevious = IROHA_FN_DeletePrevious;
+
+ DEFVAR_INT ("canna-func-kill-to-end-of-line", &canna_fn_KillToEndOfLine /*
*/ );
- DEFVAR_INT ("canna-func-henkan", &Vcanna_fn_Henkan /*
+ canna_fn_KillToEndOfLine = IROHA_FN_KillToEndOfLine;
+
+ DEFVAR_INT ("canna-func-henkan", &canna_fn_Henkan /*
*/ );
- DEFVAR_INT ("canna-func-kakutei", &Vcanna_fn_Kakutei /*
+ canna_fn_Henkan = IROHA_FN_Henkan;
+
+ DEFVAR_INT ("canna-func-kakutei", &canna_fn_Kakutei /*
*/ );
- DEFVAR_INT ("canna-func-extend", &Vcanna_fn_Extend /*
+ canna_fn_Kakutei = IROHA_FN_Kakutei;
+
+ DEFVAR_INT ("canna-func-extend", &canna_fn_Extend /*
*/ );
- DEFVAR_INT ("canna-func-shrink", &Vcanna_fn_Shrink /*
+ canna_fn_Extend = IROHA_FN_Extend;
+
+ DEFVAR_INT ("canna-func-shrink", &canna_fn_Shrink /*
*/ );
+ canna_fn_Shrink = IROHA_FN_Shrink;
+
#ifdef CANNA_FN_AdjustBunsetsu
- DEFVAR_INT ("canna-func-adjust-bunsetsu", &Vcanna_fn_AdjustBunsetsu /*
+ DEFVAR_INT ("canna-func-adjust-bunsetsu", &canna_fn_AdjustBunsetsu /*
*/ );
+ canna_fn_AdjustBunsetsu = CANNA_FN_AdjustBunsetsu;
#endif
- DEFVAR_INT ("canna-func-quit", &Vcanna_fn_Quit /*
+ DEFVAR_INT ("canna-func-quit", &canna_fn_Quit /*
*/ );
- DEFVAR_INT ("canna-func-convert-as-hex", &Vcanna_fn_ConvertAsHex /*
+ canna_fn_Quit = IROHA_FN_Quit;
+
+ DEFVAR_INT ("canna-func-convert-as-hex", &canna_fn_ConvertAsHex /*
*/ );
- DEFVAR_INT ("canna-func-convert-as-bushu", &Vcanna_fn_ConvertAsBushu /*
+ canna_fn_ConvertAsHex = IROHA_FN_ConvertAsHex;
+
+ DEFVAR_INT ("canna-func-convert-as-bushu", &canna_fn_ConvertAsBushu /*
*/ );
- DEFVAR_INT ("canna-func-kouho-ichiran", &Vcanna_fn_KouhoIchiran /*
+ canna_fn_ConvertAsBushu = IROHA_FN_ConvertAsBushu;
+
+ DEFVAR_INT ("canna-func-kouho-ichiran", &canna_fn_KouhoIchiran /*
*/ );
- DEFVAR_INT ("canna-func-bubun-muhenkan", &Vcanna_fn_BubunMuhenkan /*
+ canna_fn_KouhoIchiran = IROHA_FN_KouhoIchiran;
+
+ DEFVAR_INT ("canna-func-bubun-muhenkan", &canna_fn_BubunMuhenkan /*
*/ );
- DEFVAR_INT ("canna-func-zenkaku", &Vcanna_fn_Zenkaku /*
+ canna_fn_BubunMuhenkan = IROHA_FN_BubunMuhenkan;
+
+ DEFVAR_INT ("canna-func-zenkaku", &canna_fn_Zenkaku /*
*/ );
- DEFVAR_INT ("canna-func-hankaku", &Vcanna_fn_Hankaku /*
+ canna_fn_Zenkaku = IROHA_FN_Zenkaku;
+
+ DEFVAR_INT ("canna-func-hankaku", &canna_fn_Hankaku /*
*/ );
- DEFVAR_INT ("canna-func-to-upper", &Vcanna_fn_ToUpper /*
+ canna_fn_Hankaku = IROHA_FN_Hankaku;
+
+ DEFVAR_INT ("canna-func-to-upper", &canna_fn_ToUpper /*
*/ );
- DEFVAR_INT ("canna-func-capitalize", &Vcanna_fn_Capitalize /*
+ canna_fn_ToUpper = IROHA_FN_ToUpper;
+
+ DEFVAR_INT ("canna-func-capitalize", &canna_fn_Capitalize /*
*/ );
- DEFVAR_INT ("canna-func-to-lower", &Vcanna_fn_ToLower /*
+ canna_fn_Capitalize = IROHA_FN_Capitalize;
+
+ DEFVAR_INT ("canna-func-to-lower", &canna_fn_ToLower /*
*/ );
- DEFVAR_INT ("canna-func-hiragana", &Vcanna_fn_Hiragana /*
+ canna_fn_ToLower = IROHA_FN_ToLower;
+
+ DEFVAR_INT ("canna-func-hiragana", &canna_fn_Hiragana /*
*/ );
- DEFVAR_INT ("canna-func-katakana", &Vcanna_fn_Katakana /*
+ canna_fn_Hiragana = IROHA_FN_Hiragana;
+
+ DEFVAR_INT ("canna-func-katakana", &canna_fn_Katakana /*
*/ );
- DEFVAR_INT ("canna-func-romaji", &Vcanna_fn_Romaji /*
+ canna_fn_Katakana = IROHA_FN_Katakana;
+
+ DEFVAR_INT ("canna-func-romaji", &canna_fn_Romaji /*
*/ );
+ canna_fn_Romaji = IROHA_FN_Romaji;
+
#ifdef CANNA_FN_BaseHiragana
- DEFVAR_INT ("canna-func-base-hiragana", &Vcanna_fn_BaseHiragana /*
+ DEFVAR_INT ("canna-func-base-hiragana", &canna_fn_BaseHiragana /*
*/ );
- DEFVAR_INT ("canna-func-base-katakana", &Vcanna_fn_BaseKatakana /*
+ canna_fn_BaseHiragana = CANNA_FN_BaseHiragana;
+
+ DEFVAR_INT ("canna-func-base-katakana", &canna_fn_BaseKatakana /*
*/ );
- DEFVAR_INT ("canna-func-base-eisu", &Vcanna_fn_BaseEisu /*
+ canna_fn_BaseKatakana = CANNA_FN_BaseKatakana;
+
+ DEFVAR_INT ("canna-func-base-eisu", &canna_fn_BaseEisu /*
*/ );
- DEFVAR_INT ("canna-func-base-zenkaku", &Vcanna_fn_BaseZenkaku /*
+ canna_fn_BaseEisu = CANNA_FN_BaseEisu;
+
+ DEFVAR_INT ("canna-func-base-zenkaku", &canna_fn_BaseZenkaku /*
*/ );
- DEFVAR_INT ("canna-func-base-hankaku", &Vcanna_fn_BaseHankaku /*
+ canna_fn_BaseZenkaku = CANNA_FN_BaseZenkaku;
+
+ DEFVAR_INT ("canna-func-base-hankaku", &canna_fn_BaseHankaku /*
*/ );
- DEFVAR_INT ("canna-func-base-kana", &Vcanna_fn_BaseKana /*
+ canna_fn_BaseHankaku = CANNA_FN_BaseHankaku;
+
+ DEFVAR_INT ("canna-func-base-kana", &canna_fn_BaseKana /*
*/ );
- DEFVAR_INT ("canna-func-base-kakutei", &Vcanna_fn_BaseKakutei /*
+ canna_fn_BaseKana = CANNA_FN_BaseKana;
+
+ DEFVAR_INT ("canna-func-base-kakutei", &canna_fn_BaseKakutei /*
*/ );
- DEFVAR_INT ("canna-func-base-henkan", &Vcanna_fn_BaseHenkan /*
+ canna_fn_BaseKakutei = CANNA_FN_BaseKakutei;
+
+ DEFVAR_INT ("canna-func-base-henkan", &canna_fn_BaseHenkan /*
*/ );
+ canna_fn_BaseHenkan = CANNA_FN_BaseHenkan;
+
DEFVAR_INT ("canna-func-base-hiragana-katakana-toggle",
- &Vcanna_fn_BaseHiraKataToggle /*
+ &canna_fn_BaseHiraKataToggle /*
*/ );
+ canna_fn_BaseHiraKataToggle = CANNA_FN_BaseHiraKataToggle;
+
DEFVAR_INT ("canna-func-base-zenkaku-hankaku-toggle",
- &Vcanna_fn_BaseZenHanToggle /*
+ &canna_fn_BaseZenHanToggle /*
*/ );
+ canna_fn_BaseZenHanToggle = CANNA_FN_BaseZenHanToggle;
+
DEFVAR_INT ("canna-func-base-kana-eisu-toggle",
- &Vcanna_fn_BaseKanaEisuToggle /*
+ &canna_fn_BaseKanaEisuToggle /*
*/ );
+ canna_fn_BaseKanaEisuToggle = CANNA_FN_BaseKanaEisuToggle;
+
DEFVAR_INT ("canna-func-base-kakutei-henkan-toggle",
- &Vcanna_fn_BaseKakuteiHenkanToggle /*
+ &canna_fn_BaseKakuteiHenkanToggle /*
*/ );
+ canna_fn_BaseKakuteiHenkanToggle = CANNA_FN_BaseKakuteiHenkanToggle;
+
DEFVAR_INT ("canna-func-base-rotate-forward",
- &Vcanna_fn_BaseRotateForward /*
+ &canna_fn_BaseRotateForward /*
*/ );
+ canna_fn_BaseRotateForward = CANNA_FN_BaseRotateForward;
+
DEFVAR_INT ("canna-func-base-rotate-backward",
- &Vcanna_fn_BaseRotateBackward /*
+ &canna_fn_BaseRotateBackward /*
*/ );
+ canna_fn_BaseRotateBackward = CANNA_FN_BaseRotateBackward;
+
#endif
- DEFVAR_INT ("canna-func-extend-mode", &Vcanna_fn_ExtendMode /*
+ DEFVAR_INT ("canna-func-extend-mode", &canna_fn_ExtendMode /*
*/ );
- DEFVAR_INT ("canna-func-touroku", &Vcanna_fn_Touroku /*
+ canna_fn_ExtendMode = IROHA_FN_ExtendMode;
+
+ DEFVAR_INT ("canna-func-touroku", &canna_fn_Touroku /*
*/ );
- DEFVAR_INT ("canna-func-hex-mode", &Vcanna_fn_HexMode /*
+ canna_fn_Touroku = IROHA_FN_Touroku;
+
+ DEFVAR_INT ("canna-func-hex-mode", &canna_fn_HexMode /*
*/ );
- DEFVAR_INT ("canna-func-bushu-mode", &Vcanna_fn_BushuMode /*
+ canna_fn_HexMode = IROHA_FN_HexMode;
+
+ DEFVAR_INT ("canna-func-bushu-mode", &canna_fn_BushuMode /*
*/ );
- DEFVAR_INT ("canna-func-kigo-mode", &Vcanna_fn_KigouMode /*
+ canna_fn_BushuMode = IROHA_FN_BushuMode;
+
+ DEFVAR_INT ("canna-func-kigo-mode", &canna_fn_KigouMode /*
*/ );
+ canna_fn_KigouMode = IROHA_FN_KigouMode;
+
#ifdef CANNA_FN_Mark
- DEFVAR_INT ("canna-func-mark", &Vcanna_fn_Mark /*
+ DEFVAR_INT ("canna-func-mark", &canna_fn_Mark /*
*/ );
+ canna_fn_Mark = CANNA_FN_Mark;
#endif
#ifdef CANNA_FN_TemporalMode
- DEFVAR_INT ("canna-func-temporal-mode", &Vcanna_fn_TemporalMode /*
+ DEFVAR_INT ("canna-func-temporal-mode", &canna_fn_TemporalMode /*
*/ );
+ canna_fn_TemporalMode = CANNA_FN_TemporalMode;
#endif
- DEFVAR_INT ("canna-key-nfer", &Vcanna_key_Nfer /*
+ DEFVAR_INT ("canna-key-nfer", &canna_key_Nfer /*
*/ );
- DEFVAR_INT ("canna-key-xfer", &Vcanna_key_Xfer /*
+ canna_key_Nfer = IROHA_KEY_Nfer;
+
+ DEFVAR_INT ("canna-key-xfer", &canna_key_Xfer /*
*/ );
- DEFVAR_INT ("canna-key-up", &Vcanna_key_Up /*
+ canna_key_Xfer = IROHA_KEY_Xfer;
+
+ DEFVAR_INT ("canna-key-up", &canna_key_Up /*
*/ );
- DEFVAR_INT ("canna-key-left", &Vcanna_key_Left /*
+ canna_key_Up = IROHA_KEY_Up;
+
+ DEFVAR_INT ("canna-key-left", &canna_key_Left /*
*/ );
- DEFVAR_INT ("canna-key-right", &Vcanna_key_Right /*
+ canna_key_Left = IROHA_KEY_Left;
+
+ DEFVAR_INT ("canna-key-right", &canna_key_Right /*
*/ );
- DEFVAR_INT ("canna-key-down", &Vcanna_key_Down /*
+ canna_key_Right = IROHA_KEY_Right;
+
+ DEFVAR_INT ("canna-key-down", &canna_key_Down /*
*/ );
- DEFVAR_INT ("canna-key-insert", &Vcanna_key_Insert /*
+ canna_key_Down = IROHA_KEY_Down;
+
+ DEFVAR_INT ("canna-key-insert", &canna_key_Insert /*
*/ );
- DEFVAR_INT ("canna-key-rollup", &Vcanna_key_Rollup /*
+ canna_key_Insert = IROHA_KEY_Insert;
+
+ DEFVAR_INT ("canna-key-rollup", &canna_key_Rollup /*
*/ );
- DEFVAR_INT ("canna-key-rolldown", &Vcanna_key_Rolldown /*
+ canna_key_Rollup = IROHA_KEY_Rollup;
+
+ DEFVAR_INT ("canna-key-rolldown", &canna_key_Rolldown /*
*/ );
- DEFVAR_INT ("canna-key-home", &Vcanna_key_Home /*
+ canna_key_Rolldown = IROHA_KEY_Rolldown;
+
+ DEFVAR_INT ("canna-key-home", &canna_key_Home /*
*/ );
- DEFVAR_INT ("canna-key-help", &Vcanna_key_Help /*
+ canna_key_Home = IROHA_KEY_Home;
+
+ DEFVAR_INT ("canna-key-help", &canna_key_Help /*
*/ );
- DEFVAR_INT ("canna-key-kp-key", &Vcanna_key_KP_Key /*
+ canna_key_Help = IROHA_KEY_Help;
+
+ DEFVAR_INT ("canna-key-kp-key", &canna_key_KP_Key /*
*/ );
- DEFVAR_INT ("canna-key-shift-nfer", &Vcanna_key_Shift_Nfer /*
+ canna_key_KP_Key = IROHA_KEY_KP_Key;
+
+ DEFVAR_INT ("canna-key-shift-nfer", &canna_key_Shift_Nfer /*
*/ );
- DEFVAR_INT ("canna-key-shift-xfer", &Vcanna_key_Shift_Xfer /*
+ canna_key_Shift_Nfer = IROHA_KEY_Shift_Nfer;
+
+ DEFVAR_INT ("canna-key-shift-xfer", &canna_key_Shift_Xfer /*
*/ );
- DEFVAR_INT ("canna-key-shift-up", &Vcanna_key_Shift_Up /*
+ canna_key_Shift_Xfer = IROHA_KEY_Shift_Xfer;
+
+ DEFVAR_INT ("canna-key-shift-up", &canna_key_Shift_Up /*
*/ );
- DEFVAR_INT ("canna-key-shift-left", &Vcanna_key_Shift_Left /*
+ canna_key_Shift_Up = IROHA_KEY_Shift_Up;
+
+ DEFVAR_INT ("canna-key-shift-left", &canna_key_Shift_Left /*
*/ );
- DEFVAR_INT ("canna-key-shift-right", &Vcanna_key_Shift_Right /*
+ canna_key_Shift_Left = IROHA_KEY_Shift_Left;
+
+ DEFVAR_INT ("canna-key-shift-right", &canna_key_Shift_Right /*
*/ );
- DEFVAR_INT ("canna-key-shift-down", &Vcanna_key_Shift_Down /*
+ canna_key_Shift_Right = IROHA_KEY_Shift_Right;
+
+ DEFVAR_INT ("canna-key-shift-down", &canna_key_Shift_Down /*
*/ );
- DEFVAR_INT ("canna-key-control-nfer", &Vcanna_key_Cntrl_Nfer /*
+ canna_key_Shift_Down = IROHA_KEY_Shift_Down;
+
+ DEFVAR_INT ("canna-key-control-nfer", &canna_key_Cntrl_Nfer /*
*/ );
- DEFVAR_INT ("canna-key-control-xfer", &Vcanna_key_Cntrl_Xfer /*
+ canna_key_Cntrl_Nfer = IROHA_KEY_Cntrl_Nfer;
+
+ DEFVAR_INT ("canna-key-control-xfer", &canna_key_Cntrl_Xfer /*
*/ );
- DEFVAR_INT ("canna-key-control-up", &Vcanna_key_Cntrl_Up /*
+ canna_key_Cntrl_Xfer = IROHA_KEY_Cntrl_Xfer;
+
+ DEFVAR_INT ("canna-key-control-up", &canna_key_Cntrl_Up /*
*/ );
- DEFVAR_INT ("canna-key-control-left", &Vcanna_key_Cntrl_Left /*
+ canna_key_Cntrl_Up = IROHA_KEY_Cntrl_Up;
+
+ DEFVAR_INT ("canna-key-control-left", &canna_key_Cntrl_Left /*
*/ );
- DEFVAR_INT ("canna-key-control-right", &Vcanna_key_Cntrl_Right /*
+ canna_key_Cntrl_Left = IROHA_KEY_Cntrl_Left;
+
+ DEFVAR_INT ("canna-key-control-right", &canna_key_Cntrl_Right /*
*/ );
- DEFVAR_INT ("canna-key-control-down", &Vcanna_key_Cntrl_Down /*
+ canna_key_Cntrl_Right = IROHA_KEY_Cntrl_Right;
+
+ DEFVAR_INT ("canna-key-control-down", &canna_key_Cntrl_Down /*
*/ );
+ canna_key_Cntrl_Down = IROHA_KEY_Cntrl_Down;
Fprovide(intern("CANNA"));
}
xzero (*cp);
cp->fd = -1;
cp->pid = -1;
+ if (cp->procinfo.hProcess)
+ CloseHandle(cp->procinfo.hProcess);
cp->procinfo.hProcess = NULL;
cp->status = STATUS_READ_ERROR;
/* Our identity */
cp = (child_process *)arg;
- /* We have to wait for the go-ahead before we can start */
+ /* <matts@tibco.com> - I think the test below is wrong - we don't
+ want to wait for someone to signal char_consumed, as we haven't
+ read anything for them to consume yet! */
+
+ /*
if (cp == NULL ||
WaitForSingleObject (cp->char_consumed, INFINITE) != WAIT_OBJECT_0)
- return 1;
+ */
+
+ if (cp == NULL)
+ {
+ return 1;
+ }
for (;;)
{
}
if (rc == STATUS_READ_ERROR)
- return 1;
+ {
+ /* We are finished, so clean up handles and set to NULL so
+ that CHILD_ACTIVE will see what is going on */
+ if (cp->char_avail) {
+ CloseHandle (cp->char_avail);
+ cp->char_avail = NULL;
+ }
+ if (cp->thrd) {
+ CloseHandle (cp->thrd);
+ cp->thrd = NULL;
+ }
+ if (cp->char_consumed) {
+ CloseHandle(cp->char_consumed);
+ cp->char_consumed = NULL;
+ }
+ if (cp->procinfo.hProcess)
+ {
+ CloseHandle (cp->procinfo.hProcess);
+ cp->procinfo.hProcess=NULL;
+ }
+ return 1;
+ }
/* If the read died, the child has died so let the thread die */
if (rc == STATUS_READ_FAILED)
break;
}
}
+ /* We are finished, so clean up handles and set to NULL so that
+ CHILD_ACTIVE will see what is going on */
+ if (cp->char_avail) {
+ CloseHandle (cp->char_avail);
+ cp->char_avail = NULL;
+ }
+ if (cp->thrd) {
+ CloseHandle (cp->thrd);
+ cp->thrd = NULL;
+ }
+ if (cp->char_consumed) {
+ CloseHandle(cp->char_consumed);
+ cp->char_consumed = NULL;
+ }
+ if (cp->procinfo.hProcess)
+ {
+ CloseHandle (cp->procinfo.hProcess);
+ cp->procinfo.hProcess=NULL;
+ }
+
return 0;
}
cp->pid = (int) cp->procinfo.dwProcessId;
+ CloseHandle (cp->procinfo.hThread);
+ CloseHandle (cp->procinfo.hProcess);
+ cp->procinfo.hThread=NULL;
+ cp->procinfo.hProcess=NULL;
+
/* Hack for Windows 95, which assigns large (ie negative) pids */
if (cp->pid < 0)
cp->pid = -cp->pid;
#ifdef __CYGWIN32__
#define stricmp strcasecmp
+#define FONTENUMPROC FONTENUMEXPROC
+#define ntmTm ntmentm
#endif
typedef struct colormap_t
{
- char *name;
- COLORREF colorref;
+ CONST char *name;
+ CONST COLORREF colorref;
} colormap_t;
/* Colors from X11R6 "XConsortium: rgb.txt,v 10.41 94/02/20 18:39:36 rws Exp" */
{"LightGreen" , PALETTERGB (144, 238, 144) }
};
+
+typedef struct fontmap_t
+{
+ CONST char *name;
+ CONST int value;
+} fontmap_t;
+
+/* Default weight first, preferred names listed before synonyms */
+static CONST fontmap_t fontweight_map[] =
+{
+ {"Regular" , FW_REGULAR}, /* The standard font weight */
+ {"Thin" , FW_THIN},
+ {"Extra Light" , FW_EXTRALIGHT},
+ {"Ultra Light" , FW_ULTRALIGHT},
+ {"Light" , FW_LIGHT},
+ {"Normal" , FW_NORMAL},
+ {"Medium" , FW_MEDIUM},
+ {"Semi Bold" , FW_SEMIBOLD},
+ {"Demi Bold" , FW_DEMIBOLD},
+ {"Bold" , FW_BOLD}, /* The standard bold font weight */
+ {"Extra Bold" , FW_EXTRABOLD},
+ {"Ultra Bold" , FW_ULTRABOLD},
+ {"Heavy" , FW_HEAVY},
+ {"Black" , FW_BLACK}
+};
+
+/* Default charset first, no synonyms allowed because these names are
+ * matched against the names reported by win32 by match_font() */
+static CONST fontmap_t charset_map[] =
+{
+ {"Western" , ANSI_CHARSET},
+ {"Symbol" , SYMBOL_CHARSET},
+ {"Shift JIS" , SHIFTJIS_CHARSET}, /* #### Name to be verified */
+ {"GB2312" , GB2312_CHARSET}, /* #### Name to be verified */
+ {"Hanguel" , HANGEUL_CHARSET},
+ {"Chinese Big 5" , CHINESEBIG5_CHARSET}, /* #### Name to be verified */
+#if (WINVER >= 0x0400)
+ {"Johab" , JOHAB_CHARSET}, /* #### Name to be verified */
+ {"Hebrew" , HEBREW_CHARSET}, /* #### Name to be verified */
+ {"Arabic" , ARABIC_CHARSET}, /* #### Name to be verified */
+ {"Greek" , GREEK_CHARSET},
+ {"Turkish" , TURKISH_CHARSET},
+ {"Vietnamese" , VIETNAMESE_CHARSET}, /* #### Name to be verified */
+ {"Thai" , THAI_CHARSET}, /* #### Name to be verified */
+ {"Central European" , EASTEUROPE_CHARSET},
+ {"Cyrillic" , RUSSIAN_CHARSET},
+ {"Mac" , MAC_CHARSET},
+ {"Baltic" , BALTIC_CHARSET},
+#endif
+ {"OEM/DOS" , OEM_CHARSET}
+};
+
\f
/************************************************************************/
/* helpers */
return 1;
}
+
+
+
+\f
+/************************************************************************/
+/* exports */
+/************************************************************************/
+
+struct font_enum_t
+{
+ HDC hdc;
+ struct device *d;
+};
+
+static int CALLBACK
+font_enum_callback_2 (ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme,
+ int FontType, struct font_enum_t *font_enum)
+{
+ struct mswindows_font_enum *fontlist, **fonthead;
+ char fontname[MSW_FONTSIZE];
+ int i;
+
+ /*
+ * The enumerated font weights are not to be trusted because:
+ * a) lpelfe->elfStyle is only filled in for TrueType fonts.
+ * b) Not all Bold and Italic styles of all fonts (inluding some Vector,
+ * Truetype and Raster fonts) are enumerated.
+ * I guess that fonts for which Bold and Italic styles are generated
+ * 'on-the-fly' are not enumerated. It would be overly restrictive to
+ * disallow Bold And Italic weights for these fonts, so we just leave
+ * weights unspecified. This means that we have to weed out duplicates of
+ * those fonts that do get enumerated with different weights.
+ */
+ if (FontType == 0 /*vector*/ || FontType == TRUETYPE_FONTTYPE)
+ /* Scalable, so leave pointsize blank */
+ sprintf (fontname, "%s::::", lpelfe->elfLogFont.lfFaceName);
+ else
+ /* Formula for pointsize->height from LOGFONT docs in Platform SDK */
+ sprintf (fontname, "%s::%d::", lpelfe->elfLogFont.lfFaceName,
+ MulDiv (lpntme->ntmTm.tmHeight - lpntme->ntmTm.tmInternalLeading,
+ 72, DEVICE_MSWINDOWS_LOGPIXELSY (font_enum->d)));
+
+ /*
+ * The enumerated font character set strings are not to be trusted because
+ * lpelfe->elfScript is returned in the host language and not in English.
+ * We can't know a priori the translations of "Western", "Central European"
+ * etc into the host language, so we must use English. The same argument
+ * applies to the font weight string when matching fonts.
+ */
+ for (i=0; i<countof (charset_map); i++)
+ if (lpelfe->elfLogFont.lfCharSet == charset_map[i].value)
+ {
+ strcat (fontname, charset_map[i].name);
+ break;
+ }
+ if (i==countof (charset_map))
+ strcpy (fontname, charset_map[0].name);
+
+ /* Check that the new font is not a duplicate */
+ fonthead = &DEVICE_MSWINDOWS_FONTLIST (font_enum->d);
+ fontlist = *fonthead;
+ while (fontlist)
+ if (!strcmp (fontname, fontlist->fontname))
+ return 1; /* found a duplicate */
+ else
+ fontlist = fontlist->next;
+
+ /* Insert entry at head */
+ fontlist = *fonthead;
+ *fonthead = xmalloc (sizeof (struct mswindows_font_enum));
+ if (*fonthead == NULL)
+ {
+ *fonthead = fontlist;
+ return 0;
+ }
+ strcpy ((*fonthead)->fontname, fontname);
+ (*fonthead)->next = fontlist;
+ return 1;
+}
+
+static int CALLBACK
+font_enum_callback_1 (ENUMLOGFONTEX *lpelfe, NEWTEXTMETRICEX *lpntme,
+ int FontType, struct font_enum_t *font_enum)
+{
+ /* This function gets called once per facename per character set.
+ * We call a second callback to enumerate the fonts in each facename */
+ return EnumFontFamiliesEx (font_enum->hdc, &lpelfe->elfLogFont,
+ (FONTENUMPROC) font_enum_callback_2,
+ (LPARAM) font_enum, 0);
+}
+
+/*
+ * Enumerate the available fonts. Called by mswindows_init_device().
+ * Fills in the device's device-type-specfic fontlist.
+ */
+void
+mswindows_enumerate_fonts (struct device *d)
+{
+ HDC hdc = CreateCompatibleDC (NULL);
+ LOGFONT logfont;
+ struct font_enum_t font_enum;
+
+ assert (hdc!=NULL);
+ logfont.lfCharSet = DEFAULT_CHARSET;
+ logfont.lfFaceName[0] = '\0';
+ logfont.lfPitchAndFamily = DEFAULT_PITCH;
+ font_enum.hdc = hdc;
+ font_enum.d = d;
+ DEVICE_MSWINDOWS_FONTLIST (d) = NULL;
+ EnumFontFamiliesEx (hdc, &logfont, (FONTENUMPROC) font_enum_callback_1,
+ (LPARAM) (&font_enum), 0);
+ DeleteDC (hdc);
+}
+
\f
/************************************************************************/
/* methods */
}
}
+
static int
mswindows_initialize_font_instance (struct Lisp_Font_Instance *f, Lisp_Object name,
Lisp_Object device, Error_behavior errb)
{
CONST char *extname;
LOGFONT logfont;
- int fields;
+ int fields, i;
int pt;
char fontname[LF_FACESIZE], weight[LF_FACESIZE], *style, points[8];
char effects[LF_FACESIZE], charset[LF_FACESIZE];
char *c;
-
- GET_C_STRING_CTEXT_DATA_ALLOCA (f->name, extname);
+ HDC hdc;
+ HFONT holdfont;
+ TEXTMETRIC metrics;
+
+ extname = XSTRING_DATA (name);
/*
* mswindows fonts look like:
/* This function is implemented in a fairly ad-hoc manner.
* The general idea is to validate and canonicalize each of the above fields
* at the same time as we build up the win32 LOGFONT structure. This enables
- * us to use math_font() on a canonicalized font string to check the
+ * us to use match_font() on a canonicalized font string to check the
* availability of the requested font */
- if (fields<0)
+ if (fields < 0)
{
- maybe_signal_simple_error ("Invalid font", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Invalid font", name, Qfont, errb);
return (0);
}
}
else
{
- maybe_signal_simple_error ("Must specify a font name", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Must specify a font name", name, Qfont, errb);
return (0);
}
/* weight */
if (fields < 2)
- strcpy (weight, "Regular");
+ strcpy (weight, fontweight_map[0].name);
/* Maybe split weight into weight and style */
if ((c=strchr(weight, ' ')))
else
style = NULL;
-#define FROB(wgt) \
- if (stricmp (weight, #wgt) == 0) \
- logfont.lfWeight = FW_##wgt
-
- FROB (REGULAR);
- else FROB (THIN);
- else FROB (EXTRALIGHT);
- else FROB (ULTRALIGHT);
- else FROB (LIGHT);
- else FROB (NORMAL);
- else FROB (MEDIUM);
- else FROB (SEMIBOLD);
- else FROB (DEMIBOLD);
- else FROB (BOLD);
- else FROB (EXTRABOLD);
- else FROB (ULTRABOLD);
- else FROB (HEAVY);
- else FROB (BLACK);
- else if (!style)
- {
- logfont.lfWeight = FW_REGULAR;
- style = weight; /* May have specified style without weight */
- }
- else
+ for (i=0; i<countof (fontweight_map); i++)
+ if (!stricmp (weight, fontweight_map[i].name))
+ {
+ logfont.lfWeight = fontweight_map[i].value;
+ break;
+ }
+ if (i == countof (fontweight_map)) /* No matching weight */
{
- maybe_signal_simple_error ("Invalid font weight", f->name, Qfont, errb);
- return (0);
+ if (!style)
+ {
+ logfont.lfWeight = FW_REGULAR;
+ style = weight; /* May have specified style without weight */
+ }
+ else
+ {
+ maybe_signal_simple_error ("Invalid font weight", name, Qfont, errb);
+ return (0);
+ }
}
-#undef FROB
-
if (style)
{
/* #### what about oblique? */
logfont.lfItalic = TRUE;
else
{
- maybe_signal_simple_error ("Invalid font weight or style", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Invalid font weight or style", name, Qfont, errb);
return (0);
}
pt = 10; /* #### Should we reject strings that don't specify a size? */
else if ((pt=atoi(points)) == 0)
{
- maybe_signal_simple_error ("Invalid font pointsize", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Invalid font pointsize", name, Qfont, errb);
return (0);
}
/* Formula for pointsize->height from LOGFONT docs in MSVC5 Platform SDK */
- logfont.lfHeight = -MulDiv(pt, DEVICE_MSWINDOWS_LOGPIXELSY(XDEVICE (device)), 72);
+ logfont.lfHeight = -MulDiv(pt, DEVICE_MSWINDOWS_LOGPIXELSY (XDEVICE (device)), 72);
logfont.lfWidth = 0;
/* Effects */
logfont.lfStrikeOut = TRUE;
else
{
- maybe_signal_simple_error ("Invalid font effect", f->name,
- Qfont, errb);
+ maybe_signal_simple_error ("Invalid font effect", name, Qfont, errb);
return (0);
}
logfont.lfStrikeOut = TRUE;
else
{
- maybe_signal_simple_error ("Invalid font effect", f->name,
+ maybe_signal_simple_error ("Invalid font effect", name,
Qfont, errb);
return (0);
}
else
effects[0] = '\0';
-#define FROB(cs) \
- else if (stricmp (charset, #cs) == 0) \
- logfont.lfCharSet = cs##_CHARSET
-
- /* Charset aliases. Hangeul = Hangul is defined in windows.h.
- We do not use the name "russian", only "cyrillic", as it is
- the common name of this charset, used in other languages
- than Russian. */
-#define CYRILLIC_CHARSET RUSSIAN_CHARSET
-#define CENTRALEUROPEAN_CHARSET EASTEUROPE_CHARSET
-#define CENTRALEUROPEAN_CHARSET EASTEUROPE_CHARSET
-
+ /* Charset */
/* charset can be specified even if earlier fields havn't been */
- if ((fields < 5) && (c=strchr (extname, ':')) && (c=strchr (c+1, ':')) &&
- (c=strchr (c+1, ':')) && (c=strchr (c+1, ':')))
- {
- strncpy (charset, c+1, LF_FACESIZE);
- charset[LF_FACESIZE-1] = '\0';
- }
- else
- charset[0] = '\0';
-
- if (charset[0] == '\0' || (stricmp (charset, "ansi") == 0) ||
- (stricmp (charset, "western") == 0))
+ if (fields < 5)
{
- logfont.lfCharSet = ANSI_CHARSET;
- strcpy (charset, "western");
+ if ((c=strchr (extname, ':')) && (c=strchr (c+1, ':')) &&
+ (c=strchr (c+1, ':')) && (c=strchr (c+1, ':')))
+ {
+ strncpy (charset, c+1, LF_FACESIZE);
+ charset[LF_FACESIZE-1] = '\0';
+ }
+ else
+ strcpy (charset, charset_map[0].name);
}
- FROB (SYMBOL);
- FROB (SHIFTJIS);
- FROB (GB2312);
- FROB (HANGEUL);
- FROB (CHINESEBIG5);
- FROB (JOHAB);
- FROB (HEBREW);
- FROB (ARABIC);
- FROB (GREEK);
- FROB (TURKISH);
- FROB (THAI);
- FROB (EASTEUROPE);
- FROB (CENTRALEUROPEAN);
- FROB (CYRILLIC);
- FROB (MAC);
- FROB (BALTIC);
- else if (stricmp (charset, "oem/dos") == 0)
- logfont.lfCharSet = OEM_CHARSET;
- else
+
+ for (i=0; i<countof (charset_map); i++)
+ if (!stricmp (charset, charset_map[i].name))
+ {
+ logfont.lfCharSet = charset_map[i].value;
+ break;
+ }
+
+ if (i == countof (charset_map)) /* No matching charset */
{
- maybe_signal_simple_error ("Invalid charset", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Invalid charset", name, Qfont, errb);
return 0;
}
-#undef FROB
+ /* Misc crud */
+ logfont.lfEscapement = logfont.lfOrientation = 0;
+#if 1
+ logfont.lfOutPrecision = OUT_DEFAULT_PRECIS;
+ logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
+ logfont.lfQuality = DEFAULT_QUALITY;
+#else
+ logfont.lfOutPrecision = OUT_STROKE_PRECIS;
+ logfont.lfClipPrecision = CLIP_STROKE_PRECIS;
+ logfont.lfQuality = PROOF_QUALITY;
+#endif
+ /* Default to monospaced if the specified fontname doesn't exist. */
+ logfont.lfPitchAndFamily = FF_MODERN;
/* Windows will silently substitute a default font if the fontname
* specifies a non-existent font. So we check the font against the device's
- * list of font patterns to make sure that at least one of them matches */
+ * list of font patterns to make sure that at least one of them matches. */
{
struct mswindows_font_enum *fontlist;
char truename[MSW_FONTSIZE];
}
if (!done)
{
- maybe_signal_simple_error ("No matching font", f->name, Qfont, errb);
+ maybe_signal_simple_error ("No matching font", name, Qfont, errb);
return 0;
}
}
- /* Misc crud */
- logfont.lfEscapement = logfont.lfOrientation = 0;
-#if 1
- logfont.lfOutPrecision = OUT_DEFAULT_PRECIS;
- logfont.lfClipPrecision = CLIP_DEFAULT_PRECIS;
- logfont.lfQuality = DEFAULT_QUALITY;
-#else
- logfont.lfOutPrecision = OUT_STROKE_PRECIS;
- logfont.lfClipPrecision = CLIP_STROKE_PRECIS;
- logfont.lfQuality = PROOF_QUALITY;
-#endif
- /* Default to monospaced if the specified fontname doesn't exist.
- * The match_font calls above should mean that this can't happen. */
- logfont.lfPitchAndFamily = FF_MODERN;
-
if ((f->data = CreateFontIndirect(&logfont)) == NULL)
{
- maybe_signal_simple_error ("Couldn't create font", f->name, Qfont, errb);
+ maybe_signal_simple_error ("Couldn't create font", name, Qfont, errb);
return 0;
}
- {
- HDC hdc;
- HFONT holdfont;
- TEXTMETRIC metrics;
-
- hdc = CreateCompatibleDC (NULL);
- if (hdc)
- {
- holdfont = SelectObject(hdc, f->data);
- if (holdfont)
- {
- GetTextMetrics (hdc, &metrics);
- SelectObject(hdc, holdfont);
- DeleteDC (hdc);
- f->width = (unsigned short) metrics.tmAveCharWidth;
- f->height = (unsigned short) metrics.tmHeight;
- f->ascent = (unsigned short) metrics.tmAscent;
- f->descent = (unsigned short) metrics.tmDescent;
- f->proportional_p = (metrics.tmPitchAndFamily & TMPF_FIXED_PITCH);
- return 1;
- }
- DeleteDC (hdc);
- }
- mswindows_finalize_font_instance (f);
- maybe_signal_simple_error ("Couldn't map font", f->name, Qfont, errb);
- }
+ hdc = CreateCompatibleDC (NULL);
+ if (hdc)
+ {
+ holdfont = SelectObject(hdc, f->data);
+ if (holdfont)
+ {
+ GetTextMetrics (hdc, &metrics);
+ SelectObject(hdc, holdfont);
+ DeleteDC (hdc);
+ f->width = (unsigned short) metrics.tmAveCharWidth;
+ f->height = (unsigned short) metrics.tmHeight;
+ f->ascent = (unsigned short) metrics.tmAscent;
+ f->descent = (unsigned short) metrics.tmDescent;
+ f->proportional_p = (metrics.tmPitchAndFamily & TMPF_FIXED_PITCH);
+ return 1;
+ }
+ DeleteDC (hdc);
+ }
+ mswindows_finalize_font_instance (f);
+ maybe_signal_simple_error ("Couldn't map font", name, Qfont, errb);
return 0;
}
#include <winsock.h>
#endif
+/* Arbitrary size limit for code fragments passed to run_in_other_process */
+#define FRAGMENT_CODE_SIZE 32
+
/* Bound by winnt.el */
Lisp_Object Qnt_quote_process_args;
/*
* Run ROUTINE in the context of process determined by H_PROCESS. The
- * routine is passed the address of DATA as parameter. CODE_END is the
- * address immediately after ROUTINE's code. DATA_SIZE is the size of
+ * routine is passed the address of DATA as parameter. The ROUTINE must
+ * not be longer than ROUTINE_CODE_SIZE bytes. DATA_SIZE is the size of
* DATA structure.
*
* Note that the code must be positionally independent, and compiled
*/
static DWORD
run_in_other_process (HANDLE h_process,
- LPTHREAD_START_ROUTINE routine, LPVOID code_end,
+ LPTHREAD_START_ROUTINE routine,
LPVOID data, size_t data_size)
{
process_memory pm;
- size_t code_size = (LPBYTE)code_end - (LPBYTE)routine;
+ CONST size_t code_size = FRAGMENT_CODE_SIZE;
/* Need at most 3 extra bytes of memory, for data alignment */
size_t total_size = code_size + data_size + 3;
LPVOID remote_data;
* SIGKILL, SIGTERM, SIGQUIT, SIGHUP - These four translate to ExitProcess
* executed by the remote process
* SIGINT - The remote process is sent CTRL_BREAK_EVENT
+ *
+ * The MSVC5.0 compiler feels free to re-order functions within a
+ * compilation unit, so we have no way of finding out the size of the
+ * following functions. Therefore these functions must not be larger than
+ * FRAGMENT_CODE_SIZE.
*/
/*
return 1;
}
-/* Watermark in code space */
-static void
-sigkill_code_end (void)
-{
-}
-
/*
* Sending break or control c
*/
return (*data->adr_GenerateConsoleCtrlEvent) (data->event, 0);
}
-/* Watermark in code space */
-static void
-sigint_code_end (void)
-{
-}
-
/*
* Enabling signals
*/
return 1;
}
-/* Watermark in code space */
-static void
-sig_enable_code_end (void)
-{
-}
-
/*
* Send signal SIGNO to process H_PROCESS.
* Return nonzero if successful.
sigkill_data d;
d.adr_ExitProcess = GetProcAddress (h_kernel, "ExitProcess");
assert (d.adr_ExitProcess);
- retval = run_in_other_process (h_process,
- sigkill_proc, sigkill_code_end,
+ retval = run_in_other_process (h_process, sigkill_proc,
&d, sizeof (d));
break;
}
GetProcAddress (h_kernel, "GenerateConsoleCtrlEvent");
assert (d.adr_GenerateConsoleCtrlEvent);
d.event = CTRL_C_EVENT;
- retval = run_in_other_process (h_process,
- sigint_proc, sigint_code_end,
+ retval = run_in_other_process (h_process, sigint_proc,
&d, sizeof (d));
break;
}
d.adr_SetConsoleCtrlHandler =
GetProcAddress (h_kernel, "SetConsoleCtrlHandler");
assert (d.adr_SetConsoleCtrlHandler);
- run_in_other_process (h_process,
- sig_enable_proc, sig_enable_code_end,
+ run_in_other_process (h_process, sig_enable_proc,
&d, sizeof (d));
}
EMACS_SET_TTY_PROCESS_GROUP (xforkin, &piddly);
}
-# ifdef AIX
/* On AIX, we've disabled SIGHUP above once we start a
child on a pty. Now reenable it in the child, so it
- will die when we want it to. */
+ will die when we want it to.
+ JV: This needs to be done ALWAYS as we might have inherited
+ a SIG_IGN handling from our parent (nohup) and we are in new
+ process group.
+ */
signal (SIGHUP, SIG_DFL);
-# endif /* AIX */
}
#endif /* HAVE_PTYS */
\f
/* The hook `malloc' uses for the function which gets more space
from the system. */
-/* extern POINTER (*__morecore) (long size); */
+#ifndef DOUG_LEA_MALLOC
+extern POINTER (*__morecore) (long size);
+#endif
/* Initialize various things for memory allocation. */
mask |= GCBackground;
}
- if (IMAGE_INSTANCEP (bg_pmap)
- && IMAGE_INSTANCE_PIXMAP_TYPE_P (XIMAGE_INSTANCE (bg_pmap)))
+ /* This special case comes from a request to draw text with a face which has
+ the dim property. We'll use a stippled foreground GC. */
+ if (EQ (bg_pmap, Qdim))
+ {
+ assert (DEVICE_X_GRAY_PIXMAP (d) != None);
+
+ gcv.fill_style = FillStippled;
+ gcv.stipple = DEVICE_X_GRAY_PIXMAP (d);
+ mask |= (GCFillStyle | GCStipple);
+ }
+ else if (IMAGE_INSTANCEP (bg_pmap)
+ && IMAGE_INSTANCE_PIXMAP_TYPE_P (XIMAGE_INSTANCE (bg_pmap)))
{
if (XIMAGE_INSTANCE_PIXMAP_DEPTH (bg_pmap) == 0)
{
if (cursor && cursor_cachel && focus && NILP (bar_cursor_value))
gc = x_get_gc (d, font, cursor_cachel->foreground,
cursor_cachel->background, Qnil, Qnil);
+ else if (cachel->dim)
+ {
+ /* Ensure the gray bitmap exists */
+ if (DEVICE_X_GRAY_PIXMAP (d) == None)
+ DEVICE_X_GRAY_PIXMAP (d) =
+ XCreateBitmapFromData (dpy, x_win, (char *)gray_bits,
+ gray_width, gray_height);
+
+ /* Request a GC with the gray stipple pixmap to draw dimmed text */
+ gc = x_get_gc (d, font, cachel->foreground, cachel->background,
+ Qdim, Qnil);
+ }
else
gc = x_get_gc (d, font, cachel->foreground, cachel->background,
Qnil, Qnil);
temporary change to the echo area. */
&& !(MINI_WINDOW_P (w) && f->buffers_changed)
&& !f->frame_changed
- && !truncation_changed)
+ && !truncation_changed
+ /* check whether start is really at the begining of a line GE */
+ && (!w->start_at_line_beg || beginning_of_line_p (b, startp))
+ )
{
/* Check if the cursor has actually moved. */
if (EQ (Fmarker_buffer (w->last_point[CURRENT_DISP]), w->buffer)
highest_active_reg = NO_HIGHEST_ACTIVE_REG;
}
else
- highest_active_reg = r;
- }
+ {
+ highest_active_reg = r;
+
+ /* 98/9/21 jhod: We've also gotta set lowest_active_reg, don't we? */
+ r = 1;
+ while (r < highest_active_reg && !IS_ACTIVE(reg_info[r]))
+ r++;
+ lowest_active_reg = r;
+ }
+ }
/* If just failed to match something this time around with a
group that's operated on by a repetition operator, try to
/* cheesy way to determine cygwin version */
#ifndef NOT_C_CODE
#include <signal.h>
+#ifdef HAVE_CYGWIN32_VERSION_H
+#include <cygwin32/version.h>
+#else
#ifdef SIGIO
#define CYGWIN_B19
#else
#define BROKEN_CYGWIN
#endif
+#endif
+
extern void cygwin32_win32_to_posix_path_list(const char*, char*);
extern int cygwin32_win32_to_posix_path_list_buf_size(const char*);
extern void cygwin32_posix_to_win32_path_list(const char*, char*);
extern int cygwin32_posix_to_win32_path_list_buf_size(const char*);
+#ifndef CYGWIN_DLL_VERSION_MAJOR
struct timeval;
struct timezone;
struct itimerval;
extern int srandom( unsigned seed);
extern long random();
+
+#define SND_ASYNC 1
+#define SND_NODEFAULT 2
+#define SND_MEMORY 4
+#define SND_FILENAME 0x2000L
+#define VK_APPS 0x5D
+#define SIF_TRACKPOS 0x0010
+#endif
#endif
#ifdef HAVE_MS_WINDOWS
#define LIBS_SYSTEM -lwinmm
#define ICC_BAR_CLASSES 4
-#define SIF_TRACKPOS 0x0010
#define FW_BLACK FW_HEAVY
#define FW_ULTRABOLD FW_EXTRABOLD
#define FW_DEMIBOLD FW_SEMIBOLD
#define FW_ULTRALIGHT FW_EXTRALIGHT
-#define VK_APPS 0x5D
#define APPCMD_FILTERINITS 0x20L
#define CBF_FAIL_SELFCONNECTIONS 0x1000
#define CBF_SKIP_ALLNOTIFICATIONS 0x3C0000
#define CBF_FAIL_POKES 0x10000
#define CBF_FAIL_REQUESTS 0x20000
#define SZDDESYS_TOPIC "System"
-#define SND_ASYNC 1
-#define SND_NODEFAULT 2
-#define SND_MEMORY 4
-#define SND_FILENAME 0x2000L
#define JOHAB_CHARSET 130
#define MAC_CHARSET 77
#define regoff_t sys_regoff_t
#define regmatch_t sys_regmatch_t
+/* A perfectly ordinary link wins again - martin */
#undef C_SWITCH_SYSTEM
-#define C_SWITCH_SYSTEM "-D_BSD"
+#undef LIBS_SYSTEM
+#undef LIBS_DEBUG
+#define ORDINARY_LINK
#define SYSTEM_MALLOC
+#if 0 /* martin */
/* Some V4.0* versions before V4.0B don't detect rename properly. */
#ifndef HAVE_RENAME
#define HAVE_RENAME
#endif
#define LIBS_DEBUG
+#endif /* 0 */
#define LIBS_TERMCAP "-ltermcap"
+#ifdef __ELF__ /* since from 3.0-CURRENT(maybe 19980831 or later) */
+#ifndef NOT_C_CODE
+#include <stddef.h>
+#endif
+#define LD_SWITCH_SYSTEM
+#define START_FILES pre-crt0.o /usr/lib/crt1.o /usr/lib/crti.o /usr/lib/crtbegin.o
+#define UNEXEC unexelf.o
+#define LIB_STANDARD -lgcc -lc -lgcc /usr/lib/crtend.o /usr/lib/crtn.o
+#define LINKER "$(CC) -nostdlib"
+#undef LIB_GCC
+#define LIB_GCC
+
+#else /* not __ELF__ */
+
#ifndef NO_SHARED_LIBS
#if 0 /* mrb */
#define LIB_GCC "-lgcc"
#endif /* __FreeBSD__ */
#endif /* NO_SHARED_LIBS */
+#endif /* not __ELF__ */
+
#define HAVE_GETLOADAVG
/* #define NO_TERMIO */ /* detected in configure */
#define DECLARE_GETPWUID_WITH_UID_T
if (EQ (b->undo_list, Qt))
return (0);
- if (NILP (last_undo_buffer) || b != XBUFFER (last_undo_buffer))
+ if (NILP (last_undo_buffer)
+ || (BUFFER_BASE_BUFFER (b)
+ != BUFFER_BASE_BUFFER (XBUFFER (last_undo_buffer))))
{
undo_boundary (b);
XSETBUFFER (last_undo_buffer, b);
#define DEFAULT_ENTRY_ADDRESS __start
#endif
\f
-unexec (new_name, a_name, data_start, bss_start, entry_address)
- char *new_name, *a_name;
- unsigned long data_start, bss_start, entry_address;
+int
+unexec (char *new_name, char *a_name,
+ unsigned long data_start,
+ unsigned long bss_start,
+ unsigned long entry_address)
{
int new, old;
char * oldptr;
struct stat stat;
long pagesize, brk;
long newsyms, symrel;
- int nread;
int i;
long vaddr, scnptr;
#define BUFSIZE 8192
*/
-
-update_dynamic_symbols (old, new_name, new, newsyms, nsyms, symoff, stroff)
- char *old; /* Pointer to old executable */
- char *new_name; /* Name of new executable */
- int new; /* File descriptor for new executable */
- long newsyms; /* Offset of Symbol table in new executable */
- int nsyms; /* Number of symbol table entries */
- long symoff; /* Offset of External Symbols in old file */
- long stroff; /* Offset of string table in old file */
+int
+update_dynamic_symbols (
+ char *old, /* Pointer to old executable */
+ char *new_name, /* Name of new executable */
+ int new, /* File descriptor for new executable */
+ long newsyms, /* Offset of Symbol table in new executable */
+ int nsyms, /* Number of symbol table entries */
+ long symoff, /* Offset of External Symbols in old file */
+ long stroff) /* Offset of string table in old file */
{
long i;
int found = 0;
for (; symp < symendp; symp ++)
if (strcmp ((char *) (symnames + symp->st_name), "_end") == 0
- || strcmp ((char *) (symnames + symp->st_name), "_edata") == 0)
+ || strcmp ((char *) (symnames + symp->st_name), "end") == 0
+ || strcmp ((char *) (symnames + symp->st_name), "_edata") == 0
+ || strcmp ((char *) (symnames + symp->st_name), "edata") == 0)
memcpy (&symp->st_value, &new_bss_addr, sizeof (new_bss_addr));
}
CHECK_INT_COERCE_MARKER (pos);
set_marker_restricted (w->start[CURRENT_DISP], pos, w->buffer);
/* this is not right, but much easier than doing what is right. */
- w->start_at_line_beg = 0;
+ /* w->start_at_line_beg = 0; */
+ /* WTF is the above supposed to mean? GE */
+ w->start_at_line_beg = beginning_of_line_p (XBUFFER (w->buffer), XINT (pos));
if (NILP (noforce))
w->force_start = 1;
w->redo_modeline = 1;
make_int (XBUFFER (buffer)->last_window_start),
buffer);
Fset_marker (w->sb_point, w->start[CURRENT_DISP], buffer);
- w->start_at_line_beg = 0;
+ /* set start_at_line_beg correctly. GE */
+ w->start_at_line_beg = beginning_of_line_p (XBUFFER (buffer),
+ XBUFFER (buffer)->last_window_start);
w->force_start = 0; /* Lucid fix */
SET_LAST_MODIFIED (w, 1);
SET_LAST_FACECHANGE (w);