~ubuntu-branches/ubuntu/jaunty/xterm/jaunty

« back to all changes in this revision

Viewing changes to util.c

  • Committer: Bazaar Package Importer
  • Author(s): Julien Cristau, Branden Robinson, Julien Cristau
  • Date: 2007-06-18 14:02:22 UTC
  • mfrom: (1.1.6 upstream)
  • Revision ID: james.westby@ubuntu.com-20070618140222-pk2uof6pyni5omqf
Tags: 226-1
[ Branden Robinson ]
* Remove debian/NEWS; the events it attested to (like the "upcoming 7.0
  modularization" are no longer news, and are in the past.

[ Julien Cristau ]
* Configure with --with-tty-group=tty, to prevent security problems in case
  of buggy build environment (closes: #349142).
* New upstream release.
  + fix  an  infinite  loop  when  showing  a  2-column character in a
    1-column screen (closes: #426863).
  + add  XF86Paste  and  SunPaste  to the default translations
    (closes: #422521, patch by Bernhard R Link).
  + improve  permissions  logic  when  closing pseudo-terminal
    (closes: #12261, patch by Nathanael Nerode, analysis by Richard
    Braakman).
  + add  a check in case someone tries to call the popup-menu() action
    on a menu which is not initialized (closes: #426364).
  + fix error-checking on internal font switching for "Selection" menu
    entry (closes: #421523).
  + amend select/paste change from patch #225 by limiting it to
    non-UTF-8/non-KOI8-R encoding (closes: #420974).
  + add  workaround  for  groff  ".URL" codes which are not present in
    some commonly-used bitmap fonts (closes: #418324).
* Update reference to xlibs-data in xterm's description, refer to xbitmaps
  instead.
* Build-depend on desktop-file-utils to install the new desktop files for
  xterm and uxterm, and change debian/rules and debian/xterm.install to
  install these files and the icons.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* $XTermId: util.c,v 1.351 2007/03/21 22:04:14 tom Exp $ */
 
1
/* $XTermId: util.c,v 1.363 2007/06/17 13:52:18 tom Exp $ */
2
2
 
3
3
/* $XFree86: xc/programs/xterm/util.c,v 3.98 2006/06/19 00:36:52 dickey Exp $ */
4
4
 
1442
1442
        XClearArea(screen->display, VWindow(screen),
1443
1443
                   rect_x,
1444
1444
                   rect_y,
1445
 
                   rect_width,
1446
 
                   rect_height, False);
 
1445
                   (unsigned) rect_width,
 
1446
                   (unsigned) rect_height, False);
1447
1447
    }
1448
1448
    toprow = y0 / FontHeight(screen);
1449
1449
    if (toprow < 0)
1635
1635
    Pixel bg;
1636
1636
} ToSwap;
1637
1637
 
 
1638
/*
 
1639
 * Use this to swap the foreground/background color values in the resource
 
1640
 * data, and to build up a list of the pairs which must be swapped in the
 
1641
 * GC cache.
 
1642
 */
1638
1643
static void
1639
1644
swapLocally(ToSwap * list, int *count, ColorRes * fg, ColorRes * bg)
1640
1645
{
1650
1655
    Pixel bg_color = *bg;
1651
1656
#endif
1652
1657
 
1653
 
    EXCHANGE(*fg, *bg, tmp);
1654
 
    for (n = 0; n < *count; ++n) {
1655
 
        if ((list[n].fg == fg_color && list[n].bg == bg_color)
1656
 
            || (list[n].fg == bg_color && list[n].bg == fg_color)) {
1657
 
            found = True;
1658
 
            break;
1659
 
        }
1660
 
    }
1661
 
    if (!found) {
1662
 
        list[*count].fg = fg_color;
1663
 
        list[*count].bg = bg_color;
1664
 
        *count = *count + 1;
 
1658
    if (fg_color != bg_color) {
 
1659
        EXCHANGE(*fg, *bg, tmp);
 
1660
        for (n = 0; n < *count; ++n) {
 
1661
            if ((list[n].fg == fg_color && list[n].bg == bg_color)
 
1662
                || (list[n].fg == bg_color && list[n].bg == fg_color)) {
 
1663
                found = True;
 
1664
                break;
 
1665
            }
 
1666
        }
 
1667
        if (!found) {
 
1668
            list[*count].fg = fg_color;
 
1669
            list[*count].bg = bg_color;
 
1670
            *count = *count + 1;
 
1671
            TRACE(("swapLocally fg %#lx, bg %#lx ->%d\n", fg_color,
 
1672
                   bg_color, *count));
 
1673
        }
1665
1674
    }
1666
1675
}
1667
1676
 
1670
1679
{
1671
1680
    int j, k;
1672
1681
 
 
1682
    TRACE(("reallySwapColors\n"));
1673
1683
    for (j = 0; j < count; ++j) {
1674
1684
        for_each_text_gc(k) {
1675
1685
            redoCgs(xw, list[j].fg, list[j].bg, (CgsEnum) k);
1709
1719
        swapAColor(8, 15);
1710
1720
    });
1711
1721
 
 
1722
    if (T_COLOR(screen, TEXT_CURSOR) == T_COLOR(screen, TEXT_FG))
 
1723
        T_COLOR(screen, TEXT_CURSOR) = T_COLOR(screen, TEXT_BG);
 
1724
 
1712
1725
#define swapTColor(a,b) swapAnyColor(Tcolors, a, b)
1713
1726
    swapTColor(TEXT_FG, TEXT_BG);
1714
1727
    swapTColor(MOUSE_FG, MOUSE_BG);
1870
1883
                   int x,
1871
1884
                   int y,
1872
1885
                   PAIRED_CHARS(Char * text, Char * text2),
1873
 
                   int len,
 
1886
                   Cardinal len,
1874
1887
                   Bool really)
1875
1888
{
1876
1889
    TScreen *screen = &(xw->screen);
1879
1892
    if (len != 0) {
1880
1893
#if OPT_RENDERWIDE
1881
1894
        static XftCharSpec *sbuf;
1882
 
        static int slen = 0;
 
1895
        static Cardinal slen = 0;
1883
1896
 
1884
1897
        XftFont *wfont;
1885
 
        int src, dst;
 
1898
        Cardinal src, dst;
1886
1899
        XftFont *lastFont = 0;
1887
1900
        XftFont *currFont = 0;
1888
 
        int start = 0;
 
1901
        Cardinal start = 0;
1889
1902
        int charWidth;
1890
1903
        int fontnum = screen->menu_font_number;
1891
1904
        int fwidth = FontWidth(screen);
1904
1917
            wfont = screen->renderWideNorm[fontnum];
1905
1918
        }
1906
1919
 
1907
 
        if ((int) slen < len) {
 
1920
        if (slen < len) {
1908
1921
            slen = (len + 1) * 2;
1909
1922
            sbuf = (XftCharSpec *) XtRealloc((char *) sbuf,
1910
1923
                                             slen * sizeof(XftCharSpec));
1916
1929
            if (text2)
1917
1930
                wc |= (*text2++ << 8);
1918
1931
 
1919
 
            charWidth = xtermCellWidth(xw, wc);
 
1932
            charWidth = xtermCellWidth(xw, (wchar_t) wc);
1920
1933
            if (charWidth < 0)
1921
1934
                continue;
1922
1935
 
1933
1946
                                    color,
1934
1947
                                    lastFont,
1935
1948
                                    sbuf + start,
1936
 
                                    dst - start);
 
1949
                                    (int) (dst - start));
1937
1950
                }
1938
1951
                start = dst;
1939
1952
                lastFont = currFont;
1945
1958
                            color,
1946
1959
                            lastFont,
1947
1960
                            sbuf + start,
1948
 
                            dst - start);
 
1961
                            (int) (dst - start));
1949
1962
        }
1950
1963
#else /* !OPT_RENDERWIDE */
1951
1964
        PAIRED_CHARS((void) text, (void) text2);
1960
1973
    }
1961
1974
    return ncells;
1962
1975
}
 
1976
#define xtermXftWidth(xw, flags, color, font, x, y, paired_chars, len) \
 
1977
   xtermXftDrawString(xw, flags, color, font, x, y, paired_chars, len, False)
1963
1978
#endif /* OPT_RENDERFONT */
1964
1979
 
1965
1980
#define DrawX(col) x + (col * (font_width))
1993
2008
    case 0x201D:                /* groff rq */
1994
2009
        ch = '"';
1995
2010
        break;
 
2011
    case 0x2329:                /* groff ".URL" */
 
2012
        ch = '<';
 
2013
        break;
 
2014
    case 0x232a:                /* groff ".URL" */
 
2015
        ch = '>';
 
2016
        break;
1996
2017
    default:
1997
2018
        if (ch >= 0xff01 && ch <= 0xff5e) {
1998
2019
            /* "Fullwidth" codes (actually double-width) */
2040
2061
                          PAIRED_CHARS(text, text2),
2041
2062
                          1,
2042
2063
                          on_wide);
 
2064
            fixed = True;
 
2065
        } else if (ch == HIDDEN_CHAR) {
 
2066
            fixed = True;
2043
2067
        }
