[BUG] Disallow decimals on array decl and indices
[FEAT] Parser checks index out of bounds errors
This commit is contained in:
41
parser.cpp
41
parser.cpp
@@ -289,7 +289,9 @@ static int get_variable_address() {
|
|||||||
if (var_length > 1) {
|
if (var_length > 1) {
|
||||||
tkn_next(); EXPECT2(TOKEN_LBRACKET, "Expected '['");
|
tkn_next(); EXPECT2(TOKEN_LBRACKET, "Expected '['");
|
||||||
tkn_next(); EXPECT2(TOKEN_NUMBER, "Expected number");
|
tkn_next(); EXPECT2(TOKEN_NUMBER, "Expected number");
|
||||||
const float index = tkn_get_value();
|
const int index = (int)tkn_get_value();
|
||||||
|
if (tkn_get_value() > index) HALT2("Expected integer value");
|
||||||
|
if (index >= var_length) HALT2("Index out of bounds");
|
||||||
tkn_next(); EXPECT2(TOKEN_RBRACKET, "Expected ']'");
|
tkn_next(); EXPECT2(TOKEN_RBRACKET, "Expected ']'");
|
||||||
address += index * types_get_length(var_type);
|
address += index * types_get_length(var_type);
|
||||||
}
|
}
|
||||||
@@ -330,28 +332,6 @@ static void parse_expr_atom() {
|
|||||||
parser_finished = true; error_raise("Unknown identifier");
|
parser_finished = true; error_raise("Unknown identifier");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// XXX [RZC 27/04/2021] Per ara llevem les constants
|
|
||||||
/*int constvalue = get_constant(tkn_get_string());
|
|
||||||
if (constvalue != -1) {
|
|
||||||
emmit(OP_PUSH);
|
|
||||||
emmit(constvalue);
|
|
||||||
tkn_next();
|
|
||||||
return;
|
|
||||||
}*/
|
|
||||||
|
|
||||||
// XXX [RZC 27/04/2021] Per ara llevem les variables
|
|
||||||
/*int ivar = get_variable_index(tkn_get_string());
|
|
||||||
if (is_variable_array()) {
|
|
||||||
tkn_next(); EXPECT(TOKEN_LPAR, "Expected array index");
|
|
||||||
tkn_next(); parse_expr_atom();
|
|
||||||
EXPECT(TOKEN_RPAR, "Expected ')'");
|
|
||||||
emmit(OP_SETY);
|
|
||||||
emmit(OP_LOADI);
|
|
||||||
emmit_w(ivar);
|
|
||||||
} else {
|
|
||||||
emmit(OP_LOAD);
|
|
||||||
emmit_w(ivar);
|
|
||||||
}*/
|
|
||||||
}
|
}
|
||||||
if (tkn_get_token() == TOKEN_MINUS) {
|
if (tkn_get_token() == TOKEN_MINUS) {
|
||||||
tkn_next();
|
tkn_next();
|
||||||
@@ -372,14 +352,6 @@ static void parse_expr_atom() {
|
|||||||
tkn_next();
|
tkn_next();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// XXX [RZC 27/04/2021] No usat en JailBasic, pero hi haurà que afegir les funcions
|
|
||||||
/*
|
|
||||||
if (tkn_get_token() == TOKEN_STRLEN) { tkn_next(); parse_strlen(); return; }
|
|
||||||
if (tkn_get_token() == TOKEN_KEYPRESSED) { tkn_next(); parse_keypressed(); return; }
|
|
||||||
if (tkn_get_token() == TOKEN_ANYKEY) { tkn_next(); parse_anykey(); return; }
|
|
||||||
if (tkn_get_token() == TOKEN_GETCHAR) { tkn_next(); parse_getchar(); return; }
|
|
||||||
if (tkn_get_token() == TOKEN_GETCOLOR) { tkn_next(); parse_getcolor(); return; }
|
|
||||||
*/
|
|
||||||
parser_finished = true; error_raise("Syntax error");
|
parser_finished = true; error_raise("Syntax error");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@@ -465,7 +437,6 @@ static void parse_const() {
|
|||||||
const int var_address = scope_declare_variable(const_name, type_num, 0);
|
const int var_address = scope_declare_variable(const_name, type_num, 0);
|
||||||
emmit(scope_is_local() ? OP_STL : OP_ST);
|
emmit(scope_is_local() ? OP_STL : OP_ST);
|
||||||
emmit_dw(var_address);
|
emmit_dw(var_address);
|
||||||
//tkn_next();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void parse_var() {
|
static void parse_var() {
|
||||||
@@ -477,8 +448,10 @@ static void parse_var() {
|
|||||||
tkn_next();
|
tkn_next();
|
||||||
if (tkn_get_token() == TOKEN_ARRAY) {
|
if (tkn_get_token() == TOKEN_ARRAY) {
|
||||||
tkn_next(); EXPECT(TOKEN_OF, "Expected 'of'");
|
tkn_next(); EXPECT(TOKEN_OF, "Expected 'of'");
|
||||||
tkn_next(); EXPECT(TOKEN_NUMBER, "Expected number"); // TODO [RZC 04/05/2021] Només deuria acceptar enters.
|
tkn_next(); EXPECT(TOKEN_NUMBER, "Expected number");
|
||||||
var_length = tkn_get_value();
|
const float length = tkn_get_value();
|
||||||
|
var_length = (int)length;
|
||||||
|
if (length > var_length) HALT("Expected integer value");
|
||||||
tkn_next();
|
tkn_next();
|
||||||
}
|
}
|
||||||
EXPECT(TOKEN_IDENTIFIER, "Expected type identifier");
|
EXPECT(TOKEN_IDENTIFIER, "Expected type identifier");
|
||||||
|
|||||||
2
test.vb
2
test.vb
@@ -11,4 +11,4 @@ struct triangle
|
|||||||
end
|
end
|
||||||
|
|
||||||
var peiv as array of 2 triangle
|
var peiv as array of 2 triangle
|
||||||
const perico as number = 4-peiv[0].a.x
|
const perico as number = 4-peiv[1].a.x
|
||||||
|
|||||||
@@ -1,5 +1,6 @@
|
|||||||
#include "tokenizer.h"
|
#include "tokenizer.h"
|
||||||
#include "error.h"
|
#include "error.h"
|
||||||
|
#include <string>
|
||||||
|
|
||||||
static bool streq(const char* a, const char* b) {
|
static bool streq(const char* a, const char* b) {
|
||||||
while (*a != 0 && *b != 0) {
|
while (*a != 0 && *b != 0) {
|
||||||
@@ -79,8 +80,8 @@ static void tkn_do_next() {
|
|||||||
if (CCHR >= 48 && CCHR <= 57) {
|
if (CCHR >= 48 && CCHR <= 57) {
|
||||||
do { value = value * 10 + (CCHR - 48); NEXT; } while (CCHR >= 48 && CCHR <= 57);
|
do { value = value * 10 + (CCHR - 48); NEXT; } while (CCHR >= 48 && CCHR <= 57);
|
||||||
if (CCHR == '.') {
|
if (CCHR == '.') {
|
||||||
int d = 10;
|
float d = 0.1f; NEXT;
|
||||||
do { value = value + ((CCHR - 48) / d); d *= 10; NEXT; } while (CCHR >= 48 && CCHR <= 57);
|
do { value = value + (float(CCHR - 48) * d); d *= 0.1f; NEXT; } while (CCHR >= 48 && CCHR <= 57);
|
||||||
}
|
}
|
||||||
current_token = TOKEN_NUMBER; return;
|
current_token = TOKEN_NUMBER; return;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user