Compare commits

...

4 Commits

Author SHA1 Message Date
Bram Moolenaar
84e67dfa9c updated for version 7.2.445
Problem:    Crash when using undo/redo and a FileChangedRO autocmd event that
            reloads the buffer. (Dominique Pelle)
Solution:   Do not allow autocommands while performing and undo or redo.
2010-07-07 18:20:28 +02:00
Bram Moolenaar
31c8f28cca updated for version 7.2.444
Problem:    Can't build with GTK 1, gtk_selection_clear_targets() is not
            available. (Patrick Texier)
Solution:   Don't change the targets for GTK 1, set them once.
2010-06-13 02:35:46 +02:00
Bram Moolenaar
9ea339d58c updated for version 7.2.443
Problem:    Using taglist() on a tag file with duplicate fields generates an
            internal error. (Peter Odding)
Solution:   Check for duplicate field names.
2010-06-12 20:12:02 +02:00
Bram Moolenaar
f949563afa updated for version 7.2.442
Problem:    Copy/paste with OpenOffice doesn't work.
Solution:   Do not offer the HTML target when it is not supported. (James
            Vega)
2010-06-05 12:49:46 +02:00
9 changed files with 151 additions and 29 deletions

View File

@@ -451,7 +451,6 @@ static dictitem_T *dictitem_copy __ARGS((dictitem_T *org));
static void dictitem_remove __ARGS((dict_T *dict, dictitem_T *item));
static dict_T *dict_copy __ARGS((dict_T *orig, int deep, int copyID));
static long dict_len __ARGS((dict_T *d));
static dictitem_T *dict_find __ARGS((dict_T *d, char_u *key, int len));
static char_u *dict2string __ARGS((typval_T *tv, int copyID));
static int get_dict_tv __ARGS((char_u **arg, typval_T *rettv, int evaluate));
static char_u *echo_string __ARGS((typval_T *tv, char_u **tofree, char_u *numbuf, int copyID));
@@ -7012,7 +7011,7 @@ dict_len(d)
* If "len" is negative use strlen(key).
* Returns NULL when not found.
*/
static dictitem_T *
dictitem_T *
dict_find(d, key, len)
dict_T *d;
char_u *key;

View File