2044
2068
    }
2045
2069
    return fixed;
2185
2209
#define endXftClipping(screen)  /* nothing */
2186
2210
#endif /* OPT_CLIP_BOLD */
2187
2211
 
 
2212
#if OPT_RENDERFONT
 
2213
static int
 
2214
drawClippedXftString(XtermWidget xw,
 
2215
                     unsigned flags,
 
2216
                     XftFont * font,
 
2217
                     XftColor * fg_color,
 
2218
                     int x,
 
2219
                     int y,
 
2220
                     PAIRED_CHARS(Char * text, Char * text2),
 
2221
                     Cardinal len)
 
2222
{
 
2223
    int ncells = xtermXftWidth(xw, flags,
 
2224
                               fg_color,
 
2225
                               font, x, y,
 
2226
                               PAIRED_CHARS(text, text2),
 
2227
                               len);
 
2228
    TScreen *screen = &(xw->screen);
 
2229
 
 
2230
    beginXftClipping(screen, x, y, ncells);
 
2231
    xtermXftDrawString(xw, flags,
 
2232
                       fg_color,
 
2233
                       font, x, y,
 
2234
                       PAIRED_CHARS(text, text2),
 
2235
                       len,
 
2236
                       True);
 
2237
    endXftClipping(screen);
 
2238
    return ncells;
 
2239
}
 
