1 /**************************************************************************
3 * Copyright 2012 VMware, Inc.
6 * Permission is hereby granted, free of charge, to any person obtaining a copy
7 * of this software and associated documentation files (the "Software"), to deal
8 * in the Software without restriction, including without limitation the rights
9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10 * copies of the Software, and to permit persons to whom the Software is
11 * furnished to do so, subject to the following conditions:
13 * The above copyright notice and this permission notice shall be included in
14 * all copies or substantial portions of the Software.
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24 **************************************************************************/
35 #include <trace_callset.hpp>
38 using namespace trace;
41 // Parser class for call sets
49 CallSetParser(CallSet &_set) :
67 CallNo start = std::numeric_limits<CallNo>::min();
68 CallNo stop = std::numeric_limits<CallNo>::max();
70 CallFlags freq = FREQUENCY_ALL;
72 freq = parseFrequency();
74 if (isOperator('*')) {
77 start = parseCallNo();
78 if (isOperator('-')) {
88 if (isOperator('/')) {
92 freq = parseFrequency();
96 set.addRange(CallRange(start, stop, step, freq));
99 // match and consume an operator
100 bool isOperator(char c) {
101 if (lookahead == c) {
110 CallNo parseCallNo() {
114 CallNo digit = consume() - '0';
115 number = number * 10 + digit;
118 std::cerr << "error: expected digit, found '" << lookahead << "'\n";
125 CallFlags parseFrequency() {
129 freq.push_back(consume());
132 std::cerr << "error: expected frequency, found '" << lookahead << "'\n";
136 if (freq == "frame") {
137 return FREQUENCY_FRAME;
138 } else if (freq == "rendertarget" || freq == "fbo") {
139 return FREQUENCY_RENDERTARGET;
140 } else if (freq == "render" || freq == "draw") {
141 return FREQUENCY_RENDER;
143 std::cerr << "error: expected frequency, found '" << freq << "'\n";
145 return FREQUENCY_NONE;
149 // match lookahead with a digit (does not consume)
150 bool isDigit() const {
151 return lookahead >= '0' && lookahead <= '9';
154 bool isAlpha() const {
155 return lookahead >= 'a' && lookahead <= 'z';
158 void skipWhiteSpace() {
164 bool isSpace() const {
165 return lookahead == ' ' ||
171 virtual char consume() = 0;
175 class StringCallSetParser : public CallSetParser
180 StringCallSetParser(CallSet &_set, const char *_buf) :
198 class FileCallSetParser : public CallSetParser
200 std::ifstream stream;
203 FileCallSetParser(CallSet &_set, const char *filename) :
206 stream.open(filename);
207 if (!stream.is_open()) {
208 std::cerr << "error: failed to open \"" << filename << "\"\n";
212 stream.get(lookahead);
220 stream.get(lookahead);
227 CallSet::CallSet(const char *string)
229 if (*string == '@') {
230 FileCallSetParser parser(*this, &string[1]);
233 StringCallSetParser parser(*this, string);
239 CallSet::CallSet(CallFlags freq) {
240 if (freq != FREQUENCY_NONE) {
241 CallNo start = std::numeric_limits<CallNo>::min();
242 CallNo stop = std::numeric_limits<CallNo>::max();
244 addRange(CallRange(start, stop, step, freq));