1 /*******************************************************************************
2 * Copyright (c) 2015 EfficiOS Inc., Ericsson
4 * All rights reserved. This program and the accompanying materials
5 * are made available under the terms of the Eclipse Public License v1.0
6 * which accompanies this distribution, and is available at
7 * http://www.eclipse.org/legal/epl-v10.html
8 *******************************************************************************/
10 package org
.eclipse
.tracecompass
.analysis
.os
.linux
.core
.latency
;
12 import static org
.eclipse
.tracecompass
.common
.core
.NonNullUtils
.checkNotNull
;
14 import java
.io
.IOException
;
15 import java
.io
.ObjectInputStream
;
16 import java
.util
.HashMap
;
19 import org
.eclipse
.jdt
.annotation
.Nullable
;
20 import org
.eclipse
.tracecompass
.analysis
.os
.linux
.core
.kernelanalysis
.KernelTidAspect
;
21 import org
.eclipse
.tracecompass
.analysis
.os
.linux
.core
.trace
.IKernelAnalysisEventLayout
;
22 import org
.eclipse
.tracecompass
.analysis
.os
.linux
.core
.trace
.IKernelTrace
;
23 import org
.eclipse
.tracecompass
.analysis
.timing
.core
.segmentstore
.AbstractSegmentStoreAnalysisModule
;
24 import org
.eclipse
.tracecompass
.common
.core
.NonNullUtils
;
25 import org
.eclipse
.tracecompass
.segmentstore
.core
.ISegment
;
26 import org
.eclipse
.tracecompass
.segmentstore
.core
.ISegmentStore
;
27 import org
.eclipse
.tracecompass
.tmf
.core
.event
.ITmfEvent
;
29 import com
.google
.common
.base
.Function
;
30 import com
.google
.common
.collect
.FluentIterable
;
33 * @author Alexandre Montplaisir
36 public class LatencyAnalysis
extends AbstractSegmentStoreAnalysisModule
{
39 * The ID of this analysis
41 public static final String ID
= "org.eclipse.tracecompass.analysis.os.linux.latency"; //$NON-NLS-1$
43 private static final String DATA_FILENAME
= "latency-analysis.dat"; //$NON-NLS-1$
46 public String
getId() {
51 public String
getDataFileName() {
56 public AbstractSegmentStoreAnalysisRequest
createAnalysisRequest(ISegmentStore
<ISegment
> syscalls
) {
57 return new SyscallLatencyAnalysisRequest(syscalls
);
61 protected Object
[] readObject(ObjectInputStream ois
) throws ClassNotFoundException
, IOException
{
62 return checkNotNull((Object
[]) ois
.readObject());
65 private static class SyscallLatencyAnalysisRequest
extends AbstractSegmentStoreAnalysisRequest
{
67 private final Map
<Integer
, SystemCall
.InitialInfo
> fOngoingSystemCalls
= new HashMap
<>();
68 private @Nullable IKernelAnalysisEventLayout fLayout
;
70 public SyscallLatencyAnalysisRequest(ISegmentStore
<ISegment
> syscalls
) {
75 public void handleData(final ITmfEvent event
) {
76 super.handleData(event
);
77 IKernelAnalysisEventLayout layout
= fLayout
;
79 IKernelTrace trace
= checkNotNull((IKernelTrace
) event
.getTrace());
80 layout
= trace
.getKernelEventLayout();
83 final String eventName
= event
.getType().getName();
85 if (eventName
.startsWith(layout
.eventSyscallEntryPrefix()) ||
86 eventName
.startsWith(layout
.eventCompatSyscallEntryPrefix())) {
87 /* This is a system call entry event */
89 Integer tid
= KernelTidAspect
.INSTANCE
.resolve(event
);
91 // no information on this event/trace ?
95 /* Record the event's data into the intial system call info */
96 // String syscallName = fLayout.getSyscallNameFromEvent(event);
97 long startTime
= event
.getTimestamp().getValue();
98 String syscallName
= eventName
.substring(layout
.eventSyscallEntryPrefix().length());
99 FluentIterable
<String
> argNames
= FluentIterable
.from(event
.getContent().getFieldNames());
100 Map
<String
, String
> args
= argNames
.toMap(new Function
<String
, String
>() {
102 public String
apply(@Nullable String input
) {
103 return checkNotNull(event
.getContent().getField(input
).getValue().toString());
106 SystemCall
.InitialInfo newSysCall
= new SystemCall
.InitialInfo(startTime
, NonNullUtils
.checkNotNull(syscallName
), NonNullUtils
.checkNotNull(args
));
107 fOngoingSystemCalls
.put(tid
, newSysCall
);
109 } else if (eventName
.startsWith(layout
.eventSyscallExitPrefix())) {
110 /* This is a system call exit event */
112 Integer tid
= KernelTidAspect
.INSTANCE
.resolve(event
);
117 SystemCall
.InitialInfo info
= fOngoingSystemCalls
.remove(tid
);
120 * We have not seen the entry event corresponding to this
121 * exit (lost event, or before start of trace).
126 long endTime
= event
.getTimestamp().getValue();
127 int ret
= ((Long
) event
.getContent().getField("ret").getValue()).intValue(); //$NON-NLS-1$
128 ISegment syscall
= new SystemCall(info
, endTime
, ret
);
129 getSegmentStore().add(syscall
);
134 public void handleCompleted() {
135 fOngoingSystemCalls
.clear();