Added AROS port of all shell applications:
[cake.git] / rom / oop / parseattrs.c
blob00e07ff60b791fe3161f1ecbb52a1538652bd6e1
1 /*
2 Copyright © 1995-2007, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc: Parse a set of attributes in a single interface
6 Lang: english
7 */
8 #include <exec/lists.h>
9 #include <proto/exec.h>
10 #include "intern.h"
12 /*****************************************************************************
14 NAME */
15 #include <proto/oop.h>
17 AROS_LH5(LONG, OOP_ParseAttrs,
19 /* SYNOPSIS */
20 AROS_LHA(struct TagItem *, tags, A0),
21 AROS_LHA(IPTR *, storage, A1),
22 AROS_LHA(ULONG , numattrs, D0),
23 AROS_LHA(OOP_AttrCheck *, attrcheck, A2),
24 AROS_LHA(OOP_AttrBase , attrbase, D1),
26 /* LOCATION */
27 struct Library *, OOPBase, 20, OOP)
29 /* FUNCTION
30 Parse a taglist of attributes and put the result in an array.
31 It will only parse the attr from a single interface
32 which is indicated by the 'attrbase' parameter.
34 INPUTS
35 tags - tags to be parsed.
36 storage - array where the tag values will be stored.
37 To get the value for a certain tag just use
38 ao#? attribute offset as an index into the array.
39 The array must be of size 'numattrs', ie. the number
40 of attributes in the interface.
42 numattrs - number of attributes in the interface.
43 attrcheck - will is a flag that where flags will be set according
44 to the attributes' offset. Since this is only 32
45 bytes you can only parse interfaces
46 with <= 32 attributes with this function.
47 If you try with more, you will get a
48 ooperr_ParseAttrs_TooManyAttrs error.
49 The flags will be set like this if an attr is found:
51 attrcheck |= 1L << attribute_offset
53 attrbase - attrbase for the interface whise attrs we should look for.
56 RESULT
57 0 for success, and an error otherwise.
58 Possible values are:
59 ooperr_ParseAttrs_TooManyAttrs.
61 NOTES
63 EXAMPLE
65 BUGS
67 SEE ALSO
69 INTERNALS
71 HISTORY
72 29-10-95 digulla automatically created from
73 intuition_lib.fd and clib/intuition_protos.h
75 *****************************************************************************/
77 AROS_LIBFUNC_INIT
79 LONG err = 0;
80 BOOL done = FALSE;
82 if (numattrs > 32)
83 return ooperr_ParseAttrs_TooManyAttrs;
85 /* Parse the taglist. Since we reimplement NextTagItem() instead
86 of calling it this should be really fast. */
87 while (!done) {
88 register IPTR tag = tags->ti_Tag;
90 /* Instead of having a default: in switch we have an if test
91 here because tag > TAG_SKIP is the most-often case.
93 With the way gcc generates code for switc() when
94 there are low number of case: (no jumptable,
95 just "binarysearch" jumping) this is much faster.
97 if (tag > TAG_SKIP) {
98 /* Get the attribute offset */
99 /* Look for same attrbase */
100 if ((tag & (~METHOD_MASK)) == attrbase) {
101 register IPTR offset;
103 offset = tag & METHOD_MASK;
104 if (offset >= numattrs)
105 continue;
107 // bug("---PARSERATTRS: OFFSET %d\n", offset);
108 storage[offset] = tags->ti_Data;
109 /* Mark it as found */
110 // bug("--- ADDING %p TO ATTRCHECK\n", 1L << offset);
111 *attrcheck |= 1L << offset;
113 } else {
114 switch (tag) {
115 case TAG_DONE:
116 return err;
118 case TAG_IGNORE:
119 break;
121 case TAG_MORE:
122 tags = (struct TagItem *)tags->ti_Data;
123 if (NULL == tags)
124 return err;
125 continue;
127 case TAG_SKIP:
128 tags += tags->ti_Data + 1;
129 break;
130 } /* swithc() */
131 } /* if (tag <= TAG_SKIP) */
133 tags ++;
136 return err;
138 AROS_LIBFUNC_EXIT
139 } /* OOP_ParseAttrs */