| 41 #define __VARIABLES_CXX__ |
41 #define __VARIABLES_CXX__ |
| 42 #include <stdio.h> |
42 #include <stdio.h> |
| 43 #include <stdlib.h> |
43 #include <stdlib.h> |
| 44 #include <string.h> |
44 #include <string.h> |
| 45 #include "common.h" |
45 #include "common.h" |
| |
46 #include "array.h" |
| 46 #include "bots.h" |
47 #include "bots.h" |
| 47 #include "botcommands.h" |
48 #include "botcommands.h" |
| 48 #include "objwriter.h" |
49 #include "objwriter.h" |
| 49 #include "stringtable.h" |
50 #include "stringtable.h" |
| 50 #include "variables.h" |
51 #include "variables.h" |
| 51 #include "scriptreader.h" |
52 #include "scriptreader.h" |
| 52 |
53 |
| 53 ScriptVar* g_GlobalVariables[MAX_SCRIPT_VARIABLES]; |
54 array<ScriptVar> g_GlobalVariables; |
| 54 ScriptVar* g_LocalVariable; |
55 array<ScriptVar> g_LocalVariables; |
| 55 |
|
| 56 void InitVariables () { |
|
| 57 unsigned int u; |
|
| 58 ITERATE_GLOBAL_VARS (u) |
|
| 59 g_GlobalVariables[u] = NULL; |
|
| 60 } |
|
| 61 |
56 |
| 62 // ============================================================================ |
57 // ============================================================================ |
| 63 // Tries to declare a new global-scope variable. Returns pointer |
58 // Tries to declare a new global-scope variable. Returns pointer |
| 64 // to new global variable, NULL if declaration failed. |
59 // to new global variable, NULL if declaration failed. |
| 65 ScriptVar* DeclareGlobalVariable (ScriptReader* r, str name) { |
60 ScriptVar* DeclareGlobalVariable (ScriptReader* r, type_e type, str name) { |
| 66 // Check that the name is valid |
61 // Unfortunately the VM does not support string variables so yeah. |
| |
62 if (type == TYPE_STRING) |
| |
63 r->ParserError ("variables cannot be string\n"); |
| |
64 |
| |
65 // Check that the variable is valid |
| 67 if (FindCommand (name)) |
66 if (FindCommand (name)) |
| 68 r->ParserError ("name of variable-to-be `%s` conflicts with that of a command", name.chars()); |
67 r->ParserError ("name of variable-to-be `%s` conflicts with that of a command", name.chars()); |
| 69 |
68 |
| 70 if (IsKeyword (name)) |
69 if (IsKeyword (name)) |
| 71 r->ParserError ("name of variable-to-be `%s` is a keyword", name.chars()); |
70 r->ParserError ("name of variable-to-be `%s` is a keyword", name.chars()); |
| 72 |
71 |
| 73 // Find a NULL pointer to a global variable |
72 if (g_GlobalVariables.size() >= MAX_SCRIPT_VARIABLES) |
| 74 ScriptVar* g; |
|
| 75 unsigned int u = 0; |
|
| 76 ITERATE_GLOBAL_VARS (u) { |
|
| 77 // Check that it doesn't exist already |
|
| 78 if (!g_GlobalVariables[u]) |
|
| 79 break; |
|
| 80 |
|
| 81 if (!g_GlobalVariables[u]->name.icompare (name)) |
|
| 82 r->ParserError ("attempted redeclaration of variable `%s`", name.chars()); |
|
| 83 } |
|
| 84 |
|
| 85 if (u == MAX_SCRIPT_VARIABLES) |
|
| 86 r->ParserError ("too many global variables!"); |
73 r->ParserError ("too many global variables!"); |
| 87 |
74 |
| 88 g = new ScriptVar; |
75 for (uint i = 0; i < g_GlobalVariables.size(); i++) |
| 89 g->index = u; |
76 if (g_GlobalVariables[i].name == name) |
| 90 g->name = name; |
77 r->ParserError ("attempted redeclaration of global variable `%s`", name.chars()); |
| 91 g->statename = ""; |
|
| 92 g->next = NULL; |
|
| 93 g->value = 0; |
|
| 94 |
78 |
| 95 g_GlobalVariables[u] = g; |
79 ScriptVar g; |
| 96 return g; |
80 g.index = g_GlobalVariables.size(); |
| |
81 g.name = name; |
| |
82 g.statename = ""; |
| |
83 g.value = 0; |
| |
84 g.type = type; |
| |
85 |
| |
86 g_GlobalVariables << g; |
| |
87 return &g_GlobalVariables[g.index]; |
| 97 } |
88 } |
| 98 |
|
| 99 /* |
|
| 100 void AssignScriptVariable (ScriptReader* r, str name, str value) { |
|
| 101 ScriptVar* g = FindScriptVariable (name); |
|
| 102 if (!g) |
|
| 103 r->ParserError ("global variable %s not declared", name.chars()); |
|
| 104 } |
|
| 105 */ |
|
| 106 |
89 |
| 107 // ============================================================================ |
90 // ============================================================================ |
| 108 // Find a global variable by name |
91 // Find a global variable by name |
| 109 ScriptVar* FindGlobalVariable (str name) { |
92 ScriptVar* FindGlobalVariable (str name) { |
| 110 unsigned int u = 0; |
93 for (uint i = 0; i < g_GlobalVariables.size(); i++) { |
| 111 ITERATE_GLOBAL_VARS (u) { |
94 ScriptVar* g = &g_GlobalVariables[i]; |
| 112 ScriptVar* g = g_GlobalVariables[u]; |
95 if (g->name == name) |
| 113 if (!g) |
|
| 114 return NULL; |
|
| 115 |
|
| 116 if (!g->name.compare (name)) |
|
| 117 return g; |
96 return g; |
| 118 } |
97 } |
| 119 |
98 |
| 120 return NULL; |
99 return NULL; |
| 121 } |
100 } |
| 122 |
101 |
| 123 // ============================================================================ |
102 // ============================================================================ |
| 124 // Count all declared global variables |
103 // Count all declared global variables |
| 125 unsigned int CountGlobalVars () { |
104 uint CountGlobalVars () { |
| 126 unsigned int count = 0; |
105 return g_GlobalVariables.size(); |
| 127 unsigned int u = 0; |
|
| 128 ITERATE_GLOBAL_VARS (u) { |
|
| 129 if (g_GlobalVariables[u] != NULL) |
|
| 130 count++; |
|
| 131 } |
|
| 132 return count; |
|
| 133 } |
106 } |