comparison src/event-stream.c @ 934:c925bacdda60

[xemacs-hg @ 2002-07-29 09:21:12 by michaels] 2002-07-17 Marcus Crestani <crestani@informatik.uni-tuebingen.de> Markus Kaltenbach <makalten@informatik.uni-tuebingen.de> Mike Sperber <mike@xemacs.org> configure flag to turn these changes on: --use-kkcc First we added a dumpable flag to lrecord_implementation. It shows, if the object is dumpable and should be processed by the dumper. * lrecord.h (struct lrecord_implementation): added dumpable flag (MAKE_LRECORD_IMPLEMENTATION): fitted the different makro definitions to the new lrecord_implementation and their calls. Then we changed mark_object, that it no longer needs a mark method for those types that have pdump descritions. * alloc.c: (mark_object): If the object has a description, the new mark algorithm is called, and the object is marked according to its description. Otherwise it uses the mark method like before. These procedures mark objects according to their descriptions. They are modeled on the corresponding pdumper procedures. (mark_with_description): (get_indirect_count): (structure_size): (mark_struct_contents): These procedures still call mark_object, this is needed while there are Lisp_Objects without descriptions left. We added pdump descriptions for many Lisp_Objects: * extents.c: extent_auxiliary_description * database.c: database_description * gui.c: gui_item_description * scrollbar.c: scrollbar_instance_description * toolbar.c: toolbar_button_description * event-stream.c: command_builder_description * mule-charset.c: charset_description * device-msw.c: devmode_description * dialog-msw.c: mswindows_dialog_id_description * eldap.c: ldap_description * postgresql.c: pgconn_description pgresult_description * tooltalk.c: tooltalk_message_description tooltalk_pattern_description * ui-gtk.c: emacs_ffi_description emacs_gtk_object_description * events.c: * events.h: * event-stream.c: * event-Xt.c: * event-gtk.c: * event-tty.c: To write a pdump description for Lisp_Event, we converted every struct in the union event to a Lisp_Object. So we created nine new Lisp_Objects: Lisp_Key_Data, Lisp_Button_Data, Lisp_Motion_Data, Lisp_Process_Data, Lisp_Timeout_Data, Lisp_Eval_Data, Lisp_Misc_User_Data, Lisp_Magic_Data, Lisp_Magic_Eval_Data. We also wrote makro selectors and mutators for the fields of the new designed Lisp_Event and added everywhere these new abstractions. We implemented XD_UNION support in (mark_with_description), so we can describe exspecially console/device specific data with XD_UNION. To describe with XD_UNION, we added a field to these objects, which holds the variant type of the object. This field is initialized in the appendant constructor. The variant is an integer, it has also to be described in an description, if XD_UNION is used. XD_UNION is used in following descriptions: * console.c: console_description (get_console_variant): returns the variant (create_console): added variant initialization * console.h (console_variant): the different console types * console-impl.h (struct console): added enum console_variant contype * device.c: device_description (Fmake_device): added variant initialization * device-impl.h (struct device): added enum console_variant devtype * objects.c: image_instance_description font_instance_description (Fmake_color_instance): added variant initialization (Fmake_font_instance): added variant initialization * objects-impl.h (struct Lisp_Color_Instance): added color_instance_type * objects-impl.h (struct Lisp_Font_Instance): added font_instance_type * process.c: process_description (make_process_internal): added variant initialization * process.h (process_variant): the different process types
author michaels
date Mon, 29 Jul 2002 09:21:25 +0000
parents b0c24ea6a2a8
children 345b7d75cab4
comparison
equal deleted inserted replaced
933:f6bc42928b34 934:c925bacdda60
316 #define CHECK_COMMAND_BUILDER(x) CHECK_RECORD (x, command_builder) 316 #define CHECK_COMMAND_BUILDER(x) CHECK_RECORD (x, command_builder)
317 #define CONCHECK_COMMAND_BUILDER(x) CONCHECK_RECORD (x, command_builder) 317 #define CONCHECK_COMMAND_BUILDER(x) CONCHECK_RECORD (x, command_builder)
318 318
319 static Lisp_Object Vcommand_builder_free_list; 319 static Lisp_Object Vcommand_builder_free_list;
320 320
321 #ifdef USE_KKCC
322 static const struct lrecord_description munging_key_translation_description_1 [] = {
323 { XD_LISP_OBJECT, offsetof (struct munging_key_translation, first_mungeable_event) },
324 { XD_END }
325 };
326
327 static const struct struct_description munging_key_translation_description = {
328 sizeof (Lisp_Object),
329 munging_key_translation_description_1
330 };
331
332 static const struct lrecord_description command_builder_description [] = {
333 { XD_LISP_OBJECT, offsetof (struct command_builder, current_events) },
334 { XD_LISP_OBJECT, offsetof (struct command_builder, most_current_event) },
335 { XD_LISP_OBJECT, offsetof (struct command_builder, last_non_munged_event) },
336 { XD_LISP_OBJECT, offsetof (struct command_builder, console) },
337 { XD_STRUCT_ARRAY, offsetof (struct command_builder, munge_me), 2, &munging_key_translation_description },
338 { XD_END }
339 };
340 #endif /* USE_KKCC */
341
321 static Lisp_Object 342 static Lisp_Object
322 mark_command_builder (Lisp_Object obj) 343 mark_command_builder (Lisp_Object obj)
323 { 344 {
324 struct command_builder *builder = XCOMMAND_BUILDER (obj); 345 struct command_builder *builder = XCOMMAND_BUILDER (obj);
325 mark_object (builder->current_events); 346 mark_object (builder->current_events);
342 b->echo_buf = 0; 363 b->echo_buf = 0;
343 } 364 }
344 } 365 }
345 } 366 }
346 367
368 #ifdef USE_KKCC
369 DEFINE_LRECORD_IMPLEMENTATION ("command-builder", command_builder,
370 0, /*dumpable-flag*/
371 mark_command_builder, internal_object_printer,
372 finalize_command_builder, 0, 0,
373 command_builder_description,
374 struct command_builder);
375 #else /* not USE_KKCC */
347 DEFINE_LRECORD_IMPLEMENTATION ("command-builder", command_builder, 376 DEFINE_LRECORD_IMPLEMENTATION ("command-builder", command_builder,
348 mark_command_builder, internal_object_printer, 377 mark_command_builder, internal_object_printer,
349 finalize_command_builder, 0, 0, 0, 378 finalize_command_builder, 0, 0, 0,
350 struct command_builder); 379 struct command_builder);
380 #endif /* not USE_KKCC */
351 381
352 static void 382 static void
353 reset_command_builder_event_chain (struct command_builder *builder) 383 reset_command_builder_event_chain (struct command_builder *builder)
354 { 384 {
355 builder->current_events = Qnil; 385 builder->current_events = Qnil;
759 { 789 {
760 buf_index = 0; /* We're echoing now */ 790 buf_index = 0; /* We're echoing now */
761 clear_echo_area (selected_frame (), Qnil, 0); 791 clear_echo_area (selected_frame (), Qnil, 0);
762 } 792 }
763 793
764 format_event_object (buf, XEVENT (event), 1); 794 #ifdef USE_KKCC
795 format_event_object (buf, event, 1);
796 #else /* not USE_KKCC */
797 format_event_object (buf, XEVENT(event), 1);
798 #endif /* not USE_KKCC */
765 len = eilen (buf); 799 len = eilen (buf);
766 800
767 if (len + buf_index + 4 > command_builder->echo_buf_length) 801 if (len + buf_index + 4 > command_builder->echo_buf_length)
768 { 802 {
769 eifree (buf); 803 eifree (buf);
874 { 908 {
875 Lisp_Object traduit = Fgethash (make_char (c), Vkeyboard_translate_table, 909 Lisp_Object traduit = Fgethash (make_char (c), Vkeyboard_translate_table,
876 Qnil); 910 Qnil);
877 if (!NILP (traduit) && SYMBOLP (traduit)) 911 if (!NILP (traduit) && SYMBOLP (traduit))
878 { 912 {
913 #ifdef USE_KKCC
914 XSET_KEY_DATA_KEYSYM (XEVENT_DATA (event), traduit);
915 XSET_KEY_DATA_MODIFIERS (XEVENT_DATA (event), 0);
916 #else /* not USE_KKCC */
879 XEVENT (event)->event.key.keysym = traduit; 917 XEVENT (event)->event.key.keysym = traduit;
880 XEVENT (event)->event.key.modifiers = 0; 918 XEVENT (event)->event.key.modifiers = 0;
919 #endif /* not USE_KKCC */
881 did_translate = 1; 920 did_translate = 1;
882 } 921 }
883 else if (CHARP (traduit)) 922 else if (CHARP (traduit))
884 { 923 {
924 #ifdef USE_KKCC
925 Lisp_Object ev2 = Fmake_event(Qnil, Qnil);
926 #else /* not USE_KKCC */
885 Lisp_Event ev2; 927 Lisp_Event ev2;
886 928
887 /* This used to call Fcharacter_to_event() directly into EVENT, 929 /* This used to call Fcharacter_to_event() directly into EVENT,
888 but that can eradicate timestamps and other such stuff. 930 but that can eradicate timestamps and other such stuff.
889 This way is safer. */ 931 This way is safer. */
890 zero_event (&ev2); 932 zero_event (&ev2);
933 #endif /* not USE_KKCC */
934
935 #ifdef USE_KKCC
936 character_to_event (XCHAR (traduit), XEVENT (ev2),
937 XCONSOLE (XEVENT_CHANNEL (event)), 1, 1);
938 XSET_KEY_DATA_KEYSYM (XEVENT_DATA (event), XKEY_DATA_KEYSYM (XEVENT_DATA (ev2)));
939 XSET_KEY_DATA_MODIFIERS (XEVENT_DATA (event),
940 XKEY_DATA_MODIFIERS (XEVENT_DATA (ev2)));
941 #else /* not USE_KKCC */
891 character_to_event (XCHAR (traduit), &ev2, 942 character_to_event (XCHAR (traduit), &ev2,
892 XCONSOLE (EVENT_CHANNEL (XEVENT (event))), 1, 1); 943 XCONSOLE (EVENT_CHANNEL (XEVENT (event))), 1, 1);
893 XEVENT (event)->event.key.keysym = ev2.event.key.keysym; 944 XEVENT (event)->event.key.keysym = ev2.event.key.keysym;
894 XEVENT (event)->event.key.modifiers = ev2.event.key.modifiers; 945 XEVENT (event)->event.key.modifiers = ev2.event.key.modifiers;
946 #endif /* not USE_KKCC */
895 did_translate = 1; 947 did_translate = 1;
896 } 948 }
897 } 949 }
898 950
899 if (!did_translate) 951 if (!did_translate)
900 { 952 {
953 #ifdef USE_KKCC
954 Lisp_Object traduit = Fgethash (XKEY_DATA_KEYSYM (XEVENT_DATA (event)),
955 Vkeyboard_translate_table, Qnil);
956 #else /* not USE_KKCC */
901 Lisp_Object traduit = Fgethash (XEVENT (event)->event.key.keysym, 957 Lisp_Object traduit = Fgethash (XEVENT (event)->event.key.keysym,
902 Vkeyboard_translate_table, Qnil); 958 Vkeyboard_translate_table, Qnil);
959 #endif /* not USE_KKCC */
903 if (!NILP (traduit) && SYMBOLP (traduit)) 960 if (!NILP (traduit) && SYMBOLP (traduit))
904 { 961 {
962 #ifdef USE_KKCC
963 XSET_KEY_DATA_KEYSYM (XEVENT_DATA (event), traduit);
964 #else /* not USE_KKCC */
905 XEVENT (event)->event.key.keysym = traduit; 965 XEVENT (event)->event.key.keysym = traduit;
966 #endif /* not USE_KKCC */
906 did_translate = 1; 967 did_translate = 1;
907 } 968 }
908 else if (CHARP (traduit)) 969 else if (CHARP (traduit))
909 { 970 {
971 #ifdef USE_KKCC
972 Lisp_Object ev2 = Fmake_event(Qnil, Qnil);
973 #else /* not USE_KKCC */
910 Lisp_Event ev2; 974 Lisp_Event ev2;
911 975
976 /* This used to call Fcharacter_to_event() directly into EVENT,
977 but that can eradicate timestamps and other such stuff.
978 This way is safer. */
912 zero_event (&ev2); 979 zero_event (&ev2);
980 #endif /* not USE_KKCC */
981
982 #ifdef USE_KKCC
983 character_to_event (XCHAR (traduit), XEVENT (ev2),
984 XCONSOLE (XEVENT_CHANNEL (event)), 1, 1);
985 XSET_KEY_DATA_KEYSYM (XEVENT_DATA (event), XKEY_DATA_KEYSYM (XEVENT_DATA (ev2)));
986 XSET_KEY_DATA_MODIFIERS (XEVENT_DATA (event),
987 XKEY_DATA_MODIFIERS (XEVENT_DATA (event)) |
988 XKEY_DATA_MODIFIERS (XEVENT_DATA (ev2)));
989 #else /* not USE_KKCC */
913 character_to_event (XCHAR (traduit), &ev2, 990 character_to_event (XCHAR (traduit), &ev2,
914 XCONSOLE (EVENT_CHANNEL (XEVENT (event))), 1, 1); 991 XCONSOLE (EVENT_CHANNEL (XEVENT (event))), 1, 1);
915 XEVENT (event)->event.key.keysym = ev2.event.key.keysym; 992 XEVENT (event)->event.key.keysym = ev2.event.key.keysym;
916 XEVENT (event)->event.key.modifiers |= ev2.event.key.modifiers; 993 XEVENT (event)->event.key.modifiers |= ev2.event.key.modifiers;
994 #endif /* not USE_KKCC */
995
917 did_translate = 1; 996 did_translate = 1;
918 } 997 }
919 } 998 }
920 999
921 #ifdef DEBUG_XEMACS 1000 #ifdef DEBUG_XEMACS
1228 { XD_LISP_OBJECT, offsetof (Lisp_Timeout, function) }, 1307 { XD_LISP_OBJECT, offsetof (Lisp_Timeout, function) },
1229 { XD_LISP_OBJECT, offsetof (Lisp_Timeout, object) }, 1308 { XD_LISP_OBJECT, offsetof (Lisp_Timeout, object) },
1230 { XD_END } 1309 { XD_END }
1231 }; 1310 };
1232 1311
1312 #ifdef USE_KKCC
1313 DEFINE_LRECORD_IMPLEMENTATION ("timeout", timeout,
1314 1, /*dumpable-flag*/
1315 mark_timeout, internal_object_printer,
1316 0, 0, 0, timeout_description, Lisp_Timeout);
1317 #else /* not USE_KKCC */
1233 DEFINE_LRECORD_IMPLEMENTATION ("timeout", timeout, 1318 DEFINE_LRECORD_IMPLEMENTATION ("timeout", timeout,
1234 mark_timeout, internal_object_printer, 1319 mark_timeout, internal_object_printer,
1235 0, 0, 0, timeout_description, Lisp_Timeout); 1320 0, 0, 0, timeout_description, Lisp_Timeout);
1321 #endif /* not USE_KKCC */
1236 1322
1237 /* Generate a timeout and return its ID. */ 1323 /* Generate a timeout and return its ID. */
1238 1324
1239 int 1325 int
1240 event_stream_generate_wakeup (unsigned int milliseconds, 1326 event_stream_generate_wakeup (unsigned int milliseconds,
1626 1712
1627 void 1713 void
1628 enqueue_magic_eval_event (void (*fun) (Lisp_Object), Lisp_Object object) 1714 enqueue_magic_eval_event (void (*fun) (Lisp_Object), Lisp_Object object)
1629 { 1715 {
1630 Lisp_Object event = Fmake_event (Qnil, Qnil); 1716 Lisp_Object event = Fmake_event (Qnil, Qnil);
1631 1717 #ifdef USE_KKCC
1718 XSET_EVENT_TYPE (event, magic_eval_event);
1719 /* channel for magic_eval events is nil */
1720 XSET_MAGIC_EVAL_DATA_INTERNAL_FUNCTION (XEVENT_DATA (event), fun);
1721 XSET_MAGIC_EVAL_DATA_OBJECT (XEVENT_DATA (event), object);
1722 #else /* not USE_KKCC */
1632 XEVENT (event)->event_type = magic_eval_event; 1723 XEVENT (event)->event_type = magic_eval_event;
1633 /* channel for magic_eval events is nil */ 1724 /* channel for magic_eval events is nil */
1634 XEVENT (event)->event.magic_eval.internal_function = fun; 1725 XEVENT (event)->event.magic_eval.internal_function = fun;
1635 XEVENT (event)->event.magic_eval.object = object; 1726 XEVENT (event)->event.magic_eval.object = object;
1727 #endif /* not USE_KKCC */
1636 enqueue_command_event (event); 1728 enqueue_command_event (event);
1637 } 1729 }
1638 1730
1639 DEFUN ("enqueue-eval-event", Fenqueue_eval_event, 2, 2, 0, /* 1731 DEFUN ("enqueue-eval-event", Fenqueue_eval_event, 2, 2, 0, /*
1640 Add an eval event to the back of the eval event queue. 1732 Add an eval event to the back of the eval event queue.
1645 */ 1737 */
1646 (function, object)) 1738 (function, object))
1647 { 1739 {
1648 Lisp_Object event = Fmake_event (Qnil, Qnil); 1740 Lisp_Object event = Fmake_event (Qnil, Qnil);
1649 1741
1742 #ifdef USE_KKCC
1743 XSET_EVENT_TYPE (event, eval_event);
1744 /* channel for eval events is nil */
1745 XSET_EVAL_DATA_FUNCTION (XEVENT_DATA (event), function);
1746 XSET_EVAL_DATA_OBJECT (XEVENT_DATA (event), object);
1747 #else /* not USE_KKCC */
1650 XEVENT (event)->event_type = eval_event; 1748 XEVENT (event)->event_type = eval_event;
1651 /* channel for eval events is nil */ 1749 /* channel for eval events is nil */
1652 XEVENT (event)->event.eval.function = function; 1750 XEVENT (event)->event.eval.function = function;
1653 XEVENT (event)->event.eval.object = object; 1751 XEVENT (event)->event.eval.object = object;
1752 #endif /* not USE_KKCC */
1654 enqueue_command_event (event); 1753 enqueue_command_event (event);
1655 1754
1656 return event; 1755 return event;
1657 } 1756 }
1658 1757
1659 Lisp_Object 1758 Lisp_Object
1660 enqueue_misc_user_event (Lisp_Object channel, Lisp_Object function, 1759 enqueue_misc_user_event (Lisp_Object channel, Lisp_Object function,
1661 Lisp_Object object) 1760 Lisp_Object object)
1662 { 1761 {
1663 Lisp_Object event = Fmake_event (Qnil, Qnil); 1762 Lisp_Object event = Fmake_event (Qnil, Qnil);
1664 1763 #ifdef USE_KKCC
1764 XSET_EVENT_TYPE (event, misc_user_event);
1765 XSET_EVENT_CHANNEL (event, channel);
1766 XSET_MISC_USER_DATA_FUNCTION (XEVENT_DATA (event), function);
1767 XSET_MISC_USER_DATA_OBJECT (XEVENT_DATA (event), object);
1768 XSET_MISC_USER_DATA_BUTTON (XEVENT_DATA (event), 0);
1769 XSET_MISC_USER_DATA_MODIFIERS (XEVENT_DATA (event), 0);
1770 XSET_MISC_USER_DATA_X (XEVENT_DATA (event), -1);
1771 XSET_MISC_USER_DATA_Y (XEVENT_DATA (event), -1);
1772 #else /* not USE_KKCC */
1665 XEVENT (event)->event_type = misc_user_event; 1773 XEVENT (event)->event_type = misc_user_event;
1666 XEVENT (event)->channel = channel; 1774 XEVENT (event)->channel = channel;
1667 XEVENT (event)->event.misc.function = function; 1775 XEVENT (event)->event.misc.function = function;
1668 XEVENT (event)->event.misc.object = object; 1776 XEVENT (event)->event.misc.object = object;
1669 XEVENT (event)->event.misc.button = 0; 1777 XEVENT (event)->event.misc.button = 0;
1670 XEVENT (event)->event.misc.modifiers = 0; 1778 XEVENT (event)->event.misc.modifiers = 0;
1671 XEVENT (event)->event.misc.x = -1; 1779 XEVENT (event)->event.misc.x = -1;
1672 XEVENT (event)->event.misc.y = -1; 1780 XEVENT (event)->event.misc.y = -1;
1781 #endif /* not USE_KKCC */
1673 enqueue_command_event (event); 1782 enqueue_command_event (event);
1674 1783
1675 return event; 1784 return event;
1676 } 1785 }
1677 1786
1680 Lisp_Object object, 1789 Lisp_Object object,
1681 int button, int modifiers, int x, int y) 1790 int button, int modifiers, int x, int y)
1682 { 1791 {
1683 Lisp_Object event = Fmake_event (Qnil, Qnil); 1792 Lisp_Object event = Fmake_event (Qnil, Qnil);
1684 1793
1794 #ifdef USE_KKCC
1795 XSET_EVENT_TYPE (event, misc_user_event);
1796 XSET_EVENT_CHANNEL (event, channel);
1797 XSET_MISC_USER_DATA_FUNCTION (XEVENT_DATA (event), function);
1798 XSET_MISC_USER_DATA_OBJECT (XEVENT_DATA (event), object);
1799 XSET_MISC_USER_DATA_BUTTON (XEVENT_DATA (event), button);
1800 XSET_MISC_USER_DATA_MODIFIERS (XEVENT_DATA (event), modifiers);
1801 XSET_MISC_USER_DATA_X (XEVENT_DATA (event), x);
1802 XSET_MISC_USER_DATA_Y (XEVENT_DATA (event), y);
1803 #else /* not USE_KKCC */
1685 XEVENT (event)->event_type = misc_user_event; 1804 XEVENT (event)->event_type = misc_user_event;
1686 XEVENT (event)->channel = channel; 1805 XEVENT (event)->channel = channel;
1687 XEVENT (event)->event.misc.function = function; 1806 XEVENT (event)->event.misc.function = function;
1688 XEVENT (event)->event.misc.object = object; 1807 XEVENT (event)->event.misc.object = object;
1689 XEVENT (event)->event.misc.button = button; 1808 XEVENT (event)->event.misc.button = button;
1690 XEVENT (event)->event.misc.modifiers = modifiers; 1809 XEVENT (event)->event.misc.modifiers = modifiers;
1691 XEVENT (event)->event.misc.x = x; 1810 XEVENT (event)->event.misc.x = x;
1692 XEVENT (event)->event.misc.y = y; 1811 XEVENT (event)->event.misc.y = y;
1812 #endif /* not USE_KKCC */
1693 enqueue_command_event (event); 1813 enqueue_command_event (event);
1694 1814
1695 return event; 1815 return event;
1696 } 1816 }
1697 1817
2072 /* The command_event_queue was empty. Wait for an event. */ 2192 /* The command_event_queue was empty. Wait for an event. */
2073 event_stream_next_event (e); 2193 event_stream_next_event (e);
2074 /* If this was a timeout, then we need to extract some data 2194 /* If this was a timeout, then we need to extract some data
2075 out of the returned closure and might need to resignal 2195 out of the returned closure and might need to resignal
2076 it. */ 2196 it. */
2197 #ifdef USE_KKCC
2198 if (EVENT_TYPE (e) == timeout_event)
2199 #else /* not USE_KKCC */
2077 if (e->event_type == timeout_event) 2200 if (e->event_type == timeout_event)
2201 #endif /* not USE_KKCC */
2078 { 2202 {
2079 Lisp_Object tristan, isolde; 2203 Lisp_Object tristan, isolde;
2080 2204
2205 #ifdef USE_KKCC
2206 XSET_TIMEOUT_DATA_ID_NUMBER (EVENT_DATA (e),
2207 event_stream_resignal_wakeup (XTIMEOUT_DATA_INTERVAL_ID (EVENT_DATA (e)), 0, &tristan, &isolde));
2208
2209 XSET_TIMEOUT_DATA_FUNCTION (EVENT_DATA (e), tristan);
2210 XSET_TIMEOUT_DATA_OBJECT (EVENT_DATA (e), isolde);
2211 /* next_event_internal() doesn't print out timeout events
2212 because of the extra info we just set. */
2213 #else /* not USE_KKCC */
2081 e->event.timeout.id_number = 2214 e->event.timeout.id_number =
2082 event_stream_resignal_wakeup (e->event.timeout.interval_id, 0, 2215 event_stream_resignal_wakeup (e->event.timeout.interval_id, 0,
2083 &tristan, &isolde); 2216 &tristan, &isolde);
2084 2217
2085 e->event.timeout.function = tristan; 2218 e->event.timeout.function = tristan;
2086 e->event.timeout.object = isolde; 2219 e->event.timeout.object = isolde;
2087 /* next_event_internal() doesn't print out timeout events 2220 /* next_event_internal() doesn't print out timeout events
2088 because of the extra info we just set. */ 2221 because of the extra info we just set. */
2222 #endif /* not USE_KKCC */
2089 DEBUG_PRINT_EMACS_EVENT ("real, timeout", target_event); 2223 DEBUG_PRINT_EMACS_EVENT ("real, timeout", target_event);
2090 } 2224 }
2091 2225
2092 /* If we read a ^G, then set quit-flag and try to QUIT. 2226 /* If we read a ^G, then set quit-flag and try to QUIT.
2093 This may be blocked (see above). 2227 This may be blocked (see above).
2094 */ 2228 */
2229 #ifdef USE_KKCC
2230 if (EVENT_TYPE (e) == key_press_event &&
2231 #else /* not USE_KKCC */
2095 if (e->event_type == key_press_event && 2232 if (e->event_type == key_press_event &&
2233 #endif /* not USE_KKCC */
2096 event_matches_key_specifier_p 2234 event_matches_key_specifier_p
2097 (e, make_char (CONSOLE_QUIT_CHAR (XCONSOLE (EVENT_CHANNEL (e)))))) 2235 (e, make_char (CONSOLE_QUIT_CHAR (XCONSOLE (EVENT_CHANNEL (e))))))
2098 { 2236 {
2099 Vquit_flag = Qt; 2237 Vquit_flag = Qt;
2100 QUIT; 2238 QUIT;
2451 (event, prompt)) 2589 (event, prompt))
2452 { 2590 {
2453 /* This function can GC */ 2591 /* This function can GC */
2454 struct gcpro gcpro1; 2592 struct gcpro gcpro1;
2455 GCPRO1 (event); 2593 GCPRO1 (event);
2456 2594
2457 maybe_echo_keys (XCOMMAND_BUILDER 2595 maybe_echo_keys (XCOMMAND_BUILDER
2458 (XCONSOLE (Vselected_console)-> 2596 (XCONSOLE (Vselected_console)->
2459 command_builder), 0); /* #### This sucks bigtime */ 2597 command_builder), 0); /* #### This sucks bigtime */
2460 2598
2461 for (;;) 2599 for (;;)
2739 switch (XEVENT_TYPE (event)) 2877 switch (XEVENT_TYPE (event))
2740 { 2878 {
2741 case process_event: 2879 case process_event:
2742 { 2880 {
2743 if (NILP (process) || 2881 if (NILP (process) ||
2882 #ifdef USE_KKCC
2883 EQ (XPROCESS_DATA_PROCESS (XEVENT_DATA (event)), process))
2884 #else /* not USE_KKCC */
2744 EQ (XEVENT (event)->event.process.process, process)) 2885 EQ (XEVENT (event)->event.process.process, process))
2886 #endif /* not USE_KKCC */
2745 { 2887 {
2746 done = 1; 2888 done = 1;
2747 /* RMS's version always returns nil when proc is nil, 2889 /* RMS's version always returns nil when proc is nil,
2748 and only returns t if input ever arrived on proc. */ 2890 and only returns t if input ever arrived on proc. */
2749 result = Qt; 2891 result = Qt;
3021 case empty_event: 3163 case empty_event:
3022 return; 3164 return;
3023 3165
3024 case eval_event: 3166 case eval_event:
3025 { 3167 {
3168 #ifdef USE_KKCC
3169 call1 (XEVAL_DATA_FUNCTION (XEVENT_DATA (event)),
3170 XEVAL_DATA_OBJECT (XEVENT_DATA (event)));
3171 #else /* not USE_KKCC */
3026 call1 (XEVENT (event)->event.eval.function, 3172 call1 (XEVENT (event)->event.eval.function,
3027 XEVENT (event)->event.eval.object); 3173 XEVENT (event)->event.eval.object);
3174 #endif /* not USE_KKCC */
3028 return; 3175 return;
3029 } 3176 }
3030 3177
3031 case magic_eval_event: 3178 case magic_eval_event:
3032 { 3179 {
3180 #ifdef USE_KKCC
3181 XMAGIC_EVAL_DATA_INTERNAL_FUNCTION (XEVENT_DATA (event))
3182 XMAGIC_EVAL_DATA_OBJECT (XEVENT_DATA (event));
3183 #else /* not USE_KKCC */
3033 (XEVENT (event)->event.magic_eval.internal_function) 3184 (XEVENT (event)->event.magic_eval.internal_function)
3034 (XEVENT (event)->event.magic_eval.object); 3185 (XEVENT (event)->event.magic_eval.object);
3186 #endif /* not USE_KKCC */
3035 return; 3187 return;
3036 } 3188 }
3037 3189
3038 case pointer_motion_event: 3190 case pointer_motion_event:
3039 { 3191 {
3042 return; 3194 return;
3043 } 3195 }
3044 3196
3045 case process_event: 3197 case process_event:
3046 { 3198 {
3199 #ifdef USE_KKCC
3200 Lisp_Object p = XPROCESS_DATA_PROCESS (XEVENT_DATA (event));
3201 #else /* not USE_KKCC */
3047 Lisp_Object p = XEVENT (event)->event.process.process; 3202 Lisp_Object p = XEVENT (event)->event.process.process;
3203 #endif /* not USE_KKCC */
3048 Charcount readstatus; 3204 Charcount readstatus;
3049 int iter; 3205 int iter;
3050 3206
3051 assert (PROCESSP (p)); 3207 assert (PROCESSP (p));
3052 for (iter = 0; iter < 2; iter++) 3208 for (iter = 0; iter < 2; iter++)
3135 } 3291 }
3136 3292
3137 case timeout_event: 3293 case timeout_event:
3138 { 3294 {
3139 Lisp_Event *e = XEVENT (event); 3295 Lisp_Event *e = XEVENT (event);
3296
3297 #ifdef USE_KKCC
3298 if (!NILP (XTIMEOUT_DATA_FUNCTION (EVENT_DATA (e))))
3299 call1 (XTIMEOUT_DATA_FUNCTION (EVENT_DATA (e)),
3300 XTIMEOUT_DATA_OBJECT (EVENT_DATA (e)));
3301 #else /* not USE_KKCC */
3140 if (!NILP (e->event.timeout.function)) 3302 if (!NILP (e->event.timeout.function))
3141 call1 (e->event.timeout.function, 3303 call1 (e->event.timeout.function,
3142 e->event.timeout.object); 3304 e->event.timeout.object);
3305 #endif /* not USE_KKCC */
3143 return; 3306 return;
3144 } 3307 }
3145 case magic_event: 3308 case magic_event:
3146 {
3147 event_stream_handle_magic_event (XEVENT (event)); 3309 event_stream_handle_magic_event (XEVENT (event));
3148 return; 3310 return;
3149 }
3150 default: 3311 default:
3151 abort (); 3312 abort ();
3152 } 3313 }
3153 } 3314 }
3154 3315
3295 Lisp_Object evee = builder->current_events; 3456 Lisp_Object evee = builder->current_events;
3296 3457
3297 if (XEVENT_TYPE (evee) == misc_user_event) 3458 if (XEVENT_TYPE (evee) == misc_user_event)
3298 { 3459 {
3299 if (allow_misc_user_events_p && (NILP (XEVENT_NEXT (evee)))) 3460 if (allow_misc_user_events_p && (NILP (XEVENT_NEXT (evee))))
3461 #ifdef USE_KKCC
3462 return list2 (XEVAL_DATA_FUNCTION (XEVENT_DATA (evee)),
3463 XEVAL_DATA_OBJECT (XEVENT_DATA (evee)));
3464 #else /* not USE_KKCC */
3300 return list2 (XEVENT (evee)->event.eval.function, 3465 return list2 (XEVENT (evee)->event.eval.function,
3301 XEVENT (evee)->event.eval.object); 3466 XEVENT (evee)->event.eval.object);
3467 #endif /* not USE_KKCC */
3302 else 3468 else
3303 return Qnil; 3469 return Qnil;
3304 } 3470 }
3305 3471
3306 /* if we're currently in a menu accelerator, check there for further 3472 /* if we're currently in a menu accelerator, check there for further
3353 3519
3354 if (XEVENT_TYPE (builder->most_current_event) == key_press_event 3520 if (XEVENT_TYPE (builder->most_current_event) == key_press_event
3355 && !NILP (Vretry_undefined_key_binding_unshifted)) 3521 && !NILP (Vretry_undefined_key_binding_unshifted))
3356 { 3522 {
3357 Lisp_Object terminal = builder->most_current_event; 3523 Lisp_Object terminal = builder->most_current_event;
3524 #ifdef USE_KKCC
3525 Lisp_Key_Data* key = XKEY_DATA (XEVENT_DATA (terminal));
3526 #else /* not USE_KKCC */
3358 struct key_data *key = &XEVENT (terminal)->event.key; 3527 struct key_data *key = &XEVENT (terminal)->event.key;
3528 #endif /* not USE_KKCC */
3359 Ichar c = 0; 3529 Ichar c = 0;
3530 #ifdef USE_KKCC
3531 if ((KEY_DATA_MODIFIERS (key) & XEMACS_MOD_SHIFT)
3532 || (CHAR_OR_CHAR_INTP (KEY_DATA_KEYSYM(key))
3533 && ((c = XCHAR_OR_CHAR_INT (KEY_DATA_KEYSYM(key))),
3534 c >= 'A' && c <= 'Z')))
3535 #else /* not USE_KKCC */
3360 if ((key->modifiers & XEMACS_MOD_SHIFT) 3536 if ((key->modifiers & XEMACS_MOD_SHIFT)
3361 || (CHAR_OR_CHAR_INTP (key->keysym) 3537 || (CHAR_OR_CHAR_INTP (key->keysym)
3362 && ((c = XCHAR_OR_CHAR_INT (key->keysym)), 3538 && ((c = XCHAR_OR_CHAR_INT (key->keysym)),
3363 c >= 'A' && c <= 'Z'))) 3539 c >= 'A' && c <= 'Z')))
3540 #endif /* not USE_KKCC */
3364 { 3541 {
3365 Lisp_Object neubauten = copy_command_builder (builder, 0); 3542 Lisp_Object neubauten = copy_command_builder (builder, 0);
3366 struct command_builder *neub = XCOMMAND_BUILDER (neubauten); 3543 struct command_builder *neub = XCOMMAND_BUILDER (neubauten);
3367 struct gcpro gcpro1; 3544 struct gcpro gcpro1;
3368 3545
3369 GCPRO1 (neubauten); 3546 GCPRO1 (neubauten);
3370 terminal = event_chain_tail (neub->current_events); 3547 terminal = event_chain_tail (neub->current_events);
3548 #ifdef USE_KKCC
3549 key = XKEY_DATA (XEVENT_DATA (terminal));
3550
3551 if (KEY_DATA_MODIFIERS (key) & XEMACS_MOD_SHIFT)
3552 SET_KEY_DATA_MODIFIERS (key, (KEY_DATA_MODIFIERS (key) & (~ XEMACS_MOD_SHIFT)));
3553 else
3554 SET_KEY_DATA_KEYSYM (key, make_char (c + 'a' - 'A'));
3555 #else /* not USE_KKCC */
3371 key = &XEVENT (terminal)->event.key; 3556 key = &XEVENT (terminal)->event.key;
3372 3557
3373 if (key->modifiers & XEMACS_MOD_SHIFT) 3558 if (key->modifiers & XEMACS_MOD_SHIFT)
3374 key->modifiers &= (~ XEMACS_MOD_SHIFT); 3559 key->modifiers &= (~ XEMACS_MOD_SHIFT);
3375 else 3560 else
3376 key->keysym = make_char (c + 'a' - 'A'); 3561 key->keysym = make_char (c + 'a' - 'A');
3562 #endif /* not USE_KKCC */
3377 3563
3378 result = 3564 result =
3379 command_builder_find_leaf_no_mule_processing 3565 command_builder_find_leaf_no_mule_processing
3380 (neub, allow_misc_user_events_p, did_munge); 3566 (neub, allow_misc_user_events_p, did_munge);
3381 3567
3441 3627
3442 /* If keysym is a non-ASCII char, bind it to self-insert-char by default. */ 3628 /* If keysym is a non-ASCII char, bind it to self-insert-char by default. */
3443 if (XEVENT_TYPE (builder->most_current_event) == key_press_event 3629 if (XEVENT_TYPE (builder->most_current_event) == key_press_event
3444 && !NILP (Vcomposed_character_default_binding)) 3630 && !NILP (Vcomposed_character_default_binding))
3445 { 3631 {
3632 #ifdef USE_KKCC
3633 Lisp_Object keysym =
3634 XKEY_DATA_KEYSYM(XEVENT (builder->most_current_event));
3635 #else /* not USE_KKCC */
3446 Lisp_Object keysym = 3636 Lisp_Object keysym =
3447 XEVENT (builder->most_current_event)->event.key.keysym; 3637 XEVENT (builder->most_current_event)->event.key.keysym;
3638 #endif /* not USE_KKCC */
3448 if (CHARP (keysym) && !ichar_ascii_p (XCHAR (keysym))) 3639 if (CHARP (keysym) && !ichar_ascii_p (XCHAR (keysym)))
3449 return Vcomposed_character_default_binding; 3640 return Vcomposed_character_default_binding;
3450 } 3641 }
3451 #endif 3642 #endif
3452 3643
3865 builder to be a copy of this one with the meta-bit set instead of 4056 builder to be a copy of this one with the meta-bit set instead of
3866 pushing a new event. 4057 pushing a new event.
3867 */ 4058 */
3868 Fcopy_event (event, recent); 4059 Fcopy_event (event, recent);
3869 e = XEVENT (recent); 4060 e = XEVENT (recent);
4061 #ifdef USE_KKCC
4062 if (EVENT_TYPE (e) == key_press_event)
4063 XSET_KEY_DATA_MODIFIERS (EVENT_DATA (e),
4064 XKEY_DATA_MODIFIERS (EVENT_DATA (e)) |
4065 XEMACS_MOD_META);
4066 else if (EVENT_TYPE (e) == button_press_event
4067 || EVENT_TYPE (e) == button_release_event)
4068 XSET_BUTTON_DATA_MODIFIERS (EVENT_DATA (e),
4069 XBUTTON_DATA_MODIFIERS (EVENT_DATA (e)) |
4070 XEMACS_MOD_META);
4071 #else /* not USE_KKCC */
3870 if (e->event_type == key_press_event) 4072 if (e->event_type == key_press_event)
3871 e->event.key.modifiers |= XEMACS_MOD_META; 4073 e->event.key.modifiers |= XEMACS_MOD_META;
3872 else if (e->event_type == button_press_event 4074 else if (e->event_type == button_press_event
3873 || e->event_type == button_release_event) 4075 || e->event_type == button_release_event)
3874 e->event.button.modifiers |= XEMACS_MOD_META; 4076 e->event.button.modifiers |= XEMACS_MOD_META;
4077 #endif /* not USE_KKCC */
3875 else 4078 else
3876 abort (); 4079 abort ();
3877 4080
3878 { 4081 {
3879 int tckn = event_chain_count (Vthis_command_keys); 4082 int tckn = event_chain_count (Vthis_command_keys);
3963 is_scrollbar_event (Lisp_Object event) 4166 is_scrollbar_event (Lisp_Object event)
3964 { 4167 {
3965 #ifdef HAVE_SCROLLBARS 4168 #ifdef HAVE_SCROLLBARS
3966 Lisp_Object fun; 4169 Lisp_Object fun;
3967 4170
4171 #ifdef USE_KKCC
4172 if (XEVENT_TYPE (event) != misc_user_event)
4173 return 0;
4174 fun = XMISC_USER_DATA_FUNCTION(XEVENT_DATA (event));
4175 #else /* not USE_KKCC */
3968 if (XEVENT (event)->event_type != misc_user_event) 4176 if (XEVENT (event)->event_type != misc_user_event)
3969 return 0; 4177 return 0;
3970 fun = XEVENT (event)->event.misc.function; 4178 fun = XEVENT (event)->event.misc.function;
4179 #endif /* not USE_KKCC */
3971 4180
3972 return (EQ (fun, Qscrollbar_line_up) || 4181 return (EQ (fun, Qscrollbar_line_up) ||
3973 EQ (fun, Qscrollbar_line_down) || 4182 EQ (fun, Qscrollbar_line_down) ||
3974 EQ (fun, Qscrollbar_page_up) || 4183 EQ (fun, Qscrollbar_page_up) ||
3975 EQ (fun, Qscrollbar_page_down) || 4184 EQ (fun, Qscrollbar_page_down) ||
4102 buffer_reset_changes (XBUFFER (w->buffer)); 4311 buffer_reset_changes (XBUFFER (w->buffer));
4103 } 4312 }
4104 4313
4105 pre_command_hook (); 4314 pre_command_hook ();
4106 4315
4316 #ifdef USE_KKCC
4317 if (XEVENT_TYPE (event) == misc_user_event)
4318 {
4319 call1 (XMISC_USER_DATA_FUNCTION (XEVENT_DATA (event)),
4320 XMISC_USER_DATA_OBJECT (XEVENT_DATA (event)));
4321 }
4322 #else /* not USE_KKCC */
4107 if (XEVENT (event)->event_type == misc_user_event) 4323 if (XEVENT (event)->event_type == misc_user_event)
4108 { 4324 {
4109 call1 (XEVENT (event)->event.eval.function, 4325 call1 (XEVENT (event)->event.eval.function,
4110 XEVENT (event)->event.eval.object); 4326 XEVENT (event)->event.eval.object);
4111 } 4327 }
4328 #endif /* not USE_KKCC */
4112 else 4329 else
4113 { 4330 {
4114 Fcommand_execute (Vthis_command, Qnil, Qnil); 4331 Fcommand_execute (Vthis_command, Qnil, Qnil);
4115 } 4332 }
4116 4333
4290 console = Vselected_console; 4507 console = Vselected_console;
4291 else if (!EQ (console, Vselected_console)) 4508 else if (!EQ (console, Vselected_console))
4292 Fselect_console (console); 4509 Fselect_console (console);
4293 4510
4294 command_builder = XCOMMAND_BUILDER (XCONSOLE (console)->command_builder); 4511 command_builder = XCOMMAND_BUILDER (XCONSOLE (console)->command_builder);
4512 #ifdef USE_KKCC
4513 switch (XEVENT_TYPE (event))
4514 #else /* not USE_KKCC */
4295 switch (XEVENT (event)->event_type) 4515 switch (XEVENT (event)->event_type)
4516 #endif /* not USE_KKCC */
4296 { 4517 {
4297 case button_press_event: 4518 case button_press_event:
4298 case button_release_event: 4519 case button_release_event:
4299 case key_press_event: 4520 case key_press_event:
4300 { 4521 {
4452 anyway (for keyboard macros). There's even one instance 4673 anyway (for keyboard macros). There's even one instance
4453 (in pending-del.el) of `this-command' getting set to a cons 4674 (in pending-del.el) of `this-command' getting set to a cons
4454 (a lambda expression). So in the `eval' case I'll just 4675 (a lambda expression). So in the `eval' case I'll just
4455 convert it into a lambda expression. 4676 convert it into a lambda expression.
4456 */ 4677 */
4678 #ifdef USE_KKCC
4679 if (EQ (XMISC_USER_DATA_FUNCTION (XEVENT_DATA (event)), Qcall_interactively)
4680 && SYMBOLP (XMISC_USER_DATA_OBJECT (XEVENT_DATA (event))))
4681 Vthis_command = XMISC_USER_DATA_OBJECT (XEVENT_DATA (event));
4682 else if (EQ (XMISC_USER_DATA_FUNCTION (XEVENT_DATA (event)), Qeval))
4683 Vthis_command =
4684 Fcons (Qlambda, Fcons (Qnil, XMISC_USER_DATA_OBJECT (XEVENT_DATA (event))));
4685 else if (SYMBOLP (XMISC_USER_DATA_FUNCTION (XEVENT_DATA (event))))
4686 /* A scrollbar command or the like. */
4687 Vthis_command = XMISC_USER_DATA_FUNCTION (XEVENT_DATA (event));
4688 #else /* not USE_KKCC */
4457 if (EQ (XEVENT (event)->event.eval.function, Qcall_interactively) 4689 if (EQ (XEVENT (event)->event.eval.function, Qcall_interactively)
4458 && SYMBOLP (XEVENT (event)->event.eval.object)) 4690 && SYMBOLP (XEVENT (event)->event.eval.object))
4459 Vthis_command = XEVENT (event)->event.eval.object; 4691 Vthis_command = XEVENT (event)->event.eval.object;
4460 else if (EQ (XEVENT (event)->event.eval.function, Qeval)) 4692 else if (EQ (XEVENT (event)->event.eval.function, Qeval))
4461 Vthis_command = 4693 Vthis_command =
4462 Fcons (Qlambda, Fcons (Qnil, XEVENT (event)->event.eval.object)); 4694 Fcons (Qlambda, Fcons (Qnil, XEVENT (event)->event.eval.object));
4463 else if (SYMBOLP (XEVENT (event)->event.eval.function)) 4695 else if (SYMBOLP (XEVENT (event)->event.eval.function))
4464 /* A scrollbar command or the like. */ 4696 /* A scrollbar command or the like. */
4465 Vthis_command = XEVENT (event)->event.eval.function; 4697 Vthis_command = XEVENT (event)->event.eval.function;
4698 #endif /* not USE_KKCC */
4466 else 4699 else
4467 /* Huh? */ 4700 /* Huh? */
4468 Vthis_command = Qnil; 4701 Vthis_command = Qnil;
4469 4702
4470 /* clear the echo area */ 4703 /* clear the echo area */
4477 Fundo_boundary (); 4710 Fundo_boundary ();
4478 execute_command_event (command_builder, event); 4711 execute_command_event (command_builder, event);
4479 break; 4712 break;
4480 } 4713 }
4481 default: 4714 default:
4482 {
4483 execute_internal_event (event); 4715 execute_internal_event (event);
4484 break; 4716 break;
4485 }
4486 } 4717 }
4487 return Qnil; 4718 return Qnil;
4488 } 4719 }
4489 4720
4490 DEFUN ("read-key-sequence", Fread_key_sequence, 1, 3, 0, /* 4721 DEFUN ("read-key-sequence", Fread_key_sequence, 1, 3, 0, /*
4554 command_builder = XCOMMAND_BUILDER (con->command_builder); 4785 command_builder = XCOMMAND_BUILDER (con->command_builder);
4555 if (! command_event_p (event)) 4786 if (! command_event_p (event))
4556 execute_internal_event (event); 4787 execute_internal_event (event);
4557 else 4788 else
4558 { 4789 {
4790 #ifdef USE_KKCC
4791 if (XEVENT_TYPE (event) == misc_user_event)
4792 #else /* not USE_KKCC */
4559 if (XEVENT (event)->event_type == misc_user_event) 4793 if (XEVENT (event)->event_type == misc_user_event)
4794 #endif /* not USE_KKCC */
4560 reset_current_events (command_builder); 4795 reset_current_events (command_builder);
4561 result = lookup_command_event (command_builder, event, 1); 4796 result = lookup_command_event (command_builder, event, 1);
4562 if (!KEYMAPP (result)) 4797 if (!KEYMAPP (result))
4563 { 4798 {
4564 result = current_events_into_vector (command_builder); 4799 result = current_events_into_vector (command_builder);
4621 dribble_out_event (Lisp_Object event) 4856 dribble_out_event (Lisp_Object event)
4622 { 4857 {
4623 if (NILP (Vdribble_file)) 4858 if (NILP (Vdribble_file))
4624 return; 4859 return;
4625 4860
4861 #ifdef USE_KKCC
4862 if (XEVENT_TYPE (event) == key_press_event &&
4863 !XKEY_DATA_MODIFIERS (XEVENT_DATA (event)))
4864 {
4865 Lisp_Object keysym = XKEY_DATA_KEYSYM (XEVENT_DATA (event));
4866 if (CHARP (XKEY_DATA_KEYSYM (XEVENT_DATA (event))))
4867 #else /* not USE_KKCC */
4626 if (XEVENT (event)->event_type == key_press_event && 4868 if (XEVENT (event)->event_type == key_press_event &&
4627 !XEVENT (event)->event.key.modifiers) 4869 !XEVENT (event)->event.key.modifiers)
4628 { 4870 {
4629 Lisp_Object keysym = XEVENT (event)->event.key.keysym; 4871 Lisp_Object keysym = XEVENT (event)->event.key.keysym;
4630 if (CHARP (XEVENT (event)->event.key.keysym)) 4872 if (CHARP (XEVENT (event)->event.key.keysym))
4873 #endif /* not USE_KKCC */
4631 { 4874 {
4632 Ichar ch = XCHAR (keysym); 4875 Ichar ch = XCHAR (keysym);
4633 Ibyte str[MAX_ICHAR_LEN]; 4876 Ibyte str[MAX_ICHAR_LEN];
4634 Bytecount len = set_itext_ichar (str, ch); 4877 Bytecount len = set_itext_ichar (str, ch);
4635 Lstream_write (XLSTREAM (Vdribble_file), str, len); 4878 Lstream_write (XLSTREAM (Vdribble_file), str, len);