Project

General

Profile

Statistics
| Branch: | Revision:

root / src / tkenv / visitor.cc @ e1750c09

History | View | Annotate | Download (6.18 KB)

1 01873262 Georg Kunz
//==========================================================================
2
//  VISITOR.CC - part of
3
//
4
//                     OMNeT++/OMNEST
5
//            Discrete System Simulation in C++
6
//
7
//==========================================================================
8
9
/*--------------------------------------------------------------*
10
  Copyright (C) 1992-2008 Andras Varga
11
  Copyright (C) 2006-2008 OpenSim Ltd.
12

13
  This file is distributed WITHOUT ANY WARRANTY. See the file
14
  `license' for details on this and other legal matters.
15
*--------------------------------------------------------------*/
16
17
#include <stdio.h>
18
#include <string.h>
19
#include <assert.h>
20
21
#include "cenvir.h"
22
#include "cobject.h"
23
#include "cmodule.h"
24
#include "cmessage.h"
25
#include "cqueue.h"
26
#include "cstatistic.h"
27
#include "coutvector.h"
28
#include "cwatch.h"
29
#include "cfsm.h"
30
#include "cpar.h"
31
#include "cchannel.h"
32
#include "cgate.h"
33
34
#include "patternmatcher.h"
35
#include "visitor.h"
36
#include "tkutil.h"
37
38
USING_NAMESPACE
39
40
41
42
cCollectObjectsVisitor::cCollectObjectsVisitor()
43
{
44
    sizelimit = 0; // no limit by default
45
    size = 16;
46
    arr = new cObject *[size];
47
    count = 0;
48
}
49
50
cCollectObjectsVisitor::~cCollectObjectsVisitor()
51
{
52
    delete [] arr;
53
}
54
55
void cCollectObjectsVisitor::setSizeLimit(int limit)
56
{
57
    sizelimit = limit;
58
}
59
60
void cCollectObjectsVisitor::addPointer(cObject *obj)
61
{
62
    if (sizelimit && count==sizelimit)
63
        throw EndTraversalException();
64
65
    // if array is full, reallocate
66
    if (count==size)
67
    {
68
        cObject **arr2 = new cObject *[2*size];
69
        for (int i=0; i<count; i++) arr2[i] = arr[i];
70
        delete [] arr;
71
        arr = arr2;
72
        size = 2*size;
73
    }
74
75
    // add pointer to array
76
    arr[count++] = obj;
77
}
78
79
void cCollectObjectsVisitor::visit(cObject *obj)
80
{
81
    addPointer(obj);
82
83
    // go to children
84
    obj->forEachChild(this);
85
}
86
87
//-----------------------------------------------------------------------
88
89
cFilteredCollectObjectsVisitor::cFilteredCollectObjectsVisitor()
90
{
91
    category = ~0U;
92
    classnamepattern = NULL;
93
    objfullpathpattern = NULL;
94
}
95
96
cFilteredCollectObjectsVisitor::~cFilteredCollectObjectsVisitor()
97
{
98
    delete classnamepattern;
99
    delete objfullpathpattern;
100
}
101
102
void cFilteredCollectObjectsVisitor::setFilterPars(unsigned int cat,
103
                                                   const char *classnamepatt,
104
                                                   const char *objfullpathpatt)
