To: vim_dev@googlegroups.com Subject: Patch 7.3.1288 Fcc: outbox From: Bram Moolenaar Mime-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ------------ Patch 7.3.1288 Problem: The first ":echo 'hello'" command output doesn't show. Mapping for gets triggered during startup. Solution: Add debugging code for the termresponse. When receiving the "Co" entry and when setting 'ambiwidth' redraw right away if possible. Add redraw_asap(). Don't set 'ambiwidth' if it already had the right value. Do the 'ambiwidth' check in the second row to avoid confusion with . Files: src/term.c, src/screen.c, src/proto/screen.pro *** ../vim-7.3.1287/src/term.c 2013-07-01 20:06:13.000000000 +0200 --- src/term.c 2013-07-03 12:36:11.000000000 +0200 *************** *** 106,111 **** --- 106,119 ---- char *tgetstr __ARGS((char *, char **)); # ifdef FEAT_TERMRESPONSE + /* Change this to "if 1" to debug what happens with termresponse. */ + # if 0 + # define DEBUG_TERMRESPONSE + static void log_tr(char *msg); + # define LOG_TR(msg) log_tr(msg) + # else + # define LOG_TR(msg) + # endif /* Request Terminal Version status: */ # define CRV_GET 1 /* send T_CRV when switched to RAW mode */ # define CRV_SENT 2 /* did send T_CRV, waiting for answer */ *************** *** 1936,1941 **** --- 1944,1950 ---- full_screen = TRUE; /* we can use termcap codes from now on */ set_term_defaults(); /* use current values as defaults */ #ifdef FEAT_TERMRESPONSE + LOG_TR("setting crv_status to CRV_GET"); crv_status = CRV_GET; /* Get terminal version later */ #endif *************** *** 3326,3331 **** --- 3335,3341 ---- # endif && *T_CRV != NUL) { + LOG_TR("Sending CRV"); out_str(T_CRV); crv_status = CRV_SENT; /* check for the characters now, otherwise they might be eaten by *************** *** 3338,3347 **** # if defined(FEAT_MBYTE) || defined(PROTO) /* * Check how the terminal treats ambiguous character width (UAX #11). ! * First, we move the cursor to (0, 0) and print a test ambiguous character * \u25bd (WHITE DOWN-POINTING TRIANGLE) and query current cursor position. ! * If the terminal treats \u25bd as single width, the position is (0, 1), ! * or if it is treated as double width, that will be (0, 2). * This function has the side effect that changes cursor position, so * it must be called immediately after entering termcap mode. */ --- 3348,3357 ---- # if defined(FEAT_MBYTE) || defined(PROTO) /* * Check how the terminal treats ambiguous character width (UAX #11). ! * First, we move the cursor to (1, 0) and print a test ambiguous character * \u25bd (WHITE DOWN-POINTING TRIANGLE) and query current cursor position. ! * If the terminal treats \u25bd as single width, the position is (1, 1), ! * or if it is treated as double width, that will be (1, 2). * This function has the side effect that changes cursor position, so * it must be called immediately after entering termcap mode. */ *************** *** 3361,3367 **** { char_u buf[16]; ! term_windgoto(0, 0); buf[mb_char2bytes(0x25bd, buf)] = 0; out_str(buf); out_str(T_U7); --- 3371,3380 ---- { char_u buf[16]; ! LOG_TR("Sending U7 request"); ! /* Do this in the second row. In the first row the returned sequence ! * may be CSI 1;2R, which is the same as . */ ! term_windgoto(1, 0); buf[mb_char2bytes(0x25bd, buf)] = 0; out_str(buf); out_str(T_U7); *************** *** 3376,3381 **** --- 3389,3417 ---- } } # endif + + # ifdef DEBUG_TERMRESPONSE + static void + log_tr(char *msg) + { + static FILE *fd_tr = NULL; + static proftime_T start; + proftime_T now; + + if (fd_tr == NULL) + { + fd_tr = fopen("termresponse.log", "w"); + profile_start(&start); + } + now = start; + profile_end(&now); + fprintf(fd_tr, "%s: %s %s\n", + profile_msg(&now), + must_redraw == NOT_VALID ? "NV" + : must_redraw == CLEAR ? "CL" : " ", + msg); + } + # endif #endif /* *************** *** 3847,3852 **** --- 3883,3889 ---- need_gather = TRUE; /* need to fill termleader[] */ } detected_8bit = TRUE; + LOG_TR("Switching to 8 bit"); } #endif *************** *** 4156,4169 **** if (tp[i] == ';' && ++j == 1) extra = i + 1; if (i == len) ! return -1; /* not enough characters */ #ifdef FEAT_MBYTE ! /* eat it when it has 2 arguments and ends in 'R' */ ! if (j == 1 && tp[i] == 'R') { char *aw = NULL; u7_status = U7_GOT; # ifdef FEAT_AUTOCMD did_cursorhold = TRUE; --- 4193,4212 ---- if (tp[i] == ';' && ++j == 1) extra = i + 1; if (i == len) ! { ! LOG_TR("Not enough characters for CRV"); ! return -1; ! } #ifdef FEAT_MBYTE ! /* Eat it when it has 2 arguments and ends in 'R'. Ignore it ! * when u7_status is not "sent", sends something ! * similar. */ ! if (j == 1 && tp[i] == 'R' && u7_status == U7_SENT) { char *aw = NULL; + LOG_TR("Received U7 status"); u7_status = U7_GOT; # ifdef FEAT_AUTOCMD did_cursorhold = TRUE; *************** *** 4174,4181 **** aw = "single"; else if (extra == 3) aw = "double"; ! if (aw != NULL) set_option_value((char_u *)"ambw", 0L, (char_u *)aw, 0); key_name[0] = (int)KS_EXTRA; key_name[1] = (int)KE_IGNORE; slen = i + 1; --- 4217,4240 ---- aw = "single"; else if (extra == 3) aw = "double"; ! if (aw != NULL && STRCMP(aw, p_ambw) != 0) ! { ! /* Setting the option causes a screen redraw. Do that ! * right away if possible, keeping any messages. */ set_option_value((char_u *)"ambw", 0L, (char_u *)aw, 0); + #ifdef DEBUG_TERMRESPONSE + { + char buf[100]; + int r = redraw_asap(CLEAR); + + sprintf(buf, "set 'ambiwidth', redraw_asap(): %d", + r); + log_tr(buf); + } + #else + redraw_asap(CLEAR); + #endif + } key_name[0] = (int)KS_EXTRA; key_name[1] = (int)KE_IGNORE; slen = i + 1; *************** *** 4185,4190 **** --- 4244,4250 ---- /* eat it when at least one digit and ending in 'c' */ if (*T_CRV != NUL && i > 2 + (tp[0] != CSI) && tp[i] == 'c') { + LOG_TR("Received CRV"); crv_status = CRV_GOT; # ifdef FEAT_AUTOCMD did_cursorhold = TRUE; *************** *** 4224,4229 **** --- 4284,4290 ---- /* if xterm version >= 141 try to get termcap codes */ if (extra >= 141) { + LOG_TR("Enable checking for XT codes"); check_for_codes = TRUE; need_gather = TRUE; req_codes_from_term(); *************** *** 4262,4268 **** --- 4323,4332 ---- } if (i == len) + { + LOG_TR("not enough characters for XT"); return -1; /* not enough characters */ + } } } #endif *************** *** 5207,5212 **** --- 5271,5280 ---- return retval == 0 ? (len + extra + offset) : retval; } + #ifdef FEAT_TERMRESPONSE + LOG_TR("normal character"); + #endif + return 0; /* no match found */ } *************** *** 5661,5666 **** --- 5729,5741 ---- * many, there can be a buffer overflow somewhere. */ while (xt_index_out < xt_index_in + 10 && key_names[xt_index_out] != NULL) { + # ifdef DEBUG_TERMRESPONSE + char dbuf[100]; + + sprintf(dbuf, "Requesting XT %d: %s", + xt_index_out, key_names[xt_index_out]); + log_tr(dbuf); + # endif sprintf(buf, "\033P+q%02x%02x\033\\", key_names[xt_index_out][0], key_names[xt_index_out][1]); out_str_nf((char_u *)buf); *************** *** 5707,5712 **** --- 5782,5795 ---- break; } } + # ifdef DEBUG_TERMRESPONSE + { + char buf[100]; + + sprintf(buf, "Received XT %d: %s", xt_index_in, (char *)name); + log_tr(buf); + } + # endif if (key_names[i] != NULL) { for (i = 8; (c = hexhex2nr(code + i)) >= 0; i += 2) *************** *** 5725,5731 **** set_keep_msg_from_hist(); set_color_count(i); init_highlight(TRUE, FALSE); ! redraw_later(CLEAR); } } else --- 5808,5824 ---- set_keep_msg_from_hist(); set_color_count(i); init_highlight(TRUE, FALSE); ! #ifdef DEBUG_TERMRESPONSE ! { ! char buf[100]; ! int r = redraw_asap(CLEAR); ! ! sprintf(buf, "Received t_Co, redraw_asap(): %d", r); ! log_tr(buf); ! } ! #else ! redraw_asap(CLEAR); ! #endif } } else *** ../vim-7.3.1287/src/screen.c 2013-07-01 20:18:26.000000000 +0200 --- src/screen.c 2013-07-03 12:45:14.000000000 +0200 *************** *** 268,273 **** --- 268,414 ---- } /* + * Redraw as soon as possible. When the command line is not scrolled redraw + * right away and restore what was on the command line. + * Return a code indicating what happened. + */ + int + redraw_asap(type) + int type; + { + int rows; + int r; + int ret = 0; + schar_T *screenline; /* copy from ScreenLines[] */ + sattr_T *screenattr; /* copy from ScreenAttrs[] */ + #ifdef FEAT_MBYTE + int i; + u8char_T *screenlineUC; /* copy from ScreenLinesUC[] */ + u8char_T *screenlineC[MAX_MCO]; /* copy from ScreenLinesC[][] */ + schar_T *screenline2; /* copy from ScreenLines2[] */ + #endif + + redraw_later(type); + if (msg_scrolled || (State != NORMAL && State != NORMAL_BUSY)) + return ret; + + /* Allocate space to save the text displayed in the command line area. */ + rows = Rows - cmdline_row; + screenline = (schar_T *)lalloc( + (long_u)(rows * Columns * sizeof(schar_T)), FALSE); + screenattr = (sattr_T *)lalloc( + (long_u)(rows * Columns * sizeof(sattr_T)), FALSE); + if (screenline == NULL || screenattr == NULL) + ret = 2; + #ifdef FEAT_MBYTE + if (enc_utf8) + { + screenlineUC = (u8char_T *)lalloc( + (long_u)(rows * Columns * sizeof(u8char_T)), FALSE); + if (screenlineUC == NULL) + ret = 2; + for (i = 0; i < p_mco; ++i) + { + screenlineC[i] = (u8char_T *)lalloc( + (long_u)(rows * Columns * sizeof(u8char_T)), FALSE); + if (screenlineC[i] == NULL) + ret = 2; + } + } + if (enc_dbcs == DBCS_JPNU) + { + screenline2 = (schar_T *)lalloc( + (long_u)(rows * Columns * sizeof(schar_T)), FALSE); + if (screenline2 == NULL) + ret = 2; + } + #endif + + if (ret != 2) + { + /* Save the text displayed in the command line area. */ + for (r = 0; r < rows; ++r) + { + mch_memmove(screenline + r * Columns, + ScreenLines + LineOffset[cmdline_row + r], + (size_t)Columns * sizeof(schar_T)); + mch_memmove(screenattr + r * Columns, + ScreenAttrs + LineOffset[cmdline_row + r], + (size_t)Columns * sizeof(sattr_T)); + #ifdef FEAT_MBYTE + if (enc_utf8) + { + mch_memmove(screenlineUC + r * Columns, + ScreenLinesUC + LineOffset[cmdline_row + r], + (size_t)Columns * sizeof(u8char_T)); + for (i = 0; i < p_mco; ++i) + mch_memmove(screenlineC[i] + r * Columns, + ScreenLinesC[r] + LineOffset[cmdline_row + r], + (size_t)Columns * sizeof(u8char_T)); + } + if (enc_dbcs == DBCS_JPNU) + mch_memmove(screenline2 + r * Columns, + ScreenLines2 + LineOffset[cmdline_row + r], + (size_t)Columns * sizeof(schar_T)); + #endif + } + + update_screen(0); + ret = 3; + + if (must_redraw == 0) + { + int off = (int)(current_ScreenLine - ScreenLines); + + /* Restore the text displayed in the command line area. */ + for (r = 0; r < rows; ++r) + { + mch_memmove(current_ScreenLine, + screenline + r * Columns, + (size_t)Columns * sizeof(schar_T)); + mch_memmove(ScreenAttrs + off, + screenattr + r * Columns, + (size_t)Columns * sizeof(sattr_T)); + #ifdef FEAT_MBYTE + if (enc_utf8) + { + mch_memmove(ScreenLinesUC + off, + screenlineUC + r * Columns, + (size_t)Columns * sizeof(u8char_T)); + for (i = 0; i < p_mco; ++i) + mch_memmove(ScreenLinesC[i] + off, + screenlineC[i] + r * Columns, + (size_t)Columns * sizeof(u8char_T)); + } + if (enc_dbcs == DBCS_JPNU) + mch_memmove(ScreenLines2 + off, + screenline2 + r * Columns, + (size_t)Columns * sizeof(schar_T)); + #endif + SCREEN_LINE(cmdline_row + r, 0, Columns, Columns, FALSE); + } + ret = 4; + } + setcursor(); + } + + vim_free(screenline); + vim_free(screenattr); + #ifdef FEAT_MBYTE + if (enc_utf8) + { + vim_free(screenlineUC); + for (i = 0; i < p_mco; ++i) + vim_free(screenlineC[i]); + } + if (enc_dbcs == DBCS_JPNU) + vim_free(screenline2); + #endif + + return ret; + } + + /* * Changed something in the current window, at buffer line "lnum", that * requires that line and possibly other lines to be redrawn. * Used when entering/leaving Insert mode with the cursor on a folded line. *** ../vim-7.3.1287/src/proto/screen.pro 2012-12-05 16:10:21.000000000 +0100 --- src/proto/screen.pro 2013-07-02 22:18:00.000000000 +0200 *************** *** 5,10 **** --- 5,11 ---- void redraw_all_later __ARGS((int type)); void redraw_curbuf_later __ARGS((int type)); void redraw_buf_later __ARGS((buf_T *buf, int type)); + int redraw_asap __ARGS((int type)); void redrawWinline __ARGS((linenr_T lnum, int invalid)); void update_curbuf __ARGS((int type)); void update_screen __ARGS((int type)); *** ../vim-7.3.1287/src/version.c 2013-07-01 22:02:58.000000000 +0200 --- src/version.c 2013-07-02 23:10:57.000000000 +0200 *************** *** 730,731 **** --- 730,733 ---- { /* Add new patch number below this line */ + /**/ + 1288, /**/ -- Yesterday is history. Tomorrow is a mystery. Today is a gift. That's why it is called 'present'. /// Bram Moolenaar -- Bram@Moolenaar.net -- http://www.Moolenaar.net \\\ /// sponsor Vim, vote for features -- http://www.Vim.org/sponsor/ \\\ \\\ an exciting new programming language -- http://www.Zimbu.org /// \\\ help me help AIDS victims -- http://ICCF-Holland.org ///