168 lines
6.2 KiB
C#
168 lines
6.2 KiB
C#
|
using CanonSharp.Common.Scanner;
|
|||
|
using CanonSharp.Tests.Utils;
|
|||
|
|
|||
|
namespace CanonSharp.Tests.ScannerTest;
|
|||
|
|
|||
|
public class LexicalParserTests : LexicalTestBase
|
|||
|
{
|
|||
|
[Fact]
|
|||
|
public void LexicalParserTest1()
|
|||
|
{
|
|||
|
const string pascalProgram = """
|
|||
|
program HelloWorld;
|
|||
|
var
|
|||
|
message: char;
|
|||
|
begin
|
|||
|
message := 'h';
|
|||
|
writeln(message);
|
|||
|
end.
|
|||
|
""";
|
|||
|
|
|||
|
ValidateLexicalTokens(LexicalScanner.PascalParser(), pascalProgram, [
|
|||
|
(LexicalTokenType.Keyword, "program"),
|
|||
|
(LexicalTokenType.Identifier, "HelloWorld"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "var"),
|
|||
|
(LexicalTokenType.Identifier, "message"),
|
|||
|
(LexicalTokenType.Delimiter, ":"),
|
|||
|
(LexicalTokenType.Keyword, "char"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "begin"),
|
|||
|
(LexicalTokenType.Identifier, "message"),
|
|||
|
(LexicalTokenType.Operator, ":="),
|
|||
|
(LexicalTokenType.Character, "h"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Identifier, "writeln"),
|
|||
|
(LexicalTokenType.Delimiter, "("),
|
|||
|
(LexicalTokenType.Identifier, "message"),
|
|||
|
(LexicalTokenType.Delimiter, ")"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "end"),
|
|||
|
(LexicalTokenType.Delimiter, ".")
|
|||
|
]);
|
|||
|
}
|
|||
|
|
|||
|
[Fact]
|
|||
|
public void LexicalParserTest2()
|
|||
|
{
|
|||
|
const string program = """
|
|||
|
program main;
|
|||
|
var
|
|||
|
ab: integer;
|
|||
|
begin
|
|||
|
ab := 3;
|
|||
|
write(ab);
|
|||
|
end.
|
|||
|
""";
|
|||
|
|
|||
|
ValidateLexicalTokens(LexicalScanner.PascalParser(), program, [
|
|||
|
(LexicalTokenType.Keyword, "program"),
|
|||
|
(LexicalTokenType.Identifier, "main"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "var"),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Delimiter, ":"),
|
|||
|
(LexicalTokenType.Keyword, "integer"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "begin"),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Operator, ":="),
|
|||
|
(LexicalTokenType.ConstInteger, "3"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Identifier, "write"),
|
|||
|
(LexicalTokenType.Delimiter, "("),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Delimiter, ")"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "end"),
|
|||
|
(LexicalTokenType.Delimiter, ".")
|
|||
|
]);
|
|||
|
}
|
|||
|
|
|||
|
[Fact]
|
|||
|
public void LexicalParserTest3()
|
|||
|
{
|
|||
|
const string pascalProgram = """
|
|||
|
{test}
|
|||
|
program main;
|
|||
|
var
|
|||
|
ab, ba: integer;
|
|||
|
begin
|
|||
|
ab := 3;
|
|||
|
ba := 5;
|
|||
|
ab := 5;
|
|||
|
write(ab + ba);
|
|||
|
end.
|
|||
|
""";
|
|||
|
|
|||
|
ValidateLexicalTokens(LexicalScanner.PascalParser(), pascalProgram, [
|
|||
|
(LexicalTokenType.Keyword, "program"),
|
|||
|
(LexicalTokenType.Identifier, "main"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "var"),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Delimiter, ","),
|
|||
|
(LexicalTokenType.Identifier, "ba"),
|
|||
|
(LexicalTokenType.Delimiter, ":"),
|
|||
|
(LexicalTokenType.Keyword, "integer"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "begin"),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Operator, ":="),
|
|||
|
(LexicalTokenType.ConstInteger, "3"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Identifier, "ba"),
|
|||
|
(LexicalTokenType.Operator, ":="),
|
|||
|
(LexicalTokenType.ConstInteger, "5"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Operator, ":="),
|
|||
|
(LexicalTokenType.ConstInteger, "5"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Identifier, "write"),
|
|||
|
(LexicalTokenType.Delimiter, "("),
|
|||
|
(LexicalTokenType.Identifier, "ab"),
|
|||
|
(LexicalTokenType.Operator, "+"),
|
|||
|
(LexicalTokenType.Identifier, "ba"),
|
|||
|
(LexicalTokenType.Delimiter, ")"),
|
|||
|
(LexicalTokenType.Delimiter, ";"),
|
|||
|
(LexicalTokenType.Keyword, "end"),
|
|||
|
(LexicalTokenType.Delimiter, ".")
|
|||
|
]);
|
|||
|
}
|
|||
|
|
|||
|
[Theory]
|
|||
|
[InlineData("""
|
|||
|
program exFunction;
|
|||
|
var
|
|||
|
a, b, ret : integer;
|
|||
|
|
|||
|
begin
|
|||
|
a := 100;
|
|||
|
b := 200;
|
|||
|
{ calling a function to get max valued }
|
|||
|
ret := a - b;
|
|||
|
|
|||
|
|
|||
|
|
|||
|
end.
|
|||
|
""", 29)]
|
|||
|
[InlineData("""
|
|||
|
{
|
|||
|
This is a block comment that does closed.
|
|||
|
}
|
|||
|
program CommentClosed;
|
|||
|
""", 3)]
|
|||
|
[InlineData("""
|
|||
|
{}
|
|||
|
program CommentClosed;
|
|||
|
""", 3)]
|
|||
|
public void LexicalParserTest(string input, int count)
|
|||
|
{
|
|||
|
LexicalScanner scanner = new();
|
|||
|
|
|||
|
List<LexicalToken> tokens = scanner.Tokenize(new StringReadState(input)).ToList();
|
|||
|
Assert.Equal(count, tokens.Count);
|
|||
|
}
|
|||
|
}
|