diff --git a/SlipCompiler.py b/SlipCompiler.py new file mode 100644 index 0000000..3f346fb --- /dev/null +++ b/SlipCompiler.py @@ -0,0 +1,98 @@ +instruction_opcodes = { + "IDK": 0x00, + "LIT": 0x01, + "SWAP": 0x02, + "DEL": 0x03, + "COPY": 0x04, + "DEF": 0x05, + "END": 0x06, + "ADD": 0x10, + "SUB": 0x11, + "MUL": 0x12, + "DIV": 0x13, + "POW": 0x14, + "SQRT": 0x15, + "ONEMIN": 0x16, + "ROUND": 0x17, + "CEIL": 0x18, + "FLOOR": 0x19, + "MOD": 0x1a, + "FRACT": 0x1b, + "COMP": 0x1c, + "LERP": 0x1d, + "MIN": 0x1e, + "MAX": 0x1f +} + +type_opcodes = { + "BOOL": {"code": 0x00, "length": 1}, + "INT": {"code": 0x01, "length": 4}, + "FLT": {"code": 0x02, "length": 4}, + "VEC": {"code": 0x03, "length": 12} +} + +source_file = open("Test.slc") +source_code = source_file.read() +source_code = source_code.replace(" ", "\n") +source_code = source_code.split("\n") + +import struct + +byte_code = bytearray() +code_type = "" +lit_type = "" +for word in source_code: + print(f"\nIn: \"{word}\"") + # Handle literal types + if code_type == "lit_type": + print("Consuming literal type...") + print("Expecting next input to be a literal value.") + + # Consume a literal of this word's type next + code_type = "literal" + lit_type = word + + # Push the type opcode onto the instruction stack + opcode = type_opcodes[word]["code"] + byte_code.append(opcode) + print(f"Out: {hex(opcode)}") + continue + # Handle literal values + if code_type == "literal": + print("Consuming literal value...") + + # Consume a generic command next + code_type = "" + + # Handle float literals + if lit_type == "FLT": + lit_bytes = bytearray(struct.pack(">f", float(word))) + byte_code.extend(lit_bytes) + print(f"Out: 0x{bytes(lit_bytes).hex()}") + # Handle vector literals + if lit_type == "VEC": + # Creates an array of floats from a string like "-1.0,7.3,10.5" + vector_components = word.split(",") + lit_bytes = bytearray() + for component in vector_components: + component_bytes = bytearray(struct.pack(">f", float(component))) + lit_bytes.extend(component_bytes) + byte_code.extend(lit_bytes) + print(f"Out: 0x{bytes(lit_bytes).hex()}") + continue + # Handle generic commands + else: + print("Consuming generic command...") + if word == "LIT": + print("Expecting next input to be a literal type.") + code_type = "lit_type" + opcode = instruction_opcodes[word] + byte_code.append(opcode) + print(f"Out: {hex(opcode)}") + continue + +pure_bytes = bytes(byte_code) +with open("Test.slb", "wb") as binary_file: + binary_file.write(pure_bytes) + +print("\nWrote binary file to disk!") \ No newline at end of file diff --git a/SlipcodeCompilationTest.ipynb b/SlipcodeCompilationTest.ipynb index 25abc12..c173c5e 100644 --- a/SlipcodeCompilationTest.ipynb +++ b/SlipcodeCompilationTest.ipynb @@ -2,11 +2,11 @@ "cells": [ { "cell_type": "code", - "execution_count": 71, + "execution_count": 4, "metadata": {}, "outputs": [], "source": [ - "opcodes = {\n", + "instruction_opcodes = {\n", " \"IDK\": 0x00,\n", " \"LIT\": 0x01,\n", " \"SWAP\": 0x02,\n", @@ -30,12 +30,19 @@ " \"LERP\": 0x1d,\n", " \"MIN\": 0x1e,\n", " \"MAX\": 0x1f\n", + "}\n", + "\n", + "type_opcodes = {\n", + " \"BOOL\": {\"code\": 0x00, \"length\": 1},\n", + " \"INT\": {\"code\": 0x01, \"length\": 4},\n", + " \"FLT\": {\"code\": 0x02, \"length\": 4},\n", + " \"VEC\": {\"code\": 0x03, \"length\": 12}\n", "}" ] }, { "cell_type": "code", - "execution_count": 72, + "execution_count": 5, "metadata": {}, "outputs": [], "source": [ @@ -47,27 +54,32 @@ }, { "cell_type": "code", - "execution_count": 74, + "execution_count": 6, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ - "1\n", - "1\n", - "2\n", - "16\n", - "4\n", - "16\n", - "4\n", - "25\n", - "17\n", - "1\n", - "17\n", - "25\n", - "1\n", - "18\n" + "LIT, \n", + "Parsing generic command...\n", + "FLT, lit_type\n", + "Parsing literal type...\n", + "-1.0, literal\n", + "Parsing literal value...\n", + "LIT, literal\n", + "Parsing literal value...\n" + ] + }, + { + "ename": "ValueError", + "evalue": "could not convert string to float: 'LIT'", + "output_type": "error", + "traceback": [ + "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", + "\u001b[1;31mValueError\u001b[0m Traceback (most recent call last)", + "\u001b[1;32m~\\AppData\\Local\\Temp/ipykernel_20464/1959865281.py\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 23\u001b[0m \u001b[1;31m# Handle float literals\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 24\u001b[0m \u001b[1;32mif\u001b[0m \u001b[0mlit_type\u001b[0m \u001b[1;33m==\u001b[0m \u001b[1;34m\"FLT\"\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 25\u001b[1;33m \u001b[0mlit_bytes\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mbytearray\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mstruct\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mpack\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\">f\"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mfloat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mword\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 26\u001b[0m \u001b[0mbyte_code\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mextend\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mlit_bytes\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 27\u001b[0m \u001b[1;31m# Handle vector literals\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", + "\u001b[1;31mValueError\u001b[0m: could not convert string to float: 'LIT'" ] } ], @@ -75,18 +87,47 @@ "import struct\n", "\n", "byte_code = bytearray()\n", - "is_literal = False\n", - "for line in source_code:\n", - " if is_literal:\n", - " lit_bytes = bytearray(struct.pack(\">f\", float(line)))\n", - " byte_code.extend(lit_bytes)\n", - " is_literal = False\n", + "code_type = \"\"\n", + "lit_type = \"\"\n", + "for word in source_code:\n", + " print(f\"{word}, {code_type}\")\n", + " # Handle literal types\n", + " if code_type == \"lit_type\":\n", + " print(\"Parsing literal type...\")\n", + "\n", + " # Consume a literal of this word's type next\n", + " code_type = \"literal\"\n", + " lit_type = word\n", + "\n", + " # Push the type opcode onto the instruction stack\n", + " byte_code.append(type_opcodes[word][\"code\"])\n", + " continue\n", + " # Handle literal values\n", + " if code_type == \"literal\":\n", + " print(\"Parsing literal value...\")\n", + "\n", + " # Consume a generic command next\n", + " code_type = \"\"\n", + "\n", + " # Handle float literals\n", + " if lit_type == \"FLT\":\n", + " lit_bytes = bytearray(struct.pack(\">f\", float(word)))\n", + " byte_code.extend(lit_bytes)\n", + " # Handle vector literals\n", + " if lit_type == \"VEC\":\n", + " # Creates an array of floats from a string like \"-1.0,7.3,10.5\"\n", + " vector_components = word.split(\",\")\n", + " for component in vector_components:\n", + " lit_bytes = bytearray(struct.pack(\">f\", float(component)))\n", + " byte_code.extend(lit_bytes)\n", + " continue\n", + " # Handle generic commands\n", " else:\n", - " if line == \"LIT\":\n", - " is_literal = True\n", - " instruction = opcodes[line]\n", - " print(instruction)\n", - " byte_code.append(instruction)\n", + " print(\"Parsing generic command...\")\n", + " if word == \"LIT\":\n", + " code_type = \"lit_type\"\n", + " byte_code.append(instruction_opcodes[word])\n", + " continue\n", "\n", "pure_bytes = bytes(byte_code)\n", "with open(\"Test.slb\", \"wb\") as binary_file:\n", @@ -113,7 +154,7 @@ "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", - "version": "3.8.8" + "version": "3.7.8" }, "orig_nbformat": 4 }, diff --git a/Test.slb b/Test.slb index 37d9a5a..0ab680b 100644 Binary files a/Test.slb and b/Test.slb differ diff --git a/Test.slc b/Test.slc index fc626a7..7466c3e 100644 --- a/Test.slc +++ b/Test.slc @@ -1,5 +1,5 @@ -LIT -1.0 -LIT 57.33 +LIT FLT -1.0 +LIT FLT 57.33 SWAP ADD COPY @@ -7,8 +7,9 @@ ADD COPY FLOOR SUB -LIT 100.0 +LIT FLT 100.0 SUB FLOOR -LIT -0.97 -MUL \ No newline at end of file +LIT FLT -0.97 +MUL +LIT VEC 1.0,1.0,1.0 \ No newline at end of file