diff options
Diffstat (limited to 'emulator/qtools/parse_options-inl.h')
-rw-r--r-- | emulator/qtools/parse_options-inl.h | 147 |
1 files changed, 147 insertions, 0 deletions
diff --git a/emulator/qtools/parse_options-inl.h b/emulator/qtools/parse_options-inl.h new file mode 100644 index 0000000..f218cc1 --- /dev/null +++ b/emulator/qtools/parse_options-inl.h @@ -0,0 +1,147 @@ +// Copyright 2006 The Android Open Source Project + +#ifndef PARSE_OPTIONS_INL_H +#define PARSE_OPTIONS_INL_H + +// Define a typedef for TraceReaderType and include "parse_options.h" +// before including this header file in a C++ source file. +// +// For example: +// +// struct symbol { +// int elapsed; +// }; +// +// typedef TraceReader<symbol> TraceReaderType; + + +typedef TraceReaderType::symbol_type symbol_type; +typedef TraceReaderType::region_type region_type; +typedef TraceReaderType::ProcessState ProcessState; + +symbol_type *kernel_sym; +symbol_type *library_sym; + +// Returns true if the given event is included (or not excluded) +// from the list of valid events specified by the user on the +// command line. +inline bool IsValidEvent(BBEvent *event, symbol_type *sym) +{ + if (include_some_pids && pid_include_vector.GetBit(event->pid) == 0) + return false; + if (exclude_some_pids && pid_exclude_vector.GetBit(event->pid)) + return false; + if (include_some_procedures) { + if (sym == NULL || included_procedures.Find(sym->name) == 0) + return false; + } + if (exclude_some_procedures) { + if (sym == NULL || excluded_procedures.Find(sym->name)) + return false; + } + return true; +} + +inline symbol_type *GetSymbol(TraceReaderType *trace, int pid, uint32_t addr, + uint64_t time) +{ + symbol_type *sym = trace->LookupFunction(pid, addr, time); + + if (lump_kernel && (sym->region->flags & region_type::kIsKernelRegion)) { + if (kernel_sym == NULL) { + kernel_sym = sym; + sym->name = ":kernel"; + } else { + sym = kernel_sym; + } + } + + if (lump_libraries && (sym->region->flags & region_type::kIsLibraryRegion)) { + if (library_sym == NULL) { + library_sym = sym; + sym->name = ":libs"; + } else { + sym = library_sym; + } + } + + return sym; +} + +inline bool IsIncludedProcedure(symbol_type *sym) +{ + if (include_kernel_syms && (sym->region->flags & region_type::kIsKernelRegion)) + return true; + if (include_library_syms && (sym->region->flags & region_type::kIsLibraryRegion)) + return true; + return included_procedures.Find(sym->name); +} + +inline bool IsExcludedProcedure(symbol_type *sym) +{ + if (exclude_kernel_syms && (sym->region->flags & region_type::kIsKernelRegion)) + return true; + if (exclude_library_syms && (sym->region->flags & region_type::kIsLibraryRegion)) + return true; + return excluded_procedures.Find(sym->name); +} + +// Returns true on end-of-file. +inline bool GetNextValidEvent(TraceReaderType *trace, + BBEvent *event, + BBEvent *first_ignored_event, + symbol_type **sym_ptr) +{ + symbol_type *sym = NULL; + first_ignored_event->time = 0; + if (trace->ReadBB(event)) + return true; + bool recheck = true; + while (recheck) { + recheck = false; + if (include_some_pids) { + while (pid_include_vector.GetBit(event->pid) == 0) { + if (first_ignored_event->time == 0) + *first_ignored_event = *event; + if (trace->ReadBB(event)) + return true; + } + } else if (exclude_some_pids) { + while (pid_exclude_vector.GetBit(event->pid)) { + if (first_ignored_event->time == 0) + *first_ignored_event = *event; + if (trace->ReadBB(event)) + return true; + } + } + + if (include_some_procedures) { + sym = GetSymbol(trace, event->pid, event->bb_addr, event->time); + while (!IsIncludedProcedure(sym)) { + if (first_ignored_event->time == 0) + *first_ignored_event = *event; + if (trace->ReadBB(event)) + return true; + recheck = true; + sym = GetSymbol(trace, event->pid, event->bb_addr, event->time); + } + } else if (exclude_some_procedures) { + sym = GetSymbol(trace, event->pid, event->bb_addr, event->time); + while (IsExcludedProcedure(sym)) { + if (first_ignored_event->time == 0) + *first_ignored_event = *event; + if (trace->ReadBB(event)) + return true; + recheck = true; + sym = GetSymbol(trace, event->pid, event->bb_addr, event->time); + } + } + } + if (sym == NULL) + sym = GetSymbol(trace, event->pid, event->bb_addr, event->time); + + *sym_ptr = sym; + return false; +} + +#endif // PARSE_OPTIONS_INL_H |