105
{
106
    // Note: pattern matcher will throw exception on pattern syntax error
107
    category = cat;
108
    if (classnamepatt && classnamepatt[0])
109
        classnamepattern = new MatchExpression(classnamepatt, false, true, true);
110
111
    if (objfullpathpatt && objfullpathpatt[0])
112
        objfullpathpattern = new MatchExpression(objfullpathpatt, false, true, true);
113
}
114
115
void cFilteredCollectObjectsVisitor::visit(cObject *obj)
116
{
117
    bool ok = (category==~0U) ||
118
        ((category&CATEGORY_MODULES) && dynamic_cast<cModule *>(obj)) ||
119
        ((category&CATEGORY_MESSAGES) && dynamic_cast<cMessage *>(obj)) ||
120
        ((category&CATEGORY_QUEUES) && dynamic_cast<cQueue *>(obj)) ||
121
        ((category&CATEGORY_VARIABLES) && (dynamic_cast<cWatchBase *>(obj) ||
122
                                           dynamic_cast<cFSM *>(obj))) ||
123
        ((category&CATEGORY_STATISTICS) &&(dynamic_cast<cOutVector *>(obj) ||
124
                                           dynamic_cast<cWatchBase *>(obj) ||
125
                                           dynamic_cast<cStatistic *>(obj))) ||
126
        ((category&CATEGORY_MODPARAMS) &&(dynamic_cast<cPar *>(obj))) ||
127
        ((category&CATEGORY_CHANSGATES) &&(dynamic_cast<cChannel *>(obj) ||
128
                                           dynamic_cast<cGate *>(obj))) ||
129
        ((category&CATEGORY_OTHERS) && (!dynamic_cast<cModule *>(obj) &&
130
                                        !dynamic_cast<cMessage *>(obj) &&
131
                                        !dynamic_cast<cQueue *>(obj) &&
132
                                        !dynamic_cast<cWatchBase *>(obj) &&
133
                                        !dynamic_cast<cFSM *>(obj) &&
134
                                        !dynamic_cast<cOutVector *>(obj) &&
135
                                        !dynamic_cast<cStatistic *>(obj) &&
136
                                        !dynamic_cast<cPar *>(obj) &&
137
                                        !dynamic_cast<cChannel *>(obj) &&
138
                                        !dynamic_cast<cGate *>(obj)));
139
    if (objfullpathpattern || classnamepattern)
140
    {
141
        MatchableObjectAdapter objAdapter(MatchableObjectAdapter::FULLPATH, obj);
142
        ok = ok && (!objfullpathpattern || objfullpathpattern->matches(&objAdapter));
143
        objAdapter.setDefaultAttribute(MatchableObjectAdapter::CLASSNAME);
144
        ok = ok && (!classnamepattern || classnamepattern->matches(&objAdapter));
145
    }
146
147
    if (ok)
148
    {
149
        addPointer(obj);
150
    }
151
152
    // go to children
153
    obj->forEachChild(this);
154
}
155
156
//----------------------------------------------------------------
157
158
void cCollectChildrenVisitor::visit(cObject *obj)
159
{
160
    if (obj==parent)
161
        obj->forEachChild(this);
162
    else
163
        addPointer(obj);
164
}
165
166
//----------------------------------------------------------------
167
168
void cCountChildrenVisitor::visit(cObject *obj)
169
{
170
    if (obj==parent)
171
        obj->forEachChild(this);
172
    else
173
        count++;
174
}
175
176
//----------------------------------------------------------------
177
// utilities for sorting objects:
178
179
#define OBJPTR(a) (*(cObject **)a)
180
static int qsort_cmp_byname(const void *a, const void *b)
181
{
182
    return opp_strcmp(OBJPTR(a)->getFullName(), OBJPTR(b)->getFullName());
183
}
184
static int qsort_cmp_byfullpath(const void *a, const void *b)
185
{
186
    return opp_strcmp(OBJPTR(a)->getFullPath().c_str(), OBJPTR(b)->getFullPath().c_str());
187
}
188
static int qsort_cmp_by_shorttypename(const void *a, const void *b)
189
{
190
    return opp_strcmp(getObjectShortTypeName(OBJPTR(a)), getObjectShortTypeName(OBJPTR(b)));
191
}
192
#undef OBJPTR
193
194
void sortObjectsByName(cObject **objs, int n)
195
{
196
    qsort(objs, n, sizeof(cObject*), qsort_cmp_byname);
197
}
198
199
void sortObjectsByFullPath(cObject **objs, int n)
200
{
201
    qsort(objs, n, sizeof(cObject*), qsort_cmp_byfullpath);
202
}
203
204
void sortObjectsByShortTypeName(cObject **objs, int n)
205
{
206
    qsort(objs, n, sizeof(cObject*), qsort_cmp_by_shorttypename);
207
}
208