@@ -1433,6 +1433,10 @@ selection_received_cb(GtkWidget *widget UNUSED,
}
#endif /* !HAVE_GTK2 */
/* Chop off any traiing NUL bytes. OpenOffice sends these. */
while (len > 0 && text[len - 1] == NUL)
--len;
clip_yank_selection(motion_type, text, (long)len, cbd);
received_selection = RS_OK;
vim_free(tmpbuf);
@@ -3462,6 +3466,68 @@ gui_mch_set_curtab(nr)
#endif /* FEAT_GUI_TABLINE */
/*
* Add selection targets for PRIMARY and CLIPBOARD selections.
*/
void
gui_gtk_set_selection_targets(void)
{
int i, j = 0;
int n_targets = N_SELECTION_TARGETS;
GtkTargetEntry targets[N_SELECTION_TARGETS];
for (i = 0; i < (int)N_SELECTION_TARGETS; ++i)
{
#if defined(FEAT_MBYTE) && defined(HAVE_GTK2)
/* OpenOffice tries to use TARGET_HTML and fails when it doesn't
* return something, instead of trying another target. Therefore only
* offer TARGET_HTML when it works. */
if (!clip_html && selection_targets[i].info == TARGET_HTML)
n_targets--;
else
#endif
targets[j++] = selection_targets[i];
}
#ifdef HAVE_GTK2 /* GTK 1 doesn't have this function */
gtk_selection_clear_targets(gui.drawarea, (GdkAtom)GDK_SELECTION_PRIMARY);
gtk_selection_clear_targets(gui.drawarea, (GdkAtom)clip_plus.gtk_sel_atom);
#endif
gtk_selection_add_targets(gui.drawarea,
(GdkAtom)GDK_SELECTION_PRIMARY,
targets, n_targets);
gtk_selection_add_targets(gui.drawarea,
(GdkAtom)clip_plus.gtk_sel_atom,
targets, n_targets);
}
/*
* Set up for receiving DND items.
*/
void
gui_gtk_set_dnd_targets(void)
{
int i, j = 0;
int n_targets = N_DND_TARGETS;
GtkTargetEntry targets[N_DND_TARGETS];
for (i = 0; i < (int)N_DND_TARGETS; ++i)
{
#ifdef FEAT_MBYTE
if (!clip_html && selection_targets[i].info == TARGET_HTML)
n_targets--;
else
#endif
targets[j++] = dnd_targets[i];
}
gtk_drag_dest_unset(gui.drawarea);
gtk_drag_dest_set(gui.drawarea,
GTK_DEST_DEFAULT_ALL,
targets, n_targets,
GDK_ACTION_COPY);
}
/*
* Initialize the GUI. Create all the windows, set up all the callbacks etc.
* Returns OK for success, FAIL when the GUI can't be started.
@@ -3925,15 +3991,7 @@ gui_mch_init(void)
gtk_signal_connect(GTK_OBJECT(gui.drawarea), "selection_received",
GTK_SIGNAL_FUNC(selection_received_cb), NULL);
/*
* Add selection targets for PRIMARY and CLIPBOARD selections.
*/
gtk_selection_add_targets(gui.drawarea,
(GdkAtom)GDK_SELECTION_PRIMARY,
selection_targets, N_SELECTION_TARGETS);
gtk_selection_add_targets(gui.drawarea,
(GdkAtom)clip_plus.gtk_sel_atom,
selection_targets, N_SELECTION_TARGETS);
gui_gtk_set_selection_targets();
gtk_signal_connect(GTK_OBJECT(gui.drawarea), "selection_get",
GTK_SIGNAL_FUNC(selection_get_cb), NULL);
@@ -4057,7 +4115,6 @@ check_startup_plug_hints(gpointer data UNUSED)
return TRUE;
}
/*
* Open the GUI window which was created by a call to gui_mch_init().
*/
@@ -4225,13 +4282,8 @@ gui_mch_open(void)
GTK_SIGNAL_FUNC(form_configure_event), NULL);
#ifdef FEAT_DND
/*
* Set up for receiving DND items.
*/
gtk_drag_dest_set(gui.drawarea,
GTK_DEST_DEFAULT_ALL,
dnd_targets, N_DND_TARGETS,
GDK_ACTION_COPY);
/* Set up for receiving DND items. */
gui_gtk_set_dnd_targets();
gtk_signal_connect(GTK_OBJECT(gui.drawarea), "drag_data_received",
GTK_SIGNAL_FUNC(drag_data_received_cb), NULL);
@@ -4428,7 +4480,7 @@ gui_mch_set_shellsize(int width, int height,
/* this will cause the proper resizement to happen too */
update_window_manager_hints(0, 0);
#else /* HAVE_GTK2 */
#else
/* this will cause the proper resizement to happen too */
if (gtk_socket_id == 0)
update_window_manager_hints(0, 0);
@@ -4444,14 +4496,14 @@ gui_mch_set_shellsize(int width, int height,
else
update_window_manager_hints(width, height);
#if 0
# if 0
if (!resize_idle_installed)
{
g_idle_add_full(GDK_PRIORITY_EVENTS + 10,
&force_shell_resize_idle, NULL, NULL);
resize_idle_installed = TRUE;
}
#endif
# endif
/*
* Wait until all events are processed to prevent a crash because the
* real size of the drawing area doesn't reflect Vim's internal ideas.

View File

@@ -2467,10 +2467,12 @@ skip_to_option_part(p)
}
/*
* changed() is called when something in the current buffer is changed.
* Call this function when something in the current buffer is changed.
*
* Most often called through changed_bytes() and changed_lines(), which also
* mark the area of the display to be redrawn.
*
* Careful: may trigger autocommands that reload the buffer.
*/
void
changed()
@@ -2536,6 +2538,7 @@ static void changed_common __ARGS((linenr_T lnum, colnr_T col, linenr_T lnume, l
* - marks the windows on this buffer to be redisplayed
* - marks the buffer changed by calling changed()
* - invalidates cached values
* Careful: may trigger autocommands that reload the buffer.
*/
void
changed_bytes(lnum, col)
@@ -2649,6 +2652,7 @@ deleted_lines_mark(lnum, count)
* below the changed lines (BEFORE the change).
* When only inserting lines, "lnum" and "lnume" are equal.
* Takes care of calling changed() and updating b_mod_*.
* Careful: may trigger autocommands that reload the buffer.
*/
void
changed_lines(lnum, col, lnume, xtra)
@@ -2716,6 +2720,11 @@ changed_lines_buf(buf, lnum, lnume, xtra)
}
}
/*
* Common code for when a change is was made.
* See changed_lines() for the arguments.
* Careful: may trigger autocommands that reload the buffer.
*/
static void
changed_common(lnum, col, lnume, xtra)
linenr_T lnum;
@@ -2966,6 +2975,7 @@ check_status(buf)
* Don't use emsg(), because it flushes the macro buffer.
* If we have undone all changes b_changed will be FALSE, but "b_did_warn"
* will be TRUE.
* Careful: may trigger autocommands that reload the buffer.
*/
void
change_warning(col)

View File

@@ -7112,6 +7112,13 @@ check_clipboard_option()
clip_html = new_html;
vim_free(clip_exclude_prog);
clip_exclude_prog = new_exclude_prog;
#ifdef HAVE_GTK2 /* for GTK 1 we can't change the list of targets */
if (gui.in_use)
{
gui_gtk_set_selection_targets();
gui_gtk_set_dnd_targets();
}
#endif
}
else
vim_free(new_exclude_prog);

View File

@@ -56,6 +56,7 @@ dictitem_T *dictitem_alloc __ARGS((char_u *key));
void dictitem_free __ARGS((dictitem_T *item));
int dict_add __ARGS((dict_T *d, dictitem_T *item));
int dict_add_nr_str __ARGS((dict_T *d, char *key, long nr, char_u *str));
dictitem_T *dict_find __ARGS((dict_T *d, char_u *key, int len));
char_u *get_dict_string __ARGS((dict_T *d, char_u *key, int save));
long get_dict_number __ARGS((dict_T *d, char_u *key));
char_u *get_function_name __ARGS((expand_T *xp, int idx));

View File

@@ -9,6 +9,8 @@ void gui_mch_show_tabline __ARGS((int showit));
int gui_mch_showing_tabline __ARGS((void));
void gui_mch_update_tabline __ARGS((void));
void gui_mch_set_curtab __ARGS((int nr));
void gui_gtk_set_selection_targets __ARGS((void));
void gui_gtk_set_dnd_targets __ARGS((void));
int gui_mch_init __ARGS((void));
void gui_mch_forked __ARGS((void));
void gui_mch_new_colors __ARGS((void));

View File

@@ -3771,7 +3771,8 @@ expand_tags(tagnames, pat, num_file, file)
static int add_tag_field __ARGS((dict_T *dict, char *field_name, char_u *start, char_u *end));
/*
* Add a tag field to the dictionary "dict"
* Add a tag field to the dictionary "dict".
* Return OK or FAIL.
*/
static int
add_tag_field(dict, field_name, start, end)
@@ -3783,6 +3784,17 @@ add_tag_field(dict, field_name, start, end)
char_u buf[MAXPATHL];
int len = 0;
/* check that the field name doesn't exist yet */
if (dict_find(dict, (char_u *)field_name, -1) != NULL)
{
if (p_verbose > 0)
{
verbose_enter();
smsg((char_u *)_("Duplicate field name: %s"), field_name);
verbose_leave();
}
return FAIL;
}
if (start != NULL)
{
if (end == NULL)

View File

@@ -185,7 +185,7 @@ u_check_tree(u_header_T *uhp,
}
}
void
static void
u_check(int newhead_may_be_NULL)
{
seen_b_u_newhead = 0;
@@ -320,6 +320,9 @@ undo_allowed()
return TRUE;
}
/*
* Common code for various ways to save text before a change.
*/
static int
u_savecommon(top, bot, newbot)
linenr_T top, bot;
@@ -374,7 +377,7 @@ u_savecommon(top, bot, newbot)
size = bot - top - 1;
/*
* if curbuf->b_u_synced == TRUE make a new header
* If curbuf->b_u_synced == TRUE make a new header.
*/
if (curbuf->b_u_synced)
{
@@ -709,6 +712,12 @@ u_doit(startcount)
u_oldcount = -1;
while (count--)
{
/* Do the change warning now, so that it triggers FileChangedRO when
* needed. This may cause the file to be reloaded, that must happen
* before we do anything, because it may change curbuf->b_u_curhead
* and more. */
change_warning(0);
if (undo_undoes)
{
if (curbuf->b_u_curhead == NULL) /* first undo */
@@ -952,8 +961,11 @@ undo_time(step, sec, absolute)
/*
* First go up the tree as much as needed.
*/
for (;;)
while (!got_int)
{
/* Do the change warning now, for the same reason as above. */
change_warning(0);
uhp = curbuf->b_u_curhead;
if (uhp == NULL)
uhp = curbuf->b_u_newhead;
@@ -970,9 +982,15 @@ undo_time(step, sec, absolute)
/*
* And now go down the tree (redo), branching off where needed.
*/
uhp = curbuf->b_u_curhead;
while (uhp != NULL)
while (!got_int)
{
/* Do the change warning now, for the same reason as above. */
change_warning(0);
uhp = curbuf->b_u_curhead;
if (uhp == NULL)
break;
/* Go back to the first branch with a mark. */
while (uhp->uh_alt_prev != NULL
&& uhp->uh_alt_prev->uh_walk == mark)
@@ -1070,6 +1088,12 @@ u_undoredo(undo)
int empty_buffer; /* buffer became empty */
u_header_T *curhead = curbuf->b_u_curhead;
#ifdef FEAT_AUTOCMD
/* Don't want autocommands using the undo structures here, they are
* invalid till the end. */
block_autocmds();
#endif
#ifdef U_DEBUG
u_check(FALSE);
#endif
@@ -1099,6 +1123,9 @@ u_undoredo(undo)
if (top > curbuf->b_ml.ml_line_count || top >= bot
|| bot > curbuf->b_ml.ml_line_count + 1)
{
#ifdef FEAT_AUTOCMD
unblock_autocmds();
#endif
EMSG(_("E438: u_undo: line numbers wrong"));
changed(); /* don't want UNCHANGED now */
return;
@@ -1304,6 +1331,10 @@ u_undoredo(undo)
/* The timestamp can be the same for multiple changes, just use the one of
* the undone/redone change. */
curbuf->b_u_seq_time = curhead->uh_time;
#ifdef FEAT_AUTOCMD
unblock_autocmds();
#endif
#ifdef U_DEBUG
u_check(FALSE);
#endif

View File

@@ -681,6 +681,14 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
445,
/**/
444,
/**/
443,
/**/
442,
/**/
441,
/**/