dnotifier.c

Go to the documentation of this file.
00001 
00041 /*#*
00042  *#* $Log$
00043  *#* Revision 1.2  2006/07/19 12:56:26  bernie
00044  *#* Convert to new Doxygen style.
00045  *#*
00046  *#* Revision 1.1  2005/11/04 18:26:38  bernie
00047  *#* Import into DevLib.
00048  *#*
00049  *#* Revision 1.5  2005/06/09 13:49:22  batt
00050  *#* Reformat; correct some comments.
00051  *#*
00052  *#* Revision 1.4  2005/06/09 13:23:58  batt
00053  *#* Add some comments.
00054  *#*
00055  *#* Revision 1.3  2005/06/08 17:32:33  batt
00056  *#* Switch to new messaging system.
00057  *#*
00058  *#* Revision 1.2  2005/06/06 11:04:12  batt
00059  *#* Add some comments.
00060  *#*
00061  *#* Revision 1.1  2005/05/26 08:32:53  batt
00062  *#* Add new Develer widget system :)
00063  *#*
00064  *#*/
00065 
00066 #include <cfg/debug.h>
00067 
00068 #include <dt/dtag.h>
00069 #include <dt/dnotifier.h>
00070 #include <mware/list.h>
00071 
00076 static void notifier_update(DNotifier *n, dtag_t tag, dval_t val)
00077 {
00078     dnotify_targets(n, tag, val);
00079 }
00080 
00084 void notifier_init(DNotifier *n)
00085 {
00086     // Init instance
00087     n->update = notifier_update;
00088     LIST_INIT(&n->targets);
00089 }
00090 
00097 void filter_update(DFilter *f, dtag_t tag, dval_t val)
00098 {
00099 
00100     const DFilterMap *map = f->map;
00101 
00102     if (map)
00103     {
00104         while (map->src.tag != TAG_END)
00105         {
00106             if ((map->src.tag == tag) && (map->src.val == val))
00107             {
00108                 tag = map->dst.tag;
00109                 val = map->dst.val;
00110                 break;
00111             }
00112             /* TAG_ANY matches anything */
00113             if (map->src.tag == TAG_ANY)
00114                 break;
00115             map++;
00116         }
00117 
00118         if (map->src.tag != TAG_END)
00119             dnotify(f->target, tag, val);
00120     }
00121     else
00122         dnotify(f->target, tag, val);
00123 }
00124 
00125 
00133 void filter_mask_update(DFilter *f, dtag_t tag, dval_t val)
00134 {
00135 
00136     const DFilterMap *map = f->map;
00137     dfilter_mask_t mask;
00138 
00139     if (map)
00140     {
00141         while (map->src.tag != TAG_END)
00142         {
00143             mask = (dfilter_mask_t) map->src.val;
00144             if ((map->src.tag == tag) && ((mask & (dfilter_mask_t)val) == mask))
00145             {
00146                 tag = map->dst.tag;
00147                 val = map->dst.val;
00148                 break;
00149             }
00150             /* TAG_ANY matches anything */
00151             if (map->src.tag == TAG_ANY)
00152                 break;
00153             map++;
00154         }
00155 
00156 
00157         if (map->src.tag != TAG_END)
00158             dnotify(f->target, tag, val);
00159     }
00160     else
00161         dnotify(f->target, tag, val);
00162 }
00163 
00164 
00165 #define FILTER_MAGIC_ACTIVE 0xAA
00166 
00170 void filter_init(DFilter *f, const DFilterMap *map, bool masked, DNotifier *source, DNotifier *target)
00171 {
00172     // Init instance
00173     if (masked)
00174         f->update = (update_filter_ptr)filter_mask_update;
00175     else
00176         f->update = (update_filter_ptr)filter_update;
00177 
00178     /* set filter map and target */
00179     f->map = map;
00180     f->target = target;
00181 
00182     /* these ensure that the filter is not inserted in more than one list */
00183     ASSERT(f->magic != FILTER_MAGIC_ACTIVE);
00184     DB(f->magic = FILTER_MAGIC_ACTIVE;)
00185 
00186     /* Add the filter to source filter list */
00187     ADDTAIL(&source->targets, &f->link);
00188 }