132 lines
4.0 KiB
C#
132 lines
4.0 KiB
C#
namespace Qrakhen.Qamp.Core.Execution;
|
|
|
|
public class SerializedEnumAttribute(Type serializedType) : Attribute
|
|
{
|
|
public Type SerializedType { get; } = serializedType;
|
|
}
|
|
|
|
/// <summary>
|
|
///
|
|
/// </summary>
|
|
/// <remarks>
|
|
/// In order to keep instruction files small, all op codes are crammed into 8 bits,
|
|
/// and operation flags aren't flags, but rather should be seen as IDs (the first 4 bits)
|
|
/// and the operation itself is a number made from the last 4 bits.
|
|
/// & 0b11110000 => Handler
|
|
/// & 0b00001111 => Operation
|
|
/// </remarks>
|
|
[SerializedEnum(typeof(byte))]
|
|
public enum OpCode
|
|
{
|
|
/// <summary>
|
|
/// Mask bits, to be used like <c>opCode & F_Mask == F_Operation</c>, for example.
|
|
/// </summary>
|
|
Mask_Handler = 0xF0,
|
|
Mask_Operation = 0x0F,
|
|
|
|
Error = -1,
|
|
Void = 0,
|
|
|
|
F_Static = 0x10,
|
|
None = F_Static | 1,
|
|
True = F_Static | 2,
|
|
False = F_Static | 3,
|
|
Constant = F_Static | 4,
|
|
Null = F_Static | 5,
|
|
Cast = F_Static | 6,
|
|
|
|
Pop = F_Static | 7,
|
|
|
|
F_Retrieve = 0x20,
|
|
Val = F_Retrieve | 1,
|
|
Ref = F_Retrieve | 2,
|
|
Addr = F_Retrieve | 3,
|
|
|
|
F_Names = 0x30,
|
|
SetGlobal = F_Names | 1,
|
|
GetGlobal = F_Names | 2,
|
|
GetLocal = F_Names | 3,
|
|
SetLocal = F_Names | 4,
|
|
GetOuter = F_Names | 5,
|
|
SetOuter = F_Names | 6,
|
|
GetMember = F_Names | 7,
|
|
SetMember = F_Names | 8,
|
|
DefineGlobal = F_Names | 9,
|
|
CloseOuter = F_Names | 10,
|
|
|
|
//AssignValue = 0x0, // unsure
|
|
//AssignReference = 0x0, // unsure
|
|
|
|
F_Arithmetic = 0x40,
|
|
Add = F_Arithmetic | 1,
|
|
Subtract = F_Arithmetic | 2,
|
|
Multiply = F_Arithmetic | 3,
|
|
Pow = F_Arithmetic | 4,
|
|
Divide = F_Arithmetic | 5,
|
|
Modulo = F_Arithmetic | 6,
|
|
Negate = F_Arithmetic | 7,
|
|
|
|
F_Bitwise = 0x50,
|
|
BitwiseAnd = F_Bitwise | 1,
|
|
BitwiseOr = F_Bitwise | 2,
|
|
BitwiseXor = F_Bitwise | 3,
|
|
BitwiseLeft = F_Bitwise | 4,
|
|
BitwiseRight = F_Bitwise | 5,
|
|
BitwiseNot = F_Bitwise | 6,
|
|
|
|
F_Boolean = 0x60,
|
|
Not = F_Boolean | 1,
|
|
Equal = F_Boolean | 2,
|
|
Greater = F_Boolean | 3,
|
|
Less = F_Boolean | 4,
|
|
|
|
F_Collection = 0x70,
|
|
Array = F_Collection | 1,
|
|
List = F_Collection | 2,
|
|
Structure = F_Collection | 3,
|
|
GetItem = F_Collection | 4,
|
|
SetItem = F_Collection | 5,
|
|
AddItem = F_Collection | 6,
|
|
RemoveItem = F_Collection | 7,
|
|
|
|
F_Control = 0x80,
|
|
Return = F_Control | 1,
|
|
Jump = F_Control | 2,
|
|
JumpIfFalse = F_Control | 3,
|
|
Loop = F_Control | 4,
|
|
Invoke = F_Control | 5,
|
|
InvokeBase = F_Control | 6,
|
|
InvokeMember = F_Control | 7,
|
|
Context = F_Control | 8,
|
|
|
|
F_Class = 0x90,
|
|
Class = F_Class | 1,
|
|
Member = F_Class | 2,
|
|
Base = F_Class | 3,
|
|
Inherit = F_Class | 4,
|
|
Method = F_Class | 5,
|
|
Static = F_Class | 6,
|
|
|
|
F_Meta = 0xa0,
|
|
Print = F_Meta | 1,
|
|
PrintStack = F_Meta | 2,
|
|
PrintGlobals = F_Meta | 3,
|
|
PrintExpr = F_Meta | 4,
|
|
Typeof = F_Meta | 5,
|
|
|
|
F_Module = 0xf0,
|
|
Export = F_Module | 1, // probably shouldnt be an op code but rather be done during digestion
|
|
Import = F_Module | 2, // probably shouldnt be an op code but rather be done during digestion
|
|
}
|
|
|
|
public static class OpCodeExtensions
|
|
{
|
|
public static bool IsUnary(this OpCode op)
|
|
=> op is OpCode.Not or OpCode.Negate or OpCode.BitwiseNot;
|
|
|
|
public static bool IsHandledByAlu(this OpCode op)
|
|
=> (op & OpCode.Mask_Handler) is OpCode.F_Arithmetic or OpCode.F_Bitwise or OpCode.F_Boolean;
|
|
|
|
public static string ToString(this OpCode op)
|
|
=> $"{op & OpCode.Mask_Handler}: {op} ({(byte)op:x2})";
|
|
} |