Statistics
| Branch: | Revision:

root / src / eventlog / sequencechartfacade.cc @ 636cbdd5

History | View | Annotate | Download (25.6 KB)

1
//=========================================================================
2
//  SEQUENCECHARTFACADE.CC - part of
3
//                  OMNeT++/OMNEST
4
//           Discrete System Simulation in C++
5
//
6
//  Author: Levente Meszaros
7
//
8
//=========================================================================
9

    
10
/*--------------------------------------------------------------*
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 <algorithm>
19
#include <set>
20
#include <math.h>
21
#include "lcgrandom.h"
22
#include "ievent.h"
23
#include "ieventlog.h"
24
#include "event.h"
25
#include "messagedependency.h"
26
#include "sequencechartfacade.h"
27

    
28
USING_NAMESPACE
29

    
30
SequenceChartFacade::SequenceChartFacade(IEventLog *eventLog) : EventLogFacade(eventLog)
31
{
32
    timelineMode = NONLINEAR;
33
    timelineCoordinateSystemVersion = -1;
34
    undefineTimelineCoordinateSystem();
35

    
36
    nonLinearMinimumTimelineCoordinateDelta = 0.1;
37
    setNonLinearFocus(calculateNonLinearFocus());
38

    
39
    smallestComplexity = -1;
40
    largestComplexity = -1;
41
}
42

    
43
void SequenceChartFacade::synchronize(FileReader::FileChangedState change)
44
{
45
    if (change != FileReader::UNCHANGED) {
46
        EventLogFacade::synchronize(change);
47

    
48
        setNonLinearFocus(calculateNonLinearFocus());
49

    
50
        if (timelineCoordinateOriginEventNumber != -1) {
51
            IEvent *event = eventLog->getEventForEventNumber(timelineCoordinateOriginEventNumber);
52

    
53
            if (event)
54
                relocateTimelineCoordinateSystem(event);
55
            else
56
                undefineTimelineCoordinateSystem();
57
        }
58
    }
59
}
60

    
61
double SequenceChartFacade::calculateNonLinearFocus()
62
{
63
    if (!eventLog->isEmpty()) {
64
        double lastEventSimulationTime = eventLog->getLastEvent()->getSimulationTime().dbl();
65
        double firstEventSimulationTime = eventLog->getFirstEvent()->getSimulationTime().dbl();
66
        double totalSimulationTimeDelta = lastEventSimulationTime - firstEventSimulationTime;
67

    
68
        if (totalSimulationTimeDelta == 0)
69
            totalSimulationTimeDelta = firstEventSimulationTime;
70

    
71
        if (totalSimulationTimeDelta == 0)
72
            return 1;
73
        else
74
            return totalSimulationTimeDelta / eventLog->getApproximateNumberOfEvents() / 10;
75
    }
76
    else
77
        return 1;
78
}
79

    
80
void SequenceChartFacade::setNonLinearMinimumTimelineCoordinateDelta(double value)
81
{
82
    Assert(value >= 0);
83
    nonLinearMinimumTimelineCoordinateDelta = value;
84
}
85

    
86
void SequenceChartFacade::setNonLinearFocus(double nonLinearFocus)
87
{
88
    Assert(nonLinearFocus >= 0);
89
    this->nonLinearFocus = nonLinearFocus;
90
}
91

    
92
void SequenceChartFacade::undefineTimelineCoordinateSystem()
93
{
94
    timelineCoordinateSystemVersion++;
95
    timelineCoordinateOriginEventNumber = timelineCoordinateRangeStartEventNumber = timelineCoordinateRangeEndEventNumber = -1;
96
    timelineCoordinateOriginSimulationTime = simtime_nil;
97
}
98

    
99
void SequenceChartFacade::relocateTimelineCoordinateSystem(IEvent *event)
100
{
101
    Assert(event);
102

    
103
    timelineCoordinateSystemVersion++;
104
    timelineCoordinateOriginEventNumber = timelineCoordinateRangeStartEventNumber = timelineCoordinateRangeEndEventNumber = event->getEventNumber();
105
    timelineCoordinateOriginSimulationTime = event->getSimulationTime();
106
    event->cachedTimelineCoordinate = 0;
107
    event->cachedTimelineCoordinateSystemVersion = timelineCoordinateSystemVersion;
108
}
109

    
110
void SequenceChartFacade::setTimelineMode(TimelineMode timelineMode)
111
{
112
    this->timelineMode = timelineMode;
113

    
114
    if (timelineCoordinateOriginEventNumber != -1)
115
        relocateTimelineCoordinateSystem(eventLog->getEventForEventNumber(timelineCoordinateOriginEventNumber));
116
}
117

    
118
double SequenceChartFacade::IEvent_getTimelineCoordinate(ptr_t ptr)
119
{
120
    IEVENT_PTR(ptr);
121
    return getTimelineCoordinate((IEvent*)ptr);
122
}
123

    
124
double SequenceChartFacade::getTimelineCoordinateDelta(double simulationTimeDelta)
125
{
126
    Assert(nonLinearFocus > 0);
127

    
128
    if (timelineMode == STEP)
129
        return 1;
130
    else
131
        return nonLinearMinimumTimelineCoordinateDelta + (1 - nonLinearMinimumTimelineCoordinateDelta) * atan(fabs(simulationTimeDelta) / nonLinearFocus) / PI * 2;
132
}
133

    
134
double SequenceChartFacade::getTimelineCoordinate(ptr_t ptr, double lowerTimelineCoordinateCalculationLimit, double upperTimelineCoordinateCalculationLimit)
135
{
136
    IEVENT_PTR(ptr);
137
    return getTimelineCoordinate((IEvent *)ptr, lowerTimelineCoordinateCalculationLimit, upperTimelineCoordinateCalculationLimit);
138
}
139

    
140
double SequenceChartFacade::getTimelineCoordinate(IEvent *event, double lowerTimelineCoordinateCalculationLimit, double upperTimelineCoordinateCalculationLimit)
141
{
142
    Assert(event);
143
    Assert(event->getEventLog() == eventLog);
144
    Assert(timelineCoordinateSystemVersion != -1);
145
    Assert(timelineCoordinateOriginEventNumber != -1);
146

    
147
    if (this->timelineCoordinateSystemVersion > event->cachedTimelineCoordinateSystemVersion) {
148
        double timelineCoordinate;
149

    
150
        switch (timelineMode) {
151
            case SIMULATION_TIME:
152
                timelineCoordinate = (event->getSimulationTime() - timelineCoordinateOriginSimulationTime).dbl();
153
                break;
154
            case EVENT_NUMBER:
155
                timelineCoordinate = event->getEventNumber() - timelineCoordinateOriginEventNumber;
156
                break;
157
            case STEP:
158
            case NONLINEAR:
159
                {
160
                    IEvent *previousEvent = NULL;
161
                    // do we go forward from end or backward from start of known range
162
                    bool forward = event->getEventNumber() > timelineCoordinateRangeEndEventNumber;
163
                    IEvent *currentEvent = eventLog->getEventForEventNumber(forward ? timelineCoordinateRangeEndEventNumber : timelineCoordinateRangeStartEventNumber);
164

    
165
                    Assert(event->getEventNumber() < timelineCoordinateRangeStartEventNumber || timelineCoordinateRangeEndEventNumber < event->getEventNumber());
166

    
167
                    // TODO: LONG RUNNING OPERATION
168
                    // does a linear search towards the event to calculate the non linear timeline coordinate
169
                    do {
170
                        eventLog->progress();
171

    
172
                        Assert(currentEvent);
173
                        previousEvent = currentEvent;
174
                        currentEvent = forward ? currentEvent->getNextEvent() : currentEvent->getPreviousEvent();
175
                        Assert(currentEvent);
176

    
177
                        simtime_t previousSimulationTime = previousEvent->getSimulationTime();
178
                        double previousTimelineCoordinate = previousEvent->cachedTimelineCoordinate;
179
                        simtime_t simulationTime = currentEvent->getSimulationTime();
180
                        double timelineCoordinateDelta = getTimelineCoordinateDelta((simulationTime - previousSimulationTime).dbl());
181

    
182
                        if (forward) {
183
                            timelineCoordinate = previousTimelineCoordinate + timelineCoordinateDelta;
184

    
185
                            if (timelineCoordinate > upperTimelineCoordinateCalculationLimit)
186
                                return NaN;
187
                        }
188
                        else {
189
                            timelineCoordinate = previousTimelineCoordinate - timelineCoordinateDelta;
190

    
191
                            if (timelineCoordinate < lowerTimelineCoordinateCalculationLimit)
192
                                return NaN;
193
                        }
194

    
195
                        currentEvent->cachedTimelineCoordinate = timelineCoordinate;
196
                        currentEvent->cachedTimelineCoordinateSystemVersion = timelineCoordinateSystemVersion;
197
                    }
198
                    while (currentEvent != event);
199

    
200
                    if (forward)
201
                        timelineCoordinateRangeEndEventNumber = event->getEventNumber();
202
                    else
203
                        timelineCoordinateRangeStartEventNumber = event->getEventNumber();
204
                }
205
                break;
206
            default:
207
                throw opp_runtime_error("Unknown timeline mode");
208
        }
209

    
210
        event->cachedTimelineCoordinate = timelineCoordinate;
211
        event->cachedTimelineCoordinateSystemVersion = timelineCoordinateSystemVersion;
212
    }
213

    
214
    return event->cachedTimelineCoordinate;
215
}
216

    
217
double SequenceChartFacade::getCachedTimelineCoordinate(IEvent *event)
218
{
219
    Assert(event);
220
    Assert(timelineCoordinateSystemVersion != -1);
221
    Assert(timelineCoordinateOriginEventNumber != -1);
222

    
223
    if (this->timelineCoordinateSystemVersion > event->cachedTimelineCoordinateSystemVersion)
224
        return -1;
225
    else
226
        return event->cachedTimelineCoordinate;
227
}
228

    
229
IEvent *SequenceChartFacade::getEventForNonLinearTimelineCoordinate(double timelineCoordinate, bool &forward)
230
{
231
    Assert(timelineCoordinateOriginEventNumber != -1);
232
    IEvent *timelineCoordinateRangeStartEvent = eventLog->getEventForEventNumber(timelineCoordinateRangeStartEventNumber);
233
    IEvent *timelineCoordinateRangeEndEvent = eventLog->getEventForEventNumber(timelineCoordinateRangeEndEventNumber);
234
    IEvent *currentEvent;
235

    
236
    Assert(timelineCoordinateRangeStartEvent && timelineCoordinateRangeEndEvent);
237

    
238
    if (timelineCoordinate <= getTimelineCoordinate(timelineCoordinateRangeStartEvent)) {
239
        forward = false;
240
        currentEvent = timelineCoordinateRangeStartEvent;
241
    }
242
    else if (getTimelineCoordinate(timelineCoordinateRangeEndEvent) <= timelineCoordinate) {
243
        forward = true;
244
        currentEvent = timelineCoordinateRangeEndEvent;
245
    }
246
    else {
247
        forward = true;
248
        currentEvent = timelineCoordinateRangeStartEvent;
249
    }
250

    
251
    // TODO: LONG RUNNING OPERATION
252
    // does a linear search towards requested non linear timeline coordinate
253
    while (currentEvent && (forward ? getTimelineCoordinate(currentEvent) < timelineCoordinate :
254
                                      timelineCoordinate <= getTimelineCoordinate(currentEvent)))
255
    {
256
        eventLog->progress();
257
        currentEvent = forward ? currentEvent->getNextEvent() : currentEvent->getPreviousEvent();
258
    }
259

    
260
    return currentEvent;
261
}
262

    
263
IEvent *SequenceChartFacade::getLastEventNotAfterTimelineCoordinate(double timelineCoordinate)
264
{
265
    if (eventLog->isEmpty())
266
        return NULL;
267

    
268
    switch (timelineMode) {
269
        case SIMULATION_TIME:
270
            return eventLog->getLastEventNotAfterSimulationTime(getSimulationTimeForTimelineCoordinate(timelineCoordinate));
271
        case EVENT_NUMBER:
272
            {
273
                eventnumber_t eventNumber = (eventnumber_t)floor(timelineCoordinate) + timelineCoordinateOriginEventNumber;
274

    
275
                if (eventNumber < 0)
276
                    return NULL;
277
                else
278
                    return eventLog->getLastEventNotAfterEventNumber(eventNumber);
279
            }
280
        case STEP:
281
        case NONLINEAR:
282
            {
283
                bool forward;
284
                IEvent *currentEvent = getEventForNonLinearTimelineCoordinate(timelineCoordinate, forward);
285
                currentEvent = forward ? (currentEvent ? currentEvent->getPreviousEvent() : eventLog->getLastEvent()) : currentEvent;
286

    
287
                Assert(!currentEvent || getTimelineCoordinate(currentEvent) <= timelineCoordinate);
288
                return currentEvent;
289
            }
290
        default:
291
            throw opp_runtime_error("Unknown timeline mode");
292
    }
293
}
294

    
295
IEvent *SequenceChartFacade::getFirstEventNotBeforeTimelineCoordinate(double timelineCoordinate)
296
{
297
    if (eventLog->isEmpty())
298
        return NULL;
299

    
300
    switch (timelineMode) {
301
        case SIMULATION_TIME:
302
            return eventLog->getFirstEventNotBeforeSimulationTime(getSimulationTimeForTimelineCoordinate(timelineCoordinate));
303
        case EVENT_NUMBER:
304
            {
305
                eventnumber_t eventNumber = (eventnumber_t)floor(timelineCoordinate) + timelineCoordinateOriginEventNumber;
306

    
307
                if (eventNumber < 0)
308
                    return eventLog->getFirstEvent();
309
                else
310
                    return eventLog->getFirstEventNotBeforeEventNumber(eventNumber);
311
            }
312
        case STEP:
313
        case NONLINEAR:
314
            {
315
                bool forward;
316
                IEvent *currentEvent = getEventForNonLinearTimelineCoordinate(timelineCoordinate, forward);
317
                currentEvent = forward ? currentEvent : (currentEvent ? currentEvent->getNextEvent() : eventLog->getFirstEvent());
318

    
319
                Assert(!currentEvent || getTimelineCoordinate(currentEvent) >= timelineCoordinate);
320
                return currentEvent;
321
            }
322
        default:
323
            throw opp_runtime_error("Unknown timeline mode");
324
    }
325
}
326

    
327
void SequenceChartFacade::extractSimulationTimesAndTimelineCoordinates(
328
    IEvent *event, IEvent *&nextEvent,
329
    simtime_t &eventSimulationTime, double &eventTimelineCoordinate,
330
    simtime_t &nextEventSimulationTime, double &nextEventTimelineCoordinate,
331
    simtime_t &simulationTimeDelta, double &timelineCoordinateDelta)
332
{
333
    // if before the first event
334
    if (event) {
335
        eventSimulationTime = event->getSimulationTime();
336
        eventTimelineCoordinate = getTimelineCoordinate(event);
337
    }
338
    else {
339
        eventSimulationTime = BigDecimal::Zero;
340
        IEvent *firstEvent = eventLog->getFirstEvent();
341
        eventTimelineCoordinate = getTimelineCoordinate(firstEvent);
342

    
343
        if (timelineMode == EVENT_NUMBER)
344
            eventTimelineCoordinate -= 1;
345
        else
346
            eventTimelineCoordinate -= getTimelineCoordinateDelta(firstEvent->getSimulationTime().dbl());
347
    }
348

    
349
    // linear approximation between two enclosing events
350
    nextEvent = event ? event->getNextEvent() : eventLog->getFirstEvent();
351

    
352
    if (nextEvent) {
353
        nextEventSimulationTime = nextEvent->getSimulationTime();
354
        nextEventTimelineCoordinate = getTimelineCoordinate(nextEvent);
355

    
356
        simulationTimeDelta = nextEventSimulationTime - eventSimulationTime;
357
        timelineCoordinateDelta = nextEventTimelineCoordinate - eventTimelineCoordinate;
358
    }
359
}
360

    
361
simtime_t SequenceChartFacade::getSimulationTimeForTimelineCoordinate(double timelineCoordinate, bool upperLimit)
362
{
363
    Assert(!isNaN(timelineCoordinate));
364

    
365
    if (eventLog->isEmpty())
366
        return BigDecimal::Zero;
367

    
368
    simtime_t simulationTime;
369

    
370
    switch (timelineMode)
371
    {
372
        case SIMULATION_TIME:
373
            {
374
                simtime_t lastEventSimulationTime = eventLog->getLastEvent()->getSimulationTime();
375
                simulationTime = max(BigDecimal::Zero, min(lastEventSimulationTime, timelineCoordinate + timelineCoordinateOriginSimulationTime));
376
            }
377
            break;
378
        case EVENT_NUMBER:
379
        case STEP:
380
        case NONLINEAR:
381
            {
382
                IEvent *nextEvent;
383
                simtime_t eventSimulationTime, nextEventSimulationTime, simulationTimeDelta;
384
                double eventTimelineCoordinate, nextEventTimelineCoordinate, timelineCoordinateDelta;
385

    
386
                IEvent *event = getLastEventNotAfterTimelineCoordinate(timelineCoordinate);
387
                extractSimulationTimesAndTimelineCoordinates(event, nextEvent,
388
                                                             eventSimulationTime, eventTimelineCoordinate,
389
                                                             nextEventSimulationTime, nextEventTimelineCoordinate,
390
                                                             simulationTimeDelta, timelineCoordinateDelta);
391

    
392
                if (nextEvent) {
393
                    if (timelineCoordinateDelta == 0) {
394
                        // IMPORTANT NOTE: this is just an approximation
395
                        if (upperLimit)
396
                            simulationTime = nextEventSimulationTime;
397
                        else
398
                            simulationTime = eventSimulationTime;
399
                    }
400
                    else {
401
                        timelineCoordinate = std::max(eventTimelineCoordinate, std::min(nextEventTimelineCoordinate, timelineCoordinate));
402
                        simulationTime = eventSimulationTime + simulationTimeDelta * (timelineCoordinate - eventTimelineCoordinate) / timelineCoordinateDelta;
403
                        simulationTime = max(eventSimulationTime, min(nextEventSimulationTime, simulationTime));
404
                    }
405
                }
406
                else
407
                    simulationTime = eventSimulationTime;
408
            }
409
            break;
410
        default:
411
            throw opp_runtime_error("Unknown timeline mode");
412
    }
413

    
414
    Assert(!simulationTime.isNaN());
415
    Assert(simulationTime >= BigDecimal::Zero);
416
    Assert(simulationTime <= eventLog->getLastEvent()->getSimulationTime());
417

    
418
    return simulationTime;
419
}
420

    
421
double SequenceChartFacade::getTimelineCoordinateForSimulationTime(simtime_t simulationTime, bool upperLimit)
422
{
423
    Assert(!simulationTime.isNaN());
424

    
425
    if (eventLog->isEmpty())
426
        return 0;
427

    
428
    Assert(simulationTime >= BigDecimal::Zero);
429
    Assert(simulationTime <= eventLog->getLastEvent()->getSimulationTime());
430

    
431
    double timelineCoordinate;
432

    
433
    switch (timelineMode)
434
    {
435
        case SIMULATION_TIME:
436
            timelineCoordinate = (simulationTime - timelineCoordinateOriginSimulationTime).dbl();
437
            break;
438
        case EVENT_NUMBER:
439
        case STEP:
440
        case NONLINEAR:
441
            {
442
                IEvent *nextEvent;
443
                simtime_t eventSimulationTime, nextEventSimulationTime, simulationTimeDelta;
444
                double eventTimelineCoordinate, nextEventTimelineCoordinate, timelineCoordinateDelta;
445

    
446
                IEvent *event = eventLog->getLastEventNotAfterSimulationTime(simulationTime);
447
                extractSimulationTimesAndTimelineCoordinates(event, nextEvent,
448
                                                             eventSimulationTime, eventTimelineCoordinate,
449
                                                             nextEventSimulationTime, nextEventTimelineCoordinate,
450
                                                             simulationTimeDelta, timelineCoordinateDelta);
451

    
452
                if (nextEvent) {
453
                    if (simulationTimeDelta == BigDecimal::Zero) {
454
                        // IMPORTANT NOTE: this is just an approximation
455
                        if (upperLimit)
456
                            timelineCoordinate = nextEventTimelineCoordinate;
457
                        else
458
                            timelineCoordinate = eventTimelineCoordinate;
459
                    }
460
                    else {
461
                        simulationTime = max(eventSimulationTime, min(nextEventSimulationTime, simulationTime));
462
                        timelineCoordinate = eventTimelineCoordinate + timelineCoordinateDelta * (simulationTime - eventSimulationTime).dbl() / simulationTimeDelta.dbl();
463
                        timelineCoordinate = std::max(eventTimelineCoordinate, std::min(nextEventTimelineCoordinate, timelineCoordinate));
464
                    }
465
                }
466
                else
467
                    timelineCoordinate = eventTimelineCoordinate;
468
            }
469
            break;
470
        default:
471
            throw opp_runtime_error("Unknown timeline mode");
472
    }
473

    
474
    Assert(!isNaN(timelineCoordinate));
475

    
476
    return timelineCoordinate;
477
}
478

    
479
double SequenceChartFacade::getTimelineCoordinateForSimulationTimeAndEventInModule(simtime_t simulationTime, int moduleId)
480
{
481
    IEvent *event = eventLog->getLastEventNotAfterSimulationTime(simulationTime);
482

    
483
    while (event && event->getSimulationTime() == simulationTime) {
484
        if (event->getModuleId() == moduleId)
485
            return getTimelineCoordinate(event);
486

    
487
        event = event->getNextEvent();
488
    }
489

    
490
    return getTimelineCoordinateForSimulationTime(simulationTime);
491
}
492

    
493
std::vector<ptr_t> *SequenceChartFacade::getModuleMethodBeginEntries(ptr_t startEventPtr, ptr_t endEventPtr)
494
{
495
    IEvent *startEvent = (IEvent *)startEventPtr;
496
    IEvent *endEvent = (IEvent *)endEventPtr;
497
    Assert(startEvent);
498
    Assert(endEvent);
499
    std::vector<ptr_t> *moduleMethodBeginEntries = new std::vector<ptr_t>();
500

    
501
    for (IEvent *event = startEvent;; event = event->getNextEvent()) {
502
        eventLog->progress();
503

    
504
        for (int i = 0; i < event->getNumEventLogEntries(); i++) {
505
            EventLogEntry *eventLogEntry = event->getEventLogEntry(i);
506

    
507
            if (dynamic_cast<ModuleMethodBeginEntry *>(eventLogEntry))
508
                moduleMethodBeginEntries->push_back((ptr_t)eventLogEntry);
509
        }
510

    
511
        if (event == endEvent)
512
            break;
513
    }
514

    
515
    return moduleMethodBeginEntries;
516
}
517

    
518
std::vector<ptr_t> *SequenceChartFacade::getIntersectingMessageDependencies(ptr_t startEventPtr, ptr_t endEventPtr)
519
{
520
    IEvent *startEvent = (IEvent *)startEventPtr;
521
    IEvent *endEvent = (IEvent *)endEventPtr;
522
    Assert(startEvent);
523
    Assert(endEvent);
524
    std::set<ptr_t> messageDependencies;
525
    eventnumber_t startEventNumber = startEvent->getEventNumber();
526

    
527
    // TODO: LONG RUNNING OPERATION
528
    // this might take a while if start and end events are far away from each other
529
    // if not completed then some dependencies will not be included
530
    for (IEvent *event = startEvent;; event = event->getNextEvent()) {
531
        eventLog->progress();
532
        IMessageDependencyList *causes = event->getCauses();
533

    
534
        for (IMessageDependencyList::iterator it = causes->begin(); it != causes->end(); it++) {
535
            IMessageDependency *messageDependency = *it;
536

    
537
            if (messageDependency->getCauseEventNumber() < startEventNumber)
538
                messageDependencies.insert((ptr_t)messageDependency);
539
        }
540

    
541
        IMessageDependencyList *consequences = event->getConsequences();
542

    
543
        for (IMessageDependencyList::iterator it = consequences->begin(); it != consequences->end(); it++)
544
            messageDependencies.insert((ptr_t)*it);
545

    
546
        if (event == endEvent)
547
            break;
548
    }
549

    
550
    std::vector<ptr_t> *result = new std::vector<ptr_t>;
551
    result->resize(messageDependencies.size());
552
    std::copy(messageDependencies.begin(), messageDependencies.end(), result->begin());
553

    
554
    return result;
555
}
556

    
557
std::vector<int> SequenceChartFacade::getApproximateMessageDependencyCountAdjacencyMatrix(std::map<int, int> *moduleIdToAxisIndexMap, int numberOfSamples, int messageSendWeight, int messageReuseWeight)
558
{
559
    LCGRandom lcgRandom;
560
    std::vector<int> adjacencyMatrix;
561
    std::set<int> axisIndexSet;
562
    std::map<eventnumber_t, IEvent *> eventNumberToEventMap;
563

    
564
    for (std::map<int, int>::iterator it = moduleIdToAxisIndexMap->begin(); it != moduleIdToAxisIndexMap->end(); it++)
565
        axisIndexSet.insert(it->second);
566

    
567
    int numberOfAxes = axisIndexSet.size();
568
    adjacencyMatrix.resize(numberOfAxes * numberOfAxes);
569

    
570
    for (int i = 0; i < numberOfSamples; i++)
571
    {
572
        // draw random
573
        double percentage = lcgRandom.next01();
574
        IEvent *event = eventLog->getApproximateEventAt(percentage);
575
        eventNumberToEventMap[event->getEventNumber()] = event;
576

    
577
        // look before origin
578
        if (timelineCoordinateOriginEventNumber != -1) {
579
            if (timelineCoordinateOriginEventNumber - i >= 0) {
580
                event = eventLog->getEventForEventNumber(timelineCoordinateOriginEventNumber - i);
581
                if (event)
582
                    eventNumberToEventMap[event->getEventNumber()] = event;
583
            }
584

    
585
            // look after origin
586
            event = eventLog->getEventForEventNumber(timelineCoordinateOriginEventNumber + i);
587
            if (event)
588
                eventNumberToEventMap[event->getEventNumber()] = event;
589
        }
590
    }
591

    
592
    for (std::map<eventnumber_t, IEvent *>::iterator it = eventNumberToEventMap.begin(); it != eventNumberToEventMap.end(); it++) {
593
        IEvent *event = it->second;
594
        IMessageDependencyList *causes = event->getCauses();
595

    
596
        for (IMessageDependencyList::iterator it = causes->begin(); it != causes->end(); it++) {
597
            IMessageDependency *messageDependency = *it;
598
            IEvent *causeEvent = messageDependency->getCauseEvent();
599
            IEvent *consequenceEvent = messageDependency->getConsequenceEvent();
600
            int weight = messageDependency->getIsReuse() ? messageReuseWeight : messageSendWeight;
601

    
602
            if (causeEvent && consequenceEvent && weight != 0) {
603
                int causeModuleId = causeEvent->getModuleId();
604
                int consequenceModuleId = consequenceEvent->getModuleId();
605

    
606
                std::map<int, int>::iterator causeModuleIdIt = moduleIdToAxisIndexMap->find(causeModuleId);
607
                std::map<int, int>::iterator consequenceModuleIdIt = moduleIdToAxisIndexMap->find(consequenceModuleId);
608

    
609
                if (causeModuleIdIt !=  moduleIdToAxisIndexMap->end() && consequenceModuleIdIt != moduleIdToAxisIndexMap->end())
610
                    adjacencyMatrix.at(causeModuleIdIt->second * numberOfAxes + consequenceModuleIdIt->second) += weight;
611
            }
612
        }
613
    }
614

    
615
    return adjacencyMatrix;
616
}
617

    
618

    
619
long SequenceChartFacade::getSmallestEventComplexity() {
620
    long complexity = 0;
621
    if (smallestComplexity < 0) {
622
        for (IEvent *event = eventLog->getFirstEvent();event != eventLog->getLastEvent(); event = event->getNextEvent()) {
623
             if (event->getEventEndEntry()) {
624
                 complexity = event->getEventEndEntry()->complexity;
625
             } else {
626
                 continue;
627
             }
628
             if (complexity < smallestComplexity || smallestComplexity < 0) {
629
                 smallestComplexity = complexity;
630
             }
631
             if (complexity > largestComplexity || largestComplexity < 0) {
632
                 largestComplexity = complexity;
633
             }
634
        }
635
    }
636
    if (smallestComplexity < 0) {
637
        smallestComplexity = 0;
638
    }
639
    return smallestComplexity;
640
}
641

    
642
long SequenceChartFacade::getLargestEventComplexity() {
643
    if (largestComplexity < 0) {
644
        getSmallestEventComplexity();
645
    }
646
    if (largestComplexity < 0) {
647
        largestComplexity = 0;
648
    }
649
    return largestComplexity;
650
}