示例#1
0
void PosBuffer::filter_pydb(string& answer)
{
    if (already_read != PosComplete && !answer.contains('\n'))
    {
	// Position info is incomplete
	answer_buffer = answer;
	answer = "";
	already_read = PosPart;
	return;
    }

    // `Breakpoint N, FUNCTION (ARGS...) at file:line_no'
    // rxstopped_func defined for GDB...if it changes, change here
    int fn_index = index(answer, rxstopped_func, "Breakpoint");
    if (fn_index >= 0)
    {
	fetch_function(answer, fn_index, func_buffer);
    }
    else
    {
	// `#FRAME FUNCTION(args) at file:line_no'
	// Likewise rxframe_func defined for GDB
	int frame_index = index(answer, rxframe_addr, "#");
	if (frame_index == 0
	    || frame_index > 0 && answer[frame_index - 1] == '\n')
	{
	    fetch_function(answer, frame_index, func_buffer);
	}
    }

    int lineinfo  = answer.index("Lineinfo");
    // Lineinfo <function> at file:lineno
    if (lineinfo == 0 || (lineinfo > 0 && answer[lineinfo - 1] == '\n'))
    {
	answer = answer.after('<');
	func_buffer = answer.before('>');
    }

    string result = answer.after(" at ");
    result = result.before('\n');
    if (result.contains(':'))
    {
	pos_buffer = result;
	already_read = PosComplete;
    }

    // Don't need the answer anymore when line matches 'Lineinfo'
    if (lineinfo >= 0)
    {
	answer = "";
    }
}
示例#2
0
void PosBuffer::filter_gdb(string& answer)
{
    // Try to find out current PC even for non-existent source

    if (check_pc && pc_buffer.empty())
    {
	// `$pc = ADDRESS'
#if RUNTIME_REGEX
	static regex rxpc("\\$pc  *=  *" RXADDRESS);
#endif
	int pc_index = index(answer, rxpc, "$pc ");
	if (pc_index >= 0)
	{
	    int addr_index = answer.index('=');
	    fetch_address(answer, addr_index, pc_buffer);
		    
	    // Strip this line from ANSWER
	    int end_line = answer.index('\n', pc_index);
	    int start_line = pc_index;
	    while (start_line > 0 
		   && answer[start_line - 1] != '\n')
		start_line--;
		    
	    if (end_line < 0)
		answer.from(start_line) = "";
	    else
		answer.at(start_line, end_line - start_line + 1) 
		    = "";
	}
    }
	    
    if (check_pc && pc_buffer.empty() || 
	check_func && func_buffer.empty())
    {
	// `Breakpoint N, ADDRESS in FUNCTION (ARGS...)'
#if RUNTIME_REGEX
	static regex rxstopped_addr("Breakpoint  *[1-9][0-9]*,  *"
				    RXADDRESS);
#endif
	int pc_index = index(answer, rxstopped_addr, "Breakpoint");
	if (pc_index >= 0)
	{
	    annotate("stopped");
	    pc_index = answer.index(',');
	    fetch_address(answer, pc_index, pc_buffer);
	    fetch_in_function(answer, pc_index, func_buffer);
	}
    }
	    
    if (check_pc && pc_buffer.empty() || 
	check_func && func_buffer.empty())
    {
	// `#FRAME ADDRESS in FUNCTION (ARGS...)'
#if RUNTIME_REGEX
	static regex rxframe_addr("#[0-9][0-9]*  *" RXADDRESS);
#endif
		
	int pc_index = index(answer, rxframe_addr, "#");
	if (pc_index == 0
	    || pc_index > 0 && answer[pc_index - 1] == '\n')
	{
	    pc_index = answer.index(' ');
	    fetch_address(answer, pc_index, pc_buffer);
	    fetch_in_function(answer, pc_index, func_buffer);
	}
    }
	    
    if (check_pc && pc_buffer.empty() || 
	check_func && func_buffer.empty())
    {
	// `No line number available for 
	// address ADDRESS <FUNCTION>'
#if RUNTIME_REGEX
	static regex rxaddr("address  *" RXADDRESS);
#endif
		
	int pc_index = index(answer, rxaddr, "address ");
	if (pc_index >= 0)
	{
	    pc_index = answer.index(' ');
	    fetch_address(answer, pc_index, pc_buffer);
	    if (func_buffer.empty())
	    {
		string line = answer.from(pc_index);
		line = line.after('<');
		line = line.before('>');
		if (!line.empty())
		    func_buffer = line;
	    }
	}
    }

    if (check_pc && pc_buffer.empty() && !answer.empty())
    {
	// `ADDRESS in FUNCTION'
#if RUNTIME_REGEX
	static regex rxaddress_in(RXADDRESS " in ");
#endif
	int pc_index = -1;
	if (is_address_start(answer[0]) 
	    && answer.contains(rxaddress_in, 0))
	{
	    pc_index = 0;
	}
	else
	{
#if RUNTIME_REGEX
	    static regex rxnladdress_in("\n" RXADDRESS " in ");
#endif
	    pc_index = index(answer, rxnladdress_in, "\n");
	}
		
	if (pc_index >= 0)
	{
	    fetch_address(answer, pc_index, pc_buffer);
	    fetch_in_function(answer, pc_index, func_buffer);
	}
    }

    // Try to find out current function name, even for
    // non-existing addresses
    if (check_func && func_buffer.empty())
    {
	// `Breakpoint N, FUNCTION (ARGS...)'
	// This regex used for PYDB as well.
#if RUNTIME_REGEX
	static regex rxstopped_func("Breakpoint  *[1-9][0-9]*,  *");
#endif
	int bp_index = index(answer, rxstopped_func, "Breakpoint");
	if (bp_index >= 0)
	    fetch_function(answer, bp_index, func_buffer);
    }

    if (check_func && func_buffer.empty())
    {
	// `#FRAME FUNCTION'
#if RUNTIME_REGEX
	static regex rxframe_func("#[0-9][0-9]*  *[a-zA-Z_].*[(]");
#endif
	int frame_index = index(answer, rxframe_addr, "#");
	if (frame_index == 0
	    || frame_index > 0 && answer[frame_index - 1] == '\n')
	{
	    fetch_function(answer, frame_index, func_buffer);
	}
    }

    if (check_func && func_buffer.empty())
    {
	// FUNCTION (ARGS...) at FILE:POS
	int at_index = answer.index(" at ");
	if (at_index > 0)
	{
	    int nl_index = 
		answer.index('\n', at_index - answer.length() - 1) + 1;
	    fetch_function(answer, nl_index, func_buffer);

	    // Try to construct position from `at FILE:POS' (vxworks)
	    string file = answer.after(" at ");
	    file = file.before('\n');

	    if (file.contains(rxaddress, 0))
	    {
		// This is `at ADDRESS' (GDB output)
	    }
	    else if (file.contains(":") && !file.contains(": "))
	    {
		pos_buffer = file;
		already_read = PosComplete;
		return;
	    }
		
	}
    }
	    
    // Look for regular source info
    // (GDB's annotations are prefixed with "^Z^Z")
    int index1 = answer.index ("\032\032");
	    
    if (index1 < 0) 
    {
	int index_p = answer.index ("\032");
	if (index_p >= 0 && index_p == int(answer.length()) - 1)
	{
	    // Possible begin of position info at end of ANSWER
	    answer_buffer = "\032";
	    answer = answer.before (index_p);
	    already_read = PosPart;
	    return;
	}
		
	// Handle erroneous `info line' output like
	// `Line number 10 is out of range for "t1.f".'
	// At least get the file name.
#if RUNTIME_REGEX
	static regex rxout_of_range(
	    "Line number [0-9]+ is out of range for ");
#endif
	index_p = index(answer, rxout_of_range, "Line number");
	if (index_p >= 0)
	{
	    string file = answer.after('\"', index_p);
	    file = file.before('\"');
	    pos_buffer = file + ":1";
	    already_read = PosComplete;
	    return;
	}

	// Try to construct position from `Line xxxx of "filename"' (vxworks)
	// which is the output of an 'info line' command
	string line = answer.after("Line ");
	string file = answer.after('\"');
	if (!line.empty() && !file.empty())
	{
	    line = line.before(" of");
	    file = file.before('\"') + ":" + line;
	    if (!line.empty() && !file.empty())
	    {
		pos_buffer = file;
		already_read = PosComplete;
		return;
	    }
	}
	// Try FUNCTION (ARGS...) at FILE:POS
	// here to properly handle up/down commands 
	int at_index = answer.index(" at ");
	int br_index = answer.index("Break");
	if ( (at_index > 0) && (br_index < 0) )
	{
	    int nl_index = 
		answer.index('\n', at_index - answer.length() - 1) + 1;
	    fetch_function(answer, nl_index, func_buffer);

	    // Try to construct position from `at FILE:POS' (vxworks)
	    string file = answer.after(" at ");
	    file = file.before('\n');
	    if (!file.empty())
	    {
		pos_buffer = file;
		already_read = PosComplete;
		return;
	    }
		
	}
	
	// Nothing found
	return;
    }
	    
    // ANSWER contains position info
    int index2 = answer.index ("\n", index1);

    if (index2 == -1)
    {
	// Position info is incomplete
	answer_buffer = answer.from (index1);
	answer = answer.before (index1);
	already_read = PosPart;
	return;
    }

    assert (index1 < index2);

    // Position info is complete
    pos_buffer = answer.at(index1 + 2, index2 - (index1 + 2));

    if (pos_buffer.contains("source ", 0))
    {
	// This happens with GDB in annotation level 2
	pos_buffer = pos_buffer.after("source ");
    }

    int last_colon = pos_buffer.index(':', -1);
    pc_buffer = pos_buffer.after(last_colon);
    if (!pc_buffer.contains(rxaddress_start, 0))
	pc_buffer = "0x" + pc_buffer;
    pc_buffer = pc_buffer.through(rxaddress);

    answer.at(index1, index2 - index1 + 1) = "";
    if (!pos_buffer.empty())
	already_read = PosComplete;
}
示例#3
0
// Same, but requires " in " before function
inline void fetch_in_function(const string& answer, int index, string& buffer)
{
    fetch_function(answer, index, buffer, true);
}