2240
#endif
 
2241
 
2188
2242
/*
2189
2243
 * Draws text with the specified combination of bold/underline.  The return
2190
2244
 * value is the updated x position.
2201
2255
              int on_wide)
2202
2256
{
2203
2257
    TScreen *screen = &(xw->screen);
2204
 
    int real_length = len;
2205
 
    int underline_len;
 
2258
    Cardinal real_length = len;
 
2259
    Cardinal underline_len = 0;
2206
2260
    /* Intended width of the font to draw (as opposed to the actual width of
2207
2261
       the X font, and the width of the default font) */
2208
2262
    int font_width = ((flags & DOUBLEWFONT) ? 2 : 1) * screen->fnt_wide;
2394
2448
 
2395
2449
        if (!(flags & NOBACKGROUND)) {
2396
2450
            XftColor *bg_color = getXftColor(xw, values.background);
2397
 
            ncells = xtermXftDrawString(xw, flags,
2398
 
                                        bg_color,
2399
 
                                        font, x, y,
2400
 
                                        PAIRED_CHARS(text, text2),
2401
 
                                        len,
2402
 
                                        False);
 
2451
            ncells = xtermXftWidth(xw, flags,
 
2452
                                   bg_color,
 
2453
                                   font, x, y,
 
2454
                                   PAIRED_CHARS(text, text2),
 
2455
                                   len);
2403
2456
            XftDrawRect(screen->renderDraw,
2404
2457
                        bg_color,
2405
2458
                        x, y,
2406
 
                        ncells * FontWidth(screen),
 
2459
                        (unsigned) (ncells * FontWidth(screen)),
2407
2460
                        (unsigned) FontHeight(screen));
2408
2461
        }
2409
2462
 
2441
2494
                if (xtermIsDecGraphic(ch)) {
2442
2495
                    /* line drawing character time */
2443
2496
                    if (last > first) {
2444
 
                        ncells = xtermXftDrawString(xw, flags,
2445
 
                                                    getXftColor(xw, values.foreground),
2446
 
                                                    font, curX, y,
2447
 
                                                    PAIRED_CHARS(text + first,
2448
 
                                                                 text2 + first),
2449
 
                                                    last - first,
2450
 
                                                    True);
2451
 
                        curX += ncells * FontWidth(screen);
 
2497
                        int nc = drawClippedXftString(xw,
 
2498
                                                      flags,
 
2499
                                                      font,
 
2500
                                                      getXftColor(xw, values.foreground),
 
2501
                                                      curX,
 
2502
                                                      y,
 
2503
                                                      PAIRED_CHARS(text + first,
 
2504
                                                                   text2 + first),
 
2505
                                                      (Cardinal) (last - first));
 
2506
                        curX += nc * FontWidth(screen);
 
2507
                        underline_len += nc;
2452
2508
                    }
2453
2509
                    old_wide = screen->fnt_wide;
2454
2510
                    old_high = screen->fnt_high;
2457
2513
                    xtermDrawBoxChar(xw, ch, flags, gc,
2458
2514
                                     curX, y - FontAscent(screen));
2459
2515
                    curX += FontWidth(screen);
 
2516
                    underline_len += 1;
2460
2517
                    screen->fnt_wide = old_wide;
2461
2518
                    screen->fnt_high = old_high;
2462
2519
                    first = last + 1;
2463
2520
                }
