summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/CodeParser/CParser/Argument.ts6
-rw-r--r--src/CodeParser/CParser/CParser.ts395
-rw-r--r--src/CodeParser/CParser/ParseTree.ts133
-rw-r--r--src/CodeParser/CParser/Token.ts2
4 files changed, 300 insertions, 236 deletions
diff --git a/src/CodeParser/CParser/Argument.ts b/src/CodeParser/CParser/Argument.ts
new file mode 100644
index 0000000..4cd793d
--- /dev/null
+++ b/src/CodeParser/CParser/Argument.ts
@@ -0,0 +1,6 @@
+import { ParseTree } from "./ParseTree";
+
+export class Argument {
+ public Name: string = undefined;
+ public Type: ParseTree = new ParseTree();
+}
diff --git a/src/CodeParser/CParser/CParser.ts b/src/CodeParser/CParser/CParser.ts
index d0d0dcb..6de9ae0 100644
--- a/src/CodeParser/CParser/CParser.ts
+++ b/src/CodeParser/CParser/CParser.ts
@@ -3,6 +3,7 @@ import { Config, ConfigType } from "../../Config";
import Generator from "../../DocGen/CGen";
import { IDocGen } from "../../DocGen/DocGen";
import ICodeParser from "../CodeParser";
+import { Argument } from "./Argument";
import { ParseTree } from "./ParseTree";
import { Token, TokenType } from "./Token";
@@ -18,23 +19,31 @@ export default class CParser implements ICodeParser {
protected activeEditor: TextEditor;
protected activeSelection: Position;
+ private typeKeywords: string[];
+ private stripKeywords: string[];
private keywords: string[];
private lexerVocabulary;
constructor() {
- this.keywords = [
+ this.typeKeywords = [
+ "const",
+ "struct",
+ ];
+
+ this.stripKeywords = [
"static",
"inline",
"friend",
"virtual",
"extern",
"explicit",
- "const",
- "struct",
"class",
"override",
];
+ // Non type keywords will be stripped from the final return type.
+ this.keywords = this.typeKeywords.concat(this.stripKeywords);
+
this.lexerVocabulary = {
ArraySubscript: (x: string): string => (x.match("^\\[[^\\[]*?\\]") || [])[0],
Arrow: (x: string): string => (x.match("^->") || [])[0],
@@ -42,6 +51,24 @@ export default class CParser implements ICodeParser {
Attribute: (x: string): string => (x.match("^\\[\\[[^\\[]*?\\]\\]") || [])[0],
CloseParenthesis: (x: string): string => (x.match("^\\)") || [])[0],
Comma: (x: string): string => (x.match("^,") || [])[0],
+ CommentBlock: (x: string): string => {
+ if (x.startsWith("/*") === false) {
+ return undefined;
+ }
+
+ let closeOffset: number = x.indexOf("*/");
+ closeOffset = closeOffset === -1 ? x.length : closeOffset + 2;
+ return x.slice(0, closeOffset);
+ },
+ CommentLine: (x: string): string => {
+ if (x.startsWith("//") === false) {
+ return undefined;
+ }
+
+ let closeOffset: number = x.indexOf("\n");
+ closeOffset = closeOffset === -1 ? x.length : closeOffset + 1;
+ return x.slice(0, closeOffset);
+ },
CurlyBlock: (x: string): string => {
if (x.startsWith("{") === false) {
return undefined;
@@ -63,7 +90,7 @@ export default class CParser implements ICodeParser {
return startEndOffset[1] === 0 ? undefined : x.slice(0, startEndOffset[1]);
}
- const reMatch: string = (x.match("^[a-z|A-Z|:|_|\\d]+") || [])[0];
+ const reMatch: string = (x.match("^[a-z|A-Z|:|_|~|\\d]+") || [])[0];
if (reMatch === undefined) {
return undefined;
}
@@ -86,42 +113,29 @@ export default class CParser implements ICodeParser {
this.activeEditor = activeEdit;
this.activeSelection = this.activeEditor.selection.active;
- const activeLine: TextLine = this.activeEditor.document.lineAt(this.activeEditor.selection.active.line);
-
- let line: string = this.getLogicalLine();
-
- // Not a method
- if (line.length === 0) {
+ let line: string;
+ try {
+ line = this.getLogicalLine();
+ } catch (err) {
return null;
}
// template parsing is simpler by using heuristics rather then tokenizing first.
const template: string = this.GetTemplate(line);
const templateArgs: string[] = this.GetArgsFromTemplate(template);
- let args: string[] = [];
- let retVals: string[] = [];
line = line.slice(template.length, line.length + 1).trim();
+ let retAndArgs: string[][];
try {
- // Tokenize rest of expression;
- const tokens: Token[] = this.Tokenize(line);
- // Create hierarchical tree based on the parenthesis.
- const tree: ParseTree = ParseTree.CreateTree(tokens).Compact();
-
- const parsedArgs: ParseTree[] = tree.GetArgTrees();
- const parsedReturns: ParseTree = tree.GetReturnTree();
-
- args = parsedArgs
- .map((a) => this.GetArgNameFromArgTree(a));
-
- retVals = this.GetArgTypeFromReturnTree(parsedReturns);
-
+ retAndArgs = this.GetReturnAndArgs(line);
} catch (err) {
- args = [];
- retVals = [];
+ // console.dir(err);
}
+ const retVals = retAndArgs[0];
+ const args = retAndArgs[1];
+
const cppGenerator: IDocGen = new Generator(
this.activeEditor,
this.activeSelection,
@@ -135,7 +149,7 @@ export default class CParser implements ICodeParser {
/***************************************************************************
Implementation
***************************************************************************/
- protected getLogicalLine(): string {
+ private getLogicalLine(): string {
let logicalLine: string = "";
let nextLine: Position = new Position(this.activeSelection.line + 1, this.activeSelection.character);
@@ -147,29 +161,40 @@ export default class CParser implements ICodeParser {
nextLineTxt = "";
}
- while (nextLineTxt.length === 0) { // Get first method line
- nextLine = new Position(nextLine.line + 1, nextLine.character);
- nextLineTxt = this.activeEditor.document.lineAt(nextLine.line).text.trim();
- }
-
- logicalLine += nextLineTxt;
+ let currentNest: number = 0;
+ logicalLine = nextLineTxt;
// Get method end line
- while (nextLineTxt.indexOf(";") === -1 && nextLineTxt.indexOf("{") === -1) { // Check for method end
+ let linesToGet: number = 20;
+ while (linesToGet-- > 0) { // Check for end of expression.
nextLine = new Position(nextLine.line + 1, nextLine.character);
nextLineTxt = this.activeEditor.document.lineAt(nextLine.line).text.trim();
- logicalLine += " " + nextLineTxt;
- }
+ // Check if method has finished if curly brace is opened while
+ // nesting is occuring.
+ for (let i: number = 0; i < nextLineTxt.length; i++) {
+ if (nextLineTxt[i] === "(") {
+ currentNest++;
+ } else if (nextLineTxt[i] === ")") {
+ currentNest--;
+ } else if (nextLineTxt[i] === "{" && currentNest === 0) {
+ logicalLine += "\n" + nextLineTxt.slice(0, i);
+ return logicalLine.replace(/^\s+|\s+$/g, "");
+ } else if (nextLineTxt[i] === ";" && currentNest === 0) {
+ logicalLine += "\n" + nextLineTxt.slice(0, i);
+ return logicalLine.replace(/^\s+|\s+$/g, "");
+ }
+ }
- logicalLine = logicalLine.replace(/[{|;]$/, "").trim();
+ logicalLine += "\n" + nextLineTxt;
+ }
- return logicalLine;
+ throw new Error("More then 20 lines were gotten from editor and no end of expression was found.");
}
private Tokenize(expression: string): Token[] {
const tokens: Token[] = [];
- expression = expression.trim();
+ expression = expression.replace(/^\s+|\s+$/g, "");
while (expression.length !== 0) {
const matches: Token[] = Object.keys(this.lexerVocabulary)
@@ -182,117 +207,247 @@ export default class CParser implements ICodeParser {
throw new Error("Multiple matches for next token: " + expression);
}
- const match = matches[0];
- tokens.push(match);
- expression = expression.slice(match.Value.length, expression.length).trim();
+ tokens.push(matches[0]);
+ expression = expression.slice(matches[0].Value.length, expression.length).replace(/^\s+|\s+$/g, "");
}
return tokens;
}
- private GetArgNameFromArgTree(tree: ParseTree): string {
- const hasEllipsis: boolean = tree.nodes
- .filter((n) => n instanceof Token && n.Type === TokenType.Ellipsis)
- .length > 0;
+ private GetReturnAndArgs(line: string): string[][] {
+ const retVals: string[] = [];
+ let args: string[] = [];
- const indexTrailingReturn: number = tree.nodes
- .findIndex((t) => t instanceof Token ? t.Type === TokenType.Arrow : false);
+ // Tokenize rest of expression and remove comment tokens;
+ const tokens: Token[] = this.Tokenize(line)
+ .filter((t) => t.Type !== TokenType.CommentBlock)
+ .filter((t) => t.Type !== TokenType.CommentLine);
+ // Create hierarchical tree based on the parenthesis.
+ const tree: ParseTree = ParseTree.CreateTree(tokens).Compact();
+
+ // return arg.
+ const returnArg = this.GetArgument(tree);
+ // check if it is a constructor or descructor since it has no name.
+ // and reverse the assignment of type and name.
+ if (returnArg.Name === undefined) {
+ if (returnArg.Type.nodes.length !== 1) {
+ throw new Error("Too many symbols found for constructor/descructor.");
+ } else if (returnArg.Type.nodes[0] instanceof ParseTree) {
+ throw new Error("One node found with just a parsetree. Malformed input.");
+ }
- const isFuncPtr: boolean = tree.nodes
- .slice(0, indexTrailingReturn === -1 ? tree.nodes.length : indexTrailingReturn)
- .filter((n) => n instanceof ParseTree)
- .length === 2;
-
- // If it is a function pointer the name is in the first tree.
- if (isFuncPtr === true) {
- const nestedTokens: Token[] = tree.nodes
- .filter((n) => n instanceof ParseTree)
- .map((n) => n as ParseTree)[0]
- .nodes
- .filter((n) => n instanceof Token)
- .map((n) => n as Token)
- .filter((t) => t.Type === TokenType.Symbol)
- .filter((t) => this.keywords.find((k) => k === t.Value) === undefined);
+ returnArg.Name = (returnArg.Type.nodes[0] as Token).Value;
+ returnArg.Type.nodes = [];
+ }
- return nestedTokens[0].Value;
+ // Special case for bool return type.
+ const boolReturnIndex: number = returnArg.Type.nodes
+ .findIndex((n) => n instanceof Token && n.Type === TokenType.Symbol && n.Value === "bool");
+ if (boolReturnIndex !== -1) {
+ retVals.push("true");
+ retVals.push("false");
+ } else {
+ retVals.push(returnArg.Type.Yield());
}
- const tokens: Token[] = tree.nodes
- .filter((n) => n instanceof Token)
- .map((n) => n as Token)
- .filter((t) => t.Type === TokenType.Symbol)
- .filter((t) => this.keywords.find((k) => k === t.Value) === undefined);
+ // Get arguments list.
+ args = this.GetArgumentList(tree)
+ .map((a) => this.GetArgument(a))
+ .map((a) => a.Name === undefined ? "" : a.Name);
+
+ return [retVals, args];
+ }
- if (tokens.length === 0 && hasEllipsis === true) {
- return "...";
+ private GetArgumentList(tree: ParseTree): ParseTree[] {
+ const args: ParseTree[] = [];
+
+ let cursor: ParseTree = tree;
+ while (this.IsFuncPtr(cursor.nodes) === true) {
+ cursor = cursor.nodes.find((n) => n instanceof ParseTree) as ParseTree;
}
- if (tokens.length < 2) {
- return "";
+ const argTree: ParseTree = cursor.nodes.find((n) => n instanceof ParseTree) as ParseTree;
+ if (argTree === undefined) {
+ throw new Error("Function arguments not found.");
+ }
+
+ // Split the argument tree on commas
+ let arg: ParseTree = new ParseTree();
+ for (const node of argTree.nodes) {
+ if (node instanceof Token && node.Type === TokenType.Comma) {
+ args.push(arg);
+ arg = new ParseTree();
+ } else {
+ arg.nodes.push(node);
+ }
+ }
+
+ if (arg.nodes.length > 0) {
+ args.push(arg);
}
- return tokens[1].Value;
+ return args;
}
- private GetArgTypeFromReturnTree(tree: ParseTree): string[] {
- // First strip out the param name or function name since it's not part of the type.
- const indexTrailingReturn: number = tree.nodes
- .findIndex((t) => t instanceof Token ? t.Type === TokenType.Arrow : false);
+ private IsFuncPtr(nodes: Array<Token | ParseTree>) {
+ return nodes.filter((n) => n instanceof ParseTree).length === 2;
+ }
- const isFuncPtr: boolean = tree.nodes
- .slice(0, indexTrailingReturn === -1 ? tree.nodes.length : indexTrailingReturn)
- .filter((n) => n instanceof ParseTree)
- .length === 2;
-
- let treeToModify: ParseTree = tree;
- let symbolsFound = 0;
- // If it is a function pointer the name is in the first tree.
- if (isFuncPtr === true) {
- treeToModify = tree.nodes
- .filter((n) => n instanceof ParseTree)
- .map((n) => n as ParseTree)[0];
-
- // Function pointer so delete the first symbol in the tree
- // Fake that one symbol was found.
- symbolsFound = 1;
- } else {
- // Check for special case if return type is boolean or void.
- for (const token of treeToModify.nodes) {
- if (token instanceof ParseTree) {
- break;
- }
- if (token.Type !== TokenType.Symbol) {
- continue;
- }
+ private StripNonTypeNodes(tree: ParseTree) {
+ tree.nodes = tree.nodes
+ // All strippable keywords.
+ .filter((n) => {
+ return !(n instanceof Token
+ && n.Type === TokenType.Symbol
+ && this.stripKeywords.find((k) => k === n.Value) !== undefined);
+ })
+ // Attributes aren't part of the type.
+ .filter((n) => !(n instanceof Token && n.Type === TokenType.Attribute));
+ }
- if (token.Value === "bool") {
- return ["true", "false"];
- } else if (token.Value === "void") {
- return [];
- }
+ private GetArgumentFromTrailingReturn(tree: ParseTree, startTrailingReturn: number): Argument {
+ const argument: Argument = new Argument();
+
+ // Find index of auto prior to the first parseTree.
+ // If auto is not found something is going wrong since trailing return
+ // requires auto.
+ let autoIndex: number = -1;
+ for (let i: number = 0; i < tree.nodes.length; i++) {
+ const node = tree.nodes[i];
+ if (node instanceof ParseTree) {
+ break;
+ }
+ if (node.Type === TokenType.Symbol && node.Value === "auto") {
+ autoIndex = i;
+ break;
}
}
- for (let i = 0; i < treeToModify.nodes.length; i++) {
- const node = treeToModify.nodes[i];
+ if (autoIndex === -1) {
+ throw new Error("Function declaration has trailing return but type is not auto.");
+ }
+
+ // Get symbol between auto and parseTree which is the argument name. It also may not be a keyword.
+ for (let i: number = autoIndex + 1; i < tree.nodes.length; i++) {
+ const node = tree.nodes[i];
if (node instanceof ParseTree) {
break;
}
+ if (node.Type === TokenType.Symbol && this.keywords.find((k) => k === node.Value) === undefined) {
+ argument.Name = node.Value;
+ break;
+ }
+ }
+
+ argument.Type.nodes = tree.nodes.slice(startTrailingReturn + 1, tree.nodes.length);
+ this.StripNonTypeNodes(argument.Type);
+
+ return argument;
+ }
+
+ private GetArgumentFromFuncPtr(tree: ParseTree): Argument {
+ const argument: Argument = new Argument();
+
+ argument.Type = tree;
+
+ let cursor: ParseTree = tree;
+
+ while (this.IsFuncPtr(cursor.nodes) === true) {
+ cursor = cursor.nodes.find((n) => n instanceof ParseTree) as ParseTree;
+ }
+
+ // Slice parseTree. This can be if it is a function declaration.
+ const argumentsIndex = cursor.nodes.findIndex((n) => n instanceof ParseTree);
+ if (argumentsIndex !== -1) {
+ cursor.nodes.splice(argumentsIndex, 1);
+ }
+
+ // Find first symbol that is the argument name.
+ // Remove it from the tree and set the name to the argument name
+ for (let i: number = 0; i < cursor.nodes.length; i++) {
+ const node = cursor.nodes[i];
+ if (node instanceof ParseTree) {
+ continue;
+ }
- if (node instanceof Token
- && node.Type === TokenType.Symbol
+ if (node.Type === TokenType.Symbol && this.keywords.find((k) => k === node.Value) === undefined) {
+ argument.Name = node.Value;
+ cursor.nodes.splice(i, 1);
+ }
+ }
+
+ this.StripNonTypeNodes(argument.Type);
+ return argument;
+ }
+
+ private GetDefaultArgument(tree: ParseTree): Argument {
+ const argument: Argument = new Argument();
+
+ for (const node of tree.nodes) {
+ if (node instanceof ParseTree) {
+ break;
+ }
+
+ const symbolCount = argument.Type.nodes
+ .filter((n) => n instanceof Token)
+ .map((n) => n as Token)
+ .filter((n) => n.Type === TokenType.Symbol)
+ .filter((n) => this.keywords.find((k) => k === n.Value) === undefined)
+ .length;
+
+ if (node.Type === TokenType.Symbol
&& this.keywords.find((k) => k === node.Value) === undefined
) {
- symbolsFound++;
+ if (symbolCount === 1 && argument.Name === undefined) {
+ argument.Name = node.Value;
+ continue;
+ } else if (symbolCount > 1) {
+ throw new Error("Too many non keyword symbols.");
+ }
}
- if (symbolsFound === 2) {
- treeToModify.nodes.splice(i, 1);
- break;
+ argument.Type.nodes.push(node);
+ }
+
+ this.StripNonTypeNodes(argument.Type);
+ return argument;
+ }
+
+ private GetArgument(tree: ParseTree): Argument {
+ // Copy tree structure leave original untouched.
+ const copy = tree.Copy();
+
+ // First slice of everything after assignment since that will not be used.
+ const assignmentIndex = copy.nodes.findIndex((n) => n instanceof Token && n.Type === TokenType.Assignment);
+ if (assignmentIndex !== -1) {
+ copy.nodes = copy.nodes.slice(0, assignmentIndex);
+ }
+
+ // Special case with only ellipsis. C style variadic arguments
+ if (copy.nodes.length === 1) {
+ const node = copy.nodes[0];
+ if (node instanceof Token && node.Type === TokenType.Ellipsis) {
+ const argument: Argument = new Argument();
+ argument.Name = node.Value;
+ return argument;
}
}
- return [tree.ToString()];
+ // Check if it is has a trailing return.
+ const startTrailingReturn: number = copy.nodes
+ .findIndex((t) => t instanceof Token ? t.Type === TokenType.Arrow : false);
+
+ // Special case trailing return.
+ if (startTrailingReturn !== -1) {
+ return this.GetArgumentFromTrailingReturn(copy, startTrailingReturn);
+ }
+
+ // Handle function pointers
+ if (this.IsFuncPtr(copy.nodes) === true) {
+ return this.GetArgumentFromFuncPtr(copy);
+ }
+
+ return this.GetDefaultArgument(copy);
}
private GetSubExprStartEnd(expression: string, startSearch: number, openExpr: string, closeExpr: string): number[] {
@@ -347,7 +502,7 @@ export default class CParser implements ICodeParser {
}
// Remove <> and add a comma to the end to remove edge case.
- template = template.slice(template.indexOf("<") + 1, template.lastIndexOf(">")).trim() + ",";
+ template = template.slice(template.indexOf("<") + 1, template.lastIndexOf(">")).replace(/^\s+|\s+$/g, "") + ",";
const nestedCounts: { [key: string]: number; } = {
"(": 0,
@@ -362,7 +517,7 @@ export default class CParser implements ICodeParser {
&& nestedCounts["{"] === 0;
if (notInSubExpr === true && template[i] === ",") {
- args.push(template.slice(lastSeparator + 1, i).trim());
+ args.push(template.slice(lastSeparator + 1, i).replace(/^\s+|\s+$/g, ""));
} else if (notInSubExpr === true && (template[i] === " " || template[i] === ".")) {
lastSeparator = i;
}
diff --git a/src/CodeParser/CParser/ParseTree.ts b/src/CodeParser/CParser/ParseTree.ts
index 9090212..bec5b91 100644
--- a/src/CodeParser/CParser/ParseTree.ts
+++ b/src/CodeParser/CParser/ParseTree.ts
@@ -51,7 +51,7 @@ export class ParseTree {
.map((n) => n instanceof ParseTree && isNotCompact(n) ? n.nodes[0] : n);
}
- // Compact all nested parsetrees and filter out empty branches.
+ // Compact all nested parsetrees.
newTree.nodes = newTree.nodes
.map((n) => n instanceof ParseTree ? this.Compact(n) : n);
@@ -59,14 +59,26 @@ export class ParseTree {
}
/**
+ * Copy parsetree.
+ * @param tree The ParseTree to compact. Defaults to the current tree.
+ */
+ public Copy(tree: ParseTree = this): ParseTree {
+ const newTree: ParseTree = new ParseTree();
+ newTree.nodes = tree.nodes
+ .map((n) => n instanceof Token ? n : this.Copy(n));
+ return newTree;
+ }
+
+ /**
* Create string from the parsetree which is a representation of the original code.
+ * @param tree The ParseTree to compact. Defaults to the current tree.
*/
- public ToString(tree: ParseTree = this): string {
+ public Yield(tree: ParseTree = this): string {
let code: string = "";
for (const node of tree.nodes) {
if (node instanceof ParseTree) {
- code += "(" + this.ToString(node) + ")";
+ code += "(" + this.Yield(node) + ")";
continue;
}
@@ -87,13 +99,13 @@ export class ParseTree {
code += node.Value;
break;
case TokenType.Assignment:
- code += " " + node.Value + " ";
+ code += " " + node.Value;
break;
case TokenType.Comma:
code += node.Value;
break;
case TokenType.Arrow:
- code += " " + node.Value + " ";
+ code += " " + node.Value;
break;
case TokenType.Ellipsis:
code += node.Value;
@@ -106,115 +118,4 @@ export class ParseTree {
return code;
}
-
- /**
- * Get the tree for the return.
- */
- public GetReturnTree(): ParseTree {
- const returnTree: ParseTree = new ParseTree();
-
- const indexTrailingReturn: number = this.nodes
- .findIndex((t) => t instanceof Token ? t.Type === TokenType.Arrow : false);
-
- const isFuncPtr: boolean = this.nodes
- .slice(0, indexTrailingReturn === -1 ? this.nodes.length : indexTrailingReturn)
- .filter((n) => n instanceof ParseTree)
- .length === 2;
-
- if (isFuncPtr === true) {
- const trees: ParseTree[] = this.nodes
- .filter((n) => n instanceof ParseTree)
- .map((n) => n as ParseTree);
-
- // Add left most part to the return tokens.
- for (const node of this.nodes) {
- if (node instanceof ParseTree) {
- break;
- }
- returnTree.nodes.push(node);
- }
-
- // add left and right parse tree to return tokens
- const leftTree: ParseTree = new ParseTree();
- for (const node of trees[0].nodes) {
- if (node instanceof ParseTree) {
- break;
- }
- leftTree.nodes.push(node);
- }
-
- returnTree.nodes.push(leftTree);
- returnTree.nodes.push(trees[1]);
- } else if (indexTrailingReturn !== -1) {
- returnTree.nodes = this.nodes
- .slice(indexTrailingReturn + 1, this.nodes.length);
-
- // Don't include the auto so start from index 1.
- for (let i: number = 1; i < this.nodes.length; i++) {
- if (this.nodes[i] instanceof ParseTree) {
- break;
- }
- returnTree.nodes.push(this.nodes[i]);
- }
- } else {
- for (const node of this.nodes) {
- if (node instanceof ParseTree) {
- break;
- }
- returnTree.nodes.push(node);
- }
- }
-
- return returnTree;
- }
-
- /**
- * Get the arguments of the function and create a new ParseTree for each one.
- */
- public GetArgTrees(): ParseTree[] {
- const args: ParseTree[] = [];
-
- const indexTrailingReturn: number = this.nodes
- .findIndex((t) => t instanceof Token ? t.Type === TokenType.Arrow : false);
-
- const isFuncPtr: boolean = this.nodes
- .slice(0, indexTrailingReturn === -1 ? this.nodes.length : indexTrailingReturn)
- .filter((n) => n instanceof ParseTree)
- .length === 2;
-
- let argsTree: ParseTree = this.nodes
- .filter((n) => n instanceof ParseTree)
- .map((t) => t as ParseTree)[0];
-
- // If it is a func ptr get the nested tree.
- if (isFuncPtr === true) {
- argsTree = argsTree.nodes
- .filter((n) => n instanceof ParseTree)
- .map((t) => t as ParseTree)[0];
- }
-
- if (argsTree === undefined) {
- throw new Error("Couldn't find arguments tree");
- }
-
- // split args at command and create a tree for each one.
- let lastComma: number = 0;
- for (let i = 0; i < argsTree.nodes.length; i++) {
- const node = argsTree.nodes[i];
- if (node instanceof Token && node.Type === TokenType.Comma) {
- const tree: ParseTree = new ParseTree();
- tree.nodes = argsTree.nodes.slice(lastComma, i);
- args.push(tree);
- lastComma = i + 1;
- }
- }
-
- const lastArgTree: ParseTree = new ParseTree();
- lastArgTree.nodes = argsTree.nodes.slice(lastComma, argsTree.nodes.length);
- if (lastArgTree.nodes.length > 0) {
- args.push(lastArgTree);
- }
-
- return args;
- }
}
diff --git a/src/CodeParser/CParser/Token.ts b/src/CodeParser/CParser/Token.ts
index 379fd46..b947ec0 100644
--- a/src/CodeParser/CParser/Token.ts
+++ b/src/CodeParser/CParser/Token.ts
@@ -9,6 +9,8 @@ export enum TokenType {
Assignment,
Comma,
Arrow,
+ CommentBlock,
+ CommentLine,
Ellipsis,
Attribute,
}