imRmAttr.c revision eb411b4b
1/****************************************************************** 2 3 Copyright 1992, 1993, 1994 by FUJITSU LIMITED 4 5Permission to use, copy, modify, distribute, and sell this software 6and its documentation for any purpose is hereby granted without fee, 7provided that the above copyright notice appear in all copies and 8that both that copyright notice and this permission notice appear 9in supporting documentation, and that the name of FUJITSU LIMITED 10not be used in advertising or publicity pertaining to distribution 11of the software without specific, written prior permission. 12FUJITSU LIMITED makes no representations about the suitability of 13this software for any purpose. 14It is provided "as is" without express or implied warranty. 15 16FUJITSU LIMITED DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, 17INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO 18EVENT SHALL FUJITSU LIMITED BE LIABLE FOR ANY SPECIAL, INDIRECT OR 19CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF 20USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR 21OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR 22PERFORMANCE OF THIS SOFTWARE. 23 24 Author: Takashi Fujiwara FUJITSU LIMITED 25 fujiwara@a80.tech.yk.fujitsu.co.jp 26 27******************************************************************/ 28 29#ifdef HAVE_CONFIG_H 30#include <config.h> 31#endif 32#include "Xlibint.h" 33#include "Xlcint.h" 34#include "Ximint.h" 35 36 37static XIMResourceList 38_XimGetNestedListSeparator( 39 XIMResourceList res_list, /* LISTofIMATTR or IMATTR */ 40 unsigned int res_num) 41{ 42 return _XimGetResourceListRec(res_list, res_num, XNSeparatorofNestedList); 43} 44 45static Bool 46_XimCheckInnerIMAttributes( 47 Xim im, 48 XIMArg *arg, 49 unsigned long mode) 50{ 51 XIMResourceList res; 52 int check; 53 54 if (!(res = _XimGetResourceListRec(im->private.proto.im_inner_resources, 55 im->private.proto.im_num_inner_resources, arg->name))) 56 return False; 57 58 check = _XimCheckIMMode(res, mode); 59 if(check == XIM_CHECK_INVALID) 60 return True; 61 else if(check == XIM_CHECK_ERROR) 62 return False; 63 64 return True; 65} 66 67char * 68_XimMakeIMAttrIDList( 69 Xim im, 70 XIMResourceList res_list, 71 unsigned int res_num, 72 XIMArg *arg, 73 CARD16 *buf, 74 INT16 *len, 75 unsigned long mode) 76{ 77 register XIMArg *p; 78 XIMResourceList res; 79 int check; 80 81 *len = 0; 82 if (!arg) 83 return (char *)NULL; 84 85 for (p = arg; p->name; p++) { 86 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 87 if (_XimCheckInnerIMAttributes(im, p, mode)) 88 continue; 89 return p->name; 90 } 91 92 check = _XimCheckIMMode(res, mode); 93 if (check == XIM_CHECK_INVALID) 94 continue; 95 else if (check == XIM_CHECK_ERROR) 96 return p->name; 97 98 *buf = res->id; 99 *len += sizeof(CARD16); 100 buf++; 101 } 102 return (char *)NULL; 103} 104 105static Bool 106_XimCheckInnerICAttributes( 107 Xic ic, 108 XIMArg *arg, 109 unsigned long mode) 110{ 111 XIMResourceList res; 112 int check; 113 114 if (!(res = _XimGetResourceListRec(ic->private.proto.ic_inner_resources, 115 ic->private.proto.ic_num_inner_resources, arg->name))) 116 return False; 117 118 check = _XimCheckICMode(res, mode); 119 if(check == XIM_CHECK_INVALID) 120 return True; 121 else if(check == XIM_CHECK_ERROR) 122 return False; 123 124 return True; 125} 126 127char * 128_XimMakeICAttrIDList( 129 Xic ic, 130 XIMResourceList res_list, 131 unsigned int res_num, 132 XIMArg *arg, 133 CARD16 *buf, 134 INT16 *len, 135 unsigned long mode) 136{ 137 register XIMArg *p; 138 XIMResourceList res; 139 int check; 140 XrmQuark pre_quark; 141 XrmQuark sts_quark; 142 char *name; 143 INT16 new_len; 144 145 *len = 0; 146 if (!arg) 147 return (char *)NULL; 148 149 pre_quark = XrmStringToQuark(XNPreeditAttributes); 150 sts_quark = XrmStringToQuark(XNStatusAttributes); 151 152 for (p = arg; p && p->name; p++) { 153 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 154 if (_XimCheckInnerICAttributes(ic, p, mode)) 155 continue; 156 *len = -1; 157 return p->name; 158 } 159 160 check = _XimCheckICMode(res, mode); 161 if(check == XIM_CHECK_INVALID) 162 continue; 163 else if(check == XIM_CHECK_ERROR) { 164 *len = -1; 165 return p->name; 166 } 167 168 *buf = res->id; 169 *len += sizeof(CARD16); 170 buf++; 171 if (res->resource_size == XimType_NEST) { 172 if (res->xrm_name == pre_quark) { 173 if ((name = _XimMakeICAttrIDList(ic, res_list, res_num, 174 (XIMArg *)p->value, buf, &new_len, 175 (mode | XIM_PREEDIT_ATTR)))) { 176 if (new_len < 0) *len = -1; 177 else *len += new_len; 178 return name; 179 } 180 *len += new_len; 181 buf = (CARD16 *)((char *)buf + new_len); 182 } else if (res->xrm_name == sts_quark) { 183 if ((name = _XimMakeICAttrIDList(ic, res_list, res_num, 184 (XIMArg *)p->value, buf, &new_len, 185 (mode | XIM_STATUS_ATTR)))) { 186 if (new_len < 0) *len = -1; 187 else *len += new_len; 188 return name; 189 } 190 *len += new_len; 191 buf = (CARD16 *)((char *)buf + new_len); 192 } 193 194 if (!(res = _XimGetNestedListSeparator(res_list, res_num))) { 195 p++; 196 if (p) { 197 *len = -1; 198 return p->name; 199 } 200 else { 201 return (char *)NULL; 202 } 203 } 204 *buf = res->id; 205 *len += sizeof(CARD16); 206 buf++; 207 } 208 } 209 return (char *)NULL; 210} 211 212static Bool 213_XimAttributeToValue( 214 Xic ic, 215 XIMResourceList res, 216 CARD16 *data, 217 INT16 data_len, 218 XPointer value, 219 BITMASK32 mode) 220{ 221 switch (res->resource_size) { 222 case XimType_SeparatorOfNestedList: 223 case XimType_NEST: 224 break; 225 226 case XimType_CARD8: 227 case XimType_CARD16: 228 case XimType_CARD32: 229 case XimType_Window: 230 case XimType_XIMHotKeyState: 231 _XCopyToArg((XPointer)data, (XPointer *)&value, data_len); 232 break; 233 234 case XimType_STRING8: 235 { 236 char *str; 237 238 if (!(value)) 239 return False; 240 241 if (!(str = (char *)Xmalloc(data_len + 1))) 242 return False; 243 244 (void)memcpy(str, (char *)data, data_len); 245 str[data_len] = '\0'; 246 247 *((char **)value) = str; 248 break; 249 } 250 251 case XimType_XIMStyles: 252 { 253 INT16 num = data[0]; 254 register CARD32 *style_list = (CARD32 *)&data[2]; 255 XIMStyle *style; 256 XIMStyles *rep; 257 register int i; 258 char *p; 259 int alloc_len; 260 261 if (!(value)) 262 return False; 263 264 alloc_len = sizeof(XIMStyles) + sizeof(XIMStyle) * num; 265 if (!(p = (char *)Xmalloc(alloc_len))) 266 return False; 267 268 rep = (XIMStyles *)p; 269 style = (XIMStyle *)(p + sizeof(XIMStyles)); 270 271 for (i = 0; i < num; i++) 272 style[i] = (XIMStyle)style_list[i]; 273 274 rep->count_styles = (unsigned short)num; 275 rep->supported_styles = style; 276 *((XIMStyles **)value) = rep; 277 break; 278 } 279 280 case XimType_XRectangle: 281 { 282 XRectangle *rep; 283 284 if (!(value)) 285 return False; 286 287 if (!(rep = (XRectangle *)Xmalloc(sizeof(XRectangle)))) 288 return False; 289 290 rep->x = data[0]; 291 rep->y = data[1]; 292 rep->width = data[2]; 293 rep->height = data[3]; 294 *((XRectangle **)value) = rep; 295 break; 296 } 297 298 case XimType_XPoint: 299 { 300 XPoint *rep; 301 302 if (!(value)) 303 return False; 304 305 if (!(rep = (XPoint *)Xmalloc(sizeof(XPoint)))) 306 return False; 307 308 rep->x = data[0]; 309 rep->y = data[1]; 310 *((XPoint **)value) = rep; 311 break; 312 } 313 314 case XimType_XFontSet: 315 { 316 INT16 len = data[0]; 317 char *base_name; 318 XFontSet rep = (XFontSet)NULL; 319 char **missing_list = NULL; 320 int missing_count; 321 char *def_string; 322 323 if (!(value)) 324 return False; 325 if (!ic) 326 return False; 327 328 if (!(base_name = (char *)Xmalloc(len + 1))) 329 return False; 330 331 (void)strncpy(base_name, (char *)&data[1], (int)len); 332 base_name[len] = '\0'; 333 334 if (mode & XIM_PREEDIT_ATTR) { 335 if (!strcmp(base_name, ic->private.proto.preedit_font)) { 336 rep = ic->core.preedit_attr.fontset; 337 } else if (!ic->private.proto.preedit_font_length) { 338 rep = XCreateFontSet(ic->core.im->core.display, 339 base_name, &missing_list, 340 &missing_count, &def_string); 341 } 342 } else if (mode & XIM_STATUS_ATTR) { 343 if (!strcmp(base_name, ic->private.proto.status_font)) { 344 rep = ic->core.status_attr.fontset; 345 } else if (!ic->private.proto.status_font_length) { 346 rep = XCreateFontSet(ic->core.im->core.display, 347 base_name, &missing_list, 348 &missing_count, &def_string); 349 } 350 } 351 352 Xfree(base_name); 353 Xfree(missing_list); 354 *((XFontSet *)value) = rep; 355 break; 356 } 357 358 case XimType_XIMHotKeyTriggers: 359 { 360 INT32 num = *((CARD32 *)data); 361 register CARD32 *key_list = (CARD32 *)&data[2]; 362 XIMHotKeyTrigger *key; 363 XIMHotKeyTriggers *rep; 364 register int i; 365 char *p; 366 int alloc_len; 367 368 if (!(value)) 369 return False; 370 371 alloc_len = sizeof(XIMHotKeyTriggers) 372 + sizeof(XIMHotKeyTrigger) * num; 373 if (!(p = (char *)Xmalloc(alloc_len))) 374 return False; 375 376 rep = (XIMHotKeyTriggers *)p; 377 key = (XIMHotKeyTrigger *)(p + sizeof(XIMHotKeyTriggers)); 378 379 for (i = 0; i < num; i++, key_list += 3) { 380 key[i].keysym = (KeySym)key_list[0]; /* keysym */ 381 key[i].modifier = (int)key_list[1]; /* modifier */ 382 key[i].modifier_mask = (int)key_list[2]; /* modifier_mask */ 383 } 384 385 rep->num_hot_key = (int)num; 386 rep->key = key; 387 *((XIMHotKeyTriggers **)value) = rep; 388 break; 389 } 390 391 case XimType_XIMStringConversion: 392 { 393 break; 394 } 395 396 default: 397 return False; 398 } 399 return True; 400} 401 402static Bool 403_XimDecodeInnerIMATTRIBUTE( 404 Xim im, 405 XIMArg *arg) 406{ 407 XIMResourceList res; 408 XimDefIMValues im_values; 409 410 if (!(res = _XimGetResourceListRec(im->private.proto.im_inner_resources, 411 im->private.proto.im_num_inner_resources, arg->name))) 412 return False; 413 414 _XimGetCurrentIMValues(im, &im_values); 415 return _XimDecodeLocalIMAttr(res, (XPointer)&im_values, arg->value); 416} 417 418char * 419_XimDecodeIMATTRIBUTE( 420 Xim im, 421 XIMResourceList res_list, 422 unsigned int res_num, 423 CARD16 *data, 424 INT16 data_len, 425 XIMArg *arg, 426 BITMASK32 mode) 427{ 428 register XIMArg *p; 429 XIMResourceList res; 430 int check; 431 INT16 len; 432 CARD16 *buf; 433 INT16 total; 434 INT16 min_len = sizeof(CARD16) /* sizeof attributeID */ 435 + sizeof(INT16); /* sizeof length */ 436 437 for (p = arg; p->name; p++) { 438 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 439 if (_XimDecodeInnerIMATTRIBUTE(im, p)) 440 continue; 441 return p->name; 442 } 443 444 check = _XimCheckIMMode(res, mode); 445 if(check == XIM_CHECK_INVALID) 446 continue; 447 else if(check == XIM_CHECK_ERROR) 448 return p->name; 449 450 total = data_len; 451 buf = data; 452 while (total >= min_len) { 453 if (res->id == buf[0]) 454 break; 455 456 len = buf[1]; 457 len += XIM_PAD(len) + min_len; 458 buf = (CARD16 *)((char *)buf + len); 459 total -= len; 460 } 461 if (total < min_len) 462 return p->name; 463 464 if (!(_XimAttributeToValue((Xic) im->private.local.current_ic, 465 res, &buf[2], buf[1], p->value, mode))) 466 return p->name; 467 } 468 return (char *)NULL; 469} 470 471static Bool 472_XimDecodeInnerICATTRIBUTE( 473 Xic ic, 474 XIMArg *arg, 475 unsigned long mode) 476{ 477 XIMResourceList res; 478 XimDefICValues ic_values; 479 480 if (!(res = _XimGetResourceListRec(ic->private.proto.ic_inner_resources, 481 ic->private.proto.ic_num_inner_resources, arg->name))) 482 return False; 483 484 _XimGetCurrentICValues(ic, &ic_values); 485 if (!_XimDecodeLocalICAttr(res, (XPointer)&ic_values, arg->value, mode)) 486 return False; 487 _XimSetCurrentICValues(ic, &ic_values); 488 return True; 489} 490 491char * 492_XimDecodeICATTRIBUTE( 493 Xic ic, 494 XIMResourceList res_list, 495 unsigned int res_num, 496 CARD16 *data, 497 INT16 data_len, 498 XIMArg *arg, 499 BITMASK32 mode) 500{ 501 register XIMArg *p; 502 XIMResourceList res; 503 int check; 504 INT16 len; 505 CARD16 *buf; 506 INT16 total; 507 char *name; 508 INT16 min_len = sizeof(CARD16) /* sizeof attributeID */ 509 + sizeof(INT16); /* sizeof length */ 510 XrmQuark pre_quark; 511 XrmQuark sts_quark; 512 513 if (!arg) 514 return (char *)NULL; 515 516 pre_quark = XrmStringToQuark(XNPreeditAttributes); 517 sts_quark = XrmStringToQuark(XNStatusAttributes); 518 519 for (p = arg; p->name; p++) { 520 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 521 if (_XimDecodeInnerICATTRIBUTE(ic, p, mode)) 522 continue; 523 return p->name; 524 } 525 526 check = _XimCheckICMode(res, mode); 527 if (check == XIM_CHECK_INVALID) 528 continue; 529 else if (check == XIM_CHECK_ERROR) 530 return p->name; 531 532 total = data_len; 533 buf = data; 534 while (total >= min_len) { 535 if (res->id == buf[0]) 536 break; 537 538 len = buf[1]; 539 len += XIM_PAD(len) + min_len; 540 buf = (CARD16 *)((char *)buf + len); 541 total -= len; 542 } 543 if (total < min_len) 544 return p->name; 545 546 if (res->resource_size == XimType_NEST) { 547 if (res->xrm_name == pre_quark) { 548 if ((name = _XimDecodeICATTRIBUTE(ic, res_list, res_num, 549 &buf[2], buf[1], (XIMArg *)p->value, 550 (mode | XIM_PREEDIT_ATTR)))) 551 return name; 552 } else if (res->xrm_name == sts_quark) { 553 if ((name = _XimDecodeICATTRIBUTE(ic, res_list, res_num, 554 &buf[2], buf[1], (XIMArg *)p->value, 555 (mode | XIM_STATUS_ATTR)))) 556 return name; 557 } 558 } else { 559 if (!(_XimAttributeToValue(ic, res, &buf[2], buf[1], 560 p->value, mode))) 561 return p->name; 562 } 563 } 564 return (char *)NULL; 565} 566 567static Bool 568_XimValueToAttribute( 569 XIMResourceList res, 570 XPointer buf, 571 int buf_size, 572 XPointer value, 573 int *len, 574 unsigned long mode, 575 XPointer param) 576{ 577 int ret_len; 578 579 switch (res->resource_size) { 580 case XimType_SeparatorOfNestedList: 581 case XimType_NEST: 582 *len = 0; 583 break; 584 585 case XimType_CARD8: 586 ret_len = sizeof(CARD8); 587 if (buf_size < ret_len + XIM_PAD(ret_len)) { 588 *len = -1; 589 return False; 590 } 591 592 *((CARD8 *)buf) = (CARD8)(long)value; 593 *len = ret_len; 594 break; 595 596 case XimType_CARD16: 597 ret_len = sizeof(CARD16); 598 if (buf_size < ret_len + XIM_PAD(ret_len)) { 599 *len = -1; 600 return False; 601 } 602 603 *((CARD16 *)buf) = (CARD16)(long)value; 604 *len = ret_len; 605 break; 606 607 case XimType_CARD32: 608 case XimType_Window: 609 case XimType_XIMHotKeyState: 610 ret_len = sizeof(CARD32); 611 if (buf_size < ret_len + XIM_PAD(ret_len)) { 612 *len = -1; 613 return False; 614 } 615 616 *((CARD32 *)buf) = (CARD32)(long)value; 617 *len = ret_len; 618 break; 619 620 case XimType_STRING8: 621 if (!value) { 622 *len = 0; 623 return False; 624 } 625 626 ret_len = strlen((char *)value); 627 if (buf_size < ret_len + XIM_PAD(ret_len)) { 628 *len = -1; 629 return False; 630 } 631 632 (void)memcpy((char *)buf, (char *)value, ret_len); 633 *len = ret_len; 634 break; 635 636 case XimType_XRectangle: 637 { 638 XRectangle *rect = (XRectangle *)value; 639 CARD16 *buf_s = (CARD16 *)buf; 640 641 if (!rect) { 642 *len = 0; 643 return False; 644 } 645 646 ret_len = sizeof(INT16) /* sizeof X */ 647 + sizeof(INT16) /* sizeof Y */ 648 + sizeof(CARD16) /* sizeof width */ 649 + sizeof(CARD16); /* sizeof height */ 650 if (buf_size < ret_len + XIM_PAD(ret_len)) { 651 *len = -1; 652 return False; 653 } 654 655 buf_s[0] = (CARD16)rect->x; /* X */ 656 buf_s[1] = (CARD16)rect->y; /* Y */ 657 buf_s[2] = (CARD16)rect->width; /* width */ 658 buf_s[3] = (CARD16)rect->height; /* heght */ 659 *len = ret_len; 660 break; 661 } 662 663 case XimType_XPoint: 664 { 665 XPoint *point = (XPoint *)value; 666 CARD16 *buf_s = (CARD16 *)buf; 667 668 if (!point) { 669 *len = 0; 670 return False; 671 } 672 673 ret_len = sizeof(INT16) /* sizeof X */ 674 + sizeof(INT16); /* sizeof Y */ 675 if (buf_size < ret_len + XIM_PAD(ret_len)) { 676 *len = -1; 677 return False; 678 } 679 680 buf_s[0] = (CARD16)point->x; /* X */ 681 buf_s[1] = (CARD16)point->y; /* Y */ 682 *len = ret_len; 683 break; 684 } 685 686 case XimType_XFontSet: 687 { 688 XFontSet font = (XFontSet)value; 689 Xic ic = (Xic)param; 690 char *base_name = NULL; 691 int length = 0; 692 CARD16 *buf_s = (CARD16 *)buf; 693 694 if (!font) { 695 *len = 0; 696 return False; 697 } 698 699 if (mode & XIM_PREEDIT_ATTR) { 700 base_name = ic->private.proto.preedit_font; 701 length = ic->private.proto.preedit_font_length; 702 } else if (mode & XIM_STATUS_ATTR) { 703 base_name = ic->private.proto.status_font; 704 length = ic->private.proto.status_font_length; 705 } 706 707 if (!base_name) { 708 *len = 0; 709 return False; 710 } 711 712 ret_len = sizeof(CARD16) /* sizeof length of Base name */ 713 + length; /* sizeof Base font name list */ 714 if (buf_size < ret_len + XIM_PAD(ret_len)) { 715 *len = -1; 716 return False; 717 } 718 719 buf_s[0] = (INT16)length; /* length of Base font name */ 720 (void)memcpy((char *)&buf_s[1], base_name, length); 721 /* Base font name list */ 722 *len = ret_len; 723 break; 724 } 725 726 case XimType_XIMHotKeyTriggers: 727 { 728 XIMHotKeyTriggers *hotkey = (XIMHotKeyTriggers *)value; 729 INT32 num; 730 CARD32 *buf_l = (CARD32 *)buf; 731 register CARD32 *key = (CARD32 *)&buf_l[1]; 732 register int i; 733 734 if (!hotkey) { 735 *len = 0; 736 return False; 737 } 738 num = (INT32)hotkey->num_hot_key; 739 740 ret_len = sizeof(INT32) /* sizeof number of key list */ 741 + (sizeof(CARD32) /* sizeof keysyn */ 742 + sizeof(CARD32) /* sizeof modifier */ 743 + sizeof(CARD32)) /* sizeof modifier_mask */ 744 * num; /* number of key list */ 745 if (buf_size < ret_len + XIM_PAD(ret_len)) { 746 *len = -1; 747 return False; 748 } 749 750 buf_l[0] = num; /* number of key list */ 751 for (i = 0; i < num; i++, key += 3) { 752 key[0] = (CARD32)(hotkey->key[i].keysym); 753 /* keysym */ 754 key[1] = (CARD32)(hotkey->key[i].modifier); 755 /* modifier */ 756 key[2] = (CARD32)(hotkey->key[i].modifier_mask); 757 /* modifier_mask */ 758 } 759 *len = ret_len; 760 break; 761 } 762 763 case XimType_XIMStringConversion: 764 { 765 *len = 0; 766 break; 767 } 768 769 default: 770 return False; 771 } 772 return True; 773} 774 775static Bool 776_XimSetInnerIMAttributes( 777 Xim im, 778 XPointer top, 779 XIMArg *arg, 780 unsigned long mode) 781{ 782 XIMResourceList res; 783 int check; 784 785 if (!(res = _XimGetResourceListRec(im->private.proto.im_inner_resources, 786 im->private.proto.im_num_inner_resources, arg->name))) 787 return False; 788 789 check = _XimCheckIMMode(res, mode); 790 if(check == XIM_CHECK_INVALID) 791 return True; 792 else if(check == XIM_CHECK_ERROR) 793 return False; 794 795 return _XimEncodeLocalIMAttr(res, top, arg->value); 796} 797 798char * 799_XimEncodeIMATTRIBUTE( 800 Xim im, 801 XIMResourceList res_list, 802 unsigned int res_num, 803 XIMArg *arg, 804 XIMArg **arg_ret, 805 char *buf, 806 int size, 807 int *ret_len, 808 XPointer top, 809 unsigned long mode) 810{ 811 register XIMArg *p; 812 XIMResourceList res; 813 int check; 814 CARD16 *buf_s; 815 int len; 816 int min_len = sizeof(CARD16) /* sizeof attribute ID */ 817 + sizeof(INT16); /* sizeof value length */ 818 819 *ret_len = 0; 820 for (p = arg; p->name; p++) { 821 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 822 if (_XimSetInnerIMAttributes(im, top, p, mode)) 823 continue; 824 return p->name; 825 } 826 827 check = _XimCheckIMMode(res, mode); 828 if (check == XIM_CHECK_INVALID) 829 continue; 830 else if (check == XIM_CHECK_ERROR) 831 return p->name; 832 833 if (!(_XimEncodeLocalIMAttr(res, top, p->value))) 834 return p->name; 835 836 buf_s = (CARD16 *)buf; 837 if (!(_XimValueToAttribute(res, (XPointer)&buf_s[2], (size - min_len), 838 p->value, &len, mode, (XPointer)NULL))) 839 return p->name; 840 841 if (len == 0) { 842 continue; 843 } else if (len < 0) { 844 *arg_ret = p; 845 return (char *)NULL; 846 } 847 848 buf_s[0] = res->id; /* attribute ID */ 849 buf_s[1] = len; /* value length */ 850 XIM_SET_PAD(&buf_s[2], len); /* pad */ 851 len += min_len; 852 853 buf += len; 854 *ret_len += len; 855 size -= len; 856 } 857 *arg_ret = (XIMArg *)NULL; 858 return (char *)NULL; 859} 860 861#ifdef XIM_CONNECTABLE 862Bool 863_XimEncodeSavedIMATTRIBUTE( 864 Xim im, 865 XIMResourceList res_list, 866 unsigned int res_num, 867 int *idx, 868 char *buf, 869 int size, 870 int *ret_len, 871 XPointer top, 872 unsigned long mode) 873{ 874 register int i; 875 int num = im->private.proto.num_saved_imvalues; 876 XrmQuark *quark_list = im->private.proto.saved_imvalues; 877 XIMResourceList res; 878 XPointer value; 879 CARD16 *buf_s; 880 int len; 881 int min_len = sizeof(CARD16) /* sizeof attribute ID */ 882 + sizeof(INT16); /* sizeof value length */ 883 884 if (!im->private.proto.saved_imvalues) { 885 *idx = -1; 886 *ret_len = 0; 887 return True; 888 } 889 890 *ret_len = 0; 891 for (i = *idx; i < num; i++) { 892 if (!(res = _XimGetResourceListRecByQuark(res_list, 893 res_num, quark_list[i]))) 894 continue; 895 896 if (!_XimDecodeLocalIMAttr(res, top, value)) 897 return False; 898 899 buf_s = (CARD16 *)buf; 900 if (!(_XimValueToAttribute(res, (XPointer)&buf_s[2], 901 (size - min_len), value, &len, mode, (XPointer)NULL))) 902 return False; 903 904 if (len == 0) { 905 continue; 906 } else if (len < 0) { 907 *idx = i; 908 return True; 909 } 910 911 buf_s[0] = res->id; /* attribute ID */ 912 buf_s[1] = len; /* value length */ 913 XIM_SET_PAD(&buf_s[2], len); /* pad */ 914 len += min_len; 915 916 buf += len; 917 *ret_len += len; 918 size -= len; 919 } 920 *idx = -1; 921 return True; 922} 923#endif /* XIM_CONNECTABLE */ 924 925static Bool 926_XimEncodeTopValue( 927 Xic ic, 928 XIMResourceList res, 929 XIMArg *p) 930{ 931 if (res->xrm_name == XrmStringToQuark(XNClientWindow)) { 932 ic->core.client_window = (Window)p->value; 933 if (ic->core.focus_window == (Window)0) 934 ic->core.focus_window = ic->core.client_window; 935 _XimRegisterFilter(ic); 936 937 } else if (res->xrm_name == XrmStringToQuark(XNFocusWindow)) { 938 if (ic->core.client_window) { 939 _XimUnregisterFilter(ic); 940 ic->core.focus_window = (Window)p->value; 941 _XimRegisterFilter(ic); 942 } else /* client_window not yet */ 943 ic->core.focus_window = (Window)p->value; 944 } 945 return True; 946} 947 948static Bool 949_XimEncodePreeditValue( 950 Xic ic, 951 XIMResourceList res, 952 XIMArg *p) 953{ 954 if (res->xrm_name == XrmStringToQuark(XNStdColormap)) { 955 XStandardColormap *colormap_ret; 956 int count; 957 958 if (!(XGetRGBColormaps(ic->core.im->core.display, 959 ic->core.focus_window, &colormap_ret, 960 &count, (Atom)p->value))) 961 return False; 962 963 XFree(colormap_ret); 964 } else if (res->xrm_name == XrmStringToQuark(XNFontSet)) { 965 int list_ret; 966 XFontStruct **struct_list; 967 char **name_list; 968 char *tmp; 969 int len; 970 register int i; 971 972 if (!p->value) 973 return False; 974 975 if (ic->private.proto.preedit_font) 976 Xfree(ic->private.proto.preedit_font); 977 978 list_ret = XFontsOfFontSet((XFontSet)p->value, 979 &struct_list, &name_list); 980 for (i = 0, len = 0; i < list_ret; i++) { 981 len += (strlen(name_list[i]) + sizeof(char)); 982 } 983 if (!(tmp = Xmalloc(len + 1))) { 984 ic->private.proto.preedit_font = NULL; 985 return False; 986 } 987 988 tmp[0] = '\0'; 989 for (i = 0; i < list_ret; i++) { 990 strcat(tmp, name_list[i]); 991 strcat(tmp, ","); 992 } 993 tmp[len - 1] = 0; 994 ic->private.proto.preedit_font = tmp; 995 ic->private.proto.preedit_font_length = len - 1; 996 } 997 return True; 998} 999 1000static Bool 1001_XimEncodeStatusValue( 1002 Xic ic, 1003 XIMResourceList res, 1004 XIMArg *p) 1005{ 1006 if (res->xrm_name == XrmStringToQuark(XNStdColormap)) { 1007 XStandardColormap *colormap_ret = NULL; 1008 int count; 1009 1010 if (!(XGetRGBColormaps(ic->core.im->core.display, 1011 ic->core.focus_window, &colormap_ret, 1012 &count, (Atom)p->value))) 1013 return False; 1014 1015 XFree(colormap_ret); 1016 } else if (res->xrm_name == XrmStringToQuark(XNFontSet)) { 1017 int list_ret; 1018 XFontStruct **struct_list; 1019 char **name_list; 1020 char *tmp; 1021 int len; 1022 register int i; 1023 1024 if (!p->value) 1025 return False; 1026 1027 if (ic->private.proto.status_font) 1028 Xfree(ic->private.proto.status_font); 1029 1030 list_ret = XFontsOfFontSet((XFontSet)p->value, 1031 &struct_list, &name_list); 1032 for (i = 0, len = 0; i < list_ret; i++) { 1033 len += (strlen(name_list[i]) + sizeof(char)); 1034 } 1035 if (!(tmp = Xmalloc(len+1))) { 1036 ic->private.proto.status_font = NULL; 1037 return False; 1038 } 1039 1040 tmp[0] = '\0'; 1041 for(i = 0; i < list_ret; i++) { 1042 strcat(tmp, name_list[i]); 1043 strcat(tmp, ","); 1044 } 1045 tmp[len - 1] = 0; 1046 ic->private.proto.status_font = tmp; 1047 ic->private.proto.status_font_length = len - 1; 1048 } 1049 return True; 1050} 1051 1052static Bool 1053_XimSetInnerICAttributes( 1054 Xic ic, 1055 XPointer top, 1056 XIMArg *arg, 1057 unsigned long mode) 1058{ 1059 XIMResourceList res; 1060 int check; 1061 1062 if (!(res = _XimGetResourceListRec(ic->private.proto.ic_inner_resources, 1063 ic->private.proto.ic_num_inner_resources, arg->name))) 1064 return False; 1065 1066 check = _XimCheckICMode(res, mode); 1067 if(check == XIM_CHECK_INVALID) 1068 return True; 1069 else if(check == XIM_CHECK_ERROR) 1070 return False; 1071 1072 return _XimEncodeLocalICAttr(ic, res, top, arg, mode); 1073} 1074 1075char * 1076_XimEncodeICATTRIBUTE( 1077 Xic ic, 1078 XIMResourceList res_list, 1079 unsigned int res_num, 1080 XIMArg *arg, 1081 XIMArg **arg_ret, 1082 char *buf, 1083 int size, 1084 int *ret_len, 1085 XPointer top, 1086 BITMASK32 *flag, 1087 unsigned long mode) 1088{ 1089 register XIMArg *p; 1090 XIMResourceList res; 1091 int check; 1092 CARD16 *buf_s; 1093 int len; 1094 int min_len = sizeof(CARD16) /* sizeof attribute ID */ 1095 + sizeof(INT16); /* sizeof value length */ 1096 XrmQuark pre_quark; 1097 XrmQuark sts_quark; 1098 char *name; 1099 1100 pre_quark = XrmStringToQuark(XNPreeditAttributes); 1101 sts_quark = XrmStringToQuark(XNStatusAttributes); 1102 1103 *ret_len = 0; 1104 for (p = arg; p && p->name; p++) { 1105 buf_s = (CARD16 *)buf; 1106 if (!(res = _XimGetResourceListRec(res_list, res_num, p->name))) { 1107 if (_XimSetInnerICAttributes(ic, top, p, mode)) 1108 continue; 1109 return p->name; 1110 } 1111 1112 check = _XimCheckICMode(res, mode); 1113 if (check == XIM_CHECK_INVALID) 1114 continue; 1115 else if (check == XIM_CHECK_ERROR) 1116 return p->name; 1117 1118 if (mode & XIM_PREEDIT_ATTR) { 1119 if (!(_XimEncodePreeditValue(ic, res, p))) 1120 return p->name; 1121 } else if (mode & XIM_STATUS_ATTR) { 1122 if (!(_XimEncodeStatusValue(ic, res, p))) 1123 return p->name; 1124 } else { 1125 if (!(_XimEncodeTopValue(ic, res, p))) 1126 return p->name; 1127 } 1128 1129 if (res->resource_size == XimType_NEST) { 1130 XimDefICValues *ic_attr = (XimDefICValues *)top; 1131 1132 if (res->xrm_name == pre_quark) { 1133 XIMArg *arg_rt; 1134 if ((name = _XimEncodeICATTRIBUTE(ic, res_list, res_num, 1135 (XIMArg *)p->value, &arg_rt, 1136 (char *)&buf_s[2], (size - min_len), 1137 &len, (XPointer)&ic_attr->preedit_attr, flag, 1138 (mode | XIM_PREEDIT_ATTR)))) { 1139 return name; 1140 } 1141 1142 } else if (res->xrm_name == sts_quark) { 1143 XIMArg *arg_rt; 1144 if ((name = _XimEncodeICATTRIBUTE(ic, res_list, res_num, 1145 (XIMArg *)p->value, &arg_rt, 1146 (char *)&buf_s[2], (size - min_len), 1147 &len, (XPointer)&ic_attr->status_attr, flag, 1148 (mode | XIM_STATUS_ATTR)))) { 1149 return name; 1150 } 1151 } 1152 } else { 1153#ifdef EXT_MOVE 1154 if (flag) 1155 *flag |= _XimExtenArgCheck(p); 1156#endif 1157 if (!(_XimEncodeLocalICAttr(ic, res, top, p, mode))) 1158 return p->name; 1159 1160 if (!(_XimValueToAttribute(res, (XPointer)&buf_s[2], 1161 (size - min_len), p->value, 1162 &len, mode, (XPointer)ic))) 1163 return p->name; 1164 } 1165 1166 if (len == 0) { 1167 continue; 1168 } else if (len < 0) { 1169 *arg_ret = p; 1170 return (char *)NULL; 1171 } 1172 1173 buf_s[0] = res->id; /* attribute ID */ 1174 buf_s[1] = len; /* value length */ 1175 XIM_SET_PAD(&buf_s[2], len); /* pad */ 1176 len += min_len; 1177 1178 buf += len; 1179 *ret_len += len; 1180 size -= len; 1181 } 1182 *arg_ret = (XIMArg *)NULL; 1183 return (char *)NULL; 1184} 1185 1186#ifdef XIM_CONNECTABLE 1187static Bool 1188_XimEncodeSavedPreeditValue( 1189 Xic ic, 1190 XIMResourceList res, 1191 XPointer value) 1192{ 1193 int list_ret; 1194 XFontStruct **struct_list; 1195 char **name_list; 1196 char *tmp; 1197 int len; 1198 register int i; 1199 1200 if (res->xrm_name == XrmStringToQuark(XNFontSet)) { 1201 if (!value) 1202 return False; 1203 1204 if (ic->private.proto.preedit_font) 1205 Xfree(ic->private.proto.preedit_font); 1206 1207 list_ret = XFontsOfFontSet((XFontSet)value, 1208 &struct_list, &name_list); 1209 for(i = 0, len = 0; i < list_ret; i++) { 1210 len += (strlen(name_list[i]) + sizeof(char)); 1211 } 1212 if(!(tmp = Xmalloc(len + 1))) { 1213 ic->private.proto.preedit_font = NULL; 1214 return False; 1215 } 1216 1217 tmp[0] = '\0'; 1218 for(i = 0; i < list_ret; i++) { 1219 strcat(tmp, name_list[i]); 1220 strcat(tmp, ","); 1221 } 1222 tmp[len - 1] = 0; 1223 ic->private.proto.preedit_font = tmp; 1224 ic->private.proto.preedit_font_length = len - 1; 1225 } 1226 return True; 1227} 1228 1229static Bool 1230_XimEncodeSavedStatusValue( 1231 Xic ic, 1232 XIMResourceList res, 1233 XPointer value) 1234{ 1235 int list_ret; 1236 XFontStruct **struct_list; 1237 char **name_list; 1238 char *tmp; 1239 int len; 1240 register int i; 1241 1242 if (res->xrm_name == XrmStringToQuark(XNFontSet)) { 1243 if (!value) 1244 return False; 1245 1246 if (ic->private.proto.status_font) 1247 Xfree(ic->private.proto.status_font); 1248 1249 list_ret = XFontsOfFontSet((XFontSet)value, 1250 &struct_list, &name_list); 1251 for(i = 0, len = 0; i < list_ret; i++) { 1252 len += (strlen(name_list[i]) + sizeof(char)); 1253 } 1254 if(!(tmp = Xmalloc(len + 1))) { 1255 ic->private.proto.status_font = NULL; 1256 return False; 1257 } 1258 1259 tmp[0] = '\0'; 1260 for(i = 0; i < list_ret; i++) { 1261 strcat(tmp, name_list[i]); 1262 strcat(tmp, ","); 1263 } 1264 tmp[len - 1] = 0; 1265 ic->private.proto.status_font = tmp; 1266 ic->private.proto.status_font_length = len - 1; 1267 } 1268 return True; 1269} 1270 1271Bool 1272_XimEncodeSavedICATTRIBUTE( 1273 Xic ic, 1274 XIMResourceList res_list, 1275 unsigned int res_num, 1276 int *idx, 1277 char *buf, 1278 int size, 1279 int *ret_len, 1280 XPointer top, 1281 unsigned long mode) 1282{ 1283 int i; 1284 int num = ic->private.proto.num_saved_icvalues; 1285 XrmQuark *quark_list = ic->private.proto.saved_icvalues; 1286 XIMResourceList res; 1287 XPointer value; 1288 CARD16 *buf_s; 1289 int len; 1290 int min_len = sizeof(CARD16) /* sizeof attribute ID */ 1291 + sizeof(INT16); /* sizeof value length */ 1292 XrmQuark pre_quark; 1293 XrmQuark sts_quark; 1294 XrmQuark separator; 1295 1296 if (!ic->private.proto.saved_icvalues) { 1297 *idx = -1; 1298 *ret_len = 0; 1299 return True; 1300 } 1301 1302 pre_quark = XrmStringToQuark(XNPreeditAttributes); 1303 sts_quark = XrmStringToQuark(XNStatusAttributes); 1304 separator = XrmStringToQuark(XNSeparatorofNestedList); 1305 1306 *ret_len = 0; 1307 for (i = *idx; i < num; i++) { 1308 if (quark_list[i] == separator) { 1309 *idx = i; 1310 return True; 1311 } 1312 1313 if (!(res = _XimGetResourceListRecByQuark(res_list, 1314 res_num, quark_list[i]))) 1315 continue; 1316 1317 if (!_XimDecodeLocalICAttr(res, top,(XPointer)&value, mode)) 1318 return False; 1319 1320 if (mode & XIM_PREEDIT_ATTR) { 1321 if (!(_XimEncodeSavedPreeditValue(ic, res, value))) { 1322 return False; 1323 } 1324 } else if (mode & XIM_STATUS_ATTR) { 1325 if (!(_XimEncodeSavedStatusValue(ic, res, value))) { 1326 return False; 1327 } 1328 } 1329 1330 buf_s = (CARD16 *)buf; 1331 if (res->resource_size == XimType_NEST) { 1332 XimDefICValues *ic_attr = (XimDefICValues *)top; 1333 1334 i++; 1335 if (res->xrm_name == pre_quark) { 1336 if (!_XimEncodeSavedICATTRIBUTE(ic, res_list, res_num, 1337 &i, (char *)&buf_s[2], (size - min_len), 1338 &len, (XPointer)&ic_attr->preedit_attr, 1339 (mode | XIM_PREEDIT_ATTR))) { 1340 return False; 1341 } 1342 1343 } else if (res->xrm_name == sts_quark) { 1344 if (!_XimEncodeSavedICATTRIBUTE(ic, res_list, res_num, 1345 &i, (char *)&buf_s[2], (size - min_len), 1346 &len, (XPointer)&ic_attr->status_attr, 1347 (mode | XIM_STATUS_ATTR))) { 1348 return False; 1349 } 1350 } 1351 } else { 1352 if (!(_XimValueToAttribute(res, (XPointer)&buf_s[2], 1353 (size - min_len), value, 1354 &len, mode, (XPointer)ic))) { 1355 return False; 1356 } 1357 } 1358 1359 if (len == 0) { 1360 continue; 1361 } else if (len < 0) { 1362 if (quark_list[i] == separator) 1363 i++; 1364 *idx = i; 1365 return True; 1366 } 1367 1368 buf_s[0] = res->id; /* attribute ID */ 1369 buf_s[1] = len; /* value length */ 1370 XIM_SET_PAD(&buf_s[2], len); /* pad */ 1371 len += min_len; 1372 1373 buf += len; 1374 *ret_len += len; 1375 size -= len; 1376 } 1377 *idx = -1; 1378 return True; 1379} 1380#endif /* XIM_CONNECTABLE */ 1381 1382static unsigned int 1383_XimCountNumberOfAttr( 1384 INT16 total, 1385 CARD16 *attr, 1386 int *names_len) 1387{ 1388 unsigned int n; 1389 INT16 len; 1390 INT16 min_len = sizeof(CARD16) /* sizeof attribute ID */ 1391 + sizeof(CARD16) /* sizeof type of value */ 1392 + sizeof(INT16); /* sizeof length of attribute */ 1393 1394 n = 0; 1395 *names_len = 0; 1396 while (total > min_len) { 1397 len = attr[2]; 1398 *names_len += (len + 1); 1399 len += (min_len + XIM_PAD(len + 2)); 1400 total -= len; 1401 attr = (CARD16 *)((char *)attr + len); 1402 n++; 1403 } 1404 return n; 1405} 1406 1407Bool 1408_XimGetAttributeID( 1409 Xim im, 1410 CARD16 *buf) 1411{ 1412 unsigned int n; 1413 XIMResourceList res; 1414 char *names; 1415 int names_len; 1416 XPointer tmp; 1417 XIMValuesList *values_list; 1418 char **values; 1419 int values_len; 1420 register int i; 1421 INT16 len; 1422 INT16 min_len = sizeof(CARD16) /* sizeof attribute ID */ 1423 + sizeof(CARD16) /* sizeof type of value */ 1424 + sizeof(INT16); /* sizeof length of attr */ 1425 /* 1426 * IM attribute ID 1427 */ 1428 1429 if (!(n = _XimCountNumberOfAttr(buf[0], &buf[1], &names_len))) 1430 return False; 1431 1432 if (!(res = Xcalloc(n, sizeof(XIMResource)))) 1433 return False; 1434 1435 values_len = sizeof(XIMValuesList) + (sizeof(char **) * n) + names_len; 1436 if (!(tmp = Xcalloc(1, values_len))) { 1437 Xfree(res); 1438 return False; 1439 } 1440 1441 values_list = (XIMValuesList *)tmp; 1442 values = (char **)((char *)tmp + sizeof(XIMValuesList)); 1443 names = (char *)((char *)values + (sizeof(char **) * n)); 1444 1445 values_list->count_values = n; 1446 values_list->supported_values = values; 1447 1448 buf++; 1449 for (i = 0; i < n; i++) { 1450 len = buf[2]; 1451 (void)memcpy(names, (char *)&buf[3], len); 1452 values[i] = names; 1453 names[len] = '\0'; 1454 res[i].resource_name = names; 1455 res[i].resource_size = buf[1]; 1456 res[i].id = buf[0]; 1457 names += (len + 1); 1458 len += (min_len + XIM_PAD(len + 2)); 1459 buf = (CARD16 *)((char *)buf + len); 1460 } 1461 _XIMCompileResourceList(res, n); 1462 1463 if (im->core.im_resources) 1464 Xfree(im->core.im_resources); 1465 if (im->core.im_values_list) 1466 Xfree(im->core.im_values_list); 1467 im->core.im_resources = res; 1468 im->core.im_num_resources = n; 1469 im->core.im_values_list = values_list; 1470 1471 /* 1472 * IC attribute ID 1473 */ 1474 1475 if (!(n = _XimCountNumberOfAttr(buf[0], &buf[2], &names_len))) 1476 return False; 1477 1478 if (!(res = Xcalloc(n, sizeof(XIMResource)))) 1479 return False; 1480 1481 values_len = sizeof(XIMValuesList) + (sizeof(char **) * n) + names_len; 1482 if (!(tmp = Xcalloc(1, values_len))) { 1483 Xfree(res); 1484 return False; 1485 } 1486 1487 values_list = (XIMValuesList *)tmp; 1488 values = (char **)((char *)tmp + sizeof(XIMValuesList)); 1489 names = (char *)((char *)values + (sizeof(char **) * n)); 1490 1491 values_list->count_values = n; 1492 values_list->supported_values = values; 1493 1494 buf += 2; 1495 for (i = 0; i < n; i++) { 1496 len = buf[2]; 1497 (void)memcpy(names, (char *)&buf[3], len); 1498 values[i] = names; 1499 names[len] = '\0'; 1500 res[i].resource_name = names; 1501 res[i].resource_size = buf[1]; 1502 res[i].id = buf[0]; 1503 names += (len + 1); 1504 len += (min_len + XIM_PAD(len + 2)); 1505 buf = (CARD16 *)((char *)buf + len); 1506 } 1507 _XIMCompileResourceList(res, n); 1508 1509 if (im->core.ic_resources) 1510 Xfree(im->core.ic_resources); 1511 if (im->core.ic_values_list) 1512 Xfree(im->core.ic_values_list); 1513 im->core.ic_resources = res; 1514 im->core.ic_num_resources = n; 1515 im->core.ic_values_list = values_list; 1516 1517 return True; 1518} 1519