~ubuntu-branches/ubuntu/utopic/xterm/utopic-proposed

« back to all changes in this revision

Viewing changes to xtermcap.c

  • Committer: Bazaar Package Importer
  • Author(s): Muharem Hrnjadovic
  • Date: 2009-06-03 13:00:55 UTC
  • mfrom: (1.1.15 upstream) (11.1.8 sid)
  • Revision ID: james.westby@ubuntu.com-20090603130055-1cs2n0skvpk00pw2
Tags: 243-1ubuntu1
* Merge from debian unstable, remaining changes:
  - Enabled URL highlighting
  - rm -rf for .pc patches

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* $XTermId: xtermcap.c,v 1.15 2009/01/26 00:10:15 tom Exp $ */
 
1
/* $XTermId: xtermcap.c,v 1.21 2009/03/16 00:31:06 tom Exp $ */
2
2
 
3
3
/*
4
4
 * Copyright 2007-2008,2009 by Thomas E. Dickey
56
56
 
57
57
#if OPT_TCAP_QUERY || OPT_TCAP_FKEYS
58
58
 
 
59
#define SHIFT (MOD_NONE + MOD_SHIFT)
 
60
 
 
61
#define NO_STRING (char *)(-1)
 
62
 
59
63
typedef struct {
60
64
    char *tc;
61
65
    char *ti;
62
66
    int code;
63
 
    unsigned state;
 
67
    unsigned param;             /* see xtermStateToParam() */
64
68
} TCAPINFO;
65
69
/* *INDENT-OFF* */
66
70
#define DATA(tc,ti,x,y) { tc, ti, x, y }
67
71
static TCAPINFO table[] = {
68
 
        /*      tcap    terminfo        code            param */
 
72
        /*      tcap    terminfo        code            state */
69
73
        DATA(   "%1",   "khlp",         XK_Help,        0       ),
70
 
        DATA(   "#1",   "kHLP",         XK_Help,        2       ),
 
74
        DATA(   "#1",   "kHLP",         XK_Help,        SHIFT   ),
71
75
        DATA(   "@0",   "kfnd",         XK_Find,        0       ),
72
 
        DATA(   "*0",   "kFND",         XK_Find,        2       ),
 
76
        DATA(   "*0",   "kFND",         XK_Find,        SHIFT   ),
73
77
        DATA(   "*6",   "kslt",         XK_Select,      0       ),
74
 
        DATA(   "#6",   "kSLT",         XK_Select,      2       ),
 
78
        DATA(   "#6",   "kSLT",         XK_Select,      SHIFT   ),
75
79
 
76
80
        DATA(   "kh",   "khome",        XK_Home,        0       ),
77
 
        DATA(   "#2",   "kHOM",         XK_Home,        2       ),
 
81
        DATA(   "#2",   "kHOM",         XK_Home,        SHIFT   ),
78
82
        DATA(   "@7",   "kend",         XK_End,         0       ),
79
 
        DATA(   "*7",   "kEND",         XK_End,         2       ),
 
83
        DATA(   "*7",   "kEND",         XK_End,         SHIFT   ),
80
84
 
81
85
        DATA(   "kl",   "kcub1",        XK_Left,        0       ),
82
86
        DATA(   "kr",   "kcuf1",        XK_Right,       0       ),
83
87
        DATA(   "ku",   "kcuu1",        XK_Up,          0       ),
84
88
        DATA(   "kd",   "kcud1",        XK_Down,        0       ),
85
89
 
86
 
        DATA(   "#4",   "kLFT",         XK_Left,        2       ),
87
 
        DATA(   "%i",   "kRIT",         XK_Right,       2       ),
88
 
        DATA(   "%e",   "kPRV",         XK_Up,          2       ),
89
 
        DATA(   "%c",   "kNXT",         XK_Down,        2       ),
 
90
        DATA(   "#4",   "kLFT",         XK_Left,        SHIFT   ),
 
91
        DATA(   "%i",   "kRIT",         XK_Right,       SHIFT   ),
 
92
        DATA(   "%e",   "kPRV",         XK_Up,          SHIFT   ),
 
93
        DATA(   "%c",   "kNXT",         XK_Down,        SHIFT   ),
90
94
 
91
95
        DATA(   "k1",   "kf1",          XK_Fn(1),       0       ),
92
96
        DATA(   "k2",   "kf2",          XK_Fn(2),       0       ),
202
206
#undef DATA
203
207
/* *INDENT-ON* */
204
208
 
 
209
#if OPT_TCAP_FKEYS
 
210
static void
 
211
loadTermcapStrings(TScreen * screen)
 
212
{
 
213
    if (screen->tcap_fkeys == 0) {
 
214
        Cardinal want = XtNumber(table);
 
215
        Cardinal have;
 
216
        char *fkey;
 
217
 
 
218
#if !(USE_TERMINFO && defined(HAVE_TIGETSTR))
 
219
        char *area = screen->tcap_area;
 
220
#endif
 
221
 
 
222
        if ((screen->tcap_fkeys = TypeCallocN(char *, want)) != 0) {
 
223
            for (have = 0; have < want; ++have) {
 
224
#if USE_TERMINFO && defined(HAVE_TIGETSTR)
 
225
                fkey = tigetstr(table[have].ti);
 
226
#else
 
227
                fkey = tgetstr(table[have].tc, &area);
 
228
#endif
 
229
                if (fkey != 0 && fkey != NO_STRING) {
 
230
                    screen->tcap_fkeys[have] = x_strdup(fkey);
 
231
                } else {
 
232
                    screen->tcap_fkeys[have] = NO_STRING;
 
233
                }
 
234
            }
 
235
        }
 
236
    }
 
237
}
 
238
#endif
 
239
 
205
240
#if OPT_TCAP_QUERY
206
241
static int
207
242
hex2int(int c)
215
250
    return -1;
216
251
}
217
252
 
