BadScript 2
Loading...
Searching...
No Matches
BadFunction.cs
Go to the documentation of this file.
10
12
16public abstract class BadFunction : BadObject
17{
21 public static readonly BadClassPrototype Prototype = BadNativeClassBuilder.GetNative("Function");
22
26 private readonly Dictionary<int, BadObject> m_Cache = new Dictionary<int, BadObject>();
27
36 protected BadFunction(BadWordToken? name,
37 bool isConstant,
38 bool isStatic,
39 BadClassPrototype returnType,
40 bool isSingleLine,
41 params BadFunctionParameter[] parameters)
42 {
43 Name = name;
44 IsConstant = isConstant;
45 IsStatic = isStatic;
46 Parameters = parameters;
47 ReturnType = returnType;
48 IsSingleLine = isSingleLine;
49 }
50
55
59 public bool IsStatic { get; }
60
65
69 public bool IsConstant { get; }
70
81 public bool IsSingleLine { get; }
82
86 public BadWordToken? Name { get; }
87
92
95 {
96 return Prototype;
97 }
98
105 {
106 return this;
107 }
108
115 protected static BadObject GetParameter(BadObject[] args, int i)
116 {
117 return args.Length > i
118 ? args[i]
119 .Dereference(null)
120 : Null;
121 }
122
130 protected void CheckParameters(BadObject[] args, BadExecutionContext caller, BadSourcePosition? position = null)
131 {
132 for (int i = 0; i < Parameters.Length; i++)
133 {
134 BadFunctionParameter parameter = Parameters[i];
135
136 if (parameter.IsRestArgs)
137 {
138 //Do Nothing
139 }
140 else if (args.Length <= i)
141 {
142 if (!parameter.IsOptional)
143 {
144 throw BadRuntimeException.Create(caller.Scope,
145 $"Wrong number of parameters for '{this}'. Expected Argument for '{parameter}'",
146 position
147 );
148 }
149 }
150 else
151 {
152 if (parameter.IsNullChecked && args[i] == Null)
153 {
154 throw BadRuntimeException.Create(caller.Scope,
155 $"Null value not allowed for '{this}' parameter '{parameter}'",
156 position
157 );
158 }
159 }
160 }
161 }
162
172 public static void ApplyParameters(string funcStr,
173 BadFunctionParameter[] parameters,
174 BadExecutionContext context,
175 BadObject[] args,
176 BadSourcePosition? position = null)
177 {
178 for (int i = 0; i < parameters.Length; i++)
179 {
180 BadFunctionParameter parameter = parameters[i];
181
182 if (parameter.IsRestArgs)
183 {
184 context.Scope.DefineVariable(parameter.Name,
185 new BadArray(args.Skip(i)
186 .ToList()
187 ),
188 null,
190 );
191 }
192 else if (args.Length <= i)
193 {
194 if (parameter.IsOptional)
195 {
196 context.Scope.DefineVariable(parameter.Name,
197 Null,
198 null,
200 );
201 }
202 else
203 {
204 throw BadRuntimeException.Create(context.Scope,
205 $"Wrong number of parameters for '{funcStr}'. Expected Argument for '{parameter}'",
206 position
207 );
208 }
209 }
210 else
211 {
212 if (parameter.IsNullChecked && args[i] == Null)
213 {
214 throw BadRuntimeException.Create(context.Scope,
215 $"Null value not allowed for '{funcStr}' parameter '{parameter}'",
216 position
217 );
218 }
219
220 context.Scope.DefineVariable(parameter.Name,
221 args[i],
222 null,
224 );
225 }
226 }
227 }
228
236 public void ApplyParameters(BadExecutionContext context, BadObject[] args, BadSourcePosition? position = null)
237 {
238 ApplyParameters(ToString(), Parameters, context, args, position);
239 }
240
246 private static int? GetHash(IEnumerable<BadObject> args)
247 {
248 int hash = 0;
249
250 //Generate Hash from arguments
251 foreach (BadObject o in args)
252 {
253 if (o is not IBadNative native)
254 {
255 return null;
256 }
257
258 hash = hash == 0 ? native.Value.GetHashCode() : BadHashCode.Combine(hash, native.Value);
259 }
260
261 return hash;
262 }
263
270 public IEnumerable<BadObject> Invoke(BadObject[] args, BadExecutionContext caller)
271 {
272 if (IsConstant && BadNativeOptimizationSettings.Instance.UseConstantFunctionCaching)
273 {
274 int? hash = GetHash(args);
275
276 if (hash != null && m_Cache.TryGetValue(hash.Value, out BadObject? v))
277 {
278 BadLogger.Warn($"Found Cached value with Hash {hash}", "Runtime");
279
280 yield return v;
281
282 yield break;
283 }
284 }
285
286 BadObject? ret = null;
287
288 foreach (BadObject o in InvokeBlock(args, caller))
289 {
290 ret = o;
291
292 yield return o;
293 }
294
295 if (ret != null && !ReturnType.IsAssignableFrom(ret))
296 {
297 throw new
298 BadRuntimeException($"Invalid return type for function '{GetHeader()}'. Expected '{ReturnType.Name}' got '{ret.GetPrototype().Name}'"
299 );
300 }
301
302 if (!IsConstant ||
303 ret == null ||
304 !BadNativeOptimizationSettings.Instance.UseConstantFunctionCaching)
305 {
306 yield break;
307 }
308
309 {
310 int? hash = GetHash(args);
311
312 if (hash != null)
313 {
314 //BadLogger.Warn($"Caching Result {ret.ToSafeString()} for function '{GetHeader()}'", "Runtime");
315 m_Cache[hash.Value] = ret;
316 }
317 }
318 }
319
326 protected abstract IEnumerable<BadObject> InvokeBlock(BadObject[] args, BadExecutionContext caller);
327
328
333 public string GetHeader()
334 {
335 return GetHeader(Name?.ToString() ?? "<anonymous>", ReturnType, Parameters);
336 }
337
345 public static string GetHeader(string name,
346 BadClassPrototype returnType,
347 IEnumerable<BadFunctionParameter> parameters)
348 {
349 return $"{BadStaticKeys.FUNCTION_KEY} {returnType.Name} {name}({string.Join(", ", parameters.Cast<object>())})";
350 }
351
353 public override string ToSafeString(List<BadObject> done)
354 {
355 return GetHeader();
356 }
357}
Describes a specific position inside a source file.
Public facing interface for a logger.
Definition BadLogger.cs:7
static void Warn(string message)
Writes a Warning to the Message Handler.
Definition BadLogger.cs:56
Implements a Meta Data container for an expression.
static readonly BadMetaData Empty
An empty Meta Data object.
The Execution Context. Every execution of a script needs a context the script is running in....
BadScope Scope
The Root Scope of the Context.
Implements the Scope for the Script Engine.
Definition BadScope.cs:16
void DefineVariable(string name, BadObject value, BadScope? caller=null, BadPropertyInfo? info=null, BadObject[]? attributes=null)
Defines a new Variable in the current scope.
Definition BadScope.cs:784
static BadRuntimeException Create(BadScope? scope, string message)
Creates a new BadScriptException.
Implements a Dynamic List/Array for the BadScript Language.
Definition BadArray.cs:17
The Base Class for all BadScript Objects.
Definition BadObject.cs:14
override string ToString()
Returns a String Representation of this Object.
Definition BadObject.cs:224
static readonly BadObject Null
The Null Value for the BadScript Language.
Definition BadObject.cs:28
Stores Meta Information about a Property.
Implements a function that can be called from the script.
readonly Dictionary< int, BadObject > m_Cache
The Result Cache.
BadFunctionParameter[] Parameters
The Function Parameters.
virtual BadFunction BindParentScope(BadScope scope)
Returns an instance that is bound to the given scope.
bool IsSingleLine
Indicates if the function is a single line function(without block) Is used to determine the behaviour...
BadWordToken? Name
(optional) Name of the Function
IEnumerable< BadObject > InvokeBlock(BadObject[] args, BadExecutionContext caller)
Invokes the function with the specified arguments.
BadFunction(BadWordToken? name, bool isConstant, bool isStatic, BadClassPrototype returnType, bool isSingleLine, params BadFunctionParameter[] parameters)
Creates a new Function.
static readonly BadClassPrototype Prototype
The Prototype for the Function Object.
override string ToSafeString(List< BadObject > done)
static ? int GetHash(IEnumerable< BadObject > args)
Returns the Hash of the function arguments.
static void ApplyParameters(string funcStr, BadFunctionParameter[] parameters, BadExecutionContext context, BadObject[] args, BadSourcePosition? position=null)
Applies the function arguments to the context of the function.
IEnumerable< BadObject > Invoke(BadObject[] args, BadExecutionContext caller)
Invokes the function with the specified arguments.
static BadObject GetParameter(BadObject[] args, int i)
Returns the Function Parameter at the given index.
void ApplyParameters(BadExecutionContext context, BadObject[] args, BadSourcePosition? position=null)
Applies the function arguments to the context of the function.
string GetHeader()
Returns the Header of the function.
static string GetHeader(string name, BadClassPrototype returnType, IEnumerable< BadFunctionParameter > parameters)
Returns the Header of the function.
override BadClassPrototype GetPrototype()
void CheckParameters(BadObject[] args, BadExecutionContext caller, BadSourcePosition? position=null)
Checks Parameters for the given function call.
bool IsConstant
Indicates if the function has no side effects and the result can be cached.
bool IsStatic
Indicates if the Function is static.
virtual BadMetaData MetaData
The Metadata of the Function.
BadClassPrototype ReturnType
The Return Type of the Function.
bool IsOptional
Indicates if this parameter is optional.
BadClassPrototype? Type
The Class Prototype of the Parameter.
bool IsRestArgs
Indicates if this parameter is the rest parameter of the function.
bool IsNullChecked
Indicates if this parameter is null checked by the runtime.
The Any Prototype, Base type for all types.
static readonly BadAnyPrototype Instance
The Instance of the BadAnyPrototype.
Implements a Class Prototype for the BadScript Language.
virtual bool IsAssignableFrom(BadObject obj)
Returns true if the provided object is an instance of this class or a subclass of this class.
Helper Class that Builds a Native Class from a Prototype.
static BadClassPrototype GetNative(string name)
Returns a Native Class Prototype for the given Native Type.
static T Instance
Returns the Instance of the Settings Provider.
Implements Combination of HashCode Functions Taken from decompiled source of System....
Defines properties for Native Types.
Definition IBadNative.cs:7
Contains Logging system for the BadScript Runtime.
Definition BadLog.cs:6
Contains Shared Data Structures and Functionality.
Contains the Parser for the BadScript2 Language.
Contains the Reader Tokens for the BadScript2 Language.
Contains the Error Objects for the BadScript2 Language.
Contains Runtime Function Objects.
Contains the Native Runtime Objects.
Definition BadBoolean.cs:6
Contains Runtime Settings Objects.
Contains Utility Functions and Classes.
Definition BadEnum.cs:5