2 Copyright (c) 1993 by Silicon Graphics Computer Systems, Inc.
4 Permission to use, copy, modify, and distribute this
5 software and its documentation for any purpose and without
6 fee is hereby granted, provided that the above copyright
7 notice appear in all copies and that both that copyright
8 notice and this permission notice appear in supporting
9 documentation, and that the name of Silicon Graphics not be
10 used in advertising or publicity pertaining to distribution
11 of the software without specific prior written permission.
12 Silicon Graphics makes no representation about the suitability
13 of this software for any purpose. It is provided "as is"
14 without any express or implied warranty.
16 SILICON GRAPHICS DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS
17 SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
18 AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SILICON
19 GRAPHICS BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
20 DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
21 DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
22 OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH
23 THE USE OR PERFORMANCE OF THIS SOFTWARE.
30 #include "xkbcommon/xkbcommon.h"
31 #include "XKBcommonint.h"
32 #include <X11/extensions/XKB.h>
35 _XkbFreeGeomLeafElems(Bool freeAll, int first, int count,
36 unsigned short *num_inout, unsigned short *sz_inout,
37 char **elems, unsigned int elem_sz)
39 if (freeAll || !(*elems)) {
40 *num_inout = *sz_inout = 0;
46 if ((first >= (*num_inout)) || (first < 0) || (count < 1))
49 if (first + count >= (*num_inout))
50 /* truncating the array is easy */
54 int extra = ((*num_inout) - first + count) * elem_sz;
57 memmove(&ptr[first * elem_sz], &ptr[(first + count) * elem_sz],
60 (*num_inout) -= count;
64 typedef void (*ContentsClearFunc)(char *priv);
67 _XkbFreeGeomNonLeafElems(Bool freeAll, int first, int count,
68 unsigned short *num_inout, unsigned short *sz_inout,
69 char **elems, unsigned int elem_sz,
70 ContentsClearFunc freeFunc)
79 else if ((first >= (*num_inout)) || (first < 0) || (count < 1))
81 else if (first + count > (*num_inout))
82 count = (*num_inout) - first;
89 ptr += first * elem_sz;
90 for (i = 0; i < count; i++) {
97 *num_inout = *sz_inout = 0;
101 else if (first + count >= (*num_inout))
104 i = ((*num_inout) - first + count) * elem_sz;
106 memmove(&ptr[first * elem_sz], &ptr[(first + count) * elem_sz], i);
107 (*num_inout) -= count;
112 _XkbClearProperty(char *prop_in)
114 struct xkb_property * prop = (struct xkb_property *)prop_in;
123 XkbcFreeGeomProperties(struct xkb_geometry * geom, int first, int count, Bool freeAll)
125 _XkbFreeGeomNonLeafElems(freeAll, first, count,
126 &geom->num_properties, &geom->sz_properties,
127 (char **)&geom->properties,
128 sizeof(struct xkb_property),
133 XkbcFreeGeomKeyAliases(struct xkb_geometry * geom, int first, int count, Bool freeAll)
135 _XkbFreeGeomLeafElems(freeAll, first, count,
136 &geom->num_key_aliases, &geom->sz_key_aliases,
137 (char **)&geom->key_aliases,
138 sizeof(struct xkb_key_alias));
142 _XkbClearColor(char *color_in)
144 struct xkb_color * color = (struct xkb_color *)color_in;
150 XkbcFreeGeomColors(struct xkb_geometry * geom, int first, int count, Bool freeAll)
152 _XkbFreeGeomNonLeafElems(freeAll, first, count,
153 &geom->num_colors, &geom->sz_colors,
154 (char **)&geom->colors, sizeof(struct xkb_color),
159 XkbcFreeGeomPoints(struct xkb_outline * outline, int first, int count, Bool freeAll)
161 _XkbFreeGeomLeafElems(freeAll, first, count,
162 &outline->num_points, &outline->sz_points,
163 (char **)&outline->points, sizeof(struct xkb_point));
167 _XkbClearOutline(char *outline_in)
169 struct xkb_outline * outline = (struct xkb_outline *)outline_in;
172 XkbcFreeGeomPoints(outline, 0, outline->num_points, True);
176 XkbcFreeGeomOutlines(struct xkb_shape * shape, int first, int count, Bool freeAll)
178 _XkbFreeGeomNonLeafElems(freeAll, first, count,
179 &shape->num_outlines, &shape->sz_outlines,
180 (char **)&shape->outlines, sizeof(struct xkb_outline),
185 _XkbClearShape(char *shape_in)
187 struct xkb_shape * shape = (struct xkb_shape *)shape_in;
190 XkbcFreeGeomOutlines(shape, 0, shape->num_outlines, True);
194 XkbcFreeGeomShapes(struct xkb_geometry * geom, int first, int count, Bool freeAll)
196 _XkbFreeGeomNonLeafElems(freeAll, first, count,
197 &geom->num_shapes, &geom->sz_shapes,
198 (char **)&geom->shapes, sizeof(struct xkb_shape),
203 XkbcFreeGeomKeys(struct xkb_row * row, int first, int count, Bool freeAll)
205 _XkbFreeGeomLeafElems(freeAll, first, count,
206 &row->num_keys, &row->sz_keys,
207 (char **)&row->keys, sizeof(struct xkb_key));
211 _XkbClearRow(char *row_in)
213 struct xkb_row * row = (struct xkb_row *)row_in;
216 XkbcFreeGeomKeys(row, 0, row->num_keys, True);
220 XkbcFreeGeomRows(struct xkb_section * section, int first, int count, Bool freeAll)
222 _XkbFreeGeomNonLeafElems(freeAll, first, count,
223 §ion->num_rows, §ion->sz_rows,
224 (char **)§ion->rows, sizeof(struct xkb_row),
231 _XkbClearDoodad(char *doodad_in)
233 union xkb_doodad * doodad = (union xkb_doodad *)doodad_in;
235 switch (doodad->any.type) {
237 free(doodad->text.text);
238 doodad->text.text = NULL;
239 free(doodad->text.font);
240 doodad->text.font = NULL;
244 free(doodad->logo.logo_name);
245 doodad->logo.logo_name = NULL;
251 XkbcFreeGeomDoodads(union xkb_doodad * doodads, int nDoodads, Bool freeAll)
254 union xkb_doodad * doodad;
256 for (i = 0, doodad = doodads; i < nDoodads && doodad; i++, doodad++)
257 _XkbClearDoodad((char *)doodad);
263 _XkbClearSection(char *section_in)
265 struct xkb_section * section = (struct xkb_section *)section_in;
268 XkbcFreeGeomRows(section, 0, section->num_rows, True);
269 XkbcFreeGeomDoodads(section->doodads, section->num_doodads, True);
270 section->doodads = NULL;
274 XkbcFreeGeomSections(struct xkb_geometry * geom, int first, int count, Bool freeAll)
276 _XkbFreeGeomNonLeafElems(freeAll, first, count,
277 &geom->num_sections, &geom->sz_sections,
278 (char **)&geom->sections, sizeof(struct xkb_section),
283 XkbcFreeGeometry(struct xkb_geometry * geom, unsigned which, Bool freeMap)
289 which = XkbGeomAllMask;
291 if ((which & XkbGeomPropertiesMask) && geom->properties)
292 XkbcFreeGeomProperties(geom, 0, geom->num_properties, True);
294 if ((which & XkbGeomColorsMask) && geom->colors)
295 XkbcFreeGeomColors(geom, 0, geom->num_colors, True);
297 if ((which & XkbGeomShapesMask) && geom->shapes)
298 XkbcFreeGeomShapes(geom, 0, geom->num_shapes, True);
300 if ((which & XkbGeomSectionsMask) && geom->sections)
301 XkbcFreeGeomSections(geom, 0, geom->num_sections, True);
303 if ((which & XkbGeomDoodadsMask) && geom->doodads) {
304 XkbcFreeGeomDoodads(geom->doodads, geom->num_doodads, True);
305 geom->doodads = NULL;
306 geom->num_doodads = geom->sz_doodads = 0;
309 if ((which & XkbGeomKeyAliasesMask) && geom->key_aliases)
310 XkbcFreeGeomKeyAliases(geom, 0, geom->num_key_aliases, True);
313 free(geom->label_font);
314 geom->label_font = NULL;
320 _XkbGeomAlloc(char **old, unsigned short *num, unsigned short *total,
321 int num_new, size_t sz_elem)
329 if ((*num) + num_new <= (*total))
332 *total = (*num) + num_new;
335 *old = (char *)realloc(*old, (*total) * sz_elem);
337 *old = (char *)calloc(*total, sz_elem);
345 bzero(&tmp[sz_elem * (*num)], num_new * sz_elem);
351 #define _XkbAllocProps(g, n) _XkbGeomAlloc((char **)&(g)->properties, \
352 &(g)->num_properties, \
353 &(g)->sz_properties, \
354 (n), sizeof(struct xkb_property))
355 #define _XkbAllocColors(g, n) _XkbGeomAlloc((char **)&(g)->colors, \
358 (n), sizeof(struct xkb_color))
359 #define _XkbAllocShapes(g, n) _XkbGeomAlloc((char **)&(g)->shapes, \
362 (n), sizeof(struct xkb_shape))
363 #define _XkbAllocSections(g, n) _XkbGeomAlloc((char **)&(g)->sections, \
364 &(g)->num_sections, \
366 (n), sizeof(struct xkb_section))
367 #define _XkbAllocDoodads(g, n) _XkbGeomAlloc((char **)&(g)->doodads, \
370 (n), sizeof(union xkb_doodad))
371 #define _XkbAllocKeyAliases(g, n) _XkbGeomAlloc((char **)&(g)->key_aliases, \
372 &(g)->num_key_aliases, \
373 &(g)->sz_key_aliases, \
374 (n), sizeof(struct xkb_key_alias))
376 #define _XkbAllocOutlines(s, n) _XkbGeomAlloc((char **)&(s)->outlines, \
377 &(s)->num_outlines, \
379 (n), sizeof(struct xkb_outline))
380 #define _XkbAllocRows(s, n) _XkbGeomAlloc((char **)&(s)->rows, \
383 (n), sizeof(struct xkb_row))
384 #define _XkbAllocPoints(o, n) _XkbGeomAlloc((char **)&(o)->points, \
387 (n), sizeof(struct xkb_point))
388 #define _XkbAllocKeys(r, n) _XkbGeomAlloc((char **)&(r)->keys, \
391 (n), sizeof(struct xkb_key))
392 #define _XkbAllocOverlays(s, n) _XkbGeomAlloc((char **)&(s)->overlays, \
393 &(s)->num_overlays, \
395 (n), sizeof(struct xkb_overlay))
396 #define _XkbAllocOverlayRows(o, n) _XkbGeomAlloc((char **)&(o)->rows, \
399 (n), sizeof(struct xkb_overlay_row))
400 #define _XkbAllocOverlayKeys(r, n) _XkbGeomAlloc((char **)&(r)->keys, \
403 (n), sizeof(struct xkb_overlay_key))
406 XkbcAllocGeomKeyAliases(struct xkb_geometry * geom, int nKeyAliases)
408 return _XkbAllocKeyAliases(geom, nKeyAliases);
412 XkbcAllocGeometry(struct xkb_desc * xkb, struct xkb_geometry_sizes * sizes)
414 struct xkb_geometry * geom;
418 xkb->geom = _XkbTypedCalloc(1, struct xkb_geometry);
424 if ((sizes->which & XkbGeomPropertiesMask) &&
425 ((rtrn = _XkbAllocProps(geom, sizes->num_properties)) != Success))
428 if ((sizes->which & XkbGeomColorsMask) &&
429 ((rtrn = _XkbAllocColors(geom, sizes->num_colors)) != Success))
432 if ((sizes->which & XkbGeomShapesMask) &&
433 ((rtrn = _XkbAllocShapes(geom, sizes->num_shapes)) != Success))
436 if ((sizes->which & XkbGeomSectionsMask) &&
437 ((rtrn = _XkbAllocSections(geom, sizes->num_sections)) != Success))
440 if ((sizes->which & XkbGeomDoodadsMask) &&
441 ((rtrn = _XkbAllocDoodads(geom, sizes->num_doodads)) != Success))
444 if ((sizes->which & XkbGeomKeyAliasesMask) &&
445 ((rtrn = _XkbAllocKeyAliases(geom, sizes->num_key_aliases)) != Success))
450 XkbcFreeGeometry(geom, XkbGeomAllMask, True);
455 struct xkb_property *
456 XkbcAddGeomProperty(struct xkb_geometry * geom,const char *name,const char *value)
459 struct xkb_property * prop;
461 if ((!geom)||(!name)||(!value))
463 for (i=0,prop=geom->properties;i<geom->num_properties;i++,prop++) {
464 if ((prop->name)&&(strcmp(name,prop->name)==0)) {
466 prop->value = strdup(value);
470 if ((geom->num_properties>=geom->sz_properties)&&
471 (_XkbAllocProps(geom,1)!=Success)) {
474 prop= &geom->properties[geom->num_properties];
475 prop->name = strdup(name);
478 prop->value = strdup(value);
484 geom->num_properties++;
489 XkbcAddGeomColor(struct xkb_geometry * geom,const char *spec,unsigned int pixel)
492 struct xkb_color * color;
494 if ((!geom)||(!spec))
496 for (i=0,color=geom->colors;i<geom->num_colors;i++,color++) {
497 if ((color->spec)&&(strcmp(color->spec,spec)==0)) {
502 if ((geom->num_colors>=geom->sz_colors)&&
503 (_XkbAllocColors(geom,1)!=Success)) {
506 color= &geom->colors[geom->num_colors];
508 color->spec = strdup(spec);
516 XkbcAddGeomOutline(struct xkb_shape * shape,int sz_points)
518 struct xkb_outline * outline;
520 if ((!shape)||(sz_points<0))
522 if ((shape->num_outlines>=shape->sz_outlines)&&
523 (_XkbAllocOutlines(shape,1)!=Success)) {
526 outline= &shape->outlines[shape->num_outlines];
527 bzero(outline,sizeof(struct xkb_outline));
528 if ((sz_points>0)&&(_XkbAllocPoints(outline,sz_points)!=Success))
530 shape->num_outlines++;
535 XkbcAddGeomShape(struct xkb_geometry * geom,uint32_t name,int sz_outlines)
537 struct xkb_shape *shape;
540 if ((!geom)||(!name)||(sz_outlines<0))
542 if (geom->num_shapes>0) {
543 for (shape=geom->shapes,i=0;i<geom->num_shapes;i++,shape++) {
544 if (name==shape->name)
548 if ((geom->num_shapes>=geom->sz_shapes)&&
549 (_XkbAllocShapes(geom,1)!=Success))
551 shape= &geom->shapes[geom->num_shapes];
552 bzero(shape,sizeof(struct xkb_shape));
553 if ((sz_outlines>0)&&(_XkbAllocOutlines(shape,sz_outlines)!=Success))
556 shape->primary= shape->approx= NULL;
562 XkbcAddGeomKey(struct xkb_row * row)
564 struct xkb_key * key;
567 if ((row->num_keys>=row->sz_keys)&&(_XkbAllocKeys(row,1)!=Success))
569 key= &row->keys[row->num_keys++];
570 bzero(key,sizeof(struct xkb_key));
575 XkbcAddGeomRow(struct xkb_section * section,int sz_keys)
577 struct xkb_row * row;
579 if ((!section)||(sz_keys<0))
581 if ((section->num_rows>=section->sz_rows)&&
582 (_XkbAllocRows(section,1)!=Success))
584 row= §ion->rows[section->num_rows];
585 bzero(row,sizeof(struct xkb_row));
586 if ((sz_keys>0)&&(_XkbAllocKeys(row,sz_keys)!=Success))
593 XkbcAddGeomSection( struct xkb_geometry * geom,
600 struct xkb_section * section;
602 if ((!geom)||(name==None)||(sz_rows<0))
604 for (i=0,section=geom->sections;i<geom->num_sections;i++,section++) {
605 if (section->name!=name)
607 if (((sz_rows>0)&&(_XkbAllocRows(section,sz_rows)!=Success))||
608 ((sz_doodads>0)&&(_XkbAllocDoodads(section,sz_doodads)!=Success))||
609 ((sz_over>0)&&(_XkbAllocOverlays(section,sz_over)!=Success)))
613 if ((geom->num_sections>=geom->sz_sections)&&
614 (_XkbAllocSections(geom,1)!=Success))
616 section= &geom->sections[geom->num_sections];
617 if ((sz_rows>0)&&(_XkbAllocRows(section,sz_rows)!=Success))
619 if ((sz_doodads>0)&&(_XkbAllocDoodads(section,sz_doodads)!=Success)) {
622 section->sz_rows= section->num_rows= 0;
626 geom->num_sections++;
631 XkbcAddGeomDoodad(struct xkb_geometry * geom,struct xkb_section * section,uint32_t name)
633 union xkb_doodad *old, *doodad;
636 if ((!geom)||(name==None))
638 if ((section!=NULL)&&(section->num_doodads>0)) {
639 old= section->doodads;
640 nDoodads= section->num_doodads;
644 nDoodads= geom->num_doodads;
646 for (i=0,doodad=old;i<nDoodads;i++,doodad++) {
647 if (doodad->any.name==name)
651 if ((section->num_doodads>=geom->sz_doodads)&&
652 (_XkbAllocDoodads(section,1)!=Success)) {
655 doodad= §ion->doodads[section->num_doodads++];
658 if ((geom->num_doodads>=geom->sz_doodads)&&
659 (_XkbAllocDoodads(geom,1)!=Success))
661 doodad= &geom->doodads[geom->num_doodads++];
663 bzero(doodad,sizeof(union xkb_doodad));
664 doodad->any.name= name;
668 struct xkb_overlay_row *
669 XkbcAddGeomOverlayRow(struct xkb_overlay * overlay,int row_under,int sz_keys)
672 struct xkb_overlay_row *row;
674 if ((!overlay)||(sz_keys<0))
676 if (row_under>=overlay->section_under->num_rows)
678 for (i=0;i<overlay->num_rows;i++) {
679 if (overlay->rows[i].row_under==row_under) {
680 row= &overlay->rows[i];
681 if ((row->sz_keys<sz_keys)&&
682 (_XkbAllocOverlayKeys(row,sz_keys)!=Success)) {
685 return &overlay->rows[i];
688 if ((overlay->num_rows>=overlay->sz_rows)&&
689 (_XkbAllocOverlayRows(overlay,1)!=Success))
691 row= &overlay->rows[overlay->num_rows];
692 bzero(row,sizeof(struct xkb_overlay_row));
693 if ((sz_keys>0)&&(_XkbAllocOverlayKeys(row,sz_keys)!=Success))
695 row->row_under= row_under;
701 XkbcAddGeomOverlay(struct xkb_section * section,uint32_t name,int sz_rows)
704 struct xkb_overlay *overlay;
706 if ((!section)||(name==None)||(sz_rows==0))
709 for (i=0,overlay=section->overlays;i<section->num_overlays;i++,overlay++) {
710 if (overlay->name==name) {
711 if ((sz_rows>0)&&(_XkbAllocOverlayRows(overlay,sz_rows)!=Success))
716 if ((section->num_overlays>=section->sz_overlays)&&
717 (_XkbAllocOverlays(section,1)!=Success))
719 overlay= §ion->overlays[section->num_overlays];
720 if ((sz_rows>0)&&(_XkbAllocOverlayRows(overlay,sz_rows)!=Success))
723 overlay->section_under= section;
724 section->num_overlays++;