1 /* --COPYRIGHT--,EPL
2 * Copyright (c) 2008 Texas Instruments and others.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
7 *
8 * Contributors:
9 * Texas Instruments - initial implementation
10 *
11 * --/COPYRIGHT--*/
12
13 /*!
14 * Callback notification on RTSC config parameters.
15 *
16 * Lets user code receive a notification whenever a
17 * config param of a module or instance is read or modified.
18 *
19 * @see ./doc-files/xdc/services/getset/package-summary.html JavaDoc
20 */
21 metaonlymodule GetSet
22 {
23 /*!
24 * ======== onGet ========
25 * Add a getter function to a field.
26 *
27 * Each getter acts like an interrupt that is triggered by a read
28 * a field of an object. The field could be a config param of a module
29 * or an instance, or a field of a struct.
30 *
31 * @a(example) 32 * The following example prints a message on any read of a
33 * config param named `cfg` in module `pkg.Mod`:
34 * @p(code) 35 * GetSet.onGet(Mod, "cfg", function(sel, val) {
36 * // prints "pkg.Mod.cfg returned <value>"
37 * print(this.$name + "." + sel + " returned " + val);
38 * });
39 * @p 40 */
41 function onGet(obj, sel, getter);
42
43 /*!
44 * ======== onSet ========
45 * Add a setter function to a field.
46 *
47 * Each setter acts like an interrupt that is triggered by modifying
48 * a field of an object. The field could be a config param of a module
49 * or an instance, or a field of a struct.
50 *
51 * Setters execute only when the field actually changes value. They do
52 * not execute if the field's current value is written back to it.
53 *
54 * Setters may themselves modify fields, and so trigger other setters.
55 * The original execution flow resumes when all fields stop changing
56 * value. In the case of cycles between setters, typically this means
57 * that at least one setter executes twice and makes no further
58 * changes the second time through.
59 *
60 * If the setter throws a JavaScript Error or Java exception, then
61 * the field's original value is restored. The exception bubbles back
62 * through the call stack, so that if a setter caused a cascade of
63 * changes, all are restored to their original values.
64 *
65 * @a(example) 66 * The following example prints a message on any write to a
67 * config param named `cfg` in module `pkg.Mod`:
68 * @p(code) 69 * GetSet.onSet(Mod, "cfg", function(sel, val) {
70 * // prints "pkg.Mod.cfg set to <value>"
71 * print(this.$name + "." + sel + " set to " + val);
72 * });
73 * @p 74 *
75 * @a(example) 76 * The following example makes it an error to change `Mod.cfg`:
77 * @p(code) 78 * GetSet.onSet(Mod, "cfg", function(sel, val) {
79 * throw new Error("You'll never change me!");
80 * });
81 * @p 82 */
83 function onSet(obj, sel, setter);
84
85 /*!
86 * ======== createGroup ========
87 * Create a group of related setter functions.
88 *
89 * The purpose of a group is to control interactions between setters.
90 * If each setter acts like an interrupt, then a group is like an
91 * interrupt controller that determines when setters are permitted
92 * to run.
93 *
94 * Each group is non-reentrant. Once any setter in the group is
95 * running, it runs to completion before any other setter in the
96 * same group may run. This allows the setters to modify internal
97 * state without interference from other setters that operate on
98 * the same internal state.
99 *
100 * Each group runs to completion. When a setter in the group runs, it
101 * might modify other config params and cause further setters in the
102 * same group to run. All of these complete before control is returned
103 * to the original execution flow. From the point of view of code
104 * outside the group, all the setters ran as an atomic operation.
105 *
106 * Groups may be interrupted. When a setter modifies a config param
107 * that is being monitored by a second group, the second group starts
108 * running immediately. It will run to completion before returning
109 * control to the first group. So the first group sees the second
110 * group as atomic. This allows groups to be tested independently,
111 * and combined without affecting their behavior.
112 *
113 * Cycles aren't permitted in the execution flow between groups. If a
114 * setter gets triggered from a group that has already been interrupted,
115 * it is deferred and run when control eventually returns to its own
116 * group. Cycles between groups can break the appearance of atomic
117 * execution, and so should be avoided when possible.
118 *
119 * @a(returns) 120 * A Java object of class
121 * {@link ./doc-files/xdc/services/getset/Group.html Group}.
122 * Can then use Group.onSet() to add functions to the group.
123 *
124 * @a(example) 125 * The following example code forces the values of the config params
126 * `ModA.a` and `ModB.b` to be equal:
127 * @p(code) 128 * var group = GetSet.createGroup();
129 * group.onSet(ModA, "a", function aToB(){ ModB.b = ModA.a; });
130 * group.onSet(ModB, "b", function bToA(){ ModA.a = ModB.b; });
131 * @p 132 */
133 function createGroup();
134
135 /*!
136 * ======== init ========
137 * Add support for getters and setters to all fields of an object.
138 *
139 * Initializes getter and setter support for every field of
140 * the object. The object can be a module, instance, or structure.
141 *
142 * This is a convenience function. The `onSet` and `onGet` functions
143 * already add support to the one field of interest. The `init`
144 * function is useful mostly to make fields visible to global setters
145 * and getters, for example for debugging.
146 */
147 function init(obj);
148
149 /*!
150 * ======== debug ========
151 * Print execution trace info showing the flow of getters and setters.
152 */
153 config Bool debug = false;
154
155 /*!
156 * ======== maxIterations ========
157 * Limit the number of iterations allowed for a group to converge, to
158 * help debug. The default value of 0 means no limit.
159 */
160 configint maxIterations = 0;
161
162 /*!
163 * ======== maxStackDepth ========
164 * Set the maximum allowed depth of recursively nested setters, as
165 * a debugging aid. The default value of 0 means no limit.
166 */
167 configint maxStackDepth = 0;
168 }