218
 
static TCAPINFO *
219
 
lookupTcapByName(XtermWidget xw, const char *name)
220
 
{
221
 
    TCAPINFO *result = 0;
222
 
    Cardinal n;
 
253
static Boolean
 
254
keyIsDistinct(XtermWidget xw, int which)
 
255
{
 
256
    Boolean result = True;
 
257
 
 
258
    switch (xw->keyboard.type) {
 
259
    case keyboardIsTermcap:
 
260
#if OPT_TCAP_FKEYS
 
261
        if (table[which].param == SHIFT) {
 
262
            TScreen *screen = TScreenOf(xw);
 
263
            Cardinal k;
 
264
            char *fkey;
 
265
 
 
266
            loadTermcapStrings(screen);
 
267
            if ((fkey = screen->tcap_fkeys[which]) != NO_STRING) {
 
268
                for (k = 0; k < XtNumber(table); k++) {
 
269
                    if (table[k].code == table[which].code
 
270
                        && table[k].param == 0) {
 
271
                        if ((fkey = screen->tcap_fkeys[k]) != NO_STRING
 
272
                            && !strcmp(fkey, screen->tcap_fkeys[which])) {
 
273
                            TRACE(("shifted/unshifted keys do not differ\n"));
 
274
                            result = False;
 
275
                        }
 
276
                        break;
 
277
                    }
 
278
                }
 
279
            } else {
 
280
                /* there is no data for the shifted key */
 
281
                result = -1;
 
282
            }
 
283
        }
 
284
#endif
 
285
        break;
 
286
        /*
 
287
         * The vt220-keyboard will not return distinct key sequences for
 
288
         * shifted cursor-keys.  Just pretend they do not exist, since some
 
289
         * programs may be confused if we return the same data for
 
290
         * shifted/unshifted keys.
 
291
         */
 
292
    case keyboardIsVT220:
 
293
        if (table[which].param == SHIFT) {
 
294
            TRACE(("shifted/unshifted keys do not differ\n"));
 
295
            result = False;
 
296
        }
 
297
        break;
 
298
    case keyboardIsLegacy:
 
299
    case keyboardIsDefault:
 
300
    case keyboardIsHP:
 
301
    case keyboardIsSCO:
 
302
    case keyboardIsSun:
 
303
        break;
 
304
    }
 
305
 
 
306
    return result;
 
307
}
 
308
 
 
309
static int
 
310
lookupTcapByName(const char *name)
 
311
{
 
312
    int result = -2;
 
313
    Cardinal j;
223
314
 
224
315
    if (name != 0 && *name != '\0') {
225
 
        for (n = 0; n < XtNumber(table); n++) {
226
 
            if (!strcmp(table[n].ti, name) || !strcmp(table[n].tc, name)) {
227
 
                result = table + n;
 
316
        for (j = 0; j < XtNumber(table); j++) {
 
317
            if (!strcmp(table[j].ti, name) || !strcmp(table[j].tc, name)) {
 
318
                result = (int) j;
228
319
                break;
229
320
            }
230
321
        }
231
322
    }
232
323
 
233
 
    /*
234
 
     * The vt220-keyboard will not return distinct key sequences for shifted
235
 
     * cursor-keys.  Just pretend they do not exist, since some programs may
236
 
     * be confused if we return the same data for shifted/unshifted keys.
237
 
     */
238
 
    if (xw->keyboard.type == keyboardIsVT220
239
 
        && result != 0
240
 
        && result->state == 2) {
241
 
        result = 0;
242
 
    }
243
 
 
244
 
    if (result != 0) {
245
 
        TRACE(("lookupTcapByName(%s) tc=%s, ti=%s code %#x, state %#x\n",
246
 
               name, result->tc, result->ti, result->code, result->state));
 
324
    if (result >= 0) {
 
325
        TRACE(("lookupTcapByName(%s) tc=%s, ti=%s code %#x, param %#x\n",
 
326
               name,
 
327
               table[result].tc,
 
328
               table[result].ti,
 
329
               table[result].code,
 
330
               table[result].param));
247
331
    } else {
248
332
        TRACE(("lookupTcapByName(%s) FAIL\n", name));
249
333
    }
264
348
{
265
349
    TCAPINFO *data;
266
350
    unsigned len = 0;
 
351
    int which;
267
352
    int code = -1;
268
353
#define MAX_TNAME_LEN 6
269
354
    char name[MAX_TNAME_LEN + 1];
283
368
    *state = 0;
284
369
    *fkey = False;
285
370
 
286
 
    if (*p == 0 || *p == ';') {
287
 
        if ((data = lookupTcapByName(xw, name)) != 0) {
288
 
            code = data->code;
289
 
            *state = xtermParamToState(xw, data->state);
290
 
            if (IsFunctionKey(code)) {
291
 
                *fkey = True;
292
 
            } else if (code < 0) {
293
 
                *fkey = True;
294
 
                code = XK_Fn((-code));
295
 
            }
 
371
    if (len && (*p == 0 || *p == ';')) {
 
372
        if ((which = lookupTcapByName(name)) >= 0) {
 
373
            if (keyIsDistinct(xw, which)) {
 
374
                data = table + which;
 
375
                code = data->code;
 
376
                *state = xtermParamToState(xw, data->param);
 
377
                if (IsFunctionKey(code)) {
 
378
                    *fkey = True;
 
379
                } else if (code < 0) {
 
380
                    *fkey = True;
 
381
                    code = XK_Fn((-code));
 
382
                }
296
383
#if OPT_SUN_FUNC_KEYS
297
 
            if (*fkey && xw->keyboard.type == keyboardIsSun) {
298
 
                int num = code - XK_Fn(0);
 
384
                if (*fkey && xw->keyboard.type == keyboardIsSun) {
 
385
                    int num = code - XK_Fn(0);
299
386
 
300
 
                /* match function-key case in sunfuncvalue() */
301
 
                if (num > 20) {
302
 
                    if (num <= 30 || num > 47) {
303
 
                        code = -1;
304
 
                    } else {
305
 
                        code -= 10;
306
 
                        switch (num) {
307
 
                        case 37:        /* khome */
308
 
                        case 39:        /* kpp */
309
 
                        case 41:        /* kb2 */
310
 
                        case 43:        /* kend */
311
 
                        case 45:        /* knp */
 
387
                    /* match function-key case in sunfuncvalue() */
 
388
                    if (num > 20) {
 
389
                        if (num <= 30 || num > 47) {
312
390
                            code = -1;
313
 
                            break;
 
391
                        } else {
 
392
                            code -= 10;
 
393
                            switch (num) {
 
394
                            case 37:    /* khome */
 
395
                            case 39:    /* kpp */
 
396
                            case 41:    /* kb2 */
 
397
                            case 43:    /* kend */
 
398
                            case 45:    /* knp */
 
399
                                code = -1;
 
400
                                break;
 
401
                            }
314
402
                        }
315
403
                    }
316
404
                }
 
405
#endif
 
406
            } else {
 
407
                TRACE(("... name ok, data not ok\n"));
 
408
                code = -1;
317
409
            }
318
 
#endif
 
410
        } else {
 
411
            TRACE(("... name not ok\n"));
 
412
            code = -2;
319
413
        }
 
414
    } else {
 
415
        TRACE(("... name not ok\n"));
 
416
        code = -2;
320
417
    }
321
418
 
322
419
    TRACE(("... xtermcapKeycode(%s, %u, %d) -> %#06x\n",
327
424
 
328
425
#if OPT_TCAP_FKEYS
329
426
static TCAPINFO *
330
 
lookupTcapByCode(int code, unsigned mask)
 
427
lookupTcapByCode(int code, unsigned param)
331
428
{
332
429
    TCAPINFO *result = 0;
333
430
    Cardinal n;
334
431
 
335
 
    TRACE(("lookupTcapByCode %d:%#x\n", code, mask));
 
432
    TRACE(("lookupTcapByCode %#x:%#x\n", code, param));
336
433
    for (n = 0; n < XtNumber(table); n++) {
337
434
        if (table[n].code == code &&
338
 
            table[n].state == mask) {
339
 
            TRACE(("lookupTcapByCode %d:%s\n", n, table[n].ti));
 
435
            table[n].param == param) {
 
436
            TRACE(("->lookupTcapByCode %d:%s\n", n, table[n].ti));
340
437
            result = table + n;
341
438
            break;
342
439
        }
344
441
    return result;
345
442
}
346
443
 
347
 
#define NO_STRING (char *)(-1)
348
 
 
349
444
int
350
445
xtermcapString(XtermWidget xw, int keycode, unsigned mask)
351
446
{
355
450
 
356
451
    if ((data = lookupTcapByCode(keycode, param)) != 0) {
357
452
        TScreen *screen = TScreenOf(xw);
358
 
        Cardinal which = data - table;
 
453
        Cardinal which = (Cardinal) (data - table);
359
454
        char *fkey;
360
455
 
361
 
        if (screen->tcap_fkeys == 0) {
362
 
            Cardinal want = XtNumber(table);
363
 
            Cardinal have;
364
 
#if !(USE_TERMINFO && defined(HAVE_TIGETSTR))
365
 
            char *area = screen->tcap_area;
366
 
#endif
367
 
 
368
 
            if ((screen->tcap_fkeys = TypeCallocN(char *, want)) != 0) {
369
 
                for (have = 0; have < want; ++have) {
370
 
#if USE_TERMINFO && defined(HAVE_TIGETSTR)
371
 
                    fkey = tigetstr(table[have].ti);
372
 
#else
373
 
                    fkey = tgetstr(table[have].tc, &area);
374
 
#endif
375
 
                    if (fkey != 0 && fkey != NO_STRING) {
376
 
                        screen->tcap_fkeys[have] = x_strdup(fkey);
377
 
                    } else {
378
 
                        screen->tcap_fkeys[have] = NO_STRING;
379
 
                    }
380
 
                }
381
 
            }
382
 
        }
 
456
        loadTermcapStrings(screen);
383
457
        if (screen->tcap_fkeys != 0) {
384
458
            if ((fkey = screen->tcap_fkeys[which]) != NO_STRING) {
385
459
                StringInput(xw, (Char *) fkey, strlen(fkey));