2464
2521
            }
2465
2522
            if (last > first) {
2466
 
                beginXftClipping(screen, curX, y, len);
2467
 
                xtermXftDrawString(xw, flags,
2468
 
                                   getXftColor(xw, values.foreground),
2469
 
                                   font, curX, y,
2470
 
                                   PAIRED_CHARS(text + first, text2 + first),
2471
 
                                   last - first,
2472
 
                                   True);
2473
 
                endXftClipping(screen);
 
2523
                underline_len +=
 
2524
                    drawClippedXftString(xw,
 
2525
                                         flags,
 
2526
                                         font,
 
2527
                                         getXftColor(xw, values.foreground),
 
2528
                                         curX,
 
2529
                                         y,
 
2530
                                         PAIRED_CHARS(text + first,
 
2531
                                                      text2 + first),
 
2532
                                         (Cardinal) (last - first));
2474
2533
            }
2475
2534
        } else
2476
2535
#endif /* OPT_BOX_CHARS */
2477
2536
        {
2478
 
            beginXftClipping(screen, x, y, len);
2479
 
            xtermXftDrawString(xw, flags,
2480
 
                               getXftColor(xw, values.foreground),
2481
 
                               font, x, y,
2482
 
                               PAIRED_CHARS(text, text2),
2483
 
                               (int) len,
2484
 
                               True);
2485
 
            endXftClipping(screen);
 
2537
            underline_len +=
 
2538
                drawClippedXftString(xw,
 
2539
                                     flags,
 
2540
                                     font,
 
2541
                                     getXftColor(xw, values.foreground),
 
2542
                                     x,
 
2543
                                     y,
 
2544
                                     PAIRED_CHARS(text, text2),
 
2545
                                     len);
2486
2546
        }
2487
2547
 
2488
2548
        if ((flags & UNDERLINE) && screen->underline && !did_ul) {
2490
2550
                y++;
2491
2551
            XDrawLine(screen->display, VWindow(screen), gc,
2492
2552
                      x, y,
2493
 
                      x + (int) len * FontWidth(screen) - 1,
 
2553
                      x + (int) underline_len * FontWidth(screen) - 1,
2494
2554
                      y);
2495
2555
        }
2496
2556
        return x + len * FontWidth(screen);
2539
2599
#if OPT_WIDE_CHARS
2540
2600
            if (text2 != 0)
2541
2601
                ch |= (text2[last] << 8);
 
2602
            if (ch == HIDDEN_CHAR) {
 
2603
                if (last > first)
 
2604
                    DrawSegment(first, last);
 
2605
                first = last + 1;
 
2606
                continue;
 
2607
            }
2542
2608
            isMissing = (ch != HIDDEN_CHAR)
