mirror of https://github.com/buggins/dlangide.git
GDB MI output parser
This commit is contained in:
parent
8c3a284d90
commit
820c88847c
|
@ -650,33 +650,75 @@ MIToken[] tokenizeMI(string s, out bool error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
MIValue parseMI(string s) {
|
MIValue parseMI(string s) {
|
||||||
bool err = false;
|
string src = s;
|
||||||
MIToken[] tokens = tokenizeMI(s, err);
|
try {
|
||||||
if (error) {
|
bool err = false;
|
||||||
// tokenizer error
|
MIToken[] tokens = tokenizeMI(s, err);
|
||||||
return new MIValue(MIValueType.empty);
|
if (err) {
|
||||||
|
// tokenizer error
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
MIValue[] items = parseMIList(tokens);
|
||||||
|
return new MIList(items);
|
||||||
|
} catch (Exception e) {
|
||||||
|
Log.e("Cannot parse MI from " ~ src, e);
|
||||||
|
return null;
|
||||||
}
|
}
|
||||||
MIValue[] items = parseMI(tokens);
|
|
||||||
return new MIList(items);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
MIValue[] parseMI(MIToken[] tokens) {
|
MIValue parseMIValue(ref MIToken[] tokens) {
|
||||||
MIValue[] res;
|
|
||||||
if (tokens.length == 0)
|
if (tokens.length == 0)
|
||||||
return res;
|
return null;
|
||||||
MITokenType tokenType = tokens.length > 0 ? tokens[0].type : MITokenType.eol;
|
MITokenType tokenType = tokens.length > 0 ? tokens[0].type : MITokenType.eol;
|
||||||
MITokenType nextTokenType = tokens.length > 1 ? tokens[1].type : MITokenType.eol;
|
MITokenType nextTokenType = tokens.length > 1 ? tokens[1].type : MITokenType.eol;
|
||||||
if (tokenType = MITokenType.ident) {
|
if (tokenType == MITokenType.ident) {
|
||||||
string ident = tokens[0].str;
|
string ident = tokens[0].str;
|
||||||
if (nextTokenType == MITokenType.eol || nextTokenType == MITokenType.comma) {
|
if (nextTokenType == MITokenType.eol || nextTokenType == MITokenType.comma) {
|
||||||
res ~= new MIIdent(ident);
|
MIValue res = new MIIdent(ident);
|
||||||
tokens = tokens[1..$];
|
tokens = tokens[1..$];
|
||||||
if (nextTokenType == MITokenType.comma)
|
return res;
|
||||||
tokens = tokens[1..$];
|
|
||||||
} else if (nextTokenType == MITokenType.eq) {
|
} else if (nextTokenType == MITokenType.eq) {
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
MIValue value = parseMIValue(tokens);
|
||||||
|
MIValue res = new MIKeyValue(ident, value);
|
||||||
|
return res;
|
||||||
}
|
}
|
||||||
|
throw new Exception("Unexpected token " ~ to!string(tokenType));
|
||||||
|
} else if (tokenType == MITokenType.str) {
|
||||||
|
string str = tokens[0].str;
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
MIValue res = new MIString(str);
|
||||||
|
} else if (tokenType == MITokenType.curlyOpen) {
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
MIValue[] list = parseMIList(tokens, MITokenType.curlyClose);
|
||||||
|
return new MIMap(list);
|
||||||
|
} else if (tokenType == MITokenType.squareOpen) {
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
MIValue[] list = parseMIList(tokens, MITokenType.squareClose);
|
||||||
|
return new MIList(list);
|
||||||
|
}
|
||||||
|
throw new Exception("Invalid token at end of list: " ~ tokenType.to!string);
|
||||||
|
}
|
||||||
|
|
||||||
|
MIValue[] parseMIList(ref MIToken[] tokens, MITokenType closingToken = MITokenType.eol) {
|
||||||
|
MIValue[] res;
|
||||||
|
for (;;) {
|
||||||
|
MITokenType tokenType = tokens.length > 0 ? tokens[0].type : MITokenType.eol;
|
||||||
|
if (tokenType == MITokenType.eol)
|
||||||
|
return res;
|
||||||
|
if (tokenType == closingToken) {
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
MIValue value = parseMIValue(tokens);
|
||||||
|
res ~= value;
|
||||||
|
tokenType = tokens.length > 0 ? tokens[0].type : MITokenType.eol;
|
||||||
|
if (tokenType == MITokenType.comma) {
|
||||||
|
tokens = tokens[1..$];
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
throw new Exception("Unexpected token in list " ~ to!string(tokenType));
|
||||||
}
|
}
|
||||||
return res;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
enum MIValueType {
|
enum MIValueType {
|
||||||
|
@ -700,43 +742,79 @@ class MIValue {
|
||||||
this.type = type;
|
this.type = type;
|
||||||
}
|
}
|
||||||
@property string str() { return null; }
|
@property string str() { return null; }
|
||||||
|
@property int length() { return 1; }
|
||||||
|
MIValue opIndex(int index) { return null; }
|
||||||
|
MIValue opIndex(string key) { return null; }
|
||||||
}
|
}
|
||||||
|
|
||||||
class MIKeyValue {
|
class MIKeyValue : MIValue {
|
||||||
string key;
|
private string _key;
|
||||||
MIValue value;
|
private MIValue _value;
|
||||||
this(string key, MIValue value) {
|
this(string key, MIValue value) {
|
||||||
super(MIValueType.keyValue);
|
super(MIValueType.keyValue);
|
||||||
this.key = key;
|
_key = key;
|
||||||
this.value = value;
|
_value = value;
|
||||||
}
|
}
|
||||||
|
@property string key() { return _key; }
|
||||||
|
@property string str() { return _key; }
|
||||||
|
@property MIValue value() { return _value; }
|
||||||
}
|
}
|
||||||
|
|
||||||
class MIIdent {
|
class MIIdent : MIValue {
|
||||||
string ident;
|
private string _ident;
|
||||||
this(string ident) {
|
this(string ident) {
|
||||||
super(MIValueType.ident);
|
super(MIValueType.ident);
|
||||||
this.ident = ident;
|
_ident = ident;
|
||||||
}
|
}
|
||||||
override @property string str() { return ident; }
|
override @property string str() { return _ident; }
|
||||||
}
|
}
|
||||||
|
|
||||||
class MIString {
|
class MIString : MIValue {
|
||||||
string str;
|
private string _str;
|
||||||
this(string str) {
|
this(string str) {
|
||||||
super(MIValueType.str);
|
super(MIValueType.str);
|
||||||
this.str = str;
|
_str = str;
|
||||||
}
|
}
|
||||||
override @property string str() { return str; }
|
override @property string str() { return _str; }
|
||||||
}
|
}
|
||||||
|
|
||||||
class MIList {
|
class MIList : MIValue {
|
||||||
MIValue[] items;
|
private MIValue[] _items;
|
||||||
|
private MIValue[string] _map;
|
||||||
|
|
||||||
|
override @property int length() { return cast(int)_items.length; }
|
||||||
|
override MIValue opIndex(int index) {
|
||||||
|
if (index < 0 || index >= _items.length)
|
||||||
|
return null;
|
||||||
|
return _items[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
override MIValue opIndex(string key) {
|
||||||
|
if (key in _map) {
|
||||||
|
MIValue res = _map[key];
|
||||||
|
return res;
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
this(MIValue[] items) {
|
this(MIValue[] items) {
|
||||||
super(MIValueType.list);
|
super(MIValueType.list);
|
||||||
this.items = items;
|
_items = items;
|
||||||
|
// fill map
|
||||||
|
foreach(item; _items) {
|
||||||
|
if (item.type == MIValueType.keyValue) {
|
||||||
|
if (!item.str.empty)
|
||||||
|
_map[item.str] = (cast(MIKeyValue)item).value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class MIMap : MIList {
|
||||||
|
this(MIValue[] items) {
|
||||||
|
super(items);
|
||||||
|
type = MIValueType.map;
|
||||||
}
|
}
|
||||||
override @property string str() { return str; }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private char nextChar(ref string s) {
|
private char nextChar(ref string s) {
|
||||||
|
|
Loading…
Reference in New Issue