2543
2609
                && (xtermMissingChar(xw, ch,
2544
2610
                                     ((on_wide || iswide((int) ch))
2749
2815
        if (FontDescent(screen) > 1)
2750
2816
            y++;
2751
2817
        XDrawLine(screen->display, VWindow(screen), gc,
2752
 
                  x, y, x + underline_len * font_width - 1, y);
 
2818
                  x, y, (int) (x + underline_len * font_width - 1), y);
2753
2819
    }
2754
2820
 
2755
2821
    return x + real_length * FontWidth(screen);
2820
2886
#if OPT_HIGHLIGHT_COLOR
2821
2887
    Pixel selbg_pix = T_COLOR(screen, HIGHLIGHT_BG);
2822
2888
    Pixel selfg_pix = T_COLOR(screen, HIGHLIGHT_FG);
 
2889
    Boolean use_selbg = isNotForeground(xw, fg_pix, bg_pix, selbg_pix);
 
2890
    Boolean use_selfg = isNotBackground(xw, fg_pix, bg_pix, selfg_pix);
2823
2891
#endif
2824
2892
 
2825
2893
    (void) fg_bg;
2828
2896
 
2829
2897
    checkVeryBoldColors(flags, my_fg);
2830
2898
 
2831
 
#if OPT_HIGHLIGHT_COLOR
2832
 
    if (hilite) {
2833
 
        Bool use_selbg = isNotForeground(xw, fg_pix, bg_pix, selbg_pix);
2834
 
        Bool use_selfg = isNotBackground(xw, fg_pix, bg_pix, selfg_pix);
 
2899
    if (ReverseOrHilite(screen, flags, hilite)) {
 
2900
        if (flags & BOLDATTR(screen)) {
 
2901
            cgsId = gcBoldReverse;
 
2902
        } else {
 
2903
            cgsId = gcNormReverse;
 
2904
        }
2835
2905
 
 
2906
        EXCHANGE(fg_pix, bg_pix, xx_pix);
 
2907
#if OPT_HIGHLIGHT_COLOR
 
2908
        if (screen->hilite_reverse) {
 
2909
            if (use_selbg) {
 
2910
                if (use_selfg)
 
2911
                    bg_pix = fg_pix;
 
2912
                else
 
2913
                    fg_pix = bg_pix;
 
2914
            }
 
2915
            if (use_selbg)
 
2916
                bg_pix = selbg_pix;
 
2917
            if (use_selfg)
 
2918
                fg_pix = selfg_pix;
 
2919
        }
 
2920
#endif
 
2921
    } else {
 
2922
        if (flags & BOLDATTR(screen)) {
 
2923
            cgsId = gcBold;
 
2924
        } else {
 
2925
            cgsId = gcNorm;
 
2926
        }
 
2927
    }
 
2928
#if OPT_HIGHLIGHT_COLOR
 
2929
    if (hilite && !screen->hilite_reverse) {
2836
2930
        if (use_selbg)
2837
 
            fg_pix = selbg_pix;
 
2931
            bg_pix = selbg_pix;
2838
2932
        if (use_selfg)
2839
 
            bg_pix = selfg_pix;
 
2933
            fg_pix = selfg_pix;
2840
2934
    }
2841
2935
#endif
2842
2936
 
2843
 
    if (ReverseOrHilite(screen, flags, hilite)) {
2844
 
        if (flags & BOLDATTR(screen)) {
2845
 
            cgsId = gcBoldReverse;
2846
 
        } else {
2847
 
            cgsId = gcNormReverse;
2848
 
        }
2849
 
        EXCHANGE(fg_pix, bg_pix, xx_pix);
2850
 
    } else {
2851
 
        if (flags & BOLDATTR(screen)) {
2852
 
            cgsId = gcBold;
2853
 
        } else {
2854
 
            cgsId = gcNorm;
2855
 
        }
2856
 
    }
2857
 
 
2858
2937
#if OPT_BLINK_TEXT
2859
2938
    if ((screen->blink_state == ON) && (!screen->blink_as_bold) && (flags & BLINK)) {
2860
2939
        fg_pix = bg_pix;
3252
3331
 * old runtime configurations which yield incomplete or inaccurate data.
3253
3332
 */
3254
3333
static Bool
3255
 
systemWcwidthOk(void)
 
3334
systemWcwidthOk(int samplesize, int samplepass)
3256
3335
{
3257
3336
    wchar_t n;
3258
3337
    int oops = 0;
3259
 
    int last = 1024;
3260
3338
 
3261
 
    for (n = 0; n < last; ++n) {
 
3339
    for (n = 0; n < samplesize; ++n) {
3262
3340
        int system_code = wcwidth(n);
3263
3341
        int intern_code = mk_wcwidth(n);
3264
3342
 
3284
3362
            ++oops;
3285
3363
        }
3286
3364
    }
3287
 
    TRACE(("systemWcwidthOk: %d/%d mismatches\n", oops, last));
3288
 
    return (oops < (last / 4));
 
3365
    TRACE(("systemWcwidthOk: %d/%d mismatches, allowed %d\n",
 
3366
           oops, samplesize, samplepass));
 
3367
    return (oops <= samplepass);
3289
3368
}
3290
3369
#endif /* HAVE_WCWIDTH */
3291
3370
 
3292
3371
void
3293
 
decode_wcwidth(int mode)
 
3372
decode_wcwidth(int mode, int samplesize, int samplepass)
3294
3373
{
3295
3374
    switch (mode) {
3296
3375
    default:
3297
3376
#if defined(HAVE_WCHAR_H) && defined(HAVE_WCWIDTH)
3298
 
        if (xtermEnvUTF8() && systemWcwidthOk()) {
 
3377
        if (xtermEnvUTF8() && systemWcwidthOk(samplesize, samplepass)) {
3299
3378
            my_wcwidth = wcwidth;
3300
3379
            TRACE(("using system wcwidth() function\n"));
3301
3380
            break;
3302
3381
        }
3303
3382
        /* FALLTHRU */
 
3383
#else
 
3384
        (void) samplesize;
 
3385
        (void) samplepass;
 
3386
#endif
3304
3387
    case 2:
3305
 
#endif
3306
3388
        my_wcwidth = &mk_wcwidth;
3307
3389
        TRACE(("using MK wcwidth() function\n"));
3308
3390
        break;